vue+mousemove实现鼠标拖动功能(拖动过快失效问题解决方法)


Posted in Javascript onAugust 24, 2018

今天用vue+原生js的mousemove事件,写了个拖动,发现只能慢慢拖动才行,鼠标只要移动快了,就失效,不能拖动了;

搞了半天在,总算解决了,但是问题的深层原理还没搞清楚,知道的大侠可以留言分享,下面直接上代码:

只能慢速拖动的代码:

<!DOCTYPE html>
<html>
<head>
 <title>vue结合原生js实现拖动</title>
<script src="https://cdn.bootcss.com/vue/2.4.2/vue.min.js"></script>
</head>
<body>
<div id="app">
<div class="ctn ctn1">
 <div class="sub sub1" v-for="(site, index) in list1">
   <div class="dragCtn fixed" @mousedown="mousedown(site, $event)" @mousemove.prevent='mousemove(site, $event)' @mouseup='mouseup(site, $event)'>
   {{ site.name }}
   </div>
 </div>
</div>
<div class="ctn ctn2">
 <div class="sub sub2" v-for="(site, index) in list2">
   <div class="dragCtn">
    {{ index }} : {{ site.name }}
   </div>
 </div> 
</div> 
</div>
<script>
new Vue({
 el: '#app',
 data: {
 list1: [{name:'拖动我', index:0}],
 list2: [{name:'a', index:0}, {name:'b', index:1}, {name:'c', index: 2}, {name:'d', index: 3}],
 vm:'',
 sb_bkx: 0,
 sb_bky: 0,
 is_moving: false
 },
 methods: {
  mousedown: function (site, event) {
  var startx=event.x;
  var starty=event.y;
  this.sb_bkx=startx - event.target.offsetLeft;
  this.sb_bky=starty - event.target.offsetTop;
  this.is_moving = true;
  },
  mousemove: function (site, event) {
   var endx=event.x - this.sb_bkx;
  var endy=event.y - this.sb_bky;
  var _this = this
  if(this.is_moving){
   event.target.style.left=endx+'px';
   event.target.style.top=endy+'px';
  }
  },
  mouseup: function (e) {
  this.is_moving = false;
  }
 }
})
</script>
<style>
 .ctn{
  line-height: 50px;
  cursor: pointer;
  font-size: 20px;
  text-align: center;
  float: left;
 }
 .sub:hover{
  background: #e6dcdc;
  color: white;
  width: 100px;
 }
  .ctn1{
   border: 1px solid green;
   width: 100px;
  }
  .ctn2{
   border: 1px solid black;
   width: 100px;
   margin-left: 50px;
  }
  .fixed{
   width: 100px;
   height: 100px;
  position: fixed;
  background: red;
  left: 10px;
  top: 10px;
  cursor: move;
  }
</style>
</body>
</html>

可以快速拖动的代码:

<!DOCTYPE html>
<html>
<head>
 <title>vue结合原生js实现拖动</title>
<script src="https://cdn.bootcss.com/vue/2.4.2/vue.min.js"></script>
</head>
<body>
<div id="app">
<div class="ctn ctn1">
<!-- draggable=true -->
 <div class="sub sub1" v-for="(site, index) in list1">
 <!-- @mousemove.prevent='mousemove(site, $event)' -->
   <div class="dragCtn fixed" @mousedown="mousedown(site, $event)" @mouseup='mouseup(site, $event)'>
    {{ site.name }}
   </div>
 </div>
</div>
<div class="ctn ctn2">
 <div class="sub sub2" v-for="(site, index) in list2">
   <div class="dragCtn">
    {{ index }} : {{ site.name }}
   </div>
 </div> 
