vue自定义指令之面板拖拽的实现


Posted in Javascript onApril 14, 2019

前言

在指令里获取的this并不是vue对象,vnode.context才是vue对象,一般来说,指令最好不要访问vue上的data,以追求解耦,但是可以通过指令传进来的值去访问method或ref之类的。

vue指令

官方文档其实已经解释的蛮清楚了,这里挑几个重点的来讲。

1、arguments

el: 当前的node对象,用于操作dom
binding:模版解析之后的值
vNode: Vue 编译生成的虚拟节点,可以在上面获取vue对象
oldVnode: 使用当前指令上一次变化的node内容

2、 生命周期

bind: 初始化的时候调用,但这时候node不一定渲染完成
inserted: 被绑定元素插入父节点时调用,关于dom操作尽量在这里用
update:就是内部this.update时会触发这里

面板拖拽逻辑

使用relative,舰艇event上的clientX和clientY鼠标距离页面的位置来改变面板的top和left。

涉及属性

  • offsetLeft:距离参照元素左边界偏移量
  • offsetTop:距离参照元素上边界偏移量
  • clientWidth:此属性可以返回指定元素客户区宽度
  • clientHeight: 此属性可以返回指定元素客户区高度
  • clientX:事件被触发时鼠标指针相对于浏览器页面(或客户区)的水平坐标
  • clientY: 事件被触发时鼠标指针相对于浏览器页面(或客户区)的垂直坐标
  • onmousedown:鼠标按下事件
  • onmousemove: 鼠标滑动事件
  • onmouseup: 鼠标松开事件

实现代码

<div v-drag="'refName'"></div>

在绑定的组件上使用,value非必选项,不挑就默认是基于document的移动

directives: {
  drag: {
   // 使用bind会有可能没有渲染完成
   inserted: function(el, binding, vnode) {
    const _el = el; //获取当前元素
    const ref = vnode.context.$refs[binding.value]; // 判断基于移动的是哪一个盒子
    const masterNode = ref ? ref : document; // 用于绑定事件
    const masterBody = ref ? ref : document.body; // 用于获取高和宽
    const mgl = _el.offsetLeft;
    const mgt = _el.offsetTop;
    const maxWidth = masterBody.clientWidth;
    const maxHeight = masterBody.clientHeight;
    const elWidth = _el.clientWidth;
    const elHeight = _el.clientHeight;
    let positionX = 0,
     positionY = 0;
    _el.onmousedown = e => {
     //算出鼠标相对元素的位置,加上的值是margin的值
     let disX = e.clientX - _el.offsetLeft + mgl; 
     let disY = e.clientY - _el.offsetTop + mgt;
     masterNode.onmousemove = e => {
      //用鼠标的位置减去鼠标相对元素的位置,得到元素的位置
      let left = e.clientX - disX;
      let top = e.clientY - disY;
      // 绑定的值不能滑出基于盒子的范围
      left < 0 && (left = 0);
      left > (maxWidth - elWidth - mgl) && (left = maxWidth - elWidth - mgl);
      top < 0 && (top = 0);
      top > (maxHeight - elHeight - mgt) && (top = maxHeight - elHeight - mgt);
      //绑定元素位置到positionX和positionY上面
      positionX = top;
      positionY = left;
      
      //移动当前元素
      _el.style.left = left + "px";
      _el.style.top = top + "px";
     };
     // 这里是鼠标超出基于盒子范围之后再松开,会监听不到
     document.onmouseup = e => {
      masterNode.onmousemove = null;
      document.onmouseup = null;
     };
    };
   }
  }
 }

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
Ajax提交与传统表单提交的区别说明
Feb 07 Javascript
javascript模拟订火车票和退票示例
Apr 24 Javascript
ionic 上拉菜单(ActionSheet)实例代码
Jun 06 Javascript
Bootstrap风格的WPF样式
Dec 07 Javascript
Javascript Event(事件)的传播与冒泡
Jan 23 Javascript
微信小程序request出现400的问题解决办法
May 23 Javascript
JS 中document.write()的用法和清空的原因浅析
Dec 04 Javascript
使用vue-cli编写vue插件的方法
Feb 26 Javascript
JavaScript捕捉事件和阻止冒泡事件实例分析
Aug 03 Javascript
VUE v-model表单数据双向绑定完整示例
Jan 21 Javascript
JavaScript实现点击切换功能
Jan 27 Javascript
JavaScript实现队列结构过程
Dec 06 Javascript
详解Vue组件之间通信的七种方式
Apr 14 #Javascript
浅谈Vue CLI 3结合Lerna进行UI框架设计
Apr 14 #Javascript
vue使用axios上传文件(FormData)的方法
Apr 14 #Javascript
详解如何理解vue的key属性
Apr 14 #Javascript
axios+Vue实现上传文件显示进度功能
Apr 14 #Javascript
Vue 使用formData方式向后台发送数据的实现
Apr 14 #Javascript
说说如何使用Vuex进行状态管理(小结)
Apr 14 #Javascript
You might like
JavaScript中变量提升 Hoisting
2012/07/03 Javascript
Jquery显示、隐藏元素以及添加删除样式
2013/08/09 Javascript
解决json日期格式问题的3种方法
2014/02/02 Javascript
jquery模拟alert的弹窗插件
2015/07/31 Javascript
js操作table元素实现表格行列新增、删除技巧总结
2015/11/18 Javascript
jQuery+ajax实现文章点赞功能的方法
2015/12/31 Javascript
jquery UI Datepicker时间控件的使用及问题解决
2016/04/28 Javascript
js基于setTimeout与setInterval实现多线程
2016/06/17 Javascript
图文详解Javascript中的上下文和作用域
2017/02/15 Javascript
原生js实现秒表计时器功能
2017/02/16 Javascript
js实现图片3D轮播效果
2019/09/21 Javascript
详解Nuxt.js 实战集锦
2019/11/19 Javascript
2020京东618叠蛋糕js脚本(亲测好用)
2020/06/02 Javascript
vue如何使用外部特殊字体的操作
2020/07/30 Javascript
[04:56]经典回顾:前Ehome 与 前LGD
2015/02/26 DOTA
Python实现 多进程导入CSV数据到 MySQL
2017/02/26 Python
详解Python的数据库操作(pymysql)
2019/04/04 Python
pandas的连接函数concat()函数的具体使用方法
2019/07/09 Python
30秒学会30个超实用Python代码片段【收藏版】
2019/10/15 Python
使用pytorch和torchtext进行文本分类的实例
2020/01/08 Python
世界上最大的铁人三项商店:Tri UK
2020/11/04 全球购物
公务员培训心得体会
2013/12/28 职场文书
销售个人求职信范文
2014/04/28 职场文书
房地产端午节活动方案
2014/08/24 职场文书
安全环保演讲稿
2014/08/28 职场文书
党在我心中的演讲稿
2014/09/13 职场文书
幼儿园学前班幼儿评语
2014/12/29 职场文书
委托公证书格式
2015/01/26 职场文书
校园开放日新闻稿
2015/07/17 职场文书
运动会通讯稿200字
2015/07/20 职场文书
2016年五四青年节校园广播稿
2015/12/17 职场文书
合作意向书怎么写
2019/06/24 职场文书
智慧人生:永远不需要向任何人解释你自己
2019/08/20 职场文书
导游词之杭州岳王庙
2019/11/13 职场文书
HTML+VUE分页实现炫酷物联网大屏功能
2021/05/27 Vue.js
mysql 带多个条件的查询方式
2021/06/05 MySQL