基于Vue实现图片在指定区域内移动的思路详解


Posted in Javascript onNovember 11, 2018

  当图片比要显示的区域大时,需要将多余的部分隐藏掉,我们可以通过绝对定位来实现,并通过动态修改图片的left值和top值从而实现图片的移动。具体实现效果如下图,如果我们移动的是div 实现思路相仿。

基于Vue实现图片在指定区域内移动的思路详解

此处需要注意的是

我们在移动图片时,需要通过draggable="false" 将图片的 <img src="/static/pano-dev/test/image-2.jpg" draggable="false" />,否则按下鼠标监听onmousemove事件时监听不到

然后还需要禁用图片的选中css

/*禁止元素选中*/
-moz-user-select: none; /*火狐*/
-webkit-user-select: none; /*webkit浏览器*/
-ms-user-select: none; /*IE10*/
-khtml-user-select: none; /*早期浏览器*/
user-select: none;

Vue 代码

<style lang="less" scoped>
@import url("./test.less");
</style>
<template>
 <div class="page">
  <div class="image-move-wapper">
   <div class="image-show-box" ref="imageShowBox">
    <div class="drag-container" ref="dragContainer" :style="'left:' + dragContainer.newPoint.left+'px; top:' + dragContainer.newPoint.top+'px'" @mousedown="DragContainerMouseDown">
     <div class="drag-image-box">
      <img src="/static/pano-dev/test/image-2.jpg" draggable="false" />
      <div class="point" style="left:10%; top:10%" @mousedown="PointMouseDown"></div>
     </div>
    </div>
   </div>
  </div>
 </div>
</template>
<script>
export default {
 data() {
  return {
   dragContainer: {
    box: {
     w: 0,
     h: 0
    },
    point: {
     left: 0,
     top: 0
    },
    newPoint: {
     left: 0,
     top: 0
    }
   },
   mousePoint: {
    x: 0,
    y: 0
   },
   imageShowBox: {
    box: {
     w: 0,
     h: 0
    },
    dragcheck: {
     h: true,
     v: true
    }
   }
  };
 },
 updated() {
  let _this = this;
  // 确保DOM元素已经渲染成功,然后获取拖拽容器和显示区域的大小
  _this.$nextTick(function() {
   _this.dragContainer.box = {
    w: _this.$refs.dragContainer.offsetWidth,
    h: _this.$refs.dragContainer.offsetHeight
   };
   _this.imageShowBox.box = {
    w: _this.$refs.imageShowBox.offsetWidth,
    h: _this.$refs.imageShowBox.offsetHeight
   };
   // 判断是否允许拖拽
   _this.imageShowBox.dragcheck = {
    h: _this.imageShowBox.box.w > _this.dragContainer.box.w ? false : true,
    v: _this.imageShowBox.box.h > _this.dragContainer.box.h ? false : true
   };
  });
 },
 methods: {
  // 鼠标在拖拽容器中按下时触发
  DragContainerMouseDown(e) {
   const _this = this;
   // 记录鼠标点击时的初始坐标
   this.mousePoint = {
    x: e.clientX,
    y: e.clientY
   };
   _this.dragContainer.point = _this.dragContainer.newPoint;
   document.body.onmousemove = _this.DragContainerMouseMove;
   document.onmouseup = _this.DragContainerMouseUp;
   return false;
  },
  // 容器拖拽时触发
  DragContainerMouseMove(e) {
   const _this = this;
   // 鼠标偏移量 = 初始坐标 - 当前坐标
   let dx = e.clientX - _this.mousePoint.x;
   let dy = e.clientY - _this.mousePoint.y;
   // 获取拖拽容器移动后的left和top值
   if (_this.imageShowBox.dragcheck.h)
    var newx = dx > 0 ? Math.min(0, _this.dragContainer.point.left + dx) : Math.max(- _this.dragContainer.box.w + _this.imageShowBox.box.w, _this.dragContainer.point.left + dx );
   if (_this.imageShowBox.dragcheck.v)
    var newy = dy > 0 ? Math.min(0, _this.dragContainer.point.top + dy) : Math.max(- _this.dragContainer.box.h + _this.imageShowBox.box.h, _this.dragContainer.point.top + dy );
   _this.dragContainer.newPoint = {
    left: typeof newx != 'undefined' ? newx : _this.dragContainer.point.left,
    top: typeof newy != 'undefined' ? newy : _this.dragContainer.point.top
   };
   console.log(_this.dragContainer.newPoint);
   return false;
  },
  // 移动完成 取消onmousemove和onmouseup事件
  DragContainerMouseUp(e) {
   document.body.onmousemove = null;
   document.onmouseup = null;
  },
  PointMouseDown(e) {
   //阻止事件冒泡
   e.stopPropagation();
  }
 }
};
</script>

样式表

