easyui源码翻译1.32--TreeGrid(树形表格)

前言

扩展自$.fn.datagrid.defaults。使用$.fn.treegrid.defaults重写默认值对象。下载该插件翻译源码

树形表格用于显示分层数据表格。它是基于数据表格、组合树控件和可编辑表格。树形表格允许用户创建可定制的、异步展开行和显示在多列上的分层数据。

源码

/**

 * jQuery EasyUI 1.3.2

 * 

 *翻译:qq 1364386878 下拉树

 */

(function ($) {

    //获取行索引

    function getObjectIndex(rows,row) {

        for (var i = 0, _2 = rows.length; i < _2; i++) {

            if (rows[i] ==row) {

                return i;

            }

        }

        return -1;

    };

    //传递数据

    function transferData(rows,row) {

        var index = getObjectIndex(rows,row);

        if (index != -1) {

            rows.splice(index, 1);

        }

    };

    //初始化函数

    function initGrid(jq) {

        var options = $.data(jq, "treegrid").options;

        //初始化表格 具体参考datagrid属性、事件

        $(jq).datagrid($.extend({}, options, {

            url: null,

            data: null,

            loader: function () {

                return false;

            },

            onLoadSuccess: function () {

            },

            onResizeColumn: function (field, width) {

                _setRowHeight(jq);

                options.onResizeColumn.call(jq, field, width);

            },

            onSortColumn: function (sortName, sortName) {

                options.sortName = sortName;

                options.sortOrder = sortName;

                if (options.remoteSort) {

                    request(jq);

                } else {

                    var data = $(jq).treegrid("getData");

                    _loadData(jq, 0, data);

                }

                options.onSortColumn.call(jq, sortName, sortName);

            },



            onBeforeEdit: function (rowIndex, rowData) {

                if (options.onBeforeEdit.call(jq, rowData) == false) {

                    return false;

                }

            },

            onAfterEdit: function (rowIndex, row, newValues) {

                options.onAfterEdit.call(jq, row, newValues);

            },

            onCancelEdit: function (rowIndex, row) {

                options.onCancelEdit.call(jq, row);

            },

            onSelect: function (parm) {

                options.onSelect.call(jq, find(jq, parm));

            },

            onUnselect: function (parm) {

                options.onUnselect.call(jq, find(jq, parm));

            },

            onSelectAll: function () {

                options.onSelectAll.call(jq, $.data(jq, "treegrid").data);

            },

            onUnselectAll: function () {

                options.onUnselectAll.call(jq, $.data(jq, "treegrid").data);

            },

            onCheck: function (parm) {

                options.onCheck.call(jq, find(jq, parm));

            },

            onUncheck: function (parm) {

                options.onUncheck.call(jq, find(jq, parm));

            },

            onCheckAll: function () {

                options.onCheckAll.call(jq, $.data(jq, "treegrid").data);

            },

            onUncheckAll: function () {

                options.onUncheckAll.call(jq, $.data(jq, "treegrid").data);

            },

            onClickRow: function (parm) {

                options.onClickRow.call(jq, find(jq, parm));

            },

            onDblClickRow: function (parm) {

                options.onDblClickRow.call(jq, find(jq, parm));

            },

            onClickCell: function (id, field) {

                options.onClickCell.call(jq, field, find(jq, id));

            },

            onDblClickCell: function (id, parm) {

                options.onDblClickCell.call(jq, parm, find(jq, id));

            },

            onRowContextMenu: function (e, id) {

                options.onContextMenu.call(jq, e, find(jq, id));

            }

        }));

        if (options.pagination) {

            var getPager = $(jq).datagrid("getPager");

            getPager.pagination({

                pageNumber: options.pageNumber,

                pageSize: options.pageSize,

                pageList: options.pageList,

                onSelectPage: function (pageNumber, pageNumber) {

                    options.pageNumber = pageNumber;

                    options.pageSize = pageNumber;

                    request(jq);

                }

            });

            options.pageSize = getPager.pagination("options").pageSize;

        }

    };

    //修正指定的行高

    function _setRowHeight(jq, id) {

        var options = $.data(jq, "datagrid").options;

        var dc = $.data(jq, "datagrid").dc;

        if (!dc.body1.is(":empty") && (!options.nowrap || options.autoRowHeight)) {

            if (id != undefined) {

                var children = _getChildren(jq, id);

                for (var i = 0; i < children.length; i++) {

                    setRowHeight(children[i][options.idField]);

                }

            }

        }

        $(jq).datagrid("fixRowHeight", id);



        function setRowHeight(_28) {

            var tr1 = options.finder.getTr(jq, _28, "body", 1);

            var tr2 = options.finder.getTr(jq, _28, "body", 2);

            tr1.css("height", "");

            tr2.css("height", "");

            var maxheight = Math.max(tr1.height(), tr2.height());

            tr1.css("height", maxheight);

            tr2.css("height", maxheight);

        };

    };

    //设置行序号

    function fixRowNumbers(jq) {

        var dc = $.data(jq, "datagrid").dc;

        var options = $.data(jq, "treegrid").options;

        if (!options.rownumbers) {

            return;

        }

        dc.body1.find("div.datagrid-cell-rownumber").each(function (i) {

            $(this).html(i + 1);

        });

    };

    //绑定事件

    function bindEvents(jq) {

        var dc = $.data(jq, "datagrid").dc;

        var body = dc.body1.add(dc.body2);

        var handler = ($.data(body[0], "events") || $._data(body[0], "events")).click[0].handler;

        dc.body1.add(dc.body2).bind("mouseover", function (e) {//当鼠标移上时

            var tt = $(e.target);

            var tr = tt.closest("tr.datagrid-row");

            if (!tr.length) {

                return;

            }

            if (tt.hasClass("tree-hit")) {

                tt.hasClass("tree-expanded") ? tt.addClass("tree-expanded-hover") : tt.addClass("tree-collapsed-hover");

            }

            e.stopPropagation();

        }).bind("mouseout", function (e) {//dang鼠标离开时

            var tt = $(e.target);

            var tr = tt.closest("tr.datagrid-row");

            if (!tr.length) {

                return;

            }

            if (tt.hasClass("tree-hit")) {

                tt.hasClass("tree-expanded") ? tt.removeClass("tree-expanded-hover") : tt.removeClass("tree-collapsed-hover");

            }

            e.stopPropagation();

        }).unbind("click").bind("click", function (e) {//触发点击事件

            var tt = $(e.target);

            var tr = tt.closest("tr.datagrid-row");

            if (!tr.length) {

                return;

            }

            if (tt.hasClass("tree-hit")) {

                _toggle(jq, tr.attr("node-id"));

            } else {

                handler(e);

            }

            e.stopPropagation();

        });

    };



    function initSubTree(jq, nodeId) {

        var options = $.data(jq, "treegrid").options;

        var tr1 = options.finder.getTr(jq, nodeId, "body", 1);

        var tr2 = options.finder.getTr(jq, nodeId, "body", 2);

        //getColumnFields返回列字段。如果设置了frozen属性为true,将返回固定列的字段名

        var colspan1 = $(jq).datagrid("getColumnFields", true).length + (options.rownumbers ? 1 : 0);

        var colspan2 = $(jq).datagrid("getColumnFields", false).length;

        createSubTree(tr1, colspan1);

        createSubTree(tr2, colspan2);

        function createSubTree(tr, colspan) {

            $("<tr class=\"treegrid-tr-tree\">" + "<td style=\"border:0px\" colspan=\"" + colspan + "\">" + "<div></div>" + "</td>" + "</tr>").insertAfter(tr);

        };

    };

    //读取树形表格数据

    function _loadData(jq, nodeId, param, param) {

        var options = $.data(jq, "treegrid").options;

        var dc = $.data(jq, "datagrid").dc;

        param = options.loadFilter.call(jq, param, nodeId);

        var row = find(jq, nodeId);

        if (row) {

            var tr1 = options.finder.getTr(jq, nodeId, "body", 1);

            var tr2 = options.finder.getTr(jq, nodeId, "body", 2);

            var cc1 = tr1.next("tr.treegrid-tr-tree").children("td").children("div");

            var cc2 = tr2.next("tr.treegrid-tr-tree").children("td").children("div");

        } else {

            var cc1 = dc.body1;

            var cc2 = dc.body2;

        }

        if (!param) {

            $.data(jq, "treegrid").data = [];

            cc1.empty();

            cc2.empty();

        }

        if (options.view.onBeforeRender) {

            options.view.onBeforeRender.call(options.view, jq, nodeId, param);

        }

        options.view.render.call(options.view, jq, cc1, true);

        options.view.render.call(options.view, jq, cc2, false);

        if (options.showFooter) {

            options.view.renderFooter.call(options.view, jq, dc.footer1, true);

            options.view.renderFooter.call(options.view, jq, dc.footer2, false);

        }

        if (options.view.onAfterRender) {

            options.view.onAfterRender.call(options.view, jq);

        }

        options.onLoadSuccess.call(jq, row, param);

        if (!nodeId && options.pagination) {

            var total = $.data(jq, "treegrid").total;

            var getPager = $(jq).datagrid("getPager");

            if (getPager.pagination("options").total != total) {

                getPager.pagination({ total: total });

            }

        }

        _setRowHeight(jq);

        fixRowNumbers(jq);

        $(jq).treegrid("autoSizeColumn");

    };



    function request(jq, parentId, param, isAppend, callBack) {

        var options = $.data(jq, "treegrid").options;

        var body = $(jq).datagrid("getPanel").find("div.datagrid-body");

        if (param) {

            options.queryParams = param;

        }

        var queryParams = $.extend({}, options.queryParams);

        if (options.pagination) {

            $.extend(queryParams, { page: options.pageNumber, rows: options.pageSize });

        }

        if (options.sortName) {

            $.extend(queryParams, { sort: options.sortName, order: options.sortOrder });

        }

        var row = find(jq, parentId);

        if (options.onBeforeLoad.call(jq, row, queryParams) == false) {

            return;

        }

        var folder = body.find("tr[node-id=" + parentId + "] span.tree-folder");

        folder.addClass("tree-loading");

        $(jq).treegrid("loading");

        var loaded = options.loader.call(jq, queryParams, function (parm) {

            folder.removeClass("tree-loading");

            $(jq).treegrid("loaded");

            _loadData(jq, parentId, parm, isAppend);

            if (callBack) {

                callBack();

            }

        }, function () {

            folder.removeClass("tree-loading");

            $(jq).treegrid("loaded");

            options.onLoadError.apply(jq, arguments);

            if (callBack) {

                callBack();

            }

        });

        if (loaded == false) {

            folder.removeClass("tree-loading");

            $(jq).treegrid("loaded");

        }

    };

    //获取根节点,返回节点对象

    function _getRoot(target) {

        var roots = _getRoots(target);

        if (roots.length) {

            return roots[0];

        } else {

            return null;

        }

    };

    //获取所有根节点,返回节点对象

    function _getRoots(target) {

        return $.data(target, "treegrid").data;

    };

    //获取父节点。

    function _getParent(jq, id) {

        var row = find(jq, id);

        if (row._parentId) {

            return find(jq, row._parentId);

        } else {

            return null;

        }

    };

    //获取子节点

    function _getChildren(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var body = $(jq).datagrid("getPanel").find("div.datagrid-view2 div.datagrid-body");

        var children = [];

        if (id) {

            findChildren(id);

        } else {

            var roots = _getRoots(jq);

            for (var i = 0; i < roots.length; i++) {

                children.push(roots[i]);

                findChildren(roots[i][options.idField]);

            }

        }

        function findChildren(id) {

            var node = find(jq, id);

            if (node && node.children) {

                for (var i = 0, len = node.children.length; i < len; i++) {

                    var child = node.children[i];

                    children.push(child);

                    findChildren(child[options.idField]);

                }

            }

        };

        return children;

    };

    //获取选择的节点并返回它,如果没有节点被选中则返回null

    function _getSelected(jq) {

        var target = _getSelections(jq);

        if (target.length) {

            return target[0];

        } else {

            return null;

        }

    };

    //获取所有选择的节点。

    function _getSelections(jq) {

        var selectedRows = [];

        var panel = $(jq).datagrid("getPanel");

        panel.find("div.datagrid-view2 div.datagrid-body tr.datagrid-row-selected").each(function () {

            var id = $(this).attr("node-id");

            selectedRows.push(find(jq, id));

        });

        return selectedRows;

    };

    //获取指定节点等级。

    function _getLevel(jq, id) {

        if (!id) {

            return 0;

        }

        var options = $.data(jq, "treegrid").options;

        var gridView = $(jq).datagrid("getPanel").children("div.datagrid-view");

        var treeNode = gridView.find("div.datagrid-body tr[node-id=" + id + "]").children("td[field=" + options.treeField + "]");

        return treeNode.find("span.tree-indent,span.tree-hit").length;

    };

    //查找指定节点并返回节点数据。

    function find(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var data = $.data(jq, "treegrid").data;

        var cc = [data];

        while (cc.length) {

            var c = cc.shift();

            for (var i = 0; i < c.length; i++) {

                var rowData = c[i];

                if (rowData[options.idField] == id) {

                    return rowData;

                } else {

                    if (rowData["children"]) {

                        cc.push(rowData["children"]);

                    }

                }

            }

        }

        return null;

    };

    //折叠一个节点。

    function _collapse(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var row = find(jq, id);

        var tr = options.finder.getTr(jq, id);

        var hit = tr.find("span.tree-hit");

        if (hit.length == 0) {

            return;

        }

        if (hit.hasClass("tree-collapsed")) {

            return;

        }

        if (options.onBeforeCollapse.call(jq, row) == false) {

            return;

        }

        hit.removeClass("tree-expanded tree-expanded-hover").addClass("tree-collapsed");

        hit.next().removeClass("tree-folder-open");

        row.state = "closed";

        tr = tr.next("tr.treegrid-tr-tree");

        var cc = tr.children("td").children("div");

        if (options.animate) {

            cc.slideUp("normal", function () {

                $(jq).treegrid("autoSizeColumn");

                _setRowHeight(jq, id);

                options.onCollapse.call(jq, row);

            });

        } else {

            cc.hide();

            $(jq).treegrid("autoSizeColumn");

            _setRowHeight(jq, id);

            options.onCollapse.call(jq, row);

        }

    };

    //展开一个节点。

    function expand(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var tr = options.finder.getTr(jq, id);

        var hit = tr.find("span.tree-hit");

        var row = find(jq, id);

        if (hit.length == 0) {

            return;

        }

        if (hit.hasClass("tree-expanded")) {

            return;

        }

        if (options.onBeforeExpand.call(jq, row) == false) {

            return;

        }

        hit.removeClass("tree-collapsed tree-collapsed-hover").addClass("tree-expanded");

        hit.next().addClass("tree-folder-open");

        var subtree = tr.next("tr.treegrid-tr-tree");

        if (subtree.length) {

            var cc = subtree.children("td").children("div");

            expandSubtree(cc);

        } else {

            initSubTree(jq, row[options.idField]);

            var subtree = tr.next("tr.treegrid-tr-tree");

            var cc = subtree.children("td").children("div");

            cc.hide();

            request(jq, row[options.idField], { id: row[options.idField] }, true, function () {

                if (cc.is(":empty")) {

                    subtree.remove();

                } else {

                    expandSubtree(cc);

                }

            });

        }

        function expandSubtree(cc) {

            row.state = "open";

            if (options.animate) {

                cc.slideDown("normal", function () {

                    $(jq).treegrid("autoSizeColumn");

                    _setRowHeight(jq, id);

                    options.onExpand.call(jq, row);

                });

            } else {

                cc.show();

                $(jq).treegrid("autoSizeColumn");

                _setRowHeight(jq, id);

                options.onExpand.call(jq, row);

            }

        };

    };

    //节点展开/折叠状态触发器

    function _toggle(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var tr = options.finder.getTr(jq, id);

        var hit = tr.find("span.tree-hit");

        if (hit.hasClass("tree-expanded")) {

            _collapse(jq, id);

        } else {

            expand(jq, id);

        }

    };

    //折叠所有节点。

    function _collapseAll(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var children = _getChildren(jq, id);

        if (id) {

            children.unshift(find(jq, id));

        }

        for (var i = 0; i < children.length; i++) {

            _collapse(jq, children[i][options.idField]);

        }

    };

    //展开所有节点。

    function _expandAll(jq, jq) {

        var options = $.data(jq, "treegrid").options;

        var children = _getChildren(jq, jq);

        if (jq) {

            children.unshift(find(jq, jq));

        }

        for (var i = 0; i < children.length; i++) {

            expand(jq, children[i][options.idField]);

        }

    };

    //打开从根节点到指定节点之间的所有节点。

    function _expandTo(jq, id) {

        var options = $.data(jq, "treegrid").options;

        var ids = [];

        var p = _getParent(jq, id);

        while (p) {

            var id = p[options.idField];

            ids.unshift(id);

            p = _getParent(jq, id);

        }

        for (var i = 0; i < ids.length; i++) {

            expand(jq, ids[i]);

        }

    };

    //追加节点到一个父节点,'param'参数包含如下属性:

    //parent:父节点ID,如果未指定则追加到根节点。

    //data:数组,节点数据。

    function _append(jq, param) {

        var options = $.data(jq, "treegrid").options;

        if (param.parent) {

            var tr = options.finder.getTr(jq, param.parent);

            if (tr.next("tr.treegrid-tr-tree").length == 0) {

                initSubTree(jq, param.parent);

            }

            var cell = tr.children("td[field=" + options.treeField + "]").children("div.datagrid-cell");

            var icon = cell.children("span.tree-icon");

            if (icon.hasClass("tree-file")) {

                icon.removeClass("tree-file").addClass("tree-folder");

                var hit = $("<span class=\"tree-hit tree-expanded\"></span>").insertBefore(icon);

                if (hit.prev().length) {

                    hit.prev().remove();

                }

            }

        }

        _loadData(jq, param.parent, param.data, true);

    };

    //插入一个新节点到指定节点。'param'参数包含一下参数:

    //before:插入指定节点ID值之前。

    //after:插入指定节点ID值之后。

    //data:新节点数据。 

    function insert(jq, param) {

        var ref = param.before || param.after;

        var options = $.data(jq, "treegrid").options;

        var parentn = _getParent(jq, ref);

        _append(jq, { parent: (parentn ? parentn[options.idField] : null), data: [param.data] });

        _insert(true);

        _insert(false);

        fixRowNumbers(jq);

        //插入数据

        function _insert(before) {

            var step = before ? 1 : 2;

            var tr = options.finder.getTr(jq, param.data[options.idField], "body", step);

            var btable = tr.closest("table.datagrid-btable");//序号列

            tr = tr.parent().children();

            var tr = options.finder.getTr(jq, ref, "body", step);

            if (param.before) {

                tr.insertBefore(tr);

            } else {

                var sub = tr.next("tr.treegrid-tr-tree");

                tr.insertAfter(sub.length ? sub : tr);

            }

            btable.remove();

        };

    };

    //移除一个节点和他的所有子节点。

    function _remove(jq, nodeId) {

        var options = $.data(jq, "treegrid").options;

        var tr = options.finder.getTr(jq, nodeId);

        tr.next("tr.treegrid-tr-tree").remove();

        tr.remove();

        var parent = del(nodeId);

        if (parent) {

            if (parent.children.length == 0) {

                tr = options.finder.getTr(jq, parent[options.idField]);

                tr.next("tr.treegrid-tr-tree").remove();

                var cell = tr.children("td[field=" + options.treeField + "]").children("div.datagrid-cell");

                cell.find(".tree-icon").removeClass("tree-folder").addClass("tree-file");

                cell.find(".tree-hit").remove();

                $("<span class=\"tree-indent\"></span>").prependTo(cell);

            }

        }

        fixRowNumbers(jq);

        function del(id) {

            var cc;

            var parent = _getParent(jq, nodeId);

            if (parent) {

                cc = parent.children;

            } else {

                cc = $(jq).treegrid("getData");

            }

            for (var i = 0; i < cc.length; i++) {

                if (cc[i][options.idField] == id) {

                    cc.splice(i, 1);

                    break;

                }

            }

            return parent;

        };

    };

    //实例化组建

    $.fn.treegrid = function (target, parm) {

        if (typeof target == "string") {

            var method = $.fn.treegrid.methods[target];

            if (method) {

                return method(this, parm);

            } else {

                return this.datagrid(target, parm);

            }

        }

        target = target || {};

        return this.each(function () {

            var treegrid = $.data(this, "treegrid");

            if (treegrid) {

                $.extend(treegrid.options, target);

            } else {

                treegrid = $.data(this, "treegrid", { options: $.extend({}, $.fn.treegrid.defaults, $.fn.treegrid.parseOptions(this), target), data: [] });

            }

            initGrid(this);

            if (treegrid.options.data) {

                $(this).treegrid("loadData", treegrid.options.data);

            }

            request(this);

            bindEvents(this);

        });

    };

    //默认方法

    $.fn.treegrid.methods = {

        //返回树形表格的属性

        options: function (jq) {

            return $.data(jq[0], "treegrid").options;

        },

        //设置树形表格大小,options包含2个属性:

        //width:树形表格的新宽度。

        //height:树形表格的新高度。

        resize: function (jq, options) {

            return jq.each(function () {

                $(this).datagrid("resize", options);

            });

        },

        //修正指定的行高

        fixRowHeight: function (jq, id) {

            return jq.each(function () {

                _setRowHeight(this, id);

            });

        },

        //读取树形表格数据

        loadData: function (jq, data) {

            return jq.each(function () {

                _loadData(this, null, data);

            });

        },

        //重新加载树形表格数据。如果'id'属性有值,将重新载入指定树形行,否则重新载入所有行

        reload: function (jq, id) {

            return jq.each(function () {

                if (id) {

                    var record = $(this).treegrid("find", id);

                    if (record.children) {

                        record.children.splice(0, record.children.length);

                    }

                    var gridBody = $(this).datagrid("getPanel").find("div.datagrid-body");

                    var tr = gridBody.find("tr[node-id=" + id + "]");

                    tr.next("tr.treegrid-tr-tree").remove();

                    var hit = tr.find("span.tree-hit");

                    hit.removeClass("tree-expanded tree-expanded-hover").addClass("tree-collapsed");

                    expand(this, id);

                } else {

                    request(this, null, {});

                }

            });

        },

        //重新载入页脚数据

        reloadFooter: function (jq, footer) {

            return jq.each(function () {

                var options = $.data(this, "treegrid").options;

                var dc = $.data(this, "datagrid").dc;

                if (footer) {

                    $.data(this, "treegrid").footer = footer;

                }

                if (options.showFooter) {

                    options.view.renderFooter.call(options.view, this, dc.footer1, true);

                    options.view.renderFooter.call(options.view, this, dc.footer2, false);

                    if (options.view.onAfterRender) {

                        options.view.onAfterRender.call(options.view, this);

                    }

                    $(this).treegrid("fixRowHeight");

                }

            });

        },

        //获取载入数据

        getData: function (jq) {

            return $.data(jq[0], "treegrid").data;

        },

        //获取页脚数据

        getFooterRows: function (jq) {

            return $.data(jq[0], "treegrid").footer;

        },

        //获取根节点,返回节点对象

        getRoot: function (jq) {

            return _getRoot(jq[0]);

        },

        //获取所有根节点,返回节点数组

        getRoots: function (jq) {

            return _getRoots(jq[0]);

        },

        //获取父节点。

        getParent: function (jq, id) {

            return _getParent(jq[0], id);

        },

        //获取子节点

        getChildren: function (jq, id) {

            return _getChildren(jq[0], id);

        },

        //获取选择的节点并返回它,如果没有节点被选中则返回null。

        getSelected: function (jq) {

            return _getSelected(jq[0]);

        },

        //获取所有选择的节点。

        getSelections: function (jq) {

            return _getSelections(jq[0]);

        },

        //获取指定节点等级

        getLevel: function (jq, id) {

            return _getLevel(jq[0], id);

        },

        //查找指定节点并返回节点数据

        find: function (jq, id) {

            return find(jq[0], id);

        },

        //判断是否是子节点

        isLeaf: function (jq, id) {

            var options = $.data(jq[0], "treegrid").options;

            var tr = options.finder.getTr(jq[0], id);

            var hit = tr.find("span.tree-hit");

            return hit.length == 0;

        },

        //选择一个节点。

        select: function (jq, id) {

            return jq.each(function () {

                $(this).datagrid("selectRow", id);

            });

        },

        //反选一个节点。

        unselect: function (jq, id) {

            return jq.each(function () {

                $(this).datagrid("unselectRow", id);

            });

        },

        //折叠一个节点。

        collapse: function (jq, id) {

            return jq.each(function () {

                _collapse(this, id);

            });

        },

        //展开一个节点。

        expand: function (jq, id) {

            return jq.each(function () {

                expand(this, id);

            });

        },

        //节点展开/折叠状态触发器。

        toggle: function (jq, id) {

            return jq.each(function () {

                _toggle(this, id);

            });

        },

        //折叠所有节点。

        collapseAll: function (jq, id) {

            return jq.each(function () {

                _collapseAll(this, id);

            });

        },

        //展开所有节点。

        expandAll: function (jq, id) {

            return jq.each(function () {

                _expandAll(this, id);

            });

        },

        //打开从根节点到指定节点之间的所有节点

        expandTo: function (jq, id) {

            return jq.each(function () {

                _expandTo(this, id);

            });

        },

        //追加节点到一个父节点,'param'参数包含如下属性:

        //parent:父节点ID,如果未指定则追加到根节点。

        //data:数组,节点数据。

        append: function (jq, param) {

            return jq.each(function () {

                _append(this, param);

            });

        },

        //插入一个新节点到指定节点。'param'参数包含一下参数:

        //before:插入指定节点ID值之前。

        //after:插入指定节点ID值之后。

        //data:新节点数据       

        insert: function (jq, param) {

            return jq.each(function () {

                insert(this, param);

            });

        }, 

        //移除一个节点和他的所有子节点。

        remove: function (jq, id) {

            return jq.each(function () {

                _remove(this, id);

            });

        },

        //弹出并返回节点数据以及它的子节点之后删除

        pop: function (jq, id) {

            var row = jq.treegrid("find", id);

            jq.treegrid("remove", id);

            return row;

        },

        //刷新指定节点

        refresh: function (jq, id) {

            return jq.each(function () {

                var options = $.data(this, "treegrid").options;

                options.view.refreshRow.call(options.view, this, id);

            });

        },

        //options更新指定节点。'param'参数包含以下属性:

        //id:要更新的节点的ID。

        //row:新的行数据

        update: function (jq, param) {

            return jq.each(function () {

                var options = $.data(this, "treegrid").options;

                options.view.updateRow.call(options.view, this, param.id, param.row);

            });

        },

        //开始编辑一个节点

        beginEdit: function (jq, id) {

            return jq.each(function () {

                $(this).datagrid("beginEdit", id);

                $(this).treegrid("fixRowHeight", id);

            });

        },

        //结束编辑一个节点

        endEdit: function (jq, id) {

            return jq.each(function () {

                $(this).datagrid("endEdit", id);

            });

        },

        //取消编辑一个节点。

        cancelEdit: function (jq, id) {

            return jq.each(function () {

                $(this).datagrid("cancelEdit", id);

            });

        }

    };

    //解析器配置

    $.fn.treegrid.parseOptions = function (target) {

        return $.extend({}, $.fn.datagrid.parseOptions(target),

            $.parser.parseOptions(target, ["treeField", { animate: "boolean" }]));

    };

    //定义数据表格的视图 该视图是一个对象,将告诉数据表格如何渲染行。该对象必须定义下列函

    var _view = $.extend({}, $.fn.datagrid.defaults.view, {

        //    数据加载时调用。

        //jq:DOM对象,数据表格对象。

        //container:行容器。

        //frozen:指明如何渲染冻结容器。

        render: function (jq, container, frozen) {

            var options = $.data(jq, "treegrid").options;

            var fields = $(jq).datagrid("getColumnFields", frozen);

            var rowIdPrefix = $.data(jq, "datagrid").rowIdPrefix;

            if (frozen) {

                if (!(options.rownumbers || (options.frozenColumns && options.frozenColumns.length))) {

                    return;

                }

            }

            var grid = this;

            var nodes = buildTreeNodes(frozen, this.treeLevel, this.treeNodes);

            $(container).append(nodes.join(""));

            //创建树节点

            function buildTreeNodes(frozen, treeLevel, rows) {

                var html = ["<table class=\"datagrid-btable\" cellspacing=\"0\" cellpadding=\"0\" border=\"0\"><tbody>"];

                for (var i = 0; i < rows.length; i++) {

                    var row = rows[i];

                    if (row.state != "open" && row.state != "closed") {

                        row.state = "open";

                    }

                    var style = options.rowStyler ? options.rowStyler.call(jq, row) : "";

                    var attr = style ? "style=\"" + style + "\"" : "";

                    var rowid = rowIdPrefix + "-" + (frozen ? 1 : 2) + "-" + row[options.idField];

                    html.push("<tr id=\"" + rowid + "\" class=\"datagrid-row\" node-id=" + row[options.idField] + " " + attr + ">");

                    html = html.concat(grid.renderRow.call(grid, jq, fields, frozen, treeLevel, row));

                    html.push("</tr>");

                    if (row.children && row.children.length) {

                        var tt = buildTreeNodes(frozen, treeLevel + 1, row.children);

                        var v = row.state == "closed" ? "none" : "block";

                        html.push("<tr class=\"treegrid-tr-tree\"><td style=\"border:0px\" colspan="

                            + (fields.length + (options.rownumbers ? 1 : 0))

                            + "><div style=\"display:"

                            + v + "\">");

                        html = html.concat(tt);

                        html.push("</div></td></tr>");

                    }

                }

                html.push("</tbody></table>");

                return html;

            };

        },

        //渲染底部

        renderFooter: function (jq, grid, frozen) {

            var options = $.data(jq, "treegrid").options;

            var footer = $.data(jq, "treegrid").footer || [];

            var fields = $(jq).datagrid("getColumnFields", frozen);

            var html = ["<table class=\"datagrid-ftable\" cellspacing=\"0\" cellpadding=\"0\" border=\"0\"><tbody>"];

            for (var i = 0; i < footer.length; i++) {

                var row = footer[i];

                row[options.idField] = row[options.idField] || ("foot-row-id" + i);

                html.push("<tr class=\"datagrid-row\" node-id=" + row[options.idField] + ">");

                html.push(this.renderRow.call(this, jq, fields, frozen, 0, row));

                html.push("</tr>");

            }

            html.push("</tbody></table>");

            $(grid).html(html.join(""));

        },

        //渲染行

        renderRow: function (jq, fields, frozen, deepth, row) {

            var opts = $.data(jq, "treegrid").options;

            var cc = [];

            if (frozen && opts.rownumbers) {

                cc.push("<td class=\"datagrid-td-rownumber\"><div class=\"datagrid-cell-rownumber\">0</div></td>");

            }

            for (var i = 0; i < fields.length; i++) {

                var field = fields[i];

                var col = $(jq).datagrid("getColumnOption", field);

                if (col) {

                    var style = col.styler ? (col.styler(row[field], row) || "") : "";

                    var style2 = col.hidden ? "style=\"display:none;" + style + "\"" : (style ? "style=\"" + style + "\"" : "");

                    cc.push("<td field=\"" + field + "\" " + style2 + ">");

                    if (col.checkbox) {

                        var style2 = "";

                    } else {

                        var style2 = "";

                        if (col.align) {

                            style2 += "text-align:" + col.align + ";";

                        }

                        if (!opts.nowrap) {

                            style2 += "white-space:normal;height:auto;";

                        } else {

                            if (opts.autoRowHeight) {

                                style2 += "height:auto;";

                            }

                        }

                    }

                    cc.push("<div style=\"" + style2 + "\" ");

                    if (col.checkbox) {

                        cc.push("class=\"datagrid-cell-check ");

                    } else {

                        cc.push("class=\"datagrid-cell " + col.cellClass);

                    }

                    cc.push("\">");

                    if (col.checkbox) {

                        if (row.checked) {

                            cc.push("<input type=\"checkbox\" checked=\"checked\"");

                        } else {

                            cc.push("<input type=\"checkbox\"");

                        }

                        cc.push(" name=\"" + field + "\" value=\"" + (row[field] != undefined ? row[field] : "") + "\"/>");

                    } else {

                        var val = null;

                        if (col.formatter) {

                            val = col.formatter(row[field], row);

                        } else {

                            val = row[field];

                        }

                        if (field == opts.treeField) {

                            for (var j = 0; j < deepth; j++) {

                                cc.push("<span class=\"tree-indent\"></span>");

                            }

                            if (row.state == "closed") {

                                cc.push("<span class=\"tree-hit tree-collapsed\"></span>");

                                cc.push("<span class=\"tree-icon tree-folder " + (row.iconCls ? row.iconCls : "") + "\"></span>");

                            } else {

                                if (row.children && row.children.length) {

                                    cc.push("<span class=\"tree-hit tree-expanded\"></span>");

                                    cc.push("<span class=\"tree-icon tree-folder tree-folder-open " + (row.iconCls ? row.iconCls : "") + "\"></span>");

                                } else {

                                    cc.push("<span class=\"tree-indent\"></span>");

                                    cc.push("<span class=\"tree-icon tree-file " + (row.iconCls ? row.iconCls : "") + "\"></span>");

                                }

                            }

                            cc.push("<span class=\"tree-title\">" + val + "</span>");

                        } else {

                            cc.push(val);

                        }

                    }

                    cc.push("</div>");

                    cc.push("</td>");

                }

            }

            return cc.join("");

        },

        //刷新行

        refreshRow: function (target, id) {

            this.updateRow.call(this, target, id, {});

        },

        //更新行

        updateRow: function (jq, id, row) {

            var options = $.data(jq, "treegrid").options;

            var row2 = $(jq).treegrid("find", id);

            $.extend(row2, row);

            var Level = $(jq).treegrid("getLevel", id) - 1;//获取指定节点等级。

            var style2 = options.rowStyler ? options.rowStyler.call(jq, row2) : "";

            function setFieldsCheck(frozen) { //设置字段选中

                var _e1 = $(jq).treegrid("getColumnFields", frozen);

                var tr = options.finder.getTr(jq, id, "body", (frozen ? 1 : 2));

                var rownumber = tr.find("div.datagrid-cell-rownumber").html();

                var checkb = tr.find("div.datagrid-cell-check input[type=checkbox]").is(":checked");

                tr.html(this.renderRow(jq, _e1, frozen, Level, row2));

                tr.attr("style", style2 || "");

                tr.find("div.datagrid-cell-rownumber").html(rownumber);

                if (checkb) {

                    tr.find("div.datagrid-cell-check input[type=checkbox]")._propAttr("checked", true);//设置选择

                }

            };

            setFieldsCheck.call(this, true);

            setFieldsCheck.call(this, false);

            $(jq).treegrid("fixRowHeight", id);

        },

        //在视图被呈现之前触发

        onBeforeRender: function (jq, nodeId, nodeId) {

            if (!nodeId) {

                return false;

            }

            var options = $.data(jq, "treegrid").options;

            if (nodeId.length == undefined) {

                if (nodeId.footer) {

                    $.data(jq, "treegrid").footer = nodeId.footer;

                }

                if (nodeId.total) {

                    $.data(jq, "treegrid").total = nodeId.total;

                }

                nodeId = this.transfer(jq, nodeId, nodeId.rows);

            } else {

                function setParent(param, nodeId) {

                    for (var i = 0; i < param.length; i++) {

                        var row = param[i];

                        row._parentId = nodeId;

                        if (row.children && row.children.length) {

                            setParent(row.children, row[options.idField]);

                        }

                    }

                };

                setParent(nodeId, nodeId);

            }

            var node = find(jq, nodeId);

            if (node) {

                if (node.children) {

                    node.children = node.children.concat(nodeId);

                } else {

                    node.children = nodeId;

                }

            } else {

                $.data(jq, "treegrid").data = $.data(jq, "treegrid").data.concat(nodeId);

            }

            if (!options.remoteSort) {

                this.sort(jq, nodeId);

            }

            this.treeNodes = nodeId;

            this.treeLevel = $(jq).treegrid("getLevel", nodeId);

        },

        //排序

        sort: function (jq, param) {

            var options = $.data(jq, "treegrid").options;

            var opt = $(jq).treegrid("getColumnOption", options.sortName);

            if (opt) {

                var sorter = opt.sorter || function (rows, b) {

                    return (rows > b ? 1 : -1);

                };

                _sorter(param);

            }

            function _sorter(param) {

                param.sort(function (r1, r2) {

                    return sorter(r1[options.sortName], r2[options.sortName]) * (options.sortOrder == "asc" ? 1 : -1);

                });

                for (var i = 0; i < param.length; i++) {

                    var children = param[i].children;

                    if (children && children.length) {

                        _sorter(children);

                    }

                }

            };

        },



        transfer: function (jq, nodeId, data) {

            var options = $.data(jq, "treegrid").options;

            var rows = [];

            for (var i = 0; i < data.length; i++) {

                rows.push(data[i]);

            }

            var children = [];

            for (var i = 0; i < rows.length; i++) {

                var row = rows[i];

                if (!nodeId) {

                    if (!row._parentId) {

                        children.push(row);

                        transferData(rows, row);

                        i--;

                    }

                } else {

                    if (row._parentId == nodeId) {

                        children.push(row);

                        transferData(rows, row);

                        i--;

                    }

                }

            }

            var toDo = [];

            for (var i = 0; i < children.length; i++) {

                toDo.push(children[i]);

            }

            while (toDo.length) {

                var node = toDo.shift();

                for (var i = 0; i < rows.length; i++) {

                    var row = rows[i];

                    if (row._parentId == node[options.idField]) {

                        if (node.children) {

                            node.children.push(row);

                        } else {

                            node.children = [row];

                        }

                        toDo.push(row);

                        transferData(rows, row);

                        i--;

                    }

                }

            }

            return children;

        }

    });

    //默认属性和事件 继承datagrid

    $.fn.treegrid.defaults = $.extend({}, $.fn.datagrid.defaults, {

        treeField: null,//定义树节点字段。

        animate: false,//定义在节点展开或折叠的时候是否显示动画效果

        singleSelect: true,//单选

        view: _view,//定义数据表格的视图

        //定义以何种方式从远程服务器读取数据。返回false可以忽略该动作。该函数具有一下参数:

        //param:传递到远程服务器的参数对象。

        //success(data):当检索数据成功的时候调用的回调函数。

        //error():当检索数据失败的时候调用的回调函数。

        loader: function (param, success, error) {

            var options = $(this).treegrid("options");

            if (!options.url) {

                return false;

            }

            $.ajax({

                type: options.method,

                url: options.url,

                data: param,

                dataType: "json",

                success: function (data) {

                    success(data);

                }, error: function () {

                    error.apply(this, arguments);

                }

            });

        },

        //返回过滤后的数据进行展示

        loadFilter: function (data, parentId) {

            return data;

        },



        finder: {



            getTr: function (jq, id, type, step) {

                type = type || "body";

                step = step || 0;

                var dc = $.data(jq, "datagrid").dc;

                if (step == 0) {

                    var opts = $.data(jq, "treegrid").options;

                    var tr1 = opts.finder.getTr(jq, id, type, 1);

                    var tr2 = opts.finder.getTr(jq, id, type, 2);

                    return tr1.add(tr2);

                } else {

                    if (type == "body") {

                        var tr = $("#" + $.data(jq, "datagrid").rowIdPrefix + "-" + step + "-" + id);

                        if (!tr.length) {

                            tr = (step == 1 ? dc.body1 : dc.body2).find("tr[node-id=" + id + "]");

                        }

                        return tr;

                    } else {

                        if (type == "footer") {

                            return (step == 1 ? dc.footer1 : dc.footer2).find("tr[node-id=" + id + "]");

                        } else {

                            if (type == "selected") {

                                return (step == 1 ? dc.body1 : dc.body2).find("tr.datagrid-row-selected");

                            } else {

                                if (type == "last") {

                                    return (step == 1 ? dc.body1 : dc.body2).find("tr:last[node-id]");

                                } else {

                                    if (type == "allbody") {

                                        return (step == 1 ? dc.body1 : dc.body2).find("tr[node-id]");

                                    } else {

                                        if (type == "allfooter") {

                                            return (step == 1 ? dc.footer1 : dc.footer2).find("tr[node-id]");

                                        }

                                    }

                                }

                            }

                        }

                    }

                }

            },

            //获取行

            getRow: function (target, p) {

                var id = (typeof p == "object") ? p.attr("node-id") : p;

                return $(target).treegrid("find", id);

            }

        },

        //在载入请求数据数据之前触发,如果返回false可终止载入数据操作

        onBeforeLoad: function (row, param) {

        },

        //在数据加载成功的时候触发

        onLoadSuccess: function (row, data) {

        },

        //在数据加载成功的时候触发

        onLoadError: function () {

        },

        //在数据加载成功的时候触发

        onBeforeCollapse: function (row) {

        },

        //在节点被折叠的时候触发

        onCollapse: function (row) {

        },

        //在节点展开之前触发,返回false可以取消展开节点的动作

        onBeforeExpand: function (row) {

        },

        //在节点被展开的时候触发

        onExpand: function (row) {

        },

        //在用户点击节点的时候触发

        onClickRow: function (row) {

        },

        //在用户双击节点的时候触发

        onDblClickRow: function (row) {

        },

        //在用户点击一个单元格的时候触发

        onClickCell: function (field, row) {

        },

        //在用户双击一个单元格的时候触发

        onDblClickCell: function (field, row) {

        },

        //在右键点击节点的时候触发。

        onContextMenu: function (e, row) {

        },

        //在用户开始编辑节点的时候触发

        onBeforeEdit: function (row) {

        },

        //在用户完成编辑的时候触发

        onAfterEdit: function (row, changes) {

        },

        //在用户取消编辑节点的时候触发。

        onCancelEdit: function (row) {

        }

    });

})(jQuery);
View Code

 

