diff options
Diffstat (limited to 'src/3rdparty/harfbuzz-ng/src/hb-ot-os2-table.hh')
-rw-r--r-- | src/3rdparty/harfbuzz-ng/src/hb-ot-os2-table.hh | 56 |
1 files changed, 37 insertions, 19 deletions
diff --git a/src/3rdparty/harfbuzz-ng/src/hb-ot-os2-table.hh b/src/3rdparty/harfbuzz-ng/src/hb-ot-os2-table.hh index 97d18b9d75..6c91402269 100644 --- a/src/3rdparty/harfbuzz-ng/src/hb-ot-os2-table.hh +++ b/src/3rdparty/harfbuzz-ng/src/hb-ot-os2-table.hh @@ -209,6 +209,23 @@ struct OS2 return ret; } + static unsigned calc_avg_char_width (const hb_hashmap_t<hb_codepoint_t, hb_pair_t<unsigned, int>>& hmtx_map) + { + unsigned num = 0; + unsigned total_width = 0; + for (const auto& _ : hmtx_map.values_ref ()) + { + unsigned width = _.first; + if (width) + { + total_width += width; + num++; + } + } + + return num ? (unsigned) roundf ((double) total_width / (double) num) : 0; + } + bool subset (hb_subset_context_t *c) const { TRACE_SUBSET (this); @@ -239,39 +256,40 @@ struct OS2 if (os2_prime->version >= 2) { + hb_barrier (); auto *table = & const_cast<OS2V2Tail &> (os2_prime->v2 ()); HB_ADD_MVAR_VAR (HB_OT_METRICS_TAG_X_HEIGHT, sxHeight); HB_ADD_MVAR_VAR (HB_OT_METRICS_TAG_CAP_HEIGHT, sCapHeight); } - } -#endif - if (c->plan->user_axes_location.has (HB_TAG ('w','g','h','t')) && - !c->plan->pinned_at_default) - { - float weight_class = c->plan->user_axes_location.get (HB_TAG ('w','g','h','t')); - if (!c->serializer->check_assign (os2_prime->usWeightClass, - roundf (hb_clamp (weight_class, 1.0f, 1000.0f)), + unsigned avg_char_width = calc_avg_char_width (c->plan->hmtx_map); + if (!c->serializer->check_assign (os2_prime->xAvgCharWidth, avg_char_width, HB_SERIALIZE_ERROR_INT_OVERFLOW)) return_trace (false); } +#endif - if (c->plan->user_axes_location.has (HB_TAG ('w','d','t','h')) && - !c->plan->pinned_at_default) + Triple *axis_range; + if (c->plan->user_axes_location.has (HB_TAG ('w','g','h','t'), &axis_range)) { - float width = c->plan->user_axes_location.get (HB_TAG ('w','d','t','h')); - if (!c->serializer->check_assign (os2_prime->usWidthClass, - roundf (map_wdth_to_widthclass (width)), - HB_SERIALIZE_ERROR_INT_OVERFLOW)) - return_trace (false); + unsigned weight_class = static_cast<unsigned> (roundf (hb_clamp (axis_range->middle, 1.0, 1000.0))); + if (os2_prime->usWeightClass != weight_class) + os2_prime->usWeightClass = weight_class; } - if (c->plan->flags & HB_SUBSET_FLAGS_NO_PRUNE_UNICODE_RANGES) - return_trace (true); + if (c->plan->user_axes_location.has (HB_TAG ('w','d','t','h'), &axis_range)) + { + unsigned width_class = static_cast<unsigned> (roundf (map_wdth_to_widthclass (axis_range->middle))); + if (os2_prime->usWidthClass != width_class) + os2_prime->usWidthClass = width_class; + } os2_prime->usFirstCharIndex = hb_min (0xFFFFu, c->plan->unicodes.get_min ()); os2_prime->usLastCharIndex = hb_min (0xFFFFu, c->plan->unicodes.get_max ()); + if (c->plan->flags & HB_SUBSET_FLAGS_NO_PRUNE_UNICODE_RANGES) + return_trace (true); + _update_unicode_ranges (&c->plan->unicodes, os2_prime->ulUnicodeRange); return_trace (true); @@ -287,8 +305,7 @@ struct OS2 /* This block doesn't show up in profiles. If it ever did, * we can rewrite it to iterate over OS/2 ranges and use * set iteration to check if the range matches. */ - for (hb_codepoint_t cp = HB_SET_VALUE_INVALID; - codepoints->next (&cp);) + for (auto cp : *codepoints) { unsigned int bit = _hb_ot_os2_get_unicode_range_bit (cp); if (bit < 128) @@ -340,6 +357,7 @@ struct OS2 { TRACE_SANITIZE (this); if (unlikely (!c->check_struct (this))) return_trace (false); + hb_barrier (); if (unlikely (version >= 1 && !v1X.sanitize (c))) return_trace (false); if (unlikely (version >= 2 && !v2X.sanitize (c))) return_trace (false); if (unlikely (version >= 5 && !v5X.sanitize (c))) return_trace (false); |