使用JavaScript拖动一个元素(转换位置CSS3)



我正在执行一项小任务,在该任务中,我必须将(translate)元素自由拖动到文档中的任何位置。我已经完成了基本的工作,但对鼠标的当前位置感到困惑。因为当我开始拖动元素时,鼠标位置不在mousedown出现的位置。

简单地说,我希望鼠标的位置保持在我点击框的位置。

这是JSFiddle链接。

你需要计算元素的宽度和高度,以便将光标保持在它的中心,请注意,现在它正在处理任何宽度和高度值,在这里我添加了一个动画,只是调整宽度和高度的大小,以确保我们总是得到元素的中心

let target = document.querySelector(".drag");
function onDrag(e) {
// we could make them global variables instead
const {width, height} = window.getComputedStyle(target);
target.style.transform = `translate(${e.clientX - +width.replace("px", "") / 2}px, ${e.clientY - +height.replace("px", "") / 2}px)`;
}
function onLetGo() {
document.removeEventListener('mousemove', onDrag);
document.removeEventListener('mouseup', onLetGo);
}
function onGrab() {
document.addEventListener('mousemove', onDrag);
document.addEventListener('mouseup', onLetGo);
}
target.addEventListener('mousedown', onGrab);
* {
box-sizing: border-box;
}
.drag{
width: 100px;
height: 100px;
border: 1px solid black;
background: blue;
cursor: pointer;
position: fixed;
animation-name: resize;
animation-duration: 4s;
animation-timing-function: linear;
animation-iteration-count: infinite;
}
@keyframes resize {
0% {width: 100px}
25% {height: 150px}
50% {width: 150px}
100% {height: 100px}
}
<div class="drag"></div>

编辑以回答OP的评论

谢谢你的回答,它运行良好。有没有办法,我们可以从单击div的任何地方拖动div?

所以现在你想从点击的点拖动元素,而不是从它的中心拖动元素,你可以从event.clientX中减去event.offsetX来获得正确的光标位置,对于y轴也是如此,并确保容器没有边距或填充,在这个例子中,我已经从HTML和BODY元素中删除了边距和填充

let target = document.querySelector(".drag"), x = 0, y = 0;
function onDrag(e) {
// we use the coords of the mousedown event
target.style.transform = `translate(${e.clientX - x}px, ${e.clientY - y}px)`;
}
function onLetGo() {
document.removeEventListener('mousemove', onDrag);
document.removeEventListener('mouseup', onLetGo);
}
function onGrab(e) {
// we store the point of click(coords)
x = e.offsetX, y = e.offsetY;
document.addEventListener('mousemove', onDrag);
document.addEventListener('mouseup', onLetGo);
}
target.addEventListener('mousedown', onGrab);
* {
box-sizing: border-box;
}
html, body {
margin: 0;
padding: 0;
}
.drag{
width: 100px;
height: 100px;
border: 1px solid black;
background: blue;
cursor: pointer;
position: fixed;
}
<div class="drag"></div>

因为转换受边距、填充和其他流控制规则的影响,所以可以避免使用它,只需使用lefttop规则来正确定位元素,如

let target = document.querySelector(".drag"), x = 0, y = 0;
function onDrag(e) {
// use the `left` and `top` rules to properly position your element, so 
// you no more care about other flow affecting rules
target.style.left = `${e.clientX - x}px`;
target.style.top = `${e.clientY - y}px`;
}
function onLetGo() {
document.removeEventListener('mousemove', onDrag);
document.removeEventListener('mouseup', onLetGo);
}
function onGrab(e) {
x = e.offsetX, y = e.offsetY;
document.addEventListener('mousemove', onDrag);
document.addEventListener('mouseup', onLetGo);
}
target.addEventListener('mousedown', onGrab);
.drag {
width: 100px;
height: 100px;
border: 1px solid black;
background: blue;
cursor: pointer;
position: fixed;
}
<div class="drag"></div>