js 实现拖拽

来源:互联网 发布:windows彩蛋星球大战 编辑:程序博客网 时间:2024/05/23 00:05

JavaScript基础入门学习,实现移动拖拽。适合新手学习和参考。不足之处希望大神提出你宝贵的意见。

一:实现简单的拖拽

二:实现浏览器的兼容性。在拖拽的过程中不会超出屏幕,当你拖拽物体放在那里,就是那里。如果放在右下角,缩小屏幕是,物体不会被遮罩。

实现效果:


一、简单的实现拖拽

一 界面设计

 

 

二 设计效果

       由于我们弹窗的遮罩我们采用了clientWidth和clientHeight,导致如果有滚动条,拖出的部分就会出现空白,我们可以尝试使用offset或者scroll获取实际或滚动条区域的内容进行遮罩,或者直接弹窗后直接去掉滚动条,禁止拖动即可。

document.documentElement.style.overflow='hidden';//禁止滚动条

document.documentElement.style.overflow='auto';//还原默认滚动条

 

       如果要设置物体拖拽,那么必须使用三个事件:mousedown, mousemove, mouseup这三个

 

1.直接写拖拽事件

Ø  拖拽流程

Ø  1.先点击鼠标

Ø  2.在点击下的物体被选中,进行move移动

Ø  3.抬起鼠标时,停止移动

Ø  4.点击某个物体,用moveDIv即可,move和up是全局区域,也就是整个页面通用,用过用document

//找到移动拖拽的区域(id获取)

    var moveDiv=document.getElementById('login');

    //实现一个鼠标按下效果

    moveDiv.onmousedown=function(){

         //拖动鼠标

         document.onmousemove=function(e){

             //浏览器兼容性

             var e=e||window.event;

             //获取X抽的位置

             moveDiv.style.left=e.clientX+'px';

             //获取Y抽的位置

             moveDiv.style.top=e.clientY+'px';

         };

         document.onmouseup=function(){//放开鼠标事件

             document.onmousemove=null;//清除鼠标移动事件

             document.onmouseup=null;//清除鼠标向上事件

         };

    };

 

备注:实现了拖动 但是 目前还存在一个为题。就是当鼠标按下移动时,鼠标会自动跳到右上角的点,而不是你鼠标按下的位置。

 

2.进一步完善拖拽事件

//找到移动拖拽的区域(id获取)

    var moveDiv=document.getElementById('login');

    moveDiv.onmousedown=function(e){//鼠标按下事件

        //浏览器的兼容性 主要是火狐浏览器

        var e = e || window.event;

        var dX=e.clientX-moveDiv.offsetLeft;

        var dY=e.clientY-moveDiv.offsetTop;

        //拖动鼠标

        document.onmousemove=function(e){

            //浏览器兼容性

            var e=e||window.event;

            //获取X抽的位置

            moveDiv.style.left=e.clientX-dX+'px';

            //获取Y抽的位置

            moveDiv.style.top=e.clientY-dY+'px';

 

        };

        document.onmouseup=function(){//放开鼠标事件

            document.onmousemove=null;//清除鼠标移动事件

            document.onmouseup=null;//清除鼠标向上事件

        };

    };

 

 

3.封装浏览器兼容并调用

//找到移动拖拽的区域(id获取)

    var moveDiv=document.getElementById('login');

    moveDiv.onmousedown=function(e){//鼠标按下事件

        var e = getEvent(e);//调用封装的对象window.event||e

        //_this==moveDiv

        var _this=this;

        var dX=e.clientX-_this.offsetLeft;

        var dY=e.clientY-_this.offsetTop;

        //拖动鼠标

        document.onmousemove=function(e){

            //浏览器兼容性

            var e=getEvent(e);//调用封装的对象window.event||e

            //获取X抽的位置

            _this.style.left=e.clientX-dX+'px';

            //获取Y抽的位置

            _this.style.top=e.clientY-dY+'px';

 

        };

        document.onmouseup=function(){//放开鼠标事件

            //this==document

            this.onmousemove=null;//清除鼠标移动事件

            this.onmouseup=null;//清除鼠标向上事件

        };

    };

 

3.1封装getEvent

//获取event对象

function getEvent(event){

    return window.event||event;

}

 

3.2封装整个拖拽事件

//封装拖拽事件

Base.prototype.drag=function(){

    for(var i=0; i<this.elements.length;i++){//遍历

        this.elements[i].onmousedown=function(e){//鼠标按下事件

        var e = getEvent(e);//调用封装的对象window.event||e

        //_this==moveDiv

        var _this=this;

        var dX=e.clientX-_this.offsetLeft;

        var dY=e.clientY-_this.offsetTop;

        //拖动鼠标

        document.onmousemove=function(e){

            //浏览器兼容性

            var e=getEvent(e);//调用封装的对象window.event||e

            //获取X抽的位置

            _this.style.left=e.clientX-dX+'px';

            //获取Y抽的位置

            _this.style.top=e.clientY-dY+'px';

 

        };

        document.onmouseup=function(){//放开鼠标事件

            //this==document

            this.onmousemove=null;//清除鼠标移动事件

            this.onmouseup=null;//清除鼠标向上事件

        };

     };   

 

 

    }

    return this;//返回再次调用 否则只能调用一次

};

 

4.调用拖拽事件(完成)

login.drag();//物体对象 调用拖拽事件

 

 

 

 

 

 

 


二、  主要是讲拖拽的一些问题进行修复

一 界面设计

二 设置效果

1.问题一:低版本的火狐在空的div拖拽时,有个bug,会拖段掉并且无法拖动,这个问题是火狐的默认行为,我们只需要取消这个默认行为即可解决这个bug。

1.1. 阻止默认行为

//阻止默认事件(跨浏览器)

