Skip to content


Flex 4 and Runtime style sheets

I just put up some files on github under the project name flex-runtime-css. Perhaps it is a misnomer if people are coming to see how to load and parse CSS files (there’s already the great F*CSS library out there for that). The flex-runtime-css project is intended to address a problem i saw when generating a Runtime CSS SWF to be loaded in a Flex Application.

Sometimes a project calls for loading in CSS at runtime rather than compiling the style sheets in. Often enough this is due to a project requirement to have dynamic styling/skinning based on separate client vendors, yadda-yadda. To generate these Runtime CSS SWF files i use the Adobe MXMLC compiler tool from the Flex SDK. If you are unfamiliar about how to generate a CSS SWF or how to load in the SWF at runtime for style declarations, you can visit the the Adobe live docs on the subject at http://livedocs.adobe.com/flex/3/html/help.html?content=styles_10.html.

The problem i was running is that the default flex-config used by the MXMLC tool in Flex 4 now links against several RSLs. I won’t go into a discussion of RSLs, but the reason for this is lower application size. That’s great for an application, but unnecessary when generating a CSS SWF. In fact, if you generated a CSS SWF using the default flex-config via the following command:

> mxmlc MyStyle.css

… your generated CSS SWf file will request those RSLs when loaded into the application via the StyleManager. Unnecessary overhead as they those RSLs are already in the application domain and the request becomes moot.

So, long story long, flex-runtime-css intends to address this issue by providing a custom configuration that does away with the RSL linking and externally compiles against the framework libraries. A CSS SWF can be generated using the flex-runtime-css files and ANT. If you use the flex-runtime-css you will need to update the build.properties file included in the project to point to the Flex SDK and file resources on your local disk.

flex-runtime-css on github.

Posted in Flash, Flex, flex-runtime-css.


9 Responses

