Make --features rand=1 available to the user
authorBehdad Esfahbod <behdad@behdad.org>
Mon, 10 Sep 2018 20:37:19 +0000 (22:37 +0200)
committerBehdad Esfahbod <behdad@behdad.org>
Tue, 11 Sep 2018 08:47:59 +0000 (10:47 +0200)
Use rand=255 to mean "randomize".

Part of https://github.com/harfbuzz/harfbuzz/pull/803

src/hb-ot-layout-gsub-table.hh
src/hb-ot-layout-gsubgpos.hh
src/hb-ot-map.cc
src/hb-ot-map.hh
src/hb-ot-shape.cc

index 255a282..dfa5097 100644 (file)
@@ -541,18 +541,15 @@ struct AlternateSet
     unsigned int shift = hb_ctz (lookup_mask);
     unsigned int alt_index = ((lookup_mask & glyph_mask) >> shift);
 
-    if (unlikely (alt_index > count || alt_index == 0)) return_trace (false);
-
-    /* This is ugly...  If alt_index is 1, we take it as "on", and randomize
-     * feature if it is the rand feature.  If it's > 1, it's a user-set value
-     * for sure, so respect it.  So, user cannot set rand=1 and expect it to
-     * choose the first alternate... */
-    if (alt_index == 1 && c->random)
+    /* If alt_index is MAX, randomize feature if it is the rand feature. */
+    if (alt_index == HB_OT_MAP_MAX_VALUE && c->random)
     {
       c->random_state = (0x5DEECE66Dull * c->random_state + 11) & (((uint64_t) 1 << 48) - 1);
       alt_index = (c->random_state >> 32) % count + 1;
     }
 
+    if (unlikely (alt_index > count || alt_index == 0)) return_trace (false);
+
     c->replace_glyph (alternates[alt_index - 1]);
 
     return_trace (true);
index df03226..be1b449 100644 (file)
@@ -33,6 +33,7 @@
 #include "hb-buffer.hh"
 #include "hb-map.hh"
 #include "hb-set.hh"
+#include "hb-ot-map.hh"
 #include "hb-ot-layout-common.hh"
 #include "hb-ot-layout-gdef-table.hh"
 
index 8617f05..cb70583 100644 (file)
@@ -210,8 +210,8 @@ hb_ot_map_builder_t::compile (hb_ot_map_t  &m,
       /* Uses the global bit */
       bits_needed = 0;
     else
-      /* Limit to 8 bits per feature. */
-      bits_needed = MIN(8u, hb_bit_storage (info->max_value));
+      /* Limit bits per feature. */
+      bits_needed = MIN(HB_OT_MAP_MAX_BITS, hb_bit_storage (info->max_value));
 
     if (!info->max_value || next_bit + bits_needed > 8 * sizeof (hb_mask_t))
       continue; /* Feature disabled, or not enough bits. */
index 091cb3b..cc36fa2 100644 (file)
@@ -32,6 +32,9 @@
 #include "hb-buffer.hh"
 
 
+#define HB_OT_MAP_MAX_BITS 8u
+#define HB_OT_MAP_MAX_VALUE ((1u << HB_OT_MAP_MAX_BITS) - 1u)
+
 struct hb_ot_shape_plan_t;
 
 static const hb_tag_t table_tags[2] = {HB_OT_TAG_GSUB, HB_OT_TAG_GPOS};
index 00a8a64..437b0fe 100644 (file)
@@ -96,7 +96,7 @@ hb_ot_shape_collect_features (hb_ot_shape_planner_t          *planner,
   map->add_feature (HB_TAG ('d','n','o','m'), 1, F_NONE);
 
   /* Random! */
-  map->add_feature (HB_TAG ('r','a','n','d'), 1, F_GLOBAL | F_RANDOM);
+  map->add_feature (HB_TAG ('r','a','n','d'), HB_OT_MAP_MAX_VALUE, F_GLOBAL | F_RANDOM);
 
   if (planner->shaper->collect_features)
     planner->shaper->collect_features (planner);