fvar — Font Variations Table

OpenType Font Variations allow a font designer to incorporate multiple faces within a font family into a single font resource. Variable fonts can provide great flexibility for content authors and designers while also allowing the font data to be represented in an efficient format.

A variable font allows for continuous variation along some given design axis, such as weight:

fvar_fig1
Figure: Continuous variation along a design axis

Conceptually, variable fonts define one or more axes over which design characteristics can vary. Weight is one possible axis of variation, but many different kinds of variation are possible. Variable fonts are not limited to a single axis of variation, but can combine two or more different axes of variation. For example, the following illustrates a combination of weight and width variation:

fvar_fig2
Figure: Continuous variation along multiple design axes

The set of axes supported by a font define a variation space for that font, supporting a potentially-vast number of design-variation instances at positions across that space.

The font variations table ('fvar') provides the global definition of variations supported within the font. It specifies the axes of variation that are used and the ranges of variation for each axis. It also allows the font designer to specify certain coordinate positions within the font’s variation space as named instances. Named instances have designer-provided names, effectively equivalent to sub-family names, that applications can use as a short list of “pre-chosen” design variants they can offer to users.

For a general introduction to OpenType Font Variations, see OpenType Font Variations Overview.

All variable fonts must include a font variations table, as well as other required or optional tables used in variable fonts. For more information on other tables used in variable fonts, see Variation Data Tables and Miscellaneous Requirements in the Overview chapter.

Note that some of the information in the font variations table also needs to be reflected in the style attributes ('STAT') table, which is also required in all variable fonts. In particular, each axis and each named instance specified in the font variations table must have matching axis records and axis value tables in the style attributes table.

Table Formats

The font variations table consists of a table header, followed by an array of variation axis records, followed by an array of named-instance records:

fvar_fig3
Figure: High-level organization of the font variations table

The format of the font variations table header is as follows.

Font variations header:

Type Name Description
USHORT majorVersion Major version number of the font variations table — set to 1.
USHORT minorVersion Minor version number of the font variations table — set to 0.
USHORT offsetToAxesArray Offset in bytes from the beginning of the table to the start of the variation axis array — set to 16 (0x0010) for this version.
USHORT countSizePairs The number of count + size field pairs that follow — set to 2 (for axis count/size plus instance count/size).
USHORT axisCount The number of variation axes in the font (the number of records in the axes array).
USHORT axisSize The size in bytes of each VariationAxisRecord — set to 20 (0x0014) for this version.
USHORT instanceCount The number of named instances defined in the font (the number of records in the instances array).
USHORT instanceSize The size in bytes of each InstanceRecord — set to either axisCount * sizeof(Fixed) + 4, or to axisCount * sizeof(Fixed) + 6.

The header is immediately followed by axes and instances arrays.

VariationAxisRecord axes[axisCount] The variation axis array.
InstanceRecord instances[instanceCount] The named instance array.

Note: The countSizePairs field is currently set to 2 to indicate that two count/size field pairs follow: the axis count/size pair, and the instance count/size pair. This number may increase in future versions of the 'fvar' table. The axes and instances arrays will always follow the last count/size field pair. To ensure forward compatibility, the offsetToAxesArray must be read to determine the start of the axes array.

Note: The axisSize and instanceSize fields indicate the size of the VariationAxisRecord and InstanceRecord structures. In this version of the 'fvar' table, the InstanceRecord structure has an optional field, and so two different size formulations are possible. The size of variation axis records or instance records may increase in future versions of the 'fvar' table. In minor-version revisions of the 'fvar' table, any increase in the size of records will be to extend the records with additional fields following the currently-defined fields.

The format of the variation axis record is as follows:

VariationAxisRecord

Type Name Description
Tag axisTag Tag identifying the design variation for the axis.
Fixed minValue The minimum coordinate value for the axis.
Fixed defaultValue The default coordinate value for the axis.
Fixed maxValue The maximum coordinate value for the axis.
USHORT flags Reserved for future use — set to 0.
USHORT axisNameID The name ID for entries in the 'name' table that provide a display name for this axis.

