一起来写段JS drag拖动代码


Posted in Javascript onDecember 09, 2010

1、为要被拖移三个事件,onmousedown,onmousemove,onmouseup
2、在onmousemove事件中来处理被拖移元素的位置的变化,其实说白了元素要移动的距离就是鼠标两次移动之间的距离。
3、其中还包括setCapture,releaseCapture,目的就是为了被搬移的元素始终能拥有焦点。
以前大致就是以前的认识,可以参见 JS拖动技术--- 关于setCapture 这个实现,后来随着工作要求的提高,做的工作都是要跨浏览器的,所以就重新构思并参考一些开源代码做了实现。
现在大致思路可分析为以下几步,我一一为您展现。
1、 我们是为了拖移而搬移吗?当然不是,如google地图,当每次搬移后他的目的是为了计算当前空间坐标来加载地理信息。所以我这里设计了几个常见事件。以下是事件列表
onDragStart :元素发生拖移时,如果注册该事件,触发时会接收到两个参数x,y分别为被搬移元素发生拖移时的坐标
onDrag : 元素拖移过程中,如果注册该事件,触发时会接收到两个参数nx,ny拖移过程中坐标发生的偏移量
onDragEnd :元素发生结束时,如果注册该事件,触发时会接收到两个参数x,y分别为被搬移元素的当前坐标
2、 onmousedown事件应该绑定给谁?以前我都是绑定给被拖移元素的,后来发现很不灵活,现在设计为可绑定给任意不相关的元素同时实现该元素的拖动。
3、 如何来实现元素搬移过程中一直拥有焦点?因为要跨浏览器,所以就不再用setCapture之类的方法,这里换种思维,为什么元素元素搬移过程中没有了焦点呢,主要是我们把onmousemove事件注册到了被拖移的元素上,而这并不是必需的,所以当元素触发onmousedown事件后,我把onmousemove、onmouseup事件直接注册到document上,这样鼠标移到哪都会有焦点。
说完了这么多,直接看代码结构吧!

Drag = { 
obj: null, 
init: function (options) { 
options.handler.onmousedown = this.start; 
options.handler.root = options.root || options.handler; 
var root = options.handler.root; 
root.onDragStart = options.dragStart || new Function(); 
root.onDrag = options.onDrag || new Function(); 
root.onDragEnd = options.onDragEnd || new Function(); 
}, 
start: function (e) {//此时的this是handler 
var obj = Drag.obj = this; 
obj.style.cursor = 'move'; 
e = e || Drag.fixEvent(window.event); 
ex = e.pageX; 
ey = e.pageY; 
obj.lastMouseX = ex; 
obj.lastMouseY = ey; 
var x = obj.root.offsetLeft; 
var y = obj.root..offsetTop; 
obj.root.style.left = x + "px"; 
obj.root.style.top = y + "px"; 
document.onmouseup = Drag.end; 
document.onmousemove = Drag.drag; 
obj.root.onDragStart(x, y); 
}, 
drag: function (e) { 
e = e || Drag.fixEvent(window.event); 
ex = e.pageX; 
ey = e.pageY; 
var root = Drag.obj.root; 
var x = root.style.left ? parseInt(root.style.left) : 0; 
var y = root.style.top ? parseInt(root.style.top) : 0; 
var nx = ex - Drag.obj.lastMouseX + x; 
var ny = ey - Drag.obj.lastMouseY + y; 
root.style.left = nx + "px"; 
root.style.top = ny + "px"; 
Drag.obj.root.onDrag(nx, ny); 
Drag.obj.lastMouseX = ex; 
Drag.obj.lastMouseY = ey; 
}, 
end: function (e) { 
var x = Drag.obj.root.style.left ? parseInt(Drag.obj.root.style.left) : 0; 
var y = Drag.obj.root.style.top ? parseInt(Drag.obj.root.style.top) : 0; 
Drag.obj.root.onDragEnd(x, y); 
document.onmousemove = null; 
document.onmouseup = null; 
Drag.obj = null; 
}, 
fixEvent: function (e) { 
e.pageX = e.clientX + document.documentElement.scrollLeft; 
e.pageY = e.clientY + document.documentElement.scrollTop; 
return e; 
} 
}

上面init主要处理一些初如化工作,如记录onDragStart、onDrag、onDragEnd三个事件, handler为处理拖动事件的那个元素,root为被拖动的元素。
当在handler上点击后触发Drag.start方法,Drag.start主要为记录住鼠标相对整个页面的位置;给document注册onmouseup、onmousemove事件,及触发onDragStart事件。
Drag.drag方法也很简单,主要作用就是更新被搬移元素位置,同时记录住鼠标相对整个页面的位置。
Drag.end方法就更简单了,就是做一些收尾工作。

