Using Shared Fonts in Flex

| 5 Comments | No TrackBacks

It turns out you can't directly embed a font into a Remote Shared Library (RSL) using Flex. Here's a handy little trick to get around that...

First, some background. I have a Flex application that consists of a main .swf that loads and manages several other "load on demand" .swf files. A user of the application doesn't necessarily need to use all parts of the application, so this modular approach allows them to only download the parts they'll be using. I'm using shared libraries to solve the problem of downloading the same information more than one time when using multiple .swfs in one application. For more information on RSLs in general, check out Roger Gonzalez's great article on the subject.

So I wanted to add a font to an RSL for a few reasons. The font should be able to be changed in only one place, it should only have to be downloaded one time, and all of the loaded .swf files should use the same font. I tried just using the embed tag to add it to an RSL, like this:

<embed source="../fonts/Arial.ttf" newSymbol="mainFont" />

When I went to compile though I was getting a failed to load resource error. Apparently you can't add .ttf files to shared libraries.

I then tried to embed the font directly into the main .swf file. The css for that looks like this:

@font-face {
src: url("../fonts/Arial.ttf");
fontFamily: mainFont;
}

Application {
fontFamily: mainFont;
}

The problem with the css approach is that the font was only appearing in the main .swf file. All of the other .swf files were attempting to use the font, but the font couldn't be found (as demonstrated by all of the text being a small serif font). So, I needed a way to reference the font from the loaded .swfs so that they would use it correctly.

The workaround for this problem, suggested by Roger, is so simple that it's perfect. Create a component that embeds the font via css, stuff that component into a shared library, and then reference the component from every .swf that needs the font. By taking this approach if I ever wanted to update the font I would simple update the shared library, and all of the application would use it.

So, I made a simple component, in Fonts.mxml:

<mx:Canvas xmlns:mx="http://www.macromedia.com/2003/mxml">
	
	<mx:Style>
		<![CDATA[
		@font-face { 
			src: url("../fonts/Arial.ttf");
			fontFamily: mainFont;
		}
		]]>
	</mx:Style>
	
</mx:Canvas>

...added that component to one of my shared libraries:

// inside the "library" tags:
<component name="Fonts" uri="*" />

... added some css for the main .swf file:

global {
fontFamily: mainFont;
}

... and then referenced the shared Fonts component inside every .swf file:

<local:Fonts width="0" height="0" />

I'm using width and height of 0 so that it doesn't actually draw anything (which would affect the layout). I suppose visible="false" would work just as well. But, by using the Fonts component, every single .swf will link to the font from the shared library, and because the global font family specifies that as the font to use, all of the text will be displayed with that font.

Good stuff... Flex handles shared libraries a million times easier than Flash does. I was pleasantly surprised to see this work, to say the least, especially thinking back to how much tweaking the Flash version of the same approach took. Go Flex go!

No TrackBacks

TrackBack URL: http://www.darronschall.com/mt/mt-tb.cgi/50

5 Comments

> Flex handles shared libraries a million times easier than Flash does

Well, I don't agree... You can use the same trick with Flash for the same result.

... and it ends up breaking dynaic/input text fields in some formats, so you fix that and then it breaks so TextFormat, so then you need to create a dummy clip and import that to force sharing. You also have to write your own preloader, make sure you wait a few frames after everything is loaded so it has enough time to initialize, etc. It can be done in Flash, it's just a pain to get right.

From my experience of doing the same thing in both Flash and Flex, it's *much* easier in Flex in general (no more trying to maintain _exclude.xml to exclude shared classes from .swf files), and it doesn't feel as fragile / error prone. Hierarchichal RSL's is a piece of cake in Flex.

It's really a world of difference. Try it and you'll see!

Flex RSL are certainly VERY impressive. But it only hides what happens behind the scene, i.e. loading and initializing everything, then start the application...

Moreover, your experience with sharing fonts in Flex is exactly what you describe of your experience with Flash ;)

Automatically excluding classes however can only be done by Flex (and Ariaware Optimizer).

Regards,

Good point, but they're not quite the same. In Flex I get to specify character ranges in the fonts that get included.. in Flash when you share a font it's either all or nothing.

I realize that the behind the scenes is roughly the same, but I imagine at some point Flex RSL's wil be able to embed .ttf files, eliminating the need to reference the component I made and just use the RSL directly.

Being a Flash developer and using Flex is really the best of both worlds. You know a lot of the nitty gritty details for advanced concepts, but the extra abstraction layer of Flex makes coding faster. I'm having a blast with Flex. :-)

Please give me the source file to know more about that.

Thank you

Leave a comment



About this Entry

This page contains a single entry by darron published on June 15, 2005 7:06 PM.

ASDT auto update, line numbers, code folding was the previous entry in this blog.

Off to get hitched... is the next entry in this blog.

Find recent content on the main index or look in the archives to find all content.

Archives

OpenID accepted here Learn more about OpenID
Powered by Movable Type 5.02