Each axis has a tag that identifies the design variation for the axis. For example, the tag 'wght' designates a weight variation. Tags are registered for commonly-used design axes, but foundry-defined tags may also be used. Registered tags define valid ranges of coordinate values for the axis across all fonts. The variation axis record defines minimum and maximum values supported by the font, which may be more limited that the valid ranges defined for a registered tag.

Note: Axis values given in the variation axis record use user scale coordinates that are specific to each axis tag. The user scale for each registered tag is described with the definition of each tag. In most other font tables that contain variations-related data, axis coordinate values are expressed using normalized coordinate scales. For more information regarding user scales and normalized scales, and a specification of the normalization process, see the Coordinate Scales and Normalization section in the OpenType Font Variations Overview chapter.

For more details on axis tags, see Variation Axis Tags below.

The default value interacts with the glyph and glyph variations tables in a particular way: the variation instance that has the default coordinate value for each axis will use glyph outlines as defined in the glyph table, without any variations from the glyph variations table applied. This instance is referred to as the default instance.

The axisNameID field provides a name ID that can be used to obtain strings from the 'name' table that can be used to refer to the axis in application user interfaces. The name ID must be greater than 255 and less than 32768. For registered axis tags, a conventional US English axis name is provided; it is recommended that that name, or localized derivative names, be used in application user interfaces to provide greater consistency in user experience between different fonts.

The instance record format includes an array of n-tuple coordinate arrays that define position within the font’s variation space. The n-tuple array has the following format:

Tuple Record (Fixed):

Type Name Description
Fixed coordinates[axisCount] Coordinate array specifying a position within the font’s variation space.

The format of the instance record is as follows.

InstanceRecord:

Type Name Description
USHORT subfamilyNameID The name ID for entries in the 'name' table that provide subfamily names for this instance.
USHORT flags Reserved for future use — set to 0.
Tuple coordinates The coordinates array for this instance.
USHORT postScriptNameID Optional. The name ID for entries in the 'name' table that provide PostScript names for this instance.

The postScriptNameID field is optional, but should be included in all variable fonts, and may be required in some platforms. Note that all of the instance records in a given font must be the same size, with all either including or omitting the postScriptNameID field.

The subfamilyNameID field provides a name ID that can be used to obtain strings from the 'name' table that can be treated as equivalent to name ID 17 (typographic subfamily) strings for the given instance. Values of 2 or 17 can be used; otherwise, values must be greater than 255 and less than 32768. The values 2 or 17 should only be used if the named instance corresponds to the font’s default instance.

The postScriptNameID field provides a name ID that can be used to obtain strings from the 'name' table that can be treated as equivalent to name ID 6 (PostScript name) strings for the given instance. Values of 6 and 0xFFFF can be used; otherwise, values must be greater than 255 and less than 32768. If the value is 0xFFFF, then the value is ignored, and no PostScript name equivalent is provided for the instance. The value 6 should only be used if the named instance corresponds to the font’s default instance.

All of the instance records in a font should have distinct coordinates and distinct subfamilyNameID and postScriptName ID values. If two or more records share the same coordinates, the same nameID values or the same postScriptNameID values, then all but the first can be ignored.

The default instance of a font is that instance for which the coordinate value of each axis is the defaultValue specified in the corresponding variation axis record. An instance record is not required for the default instance, though an instance record can be provided. When enumerating named instances, the default instance should be enumerated even if there is no corresponding instance record. If an instance record is included for the default instance (that is, an instance record has coordinates set to default values), then the nameID value should be set to either 2 or 17, and the postScriptNameID value should be set to 6.

Variation Instance Selection

When formatting text using a variable font, applications must select a particular variation instance; that is, specific, in-range values must be specified for each of the axes defined in the font variation table. An instance may be selected by reference to a named instanced defined in an instance record, or by using a set of arbitrary axis values for the various axes. If a value is not specified for any particular axis, the default value for that axis defined in the font is used. If an application specifies a value for an axis that is less than the minValue defined in the font, then minValue must be used. Similarly, if an application specifies a value greater than the maxValue defined in the font, then maxValue must be used.

Variation Axis Tags

Axis tags identify the design variation for a given axis. Axis tags are also used in the style attributes ('STAT') table, and can be used in a style attributes table in non-variable fonts. A registry of commonly-used axis tags is maintained, but private, foundry-determined tags can also be used.

Like other OpenType tags, axis tags are four unsigned bytes that can equivalently be interpreted as a string of four ASCII characters. Axis tags must begin with a letter (0x41 to 0x5A, 0x61 to 0x7A) and must use only letters, digits (0x30 to 0x39) or space (0x20). Space characters must only occur as trailing characters in tags that have fewer than four letters or digits.

Privately-defined axis tags must begin with an uppercase letter (0x41 to 0x5A), and must use only uppercase letters or digits. Registered axis tags must not use that pattern, but can be any other valid pattern.

Every registered tag provides a US English name for the axis that can be used as a display string in user interfaces to refer to the axis, or as the basis of localized display strings.

Every registered tag also provides information regarding the range of valid values for that axis. Depending on the axis, this may or may not be a bounded range. Every registered tag must also provide information regarding the scale for those values, specifying either some objective measure or some convention by which values can be interpreted. This is required to provide some means if interoperability between different fonts and between OpenType Font Variations and other specifications, such as font-weight values in CSS.

The specification of a scale interpretation for a registered axis tag may include some value that is considered “normal” for that axis. For font implementations that support a given axis, this “normal” value will usually be a good choice for the default value of that axis in the 'fvar' variation axis record. Fonts are not required to use this “normal” value as their default, however.

Five registered tags are defined as part of this version of OpenType:

Tag Name Description Scale “Normal” value
'ital' Italic Used to vary between non-italic and italic. Values must be in the range 0 to 1. A value of 0 can be interpreted as “Roman” (non-italic); a value of 1 can be interpreted as (fully) italic. 0
'opsz' Optical size Used to vary design to suit different text sizes. Values can be interpreted as text size, in points. (Text size can be as determined in an application and is not necessarily physical size on a display surface.) Values must be strictly greater than zero. 12
'slnt' Slant Used to vary between upright and slanted text. Values can be interpreted as the angle, in counter-clockwise degrees, of oblique slant from whatever the designer considers to be upright for that font design. Values must be greater than -90 and less than +90. 0
'wdth' Width Used to vary width of text from narrower to wider. Values can be interpreted as a percentage of whatever the font designer considers “normal” for that font design. Values must be strictly greater than zero. 100
'wght' Weight Used to vary stroke thicknesses to give variation from lighter to blacker. Values must be in the range 1 to 1000. Values can be interpreted in direct comparison to values for usWeightClass (in the 'OS/2' table), or the CSS font-weight property — see the note below. 400

In a variable font that implements 'slnt' variations, the value in the italicAngle field of the 'post' table must match the default 'slnt' value specified in the 'fvar' table.

In a variable font that implements 'wght' variations, the value in the usWeightClass field of the 'OS/2' table must match the default 'wght' value specified in the 'fvar' table.

In a variable font that implements 'wdth' variations, the value in the usWidthClass field of the 'OS/2' table must correspond to the default 'wdth' value specified in the 'fvar' table.

Note: The italic and slant axes are distinct. Fonts may use one or the other, depending on the nature of the design. Although italic designs typically have some slant, use of the italic axis does not require use of the slant axis.

Note: The post.italicAngle field uses the same scale as the 'slnt' axis. For non-default instances of a variable font, the 'slnt' axis value can be used as the post.italicAngle value for the instance.

