博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
[原创] 扩展jquery-treegrid插件, 实现勾选功能和全删按钮.
阅读量:6295 次
发布时间:2019-06-22

本文共 54974 字,大约阅读时间需要 183 分钟。

新上手一个项目, 因而正好想学习下bootstrap, 所以就采用asp.net mvc + bootstrap来做.  因为需要TreeGrid的控件, 本来想用easyUI、LingerUi、DWZ, 但显示效果总觉得不协调. 搜来搜去, 发现了牛人写的 jquery-treegrid, 所以就参考这园子里的两篇文章开始做:

JS组件系列——自己动手封装bootstrap-treegrid组件:      http://www.cnblogs.com/landeanfen/p/6776152.html

JS组件系列——封装自己的JS组件,你也可以:     http://www.cnblogs.com/landeanfen/p/5124542.html

 

 

这次目的是扩展jquery-treegrid插件, 实现checkbox的全选、单选, 也照着上文添加了ajax远程获取数据的功能. 虽然后来发现了Kendo UI, 但本着学习的目的, 还是完成了这次的插件扩展功能.

由于常年没有接触过前端, 所以jquery基本语法都磕磕绊绊更别说扩展插件了, 边摸索边做.  待我改完一版本, 才能理解了jquery-treegrid插件的作者真的牛掰:

1. jquery-treegrid思想: 没有硬编码的html, 全部通过css样式实现. 像树形结点的维护、结点的打开与折叠状态, 都是由写在TR元素上的css来实现. 也倒是jquery本身不熟吧, 我第一次见这么少的html来实现的jQuery控件.

2. 插件的结构: 跟上面的总体结构类似, 都是  method{}方法集合、$.fn.treegrid扩展、default{}默认参数对象. 其通过初始化函数initTree来开始渲染table元素, 通过保存控件容器(TreeContainer) -> 保存全局设置(Settings) -> 递归地初始化结点(initNode) -> 为每个结点添加事件(intExpander、initIdent、initEvents、initState、initChangeEvent、initSettingsEvents)来完成最终功能. 整体上有点面向对象的意味, 跟之前自己写的JS差距甚大.

 

 

刚开始我也是照着前面两篇的文章来实现了基本的样子, 当我快做完的时候才理解了jquery-treegrid控件作者的思路. 根据前两篇文章的思路, 就是在初始化方法中, 通过ajax获取数据, 然后在回调方法中拼接HTML表格, 来完成对jquery-treegrid的远程取数据的扩展. 当我基本理解了jQuery-treegrid作者的思想以后, 尝试将上面的代码改成: 在获取远程数据后, render表格(renderHeader、RenderBody、递归的生成List类型的Tr和Tree类型的Tr)、之后初始化Header(初始化checkAll、DelAll、操作列)、再往后初始化结点(initExpander、initIndent、initCheck、initOperation、initEvnets、initState、initChangeEvent、initSettingsEvents).   所有操作(如:全选、全部选、直选部分)等操作, 也都是通过在Tr元素上附加css来实现的.

 

总结实现过程的砍儿:

1. 理解插件开发思路及手段, 为什么采用如此结构来组织插件.

2. 控件状态的处理其实是使用了cookie, 用jquery-cookie来实现的.

3. 特别要理解This所代表的对象, 可以在调试界面一步步验证this所代表的对象.

4. 关于原jquery-treegrid插件的封装, $(this).原控件('方法名','参数')来封装. 这里需要注意的是: 在我们自己的扩展代码中, 关于状态保存、容器位置、设置保存等内容, 我都是通过对原控件的封装, 将这些数据写在同一个位置, 以便实现我们自己的控件和原控件之间的数据共享.

5. 默认default对象之中的方法的调用: 1. 通过settings.方法名.apply(this, '参数')来调用. 2. 通过我们扩展控件中封装的, $(this).treegridExt('getSetting','方法名').apply(this,'参数')来实现的.

6. 注意参数的问题: 有时用this、有时用$(this)、有时用$($(this).treegridExt('方法名'))、有使用[$(this)], 有时用apply(this)、还有时用apply($(Elem))等等. 决定使用哪种方式的的根本原因就是 this所代表的当前对象. 根据当前对象的不同, 来变换几种参数形式.

 

 

最后, 废话不多说, 上代码. 注意: 改代码只实现了全选、全不选、选子项、以及子项变更后对父级选项的调整.  之后没有再深入编码, 因为项目还是比较紧, 考虑一个个控件自己搞还是太费劲了, 准备采用Kendo控件来完成项目, 此Demo仅作为学习jquery和扩展其插件的相关知识为目的. 顺带对老大说声抱歉, 多耽误2,3天(算上端午的话可能是5天).

//jquery.treegrid.js

/* * jQuery treegrid Plugin 0.3.0 * https://github.com/maxazan/jquery-treegrid * * Copyright 2013, Pomazan Max * Licensed under the MIT licenses. */(function($) {    var methods = {        /**         * Initialize tree         *         * @param {Object} options         * @returns {Object[]}         */        initTree: function(options) {            var settings = $.extend({}, this.treegrid.defaults, options);            return this.each(function() {                var $this = $(this);                $this.treegrid('setTreeContainer', $(this));                $this.treegrid('setSettings', settings);                settings.getRootNodes.apply(this, [$(this)]).treegrid('initNode', settings);                $this.treegrid('getRootNodes').treegrid('render');            });        },        /**         * Initialize node         *         * @param {Object} settings         * @returns {Object[]}         */        initNode: function(settings) {            return this.each(function() {                var $this = $(this);                $this.treegrid('setTreeContainer', settings.getTreeGridContainer.apply(this));                $this.treegrid('getChildNodes').treegrid('initNode', settings);                $this.treegrid('initExpander').treegrid('initIndent').treegrid('initEvents').treegrid('initState').treegrid('initChangeEvent').treegrid("initSettingsEvents");            });        },        initChangeEvent: function() {            var $this = $(this);            //Save state on change            $this.on("change", function() {                var $this = $(this);                $this.treegrid('render');                if ($this.treegrid('getSetting', 'saveState')) {                    $this.treegrid('saveState');                }            });            return $this;        },        /**         * Initialize node events         *         * @returns {Node}         */        initEvents: function() {            var $this = $(this);            //Default behavior on collapse            $this.on("collapse", function() {                var $this = $(this);                $this.removeClass('treegrid-expanded');                $this.addClass('treegrid-collapsed');            });            //Default behavior on expand            $this.on("expand", function() {                var $this = $(this);                $this.removeClass('treegrid-collapsed');                $this.addClass('treegrid-expanded');            });            return $this;        },        /**         * Initialize events from settings         *         * @returns {Node}         */        initSettingsEvents: function() {            var $this = $(this);            //Save state on change            $this.on("change", function() {                var $this = $(this);                if (typeof($this.treegrid('getSetting', 'onChange')) === "function") {                    $this.treegrid('getSetting', 'onChange').apply($this);                }            });            //Default behavior on collapse            $this.on("collapse", function() {                var $this = $(this);                if (typeof($this.treegrid('getSetting', 'onCollapse')) === "function") {                    $this.treegrid('getSetting', 'onCollapse').apply($this);                }            });            //Default behavior on expand            $this.on("expand", function() {                var $this = $(this);                if (typeof($this.treegrid('getSetting', 'onExpand')) === "function") {                    $this.treegrid('getSetting', 'onExpand').apply($this);                }            });            return $this;        },        /**         * Initialize expander for node         *         * @returns {Node}         */        initExpander: function() {            var $this = $(this);            var cell = $this.find('td').get($this.treegrid('getSetting', 'treeColumn'));            var tpl = $this.treegrid('getSetting', 'expanderTemplate');            var expander = $this.treegrid('getSetting', 'getExpander').apply(this);            if (expander) {                expander.remove();            }            $(tpl).prependTo(cell).click(function() {                $($(this).closest('tr')).treegrid('toggle');            });            return $this;        },        /**         * Initialize indent for node         *         * @returns {Node}         */        initIndent: function() {            var $this = $(this);            $this.find('.treegrid-indent').remove();            var tpl = $this.treegrid('getSetting', 'indentTemplate');            var expander = $this.find('.treegrid-expander');            var depth = $this.treegrid('getDepth');            for (var i = 0; i < depth; i++) {                $(tpl).insertBefore(expander);            }            return $this;        },        /**         * Initialise state of node         *         * @returns {Node}         */        initState: function() {            var $this = $(this);            if ($this.treegrid('getSetting', 'saveState') && !$this.treegrid('isFirstInit')) {                $this.treegrid('restoreState');            } else {                if ($this.treegrid('getSetting', 'initialState') === "expanded") {                    $this.treegrid('expand');                } else {                    $this.treegrid('collapse');                }            }            return $this;        },        /**         * Return true if this tree was never been initialised         *         * @returns {Boolean}         */        isFirstInit: function() {            var tree = $(this).treegrid('getTreeContainer');            if (tree.data('first_init') === undefined) {                tree.data('first_init', $.cookie(tree.treegrid('getSetting', 'saveStateName')) === undefined);            }            return tree.data('first_init');        },        /**         * Save state of current node         *         * @returns {Node}         */        saveState: function() {            var $this = $(this);            if ($this.treegrid('getSetting', 'saveStateMethod') === 'cookie') {                var stateArrayString = $.cookie($this.treegrid('getSetting', 'saveStateName')) || '';                var stateArray = (stateArrayString === '' ? [] : stateArrayString.split(','));                var nodeId = $this.treegrid('getNodeId');                if ($this.treegrid('isExpanded')) {                    if ($.inArray(nodeId, stateArray) === -1) {                        stateArray.push(nodeId);                    }                } else if ($this.treegrid('isCollapsed')) {                    if ($.inArray(nodeId, stateArray) !== -1) {                        stateArray.splice($.inArray(nodeId, stateArray), 1);                    }                }                $.cookie($this.treegrid('getSetting', 'saveStateName'), stateArray.join(','));            }            return $this;        },        /**         * Restore state of current node.         *         * @returns {Node}         */        restoreState: function() {            var $this = $(this);            if ($this.treegrid('getSetting', 'saveStateMethod') === 'cookie') {                var stateArray = $.cookie($this.treegrid('getSetting', 'saveStateName')).split(',');                if ($.inArray($this.treegrid('getNodeId'), stateArray) !== -1) {                    $this.treegrid('expand');                } else {                    $this.treegrid('collapse');                }            }            return $this;        },        /**         * Method return setting by name         *         * @param {type} name         * @returns {unresolved}         */        getSetting: function(name) {            if (!$(this).treegrid('getTreeContainer')) {                return null;            }            return $(this).treegrid('getTreeContainer').data('settings')[name];        },        /**         * Add new settings         *         * @param {Object} settings         */        setSettings: function(settings) {            $(this).treegrid('getTreeContainer').data('settings', settings);        },        /**         * Return tree container         *         * @returns {HtmlElement}         */        getTreeContainer: function() {            return $(this).data('treegrid');        },        /**         * Set tree container         *         * @param {HtmlE;ement} container         */        setTreeContainer: function(container) {            return $(this).data('treegrid', container);        },        /**         * Method return all root nodes of tree.         *         * Start init all child nodes from it.         *         * @returns {Array}         */        getRootNodes: function () {            return $(this).treegrid('getSetting', 'getRootNodes').apply(this, [$(this).treegrid('getTreeContainer')]);        },        /**         * Method return all nodes of tree.         *         * @returns {Array}         */        getAllNodes: function() {            return $(this).treegrid('getSetting', 'getAllNodes').apply(this, [$(this).treegrid('getTreeContainer')]);        },        /**         * Mthod return true if element is Node         *         * @returns {String}         */        isNode: function() {            return $(this).treegrid('getNodeId') !== null;        },        /**         * Mthod return id of node         *         * @returns {String}         */        getNodeId: function() {            if ($(this).treegrid('getSetting', 'getNodeId') === null) {                return null;            } else {                return $(this).treegrid('getSetting', 'getNodeId').apply(this);            }        },        /**         * Method return parent id of node or null if root node         *         * @returns {String}         */        getParentNodeId: function() {            return $(this).treegrid('getSetting', 'getParentNodeId').apply(this);        },        /**         * Method return parent node or null if root node         *         * @returns {Object[]}         */        getParentNode: function() {            if ($(this).treegrid('getParentNodeId') === null) {                return null;            } else {                return $(this).treegrid('getSetting', 'getNodeById').apply(this, [$(this).treegrid('getParentNodeId'), $(this).treegrid('getTreeContainer')]);            }        },        /**         * Method return array of child nodes or null if node is leaf         *         * @returns {Object[]}         */        getChildNodes: function() {            return $(this).treegrid('getSetting', 'getChildNodes').apply(this, [$(this).treegrid('getNodeId'), $(this).treegrid('getTreeContainer')]);        },        /**         * Method return depth of tree.         *         * This method is needs for calculate indent         *         * @returns {Number}         */        getDepth: function() {            if ($(this).treegrid('getParentNode') === null) {                return 0;            }            return $(this).treegrid('getParentNode').treegrid('getDepth') + 1;        },        /**         * Method return true if node is root         *         * @returns {Boolean}         */        isRoot: function() {            return $(this).treegrid('getDepth') === 0;        },        /**         * Method return true if node has no child nodes         *         * @returns {Boolean}         */        isLeaf: function() {            return $(this).treegrid('getChildNodes').length === 0;        },        /**         * Method return true if node last in branch         *         * @returns {Boolean}         */        isLast: function() {            if ($(this).treegrid('isNode')) {                var parentNode = $(this).treegrid('getParentNode');                if (parentNode === null) {                    if ($(this).treegrid('getNodeId') === $(this).treegrid('getRootNodes').last().treegrid('getNodeId')) {                        return true;                    }                } else {                    if ($(this).treegrid('getNodeId') === parentNode.treegrid('getChildNodes').last().treegrid('getNodeId')) {                        return true;                    }                }            }            return false;        },        /**         * Method return true if node first in branch         *         * @returns {Boolean}         */        isFirst: function() {            if ($(this).treegrid('isNode')) {                var parentNode = $(this).treegrid('getParentNode');                if (parentNode === null) {                    if ($(this).treegrid('getNodeId') === $(this).treegrid('getRootNodes').first().treegrid('getNodeId')) {                        return true;                    }                } else {                    if ($(this).treegrid('getNodeId') === parentNode.treegrid('getChildNodes').first().treegrid('getNodeId')) {                        return true;                    }                }            }            return false;        },        /**         * Return true if node expanded         *         * @returns {Boolean}         */        isExpanded: function() {            return $(this).hasClass('treegrid-expanded');        },        /**         * Return true if node collapsed         *         * @returns {Boolean}         */        isCollapsed: function() {            return $(this).hasClass('treegrid-collapsed');        },        /**         * Return true if at least one of parent node is collapsed         *         * @returns {Boolean}         */        isOneOfParentsCollapsed: function() {            var $this = $(this);            if ($this.treegrid('isRoot')) {                return false;            } else {                if ($this.treegrid('getParentNode').treegrid('isCollapsed')) {                    return true;                } else {                    return $this.treegrid('getParentNode').treegrid('isOneOfParentsCollapsed');                }            }        },        /**         * Expand node         *         * @returns {Node}         */        expand: function() {            if (!this.treegrid('isLeaf') && !this.treegrid("isExpanded")) {                this.trigger("expand");                this.trigger("change");                return this;            }            return this;        },        /**         * Expand all nodes         *         * @returns {Node}         */        expandAll: function() {            var $this = $(this);            $this.treegrid('getRootNodes').treegrid('expandRecursive');            return $this;        },        /**         * Expand current node and all child nodes begin from current         *         * @returns {Node}         */        expandRecursive: function() {            return $(this).each(function() {                var $this = $(this);                $this.treegrid('expand');                if (!$this.treegrid('isLeaf')) {                    $this.treegrid('getChildNodes').treegrid('expandRecursive');                }            });        },        /**         * Collapse node         *         * @returns {Node}         */        collapse: function() {            return $(this).each(function() {                var $this = $(this);                if (!$this.treegrid('isLeaf') && !$this.treegrid("isCollapsed")) {                    $this.trigger("collapse");                    $this.trigger("change");                }            });        },        /**         * Collapse all nodes         *         * @returns {Node}         */        collapseAll: function() {            var $this = $(this);            $this.treegrid('getRootNodes').treegrid('collapseRecursive');            return $this;        },        /**         * Collapse current node and all child nodes begin from current         *         * @returns {Node}         */        collapseRecursive: function() {            return $(this).each(function() {                var $this = $(this);                $this.treegrid('collapse');                if (!$this.treegrid('isLeaf')) {                    $this.treegrid('getChildNodes').treegrid('collapseRecursive');                }            });        },        /**         * Expand if collapsed, Collapse if expanded         *         * @returns {Node}         */        toggle: function() {            var $this = $(this);            if ($this.treegrid('isExpanded')) {                $this.treegrid('collapse');            } else {                $this.treegrid('expand');            }            return $this;        },        /**         * Rendering node         *         * @returns {Node}         */        render: function() {            return $(this).each(function() {                var $this = $(this);                //if parent colapsed we hidden                if ($this.treegrid('isOneOfParentsCollapsed')) {                    $this.hide();                } else {                    $this.show();                }                if (!$this.treegrid('isLeaf')) {                    $this.treegrid('renderExpander');                    $this.treegrid('getChildNodes').treegrid('render');                }            });        },        /**         * Rendering expander depends on node state         *         * @returns {Node}         */        renderExpander: function() {            return $(this).each(function() {                var $this = $(this);                var expander = $this.treegrid('getSetting', 'getExpander').apply(this);                if (expander) {                    if (!$this.treegrid('isCollapsed')) {                        expander.removeClass($this.treegrid('getSetting', 'expanderCollapsedClass'));                        expander.addClass($this.treegrid('getSetting', 'expanderExpandedClass'));                    } else {                        expander.removeClass($this.treegrid('getSetting', 'expanderExpandedClass'));                        expander.addClass($this.treegrid('getSetting', 'expanderCollapsedClass'));                    }                } else {                    $this.treegrid('initExpander');                    $this.treegrid('renderExpander');                }            });        }    };    $.fn.treegrid = function(method) {        if (methods[method]) {            return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));        } else if (typeof method === 'object' || !method) {            return methods.initTree.apply(this, arguments);        } else {            $.error('Method with name ' + method + ' does not exists for jQuery.treegrid');        }    };    /**     *  Plugin's default options     */    $.fn.treegrid.defaults = {        initialState: 'expanded',        saveState: false,        saveStateMethod: 'cookie',        saveStateName: 'tree-grid-state',        expanderTemplate: '',        indentTemplate: '',        expanderExpandedClass: 'treegrid-expander-expanded',        expanderCollapsedClass: 'treegrid-expander-collapsed',        treeColumn: 0,        getExpander: function() {            return $(this).find('.treegrid-expander');        },        getNodeId: function() {            var template = /treegrid-([A-Za-z0-9_-]+)/;            if (template.test($(this).attr('class'))) {                return template.exec($(this).attr('class'))[1];            }            return null;        },        getParentNodeId: function() {            var template = /treegrid-parent-([A-Za-z0-9_-]+)/;            if (template.test($(this).attr('class'))) {                return template.exec($(this).attr('class'))[1];            }            return null;        },        getNodeById: function(id, treegridContainer) {            var templateClass = "treegrid-" + id;            return treegridContainer.find('tr.' + templateClass);        },        getChildNodes: function(id, treegridContainer) {            var templateClass = "treegrid-parent-" + id;            return treegridContainer.find('tr.' + templateClass);        },        getTreeGridContainer: function() {            return $(this).closest('table');        },        getRootNodes: function(treegridContainer) {            var result = $.grep(treegridContainer.find('tr'), function(element) {                var classNames = $(element).attr('class');                var templateClass = /treegrid-([A-Za-z0-9_-]+)/;                var templateParentClass = /treegrid-parent-([A-Za-z0-9_-]+)/;                return templateClass.test(classNames) && !templateParentClass.test(classNames);            });            return $(result);        },        getAllNodes: function(treegridContainer) {            var result = $.grep(treegridContainer.find('tr'), function(element) {                var classNames = $(element).attr('class');                var templateClass = /treegrid-([A-Za-z0-9_-]+)/;                return templateClass.test(classNames);            });            return $(result);        },        //Events        onCollapse: null,        onExpand: null,        onChange: null    };})(jQuery);
View Code

 

 

//jquery.treegrid.css

.treegrid-indent {
width:16px; height: 16px; display: inline-block; position: relative;}.treegrid-expander {
width:16px; height: 16px; display: inline-block; position: relative; cursor: pointer;}.treegrid-expander-expanded{
background-image: url(../img/collapse.png); }.treegrid-expander-collapsed{
background-image: url(../img/expand.png);}
View Code

 

//jquery.treegrid.bootstrap3.js

$.extend($.fn.treegrid.defaults, {
expanderExpandedClass: 'glyphicon glyphicon-chevron-down', expanderCollapsedClass: 'glyphicon glyphicon-chevron-right'});
View Code

 

//jquey.cookie.js

/*! * jQuery Cookie Plugin v1.3.1 * https://github.com/carhartl/jquery-cookie * * Copyright 2013 Klaus Hartl * Released under the MIT license */(function (factory) {    if (typeof define === 'function' && define.amd) {        // AMD. Register as anonymous module.        define(['jquery'], factory);    } else {        // Browser globals.        factory(jQuery);    }}(function ($) {    var pluses = /\+/g;    function decode(s) {        if (config.raw) {            return s;        }        return decodeURIComponent(s.replace(pluses, ' '));    }    function decodeAndParse(s) {        if (s.indexOf('"') === 0) {            // This is a quoted cookie as according to RFC2068, unescape...            s = s.slice(1, -1).replace(/\\"/g, '"').replace(/\\\\/g, '\\');        }        s = decode(s);        try {            return config.json ? JSON.parse(s) : s;        } catch(e) {}    }    var config = $.cookie = function (key, value, options) {        // Write        if (value !== undefined) {            options = $.extend({}, config.defaults, options);            if (typeof options.expires === 'number') {                var days = options.expires, t = options.expires = new Date();                t.setDate(t.getDate() + days);            }            value = config.json ? JSON.stringify(value) : String(value);            return (document.cookie = [                config.raw ? key : encodeURIComponent(key),                '=',                config.raw ? value : encodeURIComponent(value),                options.expires ? '; expires=' + options.expires.toUTCString() : '', // use expires attribute, max-age is not supported by IE                options.path    ? '; path=' + options.path : '',                options.domain  ? '; domain=' + options.domain : '',                options.secure  ? '; secure' : ''            ].join(''));        }        // Read        var cookies = document.cookie.split('; ');        var result = key ? undefined : {};        for (var i = 0, l = cookies.length; i < l; i++) {            var parts = cookies[i].split('=');            var name = decode(parts.shift());            var cookie = parts.join('=');            if (key && key === name) {                result = decodeAndParse(cookie);                break;            }            if (!key) {                result[name] = decodeAndParse(cookie);            }        }        return result;    };    config.defaults = {};    $.removeCookie = function (key, options) {        if ($.cookie(key) !== undefined) {            // Must not alter options, thus extending a fresh object...            $.cookie(key, '', $.extend({}, options, { expires: -1 }));            return true;        }        return false;    };}));
View Code

 

以上是jquery-treegrid的主要先关内容, 以下是这次扩展的代码

//jquey.treegrid.extention.js

/* * jQuery treegrid extension 0.1.0 * * Copyright 2017, Jalen Zhang * Licensed under the MIT licenses. */; (function ($) {    "use strict";   //严格模式下, 全局对象无法使用默认绑定    /*begin private functions*/    var nodeCount = 0;  //全局结点计数    //从数据中获取跟结点    var getRootNodesFromData = function (data,isTreedData,parentCol,sortCol) {        var result = [];        $.each(data, function (index, item) {            if (isTreedData || !item[parentCol] || item[parentCol] == 0) {                result.push(item);            }        });        if (sortCol) {            result.sort(function (a, b) {                return a[sortCol] - b[sortCol];            });        }        return result;    }    //从数据中获取子节点    var getListChildNodesFromData = function (data, parentNode,idCol,parentCol,sortCol) {        var unsort = [];        $.each(data, function (i, item) {            if (item[parentCol] == parentNode[idCol]) {                unsort.push(item);            }        });        if (unsort == null || unsort.length < 1)            return;        if (sortCol) {            unsort.sort(function (a, b) {                return a[sortCol] - b[sortCol];            });        }        return unsort;    }    var getTreeChildNodesFromdata = function (parentNode,childCol,sortCol) {        if (childCol) {            var childNodes = parentNode[childCol];            if (sortCol)                childNodes.sort(function (a, b) {                    return a[sortCol] - b[sortCol];                });            return childNodes;        }        return null;    }    /*end private functions*/    /*Main*/    $.fn.treegridExt = function (method) {        if (methods[method]) {            //如果是调用方法(参数对象中含有方法名)            return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));        } else if (typeof method === 'object' || !method) {            //调用初始化函数(参数不含方法名)            return methods.initExtTree.apply(this, arguments);        } else {            $.error('Method with name ' + method + ' does not exists for jQuery.treegridExt');            return this;        }    };    /*public functions*/    var methods = {        initExtTree: function (options) {            //获取配置信息            var settings = $.extend({}, this.treegrid.defaults, this.treegridExt.defaults, options || {});            var $this = $(this);            //Code            //设置控件容器            $this.treegridExt('setTreeContainer', $this);            //保存设置            $this.treegridExt('setSettings', settings);            if (!settings.url) {                //载入数据                var data = $this.treegridExt('loadData',settings);                if (data && data.length > 0) {                    //生成表格                    $this.treegridExt('renderTable',data);                }                //初始化header                settings.getTableHeader.apply(this,[$this]).treegridExt('initHeader',settings);                //初始化结点                settings.getRootNodes.apply(this, [$this]).treegridExt('initNode', settings);                //生成树                $this.treegridExt('getRootNodes').treegridExt('render');                //默认展开状态                if (!settings.expandAll) {                    $this.treegridExt('collapseAll');                }            } else {                $this.treegridExt('loadData',settings);            }            return $this;        },        dispose: function (options) {            return $(this).each(function () {                var $this = $(this);                $this.treegridExt('delState');                $this.treegridExt('delSettings');                $this.treegridExt('delTreeContainer');            });        },        val: function (options) {            //获取选择器中第一个元素的html            return this.eq(0).html();        },        //##Beigin自定义初始化方法        /*init*/        initHeader: function (settings) {            return this.each(function () {                var $this = $(this);                $this.treegridExt('setTreeContainer', settings.getTreeGridContainer.apply(this));                $this.treegridExt('initCheckAll').treegridExt('initDelAll');                if ($this.treegridExt('getSetting', 'showOperation')) {                    var cell = $('');                    cell.text('操作');                    $this.append(cell);                }                return $this;            });        },        initNode: function (settings) {            return this.each(function () {                var $this = $(this);                $this.treegridExt('setTreeContainer', settings.getTreeGridContainer.apply(this));                               $this.treegridExt('initExpander').treegridExt('initIndent').treegridExt('initCheck').treegridExt('initOperation').treegridExt('initEvents').treegridExt('initState').treegridExt('initChangeEvent').treegridExt('initSettingsEvents');                $this.treegridExt('getChildNodes').treegridExt('initNode', settings);            });        },        initCheckAll: function () {            var $this = $(this);            if ($this.treegridExt('getSetting', 'showCheck') && $this.treegridExt('getSetting', 'showCheckAll')) {                $this.addClass('treegridExt-checkboxAll');                var cell = $('');                var tpl = $this.treegridExt('getSetting', 'checkTemplate');                var checks = $this.treegridExt('getSetting', 'getCheckbox').apply(this);                if (checks && checks.length > 0) {                    checks.remove();                }                $this.prepend(cell.append(tpl));                $this.treegridExt('getSetting', 'getCheckbox').apply(this).click(function () { $this.treegridExt('toggleCheckAll'); });            }            return $this;        },        initDelAll: function () {            var $this = $(this);            if ($this.treegridExt('getSetting', 'showCheckAll') && $this.treegridExt('getSetting', 'showDelAll')) {                var cell = $this.find('th').get(0);                var delTpl = $this.treegridExt('getSetting', 'delAllTemplate');                var checks = $this.treegridExt('getSetting', 'getDelAll').apply(this);                if (checks && checks.length > 0) {                    checks.remove();                }                $(cell).append(delTpl);                $this.treegridExt('getSetting', 'getDelAll').apply(this).click(function () { $this.treegridExt('delChecked'); });            }            return $this;        },        initCheck: function () {            var $this = $(this);            if ($this.treegridExt('getSetting', 'showCheck')) {                var cell = $('');                var tpl = $this.treegridExt('getSetting', 'checkTemplate');                var checks = $this.treegridExt('getSetting', 'getCheckbox');                if (checks && checks.length > 0) {                    checks.remove();                }                $this.prepend(cell.append(tpl));                $this.treegridExt('getSetting', 'getCheckbox').apply(this).click(function () { $this.treegridExt('toggleCheck'); });            }            return $this;        },        initOperation: function () {            var $this = $(this);            if ($this.treegridExt('getSetting', 'showOperation')) {                var cell = $('');                var tpl = $this.treegridExt('getSetting', 'operationTemplate');                $this.append(cell.append(tpl));            }            return $this;        },        initEvents: function () {            var $this = $(this);            //Default behavior on check            $this.on('check', function () {                var $this = $(this);                $this.addClass('treegrid-checked');            });            //Default behavior on other operations            return $this.treegrid('initEvents');        },               initSettingsEvents: function () {            var $this = $(this);            //Save state on check            $this.on('check', function () {                var $this = $(this);                if (typeof ($this.treegridExt('getSetting', 'onCheck')) === "function") {                    $this.treegridExt('getSetting', 'onCheck').apply($this);                }            });            //Save state on other operation            return $this.treegrid('initSettingsEvents');        },        //##end自定义的初始化方法        //##Begin原组件的方法的封装        /*init*/        initExpander: function () {            return $(this).treegrid('initExpander');        },        initIndent: function () {            return $(this).treegrid('initIndent');        },        initState: function () {            return $(this).treegrid('initState');        },        initChangeEvent: function () {            var $this = $(this);            //Save state on chagne            $this.on('change', function () {                var $this = $(this);                $this.treegridExt('render');                if ($this.treegridExt('getSetting', 'saveState')) {                    $this.treegridExt('saveState');                }            });            return $this;        },        /*init-event*/        /*base*/        getTreeContainer: function () {            return $(this).treegrid('getTreeContainer');        },        setTreeContainer: function (container) {            //扩展插件和原插件使用相同的存储空间            return $(this).treegrid('setTreeContainer', container);        },        getSetting: function (name) {            return $(this).treegrid('getSetting',name);        },        setSettings: function (settings) {            return $(this).treegrid('setSettings',settings);        },        restoreState: function () {            return $(this).treegrid('restoreState');        },        saveState: function () {            return $(this).treegrid('saveState');        },        /*node*/        getAllNodes: function () {            return $(this).treegrid('getAllNodes');        },        getParentNode: function () {            return $(this).treegrid('getParentNode');        },        getChildNodes: function () {            return $(this).treegrid('getChildNodes');        },        /*fake-id*/        getNodeId: function () {            return $(this).treegrid('getNodeId');        },        getParentNodeId: function () {            return $(this).treegrid('getParentNodeId');        },        getDepth: function () {            return $(this).treegrid('getDepth');        },        /*bool*/        isRoot: function () {            return $(this).treegrid('isRoot');        },        isNode: function () {            return $(this).treegrid('isNode');        },        isLeaf: function () {            return $(this).treegrid('isLeaf');        },        isFirst: function () {            return $(this).treegrid('isFirst');        },        isLast: function () {            return $(this).treegrid('isLast');        },        isExpanded: function () {            return $(this).treegrid('isExpanded');        },        isCollapsed: function () {            return $(this).treegrid('isCollapsed');        },        isFirstInit: function () {            return $(this).treegrid('isFirstInit');        },        isOneOfParentsCollapsed: function () {            return $(this).treegrid('isOneOfParentsCollapsed');        },        /*verb*/        expand: function () {            return $(this).treegrid('expand');        },        expandAll: function () {            return $(this).treegrid('expandAll');        },        expandRecursive: function () {            return $(this).treegrid('expandRecursive');        },        collapse: function () {            return $(this).treegrid('collapse');        },        collapseAll: function () {            return $(this).treegrid('collapseAll');        },        collapseRecursive: function () {            return $(this).treegrid('collapseRecursive');        },        /*        toggle: function () {            return $(this).treegrid('toggle').apply(this);        },*/        //##End原组件方法的封装        //自定义的方法........        delState: function () {            $.cookie($this.treegridExt('getSetting', 'saveStateName'), null);        },        delSettings: function () {            if (!$(this).treegridExt('getTreeContainer'))                return;            $this.treegridExt('getTreeContainer').removeData('settings');        },        delTreeContainer: function () {            if (!$(this).treegridExt('getTreeContainer'))                return;            return $(this).removeData('treegrid', container);        },        check: function (isCheck) {            var $this = $(this);            if (isCheck) {                $this.treegridExt('getSetting', 'getCheckbox').apply(this).prop('checked',true);                $this.addClass('treegridExt-checked');                if ($this.treegrid('isCollapsed')) {                    $this.treegrid('expand');                }            } else {                $this.treegridExt('getSetting', 'getCheckbox').apply(this).prop('checked', false);                $this.removeClass('treegridExt-checked');            }            return $this;        },        checkDownRecursive: function (isCheck) {            //return $(this).each(function () {
var $this = $(this); $this.treegridExt('check', isCheck); if (!$this.treegridExt('isLeaf')) { $this.treegridExt('getChildNodes').treegridExt('checkDownRecursive', isCheck); } return $this; //}); }, checkUpRecursive: function (isCheck) { var parentNode = $(this).treegridExt('getParentNode'); if (parentNode) { var tag = true; $.each(parentNode.treegridExt('getChildNodes'), function () { var $this = $(this); //异或: T^T(false)、T^F(true)、F^T(true)、F^F(false), 全选或全不选(true), 否则为false. if (isCheck ^ $this.treegridExt('isChecked')) { tag = false; return false; } }); //与非: !(T^T)(false)、!(T^F)(true)、!(F^T)(true)、F^F(true) if (!(isCheck || tag)) { //选的不全 parentNode.treegridExt('check', true); parentNode.addClass('treegridExt-partialChecked'); } else if (isCheck) { //全选 parentNode.treegridExt('check', true); parentNode.removeClass('treegridExt-partialChecked'); } else { //全不选 parentNode.treegridExt('check', false); parentNode.removeClass('treegridExt-partialChecked'); } if (!parentNode.treegridExt('getParentNode')) { parentNode.treegridExt('checkUpRecursive', isCheck); } } else { //rootNodes var $this = $(this); var checkCount = 0; var rootNodes = $this.treegridExt('getRootNodes'); $.each(rootNodes, function (index, item) { var $item = $(item); if($item.treegridExt('isChecked')){ checkCount++; } if ($item.treegridExt('isPartialChecked')) { checkCount--; } }); var chkTr = $this.treegridExt('getSetting','getTableHeader').apply(this,[$($this.treegridExt('getTreeContainer'))]); if (checkCount < rootNodes.length) { //全不选,部分选 if (isCheck || checkCount > 0) { //chkTr.find('input[type="checkbox"]').prop('checked',true); chkTr.treegridExt('getSetting', 'getCheckbox').apply($(chkTr)).prop('checked', true); chkTr.removeClass('treegridExt-checkedAll').addClass('treegridExt-partialChecked'); } else { chkTr.treegridExt('getSetting', 'getCheckbox').apply($(chkTr)).prop('checked', false); chkTr.removeClass('treegridExt-checkedAll').removeClass('treegridExt-partialChecked'); } } else { //全选 chkTr.treegridExt('getSetting', 'getCheckbox').apply($(chkTr)).prop('checked', true); chkTr.removeClass('treegridExt-partialChecked').addClass('treegridExt-checkedAll'); } } }, toggleCheck: function () { var $this = $(this); var isCheck = $this.treegridExt('isChecked'); $this.treegridExt('check', !isCheck); $this.treegridExt('checkDownRecursive', !isCheck); $this.treegridExt('checkUpRecursive', !isCheck); return $this; }, toggleCheckAll: function () { var $this = $(this); var chkAll = $this.treegridExt('getSetting', 'getCheckbox').apply(this); var isCheck = $this.treegridExt('isCheckedAll'); if (isCheck) { chkAll.prop('checked', false); $this.removeClass('treegridExt-checkedAll'); } else { chkAll.prop('checked', true); $this.addClass('treegridExt-checkedAll'); } $.each($this.treegridExt('getRootNodes'), function (index, item) { $(item).treegridExt('checkDownRecursive', !isCheck); }); return $this; }, delChecked: function () { alert('这是删除按钮啦!'); }, getRootNodes: function () { return $(this).treegrid('getRootNodes'); }, /*bool*/ isChecked: function () { return $(this).hasClass('treegridExt-checked'); }, isPartialChecked: function(){ return $(this).hasClass('treegridExt-partialChecked'); }, isCheckedAll: function () { return $(this).hasClass('treegridExt-checkedAll'); }, isDelAll: function () { return $(this).hasClass('treegridExt-delAll'); }, /*loadData*/ loadData: function (settings) { var $this = $(this); var defData = settings.data; var url = settings.url; if (defData && defData.length >0) { return defData; } else if (url) { $.ajax({ type: settings.type, url: url, data: settings.data, dataType: "JSON", success: function (data, textStatus, jqXHR) { //debugger; if (data && data.length > 0) { //生成表格 $this.treegridExt('renderTable',data); } //初始化Header settings.getTableHeader.apply(this, [$this]).treegridExt('initHeader', settings); //初始化结点 settings.getRootNodes.apply(this, [$this]).treegridExt('initNode', settings); //生成树 $this.treegridExt('getRootNodes').treegridExt('render'); //默认展开状态 if (!settings.expandAll) { $this.treegridExt('collapseAll'); } } }); return $this; } }, /*render*/ render: function () { return $(this).each(function () { var $this = $(this); //if parent colapsed we hidden if ($this.treegrid('isOneOfParentsCollapsed')) { $this.hide(); } else { $this.show(); } if (!$this.treegrid('isLeaf')) { $this.treegrid('renderExpander'); $this.treegrid('getChildNodes').treegrid('render'); } }); }, renderExpander: function () { return $(this).each(function () { var $this = $(this); var expander = $this.treegrid('getSetting', 'getExpander').apply(this); if (expander) { if (!$this.treegrid('isCollapsed')) { expander.removeClass($this.treegrid('getSetting', 'expanderCollapsedClass')); expander.addClass($this.treegrid('getSetting', 'expanderExpandedClass')); } else { expander.removeClass($this.treegrid('getSetting', 'expanderExpandedClass')); expander.addClass($this.treegrid('getSetting', 'expanderCollapsedClass')); } } else { $this.treegrid('initExpander'); $this.treegrid('renderExpander'); } }); }, renderTable: function (data) { var $this = $(this); //debugger; //设置表样式 $this.addClass('table'); if ($this.treegridExt('getSetting', 'striped')) { $this.addClass('table-striped'); } if ($this.treegridExt('getSetting', 'bordered')) { $this.addClass('table-bordered'); } //生成表头 $this.treegridExt('renderHead'); //生成表体 $this.treegridExt('renderBody', data); return $this; }, renderHead: function () { var $this = $(this); //debugger; var thead = $('') var thr = $(''); thr.addClass('treegridExt-header'); $.each($this.treegridExt('getSetting', 'columns'), function (i, item) { var th = $(''); th.text(item.title); thr.append(th); }); thr.appendTo(thead); return $this.append(thead); }, renderBody: function (data) { var $this = $(this); var tbody = $(''); var isTreedData = $this.treegridExt('getSetting', 'treedData'); var parentCol = $this.treegridExt('getSetting', 'parentColumn'); var sortCol = $this.treegridExt('getSetting', 'sortColumn'); var cols = $this.treegridExt('getSetting', 'columns'); var rootNodes = getRootNodesFromData(data, isTreedData, parentCol, sortCol); if (rootNodes && rootNodes.length > 0) { $.each(rootNodes, function (i, item) { var tr = $(''); tr.addClass('treegrid-' + (++nodeCount)); $.each(cols, function (index, column) { var td = $(''); td.text(item[column.field]); tr.append(td); }); tbody.append(tr); if ($this.treegridExt('getSetting', 'treedData')) { var childCol = $this.treegridExt('getSetting', 'childrenColumn'); $this.treegridExt('renderTreedDataTr', item, nodeCount, cols, childCol, sortCol, tbody); } else { var idCol = $this.treegridExt('getSetting', 'idColumn'); $this.treegridExt('renderListDataTr', data, item, nodeCount, cols, idCol, parentCol, sortCol, tbody); } }); } return $this.append(tbody); }, renderListDataTr: function (data, parentData, parentIndex, columns, idColumn, parentColumn, sortColumn, tbody) { var nodes = getListChildNodesFromData(data, parentData, idColumn, parentColumn, sortColumn); if (nodes && nodes.length > 0) { $.each(nodes, function (i, item) { var tr = $(''); var nowParentIndex = ++nodeCount; tr.addClass('treegrid-' + nowParentIndex); tr.addClass('treegrid-parent-' + parentIndex); $.each(columns, function (index, column) { var td = $(''); td.text(item[column.field]); tr.append(td); }); tbody.append(tr); $(this).treegridExt('renderListDataTr', data, item, nowParentIndex, columns, idColumn, parentColumn, sortColumn, tbody); }); } }, renderTreedDataTr: function (parentNode, parentIndex, columns, childColumn, sortColumn, tbody) { var nodes = getTreeChildNodesFromdata(parentNode, childColumn, sortColumn); if (nodes && nodes.length > 0) { $each(nodes, function (i, item) { var tr = $(''); var nowParentIndex = ++nodeCount; tr.addClass('treegrid-' + nowParentIndex); tr.addClass('treegrid-parent-' + parentIndex); $each(columns, function (index, column) { var td = $(''); td.text(item[column.field]); tr.append(td); }); tbody.append(tr); $(this).treegridExt('renderTreedDataTr', item, nowParentIndex, columns, childColumn, sortColumn, tbody); }); } }, }; /*default values*/ $.fn.treegridExt.defaults = { idColumn: 'Id', parentColumn: 'ParentId', treeColumn: 0, //在哪一列上显示展开按钮 treedData: false, //是否树化的数据 childrenColumn: null, //含有孩子结点的属性, 非树化结构直接值为null data: [], //构造table的数据集合 type: "GET", //请求数据的ajax类型 url: null, //请求数据的ajax的url ajaxParams: {}, //请求数据的ajax的data属性 sortColumn: null, //按照哪一列进行排序 striped: false, //是否各行渐变色 bordered: false, //是否显示边框 expandAll: true, //是否全部展开 showCheck: true, //是否显示选择列 showCheckAll: true, //是否选择全选列 showDelAll: true, //显示全删按钮 showOperation: true, //是否显示操作列 columns: [], //列名列值 checkTemplate: '', delAllTemplate: '', operationTemplate: '', expanderExpandedClass: 'glyphicon glyphicon-chevron-down', //展开的按钮的图标 expanderCollapsedClass: 'glyphicon glyphicon-chevron-right', //缩起的按钮的图标 getCheckbox: function () { return $(this).find('input[type="checkbox"]'); }, getDelAll: function () { return $(this).find('input[type="reset"]'); }, getTableHeader: function (treegridContainer) { var result = $.grep(treegridContainer.find('tr'), function (element) { var classNames = $(element).attr('class'); var templateClass = /treegridExt-header/; return templateClass.test(classNames); }); return $(result); }, /*Event*/ onCollpase: null, onExpand: null, onChange: null, onCheck: null };})(jQuery);
View Code

 

//jquery.treegridExt.css

.treegridExt-checkbox {}.treegridExt-checkboxAll {}.treegridExt-checked {
background-color:transparent;}.treegridExt-checkedAll {
background-color:transparent;}.treegridExt-partialChecked td {
background-color: red; }.treegrid-header {}
View Code

 

 //前台HTMl

List.cshtml片段

查询结果

@section scripts{ }
View Code

 

相关图片, 就从treegrid的源码包里面找吧...

 

最终效果如下:

 

 

转载于:https://www.cnblogs.com/cs_net/p/6926432.html

你可能感兴趣的文章
解决无扬声器(无喇叭)的HDMI接口显示屏声音问题
查看>>
2008R2 AD 域的安装
查看>>
CopyCat 代码克隆检测发布,剑指开源软件抄袭
查看>>
Xen的network-bridge模式
查看>>
我的友情链接
查看>>
spring--(14)利用注解建立bean与bean之间的关系
查看>>
OSPF详解-2 区域结构
查看>>
安装交叉工具链arm-linux-gcc
查看>>
RAID详解[RAID0/RAID1/RAID10/RAID5]
查看>>
前端渐进式框架Vue讲解
查看>>
linux有关Block的知识
查看>>
判断出栈顺序的合法性(面试题)
查看>>
注释转换——(小项目)
查看>>
注释转换
查看>>
MFC界面库BCGControlBar v25.0新功能详解二:网格和报表控件
查看>>
MFC界面库BCGControlBar v25.0新功能详解六:属性网格和其他
查看>>
【重大更新】DevExpress v17.1新版亮点(DevExtreme & HTML5/JS篇)
查看>>
IT十八掌作业_java基础第十二天_集合
查看>>
超详细派克斯使用安装教程
查看>>
电磁搅扰EMI
查看>>