模拟拖拽的原理:

x1等于div.offsetLeft

y1等于div.offsetTop

x2等于ev.clientX(ev表示event事件)

y2等于ev.clientY

当我们在方块上按下鼠标的时候,x2-x1即可确定。移动鼠标之后,我们用鼠标当前的位置即x4、y4减去x2-x1、y2-y1就可以得到方块现在的位置。

效果图:点击查看

代码:

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
#box{
width: 100px;
height: 100px;
background: red;
position: absolute;
}
</style>
</head>
<body> <div id="box"></div>
<script type="text/javascript">
var oBox = document.getElementById('box'); oBox.onmousedown = function(ev){
// 鼠标按下 var ev = ev || event; // 获取鼠标离div得距离
var mouseBoxleft = ev.clientX - this.offsetLeft;
var mouseBoxTop = ev.clientY - this.offsetTop; oBox.onmousemove = function(ev){
// 鼠标按下左键并移动 var ev = ev || event; // 设置div移动时,它的位置
oBox.style.left = ev.clientX - mouseBoxleft + 'px';
oBox.style.top = ev.clientY - mouseBoxleft + 'px'; } oBox.onmouseup = function(){
// 鼠标左键抬起 oBox.onmousemove = oBox.onmouseup = null;
}
}
</script>
</body>
</html>

优化代码:

  【1】鼠标移动快的时候,鼠标会移出方块,这时方块就不会再跟随鼠标动了。

      解决办法:就是将onmousemove和onmouseup加到document对象上

效果:点击查看

代码:

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
#box{
width: 100px;
height: 100px;
background: red;
position: absolute;
}
</style>
</head>
<body> <div id="box"></div>
<script>
var oBox = document.getElementById('box'); oBox.onmousedown = function(ev){
// 鼠标按下 var ev = ev || event; // 获取鼠标离div得距离
var mouseBoxleft = ev.clientX - this.offsetLeft;
var mouseBoxTop = ev.clientY - this.offsetTop; document.onmousemove = function(ev){
// 鼠标按下左键并移动 var ev = ev || event; // 设置div移动时,它的位置
oBox.style.left = ev.clientX - mouseBoxleft + 'px';
oBox.style.top = ev.clientY - mouseBoxleft + 'px'; } document.onmouseup = function(){
// 鼠标左键抬起 document.onmousemove = document.onmouseup = null;
}
}
</script>
</body>
</html>

  【2】当要拖动的方块中有文字时会触发浏览器的默认行为

      解决办法:1、使用return false添加到onmousedown事件中阻止浏览器的默认行为(IE除外)

           2、使用全局捕获(IE)

1、使用return false添加到onmousedown事件中阻止浏览器的默认行为(IE除外)

效果:点击查看

代码:

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
#box{
width: 100px;
height: 100px;
background: red;
position: absolute;
top: 0;
left: 0;
}
</style>
</head>
<body> <div id="box">模拟拖拽</div>
<script>
var oBox = document.getElementById('box'); oBox.onmousedown = function(ev){
// 鼠标按下 var ev = ev || event;
// 获取鼠标离div得距离
var mouseBoxleft = ev.clientX - this.offsetLeft;
var mouseBoxTop = ev.clientY - this.offsetTop; document.onmousemove = function(ev){
// 鼠标按下左键并移动 var ev = ev || event; // 设置div移动时,它的位置
oBox.style.left = ev.clientX - mouseBoxleft + 'px';
oBox.style.top = ev.clientY - mouseBoxleft + 'px'; } document.onmouseup = function(){
// 鼠标左键抬起 document.onmousemove = document.onmouseup = null;
} // 阻止默认行为
return false;
}
</script>
</body>
</html>

2、使用全局捕获(IE)

  全局捕获:当我们给一个元素这只全局捕获后,改元素会监听后续发生的所有事件,当有事件发生的时候就会触发改元素的事件

  举个栗子:点击查看

