Blog

  • No exclude.xml in Flash CS3 for AS3: Solution via Bridge Pattern

    Exclude.xml, functionality in Flash 8 and MX 2004 that allowed you to exclude ActionScript 2 classes compiled into your SWF, does not work in Flash CS3 for ActionScript 3. A similar function is available in Flex 2 via the load-externs option. This is the basis of how Flex modules work. The lack of this functionality just adds another challenge to Flash Developers who have expectations coming from AS2; this actually makes AS3 usage in Flash worse than AS2 when creating Flash sites, or large Flash applications.

    “Great Jesse, no one cares about your vendetta, so how do we fix it?”

    I have no clue, but the server architect I work with, John Howard, had a good idea. We’ll probably implement it in the next 2 weeks after we hit some interim milestones. I’ll explain his idea at the bottom, but first a review. If you want to skip the review, go to the bottom.

    Why Exclude Classes?

    When creating large Flash websites or applications, you’ll tend to have many SWF’s. This was especially true with AS2 driven not just from a media perspective, but also from a performance one. If you go to a visual website, say Flickr, and spend 20 minutes on it, you’ll probably download hundreds of images. Rather than download 20 minutes worth of images initially, you download on the fly and download whats needed. Flash and Flex apps can be built this way; it’s called excluding classes in Flash, and modules in Flex.

    In Flash, the main way to download assets over time is to load external SWF’s into another SWF. You use the loadMovie/loadMovieNum functions or the MovieClipLoader class, or the Loader component to do this pre-AS3. Although you can load images and video externally from a SWF just like a webpage can, the SWF format itself has visual advantages, such as images that can have alpha channels, yet also have JPEG compression applied to those images. JPEG does not have alpha channels, GIF only has a 1 bit alpha, and PNG never got the glorious browser support we all desired and only has lossless compression. When creating visual layouts that have a lot of media such as a multitude of images, audio, and/or video meshed with animations, this can be a stand alone SWF. Typically those types of things would be put into their own symbols such as a Graphic or MovieClip. However, if they got large enough, you should make it an external SWF for 3 reasons.

    The first is because it’s faster for you to make changes to the SWF. When you do a test movie, aka compile a SWF, Flash has to render animations, compress your bitmaps and sounds, as well as integrate your video if any. This can take a lot of time. Sometimes that time isn’t actually that bad, but because of the frequency in which you are re-compiling your SWF’s to check for visual accuracy, and doing this say every 2 minutes, and you end up saving 2 seconds in your compile… well, hey, that’s almost 10 minutes of your day you just saved right there! This is more apparent for larger media, however, like mp3 compressing a bunch of audio, or integrated video that can make your FLA’s take a minute or more to compile.

    The second is you can get help, aka RAD development. Instead of sharing the same FLA, you can have a project broken up into multiple FLA’s that another designer/developer can use so you both can work together on the same project.

    The third is that you only make the user download what they need to download. If you have a site that has 6 sections, you only need to make the user download the first section. You can either load the other section when the user clicks to go there, or download in the background once the first is done.

    The work-flow for visual projects in Flash is dead easy. There are a lot of frameworks, such as Gaia, and methodologies out there for facilitating this kind of work.

    For Flex, you have to be a rocket scientist. Flex 3 has some help in this department, but they are a long way off in how easy this is in Flash.

    For Flash applications, it’s a little different. In the beginning, our first enhancement to this was Remote Shared Libraries. What this allowed you to do was have a “reference MovieClip”, or any other symbol for that matter, in your library. Your symbol would have the SWF that it is stored in stored with the symbol as metadata. You’d go make that Symbol in another FLA, and upload those SWF’s together to your website. When your SWF was played, if a remotely shared symbol appeared on the time line, the Flash Player would automatically go download this for you.

    The bad was you really didn’t have much in the way of code in control or getting events about this. However, that ended up saving you a lot of work since it did it for you. Either way, this worked out pretty good because you could treat the symbols as normal symbols; the FLA would actually keep a local copy. You could update the symbol from the Library in case it changed in another FLA. You could additionally ensure every time you compiled it updated for you, but this was the slowest thing on the planet.

    In the end, Remote Shared Libraries were a management nightmare in Flash. For simple projects where you had a master SWF, they worked damn good. For anything more complicated, it was what I call “Flash Jenga” (Jenga is a game consisting of a tower of stacked wooden blacks the size of your pinky. The challenge was to remove bottom blocks without making the whole thing topple). If you got it to work, you were the shit, but it was very easy to break, and once it did, things came crashing down. The tools never really helped you manage your Remote Shared Libraries.

    Flex Builder has some nice improvements in this realm with regards to tool support.

    The biggest problem, however, with Remote Shared Libraries in regards to application development and code. Like I said, they still work good for assets; anything that isn’t ActionScript classes.

    Since ActionScript 2 and 3 utilize a lot of classes, and thus have dependencies, this makes things challenging when creating your applications for low initial download impact in mind. I’ll rehash my version here, but reading these 3 blog posts by one of the the mxmlc compiler creators, Roger Gonzalez formerly of Adobe, is probably a little more authoritative and better written. (Multi-SWF Applications, Modular Applications (part 1), Modular Applications (part 2)).

    It’s hard enough to architect an application, especially when accounting for a designers needs for dynamic Views. It’s another when you visualize a package of classes, and then have to account on how to reduce dependencies so you only load some classes in some SWF’s, and others in another SWF, but be sure not to use in a master SWF, thus reducing the overall file size. This can lead to code duplication, or a non-efficient use of a RSL, or too much in an RSL that’s not used by 80% of the application. As if software development wasn’t hard enough, you have a designer who keeps changing your MovieClip instance names.

    You could just say fuggit, and just load a bunch of SWF’s as users navigate to those sections. However, your wasting bandwidth by using duplicated code. For example, in the image below, 3 forms are loaded into a master SWF on the fly whenever a user navigates to that section. Each other has it’s own unique set of components; however, each also has it’s own copy of Button, or mx.controls.Button to be exact in AS2. Say that your Button is 14k. You’ve now duplicated that 14k across 3 SWF’s.

    Exclude-01

    …however, why not just load that class once, and have all other SWF’s use that same already loaded class? You can! First, a review on how AS1/AS2 classes work.

    In the old AVM, aka, the one that runs AS2 and A1 (regardless of player version), classes are defined on _global. The _global keyword is like this object that never dies, and is accessible via the _global keyword in ActionScript. It’s also accessible across SWF’s and across _levels (_level is like a loaded SWF basically). This means that SWF’s loaded in can access classes on _global as well as defining their own. They cannot, however, overwrite classes. In AS3, this behavior is controlled via ApplicationDomain; in AS2, it is what it is.

    Since you know you’ll be loading those 3 SWF’s into a SWF that will already have the Button class defined, you can then just not compile those 3 SWF’s with the Button class. The user then only has to download 14k once; any other SWF that uses the Button class can use that already downloaded class. In the example below, the Button class has been moved to the shell.swf, increasing it’s size from 8k to 22k. However, notice that that same 14k is now removed from the login.swf, the amount.swf, and settings.swf.

    Exclude-02

    In this particular example, you’ve ended up saving 24k! Now, imagine a large website or large application consisting of dozens of SWF’s that could potentially use the same class. You can see how this feature saves a ton of bandwidth.

    How Exclude.xml Works

    Exclude.xml works like dis. If you have a FLA called “my.fla”, you create an XML file in the same directory next to the FLA called “my_exclude.xml”. When you compile your FLA, Flash will look for that exclude.xml file. If it finds it, it’ll read it. Any class written in that XML file will NOT be compiled into your SWF. The con to this is the SWF no longer works on it’s own; you have to load it into another SWF to test. The plus is that you’ve now saved file-size since the SWF will get the class it needs to work from another main.swf. Most importantly, your work flow has changed; just your SWF.

    In the past, I wrote some JSFL to automate this. One JSFL script would delete the exclude.xml file, and then do a test movie. You map this JSFL to Control + Enter so your Test Movie works as normal. I then created another JSFL script to create the exclude.xml based off of a set of classes I knew would be shared throughout the site, and then test your movie. I then mapped this JSFL to Control + Alt + Enter, replacing test scene. That way, you can create SWF’s ready for deployment easily.

    Now that Flash CS3 has E4X, writing such scripts is a ton easier, and gives ANT in Eclipse a run for it’s money in automation. Course one could use Rake (Ruby‘s version of Make), but anyway.

    In Flex using mxmlc, this part is actually automated for you; the XML you need is generated via the mxmlc -link-report parameter. You immediately feed that generated XML file to -load-externs, and booya, you have a SWF with those classes removed.

    So, pretty pimp, huh? Guess what; it doesn’t work in Flash CS3 for AS3. I know, right? “Yeah hi, I’ll take some AS3 with a side of lame sauce.”

    Using mxmlc Doesn’t Work

    I tried using mxmlc with -incremental set to true, making sure it doesn’t actually recompile the entire SWF, but just those classes that have changed. If you make sure your FLA has a Document class, this’ll work; mxmlc can use that as the root class. However, in recompiling your classes, it basically ignores the symbols your FLA has created, thus “I’ll take it from here” attitude. Um…mxmlc, dude, f-off, at least we can use pixel fonts…

    You could do this in MTASC for AS2, I guess their bytecode replacement techniques are just different. Either that, or I’m maybe missing a mixture of mxmlc compiler arguments… :: crosses fingers hoping someone says so in comments ::

    Bridge Pattern to the Rescue (sort of)

    So, my boss suggested a proxy technique. Basically, we use the J2EE blah blah blah official blah blah Bridge Pattern. The Bridge Pattern in a nutshell is 2 classes that implement the same interface; one provides the pretty face, whilst the other does all the work. The pretty face is called the Abstraction and the one who does the work is called the Implementation.

    If you were going to create a Button component using the Bridge Pattern, you would do it in 3 steps.

    1. Create the IButton interface
    2. Create the Button class that implements IButton
    3. Create the ButtonImpl class that implements IButton, and does all the work.

    Flex 2 actually uses this in a few places, specifically the ToolTipManager class. ToolTipManager merely proxies everything to ToolTipManagerImpl. He instantiates an Implementation class (ToolTipManagerImpl) via a magic string to ensure there are no dependencies, meaning the compiler doesn’t know to compile it in. To ensure it is compiled in, however, they do do (gross) a dependency variable above that.

    This is how the Bridge pattern will work to save file size. The child SWF’s will only contain the interfaces and abstractions; the implementations will be in the main SWF. First thing to do is create the interface, mainly for typing purposes.

    Now that that’s done, I do the same thing the ToolTipManager does; I instantiate the ButtonImpl class inside of Button via a magic string. This ensures that Flash doesn’t see the usage of the class. If it did that, Flash would compile it in. A magic string, however, cloaks it from the compiler. Using flash.utils.getDefinitionByName, I can instantiate the ButtonImpl class with my magic string:

    var btnImpl:Object = getDefinitionByName("com.multicast.controls.ButtonImpl");
    impl = new btnIpml() as IButton;

    Now, I can just create my sets of components as normal:

    var btn:Button = new Button();
    addChild(btn);

    However, the ButtonImpl class won’t be compiled into the child SWF’s. Instead, he’ll be compiled into the main shell.swf.

    Based on some initial tests, I reckon interface will run about 500 bytes to 2k, and the Button class from 2k to 4k. The Impl will be around 8k. So, being conservative and rounding up, all of my child SWF’s will no longer have 14k in them, but rather 6k. Like exclude, the developer whether using Flex Builder with an ActionScript project, or Flash CS3, can code normally with AS3’s strong-typing, and/or Flash’s time line and symbols. The down-side is I’m still duplicating anywhere from 2k to 6k in any additional child SWF that uses Button.

    It’s not perfect, but it’ll do.

    Unknowns

    What I haven’t figured out yet is the implementation details. Premature optimization is the root of all evil so I hear, but seriously, how much speed does keeping the interface for strong-typing really give me? What if I just remove the interface, and cast impl in the example above as a DisplayObject, or more accurately, a MovieClip? I feel the Interface is for Java people who like a bunch of classes; to me, 2 is too many, let alone 2 and an interface. I’m only doing this because a feature that worked in 2 previous Flash IDE’s now doesn’t; don’t punish me by making me write more classes to compensate for a feature that removed classes in the first place. Convention works for the Ruby guys; why not me? I don’t really want to spend much time on benchmarks, but any dynamic look up will cause the old AVM to be used, and since this component set is created with AS3, it kind of defeats the purpose of using AS3 if you aren’t going to take advantage of the runtime speed.

    Secondly, what is impl, a DisplayObject, or rather a class that uses a DisplayObject via Composition? Traditional programmers who came to Flash in the past would use Composition all the time because the thought of extending a GUI base class freaked them out. So, instead of extending MovieClip or Sprite, they’d instead store a reference to the MovieClip or Sprite passed in the constructor. All methods would then act on that reference, as opposed to the class itself via Inheritance. Would doing Composition be better? Although it may have a tad more code, it’d be redundant, so hopefully zlib SWF compression would see that and I’d still hit my small file size goal. Furthermore, I wouldn’t end up with twice as many DisplayObjects. In AS2 that was bad, but in AS3… not so much. If all Buttons were just a simple shell with the “real” Button inside it as the impl, is that really that bad? My gut says make the Implementation class via Composition to save on the number of DisplayObjects.

    Basically, rather than doing:

    // Button.as
    private var impl:IButton;
    
    public function Button():void
    {
            var btnImplClass:Object = getClassByDefinition("com.multicast.controls.ButtonImpl");
            impl = new btnImplClass() as IButton;
            addChild(impl);
    }
    
    public function setSize(w:Number, h:Number):void
    {
            impl.setSize(w, h);
    }
    
    // ButtonImpl.as
    public function setSize(w:Number, h:Number):void
    {
            this.width         = w;
            this.height     = h;
    }

    I’d instead do:

    // Button.as
    private var impl:IButton;
    
    public function Button():void
    {
            var btnImplClass:Object = getClassByDefinition("com.multicast.controls.ButtonImpl");
            impl = new btnImplClass(this) as IButton;
    }
    
    public function setSize(w:Number, h:Number):void
    {
            impl.setSize(w, h);
    }
    
    // ButtonImpl.as
    private var btn:IButton;
    
    public function ButtonImpl(ref:IButton):void
    {
            btn = ref;
    }
    
    public function setSize(w:Number, h:Number):void
    {
            btn.width         = w;
            btn.height        = h;
    }

    Any other ideas (or corrections), lemme know.

  • How to Show Regular Time in Google Spreadsheets

    I cannot read military time. I can read regular time. Google Spreadsheets at the time of this writing only supports formatting for military time. After digging around, I found this formula works:

    =TEXT ( theCell, “hh:mm a”)

    You can then have the military time column (which will auto-format when you type a time value in) to the left, and then use the above formula for the column to the right. Combined with changing the military time column to a lighter text to lower it’s visual prominence, you get something like this:

  • Flex GUI WYSIWYG Creator Prototype

    Screen cast and source at the bottom.


    Preface

    John Grden created something like this in the past called FLEXible. Basically, you use Flex as a drag and drop interface to create GUI’s. The GUI’s are represented as XML, and this XML is used in another context. FlexBuilder creates and renders MXML as well as ActionScript. Web browsers render HTML, and a variety of tools from Notepad and Dreamweaver can create HTML.

    The reason to use a WYSIWYG editor for layout is that you get more visual control when laying out interfaces. Sure, you can edit an x attribute on an XML tag for pixel precision, but if you want to see the entire interface, a WYSIWYG is the way to go. You can make a visual change, and see how your design is affected. A lot of early Flash Development was layout of the interface first, code second.

    Another use of WYSIWYG editors is for Content Management Systems. In the case of intranets, some have small sections where you can enter custom text, whether normal or HTML, that show up in approved sections of the company website. More advanced ones like WordPress blogging software has a plethora of controls for writing a blog entry. Many buttons will automatically write the appropriate HTML for you. This saves massive amount of time, and allows you to focus on your blog and, and less time on how your blog entry is made.

    We have wants at work for a variety of visual CMS WYSIWYG editors. For customers who request minor graphical and layout changes to their products they purchase from us, it is much quicker to simply re-position a GUI element via a WYSIWYG editor, confirm visually in real-time that is what they want, and save these settings to the profile. This, as opposed to changing some text markup or a value in a MySQL table, and going through the management chain through phone calls and email to answer the question, “I made the change; were they ok with it?”.

    While both actions can take about the same amount of time, using a simple WYSIWYG editor doesn’t require a degree in computer science. Nor does using WordPress ‘ text editor. Easy to use interfaces that generate the necessary code. Whether they are used by users, or client managers doesn’t matter; what matters is that developers are developing instead of spending their valuable (read costly) time on making extremely minor graphical changes to things that anyone could do that had an Internet connection, a web browser, and login credentials.

    I’m all about reducing overhead costs.

    The OTHER Drag and Drop in Flex

    Flex is known to have pimp drag and drop features. They are built into the SDK, and require a boolean and 2 event handlers to work. Mizz-nagic. However, there is another way to do drag and drop in Flex. It’s called the startDrag method, and it’s a party of Sprite. He has a stopDrag method as well. These methods are more efficient than doing your own emulation of drag and drop since they are built-in. The downside is they still have the same refresh problem, but you can fix that the same way you have in the past using a mouse move event handler, and calling updateAfterEvent on the event parameter.

    Using these 2 methods, you can build your own drag and drop interface that consists more of just using the Flex SDK list classes. They are, however, more low level so you have to do some more coding legwork.

    Introduction

    I built this Viewer Editor for a co-worker at work. The goals were thus:

    1. Needs to be done in 2 days.
    2. Worked on outside of work core hours.
    3. Implement important features to showcase ability to create interfaces vs. being feature complete.

    In short, a prototype for a demo. You know what that means kiddies: uber-hacks, kludgey code, and something you don’t bring to an interview (unless you are damn good at explaining context). The GUI you build can be saved as XML. This XML can be re-read in and the Viewer Editor will re-build the interface so you can edit it. This XML ultimately is read by a .NET web service that will build an HTML front-end based on the client’s settings and this layout XML. If a client wants something moved “20 pixels to the right”, you launch the interface, move the GUI element, and click save.

    So why show it knowing the code is bleh? A few reasons:

    • Shows how to do the ‘other’ drag and drop in Flex as well as the regular, built-in kind
    • Shows how to dynamically build forms through ActionScript using the Flex Form & FormItem classes
    • Shows how to use 50 billion bindings through ActionScript
    • Shows what you can build in 12 hours or less using Flex and Red Bull.

    Built JB Style; no Cairngorm overkill insanity here. Speed, people, speed! Code gen is for people who can’t type fast.

    You can view the Captivate screen cast, read the following, or both… or cross the border with a chicken and crowbar.

    Controls

    The Viewer Editor is made up of 3 panels to interact with laying out controls on the Canvas. The first is the Control Panel. This guy is configured via external XML. He dictates what you can drag and drop onto the Viewer Canvas.

    The Viewer Canvas itself is basically just a Canvas that draws draggable controls inside itself. You can select controls, drag them, as well as modify their properties in the Property Inspector.

    The Property Inspector shows the modifiable properties of a control when you select that control. You can also select the Viewer Canvas.

    Although there are 2 missing features such as deleting and changing z-order of elements, this could be easily done by having the Controller either remove an item from the currentViewer.children, or by changing the order of an item in the currentViewer.children.

    Conclusions

    Although Flex 2 is positioned as a way to build Enterprise applications, whilst Flash is for lightweight, speedy RIA development, clearly with the right attitude you can use Flex Builder as a prototyping tool. Drop the frameworks, ignore the code review, and down the caffeine.

    There is also a lot of potential for GUI WYSIWYG’s as front ends for CMS systems. From Scrapblog.com, gModeler, and many others. While it’s great to have a extremely configurable back-end, it’s also nice to have a quick, easy way to modify values in that back-end. It’s even more cool when users and clients can do this themselves in a controlled manner using a tool specifically built for allowing them to configure what they want changed most, without having to utilize a developer’s time.

    It’s fun to do prototypes and CMS’ in Flex.

    Viewer Editor – Screencast | App | Source | ZIP

  • Weak Activation Object

    It appears either A) The Activation Object in ActionScript 3 is dumber than it’s predecessor, or B) the new Garbage Collector implemented in Flash Player 8 is more aggressive, or C) I’ve never had this use case. Naturally, I’d like to believe that it’s A, but I have a sinking suspicion it’s a combination of B & C.

    I read this post by Matthew Tretter describing how reference-less objects such as Tweens and URLLoader’s won’t work consistently when there are no references to them.  This is because they have no references, and when the Garbage Collector comes around, he sees this, and destroys the mofo’s. This is in direct violation of how a lot of us have coded in the past since Flash Player 6 implemented dynamic MovieClip methods like onPress, and onRelease. Using anonymous functions with anonymous variables was just the lay of the land:

    my_mc.onPress = function()
    {
        var my_xml = new XML();
        my_xml.ignoreWhite = true;
        my_xml.onLoad = function(success)
        {
           trace("success!, parse this.");
        };
    }

    In the above example, my_xml is a local variable. In ActionScript 1 and 2, no one has a reference to it. Thus, at the end of onPress, it’ll die… or, so it would appear. However, Garbage Collection first has to activate to kill it; theoretically GC only runs every 60 seconds, or when memory increases 20% in 1 frame. The GC will kill it if no one has a reference to it. However, the Activation Object does. For both XML and LoadVars, I and thousands of other Flash Developers have used this technique with a variety of ways to handle scope as well.

    You’ll notice, however, that this code isn’t very memory intensive, thus I guess staying under the radar of GC. It merely makes an XML object, gets the XML, parses it, and that’s it, done. When AS2 came out, I started keeping class references to these variables for ease of writing code, and confirmation I was in fact deleting them later when I was done. Therefore, my guess as to why I’ve never seen the problem Matthew talks about is that I’ve never created extremely memory intensive applications pre-AS2 that used of asynchronous operations created via local variables. Seems plausible.

    So, I told him he was wrong and moved on. He tracked my ass down to Flashmedia to politely plead his case. Turns out I was wrong… and extremely lazy. I didn’t do diligence and actually test his code. Upon testing his code (1000 creations vs. my 1), and his problem was easily reproducible. He’s created some classes that help encapsulate this so you don’t have to worry about it.

    For example, Robert Penner’s original Tween classes actually kept a global reference of all crated Tween instances in a static array, so there was always at least 1 reference. I had just always assumed that the Activation Object knew of asynchronous objects, and thus released the lock (killed the reference) on it after their asynchronous operation had completed such as onData, or onLoad for LoadVars/XML.

    I often create local variables for loading such as Loader or URLoader for generic loading code, so I was horrified that this scenario was this predictable. I’m not sure how to best resolve this yet since I’ve been doing this for years and it’ll really be a pain in the ass to start either keeping class references for these things or using a wrapper class. I only load 1 or 3 of these at any one time, not 1000 so maybe I’ve just gotten lucky all of these years. Maybe a beer will help… yeah… a beer…

    Anyway, I apologize Matthew for saying you were wrong without due diligence on my part; I was wrong and could of at least had the common courtesy to actually test your provided code before making judgments based on long held assumptions.