Stay in touch with the conversation, subscribe to the RSS feed for comments on this post.

  1. Ramin Zarghany says

    Hi,

    Because of the Security Sandbox you can not just load swf into your mobile project, instead you have to get the bytes first, then load the bytes.
    I have managed to load a css-compiled SWF into my FLEX Mobile Project using the following code :

    var urlRequest:URLRequest = new URLRequest(”http://{my domain}/theme_mobile_blue.swf”);
    var urlLoader:URLLoader = new URLLoader(urlRequest);
    urlLoader.dataFormat = URLLoaderDataFormat.BINARY;
    urlLoader.addEventListener(Event.COMPLETE, bytesLoadedHandler);

    private function bytesLoadedHandler(event:Event):void
    {
    var ModuleBytes:ByteArray = ByteArray(URLLoader(event.target).data);
    module = ModuleManager.getModule(url);
    module.addEventListener(ModuleEvent.READY, modReadyHandler);
    module.load(null, null, ModuleBytes);
    }

    private function modReadyHandler(event:ModuleEvent):void
    {
    Singleton.getInstance(”mx.styles::IStyleManager2″).styleDeclarationsC hanged();
    }

    now i used your method to compile my swf file,
    BUT I CAN NOT SEE THE NEW STYLE ?!!!!!!! ANY IDEA????

  2. todd anderson says

    Hello Ramin,

    I think the issue is that the styles are not being registered with the stylemanager before invoking a change. Without really testing this theory, I am thinking this may help:

    private function modReadyHandler(event:ModuleEvent):void
    {
    var factory:IFlexModuleFactory = event.module.factory;
    var styleManager:IStyleManager2 = this.styleManager || StyleManager.getStyleManager( FlexGlobals.topLevelApplication.moduleFactory );
    var styleModule:IStyleModule = IStyleModule(factory.create());

    factory.registerImplementation(”mx.styles::IStyleManager2″, styleManager);
    styleModule.setStyleDeclarations( styleManager );
    styleManager.styleDeclarationsChanged();
    }

    Hope that helps.

  3. Ramin Zarghany says

    Thanks a lot todd, I realy appreciate your help. it worked. I will keep in touch every now and again. thanks

  4. Ramin Zarghany says

    I have a question, I want to load resources at runtime for my mobile project,
    should I use mxmlc using the default configuration file to compile my resources to .swf ?

    I try compilying my resources to swf files like the following :

    mxmlc -locale=en_US
                 -source-path="....my path.../ISVLibrary/locale/{locale}"
                 -include-resource-bundles=RegistrationForm,collections,containers,controls,core,effects,skins,styles
                 -output "...my path.../fr_FR_ResourceModule.swf"
    

    however my resources won’t show in my mobile APPLE IOS-iPad project. here is the code :

    var urlRequest:URLRequest = new URLRequest(”http://{my domain}/fr_FR_ResourceModule.swf”);
    var urlLoader:URLLoader = new URLLoader(urlRequest);
    urlLoader.dataFormat = URLLoaderDataFormat.BINARY;
    urlLoader.addEventListener(Event.COMPLETE, bytesLoadedHandler);
    
    private function bytesLoadedHandler(event:Event):void
    {
    var ModuleBytes:ByteArray = ByteArray(URLLoader(event.target).data);
    module = ModuleManager.getModule(url);
    module.addEventListener(ModuleEvent.READY, modReadyHandler);
    module.load(null, null, ModuleBytes);
    }
    
    private function modReadyHandler(event:ModuleEvent):void
    {
       resourceManager.localeChain = [fr_FR];
    }
    

    it won’t show and get stuck here on Apple iPad flex mobile projects.

    CAN YOU PLEASE HELP ME WITH THIS?

  5. todd anderson says

    Hello Ramin,

    I have not tried loading in runtime SWFs on iOS, so i can only speak from assumption, but I think it is relatively the same procedure as discussed for styles; only this time for locale.

    I would use the same custom config, but instead of pointing to the local locale folder, point to the one for the SDK. For example, in the external library path declarations of the custom config:

    ...
    <external-library-path>
           	<path-element>${flex.lib.dir}</path-element>
           	<path-element>${playerglobal.lib.dir}</path-element>
           	<path-element>${playerglobal.lib.dir}/${player.version}</path-element>
           	<path-element>${flex.locale.dir}/{locale}</path-element>
    </external-library-path>
    ...
    

    And you need to activate it in the modReadyHandler, like such:

    private function modReadyHandler(event:ModuleEvent):void
    {
        var resourceModule:mx.resources.IResourceModule  = event.module.factory.create();
        var bundles:Array = resourceModule.resourceBundles;
        var i:int = 0;
        var length:int = bundles.length;
        for( i; i < length; i++ )
        {
            resourceManager.addResourceBundle( bundles[i] as IResourceBundle );
        }
        resourceManager.update();
        resourceManager.localeChain = [fr_FR];
    }
    

    Again, that is untested code, but i think that may set you on the right path.

    Hope it helps.

  6. Rich says

    Did this work for you on IOS / production build? Where you able to get runtime css loading working on IPad/IPhone?

  7. Gaius says

    I found this: https://bugbase.adobe.com/index.cfm?event=bug&id=2910342
    I think iOS is not very open to the idea of loading in external byte code… :(

  8. Kelsey says

    Has anyone ever found a solution to loading runtime style sheets for iOS? I have about 16 different style sheets in my flex app, and I am trying to convert to an iOS app. Please enlighten me!
    Thanks

  9. G S V Ravi Sankar says

    hi todd,
    Currently i am migrating flex 3.5 to flex 4.6 in flash builder in flex3 compatibility mode
    Every thing resolved but at styles part we are facing the following issue. we are using runtime styles. the script error:
    TypeError: Error #1009: Cannot access a property or method of a null object reference.
    at Function/()[E:\dev\4.y\frameworks\projects\framework\src\mx\styles\StyleManagerImpl.as:1554]
    at flash.events::EventDispatcher/dispatchEventFunction()
    at flash.events::EventDispatcher/dispatchEvent()
    at ModuleInfoProxy/moduleEventHandler()[E:\dev\4.y\frameworks\projects\framework\src\mx\modules\ModuleManager.as:1149]
    at flash.events::EventDispatcher/dispatchEventFunction()
    at flash.events::EventDispatcher/dispatchEvent()
    at ModuleInfo/readyHandler()[E:\dev\4.y\frameworks\projects\framework\src\mx\modules\ModuleManager.as:793]
    at flash.events::EventDispatcher/dispatchEventFunction()
    at flash.events::EventDispatcher/dispatchEvent()
    at mx.core::FlexModuleFactory/update()[E:\dev\4.y\frameworks\projects\framework\src\mx\core\FlexModuleFactory.as:535]
    at mx.core::FlexModuleFactory/docFrameHandler()[E:\dev\4.y\frameworks\projects\framework\src\mx\core\FlexModuleFactory.as:681]
    at mx.core::FlexModuleFactory/docFrameListener()[E:\dev\4.y\frameworks\projects\framework\src\mx\core\FlexModuleFactory.as:131]



Some HTML is OK

or, reply to this post via trackback.