代码:

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
</head>
<body>
<input type="button" id="button1" value="弹出1" />
<input type="button" id="button2" value="弹出2" />
<script type="text/javascript">
window.onload = function(){
var Btn1 = document.getElementById('button1');
var Btn2 = document.getElementById('button2'); Btn1.setCapture(); Btn1.onclick = function(){
alert(1);
}
Btn2.onclick = function(){
alert(2);
} }
</script>
</body>
</html>

给Btn1设置了全局捕获之后,即使我们点击了Btn2还是会触发Btn1的点击事件

在模拟拖拽中,给要拖拽的方块onmousedown添加全局捕获然后再onmouseup中取消全局捕获

效果:点击查看

代码:

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
#box{
width: 100px;
height: 100px;
background: red;
position: absolute; }
</style>
</head>
<body> <div id="box">模拟拖拽</div>
<script>
var oBox = document.getElementById('box'); oBox.onmousedown = function(ev){
// 鼠标按下 var ev = ev || event; // 获取鼠标离div得距离
var mouseBoxleft = ev.clientX - this.offsetLeft;
var mouseBoxTop = ev.clientY - this.offsetTop; // IE浏览器,全局捕获
if(oBox.setCapture){
oBox.setCapture();
} document.onmousemove = function(ev){
// 鼠标按下左键并移动 var ev = ev || event; // 设置div移动时,它的位置
oBox.style.left = ev.clientX - mouseBoxleft + 'px';
oBox.style.top = ev.clientY - mouseBoxleft + 'px'; } document.onmouseup = function(){
// 鼠标左键抬起 document.onmousemove = document.onmouseup = null; //IE下,释放全局捕获 releaseCapture();
if ( oBox.releaseCapture ) {
oBox.releaseCapture();
}
} // 阻止默认行为
return false;
}
</script>
</body>
</html>

  

  【3】封装模拟拖拽函数

效果:点击查看

 代码:

 <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
#box{
width: 100px;
height: 100px;
background: red;
position: absolute; }
</style>
</head>
<body> <div id="box">模拟拖拽</div>
<script>
var oBox = document.getElementById('box'); drag(oBox); function drag(obj){
obj.onmousedown = function(ev){
// 鼠标按下 var ev = ev || event; // 获取鼠标离div得距离
var mouseBoxleft = ev.clientX - this.offsetLeft;
var mouseBoxTop = ev.clientY - this.offsetTop; // IE浏览器,全局捕获
if(obj.setCapture){
obj.setCapture();
} document.onmousemove = function(ev){
// 鼠标按下左键并移动 var ev = ev || event; // 设置div移动时,它的位置
obj.style.left = ev.clientX - mouseBoxleft + 'px';
obj.style.top = ev.clientY - mouseBoxleft + 'px'; } document.onmouseup = function(){
// 鼠标左键抬起 document.onmousemove = document.onmouseup = null; //IE下,释放全局捕获 releaseCapture();
if ( obj.releaseCapture ) {
obj.releaseCapture();
}
} // 阻止默认行为
return false;
}
} </script>
</body>
</html>

