ActionScript.org Flash, Flex and ActionScript Resources - http://www.actionscript.org/resources
Typography in Flash
http://www.actionscript.org/resources/articles/179/1/Typography-in-Flash/Page1.html
JT Paasch
This user is yet to take control of their account and provide a biography. If you are the author of this article, please contact us via support AT actionscript DOT org. 
By JT Paasch
Published on September 9, 2005
 
Tutorial details:
Written by: JT Paasch www.absconditus.com [email:jt@absconditus.com]
Difficulty Level: advanced

Page 1 of 5
Tutorial details:
Written by: JT Paasch www.absconditus.com [email:jt@absconditus.com]
Difficulty Level: advanced

Typography in Flash: Principles (part1)

The role of typography in the overall design of a website is very subtle, often entirely overlooked. Nevertheless, typography plays a substantialrole in the overall design of a website. Poor typographic design will inevitably destroy an otherwise well designed Flash movie. Choosing the right font, the right size, the right color, and other typographic aspects is crucial to a well designed website. So how does one know when to do what with their type?

There is of course a rich tradition of guidelines for typographic design. Unfortunately, many of us haven't had any formal training in typography and consequently find ourselves floundering in the dark as we try to choose the right font or set the right font size. As if that weren't enough, Flash presents a number of limitations to traditional typographic design principles, and so we need to improvise a little to make our typography work well in Flash.

What I want to do here is present some basic guidelines specifically relevant to typographic design in the Flash medium. If you are like me and need some basic principles with which to make concrete decisions about type design, then write these guidelines down and keep them in mind as you design your Flash movies.

This article spans two parts. The first part, the part you are now reading, presents some principles for good typographic design in Flash. We will not look at any particular actionscript examples, but the discussion is tailored entirely to how type works in Flash. The simple guidelines discussed here go along way towards good typographic style in Flash and can often make the difference between an amateur and professional looking site.

In the first section I discuss some of Flash's limitations with regard to typography. Understanding what Flash cannot do is crucial for understanding what Flash can do, and for understanding workarounds. In the second section I look at some basic principles of good typographic style to which Flash is particularly well suited. Such principles help us make the most of what Flash can and cannot do. In the third and final section of this first part, I discuss a few guidelines for how typographic design integrates with the rest of a site's design.

In the second part of this article, I turn to the role that actionscript can play in typographic design. Since this part deals with some practical aspects of writing code, I assume some familiarity with actionscript, though I don't expect you to be a guru. While the emphasis in the first part is on general principles, the emphasis in the second part is on what actionscript can do to push your type design into arenas impossible for print.

In the first section of the second part I look at the TextFormat and CSS objects. With these objects, we are afforded a relatively precise degree of programmatic control over typographic formatting. In the second section of the second part, we will use actionscript to gain even more typographic control: by placing each character of a string in its own movieclip, each character of a string can be manipulated just as any movieclip can. When wrapped up nicely in a class, such code provides possibilities far beyond that of the printed page.

I should say this is not a tutorial on typography in general. Rather, this looks at basic typography as it is applied in Flash. Consequently, I will assume some very, very basic typographic knowledge. That said, however, I tend to over-explain myself, so if you are completely new to typography, read on. If you come to some unfamiliar topic, take a peak at Counter Space to get a very simple introduction. There is also a short list of useful resources at the end of the first part.

1 Flash and Type Limitations

There is a whole world of design possibilities once you understand how to use type well in Flash. But understanding what we can do with type in Flash requires first that we understand Flash's limitations with respect to typography. Let me take this section to enumerate some of the more important limitations Flash presents to typographic design.

1.1 Immature text handling

Flash was originally designed as a tool for animation, not as a tool for presenting lengthy documents as you might find in a medical database or a library. Consequently, Flash's text handling abilities are pretty basic. MX and MX 2004 show some notable improvements in this area, but Flash still has miles to go.

That means that you only have access to a limited number of type properties. You can, for example, set the spacing between lines, but you cannot adjust the space between words. To set some of these other properties to which Flash does not offer immediate access (e.g. the just mentioned word spacing), you must pursue some rather impractical workarounds.

Flash is showing notable signs of improvement with respect to typographic control in recent versions. MX 2004, for example, introduces basic CSS support, a mighty leap forward for typography in Flash. Nevertheless, Flash is still very immature. The more you work with type in Flash, the more you encounter gaping holes in typographic support. It is important to remember just which type properties you have immediate access to, and then work from those. I often keep a list of such properties on my desk.

1.2 Pixelization

In addition to being intrinsically limited, Flash is also limited typographically simply because it is a computer technology. Computer monitors present a whole set of problems for type design. Most importantly, computer monitors display images by a square grid of pixels. That means everything you see on the screen is ultimately made up of only horizontal and vertical lines (or rather, square dots), including curved or sloped lines. In other words, everything is pixelized on the screen.

This feature of the computer screen makes both the size and the positionof a font on the screen very important. For example, curved strokes in a font show up fine at a large size, because many tiny horizontal and vertical lines can be put together to make what appears to be a smooth curve. At a small size, however, the curve must be built with only a few horizontal and vertical lines, and thus the curve often doesn't even look like a curve.

Thus, one should always consider how a font looks when it is pixelized and at different sizes. Fonts which look great on paper often look terrible on the screen, and fonts which often look great on the screen often look terrible on paper. It's not a bad idea to keep a list of fonts which look good on the screen, and at what sizes those fonts look best.

1.3 Anti-aliasing

Further, pixelized screens gave rise to another problem. Early on, when pixels were big enough to be noticeable to your average human eye, the pixelization of fonts looked pretty bad. To compensate, computers started rendering fonts with fuzzy edges. This helped to blur those sharply cornered pixels so as to make the curve appear more a natural curve. This blurring is called anti-aliasing.

Anti-aliasing looks great for large font sizes, so much so that usually one should use anti-aliasing for big sizes wherever possible, even now when computer monitors have such high resolutions. However, with small font sizes, anti-aliasing is not a good thing because the blurring of the edges ends up blurring the lines together, making it difficult to distinguish them. At small sizes, fonts cannot be anti-aliased or they are in danger of becoming completely unreadable.

Flash by default renders all type with anti-aliasing. This was for many years a serious problem because any small text was virtually unreadable. Fortunately, with more recent versions, Flash introduced dynamic and HTML-enabled text fields which could be rendered with no anti-aliasing. MX 2004 has finally given us the ability to turn off anti-aliasing, which is crucial when the type is small.

1.4 Italics and serifs

The pixelization of the computer screen also affects different type styles. The most important type style affected by pixelization is the italic style. Italic type is slanted, and that means it is made of sloped strokes. As was said, pixelization cannot properly display sloped strokes due to the fact that it uses a square grid of pixels for rendering.

Thus, just as curves look okay at large sizes but not at small sizes, so too then does italic type look okay at large sizes but not at small sizes. Similarly, anti-aliasing smaller italic type almost always makes that type even more unreadable than non-italic text of the same size. So if you're using small text, it's not a good idea to use italics, and it's an even worse idea to use anti-aliased italics.

The same rules apply to a font's serifs. Letters have serifs because serifs act to guide the reader's eye smoothly to the next letter. Serifs make reading text much easier and much faster. One can read a large page of serif type more easily than a large page of sans-serif type. However, serifs are often comprised of curved strokes, and thus such curved stroke serifs will only look good on a computer screen if they're big. At small font sizes, serifs lose their definition and end up cluttering the letters. Here too anti-aliasing can complicate things. Avoid serifs and anti-aliasing at small sizes wherever possible.

1.5 Typefaces

Yet another limitation of typography in Flash is that the viewer must have the relevant font installed on their computer. This limits the number of typefaces from which the Flash designer can choose. Just as with pixelization, this is a problem due not so much to Flash but to the way computers work.

To know how to draw the letters on the screen, every computer looks for a file installed on its hard drive which contains instructions for how to draw those letters on the screen. These files are the 'font' files in your fonts directory (e.g. Georgia.TTF in the Fonts folder). Consequently, if your computer doesn't have a particular font file stored somewhere on its hard drive, it can't draw the letters on your screen in that font. In such situations, your computer usually uses an alternative font. The result is that different end users often see different fonts.

Contrast this with type in print, where everybody sees the same font. In the world of computers, people often don't have a font on their computer, and so the type ends up getting rendered in some alternative font. That means that a Flash movie might show up on somebody's computer with its type in a font entirely different from the original designer's choice. On your computer, your Flash movie might look great with Palatino, but on another computer which does not have Palatino on its hard drive, the movie looks terrible with Courier.

That means the designer has to be very careful about the font they wish to use. On the one hand, we are limited to only a few fonts which pretty much everybody has installed on their computer. Those fonts are Courier, Times New Roman, Arial, Verdana, and Georgia. If you use one of those fonts in your Flash movies, you're probably safe as 99% of the people who see your movie will also have those fonts installed on their computers. The type in your movie will show up for them just as it does for you. If you use some other font, though, it is not very likely that most of the people who see your movie will see the type as you see it.

On the other hand, Flash allows us to 'embed' a font in our movies, which means that the font itself gets sent to the viewer along with the Flash movie. That ensures that the viewer will have the font when they look at your movie. If they don't have the font on their computer, it doesn't matter because the movie will use the embedded font to render the type.

However, embedding fonts severely limits your ability to use different fonts and different styles (at least not if you want to keep your movie at a reasonable file size). This applies to different styles and to different fonts. You must embed one font for normal type, you must embed another font for italic type, another for bold type, and still another for a completely different font altogether (e.g. Times New Roman). Each embedded font dramatically increases the size of your Flash movie, so if you want any sort of typographic variation, embedding the fonts will make your movie very large and unwieldy.

Further, embedded fonts are always anti-aliased, even in HTML text fields where type is usually rendered clear, and thus you normally cannot use embedded fonts at small sizes or else they are unreadable. However, if you must embed your fonts, you can use embedded 'pixel fonts' (sometimes called 'screen fonts') for small type. Pixel fonts are fonts designed to be crisp and sharp at a certain small size because every pixel of the font lines up with the screen's pixel grid. Pixel fonts allow you to embed your desired font and it be readable at small sizes. However, pixel fonts have their limitations. If you want to use bold or italic, you must embed a bold or italic pixel font too. And pixel fonts usually only look good at one size, so you often need to embed another font for larger sized text. Thus, pixel fonts or not, embedding fonts severely limits your formatting options.

When choosing your fonts, it is often worth your while to consider whether you really need that 'cool' font you've had your eyes on all week. Any font other than the afore mentioned 'safe' fonts requires that you embed it in your movie. But as just said, this can either limit you to a single font at a single size, or it will make your movie very large. In many cases, the site's design will not suffer by using one of those boring 'safe' fonts but will rather be better off because it affords you far more diverse formatting capabilities. Due to Flash's limitation with typefaces, good typographic design often means using those traditional 'safe' fonts with varying font sizes, colors, and formatting rather than using some hot new font which must be embedded.

1.6 Loss of layout control

Another factor in Flash's typographic limitations is that the designer loses some control over the layout of a movie. There are a number of things at work here: computer monitors are different sizes and resolutions, browsers can be resized to be narrower or longer, text can come from a dynamic source (e.g. a database), end users may not have the proper font installed, and so on. All of these factors mean that the movie might look different on the end user's computer than it does for you.

Contrast this with type design for print. The printed page maintains its layout for everybody who looks at it. The page will always look the same size at the same resolution, the user cannot resize the page, the text is not dynamic, and the reader will always see the same font. The layout for websites, on the other hand, is much more fluid and is almost guaranteed to change from end user to end user. That nice rosy pink color on my old low-res monitor might appear blood red on my neighbor's high definition flat panel display. The web designer loses some control over the layout of their designs.

This means that you need to approach type design in Flash with flexible design principles, not static ones. Design so that your type will look good no matter how big the site appears. For example, rather than design your site to look good with 9pt body text and 12pt header text, design your site to look good with body text that is 3/4th the size of header text. That way the text will look right if things get resized. Designing with a mind for change will help preserve your site's good design when things start to look differently from end user to end user.

Understanding these limitations is crucial for understanding how to use type in Flash to maximal advantage. Keep these limitations in mind as you work and ask yourself if your typographic design will suffer if (and when!) any of these limitations come into play. With a constant awareness of these limitations, you can more appropriately use type for good design, focusing your attention on those principles which are applicable to Flash typography. With these limitations in mind, we turn next to some basic typographic design guidelines which are particularly useful in Flash.

2 Typography basics

Now that we've looked at some of Flash's important limitations to typographic design, we can look at what you cando with type in Flash. The set of principles in this section are very basic principles of good typographic style, but they are principles which go a long way in Flash.

Since Flash is still immature in its typographic abilities, it often doesn't render eye-popping text on its own. Instead, the type usually appears pretty primitive. The designer, then, has to be extra careful in following good typographic principles so as to make Flash text look good. Following a few basic principles can really improve the type in your movies. In this section I will discuss these basic typographic design principles.

2.1 Readability

The fundamental principle in any typographic design is this: the type must be readable. The goal of any typographic design, then, is to make the type as readable as possible. One should pursue readability above all else in their type designs.

One might think the goal of typography is to make the type look 'cool'. It is precisely at this point that the essence of good typographic style can be most clearly seen. Typographic design is subtle, it serves a very functional purpose: namely, that the reader can read the type as easily and clearly as possible. The stuff which the viewer should get from type is the content of the text, not the look of the text. The look of the text is as it is only to make the content more apparent.

The typographic designer's work, then, should sink into the background and remain unnoticed. The viewer should notice the content of the text, not the look. If the typographic design is poor, the viewer will be distracted and not read what they're supposed to read at all. The cause of this may be that the font is simply ugly and thus makes the reader wretch when they see it, or it may be that the font is so interesting and 'cool' that the reader never gets around to reading the substance of the text. Either way, if the reader does not focus instantly and easily on the content of the text, the typographic design is poor.

Thus, in good typographic design, the look of the text remains entirely at the service of the content of the text. The text looks a certain way so the viewer can access the contentin the easiest and clearest possible way. I can't stress this enough. Your primary goal as typographic designer is to make the text as readable as possible.

This means choosing the right font, the right color, the right size, the right letter and line spacing, and so forth. If any of these aspects are not correct, the reader will have trouble reading the text. For example, imagine reading a 500 word company description in 96pt Arial type. That simply wouldn't work. The only aspect amiss, presumably, is the font size, but it's enough to make the whole thing entirely unreadable. This is an extreme example, of course, but it serves to illustrate the point that choosing the right type features greatly enhances the readability of a text. The principles discussed throughout this article are all aimed at improving readability, they are aimed at helping the designer choose the type features which make the text the most readable.

2.2 Spacing

One major factor in a text's readability is its spacing. Letters appear in space, and so there are many different kinds of spacing that affect the readability of type. The space between letters is one such kind of spacing. The space between words is another, and the vertical space between each line is still yet another kind of spacing which affects readability.

In principle, the smaller your type is, the greater the spacing should be. Contrariwise, the larger your type is, the lesser the spacing should be. For example, if you are using 7-9pt type, set the line spacing to a generous amount. 8pt type is much easier to read with line spacing at 1.5 than at 1.1. Fortunately, Flash lets us set line spacing with the TextFormat object (or with CSS in MX 2004). I will discuss the TextFormat object in part two.

However, Flash does not let us set the spacing between letters (although you can do this with static text in the IDE). Small type in Flash, consequently, usually ends up having its letters look a bit smashed together. Be sure not to make your type so small that the letter spacing becomes too tight and jumbled. Sometimes choosing a font with fixed width letters can help at small sizes. A font with fixed width letters is a font which draws each letter at exactly the same width. The result is a very evenly spaced font.

However, fixed width fonts sometimes look bad. The reason is that in every alphabet, some letters are very wide (e.g. a 'w' or an 'm') and some letters are very narrow (e.g. an 'i' or a 't'). Spacing such letters evenly can make them look unbalanced. For this reason, non fixed width fonts automatically space their letters according to the proportion of each letter's size, and this gives the font a more even feel.

In some cases, a fixed width font will not do because it will look unbalanced. In other cases, a non fixed width font will not do because its automatic spacing will make the letters look jumbled. In general, it is a good idea to be generous with spacing in Flash. Be generous with your type's line height, and be generous with letter spacing wherever possible. Additionally, be generous with the space surrounding the text wherever possible.

2.3 Color and contrast

The color of type in relation to its background and in relation to the viewer is also a crucial factor in readability. If the color of the type is only a shade off that of its background, the type will be very difficult to read because the viewer will have trouble clearly distinguishing the letter shapes (remember that the letters aren't all that clear on a computer screen anyways due to pixelization).

But if your type color is opposite that of its background, the type will be very easy to read. In principle, the more the type color contrasts with its background color, the easier it is to read. Remember too that many people are color blind, and what looks like a contrast to you may not be for others. It's always a good idea to check your colors against different kinds of color blindness (e.g., at http://www.pixy.cz/apps/barvy/index-en.html).

Good type design, then, will always implement a strong contrastbetween the type and the background. You can achieve contrast in a number of ways. You can achieve contrast by using complimentary colors (i.e. colors opposite each other on the color wheel). Orange text will stick out great against a blue background because orange and blue are complimentary and thus opposite colors. The same is true of the converse. You can also choose more subtle forms of color complimentarity to achieve contrast. For example, you might use split-complimentary colors, or you might use the strong color of an analogous color scheme against the weak color.

You can also use value (how light or dark it is) and saturation (how much black or white is in the color) to achieve contrast. In terms of color value, a dark color will contrast with a light color, and vice versa. You can even use the same color, with the type dark and the background light, provided the difference in value is strong enough to create contrast. Saturation can be used to create contrast in just the same way. You can also use the neutral colors (black, white, grey, brown) to provide contrast. Black contrasts with any light color, and white contrasts with any dark color.

In any case, be sure to use contrast in your typographic design. The reader must be able to easily distinguish the text from its background. You don't want to make their eyes exhausted by forcing their eyes to maintain too high a level of concentration, just to make out the text against its background. Use contrast to your advantage.

2.4 Different fonts and different sizes

Contrast can also be achieved with different fonts and different font sizes. Here, however, the contrast is not so much between the text and its background but between different portions of text. Here you can use different typefaces and different sizes to create contrast to clearly delineate different bits of text from each other. This is very useful in helping the reader navigate your text. The more clearly the different parts are demarcated, the easier the reader can work their way through the relevant bits.

Varying and contrast font sizes can go a long way in clearly marking off distinct portions of text. For example, a large font size might indicate a heading, while a small font size might indicate body text. With a strong contrast in size, you clearly distinguish different parts of the text, and the reader immediately understands that the big text serves one function (a heading) and the little text serves another function (body text). By contrast, imagine if your headings were exactly the same size and weight as your body text. The reader would have a difficult time recognizing the headings as headings. Thus, contrasting different bits of text with varying size goes a long way to making your type more readable and more accessible.

You can also use different typefaces to create contrast. You might use one typeface for headings and another for body text. The contrast will here too help the reader clearly differentiate parts of the text. That said, however, It is a general typographic rule to use no more than two fonts in the same document, and one should be sans-serifed while the other is serifed. Do not, then, mix two sans-serif fonts or two serif fonts on the same page. Instead, use different sizes to give further levels of differentiation. Additionally, you can use bold and italic text to add further levels of distinction.

Keep these basic guidelines in mind as you design with type. They are some of the most basic typographic design principles, but they are principles which go a long way in Flash design. Since Flash is fairly immature and does not always render stunningly beautiful text on its own, the burden is even more on the designer's shoulders to ensure the text looks good enough to be easily readable. You can greatly improve your type's readability simply by following some of these guidelines.

3 Designing with Type

Thus far we've looked at Flash's limitations and some basic typography principles which go a long way to making type in Flash all the better. But type is also part of your overall site design in just the same way as lines and color. Perhaps we can think of type as one of the paints with which we paint our Flash movies. It is, then, important to understand how your typographic design works with the rest of your movie's design. In this section, I will discuss a few guidelines for using type to design your site, guidelines which help the type play a major role in your movie's overall design and ensure that your typographic design is consistent with the rest of your movie's design.

3.1 Character Axis

The letters in fonts are designed according to at least one axis. The axis is defined by the angle of the pen's blade when the letter stroke is drawn. By the pen's 'blade' I mean the thin, wide tip of a fountain pen. By holding the blade at the same angle all the while the letter is drawn, one gets thin strokes and thick strokes, due to the thin and thick shape of the pen's tip.

A font has a vertical axis if the font designer kept the pen's flat tip vertical on the page when the letter was drawn. If the font designer kept the pen's flat tip at a slight angle to the page, the font has a diagonal axis. Additionally, a font can have more than one axis if different strokes of each letter are drawn with the pen held at different angles. These can further be broken down into a major and minor axis or axes.

The axes of a font are important because the axes of a font should line up with the axes of your movie's design. For example, if your movie is laid out in a very rectangular fashion (and thus it has horizontal and vertical axes), choosing a font with strong horizontal and vertical axes will ensure that your type fits nicely with your movie.

I often find it helpful to imagine (or even draw) the lines of my font axes and the lines of the axes from the rest of my movie's design. That often helps me see very clearly just how the structure of the font letters is working with the structure of the rest of the site. Sometimes the axes of the font can even provide important connecting 'lines' between parts of the movie's stage. And sometimes a diagonal font axis or two can provide an interesting diagonal aspect to an otherwise rectangular site layout.

So be sure to consider the major and minor axis of both your font(s) and your site, and use this to make your designs all the more interesting. If your site is laid out in squarish fashion, then a squarish font will probably fit well, since the axes of the font and the rest of the site are consistent. At the same time, perhaps using a different font axis will add another important axis to your overall site design. Be aware, however, that a font with a major axis that doesn't work with your overall site design will look bad and will not 'feel' right.

3.2 Stroke width

Closely related to the major and minor axis of a font is the stroke shape and width. Some fonts have thick strokes along their major axis while others have thin strokes. A thick stroke on one axis will emphasize that axis. A thin stroke on that axis will de-emphasize that axis. If you want a very strong vertical feel to your site, then design the layout with a strong vertical axis and choose a font with a strong vertical stroke on the major axis.

Further, a thick stroke provides a more obvious shape. A thin stroke is more like a line to the viewer, but a thick stroke is more like a rectangle. This shapely character of letter strokes can be used to your advantage. If you have a site full of rectangles, then perhaps a font with strong, rectanglularly shaped strokes might fit in well. On the other hand, using a font with thick strokes in a site otherwise containing only thin lines might provide an important bit of contrast. You can use this to emphasize (or de-emphasize) the type and make it stick out more clearly (or vice versa).

Remember that a font's stroke width helps to define the shape of the letters, and those shapes can be used in your overall design. Be aware of the stroke width as you design and try to put the stroke width to work in your movie's comprehensive design.

3.3 Contrast and text group shape

I've already mentioned contrast with respect to type's readability. But your type's contrast can also play an important role in the overall design of a site too. Consider a site which is nothing but a pure white space. Black text would strongly contrast with the white background and thus would jump out immediately to the end user. Or you might make all the text grey except the one bit you want emphasized, which might be black, and this would give the black type another level of importance. The darker text is in such cases going to serve to define the relevant spaces on the movie's stage. You can then use the text -- rather than lines -- as markers and boundaries for different areas on your site. Simply by using contrast, you can enable the type to do the work of the line.

Further, the outline of a text block forms a shape, and that shape can be utilized in your design too. Consider the white and black example again. If there is nothing in the white space except the black text, the text blocks will provide the only shapes on the movie's stage. These text blocks can then be arranged and used just as any shape: for marking boundaries between sections, for delimiting a certain bit as a single unit, and so forth. By using strong contrast, you empower your text to function as a shape and thus it can play a major structural role in your overall design.

3.4 Design with type from the start, don't fit it in later

All of this is to say that type can be just as much a design tool as lines, shapes, or color. Type is one of the paints with which you paint Flash movies, and thus you can use it as such. Use type to mark off the layout of your movie's interface, use it to form shapes, use it to fill out shapes and lines, use it to connect different sections in your web site, use it to provide an important axis to your site, use it to contrast or balance your overall site design, and so on. There's no end to what you can do once you start to think of type as one of your Flash movie building blocks.

Consequently, you can think about type from the earliest stages of brainstorming. If type plays such an important role in the design of your movies, then one needn't design the site first and then 'decide' on the type (e.g. font, size, and so forth) later. That makes the type superfluous to the whole site, and that will in turn come across to the viewer. If the type design feels superfluous or just 'added on' later, then the type itself will feel superfluous, and the viewer probably won't spend much time reading the type, if they read it all. Rather than fit the type in later, start with the type as early as you start with color and layout. The type is, after all, just as much a part of the layout as the color.

With that, this first part comes to a close. We have discussed a number of practical principles and guidelines for typographic design in the Flash medium. By keeping these principles in mind as one designs, they can make more appropriate typographic decisions. By applying these principles to the type in our movies, we can better harness type as one of the central building blocks of our work. A big part of what the site 'says' to the viewer, after all, is usually said simply with type.

But we needn't stop here. One can continue to push these principles into our use of typography, especially if we use actionscript. In part two, I will look at a few ways that actionscript can give us more control over the type in our movies. This in turn empowers us to employ these principles all the more, in ways impossible on the printed page. Here Flash opens itself up as an innovative medium for typography.

Part 2. Typography in Flash: Actionscript

Resources

Robert Binghurst, The Elements of Typographic Design
This beautifully designed and well written text is the bible of basic typographic design. Whether you only use type when writing essays for university classes or use type in a professional design studio, this text will change the way you think about how you put any letters on the page.

Counter Space
http://counterspace.motivo.com/
This Flash site provides a very comfortable and semi-interactive introduction to the basic concepts of typography.

Val Casey on Typography
http://www.valcasey.com/webdesign/typ.html
Val Casey's site is an excellent summary of design principles, keeping it simple, beautiful, and to the point. The section on typography is equally as informative, simple, and insightful.

Fontsite's Rules of Typography
http://www.fontsite.com/Pages/RulesOfType/ROT1-08.html
This set of rules, adopted from Sean Cavanaugh's Digital Type Design Guide, are general enough to apply to digital media in general. These rules work for HTML just as much as for Flash.

Adobe Type
http://adobe.com/type/
Adobe is a massive force behind digital type, so their site is a great place to start any search for fonts. The collection on this site is massive.

Microsoft Type
http://www.microsoft.com/typography/
Although Microsoft is set on making their typographic technology the typographic technology on the web, there is a lot of good information here, especially in the 'Resources' section.

Type Design for TV/Video
http://www.typographer.org/2004_03_01_digests.html
This article provides some basic guidelines for type design in video, many of which apply to Flash itself, as well as to using video in your Flash movies.


Copyright 2004 JT Paasch.

Page 2 of 5

Typography in Flash: Actionscript

In part oneof this two part series on typography in Flash, we looked at a number of important guidelines and considerations for designing with type in Flash. Flash is an unique medium that has its own set of typographic limitations, and one must consequently take extra care to design according to good typographic style principles.

But Flash is also a medium with its own set of typographic abilities which aren't available to print. Here is where Flash reveals itself as a unique medium for typographic design. The purpose of this second part of the series is to explore some of the ways Flash allows us to take our typography beyond those techniques common to the traditional printed page. In particular, it is actionscript which opens up these possibilities, and thus it is actionscript which allows us to take our typography to the next level.

In this article we will cover some important techniques for using actionscript to programmatically drive our typographic designs. In the first section we will look at various ways to use actionscript to format type. In the second section we will explore a way to expose the characters in a text string to the full range of actionscript's animation powers. The techniques discussed in this article can serve as a foundation for pushing our programmatic control even deeper into our typographic style.


1 Actionscripted type formatting

As mentioned above, it is actionscript which lets us take our typographic design to the next level. Actionscript provides some important means by which we can control our type programmatically. On the one hand, we can use actionscript to handle type formatting in sophisticated and precise ways. On the other hand, we can use actionscript to turn our type into important entities in our movie design. For example, with actionscript we can format our type, animate our type, break up the characters, and so forth. In this section, I want to discuss a few helpful guidelines for using actionscript to format type. I will assume some basic actionscript skills in this section, though I don't expect you to be a guru since the emphasis here is not so much on how to write specific scripts as it is on the general techniques for using actionscript to control type.

1.1 The TextFormat object

In Flash MX and higher, you can control the formatting of each individual character with the TextFormat object. This object is consequently a very powerful tool. With the TextFormat object, you have a relatively high degree of control over the look of your textfields, and it can even achieve some interesting effects.

Using the TextFormat can be a bit strange the first time around, but basically a TextFormat object is nothing but a bundle of formatting properties (e.g. font family, font size, font color, and so forth) which is then applied to a text field. What might seem odd about this is that the TextFormat object is just a bundle of properties, completely apart from any text field.

This is, in fact, advantageous because it means you can create your formatting properties only once and then apply them to many different text fields. It also lets you keep your formatting in one place, so changing the look of many text fields can be accomplished by changing one value (namely, that of the TextFormat object) rather than changing the value in each and every textfield.

In any case, the important feature of the TextFormat object is that it is distinct from a textfield. Thus, first you create a TextFormat object, and only later do you apply it to specific text fields. The first step in using a TextFormat, then, is to create a TextFormat object. The following line of code creates a new TextFormat object and stores it in a variable named myFormat:

[as]var myFormat = new TextFormat ();
[/as]

From this point forward, we will refer to the TextFormat object by the name of the variable, namely myFormat. You can, of course, change the name of the variable to whatever you like, but whatever name you choose, that is the name with which you reference the TextFormat object.

Now that we have a TextFormat object, we need to fill it with formatting properties. Once we fill this object with formatting properties, we can then apply it to a textfield. In this case, let's set the font to 'Arial'. To do that, we simply write the name of the TextFormat ( here it is myFormat), then a dot, then the name of the property we wish to define, then an equals sign, and lastly the value. Thus:

[as]myFormat.font = "Arial";
[/as]

Here we set the 'font' property to a value of 'Arial'. Note that the font name is in quotes. With TextFormats, any value except numbers should be in quotes.

Now let's set the size to 10pt. The procedure is the same: the TextFormat name, then the property name, then the property value:

[as]myFormat.size = 12;
[/as]

This line of code sets the 'size' property to 12, i.e. 12pt. Notice that here we did not put the number in quotes because it is a number.

Next, let's set the color to blue. In Flash, colors are usually defined as hexadecimal numbers, and so here our color will be 0x006699:

[as]myFormat.color = 0x006699;
[/as]

There are many formatting properties available to TextFormat objects. You can set line spacing, first line paragraph indentation, left and right side margins, and a whole host of other formatting properties. Here we'll just leave our TextFormat as it is, but for a full list of properties, see the Actionscript Dictionary in your Flash Help menu (or online). If you navigate to the TextFormat object, you will see a list of available properties along with their descriptions.

Now that we have a TextFormat object (named myFormat) with some formatting values (in this case, the font, size, and color properties), we can apply this TextFormat to a text field. Every text field has available to it a method called setTextFormat (). We use this method to apply a TextFormat to a text field.

Suppose we have a text field named myTextField. We can then invoke the afore mentioned setTextFormat () method to apply our TextFormat object to the text field. The setTextFormat () method takes one argument inside the parentheses: the name of the desired TextFormat object. In our case, then, the code looks like this:

[as]myTextField.setTextFormat (myFormat);
[/as]

The procedure is as follows. First we specify the name of the text field (in this case, myTextField), then we write a dot, then we write the name of the method (in this case, setTextFormat ()), and finally we write the name of the TextFormat object we wish to apply to this text field. Once we have done that, the formatting properties contained in our TextFormat object will be applied to the text of the text field. The text of myTextField will consequently show up as blue 10pt Arial text.

You can also designate that the TextFormat object should be applied only to a specific range of characters in a text field. For example, you can designate that the TextFormat object should be applied only to characters 3 - 6 of a textfield. To specify the beginning and end character to which a TextFormat should be applied, apply the TextFormat object to the text field with the setTextFormat () method in just the same way as before, but inside the parentheses list the beginning and ending character number just before the name of the TextFormat. For example, to apply our myFormat TextFormat object to characters 3 through 6 of our myTextField text field, we would use this line of code:

[as]myTextField.setTextFormat (3, 6, myFormat);
[/as]

That line of code thus tells Flash to apply the properties in the myFormat TextFormat object to characters 3 through 6 of the myTextField text field. If you omit the ending character, then Flash will apply the TextFormat only to the character specified by the beginning number. Thus, this will apply the myFormat TextFormat object only to the third character of the myTextField text field:

[as]myTextField.setTextFormat (3, myFormat);
[/as]

TextFormats are additive, not destructive. That is, when you apply a TextFormat to a text field, it does not completely reset all the text field's formatting properties and then apply only those properties which are contained in the TextFormat. Rather, it leaves any properties already applied to the text field untouched and simply adds its new properties to the text field. Accordingly, you can apply multiple TextFormat objects to any text field, layering as many properties as you need.

There is a second way to apply a TextFormat to a text field. Rather than use the setTextFormat () method to apply a TextFormat to a text field, you can use the setNewTextFormat () method. This latter method is just the same as the former, but the former will only apply the TextFormat properties to any existing text in the text field. It will not apply those properties to any new text which might appear later (if, for example, a script changes the value of the text field or appends some new text to the field). The setNewTextFormat () method, however, will apply the TextFormat properties to any new text which might appear later. Some situations require the setTextFormat () method, and other situations require the setNewTextFormat () method.

Before moving on, I should mention a few limitations to the TextFormat object. The TextFormat object only works with dynamic and input text fields. We cannot apply a TextFormat to a static text field simply because we do not have access to static text fields by actionscript. The only way to edit static text fields is in the authoring environment, in the IDE.

Further, if you are using embedded fonts, then TextFormats can sometimes cause headaches. When you embed a font and set a TextFormat's font property to that embedded font, you tell Flash to use that font and only that font. If Flash cannot find that font (because you forgot to embed it, or you named it wrong, or whatever), then absolutely nothing shows up in the text field. When you are not using embedded fonts, if Flash cannot find the specified font it will select another, and so with non-embedded fonts you always see a font, even if it's the wrong one. But with embedded fonts, Flash will use only the specified embedded font.

A result of this is that setting the bold and italic properties with a TextFormat has no effect on an embedded font. The key here is to remember that a normal font, the same font bolded, and the same font italicized, are each different fonts. Embedding a normal Arial font does not also embed Arial Bold, nor does it embed Arial Italic. Thus, you can change the size and color of an embedded normal Arial text field with a TextFormat, but you cannot make an embedded normal Arial text field bold unless you set the TextFormat's font property to the different Arial Bold font (which must also be embedded).

Let's consider an example. Suppose that you embed the normal Arial font, and then apply it to a textfield. The text field will then show up in the normal Arial font, just as expected. Suppose now that you create another TextFormat, set the 'bold' value to true, and then apply it to characters 3 - 6 of the text field:

[as]var myOtherFormat = new TextFormat ();
myOtherFormat.bold = true;
myTextField.setTextFormat (3, 6, myOtherFormat);
[/as]

Here we created a TextFormat called myOtherFormat, we set the 'bold' property to true, and then we applied it to characters 3 - 6 of the myTextField text field. If you view your movie, you will see no change: characters 3 - 6 of the text field will not be bold. The reason is, as said above, that a bold typeface is a different font from the normal typeface. To make characters 3 - 6 bold, you must embed a bold font and then apply that new font to characters 3 - 6. Suppose that we have embedded our bold font with the name 'Arial Bold'. The code would thus be this:

[as]var myOtherFormat = new TextFormat ();
myOtherFormat.font = "Arial Bold";
myTextField.setTextFormat (3, 6, myOtherFormat);
[/as]

Here we created a TextFormat called myOtherFormat, we set the font to the embedded bold font, and then we applied it to characters 3 - 6 of the myTextField text field. Notice that we did not set the 'bold' property to true. This is because the font itself is bold, so we don't need to do anything else. Remember that normal, bold, and italic typefaces are all different fonts, and thus if you are embedding your fonts, you must use the different fonts for bold and italic.

As mentioned before, using embedded fonts provides the advantage that you know the end user will see the proper font. But here we have seen that it can be cumbersome to use embedded fonts if you need to do any sort of advanced formatting. Additionally your movie's filesize increases substantially with each embedded font.

If you need to use any sort of advanced formatting capabilities, I suggest considering using one of the 'safe' fonts (Arial, Verdana, Times New Roman, Georgia, and Courier) without embedding your fonts, and just use HTML fields. With HTML fields you can use some basic HTML tags for semi complex formatting purposes, you can also use TextFormat as much as you like, and HTML fields always render without anti-aliasing, so the text is clear. I find that I often gain more with one of the 'safe' fonts and HTML text fields than I do by embedding that 'cool' font I initially wanted: I gain a much smaller movie, clearer text, and far more advanced formatting capabilities.

(Note, however, that the Macintosh OS and a few Linux desktops such as KDE automatically anti-alias any type -- even a Flash movie's HTML text fields -- at 10pt or higher unless the user changes that default value. Consequently, your text may not appear sharp and crisp on every desktop. Fortunately, the smaller font sizes (9pt and below) which really need no anti-aliasing to be sharp and clear are not anti-aliased on such desktops.)

All in all, though, the TextFormat object makes for a powerful way to control type formatting with a relatively high degree of precision. It lets us keep our formatting properties distinct from our text fields for clearer formatting management. It further allows us to apply multiple layers of formatting properties to specific characters, thereby giving us some formatting control in highly specific ways.


Page 3 of 5

1.2 CSS with AS 2.0, and with AS 1.0

Actionscript 2.0 introduced a new CSS class which allows us to use some basic CSS in our Flash movies. This is a massive step forward for typography in Flash because it allows even greater flexibility for formatting control. There are many excellent tutorials about using CSS in Actionscript 2.0 (this one at actionscript.org, for example), so I won't discuss how to use the CSS object in Actionscript 2.0 here.

But CSS is not limited to Actionscript 2.0. It is easily accomplished in Actionscript 1.0 too. The reason is that the CSS properties supported in Actionscript 2.0 correspond to the same properties supported by the TextFormat object. The only difference is that some of the CSS properties have slightly different names than they do in the TextFormat object. For example, the 'text-align' CSS property corresponds exactly to the 'textAlign' TextFormat property.

Making a CSS class in Actionscript 1.0 is thus a fairly trivial matter. You simply need to write a class which takes CSS properties, matches them up with the corresponding TextFormat properties, and then apply that TextFormat to the text field. Before Actionscript 2.0 was released, CSS was available in Actionscript 1.0 via this very technique (e.g. Thoth and DENG both provide CSS for Flash MX). For more information on using CSS with Actionscript 1.0, see my Actionscript 1.0 CSS.

In any case, using CSS in Flash is a great way to maintain a fair measure of control over type formatting. With CSS you can control your formatting externally and centrally: all in one document (or in one set of documents). This allows you to manage type formatting in one place (the CSS document) and deploy that formatting throughout your movies where needed.


2 Actionscripted type design

In addition to using the TextFormat object and CSS to control formatting, you can also use actionscript to do a whole number of things to the characters in a text field, things which aren't possible in other type mediums. With Flash, you can make your characters move, dance, flicker, disappear, transform, or whatever else your imagination can conceive. You can control character spacing with interesting algorithms, or even animate character spacing based on some relevant information. This is precisely where Flash comes into its own as a medium for typographic design. You can't do this stuff on the printed page, and you can't do it with HTML. Here Flash opens up a whole new world of typographic design considerations.

In this section I'll look at a basic technique for exposing the characters of a text string to actionscript's full range of Flash's animation powers. The technique is simple: put each character into its own movieclip so that you can control each character just as you would any other movieclip. We'll look at some code for doing just that, and we'll wrap it up in a simple Actionscript 2.0 class to provide a foundational typography API. This makes working with type in this fashion just as easy as working with text fields.

2.1 Break up a string into individual movieclips

The first thing to do here is break up a text string and put each character in its own movieclip. By putting each letter of a string into its own movieclip, you can then use actionscript to control each movieclip separately, or control them all in tandem. Then you can use actionscript to animate any of those characters just as you would any other movieclip: you can move them, scale them, rotate them, fade them, and so forth.

2.2 Keep the character movieclips in an array

There are many ways of breaking up a string and putting each character in its own movieclip. You are of course free to accomplish this however you like. The technique I have found to be most useful is this: place all the character movieclips into a single array. This gives you an array which acts much like a string.

You can then control the whole array as a single entity, just as you would control a single string. You can also access any given character by its array index, just as you would access any given character in a string by its character index. Applying transformations to any character is then as simple as applying a transformation to a particular item in the array. Similarly, applying transformations to all the characters at once is as simple as looping through each array item.

2.3 Implementing standard type methods

You can easily wrap all this up in a class which does the hard work for you. You can then implement standard text field methods for that class just as if the class were a text field. For example, you could implement a setTextFormat () method which loops through each character movieclip and applies a TextFormat object to that character. You could then define a text format and apply it to your array of character movieclips with the setTextFormat () method just as you would with a text field.

Let's create a basic Actionscript 2.0 class as an example. Let's call our class Typeset, since the class will let us set each character in the type however we like. The first step then is to define the class. We will need two class variables: typeString and typeArray. The typeString variable is the string we want to break up and put each character into its own movieclip. The typeArray variable is the array where we will store all our character movieclips:

[as]class Typeset {
        private var typeString:String;
        private var typeArray:Array;
} // end Typeset class
[/as]

Next, we need to define the constructor function. The user will pass the typeString value to the constructor as a parameter. The constructor will then invoke the init () method, which assigns the specified string to the typeString variable:

[as]class Typeset {
        
        private var typeString:String;
        private var typeArray:Array;
        
        function Typeset (_typeString:String) {
                this.init.apply (this, arguments);
        } // end constructor
        
        public function init (_typeString:String):Void {
                typeString = _typeString;
        } // end init () method
        
} // end Typeset class
[/as]

To use the class, then, we simply instantiate the class, passing the desired string as a parameter:

[as]var type:Typeset = new Typeset ("Hello World");
      [/as]

Next, of course, we need to break up the string and put each character in its own movieclip. Let's create a method called buildTypeset () to do this work, and we'll make the init () method invoke this method:

[as]class Typeset {
        
        private var typeString:String;
        private var typeArray:Array;
        
        function Typeset (_typeString:String) {
                this.init.apply (this, arguments);
        } // end constructor
        
        public function init (_typeString:String):Void {
                typeString = _typeString;
                buildTypset ();
        } // end init () method
        
        private function buildTypeset () {
                // break up typeString,
                // putting each character into its own clip
        } // end buildTypeset () method
        
} // end Typeset class
[/as]

To break up the string, we need to loop through each character of typeString and get the value of each character. Here's just the buildTypeset () method, looping through each character in the string and storing the value of that character as a temporary variable called thisChar:

[as]private function buildTypeset ():Void {
        // break up typeString,
        // putting each character into its own clip
        for (var i = 0; i < typeString.length; i++) {
                // store the current character as 'thisChar'
                var thisChar = typeString.charAt (i);
        } // end looping through typeString
} // end buildTypeset () method
[/as]


Page 4 of 5

Next we need to create a movieclip to contain each character. The next line in our buildTypeset () method then will create a movieclip for each character:

[as]private function buildTypeset ():Void {
        // break up typeString,
        // putting each character into its own clip
        for (var i = 0; i < typeString.length; i++) {
                // store the current character as 'thisChar'
                var thisChar = typeString.charAt (i);
                // create a movieclip
                _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
        } // end looping through typeString
} // end buildTypeset () method
[/as]

Here we simply create a movieclip at the next highest depth for each character in the string. Of course, we need to assign each movieclip to our typeArray:

[as]private function buildTypeset ():Void {
        // break up typeString,
        // putting each character into its own clip
        for (var i = 0; i < typeString.length; i++) {
                // store the current character as 'thisChar'
                var thisChar = typeString.charAt (i);
                // create a movieclip in the array
                typeArray[i] = _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
        } // end looping through typeString
} // end buildTypeset () method
[/as]

Next, we need to create a textfield inside each movieclip:

[as]private function buildTypeset ():Void {
        // break up typeString,
        // putting each character into its own clip
        for (var i = 0; i < typeString.length; i++) {
                // store the current character as 'thisChar'
                var thisChar = typeString.charAt (i);
                // create a movieclip in the array
                typeArray[i] = _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
                // create a textfield inside that movieclip
                typeArray[i].createTextField ("_txt", _root.getNextHighestDepth (), 0, 0, 100, 100);
        } // end looping through typeString
} // end buildTypeset () method
[/as]

Here we create a text field with the name "_txt" in each movieclip. Thus, to reference the movieclip of any character x in our string, use this inside our class:

[as]typeArray[x];
      [/as]

And to reference the textfield of any character x in our string, use this code inside our class:

[as]typeArray[x]._txt;
      [/as]

The last step is to set the value of each textfield to the value of the string's character, which is here thisChar:

[as]private function buildTypeset ():Void {
        // break up typeString,
        // putting each character into its own clip
        for (var i = 0; i < typeString.length; i++) {
                // store the current character as 'thisChar'
                var thisChar = typeString.charAt (i);
                // create a movieclip in the array
                typeArray[i] = _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
                // create a textfield inside that movieclip
                typeArray[i].createTextField ("_txt", _root.getNextHighestDepth (), 0, 0, 100, 100);
                // set the textfield's value to 'thisChar'
                typeArray[i]._txt.text = thisChar;
        } // end looping through typeString
} // end buildTypeset () method
[/as]

There, now this method takes the typeString string, breaks it up, and places each character in a movieclip. The movieclips are all stored in an array so that we can easily access each clip by the character's index number. So if we want to access the third character in the string, we can access its movieclip by an array index of 3:

[as]typeArray[3];
      [/as]

Our class thus far reads like this:

[as]class Typeset {
        
        private var typeString:String;
        private var typeArray:Array;
        
        function Typeset (_typeString:String) {
                this.init.apply (this, arguments);
        } // end constructor
        
        public function init (_typeString:String):Void {
                typeString = _typeString;
                buildTypset ();
        } // end init () method
        
        private function buildTypeset ():Void {
                // break up typeString,
                // putting each character into its own clip
                for (var i = 0; i < typeString.length; i++) {
                        // store the current character as 'thisChar'
                        var thisChar = typeString.charAt (i);
                        // create a movieclip in the array
                        typeArray[i] = _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
                        // create a textfield inside that movieclip
                        typeArray[i].createTextField ("_txt", _root.getNextHighestDepth (), 0, 0, 100, 100);
                        // set the textfield's value to 'thisChar'
                        typeArray[i]._txt.text = thisChar;
                } // end looping through typeString
        } // end buildTypeset () method
        
} // end Typeset class
[/as]

That much is the basic core of the class. It does the work of breaking up a string into its individual characters and placing each of those characters into its own movieclip. The class stores those movieclips internally as an array so that each character clip is easily accessible simply by its index number. From this point on, we can implement any other features we like simply by writing another method.

If you test this class, you'll notice that all the letters are jumbled together. The reason is that all the movieclips are created at (0, 0). Obviously it would be useful to have some methods for setting the spacing between the letters. To set the spacing between the letters, we simply adjust the _x value of each movieclip. Let's create a method called setSpacing (spacing), where spacing is the number of pixels we want between each character. Our method simply needs to loop through each movieclip and set the _x coordinate to the properly spaced value:

[as]public function setSpacing (spacing:Number):Void {
        // set the space between each character to 'spacing'
        for (var i = 0; i < typeArray.length; i++) {
                typeArray[i]._x = i * spacing;
        } // end looping through each character
} // end getLength () method
[/as]

Now in our movies, we can set the spacing of our Typesets to whatever we like. This puts 20 pixels between each letter in our 'Hello World' example:

[as]// create an "Hello World" typeset
var type:Typeset = new Typeset ("Hello World");
// space the characters 20 pixels apart
type.setSpacing (20);
      [/as]

This method sets the spacing to a consistent number for each character, but you might want even more precise control. You could then implement some spacing methods which set the spacing only between specified characters. Thus you might implement a setSpacing (spacing, startIndex, endIndex) method, where spacing is the number of pixels to place between the characters from startIndex to endIndex. I'll let you do that yourself.

Another feature we want in our class is the ability to set the TextField properties in any of the character movieclips. For example, we might want to make the whole string unselectable, and to do that we need to set the 'selectable' property of each TextField to false. We can write a method that lets us set any text field property. Let's call this method setTextFieldProperty ():

[as]public function setTextFieldProperty ():Void {
        // set a textfield property
} // end setTextFieldProperty () method
[/as]

The user will pass as parameters the name of the property to set and the value to which it should be set:

[as]public function setTextFieldProperty (propertyName:String, propertyValue):Void {
        // set a textfield property
} // end setTextFieldProperty () method
[/as]

We also want it so the user can define the start and end character index to which the property should be applied:

[as]public function setTextFieldProperty (propertyName:String, propertyValue, startIndex:Number, endIndex:Number):Void {
        // set a textfield property from startIndex to endIndex
} // end setTextFieldProperty () method
[/as]

Now, we simply need to loop through the characters from startIndex to endIndex and set the specified property to the specified value for each character:

[as]public function setTextFieldProperty (propertyName:String, propertyValue, startIndex:Number, endIndex:Number):Void {
        // set a textfield property from startIndex to endIndex
        for (var i = startIndex; i < endIndex; i++) {
                typeArray[i]._txt[propertyName] = propertyValue;
        } // end looping from startIndex to endIndex
} // end setTextFieldProperty () method
[/as]

This method now lets us set the property of any character's textfield. For example, if we want to make the characters from 3 to 6 of a typeset unselectable, we can do it like this in our movie:

[as]// create an "Hello World" typeset
var type:Typeset = new Typeset ("Hello World");
// make the characters from 3 - 6 unselectable
type.setTextFieldProperty ("selectable", false, 3, 6);
[/as]


Page 5 of 5
Another useful method might be getLength (). The length of the typeset is simply the number of items in our array, so we can just return the length of the array:

[as]public function getLength ():Number {
        return typeArray.length;
} // end getLength () method
[/as]

Thus far our whole class looks like this:

[as]class Typeset {
        
        private var typeString:String;
        private var typeArray:Array;
        
        function Typeset (_typeString:String) {
                this.init.apply (this, arguments);
        } // end constructor
        
        public function init (_typeString:String):Void {
                typeString = _typeString;
                buildTypset ();
        } // end init () method
        
        private function buildTypeset ():Void {
                // break up typeString,
                // putting each character into its own clip
                for (var i = 0; i < typeString.length; i++) {
                        // store the current character as 'thisChar'
                        var thisChar = typeString.charAt (i);
                        // create a movieclip in the array
                        typeArray[i] = _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
                        // create a textfield inside that movieclip
                        typeArray[i].createTextField ("_txt", _root.getNextHighestDepth (), 0, 0, 100, 100);
                        // set the textfield's value to 'thisChar'
                        typeArray[i]._txt.text = thisChar;
                } // end looping through typeString
        } // end buildTypeset () method
        
        public function setSpacing (spacing:Number):Void {
                // set the space between each character to 'spacing'
                for (var i = 0; i < typeArray.length; i++) {
                        typeArray[i]._x = i * spacing;
                } // end looping through each character
        } // end getLength () method
        
        public function setTextFieldProperty (propertyName:String, propertyValue, startIndex:Number, endIndex:Number):Void {
                // set a textfield property from startIndex to endIndex
                for (var i = startIndex; i < endIndex; i++) {
                        typeArray[i]._txt[propertyName] = propertyValue;
                } // end looping from startIndex to endIndex
        } // end setTextFieldProperty () method
        
        public function getLength ():Number {
                return typeArray.length;
        } // end getLength () method
        
} // end Typeset class
[/as]

Before we finish this section, let me show you how to implement some standard TextField methods. In our Typeset class, it would be very useful to have some standard TextField methods. For example, it would be useful to have a setTextFormat () method so that we could apply TextFormats to the characters in our Typeset. We can implement this method for our Typeset class so that we can apply TextFormats to our Typeset just as we do to TextFields.

The first step is to implement the method with the same name. Here we can pass the TextFormat as a parameter just as we do with a TextField.

[as]public function setTextFormat (format):Void {
        // apply the TextFormat to the characters
} // end setTextFormat () method
[/as]

To apply the specified TextFormat to our characters, we simply need to loop through each character and apply the TextFormat to each movieclip's TextField:

[as]public function setTextFormat (format):Void {
        // apply the TextFormat to the characters
        for (var i = 0; i < getLength (); i++) {
                typeArray[i]._txt.setTextFormat (format);
        } // end looping through the characters
} // end setTextFormat () method
[/as]

With that method in our class, we can then apply a TextFormat to our Typeset. For example, this applies a TextFormat to our 'Hello World' Typeset to make each character blue 14pt Arial:

[as]// create an "Hello World" typeset
var type:Typeset = new Typeset ("Hello World");
// set the spacing to 20 pixels
type.setSpacing (20);
// create a TextFormat
var myFormat:TextFormat = new TextFormat ();
myFormat.font = "Arial";
myFormat.size = 14;
myFormat.color = 0x006699;
// apply the TextFormat to the Typeset
type.setTextFormat (myFormat);
      [/as]

The TextField's setTextFormat () method, however, lets you specify a start and end index to which the TextFormat should be applied. To implement that same feature in our method, we need to set up some if statements at the beginning of our method which determine if a start and/or end index have been specified. We can use the arguments array to tell how many arguments have been passed to the method:

[as]public function setTextFormat (arg1, arg2, arg3):Void {
        // set 'startAt' and 'endAt' depending on
        // how many arguments have been passed to the method.
        if (arguments.length == 1) {
                var startAt = 0;
                var endAt = getLength ();
                var format = arg1;
        } else if (arguments.length == 2) {
                var startAt = arg1;
                var endAt = arg1 + 1;
                var format = arg2;
        } else if (arguments.length == 3) {
                var startAt = arg1;
                var endAt = arg2;
                var format = arg3;
        } // end if (arguments.length = 1)
        // apply the TextFormat to the characters
        // from startAt to endAt
        for (var i = startAt; i < endAt; i++) {
                typeArray[i]._txt.setTextFormat (format);
        } // end looping through the characters
} // end setTextFormat () method
[/as]

Notice that there are now three arguments named arg1, arg2, and arg3. We chose generic names because the value of arg1 will be different depending on how many arguments are passed. For example, if the user is just specifying the TextFormat --

[as]type.setTextFormat (myFormat);
      [/as]

-- then arg1 will be a TextFormat. But if the user is specifying a startIndex too --

[as]type.setTextFormat (4, myFormat);
      [/as]

-- then arg1 will be the startIndex, and arg2 will be the TextFormat. The first thing our method tests then is how many arguments have been passed. If there is only one argument, then the argument is the TextFormat and it should be applied to all the characters. Thus the first if statement sets startAt to 0, endAt to the length of the Typeset, and it sets format to arg1. The second if statement sets startAt to arg1, endAt to one number higher (so it will only loop through one value), and it sets format to arg2. The third if statement sets startAt to arg1, endAt to arg2, and format to arg3.

Once startAt, endAt, and format are set according to how many arguments were passed to the method, the method then loops from startAt to endAt and applies format to each character's TextField. The result is a setTextFormat () method which works for our Typeset class exactly as it works for the TextField class. We now can use TextFormats with our Typesets with just as much precision as with TextFields.

Here is our class, in full, with everything documented:

[as]// *********************************************************** //
// *********************************************************** //
//
// Typeset class
//
// *********************************************************** //
// *********************************************************** //
//
// This class takes a string, breaks it up into its individual
// characters, and places each of those characters in its own
// movieclip. The movieclips are stored in an array. Methods
// are then implemented to provide an interface to manipulate
// the character movieclips.
//
// Examples of use:
//
// var myType:Typeset = new Typeset ("Hello World");
// myType.setSpacing (20);
// var myFormat:TextFormat = new TextFormat ();
// myFormat.font = "Arial";
// myFormat.size = 32;
// myType.setTextFormat (myFormat);
//
// *********************************************************** //

class Typeset {
        
        // ********************************************************* //
        // Class variables
        // --------------------------------------------------------- //
        //
        // typeString: the string comprising this Typeset
        // typeArray: the array holding each character movieclip
        //
        // ********************************************************* //
        
        private var typeString:String;
        private var typeArray:Array;
        
        
        // ********************************************************* //
        // Constructor
        // --------------------------------------------------------- //
        //
        // Takes one parameter: a string to be broken up so that
        // each character is to be placed in its own movieclip.
        //
        // ********************************************************* //
        
        function Typeset (_typeString:String) {
                this.init.apply (this, arguments);
        } // end constructor
        
        
        // ********************************************************* //
        // init
        // --------------------------------------------------------- //
        //
        // Takes one parameter: a string to be broken up so that
        // each character is to be placed in its own movieclip
        // (this is passed from the constructor).
        // The method then invokes the buildTypeset method.
        //
        // ********************************************************* //
        
        public function init (_typeString:String):Void {
                typeString = _typeString;
                buildTypset ();
        } // end init () method
        
        
        // ********************************************************* //
        // buildTypeset
        // --------------------------------------------------------- //
        //
        // Takes no parameters.
        // This function breaks up 'typeString' and places each
        // character in its own movieclip. The movieclips are
        // stored in 'typeArray' so that each character clip
        // can be accessed by the character index number.
        //
        // ********************************************************* //
        
        private function buildTypeset ():Void {
                // break up typeString,
                // putting each character into its own clip
                for (var i = 0; i < typeString.length; i++) {
                        // store the current character as 'thisChar'
                        var thisChar = typeString.charAt (i);
                        // create a movieclip in the array
                        typeArray[i] = _root.createEmptyMovieClip ("typeset_" + i, _root.getNextHighestDepth ());
                        // create a textfield inside that movieclip
                        typeArray[i].createTextField ("_txt", _root.getNextHighestDepth (), 0, 0, 100, 100);
                        // set the textfield's value to 'thisChar'
                        typeArray[i]._txt.text = thisChar;
                } // end looping through typeString
        } // end buildTypeset () method
        
        
        // ********************************************************* //
        // setSpacing
        // --------------------------------------------------------- //
        //
        // Takes one parameter: a number which specifies the
        // distance between each character in the Typeset.
        //
        // ********************************************************* //
        
        public function setSpacing (spacing:Number):Void {
                // set the space between each character to 'spacing'
                for (var i = 0; i < typeArray.length; i++) {
                        typeArray[i]._x = i * spacing;
                } // end looping through each character
        } // end getLength () method
        
        
        // ********************************************************* //
        // setTextFieldProperty
        // --------------------------------------------------------- //
        //
        // Takes four parameters: (1) a string naming the property
        // you wish to set for the characters between startIndex
        // and endIndex. (2) the value of the property you wish to
        // set. (3) the character index of the first character for
        // which you want to set the property. (4) the character
        // index of the last character for which you want to
        // set the property. The method sets the value of the
        // property (1) to the value specified (2) for characters
        // between startIndex (3) and endIndex (4).
        //
        // ********************************************************* //
        
        public function setTextFieldProperty (propertyName:String, propertyValue, startIndex:Number, endIndex:Number):Void {
                // set a textfield property from startIndex to endIndex
                for (var i = startIndex; i < endIndex; i++) {
                        typeArray[i]._txt[propertyName] = propertyValue;
                } // end looping from startIndex to endIndex
        } // end setTextFieldProperty () method
        
        
        // ********************************************************* //
        // getLength
        // --------------------------------------------------------- //
        //
        // Takes no parameters. Returns the number of characters
        // in the typeset.
        //
        // ********************************************************* //
        
        public function getLength ():Number {
                return typeArray.length;
        } // end getLength () method
        
        
        // ********************************************************* //
        // setTextFormat
        // --------------------------------------------------------- //
        //
        // This method follows the same interface as it does for
        // the TextField object, so consult the entry for
        // TextField.setTextFormat () in the AS Dictionary
        // for documentation.
        //
        // ********************************************************* //
        
        public function setTextFormat (arg1, arg2, arg3):Void {
                // set 'startAt' and 'endAt' depending on
                // how many arguments have been passed to the method.
                if (arguments.length == 1) {
                        var startAt = 0;
                        var endAt = getLength ();
                        var format = arg1;
                } else if (arguments.length == 2) {
                        var startAt = arg1;
                        var endAt = arg1 + 1;
                        var format = arg2;
                } else if (arguments.length == 3) {
                        var startAt = arg1;
                        var endAt = arg2;
                        var format = arg3;
                } // end if (arguments.length = 1)
                // apply the TextFormat to the characters
                // from startAt to endAt
                for (var i = startAt; i < endAt; i++) {
                        typeArray[i]._txt.setTextFormat (format);
                } // end looping through the characters
        } // end setTextFormat () method
} // end Typeset class
[/as]

You can implement any other methods you use with TextFields in the same way we have implemented setTextFormat () here (e.g. you might implement some CSS methods). Working with your Typesets can end up being just as easy as working with TextFields: you simply call the right methods, and the class does all the work for you. The hard work is wrapped up inside the class and you never need to touch it.

You can also implement your own methods to handle character spacing (vertical and horizontal), and maybe you even want to implement some methods which move, rotate, scale, and fade the characters in your Typesets. By wrapping up all the hard work inside the class, you can then easily manipulate characters individually simply by invoking the relevant methods. Using this technique, as well as other techniques, Flash can become an innovative new medium for typographic design. You can use such techniques to make your letters come alive on the page.

2.4 Some cautions

Before finishing this section, I should mention a few cautions when using actionscripted type design in the fashion described here. First of all, text strings can easily be fairly long, and trying to manipulate each character indepedently in long strings results in many movieclips. If you get too many movieclips on the stage, Flash can quickly bog down and move slowly. It is best to prevent this by using something like the Typeset class only for short text strings. However, this isn't too much a problem if we recall the principle mentioned earlier that typographic design should be subtle. Use something like the Typeset class to give your typographic design subtle life, but don't use it to dizzy your reader with spinning letters. Nobody can read spinning letters.

Subtle use of these techniques can help your site design mature substantially. You can be very creative and use these techniques in innovative ways to help communicate and more tightly control site coherence. For example, if you are building a site for an independent film about the breakdown of a character's identity, you might use the Typeset class to make blocks of text here and there subtly flicker and shift, bit by bit, until the text itself is threatened with losing its identity. You can implement the same idea with the lines, shapes, and colors throughout the rest of the site's design too. In this way you can design your type in a way consistent with the rest of the site, bringing to your work a more mature sense of coherence.

2.5 Conclusion

In this second part of the series, we have looked at some ways to use actionscript to drive our typographic design. The TextFormat and CSS objects give us relatively precise control over type formatting. Further, if we break a string up and put each character into a movieclip, we can then control each character just as a movieclip, and thus we expose the characters of the string to Flash's full animation powers. This allows us to integrate our type into the motion design of our movies. Consequently, type can be just as much a mover and shaker as lines and shapes. This opens our typographic design up to new considerations, guidelines, and principles typically applicable to motion design. Yet even though the techniques of motion design are now available to how we use type, always remember that it is still type. Thus, the principles and guidelines we discussed in part one of this series still apply, and good typographic style -- whether the text is moving or not -- will still 'follow the rules'. Nevertheless, actionscript opens up new and interesting arenas in which to explore how principles of sound typographic design can be worked out in the world of motion.


Copyright 2004 JT Paasch.