开发者

ArrayCollection wrapper allowing binding mechanism to see changes

I have an ArrayCollection containing bindable objects. I would like to access them in multiple places like below (there's only one label for clarity). How can I achieve that? Should I write some kind of wrapper for ArrayCollection dispatching special event (which?) catchable by Flex event mechanism.

<?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"
                 creationComplete="init()">


    <mx:VBox>
        <s:Label id="lb" text="{lab(col)}" />
        <s:Button click="onC(event)" color="0x000000"/>     
    </mx:VBox>

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

            import spark.events.ListEvent;

            [Bindable] private var col:ArrayCollection;

            private function init():void {
                col = new ArrayCollection();
                col.addItem({ val: 1 });
                col.addItem({ val: -1 });
            }

            private function onC(event:MouseEvent):void {
                col.getItemAt(0).val++;

                trace(col.getItemAt(0).val);
            }

            private function lab(_:ArrayCollection):String {
                for(var i:int = 0; i < col.length; i++) {
                    if(col.getItemAt(i).val > 0)
                        return col.getItemAt(i).val.toString();
                }

                return "-666";
            }

        ]]>
    </fx:Script>
</s:Application>

I would like to create wrapper like this:

        public class BindableArrayCollection extends EventDispatcher {

    [Bindable] private var _ac:ArrayCollection;

    public function BindableArrayCollection()   {
        this.ac = new ArrayCollection();
    }


    [Bindable]
    public function set ac(val:ArrayCollection):void {
        if(_ac != null)
            _ac.removeEventListener(CollectionEvent.COLLECTION_CHANGE, toggleChangeEvent);
开发者_如何学C
        _ac = val;

        if(_ac != null)
            _ac.addEventListener(CollectionEvent.COLLECTION_CHANGE, toggleChangeEvent);

        toggleChangeEvent(); 
    }

    public function get ac():ArrayCollection {
        return _ac;
    }

    public function toggleChangeEvent(_:Object = null):void {
        dispatchEvent(....);
    }
}

so that the binding mechanism would work. What should I place instead of "...."?


Your problem is that label is not showing value that is in your ArrayCollection, am I right? It's so, because Label does not have updating mechanism for ArrayCollection like DataGrid or List.
Your ArrayCollection is bindable, but this only means, that your lab(col) function will be executed only when you change your col variable value.
You set col = new ArrayCollection(); and at this moment binding is executed. And only after that you add values to your collection. There are 2 ways of solving this problem:

  1. Call lb.executeBindings() to update label view.
  2. Listen to CollectionEvent.COLLECTION_CHANGE that ArrayCollection dispatch, when it's items are changed.

Hope, this will help you.


Looks like you are starting out. The only thing I see here bindable is the ArrayCollection, not the objects in it. If you want to make a collection (or any data in general) to be accessible anywhere in your application, those client pieces of code need to know how to get to it. One possible approach would be to implement the Singleton Design Pattern - http://www.squidoo.com/flash-tutorials_as3-singleton-design-pattern That would be a good starting point to get your data to be more "global" like.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