src/hb-ot-shape-complex-indic.cc | 153 ++++++++++++++++++++++++++++++++------- 1 file changed, 127 insertions(+), 26 deletions(-)
New commits: commit 5e72071062c015237b79fbd0521341a63166a204 Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 17:51:50 2011 -0400 [Indic] Stop looking for base upon seeing joiners Not sure where this is documented, but I remember this being the desired behavior. test-shape-complex failures are down from 48 to 46. Meh. diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index ddcdb00..8800d2f 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -439,11 +439,15 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t * base consonants. */ - unsigned int base = 0; + unsigned int base = end; /* -> starting from the end of the syllable, move backwards */ i = end; - unsigned int limit = start + (info[start].indic_category() == OT_Ra ? 2 : 0); + unsigned int limit = start; + if (info[start].indic_category() == OT_Ra && start + 2 <= end) { + limit += 2; + base = start; + }; do { i--; /* -> until a consonant is found */ @@ -476,6 +480,9 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t * be the base. */ base = i; } + else + if (is_joiner (info[i])) + break; } while (i > limit); if (base < start) base = start; /* Just in case... */ commit 281683995a46ed37aeeb84061249758c59822457 Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 16:00:35 2011 -0400 Cosmetic diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index 0888cba..ddcdb00 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -565,14 +565,21 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t /* Setup masks now */ - /* Pre-base */ - for (i = start; i < base; i++) - info[i].mask |= mask_array[HALF] | mask_array[AKHN] | mask_array[CJCT]; - /* Base */ - info[base].mask |= mask_array[AKHN] | mask_array[CJCT]; - /* Post-base */ - for (i = base + 1; i < end; i++) - info[i].mask |= mask_array[BLWF] | mask_array[PSTF] | mask_array[CJCT]; + { + hb_mask_t mask; + + /* Pre-base */ + mask = mask_array[HALF] | mask_array[AKHN] | mask_array[CJCT]; + for (i = start; i < base; i++) + info[i].mask |= mask; + /* Base */ + mask = mask_array[AKHN] | mask_array[CJCT]; + info[base].mask |= mask; + /* Post-base */ + mask = mask_array[BLWF] | mask_array[PSTF] | mask_array[CJCT]; + for (i = base + 1; i < end; i++) + info[i].mask |= mask; + } /* Apply ZWJ/ZWNJ effects */ for (i = start + 1; i < end; i++) commit 6b37bc80843e38ca7b62500f95fd70c08af68d62 Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 15:57:00 2011 -0400 [Indic] Fix ZWJ/ZWNJ application Not quite working just yet. False alarm re 10 failures. It was crashing. Ouch! Back to 48 failures. diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index 4500ef7..0888cba 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -578,13 +578,15 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t for (i = start + 1; i < end; i++) if (is_joiner (info[i])) { bool non_joiner = info[i].indic_category() == OT_ZWNJ; - unsigned int j = i - 1; + unsigned int j = i; do { - info[j].mask &= !mask_array[HALF]; - if (non_joiner) - info[j].mask &= !mask_array[CJCT]; j--; + + info[j].mask &= !mask_array[CJCT]; + if (non_joiner) + info[j].mask &= !mask_array[HALF]; + } while (j > start && !is_consonant (info[j])); } } commit e7be05702447ae270d797398132c1930cd3a9b86 Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 15:18:57 2011 -0400 [Indic] Add Final Reordering rules into comments Not applied yet. diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index cfc1c4b..4500ef7 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -460,9 +460,12 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t /* -> or that is not a pre-base reordering Ra, * - * o If the syllable starts with Ra + Halant (in a script that has Reph) - * and has more than one consonant, Ra is excluded from candidates for - * base consonants. + * TODO + */ + + /* -> o If the syllable starts with Ra + Halant (in a script that has Reph) + * and has more than one consonant, Ra is excluded from candidates for + * base consonants. * * IMPLEMENTATION NOTES: * @@ -653,6 +656,83 @@ final_reordering (const hb_ot_map_t *map, hb_buffer_t *buffer, void *user_data HB_UNUSED) { + /* 4. Final reordering: + * + * After the localized forms and basic shaping forms GSUB features have been + * applied (see below), the shaping engine performs some final glyph + * reordering before applying all the remaining font features to the entire + * cluster. + * + * o Reorder matras: + * + * If a pre-base matra character had been reordered before applying basic + * features, the glyph can be moved closer to the main consonant based on + * whether half-forms had been formed. Actual position for the matra is + * defined as âafter last standalone halant glyph, after initial matra + * position and before the main consonantâ. If ZWJ or ZWNJ follow this + * halant, position is moved after it. + * + * o Reorder reph: + * + * Rephâs original position is always at the beginning of the syllable, + * (i.e. it is not reordered at the character reordering stage). However, + * it will be reordered according to the basic-forms shaping results. + * Possible positions for reph, depending on the script, are; after main, + * before post-base consonant forms, and after post-base consonant forms. + * + * 1. If reph should be positioned after post-base consonant forms, + * proceed to step 5. + * + * 2. If the reph repositioning class is not after post-base: target + * position is after the first explicit halant glyph between the + * first post-reph consonant and last main consonant. If ZWJ or ZWNJ + * are following this halant, position is moved after it. If such + * position is found, this is the target position. Otherwise, + * proceed to the next step. + * + * Note: in old-implementation fonts, where classifications were + * fixed in shaping engine, there was no case where reph position + * will be found on this step. + * + * 3. If reph should be repositioned after the main consonant: from the + * first consonant not ligated with main, or find the first + * consonant that is not a potential pre-base reordering Ra. + * + * + * 4. If reph should be positioned before post-base consonant, find + * first post-base classified consonant not ligated with main. If no + * consonant is found, the target position should be before the + * first matra, syllable modifier sign or vedic sign. + * + * 5. If no consonant is found in steps 3 or 4, move reph to a position + * immediately before the first post-base matra, syllable modifier + * sign or vedic sign that has a reordering class after the intended + * reph position. For example, if the reordering position for reph + * is post-main, it will skip above-base matras that also have a + * post-main position. + * + * 6. Otherwise, reorder reph to the end of the syllable. + * + * o Reorder pre-base reordering consonants: + * + * If a pre-base reordering consonant is found, reorder it according to + * the following rules: + * + * 1. Only reorder a glyph produced by substitution during application + * of the feature. (Note that a font may shape a Ra consonant with + * the feature generally but block it in certain contexts.) + * + * 2. Try to find a target position the same way as for pre-base matra. + * If it is found, reorder pre-base consonant glyph. + * + * 3. If position is not found, reorder immediately before main + * consonant. + */ + + /* TODO */ + + + HB_BUFFER_DEALLOCATE_VAR (buffer, indic_category); HB_BUFFER_DEALLOCATE_VAR (buffer, indic_position); } commit cfd4382ec1af91640129551697de36fd42c0849a Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 15:07:11 2011 -0400 [Indic] Handle Reph when determining base consonant diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index 82c247a..cfc1c4b 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -443,6 +443,7 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t /* -> starting from the end of the syllable, move backwards */ i = end; + unsigned int limit = start + (info[start].indic_category() == OT_Ra ? 2 : 0); do { i--; /* -> until a consonant is found */ @@ -457,20 +458,25 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t break; } - /* TODO: or that is not a pre-base reordering Ra, */ - - /* -> or arrive at the first consonant. The consonant stopped at will be the base. */ + /* -> or that is not a pre-base reordering Ra, + * + * o If the syllable starts with Ra + Halant (in a script that has Reph) + * and has more than one consonant, Ra is excluded from candidates for + * base consonants. + * + * IMPLEMENTATION NOTES: + * + * We do this by adjusting limit accordingly before entering the loop. + */ + + /* -> or arrive at the first consonant. The consonant stopped at will + * be the base. */ base = i; } - } while (i > start); + } while (i > limit); if (base < start) base = start; /* Just in case... */ - /* TODO - * If the syllable starts with Ra + Halant (in a script that has Reph) - * and has more than one consonant, Ra is excluded from candidates for - * base consonants. */ - /* 2. Decompose and reorder Matras: * commit 97158392a5899ddb739afaac925128f33f699bd7 Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 15:01:28 2011 -0400 [Indic] Ra is a consonant too diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index d801cec..82c247a 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -446,8 +446,7 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t do { i--; /* -> until a consonant is found */ - if (info[i].indic_category() == OT_C) - //if ((FLAG (info[i].indic_category()) & (FLAG (OT_C) | FLAG (OT_Ra)))) + if (is_consonant (info[i])) { /* -> that does not have a below-base or post-base form * (post-base forms have to follow below-base forms), */ commit 0d8f8a177c4bfd4dc642a353bab8d03674e839ac Author: Behdad Esfahbod <[email protected]> Date: Sun Jul 31 14:57:59 2011 -0400 [Indic] Fix reph inhibition logic diff --git a/src/hb-ot-shape-complex-indic.cc b/src/hb-ot-shape-complex-indic.cc index ba28aa5..d801cec 100644 --- a/src/hb-ot-shape-complex-indic.cc +++ b/src/hb-ot-shape-complex-indic.cc @@ -513,10 +513,10 @@ found_consonant_syllable (const hb_ot_map_t *map, hb_buffer_t *buffer, hb_mask_t /* Handle beginning Ra */ - if (start + 2 <= end && + if (start + 3 <= end && info[start].indic_category() == OT_Ra && info[start + 1].indic_category() == OT_H && - (start + 2 == end || !is_joiner (info[start]))) + !is_joiner (info[start + 2])) { info[start].indic_position() = POS_POST; info[start].mask = mask_array[RPHF];
_______________________________________________ HarfBuzz mailing list [email protected] http://lists.freedesktop.org/mailman/listinfo/harfbuzz
