Search code examples
pythonfontspython-imaging-librarymultilingualttx-fonttools

How to access different glyph variables in a font file?


I'm using fonttools to check if a font file (otf format) contains different glyph for different languages. For example, an unicode character '\u76F4' in chinese should be rendered like enter image description here

But in Japanese, '\u76F4' should be rendered like enter image description here

I'm not sure if the font I checked contains both two glyph variables for '\u76F4'.

I write these code in jupyter notebook to check how '\u76F4' is rendered in the font

from PIL import ImageFont, ImageDraw, Image

image = Image.new(mode='L', size=(128,128), color=224)
draw = ImageDraw.Draw(image)
imageFont = ImageFont.truetype(r'SiYuanHeavyFont.otf', 64)
draw.text((0, 0), '\u76F4', font=imageFont)
image

The result is always chinese chracter enter image description here

I don't know how to check if the japanese glyph for '\u76F4' exists in the font, if exists, how can I render it in jupyter notebook?

More font details:

> font.tables
{'cmap': <'cmap' table at 1cef8baf210>,
 'CFF ': <'CFF ' table at 1cefb773d90>,
 'GlyphOrder': <fontTools.ttLib.ttFont.GlyphOrder at 0x1ce8322b250>,
 'head': <'head' table at 1ce832d9890>,
 'hhea': <'hhea' table at 1ce81fa4090>,
 'maxp': <'maxp' table at 1ce87072910>,
 'OS/2': <'OS/2' table at 1ce87067590>,
 'name': <'name' table at 1ce83235910>,
 'post': <'post' table at 1ce8714c190>,
 'BASE': <'BASE' table at 1ce867da8d0>,
 'GDEF': <'GDEF' table at 1ce832b4490>,
 'GPOS': <'GPOS' table at 1ce88c0da10>,
 'GSUB': <'GSUB' table at 1ce87c598d0>,
 'hmtx': <'hmtx' table at 1ce87142990>,
 'DSIG': <'DSIG' table at 1ce867db890>}

Thanks in advance!


Solution

  • The locl feature in an OpenType font provides the localised glyphs.

    To used localised glyphs, you need to access the locl feature for that language in the font. To access them using PIL, you need to use the raqm backend, which will require harfbuzz, firbidi and raqm to be installed.

    Assuming raqm is installed and your font has a locl feature for Japanese, your code is simply:

    from PIL import ImageFont, ImageDraw, Image
    image = Image.new(mode='L', size=(128,128), color=224)
    draw = ImageDraw.Draw(image)
    imageFont = ImageFont.truetype(r'SiYuanHeavyFont.otf', 64)
    draw.text((0, 0), '\u76F4', font=imageFont, language="ja")
    image