Jquery easyui treegrid实现树形表格的行拖拽

前几天修改了系统的一个功能——实现树形列列表的行拖拽,以达到排序的目的。现在基本上功能实现,现做一个简单的总结。

1.拿到这个直接网上搜,有好多,但是看了后都觉得不是太复杂就是些不是特别想看的例子,自己太懒(对自己不是很熟悉的东西是不愿意第一去看的)。结果选择良久,还是jquery easyui treegrid这个例子自己看起来比较熟悉。于是就专心研究了,从官方网站http://www.jeasyui.net/下载了demo,开始研读。先把jsp页面一些代码贴出

<link rel="stylesheet" type="text/css" href="../css/treegrid/default/easyui.css">
<link rel="stylesheet" type="text/css" href="../css/treegrid/icon.css">
<link rel="stylesheet" type="text/css" href="../css/treegrid/treegrid.css">
<script type="text/javascript" src="../js/jquery-1.8.0.min.js"></script>
<script type="text/javascript" src="../js/jquery.easyui.min.js"></script>
<script type="text/javascript" src="../js/treegrid-dnd.js"></script>
<script type="text/javascript">


$(function(){ //初始化弹出对话框 $('#win').window('close'); $('#tt').treegrid({ // data:data, url:'catalogListItem', method:'post', dataType:'json', rownumbers: true, singleSelect:true, idField: 'id', treeField: 'title', animate:true, columns:[[ {field:'id',title:'ckc',checkbox:true}, {field:'title',title:'分类名称',width:400,align:'left',editor:'text'}, {field:'sortid',title:'排序值',width:100,align:'left',editor:'text'}, {field:'creatorNick',title:'创建者',width:100}, {field:'createdTime',title:'创建时间',width:220}, {field:'operate',title:'操作',width:220, formatter: function(value,row,index){ var html=''; html+='<a onclick="showedit(\'编辑\','+row.id+')" >编辑 </a> '; //html+=value+'<a onclick="editrow('+row+')" >编辑 </a> <a id="cancel" onclick="cancel()"></a>'; if(row.level==0){ html+=' <a href="#" onclick="Confirm(\'确认删除这个分类及其子类\','+row.id+')">删除</a> '; html+='<a href="#" onclick="showedit(\'新建\','+row.id+')">新建子节点</a> ';//默认只有二级节点 } else html+=' <a href="#" onclick="Confirm(\'确认删除这个记录\','+row.id+')">删除</a> '; return html; } } ]], onLoadSuccess: function(row){ //$(this).treegrid('enableDnd', row?row.id:null);
//上面的代码是demo中的,但是对于要保存更改到数据库显然走不通,需要向其他办法

//启用拖动排序 enableDnd($('#tt')); } }); });
//进入修改/添加 type:操作类型 id:编辑时,当前记录的id;添加时当前记录的id(添加第一级节点id要作特殊处理)
function showedit(type,id){ $("#form")[0].reset(); $('#win').window('open'); if(type=='编辑'){ $.ajax({ url:'catalogGet?id='+id, type:'post', dataType:'json', cache:false, success:function(data){ $("#title").val(data[0].title); $("#sortid").val(data[0].sortid); $("#id").val(id); } }); } else { $("#parentId").val(id); } } //保存 function save(){ var title= $("#title").val(); var sortid=$("#sortid").val(); var id=$("#id").val(); var parentId=$("#parentId").val(); $.ajax({ url:'catalogEdit', data:{"title":title,"sortid":sortid,"id":id,"parentId":parentId}, type:'post', dataType:'json', success: function(data) { if(data.result){ $('#win').window('close'); $('#tt').treegrid('reload'); } else alert(data.result); } }); }
//是否删除
function Confirm(msg,id) { $.messager.confirm("确认", msg, function (r) { if (r) { //请求 $.ajax({url:'catalogDelete?id='+id, type:'post', dataType: 'json', success:// function (data) { if(data){ $('#tt').treegrid('reload'); } else alert("faile"); } }); } }); return false; }

 

 

想到拖动的话,一定会用到jquery easyui 中draggable这个,但是这也不会写啊,看看demo按照那个写了一个,不合适,放弃了。想着着一定会有哪位这方面的前辈写好了,就各种百度和google,经过各种实验,找到一个就是上面  onLoadSuccess  里的  enableDnd($('#tt'));摘自一个论坛http://www.jeasyui.com/forum/index.php?topic=575.0

function enableDnd(t) {

        var nodes = t.treegrid('getPanel').find('tr[node-id]');

        nodes.find('span.tree-hit').bind('mousedown.treegrid', function() {

            return false;

        });

        nodes.draggable({

            disabled: false,

            revert: true,

            cursor: 'pointer',

            proxy: function(source) {

                var p = $('<div class="tree-node-proxy tree-dnd-no"></div>').appendTo('body');

                p.html($(source).find('.tree-title').html());

                p.hide();

                return p;

            },

            deltaX: 15,

            deltaY: 15,

            onBeforeDrag: function() {

                $(this).next('tr.treegrid-tr-tree').find('tr[node-id]').droppable({ accept: 'no-accept' });

            },

            onStartDrag: function() {

                $(this).draggable('proxy').css({

                    left: -10000,

                    top: -10000

                });

            },

            onDrag: function(e) {

                $(this).draggable('proxy').show();

                this.pageY = e.pageY;

            },

            onStopDrag: function() {

                $(this).next('tr.treegrid-tr-tree').find('tr[node-id]').droppable({ accept: 'tr[node-id]' });

            }

        }).droppable({

            accept: 'tr[node-id]',

            onDragOver: function(e, source) {

                var pageY = source.pageY;

                var top = $(this).offset().top;

                var bottom = top + $(this).outerHeight();

                $(source).draggable('proxy').removeClass('tree-dnd-no').addClass('tree-dnd-yes');

                $(this).removeClass('row-append row-top row-bottom');

                if (pageY > top + (bottom - top) / 2) {

                    if (bottom - pageY < 5) {

                        $(this).addClass('row-bottom');

                    } else {

                        $(this).addClass('row-append');

                    }

                } else {

                    if (pageY - top < 5) {

                        $(this).addClass('row-top');

                    } else {

                        $(this).addClass('row-append');

                    }

                }

            },

            onDragLeave: function(e, source) {

                $(source).draggable('proxy').removeClass('tree-dnd-yes').addClass('tree-dnd-no');

                $(this).removeClass('row-append row-top row-bottom');

            },

            onDrop: function(e, source) {

                var action, point;

                if ($(this).hasClass('row-append')) {

                    action = 'append';

                } else {

                    action = 'insert';

                    point = $(this).hasClass('row-top') ? 'top' : 'bottom';

                }

                $(this).removeClass('row-append row-top row-bottom');

               // alert(action + ":" + point);

                // your logic code here

                // do append or insert action and reload the treegrid data
//==================================
//做自己的逻辑处理 var src = $('#tt').treegrid('find', $(source).attr('node-id')); var dest = $('#tt').treegrid('find', $(this).attr('node-id')); // alert(src.title+","+dest.title); $.ajax({ url: 'updateCatalogList', dataType: 'json', type:'post', data: { "srcId": src.id, "destId": dest.id }, success:function(data){ if(data.result) { $('#tt').treegrid('reload'); //重新加载treegrid } } }); //==================== } }); }

 写入自己的程序,完全可以,拖动的效果有了,拖动的处理时间自己写“//============”之间的就是逻辑代码,具体就是向后台传送拖拽节点的标识信息(一般是id)和拖拽的目标节点的标识信息,即srcId和destId后台在做处理。  


    <div id="win" title="新建/编辑分类" class="easyui-window" style="width:300px;height:180px;">

        <form id="form" style="padding:10px 20px 10px 40px;">

            <p>分类名称: <input id="title" name="title" type="text"></p>

            <p>排序值: <input id="sortid" name="sortid" type="text"></p>

            <input id="id" name="id" type="hidden">

            <input id="parentId" name="parentId" type="hidden">

            <div style="padding:5px;text-align:center;">

                <a href="#" class="easyui-linkbutton" icon="icon-ok" onclick="save()">确定</a>

                <a href="#" class="easyui-linkbutton" icon="icon-cancel" onclick="javascript: $('#win').window('close');">取消</a>

            </div>

            <input id="id" name="id" type="hidden">

        </form>

    </div>

    <table id="tt" class="easyui-treegrid" cellpadding="0" cellspacing="0" border="0" style="width100%;height:450px"></table>

 

 

 接下来看一下数据源,我的数据源用的json格式,也是demo的给的样例格式。如下:

var data=[{

    "id":1,

    "name":"C",

    "size":"",

    "date":"02/19/2010",

    "children":[{

        "id":2,

        "name":"Program Files",

        "size":"120 MB",

        "date":"03/20/2010",

        "children":[{

            "id":21,

            "name":"Java",

            "size":"",

            "date":"01/13/2010",

            "state":"closed",

            "children":[{

                "id":211,

                "name":"java.exe",

                "size":"142 KB",

                "date":"01/13/2010"

            },{

                "id":212,

                "name":"jawt.dll",

                "size":"5 KB",

                "date":"01/13/2010"

            }]

        },{

            "id":22,

            "name":"MySQL",

            "size":"",

            "date":"01/13/2010",

            "state":"closed",

            "children":[{

                "id":221,

                "name":"my.ini",

                "size":"10 KB",

                "date":"02/26/2009"

            },{

                "id":222,

                "name":"my-huge.ini",

                "size":"5 KB",

                "date":"02/26/2009"

            },{

                "id":223,

                "name":"my-large.ini",

                "size":"5 KB",

                "date":"02/26/2009"

            }]

        }]

    },{

        "id":3,

        "name":"eclipse",

        "size":"",

        "date":"01/20/2010",

        "children":[{

            "id":31,

            "name":"eclipse.exe",

            "size":"56 KB",

            "date":"05/19/2009"

        },{

            "id":32,

            "name":"eclipse.ini",

            "size":"1 KB",

            "date":"04/20/2010"

        },{

            "id":33,

            "name":"notice.html",

            "size":"7 KB",

            "date":"03/17/2005"

        }]

    }]

}];

 

这就有一点需要注意你传过来的每条数据对象需要有对应的属性(children和state),state属性控制节点的关闭状态。因为只是照猫画虎,也没多想,我就直接把后台的所有数据直接一次性封装好,送给前台了。

注意:1.这在数据量极大地情况下是很低效的。一种思路就是异步加载子节点。

        2.每次加载排序效果的好坏,还与系统定义的排序方式有关。

 

最后,虽简单的实现了功能,但是还有待改进。像 enableDnd($('#tt'));这个函数的东西,自己能看懂,但是还是自己写的少,以至于需要引用他人的。以后要多多加强一下。

你可能感兴趣的:(jquery easyui)