js实现拖动div
实现拖动div的基本思路
通过监听鼠标事件(mousedown、mousemove、mouseup)来实现div的拖动效果。需要记录鼠标按下时的初始位置和div的初始位置,计算移动距离并更新div的位置。
HTML结构准备
创建一个可拖动的div元素,并为其添加必要的样式:

<div id="draggable" style="width: 100px; height: 100px; background: red; position: absolute;"></div>
JavaScript实现
const draggable = document.getElementById('draggable');
let isDragging = false;
let offsetX, offsetY;
draggable.addEventListener('mousedown', (e) => {
isDragging = true;
offsetX = e.clientX - draggable.offsetLeft;
offsetY = e.clientY - draggable.offsetTop;
});
document.addEventListener('mousemove', (e) => {
if (!isDragging) return;
draggable.style.left = `${e.clientX - offsetX}px`;
draggable.style.top = `${e.clientY - offsetY}px`;
});
document.addEventListener('mouseup', () => {
isDragging = false;
});
优化拖动体验
为防止拖动时选中文本,可以添加CSS样式:
#draggable {
user-select: none;
cursor: grab;
}
处理边界情况
确保拖动不会超出视口边界:

document.addEventListener('mousemove', (e) => {
if (!isDragging) return;
let left = e.clientX - offsetX;
let top = e.clientY - offsetY;
// 限制在视口内
left = Math.max(0, Math.min(left, window.innerWidth - draggable.offsetWidth));
top = Math.max(0, Math.min(top, window.innerHeight - draggable.offsetHeight));
draggable.style.left = `${left}px`;
draggable.style.top = `${top}px`;
});
封装为可复用函数
将拖动功能封装为可复用的函数:
function makeDraggable(element) {
let isDragging = false;
let offsetX, offsetY;
element.addEventListener('mousedown', (e) => {
isDragging = true;
offsetX = e.clientX - element.offsetLeft;
offsetY = e.clientY - element.offsetTop;
});
document.addEventListener('mousemove', (e) => {
if (!isDragging) return;
element.style.left = `${e.clientX - offsetX}px`;
element.style.top = `${e.clientY - offsetY}px`;
});
document.addEventListener('mouseup', () => {
isDragging = false;
});
}
// 使用
makeDraggable(document.getElementById('draggable'));
支持触摸设备
添加触摸事件支持:
function makeDraggable(element) {
let isDragging = false;
let offsetX, offsetY;
const startDrag = (clientX, clientY) => {
isDragging = true;
offsetX = clientX - element.offsetLeft;
offsetY = clientY - element.offsetTop;
};
const drag = (clientX, clientY) => {
if (!isDragging) return;
element.style.left = `${clientX - offsetX}px`;
element.style.top = `${clientY - offsetY}px`;
};
const endDrag = () => {
isDragging = false;
};
// 鼠标事件
element.addEventListener('mousedown', (e) => startDrag(e.clientX, e.clientY));
document.addEventListener('mousemove', (e) => drag(e.clientX, e.clientY));
document.addEventListener('mouseup', endDrag);
// 触摸事件
element.addEventListener('touchstart', (e) => {
e.preventDefault();
startDrag(e.touches[0].clientX, e.touches[0].clientY);
});
document.addEventListener('touchmove', (e) => {
e.preventDefault();
drag(e.touches[0].clientX, e.touches[0].clientY);
});
document.addEventListener('touchend', endDrag);
}






