Optimizing Flash performance

As Flash designers and developers get a hold of even more advanced tools and scripting languages, the need for performance considerations within flash projects become ever so apparent. Lately I've seen people complaining about flash apps that bug down their CPU and memory when visiting sites containing flash media. I see this problem as two parallel problems.

1. Sites relying on advertisement (often flash banners) try to cram a gazillion banners and ads into every nook and cranny available on their site. This is simply greed, a condition for which I can offer no cure.

2. The Flash editor has been an animation tool for quite some time. As a result, things common to other development platforms, like performance optimization, has not been and still isn't a priority in most Flash projects. However, this has started to change, something I will try to contribute into trough this post. So, let's get it on...

General optimization
  • WMODE. First of all, if you don't have an amazingly good reason for using it, do not use wmode! In short, wmode is used to make the background of the swf file become transparent. Wmode will render the swf unreadable to screen readers, force the swf to run when on a hidden tab and make the content of your swf to render much more slowly than in normal mode. Read more about this (Tinic Uro).
  • Vectors and bitmaps. If you are animating a complex static vector, that is a vector that does not change it's content, e.g. a rectangle, then use the «cacheAsBitmap» property or simply use a bitmap instead. Let's say you are tweening a vector shape across the stage. The Flash-Player(FP) will have to recalculate all the vectors in the shape for every frame. For complex shapes, this will take up a lot of CPU cycles. With «cacheAsBitmap» turned on, the FP will calculate the vectors once, create a bitmap and re-render the bitmap instead. But do note this!! For vector shapes that are changing, not static, like lines that are constantly moving inside of a movieclip, if so..do not use «cacheAsBitmap». The reason for this is that FP now have to re-render both the changed vector shape AND create a new bitmap for every frame. So «cacheAsBitmap» is only good for static vector shapes.
  • MovieClips. Not every shape needs to be a movieclip. If you need frames, you do need a movieclip, but if not, use a sprite(in ActionScript) or a Shape in the editor. Shapes does not have mouse and keyboard events and leave a much smaller memory imprint than MovieClips.
  • Alpha. Crop your artwork instead of using big ass areas of alpha channel. The FP do render the alpha channel areas even if you cannot see them.
  • Alpha video. A flv video encoded with an alpha channel using the On2Vp6 codec is about 4 times more complex to decode than one without the alpha channel. FP do not support alpha using H.264. Read more.

ActionScript optimization
This section is on ActionScript 3 only and can get somewhat technical.
  • Strong typing. By typing your variables and functions the performance gain is substantial, in general 10 times faster. In AS3 the byte-code produced by the compiler actually changes based on typing. Also, strong typing makes it much easier to debug your app as the compiler will give more accurate debugger results. More on this.
  • Numbers. Even though strong typing is quite easy to do, it's not always clear as to what type is the most efficient one. For numbers the «int» type is the speediest of the bunch, however «Number» does not lag far behind. However, it's smart to use «int» for iterations and situations where you are working on integers only as this will make debugging more effective. But do avoid «uint», unless you really need it. The «uint» type is a turtle compared to «Number» and «int». More on this here.
  • Local variables. If you are going to access a variable more than two times, store it in a local variable first. Local variables are faster because they do not require a lookup into objects. E.g:
    var fName:String = person.firstname;
    if(fName == "jim" || fName == "jill")

    is faster than
    if(person.firstname == "jim" || person.firstname == "jill")
  • Data binding. Binding in Flex is a valuable and efficient way of handling data, however bindings do take up memory and they are general type. In other words bindings don't know what part of the data that will change, therefore all the data needs to be watched. If you are going the access the data only once or twice, it's better to do an manual assignment in code.

That's all folks.. be sure to check out the links as well.

1 comment:

Drew said...

Thank you... been looking for some legitimate optimization techniques for flash on the web and haven't been able to find very many that are, well, thoughtful.