论坛首页 Web前端技术论坛

[Ext扩展]JsonTreeLoader:一次加载所有树节点更新1.1版本

浏览 4715 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2010-04-14   最后修改:2010-04-29
仿照官网例子:XmlTreeLoader做的,下面有实例
注意:html文件的库引用请自行解决
/**
 * 通过读取JSON串生成树的层次结构,务必保证json数组中结点出现次序与树完全展开时一致!
 * (通过后台对编码进行排序来完成)
 * JSON串根节点默认为'list'
 * 父结点id字段为
 * 
 * 注意:
 * 1.因为是一次加载全部结点,节点数过多的话将严重影响性能,此时请使用异步加载!
 * 2.结点的id属性对应json中code属性,结点text属性对应json中name属性。
 * 3.根节点的直接子节点的parentcode字段为null或者空字符串都可以
 * 
 * v1.1改动:
 * 1.不再需要leaf属性!一个结点是否为叶子结点将基于json中下一个结点是否为其子节点来判断!
 * 本特性将提高转变叶子节点为父节点的操作效率,此时你在界面上给一个叶子结点添加一个子节点
 * 不用再修改叶子结点在后台的leaf属性,你要做的只是保证返回json中的编码规范以及出现次序。
 * 2.如果你设置了leaf属性则此属性将被忽略
 * 
 * @author chemzqm@gmail.com
 * 
 */
Ext.ns('Ext.ux.tree');


Ext.ux.tree.JsonTreeLoader = Ext.extend(Ext.tree.TreeLoader, {
    root: 'list',
    paramName: {
        parentcode: 'parentcode',
        id: 'code'
    },
    
    // private override
    processResponse: function(response, node, callback){
        var json = response.responseText;
        var array = Ext.decode(json)[this.root];     
        try {
            node.beginUpdate();
            node.appendChild(this.parseArray(array));
            node.endUpdate();
            
            if (typeof callback == "function") {
                callback(this, node);
            }
        } 
        catch (e) {
            this.handleFailure(response);
        }
    },
    
    // private
    parseArray: function(array){
        var pnodes = [];
        var nodes = [];
       	for (var i = 0; i < array.length; i++) {
			var o =  array[i];//判断是否叶子结点
			if(array[i+1]&&array[i+1][this.paramName.parentcode]==o[this.paramName.id]){
				o.leaf = false;
			}else{
				o.leaf = true;
			}
			var treeNode = this.createNode(o);
			if (!o[this.paramName.parentcode]) {
				nodes.push(treeNode);
			}
			else {
				for (var j = pnodes.length - 1; j >= 0; j--) {
					if (pnodes[j].id == o[this.paramName.parentcode]) {
						pnodes[j].appendChild(treeNode);
						break;
					}
				}
			}
			if (!treeNode.leaf) {
				pnodes.push(treeNode);
			}
			
		}
        return nodes;
    },
    // private override node的id是json里面的code字段
    createNode: function(o){	
        var attr = {
            id: o.code,
            text: o.name
        };
        Ext.applyIf(attr, o);
        attr.loaded = true;
        
        this.processAttributes(attr);
        
        return Ext.ux.tree.JsonTreeLoader.superclass.createNode.call(this, attr);
    },
    
    /*
     * Template method intended to be overridden by subclasses that need to provide
     * custom attribute processing prior to the creation of each TreeNode.  This method
     * will be passed a config object containing existing TreeNode attribute name/value
     * pairs which can be modified as needed directly (no need to return the object).
     */
    processAttributes: Ext.emptyFn
});

//backwards compat
Ext.ux.JsonTreeLoader = Ext.ux.tree.JsonTreeLoader;

   发表时间:2010-04-23  
请问,测试过吗?
为什么我下载例子后树无法显示出来?
0 请登录后投票
   发表时间:2010-04-26  
air831 写道
请问,测试过吗?
为什么我下载例子后树无法显示出来?

当然,这里的树采用异步方式加载,直接用浏览器打开文件是无法向后端发起请求的,你需要配置一个web环境(譬如tomcat、IIS、jetty等)再通过url方式访问
0 请登录后投票
   发表时间:2010-04-29   最后修改:2010-04-29
这次我配置了WEB环境,数据库返回的Json为以下格式,但是还是无法显示树
返回的Json
{
  "menu": [
    {
      "url": "Main.ASPX/Login/",
      "name": "管理信息系统",
      "code": "0",
      "leaf": false,
      "parentcode": "-1"
    },
    {
      "url": "Task.ASPX/Index",
      "name": "任务查询",
      "code": "1",
      "leaf": true,
      "parentcode": "0"
    },
    {
      "url": "BaseInfo.ASPX/Index",
      "name": "基础资料",
      "code": "2",
      "leaf": true,
      "parentcode": "0"
    }
  ]
}

生成树JS
        var menu = new Ext.tree.TreePanel({
          title: '功能菜单',
          region: "west",
          autoScroll: true,
          enableTabScroll: true,
          collapsible: true,
          collapsed: false,
          split: true,
          rootVisible: false,
          loader: new Ext.ux.tree.JsonTreeLoader({//这里配下就行了
            root: 'menu',
            dataUrl: contextpath + 'Main.ASPX/GetMenuTree'
          }),
          root: new Ext.tree.AsyncTreeNode()
        });
0 请登录后投票
   发表时间:2010-04-29   最后修改:2010-04-29
我知道问题的原因了,
       "url": "Main.ASPX/Login/",
      "name": "管理信息系统",
      "code": "0",
      "leaf": false,
      "parentcode": "-1"   --------------根节点的parentcode必须要等于" "

在firefox中显示正常,但是在IE中无法加载,查了下,说是因为“Ext.tree.TreePanel 在IE下不正常加载”
需要加上监听,有其他什么好办法吗?
      listeners: {
              "loadexception": function(loader, node, response) {
                node.loaded = false;
                node.reload.defer(10, node); //不停的加载,直到true
              }
            }



0 请登录后投票
   发表时间:2010-04-29  
air831 写道
我知道问题的原因了,
       "url": "Main.ASPX/Login/",
      "name": "管理信息系统",
      "code": "0",
      "leaf": false,
      "parentcode": "-1"   --------------根节点的parentcode必须要等于" "

在firefox中显示正常,但是在IE中无法加载,查了下,说是因为“Ext.tree.TreePanel 在IE下不正常加载”
需要加上监听,有其他什么好办法吗?
      listeners: {
              "loadexception": function(loader, node, response) {
                node.loaded = false;
                node.reload.defer(10, node); //不停的加载,直到true
              }
            }




我在ie6下测试了你的代码,没有发现任何问题啊,用不着加什么监听事件,出现loadexception可能是你在哪儿重复加载数据了吧
0 请登录后投票
   发表时间:2010-05-12  
这样设计是不好的,不要把数据组织放到服务端
0 请登录后投票
   发表时间:2010-05-12  
joehe 写道
这样设计是不好的,不要把数据组织放到服务端

这个要看情况吧,如果是死的层次结构我把层次信息存在数据库敢问有合不妥?
0 请登录后投票
论坛首页 Web前端技术版

跳转论坛:
Global site tag (gtag.js) - Google Analytics