JavaScript动画-模拟拖拽的更多相关文章

  1. javascript动画系列第一篇——模拟拖拽

    × 目录 [1]原理介绍 [2]代码实现 [3]代码优化[4]拖拽冲突[5]IE兼容 前面的话 从本文开始,介绍javascript动画系列.javascript本身是具有原生拖放功能的,但是由于兼容 ...

  2. 每天一个JavaScript实例-html5拖拽

    <!DOCTYPE html> <html> <head> <meta http-equiv="Content-Type" content ...

  3. day25—JavaScript实现文件拖拽上传案例实践

    转行学开发,代码100天——2018-04-10 今天记录一个利用JavaScript实现文件拖拽上传到浏览器,后天将文件打开的小案例. 基本功能:1点击添加文件 2 文件拖拽添加 html: < ...

  4. 模拟拖拽图片 碰撞检测 DOM 鼠标事件 闭包

    <!doctype html><html lang="en"> <head> <meta charset="UTF-8" ...

  5. JavaScript:鼠标拖拽效果

    (之前的那个模板方法模式实在没搞懂...等几天再去研究8) 预览效果: 限制拖动范围在视口内.调整窗口时自动居中... <!DOCTYPE html> <html lang=&quo ...

  6. JavaScript实现图片拖拽、粘贴上传

    前些日子为老婆做了一个web管理商品的工具,因为商品的图片比较多并且还需要剪裁图,为了上传图片方便加了一个拖拽.粘贴上传的功能. 我已经把代码整理出来放到GitHub上了,有兴趣的朋友可以下来玩玩. ...

  7. javascript实现的拖拽回放

    这个功能很简单,直接贴代码啊: <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "ht ...

  8. c++ 发送消息,模拟拖拽文件

    #include <ShlObj.h> BOOL SimulateDropFile(CString strFilePath) { }; wcstombs(szFile, strFilePa ...

  9. Javascript之盒子拖拽(跟随鼠标、边界限定、轨迹回放)

    本文通过拖拽案例,实现"跟随鼠标.边界限定.轨迹回放"三大效果: 完整代码中有详尽注释,故不再进行细致讲解: 对于案例中需要注意的重点或易错点问题,会总结在最后. 效果图(仅演示左 ...

随机推荐

  1. 网站定位之---根据IP获得区域

    记得以前做一个培训机构网站时候需要定位,那时候用的搜狐的api,不是很精准. demo:https://github.com/dunitian/LoTCodeBase/tree/master/NetC ...

  2. PHP-解析验证码类--学习笔记

    1.开始 在 网上看到使用PHP写的ValidateCode生成验证码码类,感觉不错,特拿来分析学习一下. 2.类图 3.验证码类部分代码 3.1  定义变量 //随机因子 private $char ...

  3. WPF 微信 MVVM 【续】修复部分用户无法获取列表

    看过我WPF 微信 MVVM这篇文章的朋友,应该知道我里面提到了我有一个小号是无法获取列表的,始终也没找到原因. 前两天经过GitHub上h4dex大神的指导,知道了原因,是因为微信在登录以后,web ...

  4. EntityFramework.Extended 支持 MySql

    EntityFramework.Extended 默认不支持 MySql,需要配置如下代码: [DbConfigurationType(typeof(DbContextConfiguration))] ...

  5. Oracle手边常用70则脚本知识汇总

    Oracle手边常用70则脚本知识汇总 作者:白宁超 时间:2016年3月4日13:58:36 摘要: 日常使用oracle数据库过程中,常用脚本命令莫不是用户和密码.表空间.多表联合.执行语句等常规 ...

  6. C# 对象实例化 用json保存 泛型类 可以很方便的保存程序设置

    参考页面: http://www.yuanjiaocheng.net/webapi/test-webapi.html http://www.yuanjiaocheng.net/webapi/web-a ...

  7. linux yum命令详解

    yum(全称为 Yellow dog Updater, Modified)是一个在Fedora和RedHat以及SUSE中的Shell前端软件包管理器.基於RPM包管理,能够从指定的服务器自动下载RP ...

  8. 使用Jenkins配置Git+Maven的自动化构建

    Jenkins是一个开源的持续集成工具,应用Jenkins搭建持续集成环境,可以进行自动构建.自动编译和部署,非常方便. 在服务器比较少的情况下,Jenkins的优势并不明显,但是随着项目发展,服务器 ...

  9. #ifndef

    关于c的#ifndef条件编译: 1)最好把头文件的内容都放在#ifndef和#endif中 2)一般格式: #ifndef <标识> #define <标识> ...... ...

  10. Linux系统中用DNW向ARM开发板下载程序

    在Linux下通过dnw来给开发板发送程序.包括驱动程序代码:secbulk.c,应用程序代码:dnw.c.只能运行在32位系统上,在64位系统上提示错误:DNW download Data size ...