I have an ItemRenderer
with a data that has some flags. I need to change the ItemRenderer color depending on these flags. How can I achieve that? This is my IR:
<?xml version="1.0" encoding="utf-8"?>
<s:ItemRenderer xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
autoDrawBackground="false"
x="{data.x}" y="{data.y}">
<s:states>
<s:State name="node"/>
<s:State name="nodeIn"/>
<s:State name="nodeOut"/>
<s:State name="nodeTrafficLight"/>
<s:State name="nodeIntersection"/>
<s:State name="nodeBlocked"/>
</s:states>
<s:Ellipse width="16" height="16" x="-8" y="-8">
<s:stroke>
<s:SolidColorStroke weight="2"
color="#FFFF00"
color.nodeTrafficLight="#FF00FF"
color.nodeIntersection="#FF9900"
color.nodeBlocked="#000000"
color.nodeIn="#00FF00"
color.nodeOut="#FF0000"/>
</s:stroke>
<s:fill>
<s:SolidColor alpha=".5"
color="#FFFF00"
color.nodeTrafficLight="#FF00FF"
color.nodeIntersection="#FF9900"
color.nodeBlocked="#000000"
color.nodeIn="#00FF00"
color.nodeOut="#FF0000"/>
</s:fill>
</s:Ellipse>
<fx:Script>
<![CDATA[
override protected function getCurrentRendererState():String
{
if (data.isBlocked)
return "nodeBlocked";
if (data.isIn)
return "nodeIn";
if (data.isOut)
return "nodeOut";
if (data.isIntersection)
return "nodeIntersection";
return "node";
}
]]>
</fx:Script>
</s:ItemRenderer>
But I don't get these states updated when some of these flags (eg. data.isIn
) change. My model has [Bindable]
tag.
First off; I don't think the x and y values have an affect inside a renderer. The list class will handle the positioning of the renderer.
That said, you're renderer does not respond to the dataChange event; so the renderer will not update itself when the data changes. Add a dataChange event handler:
<s:ItemRenderer xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
autoDrawBackground="false"
dataChange="onDataChange(event)">
<fx:Script>
<![CDATA[
protected function onDataChange(event:Event):void{
invalidateRendererState();
}
]]>
</fx:Script>
The invalidateRendererState() method should force commitProperties() to re-run; which will in turn force getCurrentRendererState() to execute.
If for some reason the onDataChange() event is not firing when you change the data in your dataProvider; you'll have to use the itemUpdated() or refresh() function on your dataProvider to 'announce' that you changed data.