首页 > 其他分享 >【vue】dom元素拖拽指令

【vue】dom元素拖拽指令

时间:2024-05-27 18:00:40浏览次数:12  
标签:vue const dom move 拖拽 operateEl document dragDom

directives.js:

/**
 * v-dialogDrag 弹窗拖拽
 * @params operate {String} 拖拽项的data-drag-name   
 * @params move 
 */
const dialogDrag = {
  // el, binding, vnode, oldVnode
  inserted(el, binding,vnode) {
    const { operate, move } = binding.value;
    if(typeof binding.value !== 'object') {
      throw new Error('参数错误!');
    }
    if (!move || operate === false || operate === '') return;
    // 获取拖拽内容头部
    const selector = `[data-drag-name="${operate}"]`;
    const operateElList = el.querySelectorAll(selector);
    let dragDom;
    if(move === true) {
      dragDom = el;
    }else{
      dragDom = document.querySelector(`[class*="${move}"]`);
    }
    if (!dragDom || !operateElList?.length) return;

    // 获取原有属性 ie dom元素.currentStyle 火狐谷歌 window.getComputedStyle(dom元素, null);
    const currentStyle = dragDom.currentStyle || window.getComputedStyle(dragDom, null);
    dragDom.style.position = 'absolute';
    // 鼠标按下事件
    operateElList.forEach((operateEl) => {
      operateEl.style.cursor = 'move';
      const {draggable} = vnode.context;
      operateEl.onmousedown = ($event) => moveFn($event,draggable, operateEl, currentStyle, dragDom);
    });
  },
};

// 移动
function moveFn(e, draggable,operateEl, sty, dragDom) {
  if(draggable === false) return;
  
  e.stopPropagation();
  // 鼠标按下,计算当前元素距离可视区的距离 (鼠标点击位置距离可视窗口的距离)
  const disX = e.clientX - operateEl.offsetLeft;
  const disY = e.clientY - operateEl.offsetTop;

  // 获取到的值带px 正则匹配替换
  let styL, styT;

  // 注意在ie中 第一次获取到的值为组件自带50% 移动之后赋值为px
  if (sty.left.includes('%')) {
    styL = +document.body.clientWidth * (+sty.left.replace(/\%/g, '') / 100);
    styT = +document.body.clientHeight * (+sty.top.replace(/\%/g, '') / 100);
  } else {
    styL = +sty.left.replace(/\px/g, '');
    styT = +sty.top.replace(/\px/g, '');
  }

  // 鼠标拖拽事件
  document.onmousemove = function (e) {
    // 通过事件委托,计算移动的距离 (开始拖拽至结束拖拽的距离)
    const l = e.clientX - disX;
    const t = e.clientY - disY;

    let finallyL = l + styL;
    let finallyT = t + styT;

    // 移动当前元素
    dragDom.style.left = `${finallyL}px`;
    dragDom.style.top = `${finallyT}px`;
  };

  document.onmouseup = function () {
    document.onmousemove = null;
    document.onmouseup = null;
  };
}

export default {
  dialogDrag
};

使用:

 <div  v-dialogDrag="{ operate: operateUUid, move: true,draggable:draggable}">
    <div :data-drag-name="operateUUid" />
 </div>
 import {dialogDrag} from '@/utils/directives.js'; // 指令插件
 export default {
  directives: {
    dialogDrag: dialogDrag
  },
  data(){
    operateUUid:1234,// 操作区id
    draggable:true// 是否可拖拽
  },
}

标签:vue,const,dom,move,拖拽,operateEl,document,dragDom
From: https://www.cnblogs.com/yiping5/p/18216152

相关文章

  • vue2+uni-app的实现的动态数据显示
     1:所用技术:Vue2.X,Uview2.0,确保项目上已经安装了Vue2.X 版本和组件Uview(注:其余组件:如ElementUI组件也适用,主要是样式的区别)2:template层<template> <viewclass="NavPage"> <viewclass="LoginCard"> <uni-cardis-shadow:trueclass="CardLogin"......
  • vue项目使用qrcode插件生成二维码
    下载npmiqrcodejs2--save导入importQRCodefrom'qrcodejs2'使用<divclass="qrcode"ref="qrCodeDiv"></div><script>importQRCodefrom'qrcodejs2'exportdefault{data(){return{},......
  • 用拖拽报表设计器轻松实现企业流程化发展!
    随着行业竞争的激烈化,很多企业都希望运用更优的平台产品助力企业高效发展。低代码技术平台是理想的软件平台产品,灵活操作、易维护、更可靠、可扩展性强等,是推动企业进入流程化发展的理想帮手。那么,低代码技术平台、拖拽报表设计器的优势特点表现在哪里?可以在本文中寻找出答案。目......
  • 使用nodejs安装并使用vue操作步骤
    1.下载安装nodejs官网下载nodejs并安装,我这边选择Windows的20版本下载地址:https://nodejs.org/en/download/prebuilt-installer安装完成后进入cmd窗口,使用node-v命令检查是否安装成功 如上图所示安装成功 2.配置npm的全局安装路径(npm,nodepakaagemanager,是nodejs的软......
  • VUE学习笔记(四)
    通过子组件实例实现对话框的打开AddCategory.vue页面里调整dialogvue里按钮事件<divclass="dialog-footer"><el-button@click="state.dialogVisible=false">Cancel</el-button><el-buttontype="primary"......
  • vue使用右击复制功能
      使用的库xe-clipboard右击复制的 实际使用到的库是xe-clipboard 参考的https://vxetable.cn/v4/#/table/advanced/menu<template><div><vxe-tablebordershow-footer:row-config="{isCurrent:true}":column-config=&q......
  • VUE学习笔记(三)
    本小节为设置跨域和axios请求和获取数据设置跨域,在vue.config.js添加devServer配置const{defineConfig}=require("@vue/cli-service");module.exports=defineConfig({transpileDependencies:true,devServer:{proxy:{"/api":{target:&q......
  • VUE学习笔记(二)
    本小节为搭建布局页和分类页面需要使用到element-plus,添加指令npminstallelement-plus--save布局页从elementplus官网找到布局,粘贴过来<template><el-containerclass="layout-container-demo"><el-asidewidth="200px"><el-scrollbar><divclass=&qu......
  • 宝塔:续签SSL证书报错Verification failed, domain name resolution error or verifica
    网站SSL证书因为忘了续签,导致过期后无法进行续签,点击续签验证报错:Verificationfailed,domainnameresolutionerrororverificationURLcannotbeaccessed! 解决方法:1.点击SSL,在面板中选择“Let'sEncrypt”,1.1、选择DNSVerification(Wildcardsupport);1.2、......
  • 基于SpringBoot+Vue的实验室管理系统设计与实现毕设(文档+源码)
            目录一、项目介绍二、开发环境三、功能介绍四、核心代码五、效果图六、源码获取:        大家好呀,我是一个混迹在java圈的码农。今天要和大家分享的是一款基于SpringBoot+Vue的实验室管理系统,项目源码请点击文章末尾联系我哦~目前有各类成品......