Add su[pport for symbol fonts

Adds FC_SYMBOL.

This affects fonts having a cmap with platform 3 encoding 0.
We now map their glyphs from the PUA area to the Latin1 area.

See thread "Webdings and other MS symbol fonts don't display"
on the mailing list.

Test before/after with:
$ pango-view --markup --text='<span fallback="false">&#xd7;&#xf0d7;</span>' --font=Wingdings
This commit is contained in:
Behdad Esfahbod 2015-05-18 15:26:03 -07:00
parent ead7275e05
commit bcfe167e3d
6 changed files with 59 additions and 3 deletions

View File

@ -177,6 +177,7 @@ convenience for the application's rendering mechanism.
scalable FC_SCALABLE Bool Whether glyphs can be scaled
scale FC_SCALE Double Scale factor for point->pixel
conversions (deprecated)
symbol FC_SYMBOL Bool Whether font uses MS symbol-font encoding
color FC_COLOR Bool Whether any glyphs have color
dpi FC_DPI Double Target dots per inch
rgba FC_RGBA Int unknown, rgb, bgr, vrgb,

View File

@ -96,6 +96,7 @@ typedef int FcBool;
#define FC_SCALABLE "scalable" /* Bool */
#define FC_COLOR "color" /* Bool */
#define FC_SCALE "scale" /* double (deprecated) */
#define FC_SYMBOL "symbol" /* Bool */
#define FC_DPI "dpi" /* double */
#define FC_RGBA "rgba" /* Int */
#define FC_MINSPACE "minspace" /* Bool use minimum line spacing */

View File

@ -38,6 +38,7 @@ static const struct {
{ FC_GLOBAL_ADVANCE_OBJECT, FcTrue }, /* !FC_LOAD_IGNORE_GLOBAL_ADVANCE_WIDTH */
{ FC_EMBEDDED_BITMAP_OBJECT, FcTrue }, /* !FC_LOAD_NO_BITMAP */
{ FC_DECORATIVE_OBJECT, FcFalse },
{ FC_SYMBOL_OBJECT, FcFalse },
};
#define NUM_FC_BOOL_DEFAULTS (int) (sizeof FcBoolDefaults / sizeof FcBoolDefaults[0])

View File

@ -1201,6 +1201,8 @@ FcFreeTypeQueryFace (const FT_Face face,
FcRange *r = NULL;
double lower_size = 0.0L, upper_size = DBL_MAX;
FcBool symbol = FcFalse;
FcInitDebug (); /* We might be called with no initizalization whatsoever. */
pat = FcPatternCreate ();
@ -1803,6 +1805,11 @@ FcFreeTypeQueryFace (const FT_Face face,
if (!cs)
goto bail1;
/* The FcFreeTypeCharSetAndSpacing() chose the encoding; test it for symbol. */
symbol = face->charmap && face->charmap->encoding == FT_ENCODING_MS_SYMBOL;
if (!FcPatternAddBool (pat, FC_SYMBOL, symbol))
goto bail1;
#if HAVE_FT_GET_BDF_PROPERTY
/* For PCF fonts, override the computed spacing with the one from
the property */
@ -1835,9 +1842,18 @@ FcFreeTypeQueryFace (const FT_Face face,
if (!FcPatternAddCharSet (pat, FC_CHARSET, cs))
goto bail2;
ls = FcFreeTypeLangSet (cs, exclusiveLang);
if (!ls)
goto bail2;
if (!symbol)
{
ls = FcFreeTypeLangSet (cs, exclusiveLang);
if (!ls)
goto bail2;
}
else
{
/* Symbol fonts don't cover any language, even though they
* claim to support Latin1 range. */
ls = FcLangSetCreate ();
}
if (!FcPatternAddLangSet (pat, FC_LANG, ls))
{
@ -2093,6 +2109,22 @@ FcFreeTypeCharIndex (FT_Face face, FcChar32 ucs4)
glyphindex = FT_Get_Char_Index (face, (FT_ULong) ucs4);
if (glyphindex)
return glyphindex;
if (ucs4 < 0x100 && face->charmap &&
face->charmap->encoding == FT_ENCODING_MS_SYMBOL)
{
/* For symbol-encoded OpenType fonts, we duplicate the
* U+F000..F0FF range at U+0000..U+00FF. That's what
* Windows seems to do, and that's hinted about at:
* http://www.microsoft.com/typography/otspec/recom.htm
* under "Non-Standard (Symbol) Fonts".
*
* See thread with subject "Webdings and other MS symbol
* fonts don't display" on mailing list from May 2015.
*/
glyphindex = FT_Get_Char_Index (face, (FT_ULong) ucs4 + 0xF000);
if (glyphindex)
return glyphindex;
}
}
#if HAVE_FT_HAS_PS_GLYPH_NAMES
/*
@ -2253,6 +2285,23 @@ FcFreeTypeCharSetAndSpacingForSize (FT_Face face, FcBlanks *blanks, int *spacing
}
ucs4 = FT_Get_Next_Char (face, ucs4, &glyph);
}
if (fcFontEncodings[o] == FT_ENCODING_MS_SYMBOL)
{
/* For symbol-encoded OpenType fonts, we duplicate the
* U+F000..F0FF range at U+0000..U+00FF. That's what
* Windows seems to do, and that's hinted about at:
* http://www.microsoft.com/typography/otspec/recom.htm
* under "Non-Standard (Symbol) Fonts".
*
* See thread with subject "Webdings and other MS symbol
* fonts don't display" on mailing list from May 2015.
*/
for (ucs4 = 0xF000; ucs4 < 0xF100; ucs4++)
{
if (FcCharSetHasChar (fcs, ucs4))
FcCharSetAddChar (fcs, ucs4 - 0xF000);
}
}
#ifdef CHECK
for (ucs4 = 0; ucs4 < 0x10000; ucs4++)
{
@ -2267,6 +2316,8 @@ FcFreeTypeCharSetAndSpacingForSize (FT_Face face, FcBlanks *blanks, int *spacing
}
#endif
}
break;
}
#if HAVE_FT_HAS_PS_GLYPH_NAMES
/*

View File

@ -292,6 +292,7 @@ typedef enum _FcMatcherPriority {
PRI1(LANG),
PRI_FAMILY_WEAK,
PRI_POSTSCRIPT_NAME_WEAK,
PRI1(SYMBOL),
PRI1(SPACING),
PRI1(SIZE),
PRI1(PIXEL_SIZE),

View File

@ -69,4 +69,5 @@ FC_OBJECT (PRGNAME, FcTypeString, NULL)
FC_OBJECT (HASH, FcTypeString, NULL) /* deprecated */
FC_OBJECT (POSTSCRIPT_NAME, FcTypeString, FcComparePostScript)
FC_OBJECT (COLOR, FcTypeBool, FcCompareBool)
FC_OBJECT (SYMBOL, FcTypeBool, FcCompareBool)
/* ^-------------- Add new objects here. */