The Flex framework provides a group of components that allow you to format values. You can use these formatters to format data for any reason, though they’re most useful for displaying data.
Flex ships with a handful of formatters, such as NumberFormatter
and PhoneFormatter
, and you can even build custom
formatters based on the same framework. Each formatter uses different
properties, but all the formatters work in the same basic manner. First
you must create the formatter either with MXML or with ActionScript,
assigning property values as necessary. Then you can call the format()
method of the formatter, passing it the
value you want to format. The format()
method returns a string. If the formatter can't format a string, it
dispatches an error event.
You can create a formatter using MXML with the corresponding MXML
tag. For example, the following creates a NumberFormatter
instance. This example uses all
the default property values, though you could also set the property values
in the MXML. Note that you should always assign an id
value to formatters because you’ll need to
reference them with ActionScript.
<mx:NumberFormatter id="numberFormatter" />
You can optionally create a formatter with ActionScript using the constructor, as shown here:
var numberFormatter:NumberFormatter = new NumberFormatter();
Once you’ve created a formatter object, you must call the format()
method to apply the formatting.
The format()
method
requires that you pass it the value you want to format. The method does
not change the original value, but it returns a new string formatted
according to the rules set by the formatter and its properties:
var formattedValue:String = numberFormatter.format(userInput.text);
The NumberFormatter
allows
you to format (as a string) any number or value that can
be converted to a number. You can see the default formatting using the
following code:
<mx:TextInput text="{numberFormatter.format('1234.56789')}" /> <mx:NumberFormatter id="numberFormatter" />
The preceding example displays 1,234.56789
. The default formatting doesn’t
affect the precision of the number; it merely adds a thousands place
marker.
With a NumberFormatter
you can
control whether and how a number is rounded with the rounding
property. The default value is
none
, although you can optionally
specify a value of up
, down
, or nearest
. The following example displays
1,235
, as it rounds up to the nearest
whole number:
<mx:TextInput text="{numberFormatter.format('1234.56789')}" /> <mx:NumberFormatter id="numberFormatter" rounding="nearest" />
You can also control the precision of the formatted output using
the precision
property. The default
value is −1
, which doesn’t enforce
any precision constraints. A non-negative integer value for the precision
property rounds the decimal places
to that many, if necessary. The rounding
property value is used to determine
how to round for precision, if necessary. The following displays
1,234.56
:
<mx:TextInput text="{numberFormatter.format('1234.56789')}" /> <mx:NumberFormatter id="numberFormatter" precision="2" />
If the input value uses decimal and/or thousands place markers,
the formatter needs to know how to interpret them. NumberFormatter
uses the decimalSeparatorFrom
and thousandsSeparatorFrom
properties for
this purpose. The default values are the dot (.
) and the comma (,
); however, you can specify different values.
The following example uses the delimiting characters as they are used in
many European countries (the formatted text is 1,234.56789):
<mx:TextInput text="{numberFormatter.format('1.234,56789')}" /> <mx:NumberFormatter id="numberFormatter" decimalSeparatorFrom="," thousandsSeparatorFrom="." />
You can also specify the delimiting characters to use in the
formatted output by way of the decimalSeparatorTo
and thousandsSeparatorTo
properties. The following
example displays 1.234,56789
:
<mx:TextInput text="{numberFormatter.format('1,234.56789')}" /> <mx:NumberFormatter id="numberFormatter" decimalSeparatorTo="," thousandsSeparatorTo="." />
You can also specify whether to use the thousands delimiter at all
with the useThousandsSeparator
property; the
default value is true
. A value of
false
won’t display the thousands
place delimiter.
The useNegativeSign
property
lets you specify how negative numbers are formatted. The default value
is true
, and it results in a number
preceded by a negative sign (e.g., −1
). If the property is set to false
, the number is surrounded by parentheses
(e.g., (1)
).
The DateFormatter
allows you to
format the data from a Date
object as
a string. There is one configurable property that you can use with a
DateFormatter
. That property, called
formatString
, allows you to specify
the way in which the elements of a Date
object (year, month, day, hours, etc.)
should be formatted in the output string. The default value is
MM/DD/YYYY, which is the month followed by the day of the month followed
by the four-digit year. The following characters have special meaning in
the formatString
value:
Y: year
M: month
D: day of month
E: day of week
A: AM/PM
J: hour (0–23)
H: hour (1–24)
K: hour (0–11 for use with AM/PM)
L: hour (1–12 for use with AM/PM)
N: minute
S: second
Y, M, D, and E yield different results when used in different groupings. For example, YY results in a two-digit year, whereas YYYY results in a four-digit year. This same pattern is generally true for each of these characters. For example, M/D/YYYY displays 1/2/2010 for January 2, 2010, but MM/DD/YYYY displays 01/02/2010. M and E also result in abbreviations and full names of the months and days of the week when used in groups of three and four. For example, MMM can display Jan., and MMMM displays January.
You can use any other characters in a formatString
value, and they are interpreted
literally. The following example displays January 2, 2010 at 4:25:10
PM:
<mx:TextInput text="{dateFormatter.format(new Date(2010, 0, 2, 16, 25, 10))}" /> <mx:DateFormatter id="dateFormatter" formatString="MMMM D, YYYY at L:N:S A" />
The CurrencyFormatter
works very much like the NumberFormatter
except that it adds a currency
symbol in addition to formatting a number value. CurrencyFormatter
uses all the same properties
as NumberFormatter
, but it adds two
additional properties: currencySymbol
and alignSymbol
. The default value for currencySymbol
is the U.S. dollar sign
($
). The default value for alignSymbol
is left
; the other possible value is right
.
The PhoneFormatter
takes any
number or string that can be converted to a number, and it formats that
as a phone number. The PhoneFormatter
allows you to configure the format of the output using the formatString
property. The default value of
the formatString
property is (###) ###-####
, in which the #
is a placeholder for a digit. The following
example outputs 123.456.7890
:
<mx:TextInput text="{phoneFormatter.format(1234567890)}" /> <mx:PhoneFormatter id="phoneFormatter" formatString="###.###.####" />
By default, the formatString
property allows only a specific set of characters. That set of
characters is dictated by the validPatternChars
property, which has a
default value set consisting of +
,
(
, )
, #
,
−
, .
, and a space. You can customize the
allowable characters in the pattern if you want. The following example
outputs 123*456*7890
:
<mx:TextInput text="{phoneFormatter.format(1234567890)}" /> <mx:PhoneFormatter id="phoneFormatter" formatString="###*###*####" validPatternChars="#*" />
You can also specify the area code using an areaCode
property. The areaCode
property defaults to −1, which means
that no area code is prepended to the formatted string. However, if you
specify a non-negative integer value for the areaCode
property, it gets prepended to the
phone number. For example, the following displays (123) 456-7890
:
<mx:TextInput text="{phoneFormatter.format(4567890)}" /> <mx:PhoneFormatter id="phoneFormatter" formatString="###-####" areaCode="123 " />
If you want to specify the pattern for the area code, you can use
the areaCodeFormat
property. The
default value is (###)
. The following
example displays 123 456-7890
:
<mx:TextInput text="{phoneFormatter.format(4567890)}" /> <mx:PhoneFormatter id="phoneFormatter" formatString="###-####" areaCode="123" areaCodeFormat="### " />
Note that when you use a specific value for the areaCode
property, the formatter will not
place a space between the area code and the formatted number.
Therefore, in the preceding example, we added a space as the last
character of the areaCodeFormat
property.
The ZipCodeFormatter
lets you
format a number or string as a zip or postal code in U.S. or Canadian
format. You can configure the formatter via the formatString
property. The default value is
#####
, which formats a value as a
U.S. zip code. The only other possible formatString
property values are #####-####
(U.S. zip+4 format), ##### ####
(U.S. zip+4 format with a space),
###-###
(Canadian format), and
### ###
(Canadian format with a
space). The following formats the number in U.S. zip+4 format:
<mx:TextInput text="{zipCodeFormatter.format(123456789)}" /> <mx:ZipCodeFormatter id="zipCodeFormatter" formatString="#####-####" />
If one of the standard formatters does not assist you in a
particular formatting requirement, you can write a custom formatter.
To write a custom formatter, you must write an
ActionScript class that extends mx.formatters.Formatter
. The class must override the format()
method. Example 15-11 applies zero-fill to
numbers.
Zero-fill refers to placing leading zeros to the left of digits to form a new string. For example, 15 with zero-fill to four characters is 0015.
Example 15-11. Creating a custom formatter
package com.oreilly.programmingflex.formatters { import mx.formatters.Formatter; public class ZeroFillFormatter extends Formatter { private var _count:int; // The count getter/setter allows the user of the formatter // to set the number of total characters up to which the value // may require zero-fill. public function set count(value:int):void { _count = value; } public function get count():int { return _count; } // Call the superclass constructor, and set _count to −1, which is // used as the value to indicate no zero-fill should be applied. public function ZeroFillFormatter() { super(); _count = −1; } // The format() method signature must match that of Formatter. override public function format(value:Object):String { // If necessary, convert the parameter to a string. Otherwise, // cast to a string. var stringValue:String; if(!(value is String)) { stringValue = value.toString(); } else { stringValue = String(value); } // If the length of the string value is less than _count, // prepend zeros. while(_count > stringValue.length) { stringValue = "0" + stringValue; } return stringValue; } } }
Example 15-12 illustrates how to use this custom formatter.
Example 15-12. Using a custom formatter
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
xmlns:formatters="com.oreilly.programmingflex.formatters.*"
layout="absolute">
<mx:TextInput text="{zeroFillFormatter.format(123456789)}" />
<formatters:ZeroFillFormatter id="zeroFillFormatter" count="15" />
</mx:Application>
The preceding example displays 000000123456789
in the text input
control.