Ext.tree.Panel Extjs 在表格中添加树结构,并实现节点移动功能

最近在用Extjs 做后台管理系统,真的非常好用。总结的东西分享一下。

先展示一下效果图

好了,开始吧!

首先说一下我的创建结构:

一、构造内容

这个函数中包括store的创建,treePanel的创建

一个treePanel必须绑定一个Ext.data.TreeStore.

function constructor(config){

//创建一个treeStore 数据(我的用ajax取的,你们随意~)
        var store = Ext.create('Ext.data.TreeStore', {
            proxy: {
                type: 'ajax',
                url: 'http://localhost/data/aa.txt',
                reader: {
                    type: "json",
                    rootProperty: "children",
                    transform: function (data) {
                        if (data.code === 1) console.log("error");
                        return data;
                    }
                }
            },
            folderSort: true
        });

          //   创建treePanel了
        var $tree = Ext.create('Ext.tree.Panel', {
             '100%',
            height: 600,
            store: store,
            useArrows: true,
            rootVisible: false,
            multiSelect: true,    // 多选
            //singleExpand: true,   //单展开
            autoScroll: true,    // 自动滚屏
            columns: [{          // 列项
                xtype: 'treecolumn',
                text: '菜单名称',
                 250,
                sortable: true,
                menuDisabled: true,
                dataIndex: 'text'
            },{
                text: '节点类型',
                 150,
                dataIndex: 'user',
                menuDisabled: true,
                align: 'center',
                sortable: true
            },{
                text: '新增',
                 70,
                align: 'center',
                menuDisabled: true,
                renderer: function (value, metaData) {
                    return "<a href='#" + Math.random() + "'>新增</a>";
                }
            },{
                text: '修改',
                 100,
                menuDisabled: true,
                xtype: 'actioncolumn',
                align: 'center',
                icon: '/images/edit.png'
            }, {
                xtype: 'actioncolumn',
                text: '删除',
                 100,
                menuDisabled: true,
                align: 'center',
                icon: '/images/delete.png',
                handler: function(grid, rowIndex,colIndex,record) {
                    var rec = store.getAt(rowIndex);
                    if(rec.get('children') === null){
                        Ext.MessageBox.confirm(
                            "删除"
                            ,"确定删除吗?"
                            ,function( button,text ){
                                if( button == 'yes'){
                                    rec.remove();
                                }
                            }
                        );
                    }else{
                        Ext.MessageBox.alert("删除","当前元素含有子节点,不能被删除");
                    }
                }
            }, {
                text: '上移',
                 50,
                menuDisabled: true,
                align: 'center',
                renderer:function(value, cellmeta, record, rowIndex, columnIndex, store){
                    return  "<a href='#" + Math.random() + "'>上移</a>";
                }
            },{
                text: '下移',
                 50,
                menuDisabled: true,
                align: 'center',
                renderer:function(value, cellmeta, record, rowIndex, columnIndex, store){
                    return  "<a href='#" + Math.random() + "'>下移</a>";
                }
            },{
                text: '升级',
                 50,
                menuDisabled: true,
                align: 'center',
                renderer:function(value, cellmeta, record, rowIndex, columnIndex, store){
                    return  "<a href='#" + Math.random() + "'>升级</a>";
                }
            },{
            text: '降级',
                 50,
                menuDisabled: true,
                align: 'center',
                renderer:function(value, cellmeta, record, rowIndex, columnIndex, store){
                return  "<a href='#" + Math.random() + "'>降级</a>";
            }
        }],
            listeners:{     //监听事件
                cellclick: function (view, td, cellIndex, record, tr, rowIndex, e, eOpts){   // 单元格点击,贼好用
            //判断点击的第几列(索引从0开始)
                    if(cellIndex === 2)  return display$WindowAddNode(rowIndex,record, store);   
                    if(cellIndex === 5)  return moveEvent(rowIndex,record,store);
                    if(cellIndex === 6)  return downEvent(rowIndex,record, store);
                    if(cellIndex === 7)  return upgradeEvent(rowIndex,record, store);
                    if(cellIndex === 8)  return downgradeEvent(rowIndex,record, store);
                }
            }

        });

        config.parent.add($tree);

        return $tree;
    }

面板创建完了,下面该实现功能了。

二、新增节点

  看图说话。

在行内点击新增,只会作用到当前行。