function preDef(event){

       var e=getEvent(event);

       if(typeof e.preventDefault!=='undefined'){//W3C标准

              e.preventDefault();

       }else{//IE

              e.returnValue=false;

       }

}

2.问题二:弹出窗口被拖出浏览器的边缘会导致很多问题,比如出现滚动条,比如出现空白等,不利于输入等。所以,我们需要将其规定在可见的区域。

//解决空白和滚动条问题

//判断如果左边的距离为零 就不能拖出去

if(left<0){//判断(小于零就不能被拖出去)

    left=0;

}else if(left>getInner().width-_this.offsetWidth){

     left=getInner().width-_this.offsetWidth;

}

//判断山下的距离

if(top<0){//判断(小于零就不能被拖出去)

    top=0;

}else if(top>getInner().height-_this.offsetHeight){

    top=getInner().height-_this.offsetHeight;

}

 

3.问题三:IE浏览器在拖拽出浏览器外部的时候,还会出现空白,这个bug是IE独有的,我们需要阻止这种行为。

       IE浏览器有两个独有的方法:setcapture,releaseCapture,这两方法,可以让鼠标滑动到浏览器外部也可以捕获到事件,而我们的bug就是当鼠标移除浏览器的时候,限制超过的功能就消失。

鼠标锁住时触发(点击住)

//解决IE的bug鼠标释放时触发(放开鼠标)

                     if(typeof _this.releaseCapture!='undefined'){

                            _this.releaseCapture()

                     }

 

 

鼠标释放时触发(放开鼠标)

//解决IE的bug鼠标释放时触发(放开鼠标)

                     if(typeof _this.releaseCapture!='undefined'){

                            _this.releaseCapture()

                     }

 

 

4.问题四:当我们改变浏览器大小的时候,弹窗会自动水平垂直居中,而使用了拖拽效果后,改变浏览器大小,还是会水平居中,这样的用户体验就不是很好,我们需要的是等当拖到哪里。就是哪里,但拖放到右下角,然后又缩放时,还嫩全部显示出来。

//触发浏览器窗口事件

Base.prototype.resize=function(fn){

       for(var i=0; i<this.elements.length;i++){

              var element=this.elements[i];

              window.onresize=function(){

                     fn();

                     if(element.offsetLeft>getInner().width-element.offsetWidth){

                            element.style.left=getInner().width-element.offsetWidth+'px';

                     }

                     if(element.offsetTop>getInner().height-element.offsetHeight){

                            element.style.top=getInner().height-element.offsetHeight+'px';

                     }

              };

       }

       return this;

};

5.完成

window.onload=function(){

       //个人中心

       //找到该区域实现鼠标移入移除方法

       var info=$().getClass('centerInfo');

       info.hover(function(){

                     //添加鼠标移入改变的样式

                     info.css('background','url(images/s2.png) no-repeat 70px center').addClass('a');

                     $().getTagName('ul').show();//显示

              },function(){

                     //添加鼠标移入返回原来的样式

                     info.css('background','url(images/s1.png) no-repeat 70px center').css('color','#000');

                     $().getTagName('ul').hide();//隐藏

              });

             

       //登录

       //设置物体居中、触发浏览器事件

       var login=$().getId('login');

       var screen=$().getId('screen');

       login.center(350,250).resize(function(){

              if(login.css('display')==='block'){//登录弹框打开时才执行锁屏

                     screen.lock();

              }

       });

       //点击事件 打开关闭

       $().getClass('logBtn').click(function(){

              login.css('display','block');

              screen.lock();

       });

       $().getClass('close').click(function(){

              login.css('display','none');

              screen.unlock();

       });

      

       //拖拽

       login.drag();

      

};

 

6.封装的拖拽事件drag();

//封装拖拽事件

Base.prototype.drag=function(){

       for(var i=0; i<this.elements.length;i++){//遍历

              this.elements[i].onmousedown=function(e){//鼠标按下事件

              preDef(e);//组织默认行为

              var e = getEvent(e);//调用封装的对象window.event||e

              //_this==moveDiv

              var _this=this;

              var dX=e.clientX-_this.offsetLeft;

              var dY=e.clientY-_this.offsetTop;

              //解决IE浏览器的bug鼠标锁住时触发(点击住)

              if(typeof _this.setCapture!='undefined'){

                     _this.setCapture();

              }

              //拖动鼠标

              document.onmousemove=function(e){

                     //浏览器兼容性

                     var e=getEvent(e);//调用封装的对象window.event||e

                     var left=e.clientX-dX;//左边的距离

                     var top=e.clientY-dY;//上边的距离

                     //解决空白和滚动条问题

                     //判断如果左边的距离为零 就不能拖出去

                     if(left<0){//判断(小于零就不能被拖出去)

                            left=0;

                     }else if(left>getInner().width-_this.offsetWidth){

                            left=getInner().width-_this.offsetWidth;

                     }

                     //判断山下的距离

                     if(top<0){//判断(小于零就不能被拖出去)

                            top=0;

                     }else if(top>getInner().height-_this.offsetHeight){

                            top=getInner().height-_this.offsetHeight;

                     }

                     //获取X抽的位置

                     _this.style.left=left+'px';

                     //获取Y抽的位置

                     _this.style.top=top+'px';

                    

              };

              document.onmouseup=function(){//放开鼠标事件

                     //this==document

                     this.onmousemove=null;//清除鼠标移动事件

                     this.onmouseup=null;//清除鼠标向上事件

                     //解决IE的bug鼠标释放时触发(放开鼠标)

                     if(typeof _this.releaseCapture!='undefined'){

                            _this.releaseCapture()

                     }

              };

        };  

             

             

       }

       return this;//返回再次调用 否则只能调用一次

};

 

 

0 0
原创粉丝点击