示例代码

<!DOCTYPE html>

<html>

<head>

    <meta charset="UTF-8">

    <title>Basic TreeGrid - jQuery EasyUI Demo</title>

    <link rel="stylesheet" type="text/css" href="../../themes/default/easyui.css">

    <link rel="stylesheet" type="text/css" href="../../themes/icon.css">

    <link rel="stylesheet" type="text/css" href="../demo.css">

    <script type="text/javascript" src="../../jquery-1.8.0.min.js"></script>

    <script src="../../plugins2/jquery.parser.js"></script>

    <script src="../../plugins2/jquery.panel.js"></script>

    <script src="../../plugins2/jquery.resizable.js"></script>

    <script src="../../plugins2/jquery.linkbutton.js"></script>

    <script src="../../plugins2/jquery.pagination.js"></script>

    <script src="../../plugins2/jquery.datagrid.js"></script>

    <script src="../../plugins2/jquery.treegrid.js"></script>

</head>

<body>

    <h2>Basic TreeGrid</h2>

    <div class="demo-info">

        <div class="demo-tip icon-tip"></div>

        <div>TreeGrid allows you to expand or collapse group rows.</div>

    </div>

    <div style="margin:10px 0;"></div>

    <table title="Folder Browser" class="easyui-treegrid" style="width:700px;height:250px"

            data-options="

                url: '../treegrid/treegrid_data1.json',

                rownumbers: true,

                idField: 'id',

                treeField: 'name'

            ">

        <thead>

            <tr>

                <th data-options="field:'name'" width="220">Name</th>

                <th data-options="field:'size'" width="100" align="right">Size</th>

                <th data-options="field:'date'" width="150">Modified Date</th>

            </tr>

        </thead>

    </table>



</body>

</html>
View Code

 

插件效果

easyui源码翻译1.32--TreeGrid(树形表格)

你可能感兴趣的:(treegrid)