Flex4之Tree开发【一】

1.首先得明白一点,FLEX4的TREE接受的是XML类型的数据,所以无论以何种方式获得XML数据,TREE通过dataProvider=XMLDATA和[email protected]都可以显示出来一棵树

第一种方式,读取本地或远程XML文件

XML文件的格式,大致如下

<?xml version="1.0" encoding="UTF-8"?>
<node  label='所有分类'>
<node  label='中国' value="http://www.baidu.com">
<node label='河南' value="http://www.youdao.com" >
<node  label='信阳' />
<node  label='南阳'/>
</node>
<node  label='河北'>
<node label='保定'/>
<node  label='衡水'/>
</node>
<node label='湖南' >
<node label='长沙'/>
<node  label='湘潭'/>
</node>
<node label='湖北'>
<node label='武汉'/>
<node label='仙桃'/>
</node>
</node>
</node>

 针对上面这个XML格式的文件,Flex4的TREE解析后显示的话会从第二个节点开始解析也即中国那个节点
这种方式的代码我贴出来,大家看下

<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" 
			   xmlns:s="library://ns.adobe.com/flex/spark" 
			   xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600"
			   creationComplete="SrvTreeList.send();init()">
	<fx:Style>
		Tree {
		folderClosedIcon: ClassReference(null);
		folderOpenIcon: ClassReference(null);
		}
	</fx:Style>

	<fx:Script>
		<![CDATA[
			import mx.collections.ArrayCollection;
			import mx.rpc.events.ResultEvent;

			var XMLTreeList:XML;
			protected function treeService_resultHandler(event:ResultEvent):void
			{   
				//先把数据取出来交给XML,再交给dataProvider,因为dataProvider不能直接解析String为XML
				XMLTreeList=XML(SrvTreeList.lastResult.toString()); 
				MusicTypeTree.dataProvider=XMLTreeList; 

			}
                        //这里我写了一个右键菜单		
                       public function init():void{
			
			 var item: ContextMenuItem=new ContextMenuItem("添加");
			 var menu:ContextMenu=new ContextMenu();
			 menu.customItems.push(item);
			 MusicTypeTree.contextMenu=menu;
			}



			protected function tree1_clickHandler(event:MouseEvent):void
			{
				if(MusicTypeTree.selectedItem.hasOwnProperty("@value" ))
					
				{       //如果某节点中含有VALUE属性,那么就是先跳转页面
					navigateToURL(new URLRequest([email protected])); 
				} else
				{ 
					//没有那就展开,如果展开了就收缩
					MusicTypeTree.expandItem(MusicTypeTree.selectedItem,!MusicTypeTree.isItemOpen(MusicTypeTree.selectedItem),true);
				} 
			}

		]]>
	</fx:Script>
	<fx:Declarations>
		<!-- 将非可视元素(例如服务、值对象)放在此处 -->
		<s:HTTPService  id="SrvTreeList" url="data/tree.xml" result="treeService_resultHandler(event)" useProxy="false"  resultFormat="xml" />
	</fx:Declarations>
	<[email protected]这个非常重要,指定要显示的标题为XML重的label属性值。记住要显示树,httpService的send方法要在组件创建完成后被调用-->
	<mx:Tree x="20" y="10" click="tree1_clickHandler(event)" id="MusicTypeTree"
			 left="5" right="5" 
			 showRoot="false" 
			 labelField="@label"         
			 bottom="5" top="40"
			 
			 ></mx:Tree>
	
</s:Application>

 



 

 第二种方式:将XML内容写到<fx:mxl>标签里面
这种方式我们来看看

<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" 
			   xmlns:s="library://ns.adobe.com/flex/spark" 
			   xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600"
			   creationComplete="init()">
	<fx:Declarations>
		<!-- 将非可视元素(例如服务、值对象)放在此处 -->
	</fx:Declarations>
<fx:Script>
	<![CDATA[
		import mx.collections.ICollectionView;
		import mx.events.ListEvent;
		private function tree_itemClick(evt:ListEvent):void {
			var item:Object = Tree(evt.currentTarget).selectedItem;
			if (tree.dataDescriptor.isBranch(item)) {
				tree.expandItem(item, !tree.isItemOpen(item), true);
			}
		}
		private function tree_labelFunc(item:XML):String {
			var children:ICollectionView;
			var suffix:String = "";
			if (tree.dataDescriptor.isBranch(item)) {
				children = tree.dataDescriptor.getChildren(item);
				suffix = " (" + children.length + ")";
			}
			return item[tree.labelField] + suffix;
		}
		
		
	]]>
