[truetype] Fix 'sbix' table handling.
* src/sfnt/ttsbit.c (tt_face_load_sbix_image): Correct calculation of 'metrics->horiBearingY'. Set vertical metrics. * src/sfnt/sfobjs.c (sfnt_load_face): Adjust setting of `FT_FACE_FLAG_SBIX`. Handle metrics of fonts with 'sbix' table. * src/truetype/ttgload.c (TT_Load_Glyph): For 'sbix' embedded bitmaps, apply bbox offset and bearing values of the corresponding glyph in the 'glyf' table if it exists and has a contour. * src/truetype/ttobjs.c (tt_face_init): Handle font with 'sbix' table. Fixes issue #998.
This commit is contained in:
parent
907715a6a2
commit
ac4c1ebf7e
|
@ -851,12 +851,6 @@
|
|||
is_apple_sbit = 0;
|
||||
is_apple_sbix = !face->goto_table( face, TTAG_sbix, stream, 0 );
|
||||
|
||||
/* Apple 'sbix' color bitmaps are rendered scaled and then the 'glyf'
|
||||
* outline rendered on top. We don't support that yet, so just ignore
|
||||
* the 'glyf' outline and advertise it as a bitmap-only font. */
|
||||
if ( is_apple_sbix )
|
||||
has_outline = FALSE;
|
||||
|
||||
/* if this font doesn't contain outlines, we try to load */
|
||||
/* a `bhed' table */
|
||||
if ( !has_outline && sfnt->load_bhed )
|
||||
|
@ -1059,10 +1053,12 @@
|
|||
|
||||
if ( has_outline == TRUE )
|
||||
{
|
||||
flags |= FT_FACE_FLAG_SCALABLE; /* scalable outlines */
|
||||
|
||||
if ( face->sbit_table_type == TT_SBIT_TABLE_TYPE_SBIX )
|
||||
flags |= FT_FACE_FLAG_SBIX; /* and 'sbix' bitmaps */
|
||||
/* by default (and for backward compatibility) we handle */
|
||||
/* fonts with an 'sbix' table as bitmap-only */
|
||||
if ( is_apple_sbix )
|
||||
flags |= FT_FACE_FLAG_SBIX; /* with 'sbix' bitmaps */
|
||||
else
|
||||
flags |= FT_FACE_FLAG_SCALABLE; /* scalable outlines */
|
||||
}
|
||||
|
||||
/* The sfnt driver only supports bitmap fonts natively, thus we */
|
||||
|
@ -1286,7 +1282,8 @@
|
|||
*
|
||||
* Set up metrics.
|
||||
*/
|
||||
if ( FT_IS_SCALABLE( root ) )
|
||||
if ( FT_IS_SCALABLE( root ) ||
|
||||
FT_HAS_SBIX( root ) )
|
||||
{
|
||||
/* XXX What about if outline header is missing */
|
||||
/* (e.g. sfnt wrapped bitmap)? */
|
||||
|
|
|
@ -1580,17 +1580,34 @@
|
|||
|
||||
if ( !error )
|
||||
{
|
||||
FT_Short abearing;
|
||||
FT_Short abearing; /* not used here */
|
||||
FT_UShort aadvance;
|
||||
|
||||
|
||||
tt_face_get_metrics( face, FALSE, glyph_index, &abearing, &aadvance );
|
||||
|
||||
metrics->horiBearingX = (FT_Short)originOffsetX;
|
||||
metrics->horiBearingY = (FT_Short)( -originOffsetY + metrics->height );
|
||||
metrics->vertBearingX = (FT_Short)originOffsetX;
|
||||
|
||||
metrics->horiBearingY = (FT_Short)( originOffsetY + metrics->height );
|
||||
metrics->vertBearingY = (FT_Short)originOffsetY;
|
||||
|
||||
metrics->horiAdvance = (FT_UShort)( aadvance *
|
||||
face->root.size->metrics.x_ppem /
|
||||
face->header.Units_Per_EM );
|
||||
|
||||
if ( face->vertical_info )
|
||||
tt_face_get_metrics( face, TRUE, glyph_index, &abearing, &aadvance );
|
||||
else if ( face->os2.version != 0xFFFFU )
|
||||
aadvance = (FT_UShort)FT_ABS( face->os2.sTypoAscender -
|
||||
face->os2.sTypoDescender );
|
||||
else
|
||||
aadvance = (FT_UShort)FT_ABS( face->horizontal.Ascender -
|
||||
face->horizontal.Descender );
|
||||
|
||||
metrics->vertAdvance = (FT_UShort)( aadvance *
|
||||
face->root.size->metrics.x_ppem /
|
||||
face->header.Units_Per_EM );
|
||||
}
|
||||
|
||||
return error;
|
||||
|
|
|
@ -2897,8 +2897,12 @@
|
|||
}
|
||||
else
|
||||
{
|
||||
if ( FT_IS_SCALABLE( glyph->face ) )
|
||||
if ( FT_IS_SCALABLE( glyph->face ) ||
|
||||
FT_HAS_SBIX( glyph->face ) )
|
||||
{
|
||||
TT_Face face = (TT_Face)glyph->face;
|
||||
|
||||
|
||||
/* for the bbox we need the header only */
|
||||
(void)tt_loader_init( &loader, size, glyph, load_flags, TRUE );
|
||||
(void)load_truetype_glyph( &loader, glyph_index, 0, TRUE );
|
||||
|
@ -2906,6 +2910,35 @@
|
|||
glyph->linearHoriAdvance = loader.linear;
|
||||
glyph->linearVertAdvance = loader.vadvance;
|
||||
|
||||
/* Bitmaps from the 'sbix' table need special treatment: */
|
||||
/* if there is a glyph contour, the bitmap origin must be */
|
||||
/* shifted to be relative to the lower left corner of the */
|
||||
/* glyph bounding box, also taking the left-side bearing */
|
||||
/* (or top bearing) into account. */
|
||||
if ( face->sbit_table_type == TT_SBIT_TABLE_TYPE_SBIX &&
|
||||
loader.n_contours > 0 )
|
||||
{
|
||||
FT_Int bitmap_left;
|
||||
FT_Int bitmap_top;
|
||||
|
||||
|
||||
if ( load_flags & FT_LOAD_VERTICAL_LAYOUT )
|
||||
{
|
||||
/* This is a guess, since Apple's CoreText engine doesn't */
|
||||
/* really do vertical typesetting. */
|
||||
bitmap_left = loader.bbox.xMin;
|
||||
bitmap_top = loader.top_bearing;
|
||||
}
|
||||
else
|
||||
{
|
||||
bitmap_left = loader.left_bearing;
|
||||
bitmap_top = loader.bbox.yMin;
|
||||
}
|
||||
|
||||
glyph->bitmap_left += FT_MulFix( bitmap_left, x_scale ) >> 6;
|
||||
glyph->bitmap_top += FT_MulFix( bitmap_top, y_scale ) >> 6;
|
||||
}
|
||||
|
||||
/* sanity checks: if `xxxAdvance' in the sbit metric */
|
||||
/* structure isn't set, use `linearXXXAdvance' */
|
||||
if ( !glyph->metrics.horiAdvance && glyph->linearHoriAdvance )
|
||||
|
|
|
@ -727,7 +727,8 @@
|
|||
if ( error )
|
||||
goto Exit;
|
||||
|
||||
if ( FT_IS_SCALABLE( ttface ) )
|
||||
if ( FT_IS_SCALABLE( ttface ) ||
|
||||
FT_HAS_SBIX( ttface ) )
|
||||
{
|
||||
#ifdef FT_CONFIG_OPTION_INCREMENTAL
|
||||
if ( !ttface->internal->incremental_interface )
|
||||
|
|
Loading…
Reference in New Issue