[base] Fix mono bitmap presetting (#53896).

It is rather fundamental to set monochrome bitmap based on rounded
CBox because the b/w rasterizer turns on pixels when their centers are
inside the glyph outline. The dropout control is unpredictable and can
distort narrow glyphs if the bitmap is too wide.

Reported by Chris Liddell.

* src/base/ftobjs.c (ft_glyphslot_preset_bitmap): If BBox boundaries
are too close, adjust them before rounding.
This commit is contained in:
Alexei Podtelezhnikov 2018-05-15 21:47:18 -04:00
parent 49c5e24a14
commit f1458d2e44
2 changed files with 28 additions and 20 deletions

View File

@ -1,3 +1,17 @@
2018-05-15 Alexei Podtelezhnikov <apodtele@gmail.com>
[base] Fix mono bitmap presetting (#53896).
It is rather fundamental to set monochrome bitmap based on rounded
CBox because the b/w rasterizer turns on pixels when their centers are
inside the glyph outline. The dropout control is unpredictable and can
distort narrow glyphs if the bitmap is too wide.
Reported by Chris Liddell.
* src/base/ftobjs.c (ft_glyphslot_preset_bitmap): If BBox boundaries
are too close, adjust them before rounding.
2018-05-15 Werner Lemberg <wl@gnu.org>
[psaux] Fix compiler warning (#53915).

View File

@ -374,32 +374,26 @@
/* unless the rounded box can collapse for a narrow glyph */
if ( cbox.xMax - cbox.xMin < 64 )
{
cbox.xMin = FT_PIX_FLOOR( cbox.xMin );
cbox.xMax = FT_PIX_CEIL_LONG( cbox.xMax );
}
else
{
cbox.xMin = FT_PIX_ROUND_LONG( cbox.xMin );
cbox.xMax = FT_PIX_ROUND_LONG( cbox.xMax );
cbox.xMin = ( cbox.xMin + cbox.xMax ) / 2 - 32;
cbox.xMax = cbox.xMin + 64;
}
cbox.xMin = FT_PIX_ROUND_LONG( cbox.xMin );
cbox.xMax = FT_PIX_ROUND_LONG( cbox.xMax );
if ( cbox.yMax - cbox.yMin < 64 )
{
cbox.yMin = FT_PIX_FLOOR( cbox.yMin );
cbox.yMax = FT_PIX_CEIL_LONG( cbox.yMax );
cbox.yMin = ( cbox.yMin + cbox.yMax ) / 2 - 32;
cbox.yMax = cbox.yMin + 64;
}
else
{
cbox.yMin = FT_PIX_ROUND_LONG( cbox.yMin );
cbox.yMax = FT_PIX_ROUND_LONG( cbox.yMax );
}
#else
cbox.xMin = FT_PIX_FLOOR( cbox.xMin );
cbox.yMin = FT_PIX_FLOOR( cbox.yMin );
cbox.xMax = FT_PIX_CEIL_LONG( cbox.xMax );
cbox.yMax = FT_PIX_CEIL_LONG( cbox.yMax );
#endif
cbox.yMin = FT_PIX_ROUND_LONG( cbox.yMin );
cbox.yMax = FT_PIX_ROUND_LONG( cbox.yMax );
break;
#else
goto Round;
#endif
case FT_RENDER_MODE_LCD:
pixel_mode = FT_PIXEL_MODE_LCD;