</fx:Script>
	<fx:Declarations>
		

	<fx:XML id="dp">
		<root>
			<folder label="One">
				<folder label="One.A">
					<item label="One.A.1" />
					<item label="One.A.2" />
					<item label="One.A.3" />
					<item label="One.A.4" />
					<item label="One.A.5" />
				</folder>
				<item label="One.1" />
				<item label="One.2" />
			</folder>
			<folder label="Two">
				<item label="Two.1" />
				<folder label="Two.A">
					<item label="Two.A.1" />
					<item label="Two.A.2" />
				</folder>
			</folder>
		</root>
	</fx:XML>
	</fx:Declarations>
	<mx:Tree id="tree"
			 dataProvider="{dp}"
			 showRoot="false"
			 labelField="@label"
			 labelFunction="tree_labelFunc"
			 width="742"
			 rowCount="6"
			 itemClick="tree_itemClick(event);"  x="14" y="12" height="359"/>
	
</s:Application>

 


Flex4之Tree开发【一】
 

itemClick方法可以和labelFuntion可以不写,正常的话不写方法就能显示TREE的树形结构了

第三:再看一个例子

<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" 
			   xmlns:s="library://ns.adobe.com/flex/spark" 
			   xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600">
	<fx:Declarations>
		<!-- 将非可视元素(例如服务、值对象)放在此处 -->
		<fx:XMLList id="treeData">  
			<node label="Mail Box">  
				<node label="Inbox">  
					<node label="Marketing"/>  
					<node label="Product Management"/>  
					<node label="Personal"/>  
				</node>  
				<node label="Outbox">  
					<node label="Professional"/>  
					<node label="Personal"/>  
				</node>  
				<node label="Spam"/>  
				<node label="Sent"/>  
			</node>     
		</fx:XMLList>  
	</fx:Declarations>
	<fx:Script>
		<![CDATA[
			[Bindable] 
			public var selectedNode:XML; 
			
			// Event handler for the Tree control change event. 
			public function treeChanged(event:Event):void { 
				selectedNode=Tree(event.target).selectedItem as XML; 
			} 
		]]>
	</fx:Script>
	<mx:Panel title="Tree Control Example" height="75%" width="75%"   
			  paddingTop="10" paddingLeft="10" paddingRight="10" paddingBottom="10">  
		
		<mx:Label width="100%" color="blue"   
				  text="Select a node in the Tree control."/>  
		
		<mx:HDividedBox width="100%" height="100%">  
			<mx:Tree id="myTree" width="50%" height="100%" labelField="@label"  
					 showRoot="false" dataProvider="{treeData}" change="treeChanged(event)"/>  
			<mx:TextArea height="100%" width="50%"  
						 text="Selected Item: {[email protected]}"/>  
		</mx:HDividedBox>  
		
	</mx:Panel>  
</s:Application>


Flex4之Tree开发【一】
 

第四,到目前为止,应该可以看出来了XML的显示格式了,如果获取XML文件那么结果要转换成为
var xmlList:XML=XML(event.result.toString());
mytree.dataProvider=xmlList;
要么就是<mx:Tree dataProvider="{xmlList}" >
那么就是
<fx:xml id="xmlid"></fx:xml>
<mx:Tree dataProvider="{xmlid}">

这么多的方式都可以把数据填充到TREE中去

第五:来一个增删拖拽展开,收缩的示例,这里先不涉及到后台,下一篇文章会讲到TREE与JAVA后台数据库的交互操作

