Skip to content

Commit 01a21c6

Browse files
authored
CJK metrics (#159)
* Updating the vertical metrics requirements for CJK * Update metrics.md better positioning and some adjusted language * Update metrics.md * Update metrics.md Updating based on feedback from NightFury and to clarify the situation around the vmtx / vhea tables. * Update metrics.md changing naming * Update metrics.md adding further information about the vhea / vmtx table and how to set them correctly.
1 parent a8b64ac commit 01a21c6

1 file changed

Lines changed: 111 additions & 13 deletions

File tree

gf-guide/metrics.md

Lines changed: 111 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -248,26 +248,124 @@ If the font is already hosted on [fonts.google.com](http://fonts.google.com/), y
248248
249249
## CJK Vertical Metrics
250250
251-
CJK vertical metrics are based on Source Han Sans and Noto CJK fonts.
251+
Vertical metrics for CJK fonts are based on the font em-box values. This ensures that the ideographs (or syllables) are properly positioned in the center of the em-box both in horizontal and vertical typesetting.
252252
253-
The following vertical metric values must be applied to all CJK fonts
253+
The following metrics are a distinct split from the standard approach of setting vertical metrics for CJK fonts, which normally set the `sTypo` metrics to align with the em-box values. This is also how the [OT spec recommendations](https://learn.microsoft.com/en-us/typography/opentype/spec/os2#stypoascender) are written. However, following [investigation into performance of CJK fonts](https://github.com/google/fonts/issues/8911) under the primary scenarios that Google Fonts prioritizes, the following new metrics have been established:
254254
255-
| Attrib | Value | Example using 1000upm font |
255+
| Attrib | Value | Example using a 1000 UPM font such as [Iansui](https://github.com/ButTaiwan/iansui) |
256256
|-------------------------------------------|------------------------------------------|----------------------------|
257-
| OS/2.sTypoAscender | 0.88 \* font upm | 880 |
258-
| OS/2.sTypoDescender | -0.12 \* font upm | -120 |
257+
| OS/2.sTypoAscender | ideoEmBoxTop \+ (10–20% \* em-box)/2 | 940 |
258+
| OS/2.sTypoDescender | ideoEmBoxBottom \- (10–20% \* em-box)/2 | -180 |
259259
| OS/2.sTypoLineGap | 0 | 0 |
260-
| hhea.ascender | Set to look comfortable (\~1.16 \* upm) | 1160 |
261-
| hhea.descender | Set to look comfortable (\~0.288 \* upm) | -288 |
260+
| hhea.ascender | OS/2.sTypoAscender | 940 |
261+
| hhea.descender | OS/2.sTypoDescender | -180 |
262262
| hhea.lineGap | 0 | 0 |
263-
| OS/2.usWinAscent | Same as hhea.ascent | 1160 |
264-
| OS/2.usWinDescent | abs(value) of hhea.descent | 288 |
265-
| OS/2.fsSelection bit 7 (Use_Typo_Metrics) | Do not set / disabled | 0 |
263+
| OS/2.usWinAscent | Font bbox yMax | 1066 |
264+
| OS/2.usWinDescent | Font bbox yMin | 273 |
265+
| OS/2.fsSelection bit 7 (Use_Typo_Metrics) | Set / enabled | ✅ |
266+
| BASE table | Required | |
267+
| vhea / vmtx tables | Required | |
266268
267-
Our decision to follow the Adobe schema was based on Dr. Ken Lunde’s comments and his release notes on Source Han Sans:
269+
In the case of `sTypoAscender` and `sTypoDescender`, a range of values is acceptable, per the designer's perspective and specific needs. Generally ~18% tends to produce good results, but depending on the project, wider or narrower metrics may be required.
270+
271+
Unfortunately, many typesetting environments still expect that the `sTypoMetrics` will align with the em-box. As such, the `BASE` table and `vhea` / `vmtx` tables are now required. See sections below.
272+
273+
These metrics were established based on investigations into improving metrics performance of CJK fonts across the library. Please see the following issue for more information:
274+
- <https://github.com/google/fonts/issues/8911>
275+
276+
### Base Table
277+
278+
In addition to the above metrics, CJK fonts are now required to include a `BASE` table (https://learn.microsoft.com/en-us/typography/opentype/spec/baselinetags) to ensure broad compatibility.
279+
280+
For a standard square em-box font (1000 units / 1000UPM), such as [Iansui](https://github.com/ButTaiwan/iansui), the following BASE table is added to the `.fea` file.
281+
```
282+
table BASE {
283+
HorizAxis.BaseTagList icfb icft ideo romn;
284+
HorizAxis.BaseScriptList DFLT ideo -67 827 -120 0,
285+
hani ideo -67 827 -120 0,
286+
kana ideo -67 827 -120 0,
287+
latn romn -67 827 -120 0,
288+
cyrl romn -67 827 -120 0,
289+
grek romn -67 827 -120 0,
290+
291+
VertAxis.BaseTagList icfb icft ideo romn;
292+
VertAxis.BaseScriptList DFLT ideo 53 947 0 120,
293+
hani ideo 53 947 0 120,
294+
kana ideo 53 947 0 120,
295+
latn romn 53 947 0 120,
296+
cyrl romn 53 947 0 120,
297+
grek romn 53 947 0 120,
298+
} BASE;
299+
```
300+
The BASE tags above are:
301+
302+
- `icfb`: Ideographic character face bottom edge (in HorizAxis) / left edge (in VertAxis)
303+
- `icft`: Ideographic character face top edge (in HorizAxis) / right edge (in VertAxis)
304+
- `ideo`: ideographic em-box bottom edge (in HorizAxis) / left edge (in VertAxis)
305+
- `romn`: Latin baseline. Usually 0 in HorizAxis, inverse of ideo in VertAxis
306+
307+
Some additional tags which may be useful can be reviewed on the [official documentation](https://learn.microsoft.com/en-us/typography/opentype/spec/baselinetags).
308+
309+
In the case of a design that varies from the standard square em-box, you must also include `idtp` to mark the 'top' / 'right' edge of the em-box (opposite of `ideo`). For example, [WD XL Lubrifont](https://github.com/NightFurySL2001/WD-XL-font), which has a rectangular em-box with an advance width of 765, has the following base table:
310+
311+
```
312+
table BASE {
313+
HorizAxis.BaseTagList icfb icft ideo idtp romn;
314+
HorizAxis.BaseScriptList DFLT ideo -104 814 -120 880 0,
315+
hani ideo -104 814 -120 880 0,
316+
kana ideo -104 814 -120 880 0,
317+
latn romn -104 814 -120 880 0,
318+
cyrl romn -104 814 -120 880 0,
319+
grek romn -104 814 -120 880 0;
320+
321+
VertAxis.BaseTagList icfb icft ideo idtp romn;
322+
VertAxis.BaseScriptList DFLT ideo 49 716 0 765 0,
323+
hani ideo 49 716 0 765 0,
324+
kana ideo 49 716 0 765 0,
325+
latn romn 49 716 0 765 0,
326+
cyrl romn 49 716 0 765 0,
327+
grek romn 49 716 0 765 0;
328+
} BASE;
329+
```
330+
Note the `idtp` value in the VertAxis is present to indicate the narrower width.
331+
332+
### vhea and vmtx tables
333+
In order for the `vmtx` and `vhea` tables to be generated via `fontTools`, vert-specific metrics must be set in the source prior to build.
334+
335+
In `Glyphs`, these are:
336+
- `vheaVertAscender`
337+
- `vheaVertDescender`
338+
- `vheaLineGap`
339+
340+
If building from `.ufo`, these are:
341+
- `openTypeVheaVertTypoAscender`
342+
- `openTypeVheaVertDescender`
343+
- `openTypeVheaLineGap`
344+
345+
`vheaVertAscender` is the distance from the center of the glyph to the left edge (generally 500 for a `1000UPM` font).
346+
`vheaVertDescender` is the distance from the center of the glyph to the right edge (generally -500 for a `1000UPM` font).
347+
`vheaLineGap` is the horizontal space between lines of text.
348+
349+
Most build systems (such as `makeotf` & `glyphsLib`) expect the `sTypoMetrics` to align with the font em-box, and use the `sTypoMetrics` to determine values in the `vmtx` and `vhea` tables. So the advancedHeight set in the `vmtx` table will be larger than the intended em-box value, leading to undesireable space when the font is set vertically.
350+
351+
**Solutions**
352+
It is possible to add in an override method into the `.fea` file which can correct for this issue. For example:
353+
354+
```
355+
table vmtx {
356+
VertOriginY uni30FC.vert 830;
357+
VertAdvanceY uni30FC.vert 900;
358+
} vmtx;
359+
```
360+
361+
However, this approach (unless scripted), is cumbersome for a font on the scale of CJK.
362+
363+
Two alternate options using a post-production script:
364+
365+
1) Insert the incorrect `sTypo` data into the font, then correct the font metrics afterwards. The downside of this approach is that the source is not accurate to the output of the font.
366+
367+
2) Use the correct `sTypo` data in the font, then correct the `vhea` and `vmtx` tables in post-production to follow the em-box data. While this approach is not ideal either, once the toolchains catch up, the post-production script can be removed and the output will remain the same.
268368
269-
- <https://github.com/source-foundry/font-line/issues/2>
270-
- [SourceHanSansReadMe.pdf](https://github.com/adobe-fonts/source-han-sans/raw/release/SourceHanSansReadMe.pdf)
271369
272370
------------------------------------------------------------------------
273371

0 commit comments

Comments
 (0)