[Fontconfig] libxft2 kerning difficulty
Dan Egnor
egnor at ofb.net
Tue Mar 4 14:14:12 EST 2003
Hi,
I'm using libxft2 and fontconfig (version 2.1), as currently packaged
for Debian unstable.
I'm trying to understand the precise meaning of the XGlyphInfo structure
as returned by the XftTextExtents*() functions with libxft2. The
structure has six members: x, y, width, height, xOff, yOff. Here's my
understanding (from reading documentation) of their meaning:
Consider a rectangle with the upper left corner at (0, 0) and size
(width, height). This is a sort of "bounding rectangle" that
represents the extent of the text's ink. If the text is drawn inside
this rectangle, the location (x, y) marks the "hot spot", which is the
position at the "start" of the "baseline", whatever that means for
this particular string. The location (x + xOff, y + yOff) represents
the "natural start" of the "baseline" for any text that would follow.
When you actually go to draw text with XftDraw*(), you specify the
location of that "hot spot". If you actually pass in (x, y), you
should expect the text to go from (0, 0) to (width, height).
How'd I do?
Now let's take some example glyphs. I'm going to be using MS fonts
for these examples (from msttcorefonts). If this is actually a bug
in the fonts, consider my question to be "how do I work around the
bugs in real-world fonts". These are also not isolated examples, and
I can try to find them in other fonts as well.
First example is the lowercase 'd' and 'b' in 'Comic Sans MS-8'.
(Antialiasing is off for these examples.) I'm going to outline that
rectangle I described above with |, mark the hot spot with [ ], and
use -->[ ] to mark the "logical start" defined by xOff and yOff.
|. . . . * .| |* . . . . .|
|. . . . * .| |* . . . . .|
|. . . . * .| |* . . . . .|
|. * * * * .| |* * * * . .|
|* . . . * .| |* . . . * .|
|* . . . * .| |* . . . * .|
|* . . . * .| |* . . . * .|
|* . . . * .| |* . . . * .|
|. * * * * .| |* * * * . .|
[ ]-------->[ ] [ ]------->[ ]
width = 6 width = 6
height = 9 height = 9
x = -1 x = 1
y = 9 y = 9
xOff = 6 xOff = 6
yOff = 0 yOff = 0
The immediate question is why the hot spot is moved to the left for the
'd' character, and what that's supposed to mean, and why isn't xOff one
greater for 'd' than it is for 'b'? Also, width=6, but the actual ink
is only 5 pixels wide; is the 'width' value supposed to include
intercharacter spacing? If so, why bother with xOff, and how would I
find the extent of the physical ink?
Next example is the lowercase 'g' and 'p' in 'Arial-8'.
|. . * * . *| |* . * * .|
|. * . . * *| |* * . . *|
|. * . . . *| |* . . . *|
|. * . . . *| |* . . . *|
|. * . . * *| |* * . . *|
|. . * * . *| |* . * * .|
|.[.]------*->[ ] [*]-------->[ ]
|. * * * * .| |* . . . .|
width = 6 width = 5
height = 8 height = 8
x = 1 x = 0
y = 6 y = 6
xOff = 6 xOff = 6
yOff = 0 yOff = 0
Here the 'g' seems to include some margin -- at the left, this time --
but the 'p' does not. The hot spot seems more accurately placed than
it was for Comic Sans, though.
Is it just that the FreeType renderer has trouble at smaller font
sizes? I can complain to them, but I don't know what these Xft
concepts translate into at the FreeType level. The glyphs *look*
just great (as long as antialiasing is off!); I'm just having trouble
lining them up properly!
(If I turn the autohinter on, the spacing is more regular, but the
glyphs look like hell.)
Dan
More information about the Fontconfig
mailing list