CFF.h 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. /*
  2. * Copyright (c) 2023, Rodrigo Tobar <rtobarc@gmail.com>.
  3. *
  4. * SPDX-License-Identifier: BSD-2-Clause
  5. */
  6. #pragma once
  7. #include <AK/Types.h>
  8. #include <LibPDF/Error.h>
  9. #include <LibPDF/Fonts/Type1FontProgram.h>
  10. namespace PDF {
  11. class Reader;
  12. // CFF spec: https://adobe-type-tools.github.io/font-tech-notes/pdfs/5176.CFF.pdf
  13. class CFF : public Type1FontProgram {
  14. private:
  15. // CFF spec, "Table 9 Top DICT Operator Entries"
  16. enum class TopDictOperator {
  17. Version = 0,
  18. Notice,
  19. FullName,
  20. FamilyName,
  21. Weight,
  22. FontBBox,
  23. UniqueID = 13,
  24. XUID,
  25. Charset = 15,
  26. Encoding,
  27. CharStrings,
  28. Private,
  29. Copyright = (12 << 8),
  30. IsFixedPitch,
  31. ItalicAngle,
  32. UnderlinePosition,
  33. UnderlineThickness,
  34. PaintType,
  35. CharstringType,
  36. FontMatrix,
  37. StrokeWidth,
  38. SyntheticBase = (12 << 8 | 20),
  39. PostScript,
  40. BaseFontName,
  41. BaseFontBlend,
  42. // CFF spec, "Table 10 CIDFont Operator Extensions"
  43. RegistryOrderingSupplement = (12 << 8 | 30),
  44. CIDFontVersion,
  45. CIDFontRevision,
  46. CIDFontType,
  47. CIDCount,
  48. UIDBase,
  49. FDArray,
  50. FDSelect,
  51. FontName,
  52. };
  53. // CFF spec, "Table 23 Private DICT Operators"
  54. enum class PrivDictOperator {
  55. BlueValues = 6,
  56. OtherBlues,
  57. FamilyBlues,
  58. FamilyOtherBlues,
  59. BlueScale = (12 << 8 | 9),
  60. BlueShift,
  61. BlueFuzz,
  62. StdHW = 10,
  63. StdVW,
  64. StemSnapH = (12 << 8 | 12),
  65. StemSnapV,
  66. ForceBold,
  67. LanguageGroup = (12 << 8 | 17),
  68. ExpansionFactor,
  69. InitialRandomSeed,
  70. Subrs = 19,
  71. DefaultWidthX,
  72. NominalWidthX,
  73. };
  74. public:
  75. static PDFErrorOr<NonnullRefPtr<CFF>> create(ReadonlyBytes const&, RefPtr<Encoding> encoding);
  76. // to private
  77. using Card8 = u8;
  78. using Card16 = u16;
  79. using Offset = i32;
  80. using OffSize = u8;
  81. using SID = u16;
  82. using DictOperand = Variant<int, float>;
  83. static float to_number(DictOperand operand)
  84. {
  85. if (operand.has<int>())
  86. return operand.get<int>();
  87. return operand.get<float>();
  88. }
  89. static int load_int_dict_operand(u8 b0, Reader&);
  90. static float load_float_dict_operand(Reader&);
  91. static PDFErrorOr<DictOperand> load_dict_operand(u8, Reader&);
  92. using IndexDataHandler = Function<PDFErrorOr<void>(ReadonlyBytes const&)>;
  93. static PDFErrorOr<void> parse_index(Reader& reader, IndexDataHandler&&);
  94. static PDFErrorOr<void> parse_index_data(OffSize offset_size, Card16 count, Reader& reader, IndexDataHandler&);
  95. template<typename OperatorT>
  96. using DictEntryHandler = Function<PDFErrorOr<void>(OperatorT, Vector<DictOperand> const&)>;
  97. template<typename OperatorT>
  98. static PDFErrorOr<void> parse_dict(Reader& reader, DictEntryHandler<OperatorT>&& handler);
  99. template<typename OperatorT>
  100. static PDFErrorOr<OperatorT> parse_dict_operator(u8, Reader&);
  101. // CFF spec, "8 Top DICT INDEX"
  102. struct TopDict {
  103. int charset_offset = 0;
  104. int encoding_offset = 0;
  105. int charstrings_offset = 0;
  106. Vector<ByteBuffer> local_subroutines;
  107. Optional<float> defaultWidthX;
  108. Optional<float> nominalWidthX;
  109. bool is_cid_keyed = false;
  110. int fdselect_offset = 0;
  111. int fdarray_offset = 0;
  112. };
  113. static PDFErrorOr<Vector<TopDict>> parse_top_dicts(Reader&, ReadonlyBytes const& cff_bytes);
  114. static PDFErrorOr<Vector<StringView>> parse_strings(Reader&);
  115. static PDFErrorOr<Vector<CFF::Glyph>> parse_charstrings(Reader&&, Vector<ByteBuffer> const& local_subroutines, Vector<ByteBuffer> const& global_subroutines);
  116. static DeprecatedFlyString resolve_sid(SID, Vector<StringView> const&);
  117. static PDFErrorOr<Vector<SID>> parse_charset(Reader&&, size_t);
  118. static PDFErrorOr<Vector<u8>> parse_fdselect(Reader&&, size_t);
  119. static PDFErrorOr<Vector<u8>> parse_encoding(Reader&&, HashMap<Card8, SID>& supplemental);
  120. };
  121. }