-
Notifications
You must be signed in to change notification settings - Fork 593
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Substituting ZWJ #2883
Comments
Something like this to always preserve OTL-processed glyphs? diff --git a/src/hb-ot-shape.cc b/src/hb-ot-shape.cc
index 92831e022..edad393af 100644
--- a/src/hb-ot-shape.cc
+++ b/src/hb-ot-shape.cc
@@ -775,6 +775,13 @@ hb_ot_zero_width_default_ignorables (const hb_buffer_t *buffer)
pos[i].x_advance = pos[i].y_advance = pos[i].x_offset = pos[i].y_offset = 0;
}
+static bool
+_hb_glyph_info_hide_default_ignorable (const hb_glyph_info_t *info)
+{
+ return _hb_glyph_info_is_default_ignorable (info) &&
+ !(_hb_glyph_info_get_glyph_props (info) & HB_OT_LAYOUT_GLYPH_PROPS_PRESERVE);
+}
+
static void
hb_ot_hide_default_ignorables (hb_buffer_t *buffer,
hb_font_t *font)
@@ -793,12 +800,12 @@ hb_ot_hide_default_ignorables (hb_buffer_t *buffer,
/* Replace default-ignorables with a zero-advance invisible glyph. */
for (unsigned int i = 0; i < count; i++)
{
- if (_hb_glyph_info_is_default_ignorable (&info[i]))
+ if (_hb_glyph_info_hide_default_ignorable (&info[i]))
info[i].codepoint = invisible;
}
}
else
- hb_ot_layout_delete_glyphs_inplace (buffer, _hb_glyph_info_is_default_ignorable);
+ hb_ot_layout_delete_glyphs_inplace (buffer, _hb_glyph_info_hide_default_ignorable);
} This seems to break |
Probably a better patch, since diff --git a/src/hb-ot-layout.hh b/src/hb-ot-layout.hh
index f3bb15581..2fd759b3a 100644
--- a/src/hb-ot-layout.hh
+++ b/src/hb-ot-layout.hh
@@ -314,13 +314,17 @@ _hb_glyph_info_get_unicode_space_fallback_type (const hb_glyph_info_t *info)
hb_unicode_funcs_t::NOT_SPACE;
}
+static inline bool _hb_glyph_info_substituted (const hb_glyph_info_t *info);
static inline bool _hb_glyph_info_ligated (const hb_glyph_info_t *info);
+static inline bool _hb_glyph_info_multiplied (const hb_glyph_info_t *info);
static inline bool
_hb_glyph_info_is_default_ignorable (const hb_glyph_info_t *info)
{
return (info->unicode_props() & UPROPS_MASK_IGNORABLE) &&
- !_hb_glyph_info_ligated (info);
+ !_hb_glyph_info_substituted (info) &&
+ !_hb_glyph_info_ligated (info) &&
+ !_hb_glyph_info_multiplied (info);
}
static inline bool
_hb_glyph_info_is_default_ignorable_and_not_hidden (const hb_glyph_info_t *info) I’m not sure about the Mongolian variation selector failure, though as visually the output looks the same as the
|
Re Mongolian variation selector test, the font has a single substitution lookup in |
I believe (IIRC) there may be other Mongolian fonts that don't do this, so we might be regressing their results if we do this. |
This would happen only to fonts that apply substitutions to Default_Ignorables, if no substitutions are performed, the glyph will be hidden as usual. |
True; so most likely it wouldn't be a problem, I guess. |
Don’t replace Default_Ignorables with zero-width space if they are substituted or multiplied, not just when ligated. After this change, HarfBuzz output matches that of Uniscribe and CoreText for the new tests. Fixes #2883
Don’t replace Default_Ignorables with zero-width space if they are substituted or multiplied, not just when ligated. After this change, HarfBuzz output matches that of Uniscribe and CoreText for the new tests. Fixes #2883
Don’t replace Default_Ignorables with zero-width space if they are substituted or multiplied, not just when ligated. After this change, HarfBuzz output matches that of Uniscribe and CoreText for the new tests. Fixes #2883
This change has caused ZWJ to be rendered in merged versions of Noto Sans. For example: NotoSansSouthAsian-Regular.zip util/hb-view --font-file=NotoSansSouthAsian-Regular.ttf --text="ग्र" I believe this is happening because the merge process adds a substitution rule that maps the ZWJ glyph to a family specific version of the glyph for each of the merged families. Thus the original ZWJ glyph gets substituted and then is no longer considered ignorable after this change. Not sure if anything can be done in harfbuzz for this situation. Since it's probably indistinguishable from the use case that this issue is trying to support. |
I should add the font was produced using the merge utility from fontTools. |
Probably it should be fixed in the merger, though it might be tricky. Interestingly Core Text also renders the ZWJ, but Uniscribe doesn’t. |
Sounds good, I'll open an issue in fontTools |
The actual rules that Uniscribe use seems to be rather involved. For example, I couldn’t get it to keep the ZWJ glyph in dev/dev2 scripts at all, and in Arabic only when involved in contextual substitutions, while in Latin any substitution lookup will do. Looks like the actual logic is handled by individual shapers. |
I have a font that contextually substitutes ZWJ by a visible glyph, something like (in AFDKO feature syntax):
(the idea is to give a tapering end to these glyphs)
This does not work in HarfBuzz, and it seems like the
joinerTerminal-ar.fina
glyph gets replaced byspace
glyph anyway:It works, however, with both Uniscribe and CoreText (the
joinerTerminal-ar.fina
is kept). If no substitution is performed, Uniscribe and CoreText will replace ZWJ with a space glyph just like HarfBuzz does.The text was updated successfully, but these errors were encountered: