[luatex] Question about creating virtual fonts

Marcel Fabian Krüger tex at 2krueger.de
Wed Jul 3 14:42:30 CEST 2019

Dear Henri,

there are two problems: First the sizes. You observed that all
characters appear to have zero width and adding a size field makes the
font disappear. The problem is that the size has to be given in scaled
points, so your size "10" equals "10sp" or "0.00015pt". So if you
specify the size field, the font is loaded with that fontsize and
is therefore hard to see. This size is also given to `font.read_tfm`, so
every character gets the width it would have with such a small fontsize,
resulting in effectivly zero width. You can fix both problems by passing
`655360` (10*2^16) instead. This leaves the problem of the digits
appearing "in reverse" (now *they* appear on top of each other).
TeX has to keep track of your current position on the page and it can't
know what your specials are doing. So after `{ "char", i }` TeX knows
that it moved by one character width to the right, but it doesn't
realize that the `Q` moves it back to the left. So it gets out of sync.
To avoid this, `q` and `Q` should (like `\pdfsave` and `\pdfrestore`)
always be used in a way that TeX believes these to be at the same point.
This can be archived through `push` and `pop`.
So a working version would be

f = font.read_tfm("cmtt10", 655360)
f.name = "cmtt10-digits"
f.type = "virtual"
f.fonts = {
        name = "cmtt10", 
        size = 655360
for i,v in pairs(f.characters) do
    local height = v.height
    local width = v.width
    if (string.char(i)):find("[1234567890]") then
        v.commands = {
            { "pdf", "origin", string.format("q 1 0 0 -1 0 \csstring\%.5f cm", height/65781.76) },
            { "push" },
            { "char", i },
            { "pop" },
            { "pdf", "origin", "Q" },
        v.commands = {
            { "char", i },
tex.definefont("myfont", font.define(f))


\cmtt abc 1234567 def

\myfont abc 1234567 def


Best regards,
Marcel Krüger

More information about the luatex mailing list