[subset] During LigatureSubstFormat1 subsetting always place Coverage last.

In Windows 7 on Chrome if the coverage table comes before any of the LigatureSet or Ligature subtables the font won't load. This changes the packing order to always place the Coverage table last. Virtual links are used to ensure the repacker maintains the desired ordering.

Coincidentally fontTools also does the same thing (a3f988fbf6/Lib/fontTools/ttLib/tables/otTables.py (L1137)) to reduce overflows during packing.
pull/3281/head
Garret Rieger 3 years ago
parent 9643d77086
commit 49c9392412
  1. 48
      src/hb-ot-layout-gsub-table.hh
  2. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.default.retain-all-codepoint.ttf
  3. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.drop-hints-retain-gids.retain-all-codepoint.ttf
  4. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.drop-hints.retain-all-codepoint.ttf
  5. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.gids.retain-all-codepoint.ttf
  6. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.glyph-names.retain-all-codepoint.ttf
  7. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.keep-all-layout-features.retain-all-codepoint.ttf
  8. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.layout-features.retain-all-codepoint.ttf
  9. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.name-ids.retain-all-codepoint.ttf
  10. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.name-languages.retain-all-codepoint.ttf
  11. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.name-legacy.retain-all-codepoint.ttf
  12. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.no-prune-unicode-ranges.retain-all-codepoint.ttf
  13. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.notdef-outline.retain-all-codepoint.ttf
  14. BIN
      test/subset/data/expected/basics/Comfortaa-Regular-new.retain-gids.retain-all-codepoint.ttf
  15. BIN
      test/subset/data/expected/glyph_names/Ubuntu-Regular.glyph-names.retain-all-codepoint.ttf
  16. BIN
      test/subset/data/expected/layout.duplicate_features/AlegreyaSans-BlackItalic.default.retain-all-codepoint.ttf
  17. BIN
      test/subset/data/expected/layout.duplicate_features/AlegreyaSans-BlackItalic.glyph-names.retain-all-codepoint.ttf
  18. BIN
      test/subset/data/expected/layout.duplicate_features/AlegreyaSans-BlackItalic.notdef-outline.retain-all-codepoint.ttf
  19. BIN
      test/subset/data/expected/layout.gdef-attachlist/IndicTestJalandhar-Regular.default.retain-all-codepoint.ttf
  20. BIN
      test/subset/data/expected/layout.gdef-attachlist/IndicTestJalandhar-Regular.drop-hints.retain-all-codepoint.ttf
  21. BIN
      test/subset/data/expected/layout.gdef-attachlist/IndicTestJalandhar-Regular.keep-gdef.retain-all-codepoint.ttf
  22. BIN
      test/subset/data/expected/layout.gpos5/gpos5_font1.layout-test-retain-gids.retain-all-codepoint.otf
  23. BIN
      test/subset/data/expected/layout.gpos5/gpos5_font1.layout-test.retain-all-codepoint.otf
  24. BIN
      test/subset/data/expected/layout.gsub5/gsub_context3_successive_f1.layout-test-retain-gids.retain-all-codepoint.otf
  25. BIN
      test/subset/data/expected/layout.gsub5/gsub_context3_successive_f1.layout-test.retain-all-codepoint.otf
  26. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.default.627,644,623,62D,644,627,645,2E.ttf
  27. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.default.627,644,62D,628.ttf
  28. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.default.627,644.ttf
  29. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.default.633,645,627,621,20,644,627.ttf
  30. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.default.63A,64A,631.ttf
  31. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.retain-gids.627,644,623,62D,644,627,645,2E.ttf
  32. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.retain-gids.627,644,62D,628.ttf
  33. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.retain-gids.627,644.ttf
  34. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.retain-gids.633,645,627,621,20,644,627.ttf
  35. BIN
      test/subset/data/expected/layout.notonastaliqurdu/NotoNastaliqUrdu-Bold.retain-gids.63A,64A,631.ttf
  36. BIN
      test/subset/data/expected/layout.tinos/Tinos-Italic.default.retain-all-codepoint.ttf
  37. BIN
      test/subset/data/expected/layout.tinos/Tinos-Italic.glyph-names.retain-all-codepoint.ttf
  38. BIN
      test/subset/data/expected/layout.tinos/Tinos-Italic.notdef-outline.retain-all-codepoint.ttf
  39. BIN
      test/subset/data/expected/layout.tinos/Tinos-Italic.retain-gids.retain-all-codepoint.ttf
  40. BIN
      test/subset/data/expected/math/STIXTwoMath-Regular.default.retain-all-codepoint.ttf
  41. BIN
      test/subset/data/expected/math/STIXTwoMath-Regular.glyph-names.retain-all-codepoint.ttf
  42. BIN
      test/subset/data/expected/math/STIXTwoMath-Regular.notdef-outline.retain-all-codepoint.ttf
  43. BIN
      test/subset/data/expected/math/STIXTwoMath-Regular.retain-gids.retain-all-codepoint.ttf
  44. BIN
      test/subset/data/expected/variable/Fraunces.default.26,66,69,124,125.ttf

