Vue3 实现可拖拽 div

969 阅读1分钟

Vue3 实现拖拽 div

  1. 注意要减去div的初始值
import { Directive } from "vue";
const vMove: Directive<any, void> = (el: HTMLElement) => {
  let moveEl: HTMLElement = el.firstElementChild as HTMLElement;
  const mouseDown = (e: MouseEvent) => {
    let X = e.clientX - el.offsetLeft;      //减去初始值
    let Y = e.clientY - el.offsetTop;
    const move = (e: MouseEvent) => {
      let eLeft = e.clientX - X
      let eTop = e.clientY - Y
      el.style.left = eLeft + 'px'
      el.style.top = eTop + "px"
    };
    document.addEventListener("mousemove", move);       //鼠标移动
    document.addEventListener("mouseup", () => {        //鼠标抬起
      document.removeEventListener("mousemove", move);  //鼠标抬起就清除掉mousemove事件
    });
  };
  moveEl.addEventListener("mousedown", mouseDown);
}
  1. 下面为其他代码
<template>
  <div v-move class="box">
    <div class="header"></div>
    <div>
      这是一个弹窗
    </div>
  </div>
</template>
 
<script setup lang='ts'>
// 内容在上面
</script>
 
<style lang='less'>
.box {
  position: fixed;
  left: 50%;
  top: 50%;
  transform: translate(-50%, -50%);
  width: 400px;
  height: 200px;
  border: 1px solid #ccc;

  .header {
    height: 20px;
    background: #b9e9f9;
    cursor: move;
  }
}
</style>

  1. 总结:注意clientXoffsetLeft的区别
    • clientX:鼠标事件发生与客户端左边的位置的水平坐标。不随页面滚动发生改变。
    • offsetLeft:返回当前元素相对于父节点元素发生水平偏移的位置值。也就是上面的 el 相对于根节点元素的偏移量。
    • pageX:是一个由 MouseEvent:返回的相对于整个文档的 x(水平)坐标,也就是包含 clientX + 滚动距离值。