</div> 
</div>
<script>
new Vue({
 el: '#app',
 data: {
 list1: [{name:'拖动我', index:0}],
 list2: [{name:'a', index:0}, {name:'b', index:1}, {name:'c', index: 2}, {name:'d', index: 3}],
 vm:'',
 sb_bkx: 0,
 sb_bky: 0,
 },
 methods: {
  mousedown: function (site, event) {
  var event=event||window.event;
  var _target = event.target
  var startx=event.clientX;
  var starty=event.clientY;
  var sb_bkx=startx-event.target.offsetLeft;
  var sb_bky=starty-event.target.offsetTop;
  var ww=document.documentElement.clientWidth;
  var wh = window.innerHeight;
  if (event.preventDefault) {
   event.preventDefault();
  } else{
   event.returnValue=false;
  };
  document.onmousemove=function (ev) {
   var event=ev||window.event;
   var scrolltop=document.documentElement.scrollTop||document.body.scrollTop;
   if (event.clientY < 0 || event.clientX < 0 || event.clientY > wh || event.clientX > ww) {
    return false;
   };
   var endx=event.clientX-sb_bkx;
   var endy=event.clientY-sb_bky;
   _target.style.left=endx+'px';
   _target.style.top=endy+'px';
  }
  },
  mouseup: function (e) {
  document.onmousemove=null;
  }
 }
})
</script>
<style>
 .ctn{
  line-height: 50px;
  cursor: pointer;
  font-size: 20px;
  text-align: center;
  float: left;
 }
 .sub:hover{
  background: #e6dcdc;
  color: white;
  width: 100px;
 }
  .ctn1{
   border: 1px solid green;
   width: 100px;
  }
  .ctn2{
   border: 1px solid black;
   width: 100px;
   margin-left: 50px;
  }
  .fixed{
  width: 100px;
   height: 100px;
  position: fixed;
  background: red;
  left: 10px;
  top: 15px;
  cursor: move;
  }
</style>
</body>
</html>

补充:vue 自定义指令-拖拽

主要思想: 获取拖拽的dom元素,在oDiv.onmousedown事件内获取鼠标相对dom元素本身的位置:

var disX=ev.clientX-oDiv.offsetLeft;
 var disY=ev.clientY-oDiv.offsetTop;

再通过document.onmousemove事件计算dom元素左上角相对 视口的距离:

var l=ev.clientX-disX;
var t=ev.clientY-disY;
oDiv.style.left=l+'px';
oDiv.style.top=t+'px';

完整代码:

<script>
  /* vue-自定义指令-拖拽 */
  Vue.directive('drag',function(){
   var oDiv=this.el;
   oDiv.onmousedown=function(ev){
    var disX=ev.clientX-oDiv.offsetLeft;
    var disY=ev.clientY-oDiv.offsetTop;
    document.onmousemove=function(ev){
     var l=ev.clientX-disX;
     var t=ev.clientY-disY;
     oDiv.style.left=l+'px';
     oDiv.style.top=t+'px';
    };
    document.onmouseup=function(){
     document.onmousemove=null;
     document.onmouseup=null;
    };
   };
  });
  window.onload=function(){
   var vm=new Vue({
    el:'#box',
    data:{
     msg:'welcome'
    }
   });
  };
 </script>
</head>
<body>
 <div id="box">
  <div v-drag :style="{width:'100px', height:'100px', background:'blue', position:'absolute', right:0, top:0}"></div>
  <div v-drag :style="{width:'100px', height:'100px', background:'red', position:'absolute', left:0, top:0}"></div>
 </div>
</body>

总结

