News Flash: Public Service Announcements

E-mail

I recently switched a fairly complex Ajax application that I had built to use Flex. For those that don't know, Flex Builder is a programming tool to build flash applications. I have to say that I love programming in ActionScript, which is the main language you use in Flex. One thing to know about Adobe and Flash; there are lots of confusing names here. ActionScript, Flex, Flex Builder, Air, Flash Player, Flash IDE, yada yada yada.

Anyway, the latest ActionScript fits a little better with my work flow than programming in Java, mainly because of function pointers and closures. For example, when I need to create a small event callback, I just write a little function. To do the same thing in Java I usually make a little anonymous class. I also have to make sure that any variables I need to reference in the anonymous class' containing scope are private. These aren't huge deals but they are just enough extra overhead that they interrupt my flow. Of course, there are a couple annoying things about ActionScript too.

The biggest is that there is no block scope. So variables inside an "if" block are visible outside that "if" block. And the counter declared in a "for" loop is visible everywhere inside the containing function. This can cause errors if you're not careful, but it is mostly just an annoyance.

Anyway, the point of this post is to report on a couple flex related issues in case the solutions help anyone else. My naive assumption was that I could get rid of cross-browser weirdnesses like these by writing a Flash app instead of an HTML based app. This is definitely more true than with the Ajax library I was using, but it's not totally true. So here goes.

The first bug: I wanted my Flash app to fill 100% of the browser height minus a fixed height header. You'd think this would be really common and easy. But I had a hard time finding examples on the web. I finally found this email thread which pointed me to this general technique to fill 100% height. The idea is that you specify the top and bottom in the CSS but you leave the height unspecified. Surprisingly, this worked out of the box for IE7 and Firefox. But it didn't work on Safari or Google Chrome, despite what the email thread above suggested. I guess nothing across browsers is ever simple. Luckily, Chrome has a nice feature where if you right click on an element you can select "Inspect Element" and it pops up a box that has some of the functionality you get with the Firefox Firebug plugin. After playing around in here for a while I finally found the magic invocation to make things work. The DIV that I fed to swfobject needed to have "display: block;" set on it in the CSS. Fortunately, this setting doesn't break IE7 and Firefox so it worked for all the browsers I care about for now (I'm delaying old IE and Opera support until the site is more stable).

So now my app laid out fine in the browsers and it actually functioned in Firefox, Chrome, and Safari. But it just did not work in IE. HTTP requests to my server just seemed to get lost after the server sent back a response. The app would just sit there. What the heck? I thought it was the same player in all the browsers? I did some quick google searching and got totally diverted by this set of bug reports related to IE caching. This didn't quite smell right but I was going for the quick fix rather than really thinking the problem through. Anyway, after messing with my server for a little bit, I finally remembered that I needed to separately install the debug flash player for IE. The debug version I had installed for the other browsers didn't show up for IE. After I did this, I found out that IE was parsing my HTTP POST request as form arguments. The flash player was not doing this on the other browsers. Anyway, easy to fix, I changed the content type to CONTENT_TYPE_FORM and passed in a dictionary of arguments instead of a preformatted form string. OK, things should be working great now, right? NO! Turns out IE also returns the real HTTP status codes. The other browser seem to return more process-like status codes with 0 for success and 1 for failure (Edit: Actually, I think these other browsers just don't fill in the status code, so it defaults to 0). So my success check now looks for status codes 0 or 200. I guess technically I may not need to check the status code's at all, since network errors usually get sent to a fault handler. However, I couldn't find clear documentation on what it was going to do, so I thought better safe than sorry.

The last bug is not a bug at all but an annoyance with Flex. In Flex, you can add "trace()" statements to your code and it will print the output to an error console. Well, I could not get this to work. I looked through all the Flex settings and couldn't find anything to enable this. Plus, I thought that a tool for debugging applications would surely have the debug console enabled by default. So I suspected a bug. I did some more google searching and found this line of bug reports. This didn't sound quite right and I actually had a version of Firefox that was supposed to be fixed. Plus, breakpoints seemed to work so the debugging sessions were clearly connecting correctly. I couldn't understand why it still wasn't working. Finally, I looked on the settings for the individual launcher entries in the Debug dialog in Eclipse. It turns out that there is an obscure checkbox under the third tab labeled "Common" that says "Allocate Console (necessary for input)." So you have to manually enable the debug console for every application that you want to debug. Unbelievable.

Last Updated on Sunday, 28 February 2010 20:45  

Add comment


Security code
Refresh