|
|
|
@ -492,42 +492,6 @@ hb_ot_position_complex (hb_ot_shape_context_t *c) |
|
|
|
|
return ret; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static inline void |
|
|
|
|
hb_ot_truetype_kern (hb_ot_shape_context_t *c) |
|
|
|
|
{ |
|
|
|
|
unsigned int count = c->buffer->len; |
|
|
|
|
hb_mask_t kern_mask = c->plan->map.get_1_mask (HB_DIRECTION_IS_HORIZONTAL (c->buffer->props.direction) ? |
|
|
|
|
HB_TAG ('k','e','r','n') : HB_TAG ('v','k','r','n')); |
|
|
|
|
|
|
|
|
|
if (unlikely (!count)) return; |
|
|
|
|
|
|
|
|
|
bool enabled = c->buffer->info[0].mask & kern_mask; |
|
|
|
|
for (unsigned int i = 1; i < count; i++) |
|
|
|
|
{ |
|
|
|
|
bool next = c->buffer->info[i].mask & kern_mask; |
|
|
|
|
if (enabled && next) |
|
|
|
|
{ |
|
|
|
|
hb_position_t x_kern, y_kern, kern1, kern2; |
|
|
|
|
c->font->get_glyph_kerning_for_direction (c->buffer->info[i - 1].codepoint, c->buffer->info[i].codepoint, |
|
|
|
|
c->buffer->props.direction, |
|
|
|
|
&x_kern, &y_kern); |
|
|
|
|
|
|
|
|
|
kern1 = x_kern >> 1; |
|
|
|
|
kern2 = x_kern - kern1; |
|
|
|
|
c->buffer->pos[i - 1].x_advance += kern1; |
|
|
|
|
c->buffer->pos[i].x_advance += kern2; |
|
|
|
|
c->buffer->pos[i].x_offset += kern2; |
|
|
|
|
|
|
|
|
|
kern1 = y_kern >> 1; |
|
|
|
|
kern2 = y_kern - kern1; |
|
|
|
|
c->buffer->pos[i - 1].y_advance += kern1; |
|
|
|
|
c->buffer->pos[i].y_advance += kern2; |
|
|
|
|
c->buffer->pos[i].y_offset += kern2; |
|
|
|
|
} |
|
|
|
|
enabled = next; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static inline void |
|
|
|
|
hb_ot_position (hb_ot_shape_context_t *c) |
|
|
|
|
{ |
|
|
|
@ -544,7 +508,7 @@ hb_ot_position (hb_ot_shape_context_t *c) |
|
|
|
|
/* Visual fallback goes here. */ |
|
|
|
|
|
|
|
|
|
if (fallback) |
|
|
|
|
hb_ot_truetype_kern (c); |
|
|
|
|
_hb_ot_shape_fallback_kern (c->plan, c->font, c->buffer); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|