文档章节

移动端拖拽排序

十万猛虎下画山
 十万猛虎下画山
发布于 2016/11/30 18:07
字数 832
阅读 93
收藏 0

 

var drag = {
        bindDragEvent: function (isF) {
            var father = document.getElementById("public_theme_list");//父容器
            var btns = father.getElementsByClassName("public-drag-btn");//事件源对象
            var items = father.getElementsByClassName("item");//拖拽目标

            for (var i = 0; i < items.length; i++) {
                items[i].index = i;//给拖拽目标加index属性
                if (isF) {//是否是第一次绑定
                    drag.bindTouchEvent(btns[i], items[i], items);
                }else{
                    if (items[i].getAttribute("data-isBind") == "yes") {//如果是需要绑定的再绑定事件
                        items[i].removeAttribute("data-isBind");
                        drag.bindTouchEvent(btns[i], items[i], items);
                    }
                }
            }

            /*
            * 1.循环绑定事件
            * 2.用分支绑定是为了避免重复绑定事件 造成重复调用的BUG
            * */
        },
        bindTouchEvent: function (ele, target, items) {
            var dragObj = target;//拖拽目标
            var btn = ele;//事件源对象
            var canMove = true;
            var startY, direction;

            btn.addEventListener("touchstart", touchStart, false);

            function touchStart(event) {
                dragObj.className = "item draging";
                /*
                 * .draging
                * 当手指触摸时给个 拖拽中的效果
                * transform:scale(0.8,0.8);
                * z-index: 999;
                * transition: all 1s;
                * */

                startY = event.touches[0].clientY;//记录初次触摸位置 用以判断移动方向
                dragObj.addEventListener("touchmove", touchMove, false);//给拖拽目标绑定touchmove 因为要操作拖拽目标
            }


            function touchMove(event) {
                var i = dragObj.index;//用到index
                if (event.touches[0].clientY < startY && canMove) {
                    /*移动<开始  就是向上移动
                     *canMove是在完成效果后禁止再向下移动
                     * 也就是说用户移动一次就确定方向了 禁止先 拖到上方,在拖到下方
                    * */
                    if (i != 0) {//如果不是第一个项
                        direction = 1;//有效1 up
                        dragObj.className = "item draging up";
                        /*
                        * .up
                        *  transform: translate3d(20px,-100%,10px)
                        *  给一个自身向上移动百分百
                        * */
                        items[i - 1].className = "item draging down";
                        /*当前被拖拽目标的上一个项 给一个向下移动的动效
                        * .down
                        *  transform: translate3d(20px,100%,10px)
                        * */
                        canMove = false;
                    }
                }
                else if (event.touches[0].clientY > startY && canMove) {
                    direction = 0;//向下移动
                    dragObj.className = "item draging down";
                    items[i + 1].className = "item draging up";
                    canMove = false;
                }
                dragObj.addEventListener("touchend", touchEnd, false);
            }

            function touchEnd() {
                var father = document.getElementById("public_theme_list");
                var clone = null;//克隆空对象
                var i = dragObj.index;
                var newItems;
                dragObj.className = "item";//清除拖拽目标移动效果
                clone = dragObj.cloneNode(true);//克隆移动目标
                if (direction) {
                    //向上
                    items[i - 1].className = "item";//当前被拖拽目标的上一个项 给一个向下移动的动效
                    clone.index = i - 1;//给克隆对象index 为当前上一个项index
                    items[i - 1].index = i + 1;//拖拽对象前上一个项index+1

                    clone.setAttribute("data-isBind","yes");//dom 不能克隆事件 所以在递归的时候要给克隆绑定事件

                    father.insertBefore(clone,items[i - 1]);
                    /*将克隆对象插入当前拖拽目标 前一项之前*/
                    newItems = father.getElementsByClassName("item");
                    /*因为新增了项 所以获取新项数组*/
                    father.removeChild(newItems[i + 1]);
                    /*删除当前拖拽项*/
                }
                else {
                    items[i + 1].className = "item";
                    clone.index = i + 1;
                    clone.setAttribute("data-index", i + 1);
                    items[i + 1].index = i;
                    items[i + 1].setAttribute("data-index", i);

                    clone.setAttribute("data-isBind","yes");

                    father.insertBefore(clone, items[i + 2]);
                    newItems = father.getElementsByClassName("item");
                    father.removeChild(newItems[i]);
                }

                drag.bindDragEvent(false);//递归调用
            }
        }
    };

    drag.bindDragEvent(true);

 

