@reportwright/viewer 0.12.1 → 0.13.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (101) hide show
  1. package/CHANGELOG.md +93 -0
  2. package/README.md +18 -1
  3. package/THIRD-PARTY-NOTICES.md +52 -0
  4. package/dist/{chunk-DXHLIJEY.js → chunk-47ZAKRVN.js} +6 -6
  5. package/dist/{chunk-NR2G4TMG.js → chunk-B5ZCT3UK.js} +47 -26
  6. package/dist/chunk-B5ZCT3UK.js.map +6 -0
  7. package/dist/chunk-BR5K6SBL.js +324 -0
  8. package/dist/chunk-BR5K6SBL.js.map +6 -0
  9. package/dist/chunk-CCH7CFU5.js +5026 -0
  10. package/dist/chunk-CCH7CFU5.js.map +6 -0
  11. package/dist/{peer/chunk-BQFI3DHK.js → chunk-ES2LYZ6S.js} +292 -25
  12. package/dist/chunk-ES2LYZ6S.js.map +6 -0
  13. package/dist/{chunk-S2IUUI6N.js → chunk-GOCWG6FG.js} +67 -49
  14. package/dist/chunk-GOCWG6FG.js.map +6 -0
  15. package/dist/{chunk-3D2KFKG2.js → chunk-GRYITZPG.js} +11 -9
  16. package/dist/chunk-GRYITZPG.js.map +6 -0
  17. package/dist/{chunk-2BPBQMH2.js → chunk-H422SRD3.js} +8 -8
  18. package/dist/chunk-JD6EJ3LI.js +18 -0
  19. package/dist/{chunk-Z7MKH66Z.js → chunk-MS2LQC2O.js} +236 -12
  20. package/dist/chunk-MS2LQC2O.js.map +6 -0
  21. package/dist/{chunk-Q6MMPKQA.js → chunk-PF4RFKX2.js} +13 -12
  22. package/dist/chunk-PF4RFKX2.js.map +6 -0
  23. package/dist/{chunk-PGP3QA6L.js → chunk-PKXTMC4J.js} +1351 -75
  24. package/dist/chunk-PKXTMC4J.js.map +6 -0
  25. package/dist/{chunk-M6AYND5G.js → chunk-U2ZY2NPQ.js} +16 -7
  26. package/dist/chunk-U2ZY2NPQ.js.map +6 -0
  27. package/dist/{chunk-DPVJEFKP.js → chunk-WOBRKNIA.js} +13 -13
  28. package/dist/{chunk-DPVJEFKP.js.map → chunk-WOBRKNIA.js.map} +1 -1
  29. package/dist/chunk-XXTAPZO4.js +34 -0
  30. package/dist/{chunk-VNOWPSE6.js → chunk-ZGRJJ6OW.js} +1226 -887
  31. package/dist/chunk-ZGRJJ6OW.js.map +6 -0
  32. package/dist/designer.d.ts +11 -3
  33. package/dist/designer.js +598 -390
  34. package/dist/designer.js.map +3 -3
  35. package/dist/engine.worker.bwip.js +51422 -0
  36. package/dist/engine.worker.bwip.js.map +6 -0
  37. package/dist/engine.worker.js +59582 -26
  38. package/dist/engine.worker.js.map +3 -3
  39. package/dist/peer/{chunk-WSNRD2AQ.js → chunk-3EYYRJR4.js} +13 -12
  40. package/dist/{chunk-Q6MMPKQA.js.map → peer/chunk-3EYYRJR4.js.map} +1 -1
  41. package/dist/peer/{chunk-TSC4RAH3.js → chunk-3XZY54LM.js} +1351 -75
  42. package/dist/peer/chunk-3XZY54LM.js.map +6 -0
  43. package/dist/peer/chunk-5RUNOIS7.js +33 -0
  44. package/dist/peer/chunk-5RUNOIS7.js.map +6 -0
  45. package/dist/peer/{chunk-6I2EAAVN.js → chunk-7IP67PA6.js} +47 -26
  46. package/dist/peer/chunk-7IP67PA6.js.map +6 -0
  47. package/dist/peer/{chunk-R4VX5UC7.js → chunk-A6UXBSTP.js} +8 -8
  48. package/dist/peer/{chunk-V42KN7HD.js → chunk-CFTFTV2O.js} +6 -6
  49. package/dist/peer/chunk-JQTRDHQP.js +866 -0
  50. package/dist/peer/chunk-JQTRDHQP.js.map +6 -0
  51. package/dist/peer/chunk-KD6CDYGE.js +5024 -0
  52. package/dist/peer/chunk-KD6CDYGE.js.map +6 -0
  53. package/dist/peer/chunk-MXR6JBMP.js +546 -0
  54. package/dist/peer/chunk-MXR6JBMP.js.map +6 -0
  55. package/dist/peer/chunk-N42DCZZA.js +378 -0
  56. package/dist/peer/chunk-N42DCZZA.js.map +6 -0
  57. package/dist/{chunk-6TPZ7G74.js → peer/chunk-RKFP7SDY.js} +292 -25
  58. package/dist/peer/chunk-RKFP7SDY.js.map +6 -0
  59. package/dist/peer/{chunk-BMAXIBP2.js → chunk-WABYQWMT.js} +13 -13
  60. package/dist/peer/{chunk-BMAXIBP2.js.map → chunk-WABYQWMT.js.map} +1 -1
  61. package/dist/peer/chunk-WVQQCD4M.js +14211 -0
  62. package/dist/peer/chunk-WVQQCD4M.js.map +6 -0
  63. package/dist/peer/chunk-XHCRHVRK.js +17 -0
  64. package/dist/peer/chunk-XHCRHVRK.js.map +6 -0
  65. package/dist/peer/{chunk-WQGENQZO.js → chunk-ZS3J4WBH.js} +11 -9
  66. package/dist/peer/chunk-ZS3J4WBH.js.map +6 -0
  67. package/dist/peer/designer.js +455 -247
  68. package/dist/peer/designer.js.map +3 -3
  69. package/dist/peer/engine.worker.bwip.js +51422 -0
  70. package/dist/peer/engine.worker.bwip.js.map +6 -0
  71. package/dist/peer/engine.worker.js +59582 -25
  72. package/dist/peer/engine.worker.js.map +3 -3
  73. package/dist/peer/viewer.js +16 -12
  74. package/dist/peer/viewer.js.map +1 -1
  75. package/dist/viewer.d.ts +2 -1
  76. package/dist/viewer.js +16 -12
  77. package/dist/viewer.js.map +1 -1
  78. package/package.json +3 -2
  79. package/dist/chunk-3D2KFKG2.js.map +0 -6
  80. package/dist/chunk-6TPZ7G74.js.map +0 -6
  81. package/dist/chunk-BRB34AJ2.js +0 -16
  82. package/dist/chunk-M6AYND5G.js.map +0 -6
  83. package/dist/chunk-NR2G4TMG.js.map +0 -6
  84. package/dist/chunk-PGP3QA6L.js.map +0 -6
  85. package/dist/chunk-S2IUUI6N.js.map +0 -6
  86. package/dist/chunk-ULKEEARQ.js +0 -553
  87. package/dist/chunk-ULKEEARQ.js.map +0 -6
  88. package/dist/chunk-VNOWPSE6.js.map +0 -6
  89. package/dist/chunk-Z7MKH66Z.js.map +0 -6
  90. package/dist/peer/chunk-2FZTYEDE.js +0 -15
  91. package/dist/peer/chunk-6I2EAAVN.js.map +0 -6
  92. package/dist/peer/chunk-BQFI3DHK.js.map +0 -6
  93. package/dist/peer/chunk-TSC4RAH3.js.map +0 -6
  94. package/dist/peer/chunk-WQGENQZO.js.map +0 -6
  95. package/dist/peer/chunk-WSNRD2AQ.js.map +0 -6
  96. /package/dist/{chunk-DXHLIJEY.js.map → chunk-47ZAKRVN.js.map} +0 -0
  97. /package/dist/{chunk-2BPBQMH2.js.map → chunk-H422SRD3.js.map} +0 -0
  98. /package/dist/{chunk-BRB34AJ2.js.map → chunk-JD6EJ3LI.js.map} +0 -0
  99. /package/dist/{peer/chunk-2FZTYEDE.js.map → chunk-XXTAPZO4.js.map} +0 -0
  100. /package/dist/peer/{chunk-R4VX5UC7.js.map → chunk-A6UXBSTP.js.map} +0 -0
  101. /package/dist/peer/{chunk-V42KN7HD.js.map → chunk-CFTFTV2O.js.map} +0 -0
@@ -0,0 +1,866 @@
1
+ // src/engine/lazylibs.js
2
+ var fontkit;
3
+ var PDFDocument;
4
+ var PDFName;
5
+ var PDFString;
6
+ var PDFHexString;
7
+ var PDFRawStream;
8
+ var PDFStream;
9
+ var PDFArray;
10
+ var PDFDict;
11
+ var PDFNumber;
12
+ var PDFBool;
13
+ var rgb;
14
+ var pushGraphicsState;
15
+ var popGraphicsState;
16
+ var concatTransformationMatrix;
17
+ var req = (() => {
18
+ try {
19
+ return (
20
+ /** @type {any} */
21
+ globalThis.process?.getBuiltinModule?.("module")?.createRequire(import.meta.url)
22
+ );
23
+ } catch {
24
+ return void 0;
25
+ }
26
+ })();
27
+ var load = async (name, imp) => {
28
+ if (req) try {
29
+ return req(name);
30
+ } catch {
31
+ }
32
+ return imp();
33
+ };
34
+ var fk;
35
+ var pl;
36
+ var loadFontkit = () => fk || (fk = load("@pdf-lib/fontkit", () => import("@pdf-lib/fontkit")).then((m) => {
37
+ const d = m.default || m;
38
+ fontkit = d.default || d;
39
+ }));
40
+ var loadPdfLib = () => pl || (pl = Promise.all([load("pdf-lib", () => import("pdf-lib")), loadFontkit()]).then(([L]) => {
41
+ ({
42
+ PDFDocument,
43
+ PDFName,
44
+ PDFString,
45
+ PDFHexString,
46
+ PDFRawStream,
47
+ PDFStream,
48
+ PDFArray,
49
+ PDFDict,
50
+ PDFNumber,
51
+ PDFBool,
52
+ rgb,
53
+ pushGraphicsState,
54
+ popGraphicsState,
55
+ concatTransformationMatrix
56
+ } = L);
57
+ }));
58
+
59
+ // src/engine/text/standard.js
60
+ var STANDARD_FACES = [
61
+ ["Helvetica", "Helvetica", 400, "normal"],
62
+ ["Helvetica", "Helvetica-Bold", 700, "normal"],
63
+ ["Helvetica", "Helvetica-Oblique", 400, "italic"],
64
+ ["Helvetica", "Helvetica-BoldOblique", 700, "italic"],
65
+ ["Times-Roman", "Times-Roman", 400, "normal"],
66
+ ["Times-Roman", "Times-Bold", 700, "normal"],
67
+ ["Times-Roman", "Times-Italic", 400, "italic"],
68
+ ["Times-Roman", "Times-BoldItalic", 700, "italic"],
69
+ ["Courier", "Courier", 400, "normal"],
70
+ ["Courier", "Courier-Bold", 700, "normal"],
71
+ ["Courier", "Courier-Oblique", 400, "italic"],
72
+ ["Courier", "Courier-BoldOblique", 700, "italic"],
73
+ ["Symbol", "Symbol", 400, "normal"],
74
+ ["ZapfDingbats", "ZapfDingbats", 400, "normal"]
75
+ ];
76
+ var STANDARD_KEYS = new Set(STANDARD_FACES.map((f) => String(f[1])));
77
+ var isStandard = (key) => STANDARD_KEYS.has(key);
78
+ async function standardFont(key) {
79
+ const { METRICS, ENCODINGS } = await import("./chunk-KD6CDYGE.js");
80
+ const m = (
81
+ /** @type {any} */
82
+ METRICS[key]
83
+ ), pairs = (
84
+ /** @type {number[]} */
85
+ /** @type {any} */
86
+ ENCODINGS[m.encoding]
87
+ );
88
+ const widths = m.widths;
89
+ const codeOf = /* @__PURE__ */ new Map(), cpOf = new Array(256).fill(0);
90
+ for (let i = 0; i < pairs.length; i += 2) {
91
+ const cp = pairs[i], code = pairs[i + 1];
92
+ codeOf.set(cp, code);
93
+ if (!cpOf[code] || cp === code) cpOf[code] = cp;
94
+ }
95
+ const glyphs = /* @__PURE__ */ new Map();
96
+ const getGlyph = (id) => {
97
+ let g = glyphs.get(id);
98
+ if (!g) glyphs.set(id, g = { id, advanceWidth: widths[id] || 0, codePoints: cpOf[id] ? [cpOf[id]] : [] });
99
+ return g;
100
+ };
101
+ const [x0, y0, x1, y1] = m.bbox;
102
+ return {
103
+ standard: true,
104
+ postscriptName: key,
105
+ familyName: m.familyName,
106
+ unitsPerEm: 1e3,
107
+ ascent: m.ascent,
108
+ descent: m.descent,
109
+ capHeight: m.capHeight,
110
+ xHeight: m.xHeight,
111
+ italicAngle: m.italicAngle,
112
+ underlinePosition: m.underlinePosition,
113
+ underlineThickness: m.underlineThickness,
114
+ bbox: { minX: x0, minY: y0, maxX: x1, maxY: y1 },
115
+ /** WinAnsi for the text fonts (Symbol and ZapfDingbats use their own built-in encodings) */
116
+ winAnsi: m.encoding === "WinAnsi",
117
+ widths,
118
+ /** @param {number} cp */
119
+ hasGlyphForCodePoint: (cp) => codeOf.has(cp),
120
+ /** @param {number} cp */
121
+ glyphForCodePoint: (cp) => getGlyph(codeOf.get(cp) || 0),
122
+ getGlyph
123
+ };
124
+ }
125
+
126
+ // src/engine/text/shaper.js
127
+ var LTR = 4;
128
+ var RTL = 5;
129
+ var PLAIN = ["-kern", "-liga", "-clig", "-calt", "-dlig"];
130
+ async function createShaper(wasm) {
131
+ let memory;
132
+ const { instance } = await WebAssembly.instantiate(wasm, {
133
+ env: {
134
+ _emscripten_runtime_keepalive_clear() {
135
+ },
136
+ _abort_js() {
137
+ throw new Error("HarfBuzz stopped");
138
+ },
139
+ _setitimer_js() {
140
+ return 0;
141
+ },
142
+ emscripten_resize_heap(size) {
143
+ const need = (size >>> 0) - memory.buffer.byteLength;
144
+ try {
145
+ memory.grow(Math.ceil(need / 65536));
146
+ return 1;
147
+ } catch {
148
+ return 0;
149
+ }
150
+ }
151
+ },
152
+ wasi_snapshot_preview1: { proc_exit(code) {
153
+ throw new Error(`HarfBuzz exited (${code})`);
154
+ } }
155
+ });
156
+ const x = (
157
+ /** @type {any} */
158
+ instance.exports
159
+ );
160
+ memory = x.memory;
161
+ x.__wasm_call_ctors();
162
+ const featPtr = x.malloc(16 * PLAIN.length);
163
+ PLAIN.forEach((f, i) => {
164
+ const s = x.malloc(f.length + 1);
165
+ new Uint8Array(memory.buffer).set([...f].map((c) => c.charCodeAt(0)).concat(0), s);
166
+ x.hb_feature_from_string(s, -1, featPtr + 16 * i);
167
+ x.free(s);
168
+ });
169
+ return {
170
+ /**
171
+ * A HarfBuzz font for these bytes. It lives as long as the shaper: fonts are few and reused.
172
+ * @param {Uint8Array} bytes @returns {{ ptr: number, upem: number }}
173
+ */
174
+ font(bytes) {
175
+ const buf = x.malloc(bytes.byteLength);
176
+ new Uint8Array(memory.buffer).set(bytes, buf);
177
+ const blob = x.hb_blob_create(buf, bytes.byteLength, 1, 0, 0);
178
+ const face = x.hb_face_create(blob, 0);
179
+ const ptr = x.hb_font_create(face);
180
+ const upem = x.hb_face_get_upem(face);
181
+ x.hb_face_destroy(face);
182
+ x.hb_blob_destroy(blob);
183
+ return { ptr, upem };
184
+ },
185
+ /**
186
+ * Shape one run (one font, one script, one direction).
187
+ * @param {{ ptr: number }} font @param {string} text @param {boolean} rtl
188
+ * @param {boolean} [plain] kerning and ligatures off (a simple-script run in a right-to-left context)
189
+ * @returns {number[]} [glyph id, x advance, x offset, y offset, cluster (UTF-16 index)] per glyph, in visual order
190
+ */
191
+ shape(font, text, rtl, plain = false) {
192
+ const n = text.length;
193
+ const p = x.malloc(n * 2 + 2);
194
+ const u16 = new Uint16Array(memory.buffer, p, n);
195
+ for (let i = 0; i < n; i++) u16[i] = text.charCodeAt(i);
196
+ const b = x.hb_buffer_create();
197
+ x.hb_buffer_add_utf16(b, p, n, 0, n);
198
+ x.hb_buffer_set_direction(b, rtl ? RTL : LTR);
199
+ x.hb_buffer_guess_segment_properties(b);
200
+ x.hb_shape(font.ptr, b, plain ? featPtr : 0, plain ? PLAIN.length : 0);
201
+ const len = x.hb_buffer_get_length(b);
202
+ const info = new Uint32Array(memory.buffer, x.hb_buffer_get_glyph_infos(b, 0), len * 5);
203
+ const pos = new Int32Array(memory.buffer, x.hb_buffer_get_glyph_positions(b, 0), len * 5);
204
+ const out = new Array(len * 5);
205
+ for (let i = 0; i < len; i++) {
206
+ out[i * 5] = info[i * 5];
207
+ out[i * 5 + 1] = pos[i * 5];
208
+ out[i * 5 + 2] = pos[i * 5 + 2];
209
+ out[i * 5 + 3] = pos[i * 5 + 3];
210
+ out[i * 5 + 4] = info[i * 5 + 2];
211
+ }
212
+ x.hb_buffer_destroy(b);
213
+ x.free(p);
214
+ return out;
215
+ }
216
+ };
217
+ }
218
+
219
+ // src/engine/text/fonts.js
220
+ var BUNDLED = [
221
+ ["Inter", "Inter-Regular", 400],
222
+ ["Inter", "Inter-Italic", 400, "italic"],
223
+ ["Inter", "Inter-SemiBold", 600],
224
+ ["Inter", "Inter-Bold", 700],
225
+ ["Inter", "Inter-BoldItalic", 700, "italic"],
226
+ ["JetBrains Mono", "JetBrainsMono-Regular", 400],
227
+ ["JetBrains Mono", "JetBrainsMono-Bold", 700],
228
+ ["Noto Sans Devanagari", "NotoSansDevanagari-Regular", 400],
229
+ ["Noto Sans Devanagari", "NotoSansDevanagari-Bold", 700],
230
+ ["Noto Sans Arabic", "NotoSansArabic-Regular", 400],
231
+ ["Noto Sans Arabic", "NotoSansArabic-Bold", 700],
232
+ ["Noto Sans Hebrew", "NotoSansHebrew-Regular", 400],
233
+ ["Noto Sans Hebrew", "NotoSansHebrew-Bold", 700],
234
+ // fallbacks loaded only when text uses the script (docs/TEXT.md has the sizes)
235
+ ...["Thai", "Lao", "Khmer", "Myanmar", "Tamil", "Bengali", "Telugu", "Kannada", "Gujarati"].flatMap((s) => [
236
+ [`Noto Sans ${s}`, `NotoSans${s}-Regular`, 400],
237
+ [`Noto Sans ${s}`, `NotoSans${s}-Bold`, 700]
238
+ ]),
239
+ // optional, about 40 MB (npm run fonts:cjk fetches them into /fonts/cjk): variable fonts drawn at their default
240
+ // (regular) weight. Without them the text shows as boxes, and the warning says how to add them.
241
+ ["Noto Sans JP", "NotoSansJP", 400, "normal", "cjk/NotoSansJP.ttf"],
242
+ ["Noto Sans KR", "NotoSansKR", 400, "normal", "cjk/NotoSansKR.ttf"],
243
+ ["Noto Sans SC", "NotoSansSC", 400, "normal", "cjk/NotoSansSC.ttf"],
244
+ ["Noto Emoji", "NotoEmoji", 400, "normal", "cjk/NotoEmoji.ttf"]
245
+ ];
246
+ var OPTIONAL_KEYS = ["NotoSansJP", "NotoSansKR", "NotoSansSC", "NotoEmoji"];
247
+ var FONT_FAMILIES = {};
248
+ var FACES = /* @__PURE__ */ new Map();
249
+ var addFace = (f) => {
250
+ var _a;
251
+ (FONT_FAMILIES[_a = f.family] || (FONT_FAMILIES[_a] = [])).push(f);
252
+ FACES.set(f.key, f);
253
+ };
254
+ for (const [family, key, weight, style = "normal", file] of BUNDLED) {
255
+ addFace({ family: String(family), key: String(key), weight: Number(weight), style: style === "italic" ? "italic" : "normal", file: String(file || `${key}.ttf`) });
256
+ }
257
+ for (const [family, key, weight, style] of STANDARD_FACES) {
258
+ addFace({ family: String(family), key: String(key), weight: Number(weight), style: style === "italic" ? "italic" : "normal", file: "", standard: true });
259
+ }
260
+ var BUNDLED_FAMILIES = Object.keys(FONT_FAMILIES);
261
+ var DEFAULT_FAMILY = "Inter";
262
+ var ALL_FONT_KEYS = [...FONT_FAMILIES.Inter, ...FONT_FAMILIES["JetBrains Mono"]].map((f) => f.key);
263
+ var CORE_FONT_KEY = "Inter-Regular";
264
+ var PRELOAD_KEYS = [...ALL_FONT_KEYS];
265
+ var SHAPER = "harfbuzz";
266
+ function fontFile(key) {
267
+ if (key === SHAPER) return "harfbuzz.wasm";
268
+ return FACES.get(key)?.file || `${key}.ttf`;
269
+ }
270
+ function setCustomFonts(list) {
271
+ familyCache.clear();
272
+ for (const [k, f] of FACES) if (k.startsWith("u-")) {
273
+ FACES.delete(k);
274
+ const left = FONT_FAMILIES[f.family].filter((x) => x.key !== k);
275
+ if (left.length) FONT_FAMILIES[f.family] = left;
276
+ else delete FONT_FAMILIES[f.family];
277
+ }
278
+ for (const f of list || []) {
279
+ if (BUNDLED_FAMILIES.includes(f.family) || !/^[a-f0-9]{8,64}$/.test(String(f.id))) continue;
280
+ addFace({ key: `u-${f.id}`, family: String(f.family), weight: Number(f.weight) || 400, style: f.style === "italic" ? "italic" : "normal", file: `custom/${f.id}` });
281
+ }
282
+ }
283
+ var GENERIC = {
284
+ "sans-serif": DEFAULT_FAMILY,
285
+ "system-ui": DEFAULT_FAMILY,
286
+ monospace: "JetBrains Mono",
287
+ "ui-monospace": "JetBrains Mono",
288
+ serif: "Times-Roman",
289
+ // the standard fonts' common names (metric-compatible: Arial has Helvetica's widths, and so on)
290
+ arial: "Helvetica",
291
+ times: "Times-Roman",
292
+ "times new roman": "Times-Roman",
293
+ "courier new": "Courier",
294
+ "zapf dingbats": "ZapfDingbats"
295
+ };
296
+ var MONO = /mono|courier|consol|menlo|monaco|code|typewriter|fixed|terminal|lucida console|andale/i;
297
+ var familyCache = /* @__PURE__ */ new Map();
298
+ function familyOf(name) {
299
+ let r = familyCache.get(name);
300
+ if (r) return r;
301
+ const names = String(name).split(",").map((n) => n.trim().replace(/^['"]|['"]$/g, "")).filter(Boolean);
302
+ const known = Object.keys(FONT_FAMILIES);
303
+ for (const n of names) {
304
+ const lc = n.toLowerCase();
305
+ const hit = known.find((k) => k.toLowerCase() === lc) || GENERIC[lc];
306
+ if (hit) {
307
+ r = { family: hit };
308
+ break;
309
+ }
310
+ }
311
+ const first = names[0] || DEFAULT_FAMILY;
312
+ r || (r = { family: MONO.test(first) ? "JetBrains Mono" : DEFAULT_FAMILY, unknown: first.slice(0, 60) });
313
+ if (familyCache.size >= 500) familyCache.clear();
314
+ familyCache.set(name, r);
315
+ return r;
316
+ }
317
+ function resolveFontKey(family, weight, style, unknown) {
318
+ let faces = FONT_FAMILIES[family || DEFAULT_FAMILY];
319
+ if (!faces) {
320
+ const f = familyOf(String(family));
321
+ if (f.unknown && unknown && !f.unknown.startsWith("=")) unknown.add(f.unknown);
322
+ faces = FONT_FAMILIES[f.family] || FONT_FAMILIES[DEFAULT_FAMILY];
323
+ }
324
+ const w = weight === "bold" ? 700 : weight === "normal" || weight == null ? 400 : Number(weight) || 400;
325
+ const italic = faces.filter((f) => f.style === "italic");
326
+ const list = style === "italic" && italic.length ? italic : faces.filter((f) => f.style !== "italic").length ? faces.filter((f) => f.style !== "italic") : faces;
327
+ const rank = (f) => {
328
+ const fw = f.weight;
329
+ if (w >= 400 && w <= 500) return fw >= w && fw <= 500 ? fw - w : fw < w ? 1e3 + w - fw : 2e3 + fw - w;
330
+ if (w < 400) return fw <= w ? w - fw : 1e3 + fw - w;
331
+ return fw >= w ? fw - w : 1e3 + w - fw;
332
+ };
333
+ return list.reduce((best, f) => rank(f) < rank(best) ? f : best).key;
334
+ }
335
+ function embeddedFace(key) {
336
+ if (!isStandard(key)) return key;
337
+ const f = (
338
+ /** @type {Face} */
339
+ FACES.get(key)
340
+ );
341
+ return resolveFontKey(f.family === "Courier" ? "JetBrains Mono" : DEFAULT_FAMILY, f.weight, f.style);
342
+ }
343
+ var CSS_STACK = {
344
+ Helvetica: 'Helvetica, Arial, "Liberation Sans", sans-serif',
345
+ "Times-Roman": '"Times New Roman", Times, "Liberation Serif", serif',
346
+ Courier: '"Courier New", Courier, "Liberation Mono", monospace',
347
+ Symbol: "Symbol",
348
+ ZapfDingbats: '"Zapf Dingbats", ZapfDingbats'
349
+ };
350
+ var standardCss = (key) => isStandard(key) ? CSS_STACK[
351
+ /** @type {Face} */
352
+ FACES.get(key).family
353
+ ] : null;
354
+ function officeFamily(key) {
355
+ const fam = fontCss(key).family;
356
+ return { Helvetica: "Arial", "Times-Roman": "Times New Roman", Courier: "Courier New" }[fam] || fam;
357
+ }
358
+ function fontCss(key) {
359
+ const f = FACES.get(key);
360
+ return f ? { family: f.family, weight: f.weight, style: f.style } : { family: DEFAULT_FAMILY, weight: 400, style: "normal" };
361
+ }
362
+ var FALLBACK = [
363
+ [1424, 1535, "Noto Sans Hebrew"],
364
+ [64285, 64335, "Noto Sans Hebrew"],
365
+ [1536, 2303, "Noto Sans Arabic"],
366
+ [64336, 65023, "Noto Sans Arabic"],
367
+ [65136, 65278, "Noto Sans Arabic"],
368
+ [2304, 2431, "Noto Sans Devanagari"],
369
+ [43232, 43263, "Noto Sans Devanagari"],
370
+ [7376, 7423, "Noto Sans Devanagari"],
371
+ [2432, 2559, "Noto Sans Bengali"],
372
+ [2688, 2815, "Noto Sans Gujarati"],
373
+ [2944, 3071, "Noto Sans Tamil"],
374
+ [73664, 73727, "Noto Sans Tamil"],
375
+ [3072, 3199, "Noto Sans Telugu"],
376
+ [3200, 3327, "Noto Sans Kannada"],
377
+ [3584, 3711, "Noto Sans Thai"],
378
+ [3712, 3839, "Noto Sans Lao"],
379
+ [4096, 4255, "Noto Sans Myanmar"],
380
+ [43488, 43519, "Noto Sans Myanmar"],
381
+ [43616, 43647, "Noto Sans Myanmar"],
382
+ [6016, 6143, "Noto Sans Khmer"],
383
+ [6624, 6655, "Noto Sans Khmer"],
384
+ // CJK (optional fonts): kana and Han in the Japanese face (Han shapes differ a little from Chinese; a report can
385
+ // set fontFamily "Noto Sans SC"), Hangul in the Korean one; emoji in Noto Emoji (monochrome)
386
+ [12352, 12543, "Noto Sans JP"],
387
+ [12784, 12799, "Noto Sans JP"],
388
+ [12288, 12351, "Noto Sans JP"],
389
+ [13312, 19903, "Noto Sans JP"],
390
+ [19968, 40959, "Noto Sans JP"],
391
+ [63744, 64255, "Noto Sans JP"],
392
+ [65280, 65519, "Noto Sans JP"],
393
+ [4352, 4607, "Noto Sans KR"],
394
+ [12592, 12687, "Noto Sans KR"],
395
+ [44032, 55215, "Noto Sans KR"],
396
+ [126976, 129791, "Noto Emoji"],
397
+ [9728, 10175, "Noto Emoji"],
398
+ [11008, 11263, "Noto Emoji"]
399
+ ];
400
+ var allFontKeys = () => [...FACES.keys()];
401
+ function modelFontKeys(model) {
402
+ const keys = /* @__PURE__ */ new Set(), stack = [model?.pages];
403
+ while (stack.length) {
404
+ const o = stack.pop();
405
+ if (!o || typeof o !== "object" || ArrayBuffer.isView(o)) continue;
406
+ if (typeof o.font === "string" && FACES.has(o.font)) keys.add(o.font);
407
+ for (const v of Array.isArray(o) ? o : Object.values(o)) if (v && typeof v === "object") stack.push(v);
408
+ }
409
+ return [...keys];
410
+ }
411
+ function fallbackKeys(key) {
412
+ const c = fontCss(key);
413
+ return [...new Set(FALLBACK.map((f) => String(f[2])))].map((family) => resolveFontKey(family, c.weight, c.style));
414
+ }
415
+ function unicodeRange(key) {
416
+ const family = FACES.get(key)?.family;
417
+ const r = FALLBACK.filter((f) => f[2] === family).map(([a, b]) => `U+${Number(a).toString(16)}-${Number(b).toString(16)}`);
418
+ return r.length ? [...r, "U+300-36F", "U+2000-206F", "U+25CC", "U+FE00-FE0F"].join(",") : null;
419
+ }
420
+ function fallbackKey(cp, key) {
421
+ for (const [a, b, family] of FALLBACK) {
422
+ if (cp >= /** @type {number} */
423
+ a && cp <= /** @type {number} */
424
+ b) {
425
+ const c = fontCss(key);
426
+ return resolveFontKey(String(family), c.weight, c.style);
427
+ }
428
+ }
429
+ return null;
430
+ }
431
+ var SIMPLE_FALLBACK = /* @__PURE__ */ new Set(["Noto Sans JP", "Noto Sans KR", "Noto Emoji"]);
432
+ var BEYOND_LATIN = /[^\u0000-\u024f\u1e00-\u1eff\u2000-\u20cf\u2100-\u218f]/;
433
+ function fontsForDef(def, unknown = void 0) {
434
+ const keys = /* @__PURE__ */ new Set();
435
+ const seen = /* @__PURE__ */ new Set();
436
+ const baseFamily = def?.styles?.base?.fontFamily;
437
+ const walk = (o) => {
438
+ if (!o || typeof o !== "object" || seen.has(o)) return;
439
+ seen.add(o);
440
+ if (Array.isArray(o)) {
441
+ for (const x of o) walk(x);
442
+ return;
443
+ }
444
+ if (o.fontFamily != null || o.fontWeight != null || o.fontStyle != null) keys.add(resolveFontKey(o.fontFamily ?? baseFamily, o.fontWeight, o.fontStyle, unknown));
445
+ if (o.type === "chart") keys.add(resolveFontKey(o.fontFamily ?? baseFamily, "bold", "normal"));
446
+ for (const [k, v] of Object.entries(o)) if (v && typeof v === "object" && k !== "dataSources" && k !== "data") walk(v);
447
+ };
448
+ walk(def);
449
+ return [...keys];
450
+ }
451
+ function fontsFor(texts) {
452
+ const keys = /* @__PURE__ */ new Set(), seen = /* @__PURE__ */ new Set();
453
+ let shaper = false;
454
+ for (const t of texts) {
455
+ if (typeof t !== "string" || !BEYOND_LATIN.test(t)) continue;
456
+ for (const ch of t) {
457
+ const cp = (
458
+ /** @type {number} */
459
+ ch.codePointAt(0)
460
+ );
461
+ if (cp < 592 || seen.has(cp)) continue;
462
+ seen.add(cp);
463
+ for (const [a, b, family] of FALLBACK) {
464
+ if (cp < /** @type {number} */
465
+ a || cp > /** @type {number} */
466
+ b) continue;
467
+ keys.add(resolveFontKey(String(family), 400, "normal")).add(resolveFontKey(String(family), 700, "normal"));
468
+ if (!SIMPLE_FALLBACK.has(String(family))) shaper = true;
469
+ break;
470
+ }
471
+ }
472
+ }
473
+ if (shaper) keys.add(SHAPER);
474
+ return [...keys];
475
+ }
476
+ var FontStore = class {
477
+ /** @param {(key: string) => Promise<ArrayBuffer|Uint8Array>} loader */
478
+ constructor(loader) {
479
+ this.loader = loader;
480
+ this.fonts = /* @__PURE__ */ new Map();
481
+ this.bytes = /* @__PURE__ */ new Map();
482
+ this.pending = /* @__PURE__ */ new Map();
483
+ this.failed = /* @__PURE__ */ new Set();
484
+ this.shaper = null;
485
+ this.hb = /* @__PURE__ */ new Map();
486
+ }
487
+ /** @param {string[]} keys */
488
+ async load(keys = ALL_FONT_KEYS) {
489
+ await Promise.all(keys.map((k) => {
490
+ if (this.fonts.has(k) || this.failed.has(k) || k === SHAPER && this.shaper) return null;
491
+ if (!this.pending.has(k)) {
492
+ this.pending.set(k, (async () => {
493
+ try {
494
+ if (isStandard(k)) {
495
+ this.fonts.set(k, await standardFont(k));
496
+ return;
497
+ }
498
+ if (typeof this.loader !== "function") throw new Error(`Font "${k}" needs its file. Install @reportwright/fonts, or pass { fontStore } (defaultFontStore() or new FontStore(loader))`);
499
+ const b = await this.loader(k);
500
+ const u8 = b instanceof Uint8Array ? b : new Uint8Array(b);
501
+ if (k === SHAPER) {
502
+ this.shaper = await createShaper(u8);
503
+ return;
504
+ }
505
+ await loadFontkit();
506
+ this.fonts.set(k, fontkit.create(u8));
507
+ this.bytes.set(k, u8);
508
+ } catch (e) {
509
+ this.pending.delete(k);
510
+ if (k === CORE_FONT_KEY) throw e;
511
+ this.failed.add(k);
512
+ }
513
+ })());
514
+ }
515
+ return this.pending.get(k);
516
+ }));
517
+ }
518
+ /** @param {string} key */
519
+ has(key) {
520
+ return this.fonts.has(key);
521
+ }
522
+ /** The HarfBuzz font for a loaded key (the shaper must be loaded). @param {string} key */
523
+ hbFont(key) {
524
+ let f = this.hb.get(key);
525
+ if (!f) {
526
+ f = this.shaper.font(this.bytes.get(key));
527
+ this.hb.set(key, f);
528
+ }
529
+ return f;
530
+ }
531
+ /** @param {string} key */
532
+ get(key) {
533
+ const f = this.fonts.get(key);
534
+ if (!f) throw new Error(`Font "${key}" is not loaded`);
535
+ return f;
536
+ }
537
+ };
538
+
539
+ // src/engine/image.js
540
+ var IMAGE_LIMITS = {
541
+ bytes: 10 * 1024 * 1024,
542
+ // one image
543
+ total: 50 * 1024 * 1024,
544
+ // all images of one render (each distinct image counted once)
545
+ pixels: 4e7,
546
+ // a PNG larger than this is not decoded (a small file can inflate to gigabytes)
547
+ svgBytes: 2 * 1024 * 1024,
548
+ // an SVG drawn as vector paths in the PDF
549
+ svgShapes: 1e4
550
+ };
551
+ var PX = 0.75;
552
+ var MIME = { png: "image/png", jpeg: "image/jpeg", gif: "image/gif", webp: "image/webp", svg: "image/svg+xml" };
553
+ function sniff(b) {
554
+ if (b.length >= 8 && b[0] === 137 && b[1] === 80 && b[2] === 78 && b[3] === 71) return "png";
555
+ if (b.length >= 3 && b[0] === 255 && b[1] === 216 && b[2] === 255) return "jpeg";
556
+ if (b.length >= 6 && b[0] === 71 && b[1] === 73 && b[2] === 70 && b[3] === 56) return "gif";
557
+ if (b.length >= 12 && b[0] === 82 && b[1] === 73 && b[2] === 70 && b[3] === 70 && b[8] === 87 && b[9] === 69 && b[10] === 66 && b[11] === 80) return "webp";
558
+ const head = String.fromCharCode(...b.subarray(0, 512)).replace(/^|^\xEF\xBB\xBF/, "").trimStart();
559
+ if (/^<(\?xml|svg|!--|!DOCTYPE svg)/i.test(head) && /<svg[\s>]/i.test(head + (b.length > 512 ? "<svg " : ""))) return "svg";
560
+ return null;
561
+ }
562
+ function toBase64(b) {
563
+ let s = "";
564
+ for (let i = 0; i < b.length; i += 32768) s += String.fromCharCode(...b.subarray(i, i + 32768));
565
+ return btoa(s);
566
+ }
567
+ function fromBase64(s) {
568
+ const bin = atob(s);
569
+ const out = new Uint8Array(bin.length);
570
+ for (let i = 0; i < bin.length; i++) out[i] = bin.charCodeAt(i);
571
+ return out;
572
+ }
573
+ var B64 = /^[A-Za-z0-9+/]+={0,2}$/;
574
+ function toDataUri(v) {
575
+ if (v instanceof ArrayBuffer) v = new Uint8Array(v);
576
+ if (v instanceof Uint8Array) {
577
+ if (v.length > IMAGE_LIMITS.bytes) return null;
578
+ const type2 = sniff(v);
579
+ return type2 ? `data:${MIME[type2]};base64,${toBase64(v)}` : null;
580
+ }
581
+ if (typeof v !== "string" || v.length < 16 || v.startsWith("data:")) return v;
582
+ if (/[^A-Za-z0-9+/=\r\n]/.test(v)) return v;
583
+ const s = v.replace(/[\r\n]/g, "");
584
+ if (!B64.test(s) || s.length % 4) return v;
585
+ let type;
586
+ try {
587
+ type = sniff(fromBase64(s.slice(0, 700)));
588
+ } catch {
589
+ return v;
590
+ }
591
+ return type ? `data:${MIME[type]};base64,${s}` : v;
592
+ }
593
+ function splitDataUri(uri) {
594
+ if (typeof uri !== "string" || !/^data:/i.test(uri)) return null;
595
+ const c = uri.indexOf(",");
596
+ if (c < 0) return null;
597
+ const meta = uri.slice(5, c);
598
+ return { meta, b64: meta.slice(meta.lastIndexOf(";") + 1).trim().toLowerCase() === "base64" && meta.includes(";"), body: uri.slice(c + 1) };
599
+ }
600
+ function dataUriBytes(uri) {
601
+ const d = splitDataUri(uri);
602
+ if (!d) return 0;
603
+ return d.b64 ? Math.floor(d.body.length * 3 / 4) : d.body.length;
604
+ }
605
+ function dataUriHead(uri, max = 262144) {
606
+ const d = splitDataUri(uri);
607
+ if (!d) return null;
608
+ try {
609
+ if (d.b64) return fromBase64(d.body.slice(0, Number.isFinite(max) ? Math.ceil(max / 3) * 4 : void 0).replace(/\s/g, ""));
610
+ return new TextEncoder().encode(decodeURIComponent(d.body.slice(0, max)));
611
+ } catch {
612
+ return null;
613
+ }
614
+ }
615
+ function dataUriBytesOf(uri) {
616
+ return dataUriHead(uri, Infinity);
617
+ }
618
+ var UNIT = { px: 1, pt: 4 / 3, pc: 16, mm: 96 / 25.4, cm: 96 / 2.54, in: 96, "": 1 };
619
+ function svgLength(v) {
620
+ const t = String(v ?? "").trim();
621
+ if (t.length > 64) return null;
622
+ const m = /^([\d.]+(?:e[-+]?\d+)?)(px|pt|pc|mm|cm|in)?$/i.exec(t);
623
+ if (!m) return null;
624
+ const n = Number(m[1]) * UNIT[(m[2] || "").toLowerCase()];
625
+ return Number.isFinite(n) && n > 0 ? n : null;
626
+ }
627
+ var isName = (c) => c >= "a" && c <= "z" || c >= "A" && c <= "Z" || c >= "0" && c <= "9" || c === "_" || c === ":" || c === "-" || c === ".";
628
+ var isSpace = (c) => c === " " || c === " " || c === "\n" || c === "\r";
629
+ function* xmlTags(text) {
630
+ const n = text.length;
631
+ let i = 0;
632
+ while (i < n) {
633
+ const lt = text.indexOf("<", i);
634
+ if (lt < 0) return;
635
+ if (text.startsWith("<!--", lt)) {
636
+ const e = text.indexOf("-->", lt + 4);
637
+ if (e < 0) return;
638
+ i = e + 3;
639
+ continue;
640
+ }
641
+ if (text.startsWith("<![CDATA[", lt)) {
642
+ const e = text.indexOf("]]>", lt + 9);
643
+ if (e < 0) return;
644
+ i = e + 3;
645
+ continue;
646
+ }
647
+ if (text[lt + 1] === "?" || text[lt + 1] === "!") {
648
+ const e = text.indexOf(">", lt + 2);
649
+ if (e < 0) return;
650
+ i = e + 1;
651
+ continue;
652
+ }
653
+ let j = lt + 1, q = "";
654
+ for (; j < n; j++) {
655
+ const c = text[j];
656
+ if (q) {
657
+ if (c === q) q = "";
658
+ } else if (c === '"' || c === "'") q = c;
659
+ else if (c === ">") break;
660
+ }
661
+ if (j >= n) return;
662
+ i = j + 1;
663
+ let body = text.slice(lt + 1, j);
664
+ const close = body[0] === "/";
665
+ if (close) body = body.slice(1);
666
+ const self = body.endsWith("/");
667
+ if (self) body = body.slice(0, -1);
668
+ let k = 0;
669
+ while (k < body.length && isName(body[k])) k++;
670
+ const name = body.slice(0, k);
671
+ if (!/^[a-zA-Z]/.test(name)) continue;
672
+ yield { close, name, attrs: body.slice(k), self };
673
+ }
674
+ }
675
+ function xmlAttrs(s) {
676
+ const a = /* @__PURE__ */ Object.create(null);
677
+ const n = s.length;
678
+ let i = 0;
679
+ while (i < n) {
680
+ while (i < n && !isName(s[i])) i++;
681
+ const st = i;
682
+ while (i < n && isName(s[i])) i++;
683
+ const name = s.slice(st, i);
684
+ while (i < n && isSpace(s[i])) i++;
685
+ if (s[i] !== "=") continue;
686
+ i++;
687
+ while (i < n && isSpace(s[i])) i++;
688
+ const q = s[i];
689
+ if (q !== '"' && q !== "'") continue;
690
+ const e = s.indexOf(q, i + 1);
691
+ if (e < 0) break;
692
+ if (name) a[name] = s.slice(i + 1, e);
693
+ i = e + 1;
694
+ }
695
+ return a;
696
+ }
697
+ function svgRootAttrs(text) {
698
+ for (const t of xmlTags(String(text))) if (!t.close && t.name.toLowerCase() === "svg") return xmlAttrs(t.attrs);
699
+ return null;
700
+ }
701
+ function svgSize(text) {
702
+ const a = svgRootAttrs(text);
703
+ if (!a) return null;
704
+ const vb = String(a.viewBox || "").trim().split(/[\s,]+/).map(Number);
705
+ const hasVb = vb.length === 4 && vb.every(Number.isFinite) && vb[2] > 0 && vb[3] > 0;
706
+ let w = svgLength(a.width), h = svgLength(a.height);
707
+ if (w && !h) h = hasVb ? w * vb[3] / vb[2] : null;
708
+ if (h && !w) w = hasVb ? h * vb[2] / vb[3] : null;
709
+ if (!w && hasVb) {
710
+ w = vb[2];
711
+ h = vb[3];
712
+ }
713
+ return w && h ? { w, h } : null;
714
+ }
715
+ function imageInfoOf(b) {
716
+ const type = sniff(b);
717
+ if (!type) return null;
718
+ const u32 = (i) => (b[i] << 24 | b[i + 1] << 16 | b[i + 2] << 8 | b[i + 3]) >>> 0;
719
+ if (type === "png") return pngInfo(b);
720
+ if (type === "gif" && b.length >= 10) return { type, w: b[6] | b[7] << 8, h: b[8] | b[9] << 8 };
721
+ if (type === "jpeg") {
722
+ for (let i = 2; i + 9 < b.length; ) {
723
+ if (b[i] !== 255) {
724
+ i++;
725
+ continue;
726
+ }
727
+ const mk = b[i + 1];
728
+ if (mk === 255) {
729
+ i++;
730
+ continue;
731
+ }
732
+ if (mk === 216 || mk === 1 || mk >= 208 && mk <= 215) {
733
+ i += 2;
734
+ continue;
735
+ }
736
+ if (mk >= 192 && mk <= 207 && mk !== 196 && mk !== 200 && mk !== 204) return { type, w: b[i + 7] << 8 | b[i + 8], h: b[i + 5] << 8 | b[i + 6] };
737
+ i += 2 + (b[i + 2] << 8 | b[i + 3]);
738
+ }
739
+ return { type };
740
+ }
741
+ if (type === "svg") {
742
+ const s = svgSize(new TextDecoder().decode(b));
743
+ return s ? { type, ...s } : { type };
744
+ }
745
+ return { type };
746
+ }
747
+ function pngInfo(b) {
748
+ const u32 = (i) => (b[i] << 24 | b[i + 1] << 16 | b[i + 2] << 8 | b[i + 3]) >>> 0;
749
+ let w = 0, h = 0, ihdrs = 0, animated = false;
750
+ for (let off = 8; off + 8 <= b.length; ) {
751
+ const len = u32(off);
752
+ const t = String.fromCharCode(b[off + 4], b[off + 5], b[off + 6], b[off + 7]);
753
+ const d = off + 8;
754
+ if (t === "IHDR" && d + 8 <= b.length) {
755
+ w = u32(d);
756
+ h = u32(d + 4);
757
+ ihdrs++;
758
+ } else if (t === "acTL" || t === "fcTL" || t === "fdAT") animated = true;
759
+ else if (t === "IEND") break;
760
+ off = d + len + 4;
761
+ }
762
+ if (!ihdrs) return { type: "png" };
763
+ return { type: "png", w, h, ...animated || ihdrs > 1 ? { suspect: true } : {} };
764
+ }
765
+ function imageInfo(uri) {
766
+ const b = typeof uri === "string" && uri.startsWith("data:") ? dataUriHead(uri) : null;
767
+ return b ? imageInfoOf(b) : null;
768
+ }
769
+ function resolveImageSrc(v, who, c) {
770
+ var _a;
771
+ if (v == null || v === "" || v === "#Error") return null;
772
+ if (typeof v === "string" && v.startsWith("embedded:")) {
773
+ const name = v.slice(9);
774
+ const img = c.images && Object.prototype.hasOwnProperty.call(c.images, name) ? c.images[name] : void 0;
775
+ if (typeof img !== "string" || !/^data:image\/[\w.+-]+[;,]/i.test(img)) {
776
+ c.warn(`${who}: there is no embedded image named "${name}" (add it to the report's images as a data:image/… URI)`);
777
+ return null;
778
+ }
779
+ v = img;
780
+ }
781
+ const memo = c.budget ? (_a = c.budget).memo || (_a.memo = /* @__PURE__ */ new Map()) : null;
782
+ let u = memo?.get(v);
783
+ if (u === void 0) {
784
+ u = toDataUri(v);
785
+ memo?.set(v, u);
786
+ }
787
+ if (u == null) {
788
+ c.warn(`${who}: the image data is not a PNG, JPEG, GIF, WebP or SVG image, or is larger than 10 MB`);
789
+ return null;
790
+ }
791
+ const s = String(u);
792
+ if (s.startsWith("data:")) {
793
+ const n = dataUriBytes(s);
794
+ if (n > IMAGE_LIMITS.bytes) {
795
+ c.warn(`${who}: the image is ${(n / 1048576).toFixed(1)} MB; images are limited to 10 MB each, so it is left out`);
796
+ return null;
797
+ }
798
+ const b = c.budget;
799
+ if (b && !b.seen.has(s)) {
800
+ if (b.bytes + n > IMAGE_LIMITS.total) {
801
+ c.warn(`${who}: the report's images pass 50 MB in all, so this one is left out`);
802
+ return null;
803
+ }
804
+ b.seen.add(s);
805
+ b.bytes += n;
806
+ }
807
+ }
808
+ return s;
809
+ }
810
+
811
+ export {
812
+ fontkit,
813
+ PDFDocument,
814
+ PDFName,
815
+ PDFString,
816
+ PDFHexString,
817
+ PDFRawStream,
818
+ PDFStream,
819
+ PDFArray,
820
+ PDFDict,
821
+ PDFNumber,
822
+ PDFBool,
823
+ rgb,
824
+ pushGraphicsState,
825
+ popGraphicsState,
826
+ concatTransformationMatrix,
827
+ loadFontkit,
828
+ loadPdfLib,
829
+ isStandard,
830
+ OPTIONAL_KEYS,
831
+ FONT_FAMILIES,
832
+ BUNDLED_FAMILIES,
833
+ DEFAULT_FAMILY,
834
+ ALL_FONT_KEYS,
835
+ CORE_FONT_KEY,
836
+ PRELOAD_KEYS,
837
+ SHAPER,
838
+ fontFile,
839
+ setCustomFonts,
840
+ familyOf,
841
+ resolveFontKey,
842
+ embeddedFace,
843
+ standardCss,
844
+ officeFamily,
845
+ fontCss,
846
+ allFontKeys,
847
+ modelFontKeys,
848
+ fallbackKeys,
849
+ unicodeRange,
850
+ fallbackKey,
851
+ fontsForDef,
852
+ fontsFor,
853
+ FontStore,
854
+ IMAGE_LIMITS,
855
+ PX,
856
+ dataUriBytes,
857
+ dataUriBytesOf,
858
+ svgLength,
859
+ xmlTags,
860
+ xmlAttrs,
861
+ svgRootAttrs,
862
+ imageInfoOf,
863
+ imageInfo,
864
+ resolveImageSrc
865
+ };
866
+ //# sourceMappingURL=chunk-JQTRDHQP.js.map