views:

708

answers:

1

Consider the following code:

[Bindable(event="ReportHeaderVO_effectiveFromDateJulian_updated")]
public function set effectiveFromDateJulian ( value:Number ) : void
{
    _effectiveFromDateJulian = value;
    dispatchEvent( new FlexEvent("ReportHeaderVO_effectiveFromDateJulian_updated") );
}

public function get effectiveFromDateJulian () : Number
{
    return _effectiveFromDateJulian;
}

public function get effectiveFromDate () : Date
{
    return DateUtil.convertJDEJulianToDate(_effectiveFromDateJulian);
}

There is a setter and a getter for the effectiveFromDateJulian which is a number representation of the date. I have provided a seperate getter which retrieves the same value, only converted to a proper date. It is a getter only though and relies on the setter for the numeric property to get its data from; so the effectiveFromDate property is effectively read-only.

Data binding works on the effectiveFromDateJulian property; any updates work fine and notify everything properly. But when binding to the effectiveFromDate (getter only) property, I get a warning from the compiler:

warning: unable to bind to property 'effectiveToDate' on class 'com.vo::ReportHeaderVO'

Is there a way to make it possible to bind to this read-only property? I would assume I would have to dispatch an event on the setter that effects the read-only property, but I don't know what that would look like.

This is a simple example, you could imagine a read-only property that depends on several setters to function and when any of those setters are updated the read-only property would need to fire a propertyChanged event as well. Any ideas? Please let me know if I need to clarify anything.

Update: From the Adobe documentation here:

http://livedocs.adobe.com/flex/3/html/help.html?content=databinding_8.html

Using read-only properties as the source for data binding

You can automatically use a read-only property defined by a getter method, which means no setter method, as the source for a data-binding expression. Flex performs the data binding once when the application starts.

Because the data binding from a read-only property occurs only once at application start up, you omit the [Bindable] metadata tag for the read-only property.

And this makes sense for constant values, but in this case the value does change, it just doesn't get set directly.

+5  A: 

Make the readonly getter Bindable and dispatch the corresponding event from the original setter method.

[Bindable(event="ReportHeaderVO_effectiveFromDateJulian_updated")]
public function set effectiveFromDateJulian ( value:Number ) : void
{
    _effectiveFromDateJulian = value;
    dispatchEvent( new FlexEvent("ReportHeaderVO_effectiveFromDateJulian_updated") );
    dispatchEvent( new FlexEvent("ReportHeaderVO_effectiveFromDate_updated") );
}
[Bindable(event="ReportHeaderVO_effectiveFromDate_updated")]
public function get effectiveFromDate (date:Date) : Date
{
    return DateUtil.convertJDEJulianToDate(_effectiveFromDateJulian);
}
Amarghosh
This was perfect, exactly what I was looking for. After looking at it, it makes total sense about how and why it works, but it still isn't clear in the docs that this is how it should be. So when you put the [Bindable(event)] metadata, even though the docs show it being put on the setter, it is actually just being put on the property (the publicly exposed property). It could just as easily be put on the getter and it works the same. Just out of curiosity, do you have any link to the documentation or anywhere else that shows to do it like this?Thanks again! This helped a lot.
Ryan Guill
http://livedocs.adobe.com/flex/3/html/help.html?content=databinding_2.html#190306 says that "If you specify the event name, it is your responsibility to dispatch the event when the source property changes." I just tried it and it worked. Googling brought me to http://www.deitte.com/archives/2009/04/bindable_getter.htm and http://joshblog.net/2009/07/15/flex-readonly-bindable-getter-ignored-warning-explained/
Amarghosh
And yeah, it doesn't matter where you put the [Bindable] tag (getter or setter) it applies to the property. Although for the purposes of asdoc, its good to put it on the setter.
Amarghosh
Excellent. Thanks for those links. Your google-fu must be better than mine, I spent hours clicking on links trying to find an answer to this. Again, I really appreciate your help.
Ryan Guill