diff --git a/ChangeLog b/ChangeLog index d531e9318..786207d8f 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,10 @@ +2007-01-23 David Turner + + * src/autofit/aflatin.c, src/autofit/aftypes.h, src/autofit/afwarp.h, + src/autofit/afwarp.c: fix and enable the warper to improve "light" + hinting mode. This is not necessarily a final version, but it seems + to work well + 2007-01-21 Werner Lemberg * ChangeLog: Split off older entries into... diff --git a/src/autofit/aflatin.c b/src/autofit/aflatin.c index fbb9e15d0..2f3567483 100644 --- a/src/autofit/aflatin.c +++ b/src/autofit/aflatin.c @@ -1396,7 +1396,7 @@ /* compute flags depending on render mode, etc. */ mode = metrics->root.scaler.render_mode; -#ifdef AF_USE_WARPER +#ifdef zzAF_USE_WARPER if ( mode == FT_RENDER_MODE_LCD || mode == FT_RENDER_MODE_LCD_V ) { metrics->root.scaler.render_mode = mode = FT_RENDER_MODE_NORMAL; @@ -2114,7 +2114,12 @@ goto Exit; /* analyze glyph outline */ +#ifdef AF_USE_WARPER + if ( metrics->root.scaler.render_mode == FT_RENDER_MODE_LIGHT || + AF_HINTS_DO_HORIZONTAL( hints ) ) +#else if ( AF_HINTS_DO_HORIZONTAL( hints ) ) +#endif { error = af_latin_hints_detect_features( hints, AF_DIMENSION_HORZ ); if ( error ) @@ -2133,23 +2138,24 @@ /* grid-fit the outline */ for ( dim = 0; dim < AF_DIMENSION_MAX; dim++ ) { +#ifdef AF_USE_WARPER + if ( ( dim == AF_DIMENSION_HORZ && + metrics->root.scaler.render_mode == FT_RENDER_MODE_LIGHT ) ) + { + AF_WarperRec warper; + FT_Fixed scale; + FT_Pos delta; + + + af_warper_compute( &warper, hints, dim, &scale, &delta ); + af_glyph_hints_scale_dim( hints, dim, scale, delta ); + continue; + } +#endif + if ( ( dim == AF_DIMENSION_HORZ && AF_HINTS_DO_HORIZONTAL( hints ) ) || ( dim == AF_DIMENSION_VERT && AF_HINTS_DO_VERTICAL( hints ) ) ) { -#ifdef AF_USE_WARPER - if ( dim == AF_DIMENSION_HORZ && - metrics->root.scaler.render_mode == FT_RENDER_MODE_NORMAL ) - { - AF_WarperRec warper; - FT_Fixed scale; - FT_Pos delta; - - - af_warper_compute( &warper, hints, dim, &scale, &delta ); - af_glyph_hints_scale_dim( hints, dim, scale, delta ); - continue; - } -#endif af_latin_hint_edges( hints, (AF_Dimension)dim ); af_glyph_hints_align_edge_points( hints, (AF_Dimension)dim ); af_glyph_hints_align_strong_points( hints, (AF_Dimension)dim ); diff --git a/src/autofit/aftypes.h b/src/autofit/aftypes.h index a78585d1a..d3985cdd2 100644 --- a/src/autofit/aftypes.h +++ b/src/autofit/aftypes.h @@ -53,7 +53,7 @@ FT_BEGIN_HEADER /*************************************************************************/ /*************************************************************************/ -#define xxAF_USE_WARPER /* only define to use warp hinting */ +#define AF_USE_WARPER /* only define to use warp hinting */ #define xxAF_DEBUG #ifdef AF_DEBUG diff --git a/src/autofit/afwarp.c b/src/autofit/afwarp.c index c8f86c715..9d311de67 100644 --- a/src/autofit/afwarp.c +++ b/src/autofit/afwarp.c @@ -24,11 +24,11 @@ static const AF_WarpScore af_warper_weights[64] = { - 35, 20, 20, 20, 15, 12, 10, 5, 2, 1, 0, 0, 0, 0, 0, 0, + 35, 32, 30, 20, 15, 12, 10, 5, 2, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -1, -2, -5, -8,-10,-10,-20,-20,-30,-30, -30,-30,-20,-20,-10,-10, -8, -5, -2, -1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, 2, 5, 10, 12, 15, 20, 20, 20, + 0, 0, 0, 0, 0, 0, 0, 1, 2, 5, 10, 12, 15, 20, 30, 32, }; #else static const AF_WarpScore @@ -55,10 +55,10 @@ { FT_Int idx_min, idx_max, idx0; FT_UInt nn; - AF_WarpScore scores[64]; + AF_WarpScore scores[65]; - for ( nn = 0; nn < 64; nn++ ) + for ( nn = 0; nn < 65; nn++ ) scores[nn] = 0; idx0 = xx1 - warper->t1; @@ -71,16 +71,16 @@ if ( xx1min + w < warper->x2min ) - xx1min = warper->x2min - ( xx2 - xx1 ); + xx1min = warper->x2min - w; xx1max = warper->x1max; if ( xx1max + w > warper->x2max ) - xx1max = warper->x2max - ( xx2 - xx1 ); + xx1max = warper->x2max - w; idx_min = xx1min - warper->t1; idx_max = xx1max - warper->t1; - if ( idx_min > idx_max ) + if ( idx_min < 0 || idx_min > idx_max || idx_max > 64 ) { AF_LOG(( "invalid indices:\n" " min=%d max=%d, xx1=%ld xx2=%ld,\n" @@ -97,7 +97,6 @@ FT_Pos len = segments[nn].max_coord - segments[nn].min_coord; FT_Pos y0 = FT_MulFix( segments[nn].pos, scale ) + delta; FT_Pos y = y0 + ( idx_min - idx0 ); - FT_Int idx; @@ -165,7 +164,7 @@ warper->best_scale = org_scale; warper->best_delta = org_delta; - warper->best_score = 0; + warper->best_score = INT_MIN; warper->best_distort = 0; axis = &hints->axis[dim]; @@ -178,7 +177,7 @@ *a_delta = org_delta; /* get X1 and X2, minimum and maximum in original coordinates */ - if ( axis->num_segments < 1 ) + if ( num_segments < 1 ) return; #if 1 @@ -238,19 +237,33 @@ warper->wmin = warper->x2min - warper->x1max; warper->wmax = warper->x2max - warper->x1min; - if ( warper->wmin < warper->w0 - 32 ) - warper->wmin = warper->w0 - 32; +#if 1 + { + int margin = 16; - if ( warper->wmax > warper->w0 + 32 ) - warper->wmax = warper->w0 + 32; + if ( warper->w0 <= 128 ) + { + margin = 8; + if ( warper->w0 <= 96 ) + margin = 4; + } + + if ( warper->wmin < warper->w0 - margin ) + warper->wmin = warper->w0 - margin; + + if ( warper->wmax > warper->w0 + margin ) + warper->wmax = warper->w0 + margin; + } if ( warper->wmin < warper->w0 * 3 / 4 ) warper->wmin = warper->w0 * 3 / 4; if ( warper->wmax > warper->w0 * 5 / 4 ) warper->wmax = warper->w0 * 5 / 4; - - /* warper->wmin = warper->wmax = warper->w0; */ +#else + /* no scaling, just translation */ + warper->wmin = warper->wmax = warper->w0; +#endif for ( w = warper->wmin; w <= warper->wmax; w++ ) { diff --git a/src/autofit/afwarp.h b/src/autofit/afwarp.h index 6ca1ce7ba..2c5b4c04a 100644 --- a/src/autofit/afwarp.h +++ b/src/autofit/afwarp.h @@ -33,7 +33,6 @@ FT_BEGIN_HEADER typedef struct AF_WarperRec_ { - FT_Int X1, X2; FT_Pos x1, x2; FT_Pos t1, t2; FT_Pos x1min, x1max;