[luatex] Kerning: when does it not work?

Paul Isambert zappathustra at free.fr
Tue May 3 16:58:28 CEST 2011

Le 03/05/2011 14:57, Ulrike Fischer a écrit :
> Am Tue, 03 May 2011 13:44:27 +0200 schrieb Paul Isambert:
>>> Reading Paul's answer, I realize that the technical workings of
>>> font kerns are more complex than I thought. From a layman's
>>> perspective, though, fixing the issue of suppressed kerns on the
>>> most fundamental level possible (if that is possible) and
>>> offering a "transparent" solution to users would probably be
>>> best: It would, therefore, be great if adjustments to pair
>>> kerning made in OTF feature files (or by any other means) simply
>>> worked "out of the box" and like expected for every instance of
>>> the respective glyph pair.
>> That should be the case when Taco implements it. So rejoice!
> I'm not sure that this will solve all of Till's problems. After all
> there must also exist a way to suppress kerning between two glyphs -
> and if a macro inserts such a "kerning stopper" between glyphs I
> don't see what the engine can do about it.
> Regarding Till's concrete problems (\url and biblatex) I wouldn't
> bet that they insert only penalties between the glyphs.

I haven't been able to run the example correctly (my LaTeX installation 
is far from maintained, let alone LuaLaTeX). For instance I haven't been 
able to make the feature file work. Anyway I've analysed what is produce 
by \url{http://}, and the result is (nodes are separated by space; for 
glyphs I give the character):

math_node h t t p glue_node : glue_node / / math_node

So the problem here stems from glues, not penalties, between characters. 
I suppose that's the same with biblatex (glues around the slash in e.g. 
6/2, to allow linebreaking). And it would be totally absurd to require 
that kern pairs be applied across glues; on the other hand, a 
LuaTeX-aware package should be able to mark such glues (e.g. with 
attributes) and to insert the kerns with something similar to the code 
I've proposed.  Yet it would seem much more logical to me to insert real 
penalties instead of phantom spaces (I've checked, those spaces have no 
width nor stretch nor shrink, so they're really here for the line break, 
I suppose), and I think the packages should be corrected (then my hack 
or in the long term LuaTeX's default behavior will work correctly).

As for the kerning stopper you mention, Ulrike, I go for \kern0pt. Of 
course kern pairs should be applied only across non-typographic things 
like penalties or whatsits (although that case isn't obvious, since a 
whatsit might very well be a special with instructions for drawing).

Meanwhile, Till, here's a solution that ignores glues with 0 width and 
stretch and shrink and insert kern pairs; again, I've tested it with 
plain TeX, hope it'll work in your document.

local GLYF = node.id("glyph")
local GLUE = node.id("glue")
local KERN = node.id("kern")

local function add_kerns (head)
   for glyph in node.traverse_id(GLYF, head) do
     local next = glyph.next
     while next and next.id == GLUE and next.spec.width == 0 and 
next.spec.stretch == 0 and next.spec.shrink == 0 do
       next = next.next
     if next and next.id == GLYF then
       if glyph.font == next.font then
         local kerns = font.getfont(glyph.font).characters[glyph.char].kerns
         if kerns and kerns[next.char] then
           local kern = node.new(KERN, 1)
           kern.kern = kerns[next.char]
           node.insert_after(head, next, kern)

luatexbase.add_to_callback("kerning", add_kerns, "add_kerns")


More information about the luatex mailing list