@ -861,13 +861,15 @@ struct Ligature
return_trace (true);
}
bool subset (hb_subset_context_t *c) const
bool subset (hb_subset_context_t *c, unsigned coverage_idx) const
{
TRACE_SUBSET (this);
const hb_set_t &glyphset = *c->plan->glyphset_gsub ();
const hb_map_t &glyph_map = *c->plan->glyph_map;
if (!intersects (&glyphset) || !glyphset.has (ligGlyph)) return_trace (false);
// Ensure Coverage table is always packed after this.
c->serializer->add_virtual_link (coverage_idx);
auto it =
+ hb_iter (component)
@ -968,16 +970,21 @@ struct LigatureSet
return_trace (true);
}
bool subset (hb_subset_context_t *c) const
bool subset (hb_subset_context_t *c, unsigned coverage_idx) const
{
TRACE_SUBSET (this);
auto *out = c->serializer->start_embed (*this);
if (unlikely (!c->serializer->extend_min (out))) return_trace (false);
+ hb_iter (ligature)
| hb_filter (subset_offset_array (c, out->ligature, this))
| hb_filter (subset_offset_array (c, out->ligature, this, coverage_idx))
| hb_drain
;
if (bool (out->ligature))
// Ensure Coverage table is always packed after this.
c->serializer->add_virtual_link (coverage_idx);
return_trace (bool (out->ligature));
}
@ -1092,15 +1099,38 @@ struct LigatureSubstFormat1
if (unlikely (!c->serializer->extend_min (out))) return_trace (false);
out->format = format;
hb_sorted_vector_t<hb_codepoint_t> new_coverage;
+ hb_zip (this+coverage, ligatureSet)
// Due to a bug in some older versions of windows 7 the Coverage table must be
// packed after the LigatureSet and Ligature tables, so serialize Coverage first
// which places it last in the packed order.
hb_set_t new_coverage;
+ hb_zip (this+coverage, hb_iter (ligatureSet) | hb_map (hb_add (this)))
| hb_filter (glyphset, hb_first)
| hb_filter (subset_offset_array (c, out->ligatureSet, this), hb_second)
| hb_filter ([&] (const LigatureSet& _) {
return _.intersects (&glyphset);
}, hb_second)
| hb_map (hb_first)
| hb_map (glyph_map)
| hb_sink (new_coverage)
| hb_sink (new_coverage);
if (!c->serializer->push<Coverage> ()
->serialize (c->serializer,
+ new_coverage.iter () | hb_map_retains_sorting (glyph_map)))
{
c->serializer->pop_discard ();
return_trace (false);
}
unsigned coverage_idx = c->serializer->pop_pack ();
c->serializer->add_link (out->coverage, coverage_idx);
+ hb_zip (this+coverage, ligatureSet)
| hb_filter (new_coverage, hb_first)
| hb_map (hb_second)
// to ensure that the repacker always orders the coverage table after the LigatureSet
// and LigatureSubtable's they will be linked to the Coverage table via a virtual link
// the coverage table object idx is passed down to facilitate this.
| hb_apply (subset_offset_array (c, out->ligatureSet, this, coverage_idx))
;
out->coverage.serialize_serialize (c->serializer, new_coverage.iter ());
return_trace (bool (new_coverage));
}

Loading…
Cancel
Save