最后给大家附段使用的代码吧,祝大家学习愉快!

Drag.init({ 
handler: document.getElementById("handler"), 
root:document.getElementById("root"); 
}); 
<div id="root"> 
<h2 id="handler"></h2> 
</div>
Javascript 相关文章推荐
点图片上一页下一页翻页效果
Jul 09 Javascript
jquery使用jxl插件导出excel示例
Apr 14 Javascript
jQuery新的事件绑定机制on()示例应用
Jul 18 Javascript
根据user-agent判断蜘蛛代码黑帽跳转代码(js版与php版本)
Sep 14 Javascript
jQuery AJAX timeout 超时问题详解
Jun 21 Javascript
vue mounted组件的使用
Jun 18 Javascript
JavaScript遍历DOM元素的常见方式示例
Feb 16 Javascript
微信小程序API—获取定位的详解
Apr 30 Javascript
小程序实现新用户判断并跳转激活的方法
May 20 Javascript
浅谈Vue组件单元测试究竟测试什么
Feb 05 Javascript
es6 super关键字的理解与应用实例分析
Feb 15 Javascript
Vue中component标签解决项目组件化操作
Sep 04 Javascript
教您去掉ie网页加载进度条的方法
Dec 09 #Javascript
javascript 折半查找字符在数组中的位置(有序列表)
Dec 09 #Javascript
基于jQuery的一个扩展form序列化到json对象
Dec 09 #Javascript
来自国外的页面JavaScript文件优化
Dec 08 #Javascript
js 替换功能函数,用正则表达式解决,js的全部替换
Dec 08 #Javascript
javascript中callee与caller的用法和应用场景
Dec 08 #Javascript
js下通过prototype扩展实现indexOf的代码
Dec 08 #Javascript
You might like
PHP+DBM的同学录程序(2)
2006/10/09 PHP
PHP脚本中include文件出错解决方法
2008/11/20 PHP
php fsockopen中多线程问题的解决办法[翻译]
2011/11/09 PHP
调试一段PHP程序时遇到的三个问题
2012/01/17 PHP
php inc文件使用的风险和注意事项
2013/11/12 PHP
PHP实现动态柱状图改进版
2015/03/30 PHP
PHP中preg_match正则匹配中的/u、/i、/s含义
2015/04/17 PHP
微信开发之获取JSAPI TICKET
2017/07/07 PHP
JavaScript 编程引入命名空间的方法与代码
2007/08/13 Javascript
javascript判断非数字的简单例子
2013/07/18 Javascript
判断及设置浏览器全屏模式
2014/04/20 Javascript
js类定义函数时用prototype与不用的区别示例介绍
2014/06/10 Javascript
window.open()实现post传递参数
2015/03/12 Javascript
nodejs实现获取某宝商品分类
2015/05/28 NodeJs
jquery实现select选择框内容左右移动代码分享
2015/11/21 Javascript
原生js和jQuery实现淡入淡出轮播效果
2015/12/25 Javascript
原生js实现打字动画游戏
2017/02/04 Javascript
Angular搜索 过滤 批量删除 添加 表单验证功能集锦(实例代码)
2017/10/25 Javascript
jQuery实现checkbox即点即改批量删除及中间遇到的坑
2017/11/11 jQuery
js实现转动骰子模型
2019/10/24 Javascript
vue element-ui el-date-picker限制选择时间为当天之前的代码
2019/11/07 Javascript
antd table按表格里的日期去排序操作
2020/11/17 Javascript
python中string模块各属性以及函数的用法介绍
2016/05/30 Python
python 简单的绘图工具turtle使用详解
2017/06/21 Python
python TKinter获取文本框内容的方法
2018/10/11 Python
Python第三方库安装缓慢的解决方法
2021/02/06 Python
html5使用html2canvas实现浏览器截图的示例
2017/08/31 HTML / CSS
HTML5在canvas中绘制复杂形状附效果截图
2014/06/23 HTML / CSS
巴西葡萄酒销售网站:Wine.com.br
2017/11/07 全球购物
Giglio英国站:意大利奢侈品购物网
2018/03/06 全球购物
澳大利亚汽车零部件、音响及配件超市:Automotive Superstore
2018/06/19 全球购物
澳大利亚拥有最好的家具和家居用品在线目的地:Nestz
2019/02/23 全球购物
幼儿教师个人求职信范文
2013/09/21 职场文书
大学生应聘推荐信范文
2013/11/19 职场文书
青年文明号创建口号大全
2015/12/25 职场文书
中国现代文学之经典散文三篇
2019/09/18 职场文书