other = any;
main := |*
- consonant_syllable => { process_syllable (consonant_syllable); };
- vowel_syllable => { process_syllable (vowel_syllable); };
- standalone_cluster => { process_syllable (standalone_cluster); };
- other => { process_syllable (non_indic); };
+ consonant_syllable => { found_syllable (consonant_syllable); };
+ vowel_syllable => { found_syllable (vowel_syllable); };
+ standalone_cluster => { found_syllable (standalone_cluster); };
+ other => { found_syllable (non_indic_cluster); };
*|;
}%%
-#define process_syllable(func) \
+#define found_syllable(syllable_type) \
HB_STMT_START { \
- if (0) fprintf (stderr, "syllable %d..%d %s\n", last, p+1, #func); \
+ if (0) fprintf (stderr, "syllable %d..%d %s\n", last, p+1, #syllable_type); \
for (unsigned int i = last; i < p+1; i++) \
- info[i].syllable() = syllable_serial; \
- PASTE (initial_reordering_, func) (plan, buffer, last, p+1); \
+ info[i].syllable() = (syllable_serial << 4) | syllable_type; \
last = p+1; \
syllable_serial++; \
- if (unlikely (!syllable_serial)) syllable_serial++; \
+ if (unlikely (syllable_serial == 16)) syllable_serial = 1; \
} HB_STMT_END
static void
pe = eof = buffer->len;
unsigned int last = 0;
- uint8_t syllable_serial = 1;
+ unsigned int syllable_serial = 1;
%%{
write exec;
}%%
}
static void
-initial_reordering_non_indic (const hb_ot_shape_plan_t *plan HB_UNUSED,
- hb_buffer_t *buffer HB_UNUSED,
- unsigned int start HB_UNUSED, unsigned int end HB_UNUSED)
+initial_reordering_non_indic_cluster (const hb_ot_shape_plan_t *plan HB_UNUSED,
+ hb_buffer_t *buffer HB_UNUSED,
+ unsigned int start HB_UNUSED, unsigned int end HB_UNUSED)
{
/* Nothing to do right now. If we ever switch to using the output
* buffer in the reordering process, we'd need to next_glyph() here. */
}
+
+enum syllable_type_t {
+ consonant_syllable,
+ vowel_syllable,
+ standalone_cluster,
+ broken_cluster,
+ non_indic_cluster,
+};
+
#include "hb-ot-shape-complex-indic-machine.hh"
static void
+initial_reordering_syllable (const hb_ot_shape_plan_t *plan,
+ hb_buffer_t *buffer,
+ unsigned int start, unsigned int end)
+{
+ syllable_type_t syllable_type = (syllable_type_t) (buffer->info[start].syllable() & 0x0F);
+ switch (syllable_type) {
+ case consonant_syllable: initial_reordering_consonant_syllable (plan, buffer, start, end); return;
+ case vowel_syllable: initial_reordering_vowel_syllable (plan, buffer, start, end); return;
+ case standalone_cluster: initial_reordering_standalone_cluster (plan, buffer, start, end); return;
+ case broken_cluster: initial_reordering_non_indic_cluster (plan, buffer, start, end); return;
+ case non_indic_cluster: initial_reordering_non_indic_cluster (plan, buffer, start, end); return;
+ }
+}
+
+static void
initial_reordering (const hb_ot_shape_plan_t *plan,
hb_font_t *font,
hb_buffer_t *buffer)
{
+ unsigned int count = buffer->len;
+ if (unlikely (!count)) return;
+
update_consonant_positions (plan, font, buffer);
find_syllables (plan, buffer);
+
+ hb_glyph_info_t *info = buffer->info;
+ unsigned int last = 0;
+ unsigned int last_syllable = info[0].syllable();
+ for (unsigned int i = 1; i < count; i++)
+ if (last_syllable != info[i].syllable()) {
+ initial_reordering_syllable (plan, buffer, last, i);
+ last = i;
+ last_syllable = info[last].syllable();
+ }
+ initial_reordering_syllable (plan, buffer, last, count);
}
static void
hb_buffer_t *buffer)
{
unsigned int count = buffer->len;
- if (!count) return;
+ if (unlikely (!count)) return;
hb_glyph_info_t *info = buffer->info;
unsigned int last = 0;