Picking up where I left off last month, I wanted to talk about the nature of components in Flash. Components are pre-built software that is designed for reuse. Although, in Flash, the real question is when are they reused? At runtime or compile-time? &
In Flash at runtime, components consist of 4 basic parts:
1. MovieClips (via Library Assets – attachMovie or keyframe clips)
2. Methods (typically via Class inheritance)
3. Properties (typically via Class inheritance)
4. Constructor (create classes, MC to class binding, data instantiation)
In Flash MX, Flash MX 2004, and Flex, components are packaged in an author-time/compile-time format using either FLA or SWC formats. These formats depend on a compiler toolset to properly include assets from the FLA/SWC into the end SWF using compile-time pragma, initClip and on(activate). These author-time components also provide design-time features by exposing properties and previews to the developer. With few notable exceptions, most component technology in Flash is based on an authortime model and requires a compiler that understands the component format. Binding a component format to an authoring tool is good for the toolbuilder but leaves the end developer little flexibility in regards to tool selection or tool portability. If COM was bound only to Microsoft development tools both legally (EULA) and technically, COM would not be the success that it is today.
What I find disturbing about this is that the Flash Player and the SWF format has been component-oriented since version 4 with the addition of loadMovie. LoadMovie was specifically designed to allow the player to extend itself in a nested, distributed manner at runtime. If I needed a block of content, you could load a SWF into a container movieClip that rendered the nested content. What is great is that neither clip needs to know anything other than a url and that loaded file is a SWF. From an actionscript perspective, the boundary layer between the 2 SWF files is seamless, with the exceptions of a different _url property and domain security issues. Worse still is the fact that the V1 and V2 component sets are difficult to load externally. Making this work requires an act of congress and a very deep understanding of the specific component architecture.
Looking back at my first point, components are a collection of simple parts, it makes sense to assemble parts into a component instance from an XML definition. Essentially you could build a component instance by rendering its parts at runtime from XML. There are some issues that must be overcome:
1. Class Instantiation Order (initClip) would need to be made compatible in a runtime model. Currently class instantiation order is sorted in the flash compiler via the initClip pragma. This prevents broken __proto__ references within classes at runtime. Classes can be loaded in a way to allow them to install their dependent classes automatically. If I loaded mx.controls.Button class, mx.controls.SimpleButton, mx.core.UIComponent, mx.core.UIObject should load and be instantiated in reverse order preserving __proto__ references. Also if the class is already present, the class is skipped in the loading process.
2. XML Pseudo Library – In the absence of Library assets (attachMovie failure) content needs to be created. By overloading the attachMovie method, you can build child clips inside a single attachMovie call. If I say attachMovie(com.flow.Button, ‘myButton’, 23) where com.flow.Button is an XML string, it should render the component defined within the XML document. Working in this manner also preserves existing library based methodologies that are in use in V1 and V2. A great side effect is that components are instantiated inside the attachMovie call eliminating the instantiation delay waiting for the next frame to process the newly added movieclip.
3. Instance Data – Components need to be merged with instance data to provide their functionality. Ideally there is a single constructor method for each component that merges instance data with the component properties in an organized manner. Ideally this would be compatible with XML so that higher level XML tools would be compatible.
4. Asset Loading / Preloading – It makes sense for a project to load assets in chucks to allow them to be cached in the browser. Assuming 2 applications use the same components, neither should be forced to reload embedded components that simply add to file size. Instead they should be obtained and assembled in a distributed manner. In testing it is ideal to separate a components class, dependent classes, and movieClip assets into separate SWF files. The movieClip assets become the component skin files where the skin file is loaded, class is attached and the component instance is assembled from parts. This also provides compatibility with the attachMovie SWF library rules. An interesting side effect here is that skins of many components can be consolidated into a single file or shared library. Assuming that Button, CheckBox, Tree share similar library assets (they do in V1 & V2) it makes sense to preload this one skin file and reuse it across all component instances.
What excites me about this model is that I could make changes to the component at runtime. Assuming the above was a button, I could add an icon by simply inserting a node provided it was supported in the constructor. It also makes sense that should I need a component in a project that it could be loaded via a URL into my project.
Components are not complex at runtime, but currently they are tough to create and reuse in a flexible manner (not to mention legally). I don’t think it is just me, it is time for a new component model for Flash.
More to come,