<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" 
			   xmlns:s="library://ns.adobe.com/flex/spark" 
			   xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600"
			   creationComplete="SrvTreeList.send();init()">
	<fx:Style>
		Tree {
		folderClosedIcon: ClassReference(null);
		folderOpenIcon: ClassReference(null);
		}
	</fx:Style>

	<fx:Script>
		<![CDATA[
			import mx.collections.ArrayCollection;
			import mx.controls.Alert;
			import mx.core.DragSource;
			import mx.core.UIComponent;
			import mx.events.DragEvent;
			import mx.managers.DragManager;
			import mx.rpc.events.ResultEvent;

			var XMLTreeList:XML;
			protected function treeService_resultHandler(event:ResultEvent):void
			{   
				//先把数据取出来交给XML,再交给dataProvider,因为dataProvider不能直接解析String为XML
				XMLTreeList=XML(SrvTreeList.lastResult.toString()); 
				MusicTypeTree.dataProvider=XMLTreeList; 

			}

			public function init():void{
			
			 var item: ContextMenuItem=new ContextMenuItem("添加");
			 var menu:ContextMenu=new ContextMenu();
			 menu.customItems.push(item);
			 MusicTypeTree.contextMenu=menu;
			}



			protected function tree1_clickHandler(event:MouseEvent):void
			{
				if(MusicTypeTree.selectedItem.hasOwnProperty("@value" ))
				{ 
					
					var u:URLRequest=new URLRequest([email protected]);
					//navigateToURL(new URLRequest([email protected])); 
					navigateToURL(u);
				} else
				{ 
					//没有那就展开,如果展开了就收缩
					MusicTypeTree.expandItem(MusicTypeTree.selectedItem,!MusicTypeTree.isItemOpen(MusicTypeTree.selectedItem),true);
				} 
			}

            //添加兄弟节点
			protected function addBefore():void
			{
				var xml:XML=MusicTypeTree.selectedItem as XML;
				var text:String=nextName.text;
				if(xml!=null && text.length>0) {
					var parent:XML=xml.parent();
					if(parent!=null) {
						var child:XML=new XML("<node foddersortName=\"\" foddersortId=\"\"  parentid=\"\" />");
						[email protected]=text;
						parent.insertChildBefore(xml,child);
					} else {
						Alert.show("不能选中根节点");
					}
				} else {
					Alert.show("需要先选中节点和填入文字");
				}
			}
			
			protected function addAfter():void
			{
				var xml:XML=MusicTypeTree.selectedItem as XML;
				var text:String=nextName.text;
				if(xml!=null && text.length>0) {
					var parent:XML=xml.parent();
					if(parent!=null) {
						var child:XML=new XML("<node foddersortName=\"\" foddersortId=\"\"  parentid=\"\" />");
						[email protected]=text;
						parent.insertChildAfter(xml,child);
					} else {
						Alert.show("不能选中根节点");
					}
				} else {
					Alert.show("需要先选中节点和填入文字");
				}
			}
			
			protected function addSon():void
			{
				var xml:XML=MusicTypeTree.selectedItem as XML;
				var text:String=nextName.text;
				if(xml!=null && text.length>0) {
					var parent:XML=xml.parent();
					var child:XML=new XML("<node foddersortName=\"\" foddersortId=\"\"  parentid=\"\" />");
					[email protected]=text;
					xml.appendChild(child);
					MusicTypeTree.expandChildrenOf(xml,true);
				} else {
					Alert.show("需要先选中节点和填入文字");
				}			
			}
			protected function editNode():void
			{
				var xml:XML=MusicTypeTree.selectedItem as XML;
				var text:String=nextName.text;
				if(xml!=null && text.length>0) {
					[email protected]=text;
				} else {
					Alert.show("需要先选中节点和填入文字");
				}			
			}
			protected function deleteNode():void
			{
				var xml:XML=MusicTypeTree.selectedItem as XML;
				if(xml!=null) {
					var list:Array=MusicTypeTree.selectedItems as Array;
					for(var k:int=0;k<list.length;k++) {
						xml=list[k] as XML;
						var parent:XML=xml.parent();
						if(parent!=null) {
							var children:XMLList=parent.children();
							for(var i:int=0;i<children.length();i++) {
								if(children[i]==xml) {
									delete children[i];
									break;
								}
							}
						} else {
							Alert.show("不能选中根节点");
						}
					}
				} else {
					Alert.show("需要先选中节点");
				}			
			}
			protected function selectNode():void
			{
				var text:String=nextName.text;
				if(text.length>0) {
					var items:Array=[];
					var list:XMLList=new XMLList();
					list[0]=MusicTypeTree.dataProvider[0];				
					searchItems(list,text,items);
					MusicTypeTree.selectedItems=items;
				} else {
					Alert.show("输入查找的文字");
				}
			}
			private function searchItems(list:XMLList,find:String,items:Array):void {
				for(var i:int=0;i<list.length();i++) {
					var one:XML=list[i];
					var label:[email protected];
					if(label!=null && label.indexOf(find)>=0) {
						items.push(one);
					}
					searchItems(one.children(),find,items);
				}
			}
			
			
			
			protected function closeAll():void{
				MusicTypeTree.openItems=[];
			
			}
			
			protected function openAll():void{
			
				
				MusicTypeTree.expandChildrenOf(MusicTypeTree.selectedItem,true);
			}


			protected function MusicTypeTree_dragEnterHandler(event:DragEvent):void
			{
				Alert.show([email protected]);
				DragManager.acceptDragDrop(UIComponent(event.currentTarget));
			}


			protected function MusicTypeTree_dragOverHandler(event:DragEvent):void
			{
				
				// r is the visible index in the tree 
				var dropTarget:Tree = Tree(event.currentTarget);
			
				var r:int = dropTarget.calculateDropIndex(event);
				MusicTypeTree.selectedIndex = r;
			
				// retrieving the newly selected node, you can examine it and decide to tell 
				// the user the drop is invalid by changing the feedback.
				var node:XML = MusicTypeTree.selectedItem as XML;
				if( [email protected] == "中国" ) {
					DragManager.showFeedback(DragManager.NONE);
					return;
				}
				// the type of drop - copy, link, or move can be reflected in the feedback as well. 
				// Here the control and shift keys determine that action. 
				if (event.ctrlKey)
					DragManager.showFeedback(DragManager.COPY);
				else if (event.shiftKey)
					DragManager.showFeedback(DragManager.LINK);
				else {
					DragManager.showFeedback(DragManager.MOVE);
				}

			}


			protected function MusicTypeTree_dragDropHandler(event:DragEvent):void
			{
				var xml:XML=MusicTypeTree.selectedItem as XML;
				Alert.show([email protected]);
//				var ds:DragSource = event.dragSource;
//				var dropTarget:Tree = Tree(event.currentTarget);
//				// retrieve the data associated with the "items" format. This will be the data that
//				// the dragInitiator has copied into the DragSource.
//				var items:Array = ds.dataForFormat("items") as Array;
//				// determine where in the tree the drop occurs and select that node by the index; followed by 
//				// retrieving the node itself. 
//				var r:int = MusicTypeTree.calculateDropIndex(event);
//				MusicTypeTree.selectedIndex = r;
//				var node:XML = MusicTypeTree.selectedItem as XML;
//				var p:*;
//				// if the selected node has children (it is type==city),
//				// then add the items at the beginning
//				if( MusicTypeTree.dataDescriptor.hasChildren(node) ) {
//					p = node;
//					r = 0;
//				} else {
//					p = node.parent();
//				}
//				// taking all of the items in the DragSouce, insert them into the 
//				// tree using parent p. 
//				for(var i:Number=0; i < items.length; i++) {
//					var insert:XML = <node />;
//					[email protected]= items[i];
//					//[email protected] = "restaurant";
//					MusicTypeTree.dataDescriptor.addChildAt(p, insert, r+i);
//				}
			}


			protected function MusicTypeTree_dragCompleteHandler(event:DragEvent):void
			{
				MusicTypeTree.selectedIndex = -1;

			}

		]]>
	</fx:Script>
	<fx:Declarations>
		<!-- 将非可视元素(例如服务、值对象)放在此处 -->
		<s:HTTPService  id="SrvTreeList" url="data/tree.xml" result="treeService_resultHandler(event)" useProxy="false"  resultFormat="xml" />
	</fx:Declarations>
	<[email protected]这个非常重要,指定要显示的标题为XML重的label属性值。记住要显示树,httpService的send方法要在组件创建完成后被调用-->
	<mx:Tree click="tree1_clickHandler(event)" id="MusicTypeTree"
			 left="5" right="845" 
			 showRoot="false" 
			 labelField="@foddersortName"         
			 bottom="243" top="40"
			 dragEnabled="true"
			 dropEnabled="true"
			 allowMultipleSelection="true"
			 allowDragSelection="true"
			 dragDrop="MusicTypeTree_dragDropHandler(event)"
		     dragEnter="MusicTypeTree_dragEnterHandler(event)"
			 ></mx:Tree>
	<s:TextInput id="nextName" x="432" y="40"/>
	<s:Button x="443" y="82" label="增加为哥" click="addBefore()"/>
	<s:Button x="443" y="111" label="增加为弟" click="addAfter()"/>
	<s:Button x="444" y="144" click="addSon()" label="增加为孩子"/>
	<s:Button x="444" y="178" click="editNode()" label="修改节点"/>
	<s:Button x="444" y="211" click="deleteNode()" label="删除节点"/>
	<s:Button x="443" y="244" click="selectNode()" label="选择节点"/>
	<s:Button x="443" y="277" click="closeAll()" label="全部收缩"/>
	<s:Button x="443" y="306" click="openAll()" label="全部展开"/>
	
</s:Application>

 


Flex4之Tree开发【一】