其实应该还有一段AJAX代码,是将排序后的顺序index  POST给服务器记录下来,用户再次进入之后会根据token区分用户,显示不同的顺序。

 

一开始没有思路,其实最怕写的就是多媒体和触摸拖拽相关的代码了。

但是没办法,项目驱动学习啊~

自己死笨死笨的。。。这点代码从想思路,到写,到试错,整整6个小时。。。笨死我算了

不过学习了很多东西,没有用h5拖拽,是因为考虑兼容问题,主要是在webView 里跑,js还靠谱些..

 

笨死算逑!!!

© 著作权归作者所有

共有 人打赏支持
十万猛虎下画山
粉丝 3
博文 97
码字总数 68887
作品 0
西城
程序员
一步步实现一个自适应的react-native拖拽排序

最近由于业务需求需要实现一个功能需要实现图片的上传和排序和删除,在网上搜索了几款发现都需要固定列数,感觉不太友好,所以自己实现了一个可以不需要设定列数的排序,而且布局高度实现自适...

mochixuan
08/08
0
0
jquery ui --排序(Sortable)移动位置

新人刚接触这个jquery ui的能拖拽的排序 请问下 在我拖拽完了后 怎么能知道他向上或者下拖拽了几行 嗯 说白了就是定位下位置 因为要去改排序 让他拖拽完了后数据库里也变样的 请问下Sortabl...

一色琉璃
2016/01/11
1K
1
HTML5拖拽API实现vue树形拖拽组件

因业务场景需要一个可拖拽修改节点位置的树形组件,因此动手撸了一个,乘此机会摸了一把html5原生拖拽。近期有时间将核心部分代码抽出,简单说下实现方式。 1.树形结构-组件递归使用 树形结构...

花卷爱学习
05/10
0
0
玩转iOS开发:iOS 11 新特性《UICollectionView的拖拽》

文章分享至我的个人技术博客: cainrun.github.io/15102983446… 还记得在的时候, 苹果爸爸展示的拖拽功能是多么的牛逼, 实现了可夸应用的数据分享. 如果你有看过之前的玩转iOS开发:iOS 11 ...

CainLuo
2017/11/29
0
0
Swift开发:仿Clear手势操作(拖拽、划动、捏合)UITableView

这是一个完全依靠手势的操作ToDoList的演示,功能上左划删除,右划完成任务,拖拽调整顺序,捏合张开插入。 项目源码: https://github.com/luan-ma/ClearStyleDemo.Swift 初始化 TDCToDoIte...

luan.ma
2016/01/03
129
0

没有更多内容

加载失败,请刷新页面

加载更多

js 操作cookie

var cookie = {// 设置cookie方法 set:function(key,val,time){ var date = new Date(); //获取当前时间 var expiresDays = time; //将date设置为n天以后的时间...

小丶二
2分钟前
0
0
限制root远程登录 su和sudo命令

9月21日任务 3.7 su命令 3.8 sudo命令 3.9 限制root远程登录 对于Linux而言,权限的重要性毋庸置疑!对于普通用户而言无法执行那些只有root用户才能有效的命令,导致工作无法有效进行; 系统...

robertt15
4分钟前
0
0
MQTT协议的初浅认识之通讯级别和持久会话

背景 这是我最近了解MQTT协议的最后一部分内容了,MQTT协议里面的QOS和Keep Alive是两个比较重要的内容。QOS的设置,直接影响了订阅客户端与中间件之间的消息交互行为。而Keep Alive直接影响...

亚林瓜子
6分钟前
0
0
calc

width: calc(100% - 30px); 特别注意:减号左右空格,均不能去掉。 width: calc(100% - 30px);

柴高八斗之父
14分钟前
0
0
Spring Cloud Gateway全局过滤器GlobalFilter:返回消息和重定向

Spring Cloud Gateway的全局过滤器GlobalFilter,顾名思义,声明后会对所有的请求生效,可以用来做权限控制,这里简单记录一下拦截到非法请求后如何返回自定义信息和将请求重定向到指定URL。...

夜雨寄北09
16分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部