我正在尝试根据另一个XMLListCollection的属性对XMLListCollection进行排序,但我没有取得多大成功。
我想将食物集合按照食物的顺序排序 - 它存储在另一个XMLListcollection中。
<?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:XML xmlns="" id="_foods">
<data>
<node label="Apple" id="A"/>
<node label="Banana" id="B"/>
<node label="Carrot" id="C"/>
<node label="Dandelion" id="D"/>
</data>
</fx:XML>
<fx:XML xmlns="" id="_orders">
<data>
<order id="C"/>
<order id="A"/>
<order id="D"/>
<order id="B"/>
</data>
</fx:XML>
<s:XMLListCollection id="_orderList" source=" {_orders.children()}"/>
<s:XMLListCollection id="_foodCollection" source="{_foods.children()}" sort="{_foodSort}"/>
<s:Sort id="_foodSort" compareFunction="sortFruits"/>
</fx:Declarations>
<fx:Script>
<![CDATA[
protected function sortFruits(a:Object, b:Object, fields:Array = null):int
{
var _currentItem:XML = XML(a);
var _currentOrderIndex:int= getNodeIndexByAttribute(_orderList,'id',_currentItem.@id);
var _currentFruitIndex:int= getNodeIndexByAttribute(_foodCollection,'id',_currentItem.@id)
if(_currentFruitIndex > _currentOrderIndex) {_returnData =1;}
else
if(_currentFruitIndex < _currentOrderIndex) { _returnData =-1;}
else {_returnData = 0}
var _returnData:int = 0
return _returnData
}
public function getNodeIndexByAttribute(theCollection:XMLListCollection,theAttributeName:String, theAttributeValue:String):int {
//THIS IS RETURNS THE INDEX OF A CHILD NODE BASED UPON AN ATTRIBUTE THAT IS PASSED IN - GENERIC FUNCTION
var _returnData:int
for (var i:int = 0; i < theCollection.length; i++)
{
var _currentItem:XML = theCollection.getItemAt(i) as XML
if (_currentItem.attribute(theAttributeName) == theAttributeValue) { _returnData = i;
break;
}
}
return _returnData;
}
]]>
</fx:Script>
<s:List width="100%" height="100%" labelField="@label" dataProvider="{_foodCollection}"/>
</s:Application>
就我所见,我似乎正在尽一切努力,但我必须做错事,因为它不起作用!我认为这可能与我如何实现比较功能有关。
对此有任何帮助将不胜感激! ;)
答案 0 :(得分:1)
通过定义 sort 函数,默认情况下不会对XMLListCollection进行排序。您需要在某个时刻刷新()集合,这可以在您加载视图或按需时自动完成。我添加了一个按钮来说明这一点。
如果你测试我添加的这个按钮,它应该可以工作。另外,我已经用mx替换了s:sort,因为我使用的是较旧的Flex Framework,所以请随时再修改它。
<?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"
>
<s:layout>
<s:VerticalLayout />
</s:layout>
<fx:Declarations>
<mx:Sort id="sort" compareFunction="sortFruits" />
<fx:XML xmlns="" id="_foods">
<data>
<node label="Apple" id="A"/>
<node label="Banana" id="B"/>
<node label="Carrot" id="C"/>
<node label="Dandelion" id="D"/>
</data>
</fx:XML>
<fx:XML xmlns="" id="_orders">
<data>
<order id="C"/>
<order id="A"/>
<order id="D"/>
<order id="B"/>
</data>
</fx:XML>
<s:XMLListCollection id="_orderList" source=" {_orders.children()}"/>
<s:XMLListCollection id="_foodCollection" source="{_foods.children()}" sort="{sort}"/>
</fx:Declarations>
<fx:Script>
<![CDATA[
protected function sortFruits(a:Object, b:Object, fields:Array = null):int {
var _currentItem:XML = XML(a);
var _currentOrderIndex:int = getNodeIndexByAttribute(_orderList, 'id', _currentItem.@id);
var _currentFruitIndex:int = getNodeIndexByAttribute(_foodCollection, 'id', _currentItem.@id)
if (_currentFruitIndex > _currentOrderIndex) {
_returnData = 1;
}
else if (_currentFruitIndex < _currentOrderIndex) {
_returnData = -1;
}
else {
_returnData = 0
}
var _returnData:int = 0
return _returnData
}
public function getNodeIndexByAttribute(theCollection:XMLListCollection, theAttributeName:String, theAttributeValue:String):int {
//THIS IS RETURNS THE INDEX OF A CHILD NODE BASED UPON AN ATTRIBUTE THAT IS PASSED IN - GENERIC FUNCTION
var _returnData:int
for (var i:int = 0; i < theCollection.length; i++) {
var _currentItem:XML = theCollection.getItemAt(i) as XML
if (_currentItem.attribute(theAttributeName) == theAttributeValue) {
_returnData = i;
break;
}
}
return _returnData;
}
]]>
</fx:Script>
<s:List width="100%" labelField="@label" dataProvider="{_foodCollection}"/>
<s:Button label="Sort me" click="_foodCollection.refresh()" />
</s:Application>