带搜索功能的下拉树的实现

要做个下拉框带树结构的控件。

找了几个组件拼凑了个出来了。

 

 

<?xml version="1.0" encoding="utf-8"?>
<s:WindowedApplication xmlns:fx="http://ns.adobe.com/mxml/2009"
			   xmlns:s="library://ns.adobe.com/flex/spark" 
			   xmlns:mx="library://ns.adobe.com/flex/mx"
			   creationComplete="init()"  
			   width="400" height="300"
			   showStatusBar="false">
	<fx:Script>
		<![CDATA[
			import flashx.textLayout.operations.CutOperation;
			import flashx.textLayout.operations.DeleteTextOperation;
			import flashx.textLayout.operations.FlowOperation;
			
			import mx.collections.ArrayCollection;
			import mx.collections.ArrayList;
			import mx.collections.IList;
			import mx.collections.XMLListCollection;
			import mx.events.ListEvent;
			import mx.utils.StringUtil;
			
			import spark.events.TextOperationEvent;
			
		 	[Bindable]
			private var xm:XML = 
				<root> 
						<league label="全公司" data="1234" isdep="true"> 
								<division label="开发" data="2234" isdep="true"> 
										<team label="应用" data="2234" isdep="true"/> 
										<team label="系统" data="1" isdep="true"/> 
										<team label="测试" data="234" isdep="true"> 
												<team label="研发吗" data="34" isdep="false"/>
												<team label="研发里面" data="56" isdep="false"/>
												<team label="研发里" data="153" isdep="false"/>
										</team>
										<team label="支撑" data="214" isdep="true"/> 
								</division> 
								<division label="销售"> 
										<team label="浙江" data="89" isdep="true"/> 
										<team label="cfdw" data="76" isdep="true"/> 
										<team label="江苏" data="1255" isdep="true"/> 
										<team label="上海" data="164" isdep="true"> 
												<team label="上海1" data="34" isdep="false"/>
												<team label="上海12" data="56" isdep="false"/>
												<team label="上海2" data="153" isdep="false"/>
										</team>
										<team label="Kansas" data="17834" isdep="false"/> 
								</division> 
								<division label="财务" data="1y4" isdep="true"> 
										<team label="tobg" data="1gf4" isdep="false"/> 
										<team label="tyue" data="5" isdep="false"/> 
										<team label="Toronto" data="134" isdep="false"/> 
										<team label="tyar" data="4" isdep="false"/> 
										<team label="Tampa Bay" data="ui" isdep="false"/> 
								</division> 
								<division label="产品" data="734" isdep="true"/> 
								<division label="cds" data="120" isdep="false"/> 
						</league> 
				</root>
			; 
			
			
			[Bindable]
			public var selectedNode:XML;
			
			[Bindable]
			private var a:XMLList = new XMLList();
			
			[Bindable]
			private var b:XMLListCollection = new XMLListCollection();
		
			[Bindable]
			private var c:ArrayCollection = new ArrayCollection();
			
			[Bindable]
			private var bp:ArrayCollection = new ArrayCollection();
			
			private function init():void
			{
				a = xm.league; 
				b = new XMLListCollection(a); 
				c = new ArrayCollection(b.toArray());

				this.addEventListener(MouseEvent.MOUSE_DOWN, focusOut);
			}
			
			private function focusOut(event:MouseEvent):void
			{
				if(event.currentTarget.id != 'treelist' && event.currentTarget.id != 'relist')
				{
					result.displayPopUp = false;
					frmPUA.displayPopUp = false;
				}
			}
			
			protected function openBtn_clickHandler(event:MouseEvent):void
			{
//				if(result.displayPopUp || frmPUA.displayPopUp)
//				{
//					result.displayPopUp = false;
//					frmPUA.displayPopUp = false;
//				}else
//				{
					frmPUA.displayPopUp = true;
//				}
			}
			
			protected function textin_changeHandler(event:TextOperationEvent):void
			{
				var operation:FlowOperation = event.operation;

				if (operation is DeleteTextOperation || operation is CutOperation)
				{
					result.displayPopUp = false;
				}
				else 
				{
					if (result.displayPopUp = false)
					{
						result.displayPopUp = true;
						return;
					}   

					var keyWord:String = StringUtil.trim(textin.text);  
					if(keyWord!='')
					{
						searchKeyWord(keyWord);
					}
					else
					{
						result.displayPopUp =false;
					}
				}
			}
			
			private function searchKeyWord(keyWord:String):void
			{  
				bp.removeAll();
				bp = filterData(c,keyWord); 
//				var typedLength:int = textin.text.length;
//				var ob:XML = new XML();
				if(bp.length > 0)
				{  
//					搜索时可以让输入框内文字变化,见spark的combobox组件源码
//					ob = bp[0] as XML; 
//					var itemString:String = ob.@label;
//					textin.selectAll();
//					textin.insertText(itemString);
//					textin.selectRange(typedLength, itemString.length);
					
					frmPUA.displayPopUp = false;
					result.displayPopUp = true;
					
					textin.addEventListener(KeyboardEvent.KEY_UP, changeFocous);
				}
				else
				{
					frmPUA.displayPopUp = false;
					result.displayPopUp = false;
					if(selectedNode)
					{
						textin.text = selectedNode.@label;
					}
					else
					{
						textin.text = '';
					}
				}
			}  
			
			private function changeFocous(event:KeyboardEvent):void
			{  
				if(event.keyCode == 40 || event.keyCode == 13)
				{
					relist.setFocus();
					relist.selectedIndex = 0;
				}
			}
			
			private function filterData(ac:ArrayCollection, keyword:String):ArrayCollection
			{  
				var xm:XML = ac[0] as XML;
				find(xm, keyword);
				return bp; 
			}
			
			// 递归遍历xml
			private function find( node:XML, keyword:String ):void 
			{
				for each ( var element:XML in node.elements( ) ) 
				{
					var str:String = element.@label;
					
					//区分大小写时 str.indexOf(keyword)
					//不区分大小写 str.search(new RegExp(keyword,"gi")
					if(str.search(new RegExp(keyword,"gi")) != -1 )				
					{  
//						可以根据在xml标签里定义哪些可以被搜索
//						if(element.@isdep == 'false')
//						{
							var item:Object = element as Object;
							
							if(str == keyword)//出现完全匹配但不在队列前端的将其加到列表最前端
							{ 
								bp.addItemAt(item,0);
							}else
							{
								bp.addItem(item); 
							}
//						}
					}  
					
					find( element,keyword );
				}
			} 
			
			private function listchange(e:ListEvent):void
			{
				selectedNode = Tree(e.target).selectedItem as XML;
				textin.text = selectedNode.@label;
				frmPUA.displayPopUp = false;
			}

			
			protected function relist_clickHandler(event:MouseEvent):void
			{
				selectedNode = relist.selectedItem as XML;
				textin.text = selectedNode.@label;
				result.displayPopUp = false;
			}
			
			protected function relist_keyUpHandler(event:KeyboardEvent):void
			{
				if(event.keyCode == 13)
				{
					selectedNode = relist.selectedItem as XML;
					textin.text = selectedNode.@label;
					result.displayPopUp = false;
				}
			}
			
		]]>
	</fx:Script>
	
	<fx:Declarations>
		<mx:Tree  id="tree1" dataProvider="{c}"  width="150" labelField="@label"
				  selectedIndex="0"  />   
	</fx:Declarations>

	
	<s:Panel x="10" y="10" width="90%" height="90%" title="My ComBoTree Selector Example">        
	
			<s:Group id="vg" x="10" y="10">
			
				<s:TextInput x="0" y="0" width="130" height="20" id="textin" change="textin_changeHandler(event)"/>
				<s:Button x="130" y="0" id="openBtn" width="20" height="20" label="O" 
						  click="openBtn_clickHandler(event)"/>
				
				<s:PopUpAnchor id="frmPUA" x="0" y="20" popUpWidthMatchesAnchorWidth="true"  
							   popUpPosition="topLeft" width="150" height="200">
					
					<mx:Tree  id="treelist" dataProvider="{c}" maxHeight="200" labelField="@label"
							  selectedIndex="0" change="listchange(event)"/>   
				</s:PopUpAnchor>    
				<s:PopUpAnchor id="result" x="0" y="20" popUpWidthMatchesAnchorWidth="true" 
							   popUpPosition="topLeft" width="150" height="200">
					
					<s:List  id="relist" dataProvider="{bp}" height="100%" width="100%"  maxHeight="200"
							 labelField="@label" selectedIndex="-1" keyUp="relist_keyUpHandler(event)"
							 click="relist_clickHandler(event)"/>   
				</s:PopUpAnchor> 
			</s:Group>
			
			
			
			<!--<mx:PopUpButton width="150" popUp="{tree1}" label="{tree1.selectedItem.@label}"/> -->
		
	</s:Panel>   
	
</s:WindowedApplication>
 

 

 

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值