.page {
 background: #444;
 width: 100%;
 height: 100%;
 position: relative;
 .image-move-wapper {
  position: absolute;
  right: 50px;
  top: 50px;
  background: #fff;
  box-shadow: rgba(255, 255, 255, 0.5);
  padding: 10px;
 }
 .image-show-box {
  height: 400px;
  width: 400px;
  cursor: move;
  overflow: hidden;
  position: relative;
  .drag-container {
   position: absolute;
   left: 0px;
   top: 0;
   /*禁止元素选中*/
   -moz-user-select: none; /*火狐*/
   -webkit-user-select: none; /*webkit浏览器*/
   -ms-user-select: none; /*IE10*/
   -khtml-user-select: none; /*早期浏览器*/
   user-select: none;
   .drag-image-box {
    position: relative;
    .point {
     position: absolute;
     background: red;
     height: 30px;
     width: 30px;
     border-radius: 50%;
    }
   }
  }
 }
}

总结

以上所述是小编给大家介绍的基于Vue实现图片在指定区域内移动的思路详解,希望对大家有所帮助,如果大家有任何疑问欢迎给我留言,小编会及时回复大家的!

Javascript 相关文章推荐
Jquery实现的一种常用高亮效果示例代码
Jan 28 Javascript
简介JavaScript中POSITIVE_INFINITY值的使用
Jun 05 Javascript
JavaScript实现瀑布流布局
Jun 28 Javascript
深入理解jquery跨域请求方法
May 18 Javascript
jquery鼠标悬停导航下划线滑出效果
Sep 29 jQuery
Vue官网todoMVC示例代码
Jan 29 Javascript
基于Vuejs的搜索匹配功能实现方法
Mar 03 Javascript
为什么使用koa2搭建微信第三方公众平台的原因
May 16 Javascript
Vue2.X 通过AJAX动态更新数据
Jul 17 Javascript
vuex2中使用mapGetters/mapActions报错的解决方法
Oct 20 Javascript
在Express中提供静态文件的实现方法
Oct 17 Javascript
基于Vue CSR的微前端实现方案实践
May 27 Javascript
微信小程序车牌号码模拟键盘输入功能的实现代码
Nov 11 #Javascript
详解Vue 动态组件与全局事件绑定总结
Nov 11 #Javascript
详解如何在vue项目中使用eslint+prettier格式化代码
Nov 10 #Javascript
AngularJS上传文件的示例代码
Nov 10 #Javascript
详解vue-cli 3.0 build包太大导致首屏过长的解决方案
Nov 10 #Javascript
优雅的在React项目中使用Redux的方法
Nov 10 #Javascript
Vue组件之单向数据流的解决方法
Nov 10 #Javascript
You might like
15个小时----从修改程序到自己些程序
2006/10/09 PHP
PHP session有效期session.gc_maxlifetime
2011/04/20 PHP
PHP屏蔽过滤指定关键字的方法
2014/11/03 PHP
php使用mysqli向数据库添加数据的方法
2015/03/20 PHP
Zend Framework实现留言本分页功能(附demo源码下载)
2016/03/22 PHP
PHP/HTML混写的四种方式总结
2017/02/27 PHP
JS的IE和Firefox兼容性集锦
2006/12/11 Javascript
jQuery中$.each()函数的用法引申实例
2016/05/12 Javascript
Bootstrap选项卡与Masonry插件的完美结合
2016/07/06 Javascript
用JS中split方法实现彩色文字背景效果实例
2016/08/24 Javascript
bootstrap paginator分页前后台用法示例
2017/06/17 Javascript
js实现的格式化数字和金额功能简单示例
2019/07/30 Javascript
使用 Vue 实现一个虚拟列表的方法
2019/08/20 Javascript
如何解决日期函数new Date()浏览器兼容性问题
2019/09/11 Javascript
vue 路由子组件created和mounted不起作用的解决方法
2019/11/05 Javascript
JS实现分页导航效果
2020/02/19 Javascript
用JS实现选项卡
2020/03/23 Javascript
javascript实现简易计算器功能
2020/09/23 Javascript
python不带重复的全排列代码
2013/08/13 Python
python 字典(dict)遍历的四种方法性能测试报告
2014/06/25 Python
python实现获取序列中最小的几个元素
2014/09/25 Python
python+selenium实现登录账户后自动点击的示例
2017/12/22 Python
python实现百万答题自动百度搜索答案
2018/01/16 Python
TensorFlow入门使用 tf.train.Saver()保存模型
2018/04/24 Python
对pycharm 修改程序运行所需内存详解
2018/12/03 Python
python实现数据清洗(缺失值与异常值处理)
2019/12/02 Python
Python之Django自动实现html代码(下拉框,数据选择)
2020/03/13 Python
Python猫眼电影最近上映的电影票房信息
2020/09/18 Python
美国名牌太阳镜折扣网站:Eyedictive
2017/05/15 全球购物
前台接待员岗位职责
2014/01/02 职场文书
浙江文明网签名寄语
2014/01/18 职场文书
机关搬迁方案
2014/05/18 职场文书
大学生考试作弊被抓检讨书
2014/12/27 职场文书
中考学习决心书
2015/02/04 职场文书
用Python远程登陆服务器的步骤
2021/04/16 Python
Django模型层实现多表关系创建和多表操作
2021/07/21 Python