zoukankan      html  css  js  c++  java
  • js 拖拽排序

    现在做页面的经常会有用到拖拽的东西 ,我一直用的都是jquery的一些插件,但知其然,不知其所以然不是我想要的。起码对于经常会用到的东西还是尽可能多去了解点,所以就百度百度,书翻几下。想着自己也试着写个可以拖拽并自动排列的例子,起码了解一下。

    辅助js(主要是简化document.getElement(id) 这些的写法)

    如下代码:(可略过不看 代码最后会提供下载,并且不关拖拽具体实现)


    复制代码
     1 (function (window) {
     2     var regId = /^#[\w\-]+$/,
     3     regCls = /^.[\w\-]+$/,
     4     //从园子里某位前辈那里看来的(有点时间了 忘记在哪), Array.prototype.slice.call是把一个伪数组变为数组,具体百度
     5     p_silice = Array.prototype.slice,  
     6     p_push = Array.prototype.push,
     7     markArr = function (obj) {
     8         return p_silice.call(obj, 0);
     9     };
    10     function MWood(selector) {
    11         return new MWood.prototype.init(selector);
    12     };
    13 
    14     function MWood(selector, context) {
    15         return new MWood.prototype.init(selector, context);
    16     }
    17 
    18     MWood.prototype = {
    19         init: function (selector) {
    20             if (regId.test(selector)) {
    21                 this.length = 1;
    22                 this[0] = document.getElementById(selector);
    23                 return this;
    24             }
    25             else if (regCls.test(selector)) {
    26                 if (document.querySelectorAll) {
    27                     p_push.apply(this, markArr(document.querySelectorAll(selector)));
    28                 } else {
    29                     var len = documenet.getElementsByTagName('*').length,
    30                     clsArr = [],
    31                     el, i = 0,
    32                     selector = selector.replace(/\-/g, "\\-");
    33                     var oRegExp = new RegExp("(^|\\s)" + selector + "(\\s|$)");
    34 
    35                     for (; i < len; i++) {
    36                         el = els[i];
    37                         if (oRegExp.test(el[type])) {
    38                             clsArr.push(el);
    39                         }
    40                     }
    41 
    42                     pro_push.apply(this, markArr(clsArr));
    43                     return this;
    44                 }
    45             }
    46         },
    47         length: 0
    48     }
    49 
    50     MWood.prototype.init.prototype = MWood.prototype;
    51 
    52     MWood.extend = function (obj) {
    53         for (var o in obj) {
    54             this[o] = obj[o];
    55         }
    56     }
    57 
    58     MWood.extend({
    59         addHandle: function (elm, type, fn) {
    60             if (elm.addEventListener) {
    61                 elm.addEventListener(type, fn, false);
    62             }
    63             else if (el.attachEvent) {
    64                 elm.attachEvent("on" + type, fn);
    65             } else {
    66                 elm["on" + type] = fn;
    67             }
    68         },
    69         removeHandle: function (elm, type, fn) {
    70             if (elm.removeEventListener) {
    71                 elm.removeEventListener(type, fn, false);
    72             }
    73             else if (el.detachEvent) {
    74                 elm.detachEvent("on" + type, fn);
    75             } else {
    76                 elm["on" + type] = null;
    77             }
    78         },
    79         getEvent: function (evnet) {
    80             return evnet ? evnet : window.evnet;
    81         },
    82         getTarget: function (event) {
    83             return event.target || event.srcElement;
    84         }
    85     });
    86 
    87     window.MWood = MWood;
    88 
    89 })(this);
    复制代码
     1 (function (window) {
     2     var regId = /^#[\w\-]+$/,
     3     regCls = /^.[\w\-]+$/,
     4     //从园子里某位前辈那里看来的(有点时间了 忘记在哪), Array.prototype.slice.call是把一个伪数组变为数组,具体百度
     5     p_silice = Array.prototype.slice,  
     6     p_push = Array.prototype.push,
     7     markArr = function (obj) {
     8         return p_silice.call(obj, 0);
     9     };
    10     function MWood(selector) {
    11         return new MWood.prototype.init(selector);
    12     };
    13 
    14     function MWood(selector, context) {
    15         return new MWood.prototype.init(selector, context);
    16     }
    17 
    18     MWood.prototype = {
    19         init: function (selector) {
    20             if (regId.test(selector)) {
    21                 this.length = 1;
    22                 this[0] = document.getElementById(selector);
    23                 return this;
    24             }
    25             else if (regCls.test(selector)) {
    26                 if (document.querySelectorAll) {
    27                     p_push.apply(this, markArr(document.querySelectorAll(selector)));
    28                 } else {
    29                     var len = documenet.getElementsByTagName('*').length,
    30                     clsArr = [],
    31                     el, i = 0,
    32                     selector = selector.replace(/\-/g, "\\-");
    33                     var oRegExp = new RegExp("(^|\\s)" + selector + "(\\s|$)");
    34 
    35                     for (; i < len; i++) {
    36                         el = els[i];
    37                         if (oRegExp.test(el[type])) {
    38                             clsArr.push(el);
    39                         }
    40                     }
    41 
    42                     pro_push.apply(this, markArr(clsArr));
    43                     return this;
    44                 }
    45             }
    46         },
    47         length: 0
    48     }
    49 
    50     MWood.prototype.init.prototype = MWood.prototype;
    51 
    52     MWood.extend = function (obj) {
    53         for (var o in obj) {
    54             this[o] = obj[o];
    55         }
    56     }
    57 
    58     MWood.extend({
    59         addHandle: function (elm, type, fn) {
    60             if (elm.addEventListener) {
    61                 elm.addEventListener(type, fn, false);
    62             }
    63             else if (el.attachEvent) {
    64                 elm.attachEvent("on" + type, fn);
    65             } else {
    66                 elm["on" + type] = fn;
    67             }
    68         },
    69         removeHandle: function (elm, type, fn) {
    70             if (elm.removeEventListener) {
    71                 elm.removeEventListener(type, fn, false);
    72             }
    73             else if (el.detachEvent) {
    74                 elm.detachEvent("on" + type, fn);
    75             } else {
    76                 elm["on" + type] = null;
    77             }
    78         },
    79         getEvent: function (evnet) {
    80             return evnet ? evnet : window.evnet;
    81         },
    82         getTarget: function (event) {
    83             return event.target || event.srcElement;
    84         }
    85     });
    86 
    87     window.MWood = MWood;
    88 
    89 })(this);
    复制代码

    拖拽js

    复制代码
    window.onload = function () {
        var dragDrop = function () {
            var dragInfo = {};   //存放有关拖拽对象的一些信息
            function handleEvent(event) {
                e = MWood.getEvent(event);  //获得事件
                var target = MWood.getTarget(event); //获得事件对象
                switch (event.type) {   //判断事件类型
                    case "mousedown":
                        if (target.className.indexOf("droggle") > -1) {
                            dragInfo.dObj = target;   //存放事件对象
                            var tlwh = getObjtlwh(target); //获得对象的 offsetTop,offsetLeft,offsetWidth,offsetHeight
                            //计算出鼠标的坐标与对象offsetTop,offsetLeft的差值以便于鼠标移动时实时定位拖拽对象的位置
                            target.x = e.clientX - tlwh[1];
                            target.y = e.clientY - tlwh[0];
    
                            //修改对象的position以便可以设置left和top进行拖拽 从这里开始此对象已经脱离文档流
                            //何为文档流 当怎么样设置position或别的设置会脱离文档流请百度
                            target.style.position = "absolute";
    
                            //设置拖拽对象的left top width height
                            target.style.left = tlwh[1] + "px";
                            target.style.top = tlwh[0] + "px";
                            target.style.width = tlwh[2] + "px";
                            target.style.height = tlwh[3] + "px";
    
                            //建立一个新对象填补被拖拽对象的位置,这样页面就还会按现在的排版,不会有任何更改。
                            //如果没创建,被拖拽对象的位置就会被文档流上的其他对象占用,文章最后提供代码,可以注释掉下面4句试下两种情况
                            dragInfo.vObj = document.createElement("div");
                            dragInfo.vObj.style.width = target.style.width;
                            dragInfo.vObj.style.height = target.style.height;
                            target.parentNode.insertBefore(dragInfo.vObj, target);
                        }
                        break;
                    case "mousemove":
                        if (dragInfo.dObj) {  //当鼠标移动的时候判断时候已经有对象存在(对象会在mousedown的时候存放进这个变量里)
                            //设置拖拽对象的left和top改变位置,因为position已经在mousedown的时候改变为absolute了(鼠标坐标-保存的差值)
                            dragInfo.dObj.style.left = (e.clientX - dragInfo.dObj.x) + "px";
                            dragInfo.dObj.style.top = (e.clientY - dragInfo.dObj.y) + "px";
    
                            //获取class为droggle的一组HTMl对象.Array.prototype.slice.call是给一个伪数组转为真正的数组用的,MWood(".droggle")就是取得class为droggle的一组对象
                            var arr = Array.prototype.slice.call(MWood(".droggle"), 0);
    
                            //循环对象
                            for (var i = 0; i < arr.length; i++) {
                                if (arr[i] === dragInfo.dObj)  //过滤拖拽对象
                                    continue;
                                var tlwh = getObjtlwh(arr[i]); //获得对象的 offsetTop,offsetLeft,offsetWidth,offsetHeight
    
                                //下面就主要是判断鼠标的位置是否为引起页面上各HTML元素在页面上位置的替换
                                //判断鼠标x > 对比对象offsetLeft && x < (对比对象的offsetWidth + 对象对象offsetLef)。 鼠标的坐标y同理鼠标坐标x的判断
                                //判断位置变换也可以按自己的标准来,我百度的时候看到例子里是这样判断我就直接像他那样写了
                                if (e.x > tlwh[1] && e.x < (tlwh[1] + tlwh[2]) && e.y > tlwh[0] && e.y < (tlwh[0] + tlwh[3])) {
                                    if (e.y < ((tlwh[0] + tlwh[3]) / 2)) {
                                        arr[i].parentNode.insertBefore(dragInfo.vObj, arr[i]);
                                        break;
                                    }
                                    else {
                                        if (!arr[i].nextSibling) {
                                            arr[i].parentNode.appendChild(dragInfo.vObj);
                                            break;
                                        }
                                        else {
                                            arr[i].parentNode.insertBefore(dragInfo.vObj, arr[i].nextSibling);
                                            break;
                                        }
                                    }
                                }
                            }
                        }
                        break;
                    case "mouseup":
                        if (dragInfo.dObj) {
                            //把拖拽对象重新弄进文档流(static就是默认的值),替换临时占位的对象,并初始化dragInfo;
                            dragInfo.dObj.style.position = "static";
                            dragInfo.vObj.parentNode.insertBefore(dragInfo.dObj, dragInfo.vObj);
                            dragInfo.dObj.parentNode.removeChild(dragInfo.vObj);
                            dragInfo = {};
                        }
                        break;
                }
            };
    
            //绑定事件
            MWood.addHandle(document, "mousedown", handleEvent);
            MWood.addHandle(document, "mousemove", handleEvent);
            MWood.addHandle(document, "mouseup", handleEvent);
        } ();
    };
    
    function getObjtlwh(o) {
        var arr = [];
        arr[0] = o.offsetTop;
        arr[1] = o.offsetLeft;
        arr[2] = o.offsetWidth;
        arr[3] = o.offsetHeight;
        return arr
    }
    复制代码

    下载点击       

    有什么问题或指教请留言。

     
     
    标签: javascript
  • 相关阅读:
    【洛谷3778】[APIO2017] 商旅(分数规划+Floyd)
    【AT4114】[ARC095D] Permutation Tree(简单题)
    【AT4352】[ARC101C] Ribbons on Tree(容斥+DP)
    【AT4169】[ARC100D] Colorful Sequences(DP)
    【洛谷4581】[BJOI2014] 想法(随机算法)
    【洛谷5659】[CSP-S2019] 树上的数(思维)
    【AT4439】[AGC028E] High Elements(线段树)
    【CF590E】Birthday(AC自动机+二分图匹配)
    【洛谷4298】[CTSC2008] 祭祀(Dilworth定理+二分图匹配)
    【洛谷3774】[CTSC2017] 最长上升子序列(杨表)
  • 原文地址:https://www.cnblogs.com/Leo_wl/p/2645218.html
Copyright © 2011-2022 走看看