Controlling Text in Macromedia Flash 5
- Creating Dynamic and Input Text Fields
- Troubleshooting Text
- Did You Know?
An important element of most movies is text. Text is an efficient, compact, and relatively unambiguous way to convey information. Although a picture may be worth a thousand words, if it's misinterpreted, it might be the wrong thousand words.
You can use static text fields (see Chapter 2, "Creating Artwork and Text with Flash") when the message doesn't change, but in cases when you can't predict exactly what information you need to show users, you need to use strings.
A string is an ActionScript data type that stores text information. String values can be modified by ActionScript commands by using string operators, functions, and constants.
Strings can be visible on the stage, or they can work behind the scenes, living only in the computer's memory.
Creating Dynamic and Input Text Fields
Two types of text fields can be displayed on the stage: dynamic and input. These fields are the onscreen representations of string variables stored in memory.
Dynamic Text
You use a dynamic text field when you want to display changing text values but when the users don't need to make changes to the values. Dynamic text fields can contain text in a variety of fonts and styles and can be changed based on ActionScript commands.
To create a dynamic text field, follow these steps:
Use the Text tool to draw a rectangle onscreen, just as you would for a static text field.
-
Open the Text Options panel and select Dynamic Text from the Text Type pop-up menu (see Figure 18.1).
Use the Line Type pop-up menu to control whether one or more lines of text appear.
Enter the name of the variable that will be displayed in the dynamic text field in the Variable field. The name can be virtually any combination of alphanumeric characters, but should start with a letter, such as result or t20, not 3rdline.
-
Select the HTML check box to enable dynamic text formatting. If the box is unchecked, all text including any tags is displayed. If the box is checked, all tags are hidden, and supported formatting tags are used to format the displayed text (see Figure 18.2).
Use the Border/Bg check box to control whether a border and background are displayed. If the box is unchecked, only text is displayed within the text field. If the box is checked, a 1-pixel black line is displayed around the perimeter of the field (no matter what the magnification level) and a white background is displayed within the perimeter.
The Word Wrap check box appears when the Multiline check box is selected. If you want the text to fit the width of the field, you need to either select this option or insert line break characters in the string.
Check the Selectable check box to allow users to select and copy the dynamic text. Users can't change dynamic text, but if this option is checked, the text can be copied and pasted into other programs.
Select the option(s) for which font characters will be embedded in the movie. For smaller movies, use the options that allow you to include only specific characters. If only numbers will be displayed, use the number option. Remember that decimal points aren't numbers! If a wide variety of characters are used in the field, your best choice is generally to include the entire outline.
Figure 18.1 The options for dynamic text fields appear in the Text Options panel.
Figure 18.2 Two dynamic text fields can display the same text in different ways. These dynamic text fields are identical (and reference the same string variable), except that the one on the right has its HTML check box selected. The tags shown in the field on the left style the text on the right.
NOTE
Selectable text in dynamic and input text fields can interfere with buttons and clickable areas near them. Unless this capability is necessary, make it a habit to deselect this option.
A dynamic text field is a window onto the contents of a variable. The text field and the variable should exist on the same timeline—only the variable name (and not the path to the variable) should be used in the Variable field of the Text Options panel.
When the Flash player encounters a dynamic text field in a movie, it automatically defines a variable with the name assigned to the text field if one doesn't already exist. If a variable does exist (because an ActionScript command has already defined it), the contents of the text field are modified to display the value of the variable.
If two or more dynamic text fields reference a single variable (if the names in their Variable fields are the same), changes to the variable affect all the text fields.
Dynamic text fields can contain multiple lines and paragraphs of text. They also can automatically wrap text or break lines when a carriage-return character is added to the string variable.
Adding HTML tags to the string variable lets you create limited text styling. Supported tags include the following:
<P ALIGN>—Paragraph and alignment
<FONT FACE>—Font typeface
<FONT SIZE>—Font size
<FONT COLOR>—Font color
<B>—Bold type style
<I>—Italic type style
<U>—Underline type style
<BR>—Line break
<A HREF>—Hypertext link
All the tags (with the exception of the line break and paragraph tags) require a closing tag.
The font-embedding options let you control which font outlines are added to the SWF file when it's exported. Everything from specific characters to the entire font outline can be specified. The same character set is used for all font styles included in the text field at export time.
Input Text
Input text fields work almost exactly like dynamic text fields and share most of the same options (see Figure 18.3).
The main difference between input and dynamic text is that users can type and paste directly into input text fields.
The only input text option that differs from the options for dynamic text fields is the maximum character count field. You can enter a value in this field to limit the number of characters that users can type into the field. The default value of 0 means that no limit to the number of characters in the field exists.
Figure 18.3 The options for input text fields appear in the Text Options panel.
Using String Variables
String variables are how text data is stored in Flash. ActionScript can manipulate and modify string variables in many ways. When used in conjunction with dynamic text and input text fields, they're one of the best ways to display dynamic information to the user.
String variables are attached to a timeline just like numeric variables are. Strings are composed of zero or more characters (a string with zero characters is an empty string).
String values are denoted in scripts with double quotation marks. The string value "Flash 5" includes the letters F, l, a, s, and h; a space; and the character for the number 5. The quotation marks are not part of the string value; they simply mark the beginning and end of the string. An empty string is represented by a pair of double quotation marks (as in ""). String values in quotation marks are referred to as literal values.
Creating Strings
You can create new string variables in two ways: by creating a dynamic or an input text field and designating the variable name following the previous instructions or by setting the value of the variable using an ActionScript command.
To create a string variable, use the assignment operator (=), just as you would for any other type of variable:
address = "1600 Pennsylvania Ave.";
This example creates a string variable named address and assigns it a 22-character value containing the street address of the White House. (It also would assign a new value to address if it were already in existence.)
String variables are associated with a specific timeline, whether it's the root timeline or that of a movie clip or a loaded movie. A string variable is referenced with the path to the variable followed by the variable name. You also can use this technique to create a new variable in a timeline other than the one to which the script is attached:
_level0.address = "1600 Pennsylvania Ave.";
This example creates the address variable in the root timeline of the movie in level 0. (It also would assign a new value to address if it were already in existence.)
String Expressions
You can use strings in calculations to build new strings. String variables that contain numeric values can also be used in numeric calculations.
One of the most common uses of a string expression is to concatenate two strings. Concatenation combines two strings, placing one immediately after another. This operation uses the addition operator (+).
NOTE
If you're exporting to the Flash 4 format for delivery, you must use the add operator instead of + for string concatenation.
address = "1600 " + "Pennsylvania Ave.";
Here, the two string elements are concatenated into a single string, which is assigned to the variable. Note that the space between the numbers and the word Pennsylvania is enclosed by the first pair of double quotation marks. The concatenation operation doesn't insert a space automatically.
You can combine multiple concatenation operations in a single expression, along with literal values, constants, and variables containing other strings or even numbers:
streetNum = 1600; streetName = "Pennsylvania Ave."; address = streetNum + " " + streetName;
This example combines a numeric variable (streetNum) with a string literal (the space between the double quotation marks) and combines a string variable (streetName) into a single string.
When you want to add something to the end of an existing string variable, you can use the addition assignment operator (+=) to concatenate:
address = 1600; streetName = "Pennsylvania Ave."; address += " " + streetName;
This example creates a numeric variable in the first line. Adding the space and streetName variable—both string values—converts the value of address to a string after the concatenation. This process of converting one type of data to another is called coercion.
In other cases, it might be necessary to coerce string values into numeric values. This is the case when input text fields are provided for users to enter data.
In most cases, Flash tries to determine what you want to do with string values that contain numeric characters. If you multiply or divide two strings, such as "3" and "5", you get a numeric value. Because the plus sign is also the concatenation operator, though, you'll get "35"—as a string—instead of 8 when trying to add the two numbers.
To clarify how you want Flash to interpret string values in numeric expressions, use the Number function to coerce the string value to a numeric value first:
first = "6"; second = "5"; sum = Number (first) + Number (second);
By converting both string values to numbers, the numeric sum is calculated in the third line instead of the concatenated string.
Comparing Strings
You can compare string values just like other values, using the same operators. When comparing strings, you should know that a string is really a series of numeric values filling in for the characters. The string value "1600" is not really a number—it's actually an array of four numbers. Each character in a string is an item in an array. The items are ASCII values; integers ranging from 0 to 255. That's not something peculiar to Flash, it's how all computers store string data. In the case of the string "1600," the numbers are 49 (the ASCII value for "1"), 54 ("6"), and two 48s (for the "0" characters).
NOTE
If you're exporting to the Flash 4 format for delivery, you can't use the standard comparison operators for strings. You must use the string-specific comparison operators eq (for equals ==), gt (for greater than >), and lt (for less than <).
The values computers use to represent characters were established more than 30 years ago and are called ASCII codes. Each ASCII code stands for a specific character, although this can vary between Windows and MacOS operating systems, as well as between languages.
When Flash compares two string values, it's actually comparing the ASCII values character by character. This can lead to some confusion if you're not familiar with how it works.
Take the postal abbreviation of Alabama (AL) as an example. The capital letter A has an ASCII value of 65. Capital L is 76. Therefore, the string value "AL" is actually a list of two numbers: 65 and 76.
When you look at the string "al", you can tell that the letters are the same as "AL" because you're smarter than a computer. A computer doesn't compare letters; it compares characters, and the character A is different from the character a. Consider the following:
trace ("AL" == "al");
This single line of code displays the result false in the Output window. For two string values to be equal, each of the characters in both strings must have the same ASCII character code values. Because the code for a is 97 and the code for l is 108, the strings aren't equal, even though they are the same length and contain the same letters.
The other comparison operators also depend on the ASCII codes when working with strings. All the following statements are true in ActionScript:
"AL" < "Al" "Al" < "aL" "ALA" < "al"
Even though in the last example, the first string is longer than the second, the first character of the string has a code that is less than the code for the first character of the second.
This is where working with numbers expressed as strings can cause problems. Comparing two strings with number characters does not compare them numerically. They're compared just like letters are. The ASCII code for 0 is 48, 1 is 49, 2 is 50, and so on, up to 9 and 57.
If you perform a numerical comparison of the values 99 and 100, the expression 99 < 100 is evaluated as true. If you compare two strings, though, "99" < "100" is false, because the character code for 9 is greater than the character code for 1. Because the strings are compared character by character, anything beginning with the character 9 is greater than anything beginning with 1, no matter how long it is.
Using String Functions
You can manipulate strings in many ways. Strings can be chopped up, be broken apart, have portions extracted, and have words or characters deleted. The way to accomplish this is through the string functions. String functions were introduced in Chapter 15, "ActionScript Syntax" (see Table 15.5, "String Object Functions").
The previous section mentioned the problem of comparing string values. When you're trying to determine whether one word appears before another in alphabetical order, you can't simply use the < or > comparison operator, because Z comes before a in the ASCII order. What you can do, however, is use the comparison operators on two strings in which all the characters are of the same case (upper- or lowercase).
In this sample movie (see Figure 18.4), each of the buttons is a movie clip and includes a trigger function to perform an operation on the string shown in the input text field Original. The final string appears in the dynamic text field Result.
The first pair of buttons converts the original text to all uppercase or lowercase (see Figure 18.5). The trigger function for the Uppercase button contains only one line of code.
_root.result = _root.original.toUpperCase();
By setting variables to the lower- or uppercase version of the strings you want to compare, you can better determine the alphabetical order of single words.
Something that's always good to know about a string value is how many characters it contains. The length property does this for you:
_root.result = _root.original.length;
One of the most common tasks when dealing with strings is extracting a portion of the string for use elsewhere. This is where the substring functions are useful.
Figure 18.4 This sample movie shows how the string functions work.
Figure 18.5 The Uppercase button converts the original text to all uppercase characters.
The first substring function (charAt) retrieves a single character at an index position:
_root.result = _root.original.charAt(_root.index1);
The charCodeAt function returns the ASCII code for a specific character in the string:
_root.result = _root.original.charCodeAt(_root.index1);
The other two substring functions go about this in slightly different ways. You specify a starting point for both by including an index position (the number of characters offset from the beginning of the string) within the string.
With the substring function, you specify another index position at the end of the substring. You tell the substr function, on the other hand, the number of characters following the first index you want to grab. The trigger function for the Substring (length) button is as follows (see Figure 18.6):
root.result = _root.original.substr(_root.index1, _root.index2);
Figure 18.6 The Substring buttons use the index1 and index2 fields as parameters. The result shown here is for the substring (index) function.
The two input text fields next to the substring buttons provide the values for index1 and index2. The value of index1 provides the starting point for both functions. substring uses index2 as its end point, whereas substr uses index2 as its length.
Finding a character in a string is another useful task. The indexOf function finds the first instance in which one string appears in another string. You include the string to search for in the search variable, and then the index1 variable determines the point at which the search begins:
_root.result = _root.original.indexOf(_root.search, _root.index1);
A variation on indexOf finds the last instance in which a string appears in another string:
_root.result = _root.original.lastIndexOf(_root.search);
There's not a function for everything you might want to do with a string, but you can usually accomplish it by combining functions and other actions. The Count button (see Figure 18.7) has a trigger script that determines the number of times the search string appears in the original string.
Figure 18.7 The Index and Count buttons look for the text in the search variable. This example finds three n characters after index position 8 (one of the four ns is before 8).
count = 0; index = 0; while (_root.original.indexOf (_root.search, index) > -1) { count++; index = _root.original.indexOf (_root.search, index) + 1; } _root.result = count;
The script begins searching at the first character and repeats as long as it can continue finding copies of the search string. Each time a match is found, the next search begins at the next character after the match. Both the indexOf and lastIndexOf functions return -1 when no match is found, ending the while loop.
The HTML text field shows how text styling can be affected by adding HTML tags to a string variable. The dynamic text field has its HTML option enabled:
quote = String.fromCharCode (34); root.html = "<FONT FACE=" + quote + "_serif" + quote + ">" + _root.original + "</FONT>"; _root.result = _root.html;
The script on the Serif button creates a variable containing the double quotation character by using the fromCharCode function (this is done because you need to use the character in the tags you're going to add). The FONT tag is wrapped around the original text, with the appropriate typeface used for the FACE. The result text field displays the variable, including the tags.
Scrolling Text
You can display long text blocks in a couple of ways. Breaking the text into separate bite-size chunks or pages is probably the most common method. That isn't really possible with dynamic text, though, because you can't predict line wrapping or the exact length of each text block.
Scrolling the text similar to how a word-processing program does is another answer, but one that's often intimidating to even experienced programmers.
The dynamic and input text fields in Flash share two properties that enable you to control their scrolling.
NOTE
Only dynamic and input text fields with the Multiline option enabled can be scrolled, and then only when more characters are in the string variable than can be displayed in the field.
When you create a text field in Flash, the boundaries of the field expand to enclose all the characters you enter. This means that scrolling text fields must be created as placeholders, with the actual data they display added through the use of ActionScript.
The sample movie contains two text fields that display the same text (see Figure 18.8). The dynamic text field play contains 24 lines of text. The text field html has room for only 5 lines (it has the HTML styling option selected).
Figure 18.8 The text field at the right can be viewed and scrolled in the text field on the left.
The first frame of the timeline assigns the value of play to html, which automatically displays the first 5 lines.
The first property controlling text scrolling is maxscroll. This property contains the line number in the text field that appears at the top of the text field when the last line of the text appears at the bottom.
NOTE
A text field whose boundaries are larger than the text it contains will always have a maxscroll value of 1.
The Maximum Scroll button in this example uses the same trigger mechanism as the buttons in the String function example, and its script displays the maxscroll of the html variable in the max text field:
_root.max = _root.html.maxscroll;
When it's displayed in the html text field, the text still has 24 lines (this can vary depending on fonts and relative widths of the text field, but this example attempts to make both play and html the same width relative to the size of the text). In html, 5 lines of text can be displayed, and if line 20 is at the top, 4 more lines (21, 22, 23, and 24) can be displayed below it.
The maxscroll property is determined by the Flash player, based on the text being displayed and the size of the text field, and can't be changed directly. Modifying the text in an input text field or through ActionScript commands automatically updates the property.
The other property actually controls the top line that's displayed in the text field. The scroll property can range between 1 and the maxscroll value.
The Set Current Scroll button uses the value from the input text field current to change the top line of the html text field by changing the scroll property:
_root.html.scroll = _root.current;
If you enter any value from 1 to 20, a different line of text appears at the top of the html text field.
Now that you know how to change the scroll value by the numbers, you can make the scrolling effect really scroll by incorporating a variation of the scrollbars from Chapter 17, "Scripting Interface Elements."
The scrollbar controls a value from 0 to 1. You should have the scroll property of html set to 1 when the scrollbar value is 0. In addition, the scroll property should be set to 20 when the scroll bar value is 1.
To do this, you must continually read the value from the scrollbar and then apply it to _root.html.scroll:
onClipEvent (enterFrame) { _root.html.scroll = Math.round (this.value * (_root.html.maxscroll - 1) + 1); }
Only the second line is really important. The value set in the scrollbar is multiplied by the difference between the minimum scroll value (1) and maxscroll (20), yielding a number 0–19. Then, a 1 is added to shift the actual value to the range of 1–20.
That's really all there is to it. After your scrollbar is in action, you can click, drag, and push buttons to your heart's content and watch the text move around.
The final version of the sample file also has an extra line in the script for the Set Current Scroll button. It updates the scrollbar when the button is used to change the scrolling:
_root.scroller.bar.setSlider ((_root.current - 1) / (_root.html.maxscroll - 1));
Both values are shifted from the range 1–20 into the 0–19 range so that the results of the division are in the correct range (0–1) for the slider value. Without that shift, setting the scroll to 1 wouldn't move the slide all the way to the top.
NOTE
Avoid having two text fields onscreen that display the same variable when one of them is being scrolled. The results are unpredictable to say the least.