以上所述是小编给大家介绍的vue+mousemove实现鼠标拖动功能,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
用javascript实现在小方框中浏览大图的代码
Aug 14 Javascript
Javascript 学习笔记 错误处理
Jul 30 Javascript
学习ExtJS(二) Button常用方法
Oct 07 Javascript
让你的博客飘雪花超出屏幕依然看得见
Jan 04 Javascript
使用js操作cookie的一点小收获分享
Sep 03 Javascript
基于HTML模板和JSON数据的JavaScript交互(移动端)
Apr 06 Javascript
基于jquery trigger函数无法触发a标签的两种解决方法
Jan 06 jQuery
Node.js爬取豆瓣数据实例分析
Mar 05 Javascript
Vue项目webpack打包部署到Tomcat刷新报404错误问题的解决方案
May 15 Javascript
Vuejs2 + Webpack框架里,模拟下载的实例讲解
Sep 05 Javascript
微信小程序如何引用外部js,外部样式,公共页面模板
Jul 23 Javascript
Vue 的 v-model用法实例
Nov 23 Vue.js
对vue2.0中.vue文件页面跳转之.$router.push的用法详解
Aug 24 #Javascript
微信小程序Getuserinfo解决方案图解
Aug 24 #Javascript
解决vue2.0路由跳转未匹配相应用路由避免出现空白页面的问题
Aug 24 #Javascript
JavaScript中join()、splice()、slice()和split()函数用法示例
Aug 24 #Javascript
vue 中引用gojs绘制E-R图的方法示例
Aug 24 #Javascript
解决webpack dev-server不能匹配post请求的问题
Aug 24 #Javascript
vue2中,根据list的id进入对应的详情页并修改title方法
Aug 24 #Javascript
You might like
Zend Framework教程之路由功能Zend_Controller_Router详解
2016/03/07 PHP
PHP中call_user_func_array回调函数的用法示例
2016/11/26 PHP
PHP使用phpunit进行单元测试示例
2019/09/23 PHP
tp5.1 实现setInc字段自动加1
2019/10/18 PHP
动态调用css文件——jquery的应用
2007/02/20 Javascript
文本框获得焦点和失去焦点的判断代码
2012/03/18 Javascript
js中数组Array的一些常用方法总结
2013/08/12 Javascript
jquery点击缩略图切换视频播放特效代码分享
2015/09/15 Javascript
jQuery实现查找链接文字替换属性的方法
2016/06/27 Javascript
vue制作加载更多功能的正确打开方式
2016/10/12 Javascript
JavaScript中的call和apply的用途以及区别
2017/01/11 Javascript
微信小程序 天气预报开发实例代码源码
2017/01/20 Javascript
angular十大常见问题
2017/03/07 Javascript
实例分析nodejs模块xml2js解析xml过程中遇到的坑
2017/03/18 NodeJs
基于JS代码实现简单易用的倒计时 x 天 x 时 x 分 x 秒效果
2017/07/13 Javascript
React Native 搭建开发环境的方法步骤
2017/10/30 Javascript
浅谈vuejs实现数据驱动视图原理
2018/02/23 Javascript
对Vue table 动态表格td可编辑的方法详解
2018/08/28 Javascript
axios+Vue实现上传文件显示进度功能
2019/04/14 Javascript
layui文件上传控件带更改后数据传值的方法
2019/09/23 Javascript
python简单程序读取串口信息的方法
2015/03/13 Python
对numpy中布尔型数组的处理方法详解
2018/04/17 Python
如何用Python合并lmdb文件
2018/07/02 Python
python进程和线程用法知识点总结
2019/05/28 Python
Python基于Opencv来快速实现人脸识别过程详解(完整版)
2019/07/11 Python
Python3远程监控程序的实现方法
2019/07/15 Python
解决Tensorflow sess.run导致的内存溢出问题
2020/02/05 Python
python属于解释型语言么
2020/06/15 Python
python 实时调取摄像头的示例代码
2020/11/25 Python
python 统计list中各个元素出现的次数的几种方法
2021/02/20 Python
linux面试题参考答案(4)
2014/09/21 面试题
建筑人员岗位职责
2013/12/25 职场文书
医药专业应届毕业生求职信范文
2014/01/01 职场文书
大学生冰淇淋店商业计划书
2014/01/14 职场文书
班级入场式解说词
2014/02/01 职场文书
教你win10系统中APPCRASH事件问题解决方法
2022/07/15 数码科技