//增加节点
    function display$WindowAddNode(rowIndex,record,store){

        //创建单选框
        var $radioAdd = Ext.create('Ext.form.RadioGroup',{
            xtype: 'radiogroup',
            defaultType: 'radiofield',
            layout: 'vbox',
            margin: '10 0 0 20',
            items: [
                {
                    boxLabel  : '增加子节点',
                    name      : 'addNode',
                    inputValue:'childNode'
                }, {
                    boxLabel  : '在该节点前新增节点',
                    name      : 'addNode',
                    inputValue:'frontNode'
                }, {
                    boxLabel  : '在该节点后新增节点',
                    name      : 'addNode',
                    inputValue:'afterNode'
                }
            ]
        });

        //创建面板 单选框 -输入框
        var form = Ext.create('Ext.form.Panel', {
            layout: 'absolute',
            defaultType: 'textfield',
            border: false,
            defaults: {
                anchor: '90%',
                labelStyle: 'padding-left:4px;'
            },
            fieldDefaults: {
                labelAlign: "right",
                labelWidth: 70
            },
            items: [$radioAdd,{
                id:'inputNode',
                fieldLabel: '输入标题',
                fieldWidth: 80,
                margin: '110 0 0 0'
            }]
        });

        //创建窗口
        var win = Ext.create('Ext.window.Window', {
            title: '增加节点',
             300,
            height: 230,
            layout: 'fit',
            plain: true,
            items: form,
            buttons: [{
                text: '确定',
                handler:function(){
                    return addNodeYes();
                }
            }, {
                text: '取消',
                handler : function(){
                    win.close();
                }
            }]
        });

        win.show();

        //确定增加节点
        function addNodeYes(){

            //获得单选钮的选项
            var radioText = $radioAdd.getValue();

            //输入框内容
            var inputNode = Ext.getCmp('inputNode').getValue();

            //新节点
            var newNode={
                text:inputNode,
                duration:6.5,
                user:'Tommy Maintz',
                leaf:true,
                iconCls:'text'
            };

            //当前节点父节点
            var parentNode = record.parentNode;

            //判断 单选钮是否选中
            if(inputNode !== ''){
                if(radioText.addNode === 'childNode'){
                    record.appendChild(newNode);
                    win.close();
                }else if(radioText.addNode === 'frontNode'){
                    parentNode.insertBefore(newNode,record);
                    win.close();
                }else if(radioText.addNode === 'afterNode'){
                    for(var i = 0; i < parentNode.childNodes.length; i++){
                        if(parentNode.childNodes[i] === record){
                            parentNode.insertBefore(newNode,parentNode.childNodes[i+1]);
                        }
                    }
                    win.close();
                }
            }else{
                alert('请输入标题');
            }

        }

    }

三、上移功能也是作用当前行的

这个没图,不用找了,直接上代码

//上移
    function moveEvent(rowIndex,record,store){

        //当前节点父节点
        var parentNode = record.parentNode;
        var length = parentNode.childNodes.length;
        var currentIndex = 0;

        //获取当前节点
        for(var i =0; i < length; i++){
            if(parentNode.childNodes[i] === record){
                currentIndex = i;
            }
        }

        //操作
        if(currentIndex <=0){
            currentIndex = 1;
        }else{
            currentIndex = currentIndex - 1;
        }

        parentNode.insertChild(currentIndex,record);

    }

四、下移

//下移
    function downEvent(rowIndex,record,store){

        //当前节点父节点
        var parentNode = record.parentNode;
        var length = parentNode.childNodes.length;
        var currentIndex= 0;

        // 获取当前节点的索引
        for(var i = 0; i < length; i++){
            if(parentNode.childNodes[i] === record){
                currentIndex = i;
            }
        }

        // 计算移除当前节点后,插入的目标节点索引
        var targetIndex = (currentIndex>=(length-2))? (length-1) : currentIndex+1;

        // 删除当前节点
        parentNode.childNodes[currentIndex].remove();

        // 插入当前节点,至计算的目标位置
        parentNode.insertChild(targetIndex,record);

    }

五、升级

 //升级
    function upgradeEvent(rowIndex,record,store){

        //当前节点父节点的父节点
        var parentPNode = record.parentNode.parentNode;

        parentPNode.appendChild(record);

    }

六、降级

//降级
    function downgradeEvent(rowIndex,record,store){

        //当前节点父节点
        var parentNode = record.parentNode;

        for(var i = 0; i < parentNode.childNodes.length; i++){
            if(parentNode.childNodes[i] === record){
                parentNode.childNodes[i-1].appendChild(record);
            }
        }

    }

  Srong前端小白:自己写的东西,写的不知道是否清楚,不一定都对,欢迎指正⁄(⁄ ⁄•⁄ω⁄•⁄ ⁄)⁄

最后,赠送一个福利:

 modal:true   //只可操作当前窗口,在弹出窗口中必不可少的属性

  

原文地址:https://www.cnblogs.com/webRongS/p/5412705.html