ANT, mxmlc and SWC files

Add comments

I've been working w/ANT the last few days, trying to get it to compile a flex app that makes heavy use of Cairngorm, FlexLib, and Flare.  All these libraries deliver swc files that can be compiled into the application.  This is very easy to do with FlexBuilder, but not so simple for the n00b when trying it out for the first time.

First of all, the mxmlc ant task is poorly documented; apparently, we are supposed to refer to the mxmlc documentation.  Fair enough.  However, it is not-exactly trivial when the syntax changes ever so slightly.

The first issue I had was getting the .swc files to compile in.  The example lists the following:

	<!-- List of SWC files or directories that contain SWC files. -->
            <compiler.library-path dir="${FLEX_HOME}/frameworks" append="true">
                <include name="libs" />
                <include name="../bundles/{locale}" />
            </compiler.library-path>

My mistake was trying to add my swc files here.  See the dir attribute?  That refers to flex's interal swc repository.  I, unfortunately, was thrown by <include name="libs" />, which I took to mean my project/libs/ directory.  I obediently added all my include files here, and fought compiler errors for the next few hours.

Turns out, if you want several swc files from multiple directories, you need to represent each directory tree in its own <compiler.library-path .../> block.  My code ended up looking like the following:

 

            <compiler.library-path dir="${flex.sdk.dir}/frameworks/libs" append="true">
                <include name="*" />
                <include name="../bundles/{locale}" />
            </compiler.library-path>
                
            <!-- these are our library swcs (w/a different home directory) -->
            <compiler.library-path dir="@{libDirectory}" append="true">
                <include name="cairngorm" />
                <include name="flexlib" />
                <include name="flare" />
            </compiler.library-path>
            
            <compiler.library-path dir="@{sourceDirectory}" append="true">
                <include name="flexspy" />
            </compiler.library-path>

Hopefully, somebody will be saved a lot of time.  For reference, here is the macro I am using for compilation:

 

	<macrodef name="macro.mxmlc.compileWithFlexAnt">
<attribute name="sourceDirectory" default="${src.dir}" />
<attribute name="libDirectory" default="${basedir}/libs" />
<attribute name="in" />
<attribute name="out" />
<attribute name="config" default="${flex.config.xml}" />
<attribute name="additional" default="" />
<attribute name="defaultWidth" default="800" />
<attribute name="defaultHeight" default="600" />
<attribute name="debug" default="false" />
<attribute name="incremental" default="false" />

<sequential>
<mxmlc
file="@{in}"
output="@{out}"
actionscript-file-encoding="UTF-8"
keep-generated-actionscript="false"
incremental="@{incremental}"
debug="@{debug}"
>
<!-- Get default compiler options. -->
<load-config filename="@{config}" />

<!-- List of path elements that form the roots of ActionScript class hierarchies. -->
<compiler.source-path path-element="${flex.sdk.dir}/frameworks"/>
<compiler.source-path path-element="@{sourceDirectory}"/>


<!-- List of SWC files or directories that contain SWC files. -->
<!-- these are the built-in flex swcs -->
<compiler.library-path dir="${flex.sdk.dir}/frameworks/libs" append="true">
<include name="*" />
<include name="../bundles/{locale}" />
</compiler.library-path>

<!-- these are our library swcs (w/a different home directory) -->
<compiler.library-path dir="@{libDirectory}" append="true">
<include name="cairngorm" />
<include name="flexlib" />
<include name="flare" />
</compiler.library-path>

<compiler.library-path dir="@{sourceDirectory}" append="true">
<include name="flexspy" />
</compiler.library-path>

<!-- Set size of output SWF file. -->
<default-size width="@{defaultWidth}" height="@{defaultHeight}" />
</mxmlc>
<echo>Compiled @{in} to @{out}</echo>
</sequential>
</macrodef>


Next step, RSLs. :-(

22 responses to “ANT, mxmlc and SWC files”

  1. Josh Says:
    Thanks!
  2. The real Mr. Funk Says:
    *hugs*

    I've wasted so much damned time with these ant tasks.
  3. Jason Says:
    I made exactly the same mistake. Thank you!
  4. Jason Says:
    Thanks, saved me lots of time and swearing!
  5. Piotr Dziubecki Says:
    Hi,

    I was struggling to do similar things but with use of Groovy and Ant builder - it wasn't trivial but the results are pretty the same as yours:

    http://tech4web.blogspot.com/2008/12/mxmlc-ant-flex-task-in-groovy.html
  6. srivastava Says:
    god bless!
  7. forloop5150 Says:
    God bless you!
  8. shane Says:
    Yeah, the example is misleading. Thank you, you certainly saved me some time. Cheers!
  9. Evan Says:
    Thanks for this!
  10. Chandru Says:
    Thanks a lot for this :) saved lot of my time.. though i had already wasted few hours bugging this error.
  11. Eric Says:
    Hi. I'm having this problem and at the risk of sounding like a noob I don't get you solution. do I add those lines to my build file? To the main ant build file? Where do I put the compiler.library-path?
  12. Scott Talsma Says:
    @Eric:
    You add those files to the build file (the .ant file).
  13. Frazko Says:
    is there any way to use the swc file but avoid inserting the entire swc file to the final swf file?? make sense ?

    I was experimenting with a project that just compiles a simple sprite class.. but when using a swc file with the build.. the swf file was a lot bigger in kb..

    thanks!!
  14. Scott Says:
    @franzco: the swc file is compiled into the resulting swf. Try looking into rsl files instead to keep the functionality in a seperate file for deployment.
  15. bakedbeing Says:
    Hiya Scott, hopefully you can help me with a quick query: if you have a swc that contains an importable class with the same name as something you have in your source code structure (say they both offer com.client.project.IntroPage) can you get the compiler to choose the SWC version over the .as version?

    The reason we'd want to do it here is that you're compiling the source code into the swc, and then compiling an application from your source code that needs something from the swc (it has added graphic attributes to your class via the "Class: " export).

    Ta!!
  16. Scott Talsma Says:
    @bakedbeing: I see what you are trying to do, but I don't know of a way (other than inheritance or injection) to pull off what you are trying to do. Really, you are essentially providing the class multiple times. I'm not sure what the compiler rules are around that. Seems like there should be a better design approach.

    That said, maybe look into custom namespaces? You might be able to use the custom namespace in the swc, and then reference it in the code. I've never tried this, but it is worth a shot.
  17. desp2010 Says:
    I don't think i need these compiler options in ant task. Because if we are mentioning compiler options their then what is the purpose of config file which we are mentioning the the load-config option?
    We can easily optimize this through config file. Set all compiler options in config file and then just give that config file in ant task.
  18. Peder Says:
    Is there a way for Flex builder to recognize the dependencies in the build file so you can use Flex builder without having to add all the dependencies to your project again for a second time?
  19. Scott Talsma Says:
    @Peder: Not that I know of. I think for that sort of thing, you may need something more sophisticated like Maven. Check out Flex Mojos as a possibility.
  20. Hello Says:
    Can you please tell me how to compile locale in ANT
  21. Paolo Says:
    Oh this was REALLY useful. Thank you!
  22. Colonel Says:
    Wait, I cannot fatohm it being so straightforward.

Leave a Reply





Powered by Mango Blog. Design and Icons by N.Design Studio