手动调度集合更改事件

发布于 2024-10-21 22:22:32 字数 911 浏览 3 评论 0原文

我有一个标准组合框,当数据提供者完成初始化时调度集合事件:

my_cb.addEventListener( CollectionEvent.COLLECTION_CHANGE, getMyStuff );

然后我有一个自定义组件,它也有一个 dataProvider。当其数据提供者完成加载时,如何让它调度集合更改事件?

从我读到的来看,我做不到。调度 propertychange 事件有效吗?

感谢您提供任何有用的提示!

更新:

我有一个自定义组件,我称之为“SortingComboBox”,但它根本不是一个 ComboBox;它扩展了 Button,我将 dataProvider 属性设置为我的数组集合 model.product (这是一个数组集合)。

以下是我在该组件中使用 dataProvider 的方式:

code

[Bindable] 私有 var _dataProvider :对象;

    public function get dataProvider() : Object
    {
        return _dataProvider;
    }

    public function set dataProvider(value : Object) : void
    {
        _dataProvider = value;

    }

code

在此组件的 createChildren() 方法中,我使用:

BindingUtils.bindProperty(dropDown, "dataProvider", this, "dataProvider");

dropDown 是一个自定义 VBox,我用它来显示标签。

I have a standard combobox that dispatches a collection event when the dataprovider finishes initializing:

my_cb.addEventListener( CollectionEvent.COLLECTION_CHANGE, getMyStuff );

Then I have a custom component that also has a dataProvider. How do I get it to dispatch a collection change event when its dataprovider finishes loading?

From what I've read, I can't do it. Will dispatching a propertychangeevent work?

Thanks for any helpful tips!

UPDATE:

I have a custom component that I call 'SortingComboBox' but it is not a ComboBox at all; it extends Button and I set is dataProvider property to my arraycollection, model.product (which is an arraycollection).

And here is how I use the dataProvider in that component:

code

[Bindable]
private var _dataProvider : Object;

    public function get dataProvider() : Object
    {
        return _dataProvider;
    }

    public function set dataProvider(value : Object) : void
    {
        _dataProvider = value;

    }

code

In the createChildren() method of this component, I use this:

BindingUtils.bindProperty(dropDown, "dataProvider", this, "dataProvider");

The dropDown is a custom VBox that I use to display labels.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

花桑 2024-10-28 22:22:32

当您调用 setter 时,您必须确保

1) 您实际上正在使用 setter 更改值。因此,即使您在类内部,也请调用 this.dataProvider = foo 而不是 _dataProvider = foo

2) 除非您实际更改值,否则绑定不会触发。如果您跟踪,您会发现 setter 实际上调用了 getter,如果传递给 setter 和 getter 的值相同,则不会发生绑定。

您的另一个选择是在 getter 上放置一个事件,然后调用它来触发绑定。

[Bindable( "somethingChanged" )]
public function get dataProvider() : Object
{
    return _dataProvider;
}

dispatchEvent( new Event( "somethingChanged" ) );

When you call the setter, you have to make sure

1) that you actually are changing the value with the setter. So even if you are inside the class, call this.dataProvider = foo instead of _dataProvider = foo

2) The binding will not trigger unless you actually change the value. If you trace you'll see that the setter actually calls the getter, if the values of what you pass into the setter and the getter are the same, the binding will not occur.

Your other option is to put an event on the getter, then just call it to trigger the binding.

[Bindable( "somethingChanged" )]
public function get dataProvider() : Object
{
    return _dataProvider;
}

dispatchEvent( new Event( "somethingChanged" ) );
拥有 2024-10-28 22:22:32

使您的数据提供者可绑定

Make your dataprovider bindable

半葬歌 2024-10-28 22:22:32
[Bindable]
protected var _dataProvider:ArrayCollection ;

数据绑定是 ActionScript/Flex 所独有的。
除此之外,它还会调度更改事件。
也许如果您发布自定义组件的代码,我可以更具体。

实际上你能解释一下你想要实现的目标是什么吗?
我只能告诉你你正试图让一个按钮有一个下拉菜单。
为什么?

[Bindable]
protected var _dataProvider:ArrayCollection ;

Data binding is something unique to ActionScript/Flex.
Among other things it will dispatch change events.
Maybe if you post your code for the custom component I can be more specific.

Actually can you explain what your goal is you are trying to achieve?
All I can tell is you are trying to make a button have a drop down.
Why?

不美如何 2024-10-28 22:22:32

这是自定义组件,只是为了给您一个更好的想法。

代码
包 com.fidelity.primeservices.act.components.sortingcombobox
{
导入 com.fidelity.primeservices.act.events.component.ResetSortEvent;
导入 com.fidelity.primeservices.act.events.component.SortEvent;

import flash.events.Event;
import flash.events.MouseEvent;
import flash.geom.Point;
import flash.geom.Rectangle;

import mx.binding.utils.BindingUtils;
import mx.controls.Button;
import mx.core.UIComponent;
import mx.effects.Tween;
import mx.events.FlexMouseEvent;
import mx.managers.PopUpManager;
import mx.events.PropertyChangeEvent;
import mx.events.PropertyChangeEventKind;

public class SortingComboBox extends Button
{
    private const MAX_LABEL_LENGTH : int = 400; 
    private const ELIPSES : String = "...";

    [Bindable]
    private var _dataProvider : Object;
    private var dropDown : SortingDropDown;
    private var inTween : Boolean;
    private var showingDropdown : Boolean;
    private var openCloseTween : Tween;

    public var noSelectionLabel : String = "No Filter";
    public var noSelectionData : String = "ALL"; 

    public function get dataProvider() : Object
    {
        return _dataProvider;
    }

    public function set dataProvider(value : Object) : void
    {
        _dataProvider = value;
    }

    private function collectionEvent(e : Event):void
    {
        trace(new Date(), e);   
    }


    public function SortingComboBox()
    {
        super();
        this.buttonMode = true;
        this.useHandCursor = true;

        inTween = false;
        showingDropdown = false;

        addEventListener(Event.REMOVED_FROM_STAGE, removedFromStage);
    }   

    override protected function createChildren() : void
    {
        super.createChildren();

        dropDown = new SortingDropDown();
        dropDown.width = 240;
        dropDown.maxHeight = 300;
        dropDown.visible = false;
        BindingUtils.bindProperty(dropDown, "dataProvider", this, "dataProvider");
        dropDown.styleName = "sortingDropDown";

        dropDown.addEventListener(SortEvent.CLOSE_SORT, closeDropDown);
        dropDown.addEventListener(FlexMouseEvent.MOUSE_DOWN_OUTSIDE, dropdownCheckForClose);
        dropDown.addEventListener(FlexMouseEvent.MOUSE_WHEEL_OUTSIDE, dropdownCheckForClose);

        dropDown.addEventListener(SortEvent.UPDATE_SORT, onSortUpdate); //this event bubbles
        dropDown.addEventListener(ResetSortEvent.RESET_SORT_EVENT, onSortUpdate);

        PopUpManager.addPopUp(dropDown, this);

        this.addEventListener(MouseEvent.CLICK, toggleDropDown);

        // weak reference to stage
        systemManager.addEventListener(Event.RESIZE, stageResizeHandler, false, 0, true);
    }


    private function stageResizeHandler(evt : Event) : void
    {
        showingDropdown = false;
        dropDown.visible = showingDropdown;
    }

    private function toggleDropDown(evt : MouseEvent) : void
    {
        if(!dropDown.visible)
        {
            openDropDown(evt);
        }
        else
        {
            closeDropDown(evt);
        }               
    }

    private function openDropDown(evt : MouseEvent) : void
    {
        if (dropDown.parent == null)  // was popped up then closed
        {
            PopUpManager.addPopUp(dropDown, this);
        }
        else
        {
            PopUpManager.bringToFront(dropDown);
        }

        showingDropdown = true;
        dropDown.visible = showingDropdown;
        dropDown.enabled = false;

        var point:Point = new Point(0, unscaledHeight);
        point = localToGlobal(point);
        point = dropDown.parent.globalToLocal(point);

        //if the dropdown is larger than the button and its
        //width would push it offscreen, align it to the left.
        if (dropDown.width > unscaledWidth && point.x + dropDown.width > screen.width)
        {
            point.x -= dropDown.width - unscaledWidth;
        }

        dropDown.move(point.x, point.y);            

        //run opening tween
        inTween = true;

        // Block all layout, responses from web service, and other background
        // processing until the tween finishes executing.
        UIComponent.suspendBackgroundProcessing();

        dropDown.scrollRect = new Rectangle(0, dropDown.height, dropDown.width, dropDown.height);
        openCloseTween = new Tween(this, dropDown.height, 0, 250);
    }

    private function closeDropDown(evt : Event) : void
    {
        //dropDown.visible = false;             
        showingDropdown = false;

        //run closing tween
        inTween = true;

        // Block all layout, responses from web service, and other background
        // processing until the tween finishes executing.
        UIComponent.suspendBackgroundProcessing();

        openCloseTween = new Tween(this, 0, dropDown.height, 250);
    }

    private function dropdownCheckForClose(event : MouseEvent) : void
    {
        if (event.target != dropDown)
            // the dropdown's items can dispatch a mouseDownOutside
            // event which then bubbles up to us
            return;

        if (!hitTestPoint(event.stageX, event.stageY, true))
        {
            closeDropDown(event);
        }
    }

    public function refresh():void
    {
        onSortUpdate(null);   
    }

    private function onSortUpdate(evt1 : Event) : void
    {
        //update the label          
        var dpLength : int = this.dataProvider.length;  

        var nextLabel : String = "";
        var nextData : String = "";

        for (var i : int = 0; i < dpLength; i++)
        {
            if (this.dataProvider[i].selected == true)
            {
                nextLabel += this.dataProvider[i].label + ", ";                     
                if (this.dataProvider[i].data != null)
                {
                    nextData += this.dataProvider[i].data + ", ";
                }
            }
        }

        if (nextLabel.length > 0)
        {
            // remove extra comma at end
            nextLabel = nextLabel.substr(0, nextLabel.length - 2);
        }

        if (nextData.length > 0)
        {
            nextData = nextData.substr(0, nextData.length - 2);
        }

        if (nextLabel.length > MAX_LABEL_LENGTH)
        {
            // limit label to MAX_LABEL_LENGTH  + ... REASON: tooltips with lots of characters take a long time to render
            nextLabel = nextLabel.substr(0, MAX_LABEL_LENGTH) + ELIPSES;                    
        }

        if (nextLabel.length == 0)
        {
            nextLabel = noSelectionLabel;
            //nextLabel = "No Filter";
        }

        if (nextData.length == 0)
        {
            nextData = noSelectionData;
            //nextData = "ALL";
        }

        label = nextLabel;
        data = nextData;
        toolTip = label;

        if (evt1 is SortEvent)
        {
            trace("sort event");
            var temp:Object = this.dataProvider;
            this.dataProvider = null;
            this.dataProvider = temp;
            this.refresh();
        }
        else
        {
            trace("not dispatching");
        }
    }


    public function onTweenUpdate(value:Number):void
    {
        dropDown.scrollRect = new Rectangle(0, value, dropDown.width, dropDown.height);
    }

    public function onTweenEnd(value:Number) : void
    {     
        // Clear the scrollRect here. This way if drop shadows are
        // assigned to the dropdown they show up correctly
        dropDown.scrollRect = null;

        inTween = false;
        dropDown.enabled = true;
        dropDown.visible = showingDropdown;

        UIComponent.resumeBackgroundProcessing();
    }

    private function removedFromStage(event:Event):void
    {
        if(inTween)
        {
            openCloseTween.endTween();
        }

        // Ensure we've unregistered ourselves from PopupManager, else
        // we'll be leaked.
        PopUpManager.removePopUp(dropDown);
    }
}

}

this is the custom component just to give you a better idea.

code
package com.fidelity.primeservices.act.components.sortingcombobox
{
import com.fidelity.primeservices.act.events.component.ResetSortEvent;
import com.fidelity.primeservices.act.events.component.SortEvent;

import flash.events.Event;
import flash.events.MouseEvent;
import flash.geom.Point;
import flash.geom.Rectangle;

import mx.binding.utils.BindingUtils;
import mx.controls.Button;
import mx.core.UIComponent;
import mx.effects.Tween;
import mx.events.FlexMouseEvent;
import mx.managers.PopUpManager;
import mx.events.PropertyChangeEvent;
import mx.events.PropertyChangeEventKind;

public class SortingComboBox extends Button
{
    private const MAX_LABEL_LENGTH : int = 400; 
    private const ELIPSES : String = "...";

    [Bindable]
    private var _dataProvider : Object;
    private var dropDown : SortingDropDown;
    private var inTween : Boolean;
    private var showingDropdown : Boolean;
    private var openCloseTween : Tween;

    public var noSelectionLabel : String = "No Filter";
    public var noSelectionData : String = "ALL"; 

    public function get dataProvider() : Object
    {
        return _dataProvider;
    }

    public function set dataProvider(value : Object) : void
    {
        _dataProvider = value;
    }

    private function collectionEvent(e : Event):void
    {
        trace(new Date(), e);   
    }


    public function SortingComboBox()
    {
        super();
        this.buttonMode = true;
        this.useHandCursor = true;

        inTween = false;
        showingDropdown = false;

        addEventListener(Event.REMOVED_FROM_STAGE, removedFromStage);
    }   

    override protected function createChildren() : void
    {
        super.createChildren();

        dropDown = new SortingDropDown();
        dropDown.width = 240;
        dropDown.maxHeight = 300;
        dropDown.visible = false;
        BindingUtils.bindProperty(dropDown, "dataProvider", this, "dataProvider");
        dropDown.styleName = "sortingDropDown";

        dropDown.addEventListener(SortEvent.CLOSE_SORT, closeDropDown);
        dropDown.addEventListener(FlexMouseEvent.MOUSE_DOWN_OUTSIDE, dropdownCheckForClose);
        dropDown.addEventListener(FlexMouseEvent.MOUSE_WHEEL_OUTSIDE, dropdownCheckForClose);

        dropDown.addEventListener(SortEvent.UPDATE_SORT, onSortUpdate); //this event bubbles
        dropDown.addEventListener(ResetSortEvent.RESET_SORT_EVENT, onSortUpdate);

        PopUpManager.addPopUp(dropDown, this);

        this.addEventListener(MouseEvent.CLICK, toggleDropDown);

        // weak reference to stage
        systemManager.addEventListener(Event.RESIZE, stageResizeHandler, false, 0, true);
    }


    private function stageResizeHandler(evt : Event) : void
    {
        showingDropdown = false;
        dropDown.visible = showingDropdown;
    }

    private function toggleDropDown(evt : MouseEvent) : void
    {
        if(!dropDown.visible)
        {
            openDropDown(evt);
        }
        else
        {
            closeDropDown(evt);
        }               
    }

    private function openDropDown(evt : MouseEvent) : void
    {
        if (dropDown.parent == null)  // was popped up then closed
        {
            PopUpManager.addPopUp(dropDown, this);
        }
        else
        {
            PopUpManager.bringToFront(dropDown);
        }

        showingDropdown = true;
        dropDown.visible = showingDropdown;
        dropDown.enabled = false;

        var point:Point = new Point(0, unscaledHeight);
        point = localToGlobal(point);
        point = dropDown.parent.globalToLocal(point);

        //if the dropdown is larger than the button and its
        //width would push it offscreen, align it to the left.
        if (dropDown.width > unscaledWidth && point.x + dropDown.width > screen.width)
        {
            point.x -= dropDown.width - unscaledWidth;
        }

        dropDown.move(point.x, point.y);            

        //run opening tween
        inTween = true;

        // Block all layout, responses from web service, and other background
        // processing until the tween finishes executing.
        UIComponent.suspendBackgroundProcessing();

        dropDown.scrollRect = new Rectangle(0, dropDown.height, dropDown.width, dropDown.height);
        openCloseTween = new Tween(this, dropDown.height, 0, 250);
    }

    private function closeDropDown(evt : Event) : void
    {
        //dropDown.visible = false;             
        showingDropdown = false;

        //run closing tween
        inTween = true;

        // Block all layout, responses from web service, and other background
        // processing until the tween finishes executing.
        UIComponent.suspendBackgroundProcessing();

        openCloseTween = new Tween(this, 0, dropDown.height, 250);
    }

    private function dropdownCheckForClose(event : MouseEvent) : void
    {
        if (event.target != dropDown)
            // the dropdown's items can dispatch a mouseDownOutside
            // event which then bubbles up to us
            return;

        if (!hitTestPoint(event.stageX, event.stageY, true))
        {
            closeDropDown(event);
        }
    }

    public function refresh():void
    {
        onSortUpdate(null);   
    }

    private function onSortUpdate(evt1 : Event) : void
    {
        //update the label          
        var dpLength : int = this.dataProvider.length;  

        var nextLabel : String = "";
        var nextData : String = "";

        for (var i : int = 0; i < dpLength; i++)
        {
            if (this.dataProvider[i].selected == true)
            {
                nextLabel += this.dataProvider[i].label + ", ";                     
                if (this.dataProvider[i].data != null)
                {
                    nextData += this.dataProvider[i].data + ", ";
                }
            }
        }

        if (nextLabel.length > 0)
        {
            // remove extra comma at end
            nextLabel = nextLabel.substr(0, nextLabel.length - 2);
        }

        if (nextData.length > 0)
        {
            nextData = nextData.substr(0, nextData.length - 2);
        }

        if (nextLabel.length > MAX_LABEL_LENGTH)
        {
            // limit label to MAX_LABEL_LENGTH  + ... REASON: tooltips with lots of characters take a long time to render
            nextLabel = nextLabel.substr(0, MAX_LABEL_LENGTH) + ELIPSES;                    
        }

        if (nextLabel.length == 0)
        {
            nextLabel = noSelectionLabel;
            //nextLabel = "No Filter";
        }

        if (nextData.length == 0)
        {
            nextData = noSelectionData;
            //nextData = "ALL";
        }

        label = nextLabel;
        data = nextData;
        toolTip = label;

        if (evt1 is SortEvent)
        {
            trace("sort event");
            var temp:Object = this.dataProvider;
            this.dataProvider = null;
            this.dataProvider = temp;
            this.refresh();
        }
        else
        {
            trace("not dispatching");
        }
    }


    public function onTweenUpdate(value:Number):void
    {
        dropDown.scrollRect = new Rectangle(0, value, dropDown.width, dropDown.height);
    }

    public function onTweenEnd(value:Number) : void
    {     
        // Clear the scrollRect here. This way if drop shadows are
        // assigned to the dropdown they show up correctly
        dropDown.scrollRect = null;

        inTween = false;
        dropDown.enabled = true;
        dropDown.visible = showingDropdown;

        UIComponent.resumeBackgroundProcessing();
    }

    private function removedFromStage(event:Event):void
    {
        if(inTween)
        {
            openCloseTween.endTween();
        }

        // Ensure we've unregistered ourselves from PopupManager, else
        // we'll be leaked.
        PopUpManager.removePopUp(dropDown);
    }
}

}

单调的奢华 2024-10-28 22:22:32

好吧,这里的代码

[Bindable]
private var _dataProvider : Object;

public function get dataProvider() : Object
{
   return _dataProvider;
}
public function set dataProvider(value : Object) : void
{
  _dataProvider = value;
}

没有什么不同,

[Bindable]
public var _dataProvider : Object;

因为对象是通过引用传递的,所以你无论如何都不会保护它,并且 setter 和 getter 是没有意义的。

另一方面,您使源 _dataProvider 可绑定,因此只要数据发生更改,它就会调度 CollectionEvent.COLLECTION_CHANGE

Ok this code here

[Bindable]
private var _dataProvider : Object;

public function get dataProvider() : Object
{
   return _dataProvider;
}
public function set dataProvider(value : Object) : void
{
  _dataProvider = value;
}

is no different then

[Bindable]
public var _dataProvider : Object;

Since objects are passed by reference you are not protecting it in anyway and the setter and getter are pointless.

On the other hand you made the source _dataProvider Bindable so anytime the data changes it will dispatch a CollectionEvent.COLLECTION_CHANGE

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文