1 5.1 TreePanel的基本使用
2 //树是一种非常典型的数据结构;
3 5.1.1 创建一棵树
4 //树控件有Ext.tree.TreePanel类定义,控件的名称为TreePanel;TreePanel类继承字Panel类;
5 Ext.onReady(function(){
6 var tree = new Ext.tree.TreePanel({ //创建tree对象;
7 store:new Ext.data.TreeStore({ //传入数据;
8 root:{ //root根;
9 text:'树根',
10 leaf:true
11 }
12 })
13 });
14 tree.render('tree'); //将树渲染到DOM;
15 });
16
17 5.1.2 为树添加枝和叶
18 root:{
19 text:'我是根',
20 children:[{
21 text:'我是根的第一个枝子',
22 children:[{ //子文件夹;
23 text:'我是第一个枝子的第一个叶子',
24 leaf:true //叶子文件;
25 },{
26 text:'我是根的第一个叶子'
27 leaf:true
28 }]
29 }]
30 }
31 tree.getRootNode.expand(false,true);
32 //参数一:是否递归展开所有子节点;参数二:是否要动画效果;
33
34 5.1.3 树形的配置
35 //将tree期望渲染的目标id放到{}里;
36 renderTo:'tree'
37
38 5.1.4 使用TreeStore获得数据
39 //Ext.data.TreeStore可以利用从后台获取的数据为我们组装出一棵树来;只需提供数据,让TreeStore完成数据转换和装配节点
40 var tree = new Ext.tree.TreePanel({
41 store:new Ext.data.TreeStore({
42 proxy:{
43 type:'ajax',
44 url:'xxx.txt'
45 },
46 root:{text:'我是根'}
47 });
48 renderTo:'tree'
49 });
50 //由于异步加载会使用树形TreeStore中的url向后台发送请求;当展开节点执行对应节点的expand()方法时,它会通过Ajax访问url指定的地址并获取数据;而且还会把自己的id作为参数参数传递给url指定的地址;
51 //异步读取属性的节点是非常好的方法;只有点击某一节点后才会去获取子节点属性并进行渲染;
52
53 5.1.5 使用JSP提供后台数据
54 //当某个节点展开时,TreeStore会根据设置的url地址去后台读取数据;
55 //而当发动请求时,TreeStore会把这个节点的id作为参数一起发送到后台去;
56 //对于后台来说,只要获得node参数,就知道是哪个节点正在执行展开;
57 //然后后台根据节点的id返回对应的JSON数据;其中包含id(节点唯一的标识)和text(节点的名称);
58
59 5.1.6 通过XML加载树形
60 <nodes>
61 <node>
62 <text>node 1</text>
63 <leaf>false</leaf> //是树结构的文件夹;
64 </node>
65 <node>
66 <text>node 2</text>
67 <leaf>true</leaf> //是树结构的文件;
68 </node>
69 </nodes>
70 var store = Ext.create('Ext.data.TreeStore',{
71 proxy:{
72 type:'ajax',
73 url:'xx.xml',
74 extraParams:{
75 isXml:true
76 },
77 reader:{
78 type:'xml',
79 root:'nodes',
80 record:'node'
81 }
82 },
83 sorters:[{
84 property:'leaf',
85 direction:'ASC'
86 },{
87 property:'text',
88 direction:'ASC'
89 }],
90 root:{
91 text:'Ext JS',
92 id:'src',
93 expanded:true
94 }
95 });
96 //因为读取XML数据时Ext无法区分上下节点关联,所以想获得多级层级结构,只能通过异步方式一层一层地加载,负责输出数据的后台根据每次发送的node参数判断目前是在展开哪一个节点;
1 5.2 树的事件
2 //使用on()把一个函数绑定到一个事件上;
3 tree.on('itemexpand',function(node){
4 console.info(node,"展开了");
5 });
6 tree.on("itmecollapse",function(node){
7 console.inro(node,"折叠了");
8 });
9 tree.on("itemclick",function(node){
10 console.info("你单击了",node);
11 })
1 5.3 右键菜单
2 >1.先注册一个名为contextmenu的事件,触发事件时,弹出自己定制的菜单;
3 var contextmenu = new Ext.menu.Menu({
4 id:'theContextMenu',
5 items:[{
6 text:'点我!',
7 handler:function(){
8 alert('我被点击了~');
9 }
10 }]
11 });
12 >2.绑定contextmenu事件
13 tree.on('itemcontextmenu',function(view,record,item,index,e){
14 e.preventDefault(); //阻止浏览器默认右键;
15 contextmenu.showAt(e.getXY); //调用显示菜单在点击的地方;
16 })
1 5.4 修改节点的默认图标
2 //每个树形节点都有icon和iconCls属性;
3 >.icon
4 {
5 text:'icon',
6 icon:'user_female.png',
7 leaf:true
8 }
9 >.iconCls
10 {
11 text:'iconCls',
12 iconCls:'icon-male',
13 leaf:true
14 }
15 //同时要在HTML中添加对应的CSS定义:
16 .x-tree-cion-leaf .icon-male {
17 background-image:url(user_male.png);
18 }
19 //iconCls只能定义背景图片,icon设置的是IMG的SRC部分,icon中设置的图片会把背景图片部分挡住;
1 5.5 从节点弹出对话框
2 //从事件中获得的node只是一个对象,而不是HTML中一个实际的DOM元素;所以不能直接用animateTarget:node来实现飞出效果;
3 //Ext的树节点都遵循MVC设计,所以要找到对应的DOM元素,应该使用节点的View部分;
4 tree.on("itemclick",function(view,record,item){
5 Ext.Msg.show({
6 title:'提示',
7 msg:'你单击了'+record.id,
8 animateTarget:item //弹窗从点击点弹出;
9 })
10 });
1 5.6 节点提示信息
2 //鼠标停留在某个节点的上方时,显示提示信息;
3 //在JSON中添加对应的节点提示内容,qtip:'xxx';
4 //此时代码需要对提示功能初始化;
1 5.7 为节点设置超链接
2 //在节点树形中设置超链接的地址;
3 //在JSON数据中添加参数href:"xxx.html",打开位置hrefTarget:'_blank';
1 5.8 树形的拖放
2 //在创建TreePanel时,设置启用插件treeviewdragdrop;从而实现叶子与树杈和根之间的拖放;
3 var tree = new Ext.tree.TreePanel({
4 viewConfig:{
5 plugins:{ptype:'treeviewdragdrop'} //启用拖拽插件;
6 },
7 store:new Ext.data.TreeStore({
8 proxy:{
9 type:'ajax',
10 url:'xxx.txt'
11 },
12 root:{text:'我是根'}
13 })
14 tree.renderTo('tree');
15 });
16
17 5.8.1 节点拖放的三种形式
18 >1.append:放下去的节点会变成目标节点的子节点;
19 >2.above:放下去的节点和目标节点是兄弟关系,放下去的节点排行在前;
20 >3.below:放下去的节点与目标节点是兄弟关系,放下去的节点排行在后;
21
22 5.8.2 叶子拖拽问题
23 //Ext规定:如果节点包含leaf:true;就不能用拖放的方式添加子节点;
24 tree.view.on("beforedrop",function(node,data,overModel,dropPosition,dropHandler){
25 if(overModel.get('leaf')){ //判断鼠标指针经过的节点是否包含leaf:true;
26 overModel.set('leaf',false); //更改leaf属性;
27 overModel.set('loaded',true); //设置可以拖拽;
28 }
29 return true;
30 });
31
32 5.8.3 判断拖放的目标+Ajax提交
33 //drop事件是拖放的节点放下去时触发的;
34 tree.view.on("drop",function(node,data,overModel,dropPosition,dropHandler){
35 //node:正在拖放的节点;
36 //overModel:是放下去碰到的节点;
37 //dropPosition:是放下去的方式;
38 //通过这些数据,我们可以知道当前节点的位置和状态,从而计算出数据并通过Ajax发送给后台;让后台对节点的数据进行更行;
39 Ext.Msg.alert("提示","咱们的节点"+node.id+"掉到了"+overModel.get('id')+"上,掉落方式是"+dropPosition);
40 var item = {
41 dropNode:node.id,
42 target:overModel.get('id'),
43 point:dropPosition
44 };
45 Ext.Ajax.request({
46 method:'POST',
47 url:'xxx.jsp',
48 success:function(response){
49 //response:相应对象;其中包含响应状态和响应内容;
50 Ext.Msg.alert('信息',response.responseText);
51 //responseText:以文本形式返回信息;
52 },
53 failure:function(){
54 Ext.Msg.alert("错误","与后台联系时出现问题");
55 },
56 params:{
57 //发送给后台的参数;"name1=value1&name2=value2";
58 data:encodeURIComponent(Ext.encode(item))
59 //对参数进行编码,避免出现非法字符;
60 }
61 });
62 });
63
64 5.8.4 树之间的拖放
65 //对两棵树都设置ptype:'treeviewdragdrop';
1 5.9 对树进行排序
2 //设置folderSort:true参数,可以实现为树形进行排序;
3 var tree = new Ext.tree.TreePanel({
4 store:new Ext.data.TreeStore({
5 folderSort:true, //为属性自动排序;
6 proxy:{..}
7 root:{...}
8 })
9 });
1 5.10 带Checkbox的树形
2 //在节点数据设置参数:checked:true;
3 var tree = new Ext.tree.TreePanel({
4 store:new Ext.data.TreeStore({
5 root:{
6 text:'我是根',
7 children:[{text:'Leaf No.1',leaf:true,checked:true}]
8 //为叶子前添加复选框;
9 }
10 })
11 });
1 5.11 表格与树形的结合
2 //在表格中实现分级显示的功能;两者都支持对不同分类数据执行展开和折叠的操作;
3 //通过扩展使用treecolumn插件的方式实现表格与树形结合的效果;
4 Ext.onReady(function(){
5 Ext.define('Task',{ //定义Task类;
6 extend:'Ext.data.Model',//继承Model类;
7 fields:[
8 {name:'task',type:'string'},
9 {name:'user',tyhpe:'string'},
10 {name:'duration',type:'string'}
11 ]
12 });
13
14 var tree = new Ext.tree.TreePanel({
15 rootVisible:false, //隐藏根节点;
16 title:'示例',
17 renderTo:'tree',
18 collapsible:true, //具有可折叠功能;
19 useArrows:true, //在tree中使用Vista-style样式的箭头;
20
21 columns:[{ //每一行应该分为激烈进行显示;
22 xtype:'treecolumn',
23 header:'任务',
24 width:330,
25 dataIndex:'task' //设置任务列;
26 },{
27 xtype:'treecolumn',
28 header:'持续时间',
29 width:100,
30 dataIndex:'duration'
31 },{
32 xtype:'treecolumn',
33 header:'负责人',
34 width:100,
35 dataIndex:'user'
36 }],
37
38 store:new Ext.data.TreeStore({
39 model:Task,
40 proxy:{
41 type:'ajax', //设置Ajax方式传送;
42 url:'xxx.txt'
43 },
44 root:{
45 text:'我是根'
46 }
47 })
48 });
49 });
50 //后台JSON数据
51 [{
52 task:'Ext程序开发', //第一列内容;
53 duration:'12month', //第二列内容;
54 user:'', //第三列内容;
55 cls:'master-task', //class;
56 iconCls:'task-folder', //icon图标;
57 children:[{ //子分支;
58 task:'第一章内容', //分支第一行内容
59 duration:'1month', //分支第二行内容
60 user:'Lingo', //分支第三行内容
61 leaf:true, //叶子分支
62 iconCls:'tase' //icon图标
63 },{...}]
64 }]
1 5.12 更多树形的高级应用
2 5.12.1 如何选中树的某个节点
3 >1.TreePanel.selectPath():传入的参数是想要选中的节点path值;
4 //根id='root'下有id='leaf'的节点,则selectPath('root/leaf');
5 >2.TreePanel.getSelectionModel():获得属性的选择模型;
6 //SM有一个select()函数,传入index或者节点对应的record就可以选中这个节点;
7
8 5.12.2 刷新树的所有节点
9 //根节点有一个reload()函数,使用它会刷其下的所有节点;若要刷新整棵树,就要取得根节点rootNode,然后调用reload()函数;
10
11 5.12.3 借用grid的缓冲视图插件
12 //在成千上万个树形节点需要渲染时,保证只渲染当前渲染的视图部分,自动监听滚动条的拖拽情况;按需加载,保证在显示海量数据时不发生卡顿问题;
13 plugins:[{ptype:'bufferedrenderer'}], //引入插件;
14
15 5.12.4 借用grid的锁定插件
16 //将某一列锁定,即使出现横向滚动条,也可以保证锁定的列一直显示在视图中;
17 //直接对某一列设置locked:true;就可以锁定它;
18 {
19 xtype:'treeecolumn',
20 text:'任务',
21 wdith:300,
22 dataIndex:'task',
23 locked:true
24 }