Accessibility

Table of Contents

Building web and Adobe AIR applications from a shared Flex code base

The big picture

As a developer, if you tried to compile a Flex application destined for web-browser distribution that referenced shared code with dependencies on the Adobe AIR libraries, you'd be out of luck with compile-time errors. To get around this, you need to have a specific project for your Flex web output, and another for your Adobe AIR output. On top of this, because you don't want to duplicate all your code in both projects, you need a third project that contains all the common code of the application. Then your common code makes calls to an interface that has abstracted out the functionality that relies on specific runtime functionality (desktop versus web). Don't worry, this sounds a lot worse than it is.

The easiest way to understand where to start is with the big picture of the solution. Look at Figure 1, which is a UML diagram of the sample project. I'll get down to the nitty-gritty of the code in the following sections. It's ok if you don't fully understand everything at this point; it's natural for this to take some time to sink in. Hopefully by the time you're done looking at the code, you'll be a guru of this implementation.

UML Diagram of the three projects and their source code elements.

Figure 1. UML Diagram of the three projects and their source code elements.

The core application code lives in the Common Project. Adobe AIR specific and Flex specific code live in their own projects.

The main application is MainCanvas.mxml and this needs to be added to both the Adobe AIR Project and Web Project with a call to addChild, just like adding any regular Flex control to a container from within ActionScript. Don't think of your WindowedApplication (for Adobe AIR) or Application ( for Flex Web Project) as your entry point to start coding. These are only shells that host the application.

Next, to call a method that's been extracted, like saveFile, the CommonCode must call against the IGeneral interface that defines the functionality in mind. To get at an implemented version of saveFile, the CommonCode must get a reference to IGeneral from the GeneralFactory object, which retuns objects that implement IGeneral, supporting the saveFile functionality.

GeneralFactory is self-aware of whether it's running inside Adobe AIR or a regular Flex application and will return either FlexGeneralImplementation or AirGeneralImplemenation, depending on the environment it's running in. When compiling the Adobe AIR desktop version of the application, AirGeneralImplementation is compiled into the final application with all its links to the Adobe AIR specific APIs. When compiling the Flex version into a SWF for running inside a web browser, FlexGeneralImplementation (without any references to the Adobe AIR APIs) is compiled into the application.

The GeneralFactory returns the appropriate class to the CommonCode application where the appropriate saveFile method is called. The Adobe AIR Project will use browseForSave, an API specific to Adobe AIR, to save a file locally. The Web Project's implementation just flashes a quick message informing you to download the full version of the application.

Here's how calling abstracted functionality looks in the main application code:

var general:IGeneral;
general = GeneralFactory.getGeneralInstance()
general.saveFile();

That's it; pretty straightforward after you've organized all the code and created the appropriate classes.