这次是要对上一篇的内容进行扩展。

由于需要对可拖动的 DIV 进行一个区域范围的限制,所以要给于一个容器,让可拖动的 DIV 元素不能逃出该容器的大小范围。

一、思路

1.在外层增加一个 DIV 容器,并设置好容器的大小。(即:宽和高)

当容器存在边框的时候,由于这里还没找到获取的方法,所以,在容器边框大于 0 的时候,获得的容器的限制区域的坐标会有误差。

为了避免这情况,可以在多加一次容器,有边框样式的在外层,无边框样子的在内层。

例:

<style>#mainContainer {border: 10px solid #990000;width: 600px;height: 300px;}#innerContainer {width: 100%;height: 100%;}#Drag {/*border: 5px solid #C4E3FD;*/background: #C4E3FD;width: 50px;height: 50px;top: 50px;left: 50px;z-index: 2;}#Drag2 {/*border: 5px solid #C4E3FD;*/background: #ff0000;width: 50px;height: 50px;top: 50px;left: 50px;z-index: 3;}
</style><div id="mainContainer"><div id="innerContainer"><div id="Drag" onmousedown="moveBind(this, event)">1</div><div id="Drag2" onmousedown="moveBind(this, event)">2</div></div>
</div>
<br />拖放状态:<span id="idShow">未开始</span>

2.为了方便获得元素的位置和大小,先写一个方法来辅助(谷歌不能用了可恶orz,只能百度出这个方法并稍微做点修改)。

    //获得元素的坐标与大小。function findPosition(oElement) {var x2 = 0;var y2 = 0;var width = oElement.clientWidth;var height = oElement.clientHeight;//alert(width + "=" + height);if (typeof (oElement.offsetParent) != 'undefined') {for (var posX = 0, posY = 0; oElement; oElement = oElement.offsetParent) {posX += oElement.offsetLeft;posY += oElement.offsetTop;}x2 = posX + width;y2 = posY + height;return [posX, posY, x2, y2, width, height];} else {x2 = oElement.x + width;y2 = oElement.y + height;return [oElement.x, oElement.y, x2, y2, width, height];}}

这里以数组的形式返回元素的 X 开始坐标和 Y 开始坐标,X 结束坐标和 Y 结束坐标,元素真实的宽与高(不算边框)

3.在鼠标按下事件里,先获得容器的位置数据:

//获得容器坐标。
var container = findPosition(document.getElementById("innerContainer"));
var containerLeft = container[0];
var containerTop = container[1];
var containerWidth = container[4];
var containerHeight = container[5];

4.计算拖动 DIV 元素可移动的区域坐标:

/*计算出容器的范围坐标。*///开始 X 坐标。
var startX = containerLeft;
//开始 Y 坐标。
var startY = containerTop;
//结束 X 坐标。
var maxX = startX + containerWidth - width;
//结束 Y 坐标。
var maxY = startY + containerHeight - height;

开始 X 坐标 = 容器的左上角 X 坐标。

开始 Y 坐标 = 容器的左上角 Y 坐标。

结束 X 坐标 = 开始 X 坐标 + 容器的宽度 - 拖动 DIV 元素的宽度

结束 Y 坐标 = 开始 Y 坐标 + 容器的高度 - 拖动 DIV 元素的高度

5.当区域内存在多个可拖动的 DIV 元素时,要把当前鼠标点击的那个 DIV 设置成置顶显示。

    //获得最大 Z 坐标。function getMaxIndex() {var index = 0;var ds = document.getElementById('innerContainer').getElementsByTagName('div');var length = document.getElementById('innerContainer').getElementsByTagName('div').length;for (var loop = 0; loop < length; loop++) {if (ds[loop].style.zIndex > index) index = ds[loop].style.zIndex;}return parseInt(index);}

该方法遍历容器内的所有 DIV 元素(即:可拖动元素),取得它们当中z-Index最大的值。

然后,设置点击元素的 z-Index 值:

//鼠标选中的元素设置成顶层。
obj.style.zIndex = getMaxIndex() + 1;

/*******************以上方法是在鼠标按下事件里 onmousedown  ******************/

/*******************以下方法是在鼠标按下事件里 onmousemove ******************/

6.在移动事件里,修改元素位置的外层加上如下这条件。

            //不可以超出指定的范围。if (moveLeft >= startX && moveTop >= startY && moveLeft <= maxX && moveTop <= maxY) {//当移动位置在范围内时,元素跟随鼠标移动。obj.style.left = moveLeft + "px";obj.style.top = moveTop + "px";}

这条件表示:移动的位置在容器范围内时,元素才可以跟随鼠标移动。

但是,现在这样的做法,当鼠标快速拖出容器区域时,元素就会停止不动,但并没有移动到最边界,同时,鼠标在区域外并没有放开按键,移动鼠标时元素并不会跟着移动。

解决的思路是:

(1)当元素水平(X坐标)移动的位置没有达到或超出容器限制区域的 X 坐标区域时。

继续修改拖动元素的 X 坐标位置。

(2)当元素水平(X坐标)移动的位置超出容器限制区域的最大 X 坐标(即:容器右下角的 X 坐标)区域时(即:限制区域的右边),将元素的 X 坐标设置成最大 X 坐标值。

if (moveLeft >= startX && moveLeft <= maxX) {obj.style.left = moveLeft + "px";} else if (moveLeft > maxX) {obj.style.left = maxX + "px";}

(3)当元素水平(X坐标)移动的位置小于容器限制区域的开始 X 坐标(即:容器左上角的 X 坐标)区域时(即:限制区域的左边),将元素的 X 坐标设置成最小 X 坐标值。

                if (moveLeft >= startX && moveLeft <= maxX) {obj.style.left = moveLeft + "px";} else if (moveLeft > maxX) {obj.style.left = maxX + "px";} else if (moveLeft < startX) {obj.style.left = startX + "px";}

(4)Y 坐标同以上(1)(2)(3):

                if (moveTop >= startY && moveTop <= maxY) {obj.style.top = moveTop + "px";} else if (moveTop > maxY) {obj.style.top = maxY + "px";} else if (moveTop < startY) {obj.style.top = startY + "px";}

完成了!这时,鼠标拖动到区域外面时,元素同样会跟随鼠标的位置在容器内移动。

二、以下是完整源码:

JS部分:

    //获得元素的坐标与大小。function findPosition(oElement) {var x2 = 0;var y2 = 0;var width = oElement.clientWidth;var height = oElement.clientHeight;//alert(width + "=" + height);if (typeof (oElement.offsetParent) != 'undefined') {for (var posX = 0, posY = 0; oElement; oElement = oElement.offsetParent) {posX += oElement.offsetLeft;posY += oElement.offsetTop;}x2 = posX + width;y2 = posY + height;return [posX, posY, x2, y2, width, height];} else {x2 = oElement.x + width;y2 = oElement.y + height;return [oElement.x, oElement.y, x2, y2, width, height];}}function moveBind(obj, evnt) {//获得元素坐标。var left = obj.offsetLeft;var top = obj.offsetTop;var width = obj.offsetWidth;var height = obj.offsetHeight;//计算出鼠标的位置与元素位置的差值。var cleft = evnt.clientX - left;var ctop = evnt.clientY - top;//获得容器坐标。var container = findPosition(document.getElementById("innerContainer"));var containerLeft = container[0];var containerTop = container[1];var containerWidth = container[4];var containerHeight = container[5];/*计算出容器的范围坐标。*///开始 X 坐标。var startX = containerLeft;//开始 Y 坐标。var startY = containerTop;//结束 X 坐标。var maxX = startX + containerWidth - width;//结束 Y 坐标。var maxY = startY + containerHeight - height;//鼠标选中的元素设置成顶层。obj.style.zIndex = getMaxIndex() + 1;//输出显示。//show("idShow", startX, startY);
document.onmousemove = function (doc) {//计算出移动后的坐标。var moveLeft = doc.clientX - cleft;var moveTop = doc.clientY - ctop;//设置成绝对定位,让元素可以移动。obj.style.position = "absolute";//不可以超出指定的范围。if (moveLeft >= startX && moveTop >= startY && moveLeft <= maxX && moveTop <= maxY) {//当移动位置在范围内时,元素跟随鼠标移动。obj.style.left = moveLeft + "px";obj.style.top = moveTop + "px";} else {/****************以下为处理当鼠标的位置不在范围内里,鼠标的移动,里面的元素也要跟着移动*****************///向右移动时,如果移动坐标没有大于最大 X 坐标,则移动,否则设置成最大 X 坐标的值。if (moveLeft >= startX && moveLeft <= maxX) {obj.style.left = moveLeft + "px";} else if (moveLeft > maxX) {obj.style.left = maxX + "px";} else if (moveLeft < startX) {obj.style.left = startX + "px";}//向下移动时,如果移动坐标没有大于最大 Y 坐标,则移动,否则设置成最大 Y 坐标的值。if (moveTop >= startY && moveTop <= maxY) {obj.style.top = moveTop + "px";} else if (moveTop > maxY) {obj.style.top = maxY + "px";} else if (moveTop < startY) {obj.style.top = startY + "px";}}show("idShow", moveLeft, moveTop);}document.onmouseup = function () {document.onmousemove = function () { }};}//获得最大 Z 坐标。function getMaxIndex() {var index = 0;var ds = document.getElementById('innerContainer').getElementsByTagName('div');var length = document.getElementById('innerContainer').getElementsByTagName('div').length;for (var loop = 0; loop < length; loop++) {if (ds[loop].style.zIndex > index) index = ds[loop].style.zIndex;}return parseInt(index);}//显示坐标信息。function show(id, x, y) {document.getElementById(id).innerHTML = "left:" + x + ";top:" + y;}

HTML部分:

<style>#mainContainer {border: 10px solid #990000;width: 600px;height: 300px;}#innerContainer {width: 100%;height: 100%;}#Drag {/*border: 5px solid #C4E3FD;*/background: #C4E3FD;width: 50px;height: 50px;top: 50px;left: 50px;z-index: 2;}#Drag2 {/*border: 5px solid #C4E3FD;*/background: #ff0000;width: 50px;height: 50px;top: 50px;left: 50px;z-index: 3;}
</style><div id="mainContainer"><div id="innerContainer"><div id="Drag" onmousedown="moveBind(this, event)">1</div><div id="Drag2" onmousedown="moveBind(this, event)">2</div></div>
</div>
<br />拖放状态:<span id="idShow">未开始</span>

转载于:https://www.cnblogs.com/cjnmy36723/p/3945152.html

使用JS制作一个鼠标可拖的DIV(二)——限制区域移动相关推荐

  1. 使用JS制作一个鼠标可拖的DIV(三)——移动带图片DIV

    当DIV元素里,存在图片元素的时候,会使拖动出现异常. 因为图片元素本身就支持拖动,所以,只要在图片标签加入:draggable='false'. 如下: <div onmousedown=&q ...

  2. 使用 ale.js 制作一个小而美的表格编辑器(2)

    今天来教大家如何使用 ale.js 制作一个小而美的表格编辑器,首先先上 gif: 是不是还是有一点非常 cool 的感觉的?那么我们现在开始吧! 这是我们这篇文章结束后完成的效果(如果想继续完成请访 ...

  3. 使用 ale.js 制作一个小而美的表格编辑器(3)

    今天来教大家如何使用 ale.js 制作一个小而美的表格编辑器,首先先上 gif: 是不是还是有一点非常 cool 的感觉的?那么我们现在开始吧! 这是我们这篇文章结束后完成的效果(如果想继续完成请访 ...

  4. 用JS制作一个信息管理平台完整版

      前  言 JRedu 在之前的文章中,介绍了如何用JS制作一个实用的信息管理平台. 但是那样的平台功能过于简陋了,我们今天来继续完善一下. 首先我们回顾一下之前的内容.   1.JSON的基础知识 ...

  5. 使用 ale.js 制作一个小而美的表格编辑器(1)

    今天来教大家如何使用 ale.js 制作一个小而美的表格编辑器,首先先上 gif: 是不是还是有一点非常 cool 的感觉的?那么我们现在开始吧! 这是我们这篇文章结束后完成的效果(如果想继续完成请访 ...

  6. 使用 ale.js 制作一个小而美的表格编辑器(4)

    今天来教大家如何使用 ale.js 制作一个小而美的表格编辑器,首先先上 gif: 是不是还是有一点非常 cool 的感觉的?那么我们现在开始吧! 这是我们这篇文章结束后完成的效果(如果想继续完成请访 ...

  7. jsp循环输出表格_使用 ale.js 制作一个小而美的表格编辑器(1)

    今天来教大家如何使用 ale.js 制作一个小而美的表格编辑器,首先先上 gif: 是不是还是有一点非常 cool 的感觉的?那么我们现在开始吧! 这是我们这篇文章结束后完成的效果(如果想继续完成请访 ...

  8. 用html和js制作一个控制灯泡开关效果

    用html和js制作一个控制灯泡开关效果 **用css样式来控制div图片和文本的位置,然后用js里面onclick点击事件来控制图片的更换效果来实现当前运行图的效果** 1.以下是运行的效果图 2. ...

  9. 教你用html+js制作一个自己的点名系统,实例代码分享

    简介 教你用html+js制作一个自己的点名系统,实例代码如下. 效果 代码 HTML <div class="wrapper"><h1 align=" ...

  10. js制作一个简单的div弹窗:

    js制作一个简单的div弹窗: 演示地址:http://demo.jb51.net/js/2015/jquery-simple-alert-style-demo/ <!DOCTYPE html ...

最新文章

  1. jupyter 写入csv pandas_Pandas 最详细教程在这里
  2. 专属程序员的编程日历,终于来了 | 10月书讯
  3. OpenCV alpha(权因子) 融合举例
  4. 认真工作的原因以及方法
  5. 【javascript】数字相加
  6. 关于 Orbeon form PE 版本 Unauthorized 错误消息
  7. 在ASP.NET Core 2.0中创建Web API
  8. 【报告分享】2021中国数据智能产业发展研究报告.pdf(附下载链接)
  9. android 如何从服务器端的数据库中拿数据,在客户端显示类?
  10. 关于mysql使用命令行时出现Data too long for column的解决方案:
  11. 时间序列分析工具箱——tibbletime
  12. 联邦学习-安全树模型 SecureBoost之终章
  13. 计算机网络-应用层笔记
  14. DOSBox常用快捷键
  15. 免费不限流的内网穿透,外网共享内网文件
  16. 手机app访问服务器数据库数据库文件夹,手机app怎么访问服务器数据库
  17. 教大家用python画皮卡丘的脸
  18. java8 协程_Java8 异步编程—CompletableFuture
  19. 百度文字识别OCR接口使用
  20. python实现输入一个正整数_Python中实现输入一个整数的案例

热门文章

  1. Moss网站在不同服务器的迁移
  2. Python3:递归实现输出目录下所有的文件
  3. 18-09-06天津 关于Excel的一些操作
  4. 035 spring amqp
  5. 如何在TP-LINk WR340G中禁用端口
  6. 如何自定义IHttpModule
  7. Linux之vim常用扩展操作
  8. JMeter学习笔记(四)
  9. iOS codeview
  10. 怎样成为PHP 方向的一个合格的架构师(转)