🌑

卡洛背心

Vue使用自定义指令实现按钮在区域内任意拖拽移动

在这里插入图片描述

项目场景

实现一个按钮,然后这个按钮可以在页面范围内,被拖拽到任意位置。

实现思路

  • 实现父子两个div,并且设置需要拖拽的子元素为相对定位,其父元素为绝对定位
  • 当鼠标按下(onmousedown)时,记录此时目标元素当前的 lefttop
  • 在鼠标移动(onmousemove)的过程中,计算每次移动的横向距离和纵向距离的变化值,
  • 然后实时并改变元素的 lefttop
  • 最后,鼠标松开(onmouseup)时,子元素停留在当前位置,完成一次拖拽

实现效果在这里插入图片描述

实现代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
<template>
<div>
<div class="draggable-box">
<div class="draggable-item" v-draggable>我可以移动哦!</div>
</div>
</div>
</template>

<script>
import draggable from '../../directive/test/draggable'
export default {
directives: {
draggable
},
data(){
return{
}
},
methods:{
}
}
</script>

<style lang="scss">
.draggable-box{
background-color: bisque;
position: relative;
border: 1px solid #333;
width: 500px;
height: 500px;
.draggable-item{
background-color: aqua;
position: absolute;
width: 50px;
height: 50px;
}
}
</style>

draggable.js文件如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
const draggable = {
inserted: function (el) {
el.style.cursor = 'move'
el.onmousedown = function (e) {
console.log(el, e, 123)
let disx = e.pageX - el.offsetLeft
let disy = e.pageY - el.offsetTop
document.onmousemove = function (e) {
let x = e.pageX - disx
let y = e.pageY - disy
let maxX = document.body.clientWidth - parseInt(window.getComputedStyle(el).width)
let maxY = document.body.clientHeight - parseInt(window.getComputedStyle(el).height)
if (x < 0) {
x = 0
} else if (x > maxX) {
x = maxX
}

if (y < 0) {
y = 0
} else if (y > maxY) {
y = maxY
}

el.style.left = x + 'px'
el.style.top = y + 'px'
}
document.onmouseup = function () {
document.onmousemove = document.onmouseup = null
}
}
},
}
export default draggable

如有疑问,欢迎评论区留言。

在这里插入图片描述

— Jun 8, 2021