繁体   English   中英

尝试在Flash AS3.0中使用BindingUtils

[英]Trying to use BindingUtils in Flash AS3.0

我无法在包含Flex SDK 4.0的AS3.0(Flash)中使此代码正常工作。

 import mx.binding.utils.*;


 [Bindable]
 var myValue:int = 0;
 var cw:ChangeWatcher = BindingUtils.bindSetter(myValueChanged, this, "myValue");
 addEventListener( Event.ENTER_FRAME , ef);

 function ef(e:Event):void
 {
    trace("hello",getTimer());
    myValue = getTimer();
 }

 function myValueChanged(o:Object):void
 {
    trace("myValue: " + myValue.toString());
 }

我得到的输出是:

myValue: 0
hello 157
hello 168
hello 171
hello 177
....
....

等等。

但我希望正确的输出应该是:

myValue: 0
hello 157
myValue: 157
hello 168
myValue: 168
hello 171
myValue: 171
hello 177
myValue: 177
....
....

谢谢。

数据绑定仅适用于Flex。

<?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" enterFrame="ef(event)">

    <fx:Declarations>
        <!-- Place non-visual elements (e.g., services, value objects) here -->
    </fx:Declarations>
    <fx:Script>
        <![CDATA[
            import mx.binding.utils.*;

            [Bindable]
            public var myValue:int = 0;
            private var cw:ChangeWatcher = BindingUtils.bindSetter(myValueChanged, this, "myValue");

            private function ef(e:Event):void
            {
                trace("hello", getTimer());
                myValue = getTimer();
            }

            private function myValueChanged(o:Object):void
            {
                trace("myValue: " + myValue.toString());
            }
        ]]>
    </fx:Script>
</s:WindowedApplication>

我不确定Flash Pro编译器如何处理这些东西(我始终使用Flex SDK中的免费mxmlc编译器)。

这对您有用吗?

package
{
  import flash.display.Sprite;
  import flash.events.Event;
  import flash.utils.getTimer;
  import mx.binding.utils.BindingUtils;

  public class BindingExample extends Sprite {

    private var model:Model;

    public function BindingExample()
    {
      model = new Model();
      BindingUtils.bindProperty(this, 'spy', model, ['value']);
      addEventListener( Event.ENTER_FRAME , onEnterFrame);
    }

    public function onEnterFrame(e:Event):void
    {
      model.value = getTimer();
    }

    public function set spy(value:int):void
    {
      trace('Bound property set to: ' + value);
    }
  }
}

class Model
{
  [Bindable]
  public var value:int;
}

如果没有,请尝试使用以下模型定义:

import flash.events.Event;
import flash.events.EventDispatcher;

class Model extends EventDispatcher
{
  private var _value:int;

  [Bindable("valueChange")]
  public function get value():int
  {
    return _value;
  }

  public function set value(value:int):void
  {
    if (_value != value)
    {
      trace('Model property set to: ' + value);
      _value = value;
      dispatchEvent(new Event("valueChange"));
    }
  }
}

如果这不起作用,请对模型尝试以下操作:

import flash.events.EventDispatcher;
import mx.events.PropertyChangeEvent;
import mx.events.PropertyChangeEventKind;

class Model extends EventDispatcher
{
  private var _value:int;

  [Bindable("propertyChange")]
  public function get value():int
  {
    return _value;
  }

  public function set value(value:int):void
  {
    if (_value != value)
    {
      trace('Model property set to: ' + value);
      var oldValue:int = _value;
      _value = value;
      dispatchEvent(new PropertyChangeEvent(
        PropertyChangeEvent.PROPERTY_CHANGE, false, false,
        PropertyChangeEventKind.UPDATE, "value", oldValue, value, this));
    }
  }
}

或者,也许使用ObjectProxy:

package
{
  import flash.display.Sprite;
  import flash.events.Event;
  import flash.utils.getTimer;
  import mx.binding.utils.BindingUtils;
  import mx.utils.ObjectProxy;

  public class BindingExample extends Sprite {

    private var model:ObjectProxy;

    public function BindingExample()
    {
      model = new ObjectProxy({value: 0});
      BindingUtils.bindProperty(this, 'spy', model, ['value']);
      addEventListener( Event.ENTER_FRAME , onEnterFrame);
    }

    public function onEnterFrame(e:Event):void
    {
      model.value = getTimer();
    }

    public function set spy(value:int):void
    {
      trace('Bound property set to: ' + value);
    }
  }
}

使用mxmlc进行编译时,上述所有方法均能正常工作。 我避免使用ObjectProxy,因为它的类型安全性最低。

你写了:

我无法在包含Flex SDK 4.0的AS3.0(Flash)中使此代码正常工作。

我认为这意味着您已经在使用mxmlc编译器,这对于Bindable metatag起作用是必需的。

据我了解,将Bindable meta标签添加到变量是侦听PropertyChangeEvent调度的一种方式:

Flex 4.6 API文档说明:

[在变量上使用Bindable时] Flex编译器会自动为该属性生成一个名为propertyChange的事件,该事件的类型为PropertyChangeEvent。

基本上是一种更简单的方法来执行myValue.addEventListener(...)

因此,我们希望可绑定的变量必须是扩展EventDispatcher或实现IEventDispatcher的类型。 原始int并非如此,它是您要使其可绑定的变量的类型。 intBindable将不起作用。

为了使其工作,您可以将int变量包装在实现IEventDispatcher的自定义类BindableInteger中。 另一个选择是使用ObjectProxy ,即使您不扩展EventDispatcher或实现IEventDispatcher ,它也允许您添加EventListeners并使对象可绑定。

另外,请注意,您需要将变量设为公共,受保护或私有,以使Bindable起作用。

有关使用Bindable meta标签的 Flex 4.6文档:

在将公共,受保护或私有属性定义为变量之前,可以使用[Bindable]元数据标签(...)[b]使该特定属性支持绑定。

这将不起作用:

[Bindable] var myValue:int = 0;

但这将:

[Bindable] public var myValue:int = o;

绑定适用于类属性,并且不适用于局部变量,因此您需要创建类:

package
{
import flash.display.Sprite;
import flash.events.Event;
import flash.utils.getTimer;

import mx.binding.utils.BindingUtils;
import mx.binding.utils.ChangeWatcher;

public class astest extends Sprite
{

    [Bindable]
    public var myValue:int = 0;

    public function astest()
    {
        var cw:ChangeWatcher = BindingUtils.bindSetter(myValueChanged, this, "myValue");
        addEventListener( Event.ENTER_FRAME , ef);
    }

    protected function ef(e:Event):void
    {
        trace("hello",getTimer());
        myValue = getTimer();
    }

    protected function myValueChanged(o:Object):void
    {
        trace("myValue: " + myValue.toString());
    }
}
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM