Go Beyond Flex, Part 1 – How to make your code smaller and faster

Flex is often taken for granted when implementing flash/AS3  projects. However it is not mandatory to use Flex on the flash platform. Not only that, its not always the preferred solution for most RIAs.

In this post, I will cover a few alternatives to Flex while staying in the realm of Actionscript and Flash. Yes, this may sound strange from someone who makes his living using Flex, but there are situations when Flex can become a liability.

The Right Tool?

A basic rule of thumb is: use the right tool for the job: Different projects have different requirements, so does it make sense to use the exact same tool for all of them?

Some projects require heavy back-end data support or lots of UI, while others need to be light and fast and require very minimal UI. Enterprise projects are completely different from, say, casual games or advertising projects on so many levels, and it’s not a good idea to build them in the same way.

The Flex framework was designed and written by Adobe (and later became an open source project) as a layer on top of the flash API. While it did prove to be powerful and easy to use, Flex is far from perfect. It was touted as the one solution to fits all problems, and typical to projects developed by large corporations, the objective was to cram as many features as possible, and it quickly grew in size and complexity – code size and efficiency fell victim and pushed to lower priority.

The fact is that most projects don’t use 100% of these features, and a good part of them use maybe 20% of them. The underlying overhead is significant. Sure the framework is modular, and the compiler will not include components that are not accessed, but because of so many dependencies in the flex core components the resulting swf file would be significantly larger.

The Flash community has developed a love-hate relationship with Flex, and Adobe did address some of the problems over time. However, even with the recent release of Flex 4 the fact remains that the framework is large, heavy and not very efficient. The good thing about Flex, is that being an open source project, we are able to look under the hood and see exactly what code is being used.

So How big is it anyway?

A sample project with a couple of labels and buttons can serve as a basic test case. Create two projects, one as Flex project and the other as pure actionscript project.

Use either MXML or actionscript to place these labels and buttons – in the flex project it would use the Application, Label and Button components while in the AS3 project it would use TextField and SimpleButton.

Set the linkage in the build properties to ‘merge into code’ to create a single swf. Now and build the projects and compare the resulting SWF files.

Test Results:
Flex project swf: 600-780K debug and 250-330K release
Plane AS3 project swf: 12-15K debug and 8-9K release

600K versus 12K – that is almost 50 times ratio!

Big deal, you might say, why should we even care about file sizes and memory footprint when we have gigs of memory and bandwidth to spare?

Well, if you want your flash app/game to run properly on platforms like netbooks, smartphones and mobile touch devices you already know the answer: smaller and faster is always better. Even on desktops, loading time might become a factor for some projects.

To understand this issue further, a few words on the Flex SDK architecture.

At the core of the SDK lies the forefather of Flex: UIComponent – the base class for all visual components. Developers sometimes refer to it as the ‘God Component’ – an all powerful, massive entity that contains all the functionality needed in interactive and non interactive components (lifecycle events, mouse interactions, effects, tool-tips etc.). To iterate, classes like button and label are based on UIComponent.

The class hierarchy for a simple button (spark) is:
Button -> ButtonBase -> SkinnableComponent -> UIComponent.
To get a rough estimate for the size in memory of a button, simply add up all of the classes up the hierarchy. Actual results may vary depending on how optimized the compiler and player are.

Now lets take a look at a few popular controls in the Flex SDK code and try to get an idea of how big they are.

AS3 File size Lines of code
Spark Label 60K 1560
Spark Button 7K 216
Spark Group 69K 2000
UIComponent 427K 12,000
DataGrid 201K 5750
ButtonBase 33K 1140

Wow, 1560 lines of code for a simple label? that’s not exactly compact and efficient. Also 2000 lines for a group, the container used to layout child components, looks a bit bloated.

Well, you get the point. Since all Flex visual components are derived from the jumbo size UIComponent, we start with a few hundred KBs no matter how basic our project is. And we didn’t even cover actual memory footprint for these components.

To conclude, with thousands of lines of code that make up most flex components, its no wonder we end up with SWF files that are over a Meg, and sometimes a few megabytes before adding any assets.

The Code behind

Another aspect of Flex is the usage of MXML for layouts to simplify code. Other than simple layout it offer other features, like states, data binding and styles. MXML is actually only a markup that is pre-complied into Actionscript code. The generated code is added to the ‘plain’ code and then complied into a swf.

You can look at the code generated from the MXML by setting the ‘-keep’ compiler option as described here.
The generated source code will appear in a ‘generated’ folder under the project’s /bin-debug (in Flex Builder). You’ll see that it contains dozens of files, related to styles, properties and whatever you included in the layout.
Excessive usage of states and data binding will generate massive code that (like any automatically generated code) is not optimized. To demonstrate,  here is the code genrated for binding a variable.
[Bindable]
public var myData:String;

Will generate somthing like this:

public function set myData(value:String):void
{
   var oldValue:Object = this._1167269232myData;
   if (oldValue !== value) {
      this._1167269232myData= value;
      if (this.hasEventListener("propertyChange"))
         this.dispatchEvent(mx.events.PropertyChangeEvent.createUpdateEvent
         (this, "myData", oldValue, value));
      }
}

And MXML state code like the following

<s:states>
    <s:State name="normal"/>
    <s:State name="before"/>
    <s:State name="after"/>
</s:states>
 
<s:Label text="aaa" color.before="#cccccc" color.after="#888888"/>
<s:Group includeIn="after">
    <s:Label text="bbb"/>
</s:Group>
<s:Group visible.before="false">
    <s:Label text="www"/>
</s:Group>

Generates:

var _TestApp_Group1_factory:DeferredInstanceFromFunction =
 new mx.core.DeferredInstanceFromFunction(_TestApp_Group1_i);
 
 
states = [
 new State ({
   name: "normal",
   overrides: [
   ]
 })
 ,
 new State ({
   name: "before",
   overrides: [
     new mx.states.SetStyle().initializeFromObject({
       target: "_TestApp_Label1",
       name: "color",
       value: 13421772
     })
     ,
     new mx.states.SetProperty().initializeFromObject({
       target: "_TestApp_Group2",
       name: "visible",
       value: false
     })
   ]
 })
 ,
 new State ({
   name: "after",
...

All that code only to switch a couple of properties when a state changes. A similar result could be achieved in only a few lines of hand written code.

Every Byte Counts

As we have seen, the code for the seemingly simple application could easily gain weight.  Large code not only makes a larger swf file, it also uses more memory at runtime. A large memory footprint can translate directly into a slow and sluggish performance, as the OS is frequently required to allocate more memory, triggering cache faults and page faults that dramatically slow down the running process.

This is specially significant in low memory environments like netbooks and mobile devices. Small memory footprint is a must for lightweight applications and it benefits all platforms, as the application will run well anywhere. It should be high on the priority list when your application is required to be smooth and snappy.

So we want to start a project that will use some simple UI elements and layouts. We might want to be able to use mxml and data binding as well. In the list of requirements we also have a light and fast user experience. For the type of projects that requires very simple UI, like interactive ads or games we would need a minimal set of components, and in most cases we want to heavily customize their visual appearance.

But for this minimal set, we would drag the entire Flex framework with all its overhead with it. Does it really have to be that way?

What are the options out there?
Part 2 will lay out some of the available lightweight alternatives, their pros and cons and how to incorporate them into your projects.

One thought on “Go Beyond Flex, Part 1 – How to make your code smaller and faster

  1. A 12k swf does not imply it’s going to have a better end user experience than a 600k swf. One cannot argue that a Flex based game or app is large but if you actually go through UI Component, it offers an incredible amount of utility that ActionScripter can invoke explicitly or implicitly for convenience. Flex, if used properly, lends itself to rapid feature development and find scales better in a team environment that a large AS3-only project. Because the tools and the framework lends itself to rapidly create and rapidly apply skinning to often used controls, we sacrifice file size to spend more time on selecting the right user experience paths and polishing those paths. AS3-only projects have strengths in small file size outputs but I think the granularity can been seen as a disadvantage when time to market and maintainability is critical.

Comments are closed.