1. 程式人生 > >選單管理功能實現-treegrid行編輯以及拖拽效果

選單管理功能實現-treegrid行編輯以及拖拽效果

               

使用easyui的treegrid實現行編輯和拖拽效果。

下面是demo介面。可以拖拽選單(放在tr上,則拖拽到目標的子目錄,放在邊框上則是拖拽到同級目錄)


具體實現程式碼:

menuList.jsp

<html><head> <title>選單列表</title> <base href="http://localhost:8080/mysys/"
>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><link rel="stylesheet" type="text/css" href="easyui/themes/default/easyui.css"><link rel="stylesheet" type="text/css" href="easyui/themes/icon.css"><script type="text/javascript" src="easyui/jquery.min.js"></script
>
<script type="text/javascript" src="easyui/jquery.easyui.min.js"></script><script src="easyui/locale/easyui-lang-zh_CN.js"></script><script type="text/javascript" src="js/js.js"></script><link rel="stylesheet" type="text/css" href="css/icon.css"> <script type
="text/javascript" src="ms/menuList.js?d=4">
</script> <style type="text/css"> .fitem{  margin: 5px; } .fitem label{  display:inline-block;  width: 70px;   text-align: right;  } .panel.datagrid{  margin: 0 auto; }/*  修改表格表頭裡面字型大小  */ .datagrid-header .datagrid-cell span{  font-size: 18px; }/*  修改表格裡面字型大小 */ .datagrid-cell{  font-size: 16px; }/*  修改表格行高 */ .datagrid-row {        height: 40px;    }    td[field="enable"] td{      text-align: center;    } </style> <style type="text/css">/*   treegrid拖動效果 */  .row-top td{   border-top:1px solid red;   background:#fff;  }  .row-bottom td{   border-bottom:1px solid red;   background:#fff;  }  .row-append td{   border:0;   background:#FBEC88;  } </style></head><body> <!--  資料網格 --> <table id="tg" title="選單列表"   style="width:100%;height:auto;margin:0 auto;"> </table></body></html>


menuList.js

$(function() { query();})function query() {// $('#tg').treegrid("options") $('#tg').treegrid({     url:'menu/list',     idField:'id',     treeField:'name',     rownumbers:true,//第一列顯示序號     fitColumns:true,//列寬按比例擴充套件到最大     onDblClickRow:function(row){edit()},     onLoadSuccess: function(row){            //$(this).treegrid('enableDnd', row?row.id:null);           //上面的程式碼是demo中的,但是對於要儲存更改到資料庫顯然走不通,需要向其他辦法           //啟用拖動排序            enableDnd($('#tg'));        },     columns:[[         {field:'name',title:'name',width:100,align:'left', halign: 'center',editor:"text"},         {field:'url',title:'url',width:100,align:'center',editor:"text"},         {field:'icon',title:'icon',width:160,align:'center',editor:"text"},         {field:'seq',title:'seq',width:160,align:'center',editor:"numberbox" }     ]],     toolbar: [         { text: '新增子選單', iconCls: 'icon-add', handler: function () {          append();        }         }, '-',         { text: '刪除', iconCls: 'icon-remove', handler: function () {          remove();        }         }, '-',         { text: '編輯', iconCls: 'icon-edit', handler: function () {          edit();        }         }, '-',         { text: '儲存', iconCls: 'icon-save', handler: function () {          save();        }         }, '-',         { text: '取消編輯', iconCls: 'icon-undo', handler: function () {          cancelEdit();        }         }, '-',         { text: '重新整理', iconCls: 'icon-reload', handler: function () {          query();        }         }, '-',         { text: '更新到資料庫', iconCls: 'icon-save', handler: function () {          saveToDB();        }         }, '-'] });}var editingId;function append()var node = $('#tg').treegrid('getSelected'); if(node){  var obj = {    id: -1*Math.random(),    name:'新建選單',    parent:{id:node.id},    left:true,    visible:true,    seq:99   };  $('#tg').treegrid('append',{   parent: node.id,  // the node has a 'id' value that defined through 'idField' property   data: [obj]  });  enableDnd($('#tg'));  params_data.add.push($('#tg').treegrid('find', obj.id)); }}function insert()var node = $('#tg').treegrid('getSelected'); if (node){  var obj = {    id: -1*Math.random(),    name:'新建選單',    parent:node.parent,    left:true,    visible:true,    seq:99   };  $('#tg').treegrid('insert', {   after: node.id,   data: obj  });  enableDnd($('#tg'));  params_data.add.push($('#tg').treegrid('find', obj.id)); } }function edit()if (editingId != undefined){  save(); } var row = $('#tg').treegrid('getSelected'); if (row){  editingId = row.id  $('#tg').treegrid('beginEdit', editingId);  //解決新增拖拽功能後無法編輯問題  /*  var eds = $('#tg').treegrid('getEditors',editingId);  for(var i=0;i<eds.length;i++){   $(eds[i].target).bind('mousedown',function(e){    e.stopPropagation();   });  }*/  $(".datagrid-row-editing input").each(function(){   $(this).bind('mousedown',function(e){    e.stopPropagation();   });  });   }}function save()if (editingId != undefined){  $('#tg').treegrid('endEdit', editingId);  var row = $('#tg').treegrid('find', editingId);  if(row.id > 0){   params_data.update.push(row);  }  editingId = undefined; }}function remove()var node = $('#tg').treegrid('getSelected'); if (node){  $('#tg').treegrid('remove', node.id);  if(editingId != undefined && editingId == node.id){   editingId = undefined;  }  if(node.id > 0){   params_data.delete.push(node);  }else{   var idx = params_data.add.indexOf(node);   params_data.add.remove(idx);  } }}function cancelEdit()if (editingId != undefined){  $('#tg').treegrid('cancelEdit', editingId);  editingId = undefined; }}/**儲存到資料庫*/var params_data = {add: [],update: [],delete: []};function saveToDB(){ save(); var data = {            add: [],            update: [],            delete: []    };    for(var i=0;i<params_data.add.length;i++){     delete params_data.add[i]._parentId;     delete params_data.add[i].checkState;     delete params_data.add[i].checked;     delete params_data.add[i].state;    }    for(var i=0;i<params_data.update.length;i++){     delete params_data.update[i]._parentId;     delete params_data.update[i].checkState;     delete params_data.update[i].checked;     delete params_data.update[i].state;    }    for(var i=0;i<params_data.update.length;i++){     delete params_data.update[i]._parentId;     delete params_data.update[i].checkState;     delete params_data.update[i].checked;     delete params_data.update[i].state;    }    var req_data = {};    req_data.add = JSON.stringify(params_data.add);    req_data.update = JSON.stringify(params_data.update);    req_data.delete = JSON.stringify(params_data.delete);    $.ajax({        type: "POST",        url: 'menu/save',        dataType: "json",        data: req_data,        success: function (rarg) {            if (rarg.err == undefined) {                $.messager.show({ title: '提示',                    msg: '儲存成功.',                    timeout: 3000,                    showType: 'slide'                });                params_data = {add: [],update: [],delete: []};                query();            }            else $.messager.alert('提示', rarg.err);             //refreshTab();        },        error: function (XMLHttpRequest, textStatus, errorThrown) {            $.messager.alert('提示', '儲存失敗,系統繁忙,請稍後再試!');        }    });}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  = t.treegrid('find', $(source).attr('node-id'));            var dest = t.treegrid('find', $(this).attr('node-id'));            //alert(src.name+","+dest.name);            if (src){             t.treegrid('remove', src.id);            }            if(action == "append"){             src.parent = {};             src.parent.id = dest.id;             t.treegrid('append',{              parent: dest.id,  // the node has a 'id' value that defined through 'idField' property              data: [src]             });            }else if(action == "insert"){             src.parent = dest.parent;             var obj = {                  before: dest.id,                  after: dest.id,                  data: src                }             if(point == "top"){              delete obj.after;             }else{              delete obj.before;             }             t.treegrid('insert', obj);            }            if(src.id > 0){             params_data.update.push(src);            }                        enableDnd(t);            /*            $.ajax({                url: 'updateCatalogList',                dataType: 'json',                type:'post',                data: {                    "srcId": src.id,                    "destId": dest.id                },                success:function(data){                    if(data.result)                    {                        $('#tt').treegrid('reload');    //重新載入treegrid                           }                }                        });            */  } });}
MenuAction.java

@RequestMapping(value = "list"@ResponseBody public List<Menu> list(@RequestParam Map map) {  List<Menu> list = menuService.list(map);  return list; } @RequestMapping(value = "save"@ResponseBody public Map save(@RequestParam String add   ,@RequestParam String delete   ,@RequestParam String update) {  JSONArray addArr = JSONArray.fromObject(add);  JSONArray deleteArr = JSONArray.fromObject(delete);  JSONArray updateArr = JSONArray.fromObject(update);  List<Menu> addlist = (List) JSONArray.toCollection(addArr,      Menu.class);   List<Menu> deletelist = (List) JSONArray.toCollection(deleteArr,      Menu.class);   List<Menu> updatelist = (List) JSONArray.toCollection(updateArr,      Menu.class);   menuService.saveAll(addlist,deletelist,updatelist);  Map map = new HashMap();  return map; }

訪問menu/list的結果:

[{"id":3,"parent":null,"name":"系統設定","url":null,"visible":true,"leaf":true,"seq":1,"roles":[],"children":[],"icon":null},{"id":6,"parent":null,"name":"基礎資料","url":null,"visible":true,"leaf":true,"seq":2,"roles":[],"children":[],"icon":null},{"id":7,"parent":null,"name":"許可權管理","url":null,"visible":true,"leaf":true,"seq":3,"roles":[],"children":[{"id":9,"parent":{"id":7,"parent":null,"name":null,"url":null,"visible":false,"leaf":false,"seq":0,"roles":[],"children":[],"icon":null},"name":"使用者管理","url":"user/list","visible":true,"leaf":true,"seq":1,"roles":[],"children":[],"icon":"3"},{"id":10,"parent":{"id":7,"parent":null,"name":null,"url":null,"visible":false,"leaf":false,"seq":0,"roles":[],"children":[],"icon":null},"name":"角色管理","url":"role/list","visible":true,"leaf":true,"seq":2,"roles":[],"children":[],"icon":"2"},{"id":11,"parent":{"id":7,"parent":null,"name":null,"url":null,"visible":false,"leaf":false,"seq":0,"roles":[],"children":[],"icon":null},"name":"選單管理","url":"menu/list","visible":true,"leaf":true,"seq":3,"roles":[],"children":[],"icon":null}],"icon":null},{"id":8,"parent":null,"name":"訂單管理","url":null,"visible":true,"leaf":true,"seq":4,"roles":[],"children":[],"icon":null}]


主要難點:

1.結點的新增、刪除、修改。editingId是使用treegrid控制元件後建立的一個全域性變數。

2.實現拖拽功能。呼叫方法:enableDnd($('#tg'));

3.拖拽功能導致編輯器無法正常工作。解決方法是在edit()中執行下面程式碼:

$(".datagrid-row-editing input").each(function(){   $(this).bind('mousedown',function(e){    e.stopPropagation();   });  });
4.主要使用的到api:

$('#tg').treegrid('append', {parent: node.id,data: [obj]});

$('#tg').treegrid('insert', {before: node.id,data: obj});

$('#tg').treegrid('insert', {after: node.id,data: obj});

$('#tg').treegrid('beginEdit', editingId);

$('#tg').treegrid('endEdit', editingId);

var row = $('#tg').treegrid('find', editingId);

var node = $('#tg').treegrid('getSelected');

$('#tg').treegrid('cancelEdit', editingId);


onDblClickRow:function(row){edit()},


           

再分享一下我老師大神的人工智慧教程吧。零基礎!通俗易懂!風趣幽默!還帶黃段子!希望你也加入到我們人工智慧的隊伍中來!https://blog.csdn.net/jiangjunshow