2015-09-18 41 views
1

我想創建一個佈局,可以使我的項目處於動畫狀態。因此,當我的列表中設置了數據提供者時,列表的佈局會將這些項目動畫到屏幕上。無法使自定義佈局中的動畫起作用

所以我創建了一個CustomLayout並添加了一個update()函數。

在updateDisplayList中,項目被很好地描繪出來。

但是在我想要做動畫的update()函數中,即使我追蹤layoutTarget的numElement,我也會得到四個項目,它們會作爲null追蹤出來!如果在我的Main應用程序中設置_dataProvider一秒或兩秒後使用setTimeout,然後在ListLayout中調用update(),則跡線工作正常。所以我的問題是,如何確保我調用update()以在實際可用時使項目動起來?

主要應用:

<?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" 
    xmlns:custom="*" 
    creationComplete="handleCreationComplete()"> 
    <fx:Declarations> 
     <!-- Place non-visual elements (e.g., services, value objects) here --> 
    </fx:Declarations> 

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

      [Bindable] 
      private var _dataProvider:ArrayCollection; 
      public function set dataProvider(value:ArrayCollection):void 
      { 
       _dataProvider = value; 
       listLayout.update(); 
      } 

      private function handleCreationComplete():void 
      { 
       var arr:Array = new Array({ label:"1" }, { label:"2" }, { label:"3" }, { label:"4" }); 
       dataProvider = new ArrayCollection(arr); 
      } 
     ]]> 
    </fx:Script> 

    <s:List id="list" 
     dataProvider="{ _dataProvider }" 
     labelField="label"> 
     <s:layout> 
      <custom:ListLayout id="listLayout" /> 
     </s:layout> 
    </s:List> 
</s:WindowedApplication> 

ListLayout:

package 
{ 
    import mx.core.ILayoutElement; 
    import spark.components.supportClasses.GroupBase; 
    import spark.layouts.supportClasses.LayoutBase; 

    /** 
    * ... 
    * @author 
    */ 
    public class ListLayout extends LayoutBase 
    { 
     public function update():void 
     { 
      var layoutTarget:GroupBase = target; 
      //layoutTarget.autoLayout = false; 

      var count:int = layoutTarget.numElements; 
      trace(count); //traces 4 

      for (var i:int = 0; i < count; i++) 
      { 
       var item:ILayoutElement = useVirtualLayout ? layoutTarget.getVirtualElementAt(i) : layoutTarget.getElementAt(i); 
       trace(item); //traces null 
      } 
     } 

     override public function updateDisplayList(width:Number, height:Number):void 
     { 
      super.updateDisplayList(width, height); 

      var layoutTarget:GroupBase = target; 

      var count:int = layoutTarget.numElements; 

      for (var i:int = 0; i < count; i++) 
      { 
       var item:ILayoutElement = useVirtualLayout ? layoutTarget.getVirtualElementAt(i) : layoutTarget.getElementAt(i); 
       trace(item); //traces out the item 
      } 
     } 
    } 
} 

回答

0

致電前listLayout更新,則需要驗證你 「列表」,以確保所有元素都可用。因此,添加一行list.validateNow()組數據提供程序功能如下:

public function set dataProvider(value:ArrayCollection):void 
{ 
    _dataProvider = value; 
    list.validateNow(); 
    listLayout.update(); 
} 
+0

啊!非常感謝!這讓我瘋狂! – kamcknig

+0

沒問題!很高興它解決了你的問題。 – gbdcool