Note: The OS/2.usWeightClass field uses the same scale as the 'wght' design axis. For non-default instances of a variable font, the 'wght' axis value can be used as the OS/2.usWeightClass value for the instance.

Note: The OS/2.usWidthClass field (and also the CSS font-stretch property) use a scale that is different from the 'wdth' axis scale, but for which there is a defined correspondence using mappings provided with the description of usWidthClass in the OS/2 table documentation. For non-default instances of a variable font, the 'wdth' axis value can be used to derive the OS/2.usWidthClass value for that instance. When mapping from 'wdth' values to usWidthClass, interpolate values between the mapped values and round, and clamp to the range 1 to 9.

Example

This example is for a hypothetical font with family name “SelawikV” that has two axes of variation, for weight and width. This table summarizes the description of the axes for the font:

Axis tag Minimum value Default value Maximum value Axis name ID
'wght' 300 400 700 256
'wdth' 62.5 100 150 257

This font also has the following named instances:

Instance subfamily name Subfamily name ID PostScript name PostScript name ID 'wght' value 'wdth' value
Regular 258 SelawikV-Regular 262 400 100
Bold 259 SelawikV-Bold 263 700 100
Condensed 260 SelawikV-Condensed 264 400 75
Condensed Bold 261 SelawikV-CondensedBold 265 700 75

The 'fvar' table is constructed as follows:

Hex data Field Comment
Header
0001 majorVersion
0000 minorVersion
0010 offsetToAxesArray 16 bytes — combined size of fields before the axes array.
0002 countSizePairs 2 count/size pairs: axis, instance
0002 axisCount 2 axes ('wght', 'wdth')
0014 axisCount Size of each variation axis record is 20 bytes.
0004 instanceCount 4 named instances
000E instanceSize Size of instance records is 14 bytes.
First variation axis record
77676874 axisTag Axis tag 'wght'.
012C0000 minValue Minimum 'wght' value is 300 (Fixed format).
01900000 defaultValue Default 'wght' value is 400.
02BC0000 maxValue Maximum 'wght' value is 700.
0000 flags
0100 axisNameID Display name “Weight” uses name ID 256.
Second variation axis record
77647468 axisTag Axis tag 'wdth'.
003E8000 minValue Minimum 'wdth' value is 62.5 (Fixed format).
00640000 defaultValue Default 'wdth' value is 100.
00960000 maxValue Maximum 'wdth' value is 150.
0000 flags
0101 axisNameID Display name “Width” uses name ID 257.
First instance record
0102 subfamilyNameID Instance subfamily name “Regular” uses name ID 258.
0000 flags
01900000 coordinates[0] 'wght' coordinate is 400.
00640000 coordinates[1] 'wdth' coordinate is 100.
0106 postScriptNameID Instance PostScript name “SelawikV-Regular” uses name ID 262.
Second instance record
0103 subfamilyNameID Instance subfamily name “Bold” uses name ID 259.
0000 flags
02BC0000 coordinates[0] 'wght' coordinate is 700.
00640000 coordinates[1] 'wdth' coordinate is 100.
0107 postScriptNameID Instance PostScript name “SelawikV-Bold” uses name ID 263.
Third instance record
0104 subfamilyNameID Instance subfamily name “Condensed” uses name ID 260.
0000 flags
01900000 coordinates[0] 'wght' coordinate is 400.
004B0000 coordinates[1] 'wdth' coordinate is 75.
0108 postScriptNameID Instance PostScript name “SelawikV-Condensed” uses name ID 264.
Fourth instance record
0105 subfamilyNameID Instance subfamily name “Condensed Bold” uses name ID 261.
0000 flags
02BC0000 coordinates[0] 'wght' coordinate is 700.
004B0000 coordinates[1] 'wdth' coordinate is 75.
0109 postScriptNameID Instance PostScript name “SelawikV-CondensedBold” uses name ID 265.

The total size of the table is 112 bytes.