使用 JavaScript 实现简单的拖拽
步骤
使用 JavaScript
实现拖拽的步骤:
- 让元素捕获事件(
mousedown
,mousemove
&mouseup
) - 单击并不释放,触发
mousedown
,标记开始拖拽,并获取元素和鼠标的位置 - 拖动鼠标,触发
mousemove
,不断的获取鼠标的位置,并通过计算重新确定元素的位置 - 释放师表,触发
mouseup
,结束拖拽,确定元素位置并更新
被拖拽的元素必须是相对父元素定位,或者是绝对定位
实现
绑定事件
首先,对拖拽的元素绑定 mousedown
时间,使其触发对应的函数,获取元素与鼠标的位置。在 document
对象上绑定 mousemove
和 mouseup
事件,不在拖拽的元素上绑定是因为当鼠标移动太快而超出元素的范围时会停止拖拽,而绑定在 document
上则可以避免这样的事情发生。拖拽再快都不会超出 document
的范围。
绑定事件:
var box = document.getElementById('box');
box.onmousedown = down;
document.onmousemove = move;
document.onmouseup = up;
获取鼠标位置
鼠标位置可以在 event
对象中获得,常用的属性有:
-
clientX / clientY
: 相对浏览器窗口坐标 -
offsetX / offsetY
: 相对事件目标对象坐标 -
pageX / pageY
: 相对document
对象坐标
一般鼠标的位置使用 pageX / pageY
获取,但是 IE 不支持这两个属性。所以在 IE 中使用 event.clientX + document.body.scrollLeft - document.body.clientLeft;
获取鼠标的位置。
获取鼠标位置的函数:
function getMouseXY(e) {
var x = 0, y = 0;
e = e || window.event;
if (e.pageX) {
x = e.pageX;
y = e.pageY;
} else {
x = e.clientX + document.body.scrollLeft - document.body.clientLeft;
y = e.clientY + document.body.scrollTop - document.body.clientTop;
}
return {
x: x,
y: y
};
}
事件触发函数
mousedown
当鼠标移动到元素内并点击元素不放时,触发 mousedown
事件。按照上面的步骤,这一步是获取元素与鼠标的位置,用于触发 mousemove
时计算元素的位置。
mousedown
触发的函数:
function down(e) {
dragging = true;
boxX = box.offsetLeft;
boxY = box.offsetTop;
mouseX = parseInt(getMouseXY(e).x);
mouseY = parseInt(getMouseXY(e).y);
offsetX = mouseX - boxX;
offsetY = mouseY - boxY;
}
boxX / boxY
为元素左上角相对于已定位的父元素(相对或者绝对定位的父元素)的偏移的像素值,即元素左上角的坐标。
mouseX / mouseY
是通过 getMouseXY
函数获得的鼠标的坐标。
offsetX/ offsetY
是鼠标相对于元素坐标(左上角坐标)的坐标。
mousemove
当鼠标移动时,不断的获取鼠标的位置,并计算元素的新坐标修改元素的位置样式。
function move(e) {
if (dragging) {
var x = getMouseXY(e).x - offsetX;
var y = getMouseXY(e).y - offsetY;
var width = document.documentElement.clientWidth - box.offsetWidth;
var height = document.documentElement.clientHeight - box.offsetHeight;
x = Math.min(Math.max(0, x), width);
y = Math.min(Math.max(0, y), height);
box.style.left = x + 'px';
box.style.top = y + 'px';
}
}
变量 width / height
表示可移动的位置的大小,这里是 document
减去元素的大小(元素不会超出可移动的范围)。
Math.min
使得元素不会超出可移动访问的右边界(元素 x
坐标不会超过 width
),Math.max
使得元素不会超出可移动范围的左边界(元素的 x 坐标不小于 0)。
最后将改变后的元素 left
与 top
值应用当元素上,即修改元素的样式。
mouseup
拖拽结束,取消拖拽的标记。使其触发 mousemove
事件,但不做任何处理。
function up(e) {
dragging = false;
}
在线演示
总结
上面使用的简单的 JavaScript
代码实现了元素的拖拽,但并没有对兼容性问题全面考虑,也没有对性能优化,有不必要的事件触发。
- 回家的低价票难抢?注意!可能是被“爬虫”吃了
- DeepMind团队回顾2017年:想象、推理取得突破
- flask-mail发送QQ邮件代码示例(亲测可行)
- 数据结构与算法C#版笔记--排序(Sort)-下
- pip --upgrade批量更新过期的python库
- 数据结构与算法C#版笔记--排序(Sort)-上
- android 模拟器安装二三事
- 2017小程序发展大事件和未来3大趋势分析
- [复习]The C Programming Language 2nd 习题集(1.1-1.10)
- 数据结构C#版笔记--啥夫曼树(Huffman Tree)与啥夫曼编码(Huffman Encoding)
- “单播”、“组播”和“多播”
- flash player10.1 + FMS4中的p2p功能
- fms4 p2p:图片分享
- 老域名新用的优缺点分析
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- Django {{ MEDIA_URL }}无法显示图片的解决方式
- python将音频进行变速的操作方法
- 解决django的template中如果无法引用MEDIA_URL问题
- 从源码解读 - Vue常考面试题
- Android PickerView实现三级联动效果
- Android巧用XListView实现万能下拉刷新控件
- Android获取其他应用中的assets资源
- Android自定义动态壁纸开发详解
- VsCode插件koroFileHeader一键添加文件头部注释
- 强大的 Stream API(一)
- python3 配置logging日志类的操作
- 你对CSS权重真的足够了解吗?
- python opencv实现图片缺陷检测(讲解直方图以及相关系数对比法)
- Js 的事件循环(Event Loop)机制以及实例讲解
- 你不知道的js中关于this绑定机制的解析[看完还不懂算我输]