Fix hiding of default_ignorables if font doesn't have space glyph

Based on patch from Jonathan Kew.  See discussion on the list.
This commit is contained in:
Behdad Esfahbod 2013-09-27 17:06:29 -04:00
parent 078de49ca1
commit 3d2c4f0c2f
1 changed files with 30 additions and 10 deletions

View File

@ -533,22 +533,42 @@ hb_ot_hide_default_ignorables (hb_ot_shape_context_t *c)
if (c->buffer->flags & HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES) if (c->buffer->flags & HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES)
return; return;
hb_codepoint_t space = 0; hb_codepoint_t space;
enum {
SPACE_DONT_KNOW,
SPACE_AVAILABLE,
SPACE_UNAVAILABLE
} space_status = SPACE_DONT_KNOW;
unsigned int count = c->buffer->len; unsigned int count = c->buffer->len;
hb_glyph_info_t *info = c->buffer->info;
hb_glyph_position_t *pos = c->buffer->pos;
unsigned int j = 0;
for (unsigned int i = 0; i < count; i++) for (unsigned int i = 0; i < count; i++)
if (unlikely (!is_a_ligature (c->buffer->info[i]) &&
_hb_glyph_info_is_default_ignorable (&c->buffer->info[i])))
{ {
if (!space) { if (unlikely (!is_a_ligature (info[i]) &&
/* We assume that the space glyph is not gid0. */ _hb_glyph_info_is_default_ignorable (&info[i])))
if (unlikely (!c->font->get_glyph (' ', 0, &space)) || !space) {
return; /* No point! */ if (space_status == SPACE_DONT_KNOW)
space_status = c->font->get_glyph (' ', 0, &space) ? SPACE_AVAILABLE : SPACE_UNAVAILABLE;
if (space_status == SPACE_AVAILABLE)
{
info[i].codepoint = space;
pos[i].x_advance = 0;
pos[i].y_advance = 0;
} }
c->buffer->info[i].codepoint = space; else
c->buffer->pos[i].x_advance = 0; continue; /* Delete it. */
c->buffer->pos[i].y_advance = 0;
} }
if (j != i)
{
info[j] = info[i];
pos[j] = pos[i];
}
j++;
}
c->buffer->len = j;
} }