October 12, 2009
FlashBuilder 4 Beta 2 was released as part of MAX 2009 and with it a new set of features for data centric development (DCD). Sujit has a series of posts on DCD at http://sujitreddyg.wordpress.com.
One of the goals of DCD is to enable the developer to work with data in an object oriented way irrespective of the data format (XML, JSON, AMF) or the data exchange protocol (HTTPService, SOAP) with the back end.
The classes in Flex 4 sdk through which data could be got are HTTPService, HTTPMultiService, WebService and RemoteObject
HTTPMultiService is a new class that is added to the flex sdk and supports serialization of data through a property called serializationFilter – you can find more info here . This enables one to convert the HTTP response which could be XML or JSON to a ActionScript class. This is accomplished by the default XML and JSON serializers that are there as part of serializers.swc that comes as part of the FlashBuilder project when you use the Data Menu to define a service this swc gets added as part of your build path.
The serializers are
Also, one could plugin their own serializers or override the functions of the default serializers to add custom behaviors while decoding or encoding XML / JSON data in a flex project.
Note: One could still continue to use E4X as the means to access XML responses, but working with strong types and AS classes gives much more flexibility and results in more maintainable code.
WebService class has not changed much since Flex 3, where one can use the the schemaregistry to convert the result SOAP response to AS classes. Check the section “Customizing web service type mapping” in the link http://livedocs.adobe.com/flex/3/html/help.html?content=data_access_3.html. Though sometimes, the response itself will not be indicative enough of what is being returned (check this http://www.webservicex.net/uszip.asmx?wsdl) which tells the result is of type “any” and we cannot use the schemaregistry to register a class also for this so that the webservice class converts this to a appropriate AS class (check the bug https://bugs.adobe.com/jira/browse/SDK-22574 )
This has subsequently been resolved by providing a convertResultHandler property in WebService which could be set to a function which can there by convert the returned result to any AS class that the developer wants. The signature of convertResultHandler is
public static function convertResultHandler(result:*, operation:AbstractOperation):*
Notice that this could be used across operations and based on the operation one can convert the result which is sent as the parameter and to an AS class that could be referenced in the resultHandlers of those operations.
Most PHP, CF developers love their platform because of the flexibility it provides with respect to typing of objects and they have a choice to use strong types i.e. PHP classes or CFC components or just work without classes. FlashBuilder provides a unique way to work with weak types on the server and can convert them to strong types on the client without the developer having to do anything on the client side (ofcourse you might have to invoke a wizard and type in a name for the strong type, which is not hard, compared to writing your own client side data layer and doing all the conversions of data yourself )
Check the “Configuring return type” section in http://sujitreddyg.wordpress.com/2009/10/05/building-flex-applications-for-java-based-http-services-using-flash-builder-4/
This will set you up with a return type for your data returned from PHP or CF.
But you feel that you might need additional massaging of the data returned by the server or change the type of a particular property. You can customize again by using the convertResultHandler which is again used for converting a RemoteObject response to a strong type.
you can find this in the _super_* class file’s constructor generated by FlashBuilder in the following piece of code
_serviceControl.convertResultHandler = TypeUtility.convertResultHandler;
TypeUtility is a utility class defined in serializers.swc.
The message here is that
- FlashBuilder has a robust framework to work with weak data types in a object oriented way
- There is a good customization mechanism to override and extend the default conversion mechanisms
I wanted to post this small fix that I tried out for fixing the memory leak when changing itemRenderers for a flex chart.
The sample files for the bug mentioned in http://bugs.adobe.com/jira/browse/FLEXDMV-1882 are used to illustrate the fix.
The fix done was, to set the instance cache of the itemRenderer in ColumnSeries to be removed when not being used. Specifically the following needs to be done.
1. Goto this function in ColumnSeries.as which is part of your DMV source at src\mx\charts\series\ColumnSeries.as
override public function styleChanged(styleProp : String) : void
2. For the condition – else if(styleProp == “itemRenderer”)
Have the following code
_instanceCache.discard = true;
_instanceCache.remove = true;
_instanceCache.count = 0;
_instanceCache.remove = false;
_instanceCache.discard = false;
This should take care of removing unwanted instances when the itemRenderer gets changed.
I ran the sample without and with the changes for 1 minute by changing the itemRenderer every 5 seconds. Here is the result of that, i.e. the itemRenderers that needed to get updated at that given time. Notice the number of itemRenderers that existed after the change is far fewer than the one without the change.
itemRenderer2 : 47
itemRenderer1 : 59
itemRenderer2 : 391
itemRenderer1 : 451
This fix is only for ColumnSeries, if you want it for any other series make sure to make similar changes in that file as well.
Let me know if this fixes the memory leak on changing of item renderers as well as some of the real-time flex charting itemRenderer related memory leaks.
April 15, 2008
I was responding to one of the queries by Matt Horn, who is part of the Flex Documentation team on how to get the exact DataPoint for a series based on the mouse position which has one of its axis as a DateTimeAxis, thought let me share it here.
The usual code is
var d:Array = series1.localToData(p); // p is the point for which you want the data
if you notice d will be x-coord and d will be y-coord and if DateTimeAxis is representing the x-Axis then d will be some huge number, basically it is the number of milliseconds from midnight of Jan 1 1970, so just create a Date object with that to get the actual data point.
To get the same data point which actually gets displayed on the Chart, just use the following code.
var d:Array = series1.localToData(p);
var da:Date = new Date(d);
var str:String = daxis.formatForScreen(da); // daxis is the DataTimeAxis of the Chart.
formatForScreen is a public method which translates the date object to the one which is currently being displayed on the Chart based on the dataUnits that has been specified. Its a simple method, but nevertheless handy.
The day got started pretty early literally at around 3:30 AM IST (So any glitches / goof-ups that happened during the presentation, you know the reason), we were told about 700+ participants have registered for this session worldwide in the developer week organized by Adobe, that was an awesome response, Thank you.
I hope the presentation gave an overview of the data visualization capabilities available in Flex Builder Pro. Aparting from Charting, Advanced Data Grid and OLAP capabilities are part of this library. I have attached the presentation here and some samples that were shared during the presentation.
February 29, 2008
In Flex 3, we added multiple axes and renderers feature, where the developer could have any number of axes and they could place the horizontal axes either on bottom / top and the vertical axes on left / right. However there were some requests to place it in the middle of the chart.
One could easily customize the Charting API to achieve this, just override the function updateAxisLayout in a customized chart as shown and change the positions of the axisrenderers, you should get something like the screenshot below
override protected function updateAxisLayout(unscaledWidth:Number, unscaledHeight:Number):void
verticalAxisRenderer.move(verticalAxisRenderer.x – unscaledWidth / 2, verticalAxisRenderer.y);
horizontalAxisRenderer.move(horizontalAxisRenderer.x,horizontalAxisRenderer.y – unscaledHeight / 2);
You can notice that there is some amount of overlap between the labels of the verticalAxisRenderer and the horizontalAxisRenderer, you could circumvent this by using your own labelRenderer for the AxisRenderer, something like this.
override public function set data(value:Object):void
super.data = data;
l1.text = value.text;
<mx:Label paddingTop=”-25” id = “l1“/>
January 28, 2008
My neighbor at my workplace, Srini Annam has just released a very cool AIR app, this is an awesome application for users of orkut. It has used all the great features of AIR like native window, transparency, effects, system tray etc.
Just unable to get my hands off it.
Its available on his blog, http://srinivasannam.wordpress.com/2008/01/24/scrapmate
December 3, 2007
The default drag and drop behavior in Flex 3 Charts drags the itemRenderers used in the Series. However for LineSeries and AreaSeries there need not be an itemRenderer and drag will not happen when there are no itemRenderers.
This example will enable users to drag and drop Line Series Segments in a Line Chart. The idea here is
- Create a new dragproxy for the LineChart which renders the line segments
- In the dragproxy, create the line segments and set the bounds
- Creation of line segments is handled using the instancecache classes
Couple of caveats:
- To choose the series in the dragproxy I have used the series of the item that I get from selectedChartItem, this could be changed to your requirements.
- Also, the by default dragEvent will be dispatched, only when a drag happens on an itemRenderer, this could be overcome by generating the dragEvent in MyLineChart based on the position of the mouse
Here is the screenshot of the drag and drop in Action:
Here is the source:
Hopefully you can drag and drop LineSeries which provides a better effect than just dragging the itemRenderers, I think the same concept could be applied to Area Series as well.