TreeGrid

TreeGrid.js原路径:http://www.extjs.com/forum/showthread.php?t=37831

 

效果图(查看附件treegrid.gif)

 

Ext的treePanel提供了很丰富实用功能,可以现自由拖拽、添加、删除等,但是缺点是只能显示一行信息,无法满足需求;Ext2.0的Demo里有提供一个Cloumn tree的实现,但是无法使用checkbox事件,为了让tree+cloumn+checkbox和平共处,本来打算改一下Cloumn tree的实现的,写之前浏览了一下ext论坛的扩展实现和插件,发现有写好的,就直接奉行拿来主义了。作者有讲说这是一个初期版本,需要改进的地方挺多,不管先拿过来看看再说,demo包在上面的路径可以下载到。

 

1、jsp页面需要引用的文件:

<script type='text/javascript' src='../../../ExtJS/adapter/ext/ext-base.js'></script>
 <script type='text/javascript' src='../../../ExtJS/ext-all-debug.js'></script>
 <script type='text/javascript' src='../../../ExtJS/examples/grid/RowExpander.js'></script>
 <script type='text/javascript' src='../../TreeGrid.js'></script>
<link rel="stylesheet" type="text/css" href="../../../ExtJS/resources/css/ext-all.css" />
 <link rel="stylesheet" type="text/css" href="../../css/TreeGrid.css" />  
 <link rel="stylesheet" type="text/css" href="../../css/TreeGridLevels.css" /> 

 以上文件ExtJS目录下都是ext2.0包里自带,TreeGrid.js可以在附件里下载到;样式文件TreeGrid.clss必须要,TreeGridLevels.css可以不须要引用,如果你认为这个样式好看的话也可以引入。

 

2、来看一下demo里的实现代码:

Controller = function()
{
	function createGrid()
	{
    var data = [
			{"company":"0. Johnson & Johnson","price":64.72,"change":0.06,"pct_change":0.09,"last_change":"9\/1 12:00am","_id":1,"_parent":null,"_level":1,"_lft":1,"_rgt":98,"_is_leaf":false},
			{"company":"1. American International Group, Inc.","price":64.13,"change":0.31,"pct_change":0.49,"last_change":"9\/1 12:00am","_id":2,"_parent":1,"_level":2,"_lft":2,"_rgt":17,"_is_leaf":false},
			{"company":"2. Alcoa Inc","price":29.01,"change":0.42,"pct_change":1.47,"last_change":"9\/1 12:00am","_id":3,"_parent":1,"_level":2,"_lft":18,"_rgt":65,"_is_leaf":false},
			{"company":"3. The Coca-Cola Company","price":45.07,"change":0.26,"pct_change":0.58,"last_change":"9\/1 12:00am","_id":4,"_parent":1,"_level":2,"_lft":66,"_rgt":79,"_is_leaf":false},
			{"company":"4. Citigroup, Inc.","price":49.37,"change":0.02,"pct_change":0.04,"last_change":"9\/1 12:00am","_id":5,"_parent":null,"_level":1,"_lft":99,"_rgt":100,"_is_leaf":true},
			{"company":"5. Hewlett-Packard Co.","price":36.53,"change":-0.03,"pct_change":-0.08,"last_change":"9\/1 12:00am","_id":6,"_parent":null,"_level":1,"_lft":101,"_rgt":118,"_is_leaf":false},
			{"company":"6. McDonald's Corporation","price":36.76,"change":0.86,"pct_change":2.4,"last_change":"9\/1 12:00am","_id":7,"_parent":1,"_level":2,"_lft":80,"_rgt":85,"_is_leaf":false},
			{"company":"7. The Procter & Gamble Company","price":61.91,"change":0.01,"pct_change":0.02,"last_change":"9\/1 12:00am","_id":8,"_parent":4,"_level":3,"_lft":67,"_rgt":76,"_is_leaf":false},
			{"company":"8. Johnson & Johnson","price":64.72,"change":0.06,"pct_change":0.09,"last_change":"9\/1 12:00am","_id":9,"_parent":2,"_level":3,"_lft":3,"_rgt":6,"_is_leaf":false},
			{"company":"9. Microsoft Corporation","price":25.84,"change":0.14,"pct_change":0.54,"last_change":"9\/1 12:00am","_id":10,"_parent":7,"_level":3,"_lft":81,"_rgt":82,"_is_leaf":true},
			{"company":"10. E.I. du Pont de Nemours and Company","price":40.48,"change":0.51,"pct_change":1.28,"last_change":"9\/1 12:00am","_id":11,"_parent":3,"_level":3,"_lft":19,"_rgt":36,"_is_leaf":false},
			{"company":"11. Honeywell Intl Inc","price":38.77,"change":0.05,"pct_change":0.13,"last_change":"9\/1 12:00am","_id":12,"_parent":11,"_level":4,"_lft":20,"_rgt":29,"_is_leaf":false},
			{"company":"12. Microsoft Corporation","price":25.84,"change":0.14,"pct_change":0.54,"last_change":"9\/1 12:00am","_id":13,"_parent":4,"_level":3,"_lft":77,"_rgt":78,"_is_leaf":true},
			{"company":"13. American International Group, Inc.","price":64.13,"change":0.31,"pct_change":0.49,"last_change":"9\/1 12:00am","_id":14,"_parent":null,"_level":1,"_lft":119,"_rgt":122,"_is_leaf":false},
			{"company":"14. Hewlett-Packard Co.","price":36.53,"change":-0.03,"pct_change":-0.08,"last_change":"9\/1 12:00am","_id":15,"_parent":null,"_level":1,"_lft":123,"_rgt":136,"_is_leaf":false}
];
   
    // add in some dummy descriptions and loaded flag
		for (var i = 0; i < data.length; i++) {
    	data[i].desc = 'Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Sed metus nibh, sodales a, porta at, vulputate eget, dui. Pellentesque ut nisl. Maecenas tortor turpis, interdum non, sodales non, iaculis ac, lacus. Vestibulum auctor, tortor quis iaculis malesuada, libero lectus bibendum purus, sit amet tincidunt quam turpis vel lacus. In pellentesque nisl non sem. Suspendisse nunc sem, pretium eget, cursus a, fringilla vel, urna.<br/><br/>Aliquam commodo ullamcorper erat. Nullam vel justo in neque porttitor laoreet. Aenean lacus dui, consequat eu, adipiscing eget, nonummy non, nisi. Morbi nunc est, dignissim non, ornare sed, luctus eu, massa. Vivamus eget quam. Vivamus tincidunt diam nec urna. Curabitur velit.';
    	data[i]._is_loaded = true;
		}
		
		var expander = new Ext.grid.RowExpander({
      tpl : new Ext.Template(
          '<p><b>Company:</b> {company}</p><br>',
          '<p><b>Summary:</b> {desc}</p>'
      )
    });

    // create the data store
    var record = Ext.data.Record.create([
   		{name: 'company'},
     	{name: 'price', type: 'float'},
     	{name: 'change', type: 'float'},
     	{name: 'pct_change', type: 'float'},
     	{name: 'last_change', type: 'date', dateFormat: 'n/j h:ia'},
     	{name: 'desc'},
     	{name: '_id', type: 'int'},
     	{name: '_level', type: 'int'},
     	{name: '_lft', type: 'int'},
     	{name: '_rgt', type: 'int'},
     	{name: '_is_leaf', type: 'bool'}
   	]);
    var store = new Ext.ux.maximgb.treegrid.NestedSetStore({
    	autoLoad : true,
			reader: new Ext.data.JsonReader({id: '_id'}, record),
			proxy: new Ext.data.MemoryProxy(data)
    });
    // create the Grid
    var grid = new Ext.ux.maximgb.treegrid.GridPanel({
      store: store,
      master_column_id : 'company',
      columns: [
      	expander,
				{id:'company',header: "Company", width: 160, sortable: true, dataIndex: 'company'},
        {header: "Price", width: 75, sortable: true, renderer: 'usMoney', dataIndex: 'price'},
        {header: "test", width: 75, sortable: true, renderer: 'usMoney', dataIndex: 'price',renderer:showbox,align:'center'},
        {header: "Change", width: 75, sortable: true, renderer: change, dataIndex: 'change'},
        {header: "% Change", width: 75, sortable: true, renderer: pctChange, dataIndex: 'pct_change'},
        {header: "Last Updated", width: 85, sortable: true, renderer: Ext.util.Format.dateRenderer('m/d/Y'), dataIndex: 'last_change'}
      ],
      stripeRows: true,
      autoExpandColumn: 'company',
      title: 'Array Grid',
      root_title: 'Companies', 
      plugins: expander,
      viewConfig : {
      	enableRowBody : true
      }
    });
    var vp = new Ext.Viewport({
    	layout : 'fit',
    	items : grid
    });
    grid.getSelectionModel().selectFirstRow();
	}
	
	function showbox(value){
		return "<input type=checkbox name='item' value='"+value+"'>";
	}
	
	// example of custom renderer function
  function change(val)
  {
    if (val > 0) {
      val = '<span style="color:green;">' + val + '</span>';
    } 
    else if(val < 0) {
			val = '<span style="color:red;">' + val + '</span>';
    }
    return val;
  }

  // example of custom renderer function
  function pctChange(val)
  {
    if (val > 0) {
      val = '<span style="color:green;">' + val + '%</span>';
    } 
    else if(val < 0) {
      val = '<span style="color:red;">' + val + '%</span>';
    }
    return val;
  }

	return {
		init : function()
		{
			createGrid();
		}
	}
}();

Ext.onReady(Controller.init);

 

  

 3、数据分析

{"company":"0. Johnson & Johnson","price":64.72,"change":0.06,"pct_change":0.09,"last_change":"9\/1 12:00am","_id":1,"_parent":null,"_level":1,"_lft":1,"_rgt":98,"_is_leaf":false},

  这是数组data的其中一行数据,我们可以看到除了业务数据以外,还有几个比较特殊的数据:_id,_parent,_level,_lft,_rgt,_is_leaf。这几个值必须要有的,下面我们来看看这几个属性的作用。

_id:这个不用讲了吧。

_parent:值必须为父级菜单的id值。

_level:菜单级别。

_lft & _rgt:这两个值我看了半天才明白,按照二叉树的索引位置来计算的,具体的请参考http://dev.mysql.com/tech-resources/articles/hierarchical-data.html

_is_leaf: 是不是最终节目节。

 

注:如果要跑通例子的话,把上面的这几个属性名称前面的'_'下划线都去了吧,不太习惯这样写,所以下面附件里的代码稍微做了一下改动;还有就是如果讨厌计算_lft和_rht的值,可以在数据库里或者在生json的时候就自定义排下序,如果你是按照二叉树的索引位置来排序的话,可以不用设置_lft和_rgt的值,否则会造成子菜单的位置与父菜单不对应的情况。上面是请求的本地的一个数组,下面我把远程请求json的加载方法发一下:

var store = new Ext.ux.maximgb.treegrid.AdjacencyListStore({
	autoLoad : true,
	url: '../tree!list.action?id='+id+'&format=json',
	reader: new Ext.data.JsonReader(
				{
					id: 'id',
					root: 'menu',
					totalProperty: 'total',
					successProperty: 'success'
				}, 
				record
	)
});

 

 4、创建Ext.ux.maximgb.treegrid.GridPanel参数说明

master_column_id:值为ColumnModel中设置的需要作为tree显示的一列的id,如上例中的cloumns的第一列"id:'company'",注意要将dataIndex这一列的数据放在第一列显示;

autoExpandColumn: 同上;

root_title:显示的tree的根,值是一个字符串,如果为空会自动获取title的值,都为空里显示root。

其它属性与普通grid用法一样。

 

 

之所以选择使用这个而不是cloumn tree是因为在renderer checkbox并触发checkbox事件的时候不会发生错误。如果你想调试运行可以直接去下demo域者跑通这个都可以。不使用远程数据就直接可以在apache环境运行。这里获取远程数据是结合java使用的,也可以改成php的。

 

下次再发一下TreeGrid源码解读。以上实现方式如果有不正确的地方多指证!

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
treegrid插件 当前选中的行: var config = { id: "tg1", width: "800", renderTo: "div1", headerAlign: "left", headerHeight: "30", dataAlign: "left", indentation: "20", folderOpenIcon: "images/folderOpen.gif", folderCloseIcon: "images/folderClose.gif", defaultLeafIcon: "images/defaultLeaf.gif", hoverRowBackground: "false", folderColumnIndex: "1", itemClick: "itemClickEvent", columns:[ {headerText: "", headerAlign: "center", dataAlign: "center", width: "20", handler: "customCheckBox"}, {headerText: "名称", dataField: "name", headerAlign: "center", handler: "customOrgName"}, {headerText: "拼音码", dataField: "code", headerAlign: "center", dataAlign: "center", width: "100"}, {headerText: "负责人", dataField: "assignee", headerAlign: "center", dataAlign: "center", width: "100"}, {headerText: "查看", headerAlign: "center", dataAlign: "center", width: "50", handler: "customLook"} ], data:[ {name: "城区分公司", code: "CQ", assignee: "", children:[ {name: "城区卡品分销中心"}, {name: "先锋服务厅", children:[ {name: "chlid1"}, {name: "chlid2"}, {name: "chlid3", children: [ {name: "chlid3-1"}, {name: "chlid3-2"}, {name: "chlid3-3"}, {name: "chlid3-4"} ]} ]}, {name: "半环服务厅"} ]}, {name: "清新分公司", code: "QX", assignee: "", children:[]}, {name: "英德分公司", code: "YD", assignee: "", children:[]}, {name: "佛冈分公司", code: "FG", assignee: "", children:[]} ] }; /* 单击数据行后触发该事件 id:行的id index:行的索引。 data:json格式的行数据对象。 */ function itemClickEvent(id, index, data){ window.location.href="ads"; } /* 通过指定的方法来自定义栏数据 */ function customCheckBox(row, col){ return ""; } function customOrgName(row, col){ var name = row[col.dataField] || ""; return name; } function customLook(row, col){ return "查看"; } //创建一个组件对象 var treeGrid = new TreeGrid(config); treeGrid.show(); /* 展开、关闭所有节点。 isOpen=Y表示展开,isOpen=N表示关闭 */ function expandAll(isOpen){ treeGrid.expandAll(isOpen); } /* 取得当前选中的行,方法返回TreeGridItem对象 */ function selectedItem(){ var treeGridItem = treeGrid.getSelectedItem(); if(treeGridItem!=null){ //获取数据行属性值 //alert(treeGridItem.id + ", " + treeGridItem.index + ", " + treeGridItem.data.name); //获取父数据行 var parent = treeGridItem.getParent(); if(parent!=null){ //jQuery("#currentRow").val(parent.data.name); } //获取子数据行集 var children = treeGridItem.getChildren(); if(children!=null && children.length>0){ jQuery("#currentRow").val(children[0].data.name); } } }

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值