reamkit 1.16.0 → 1.18.0

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 (76) hide show
  1. package/dist/esm/core/bidi/segments.js +1 -2
  2. package/dist/esm/core/converter/project.js +5 -1
  3. package/dist/esm/core/document-model/index.d.ts +1 -1
  4. package/dist/esm/core/document-model/types.d.ts +526 -8
  5. package/dist/esm/core/drawingml/chart-geometry.d.ts +8 -12
  6. package/dist/esm/core/drawingml/chart-geometry.js +58 -9
  7. package/dist/esm/core/drawingml/chart-parser.js +44 -5
  8. package/dist/esm/core/drawingml/colors.d.ts +1 -1
  9. package/dist/esm/core/drawingml/colors.js +27 -1
  10. package/dist/esm/core/drawingml/preset-geometry.js +233 -0
  11. package/dist/esm/core/drawingml/shape-render.d.ts +12 -0
  12. package/dist/esm/core/drawingml/shape-render.js +116 -3
  13. package/dist/esm/core/drawingml/theme-parser.d.ts +10 -0
  14. package/dist/esm/core/drawingml/theme-parser.js +19 -1
  15. package/dist/esm/core/font/measure.d.ts +5 -0
  16. package/dist/esm/core/font/measure.js +21 -1
  17. package/dist/esm/core/images.d.ts +2 -2
  18. package/dist/esm/core/images.js +219 -0
  19. package/dist/esm/core/ir/flow.d.ts +23 -1
  20. package/dist/esm/core/lzw.d.ts +17 -0
  21. package/dist/esm/core/lzw.js +83 -0
  22. package/dist/esm/core/metafile/emf.d.ts +16 -0
  23. package/dist/esm/core/metafile/emf.js +635 -0
  24. package/dist/esm/core/metafile/picture.d.ts +106 -0
  25. package/dist/esm/core/metafile/picture.js +55 -0
  26. package/dist/esm/core/metafile/wmf.d.ts +9 -0
  27. package/dist/esm/core/metafile/wmf.js +371 -0
  28. package/dist/esm/core/numbering/apply.d.ts +5 -3
  29. package/dist/esm/core/numbering/apply.js +42 -11
  30. package/dist/esm/core/numbering/index.js +2 -0
  31. package/dist/esm/core/numbering/state.d.ts +13 -1
  32. package/dist/esm/core/numbering/state.js +256 -15
  33. package/dist/esm/core/po-helpers.js +16 -1
  34. package/dist/esm/core/style-cascade/resolver.js +66 -11
  35. package/dist/esm/core/style-cascade/table.js +35 -11
  36. package/dist/esm/core/style-cascade/types.d.ts +42 -1
  37. package/dist/esm/core/style-cascade/types.js +4 -0
  38. package/dist/esm/core/tiff.d.ts +20 -0
  39. package/dist/esm/core/tiff.js +339 -0
  40. package/dist/esm/core/vector.d.ts +22 -0
  41. package/dist/esm/excel/print-model.js +4 -2
  42. package/dist/esm/excel/sheet-to-flow.js +10 -8
  43. package/dist/esm/excel/worksheet-parser.js +1 -1
  44. package/dist/esm/html/html-writer.js +20 -5
  45. package/dist/esm/layout/page-doc.d.ts +107 -4
  46. package/dist/esm/layout/styled-layout.d.ts +44 -2
  47. package/dist/esm/layout/styled-layout.js +2330 -283
  48. package/dist/esm/pdf/shading.js +76 -6
  49. package/dist/esm/pdf/styled-page-emitter.js +294 -45
  50. package/dist/esm/pdf/vector-graphics.d.ts +29 -2
  51. package/dist/esm/pdf/vector-graphics.js +96 -12
  52. package/dist/esm/pdf-reader/image-decode.js +7 -75
  53. package/dist/esm/pptx/pptx-reader.js +1 -0
  54. package/dist/esm/pptx/slide-parser.d.ts +21 -4
  55. package/dist/esm/pptx/slide-parser.js +86 -23
  56. package/dist/esm/svg/svg-writer.js +2 -2
  57. package/dist/esm/word/document-parser.d.ts +96 -7
  58. package/dist/esm/word/document-parser.js +540 -116
  59. package/dist/esm/word/docx-reader.js +135 -43
  60. package/dist/esm/word/docx-writer.js +6 -1
  61. package/dist/esm/word/drawing-parser.d.ts +58 -5
  62. package/dist/esm/word/drawing-parser.js +1632 -63
  63. package/dist/esm/word/index.d.ts +4 -4
  64. package/dist/esm/word/numbering-parser.d.ts +2 -1
  65. package/dist/esm/word/numbering-parser.js +107 -21
  66. package/dist/esm/word/paragraph-properties.d.ts +11 -1
  67. package/dist/esm/word/paragraph-properties.js +219 -10
  68. package/dist/esm/word/run-properties.js +45 -1
  69. package/dist/esm/word/settings-parser.d.ts +24 -0
  70. package/dist/esm/word/settings-parser.js +31 -5
  71. package/dist/esm/word/shading.d.ts +11 -0
  72. package/dist/esm/word/shading.js +64 -0
  73. package/dist/esm/word/styles-parser.js +8 -2
  74. package/dist/esm/word/table-parser.d.ts +9 -1
  75. package/dist/esm/word/table-parser.js +182 -30
  76. package/package.json +1 -1
@@ -0,0 +1,635 @@
1
+ import { PathBuilder } from "../vector.js";
2
+ import { applyTransform, cloneDc, colorRef, newDeviceContext } from "./picture.js";
3
+ //#region src/core/metafile/emf.ts
4
+ /** Whether the bytes open with an EMF header (MS-EMF §2.3.4.2: type 1 + " EMF"). */
5
+ function isEmf(bytes) {
6
+ if (bytes.length < 44) return false;
7
+ const v = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
8
+ return v.getUint32(0, true) === 1 && v.getUint32(40, true) === 1179469088;
9
+ }
10
+ var RECORD_NAMES = new Map([
11
+ [48, "palette"],
12
+ [49, "palette"],
13
+ [50, "palette"],
14
+ [51, "palette"],
15
+ [52, "palette"],
16
+ [70, "comment"],
17
+ [71, "region fill"],
18
+ [72, "region frame"],
19
+ [73, "region invert"],
20
+ [74, "region paint"],
21
+ [78, "masked blit"],
22
+ [79, "parallelogram blit"],
23
+ [80, "device bitmap"],
24
+ [81, "bitmap"],
25
+ [76, "bitmap"],
26
+ [77, "bitmap"],
27
+ [114, "alpha blit"],
28
+ [116, "transparent blit"],
29
+ [118, "gradient fill"]
30
+ ]);
31
+ /**
32
+ * Read an EMF into its primitives.
33
+ *
34
+ * @throws Error when the bytes are not an EMF or its header is malformed.
35
+ */
36
+ function readEmf(bytes) {
37
+ if (!isEmf(bytes)) throw new Error("EMF: not an enhanced metafile");
38
+ const v = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
39
+ const bounds = {
40
+ left: v.getInt32(8, true),
41
+ top: v.getInt32(12, true),
42
+ right: v.getInt32(16, true),
43
+ bottom: v.getInt32(20, true)
44
+ };
45
+ const prims = [];
46
+ const skipped = /* @__PURE__ */ new Set();
47
+ const objects = /* @__PURE__ */ new Map();
48
+ const stack = [];
49
+ let dc = newDeviceContext();
50
+ let win = {
51
+ x: 0,
52
+ y: 0,
53
+ cx: 1,
54
+ cy: 1
55
+ };
56
+ let view = {
57
+ x: 0,
58
+ y: 0,
59
+ cx: 1,
60
+ cy: 1
61
+ };
62
+ let haveWin = false;
63
+ let haveView = false;
64
+ const sx = () => haveWin && haveView && win.cx !== 0 ? view.cx / win.cx : 1;
65
+ const sy = () => haveWin && haveView && win.cy !== 0 ? view.cy / win.cy : 1;
66
+ /** Logical → device, through the world transform and the window mapping. */
67
+ const px = (x, y) => {
68
+ const w = applyTransform(dc.transform, x, y);
69
+ return {
70
+ x: (w.x - win.x) * sx() + view.x,
71
+ y: (w.y - win.y) * sy() + view.y
72
+ };
73
+ };
74
+ let building;
75
+ const open = () => building ?? [];
76
+ const strokeOf = () => {
77
+ if (dc.pen.style === "none") return void 0;
78
+ const w = dc.pen.widthLu <= 1 ? 1 : dc.pen.widthLu * Math.abs(sx());
79
+ return {
80
+ colorHex: dc.pen.colorHex,
81
+ widthPt: w,
82
+ ...dc.pen.style === "solid" ? {} : { dash: dc.pen.style === "dot" ? [w, 2 * w] : [4 * w, 3 * w] }
83
+ };
84
+ };
85
+ const paint = (segments, fill, stroke) => {
86
+ if (segments.length === 0) return;
87
+ const path = {
88
+ segments,
89
+ fillRule: dc.fillRule
90
+ };
91
+ const st = stroke ? strokeOf() : void 0;
92
+ const fillHex = fill && !dc.brush.hollow ? dc.brush.colorHex : void 0;
93
+ if (fillHex === void 0 && !st) return;
94
+ prims.push({
95
+ kind: "path",
96
+ paths: [path],
97
+ ...fillHex !== void 0 ? { fillColorHex: fillHex } : {},
98
+ ...st ? { stroke: st } : {}
99
+ });
100
+ };
101
+ /** A closed rectangle, as the geometry records draw one. */
102
+ const rectSegments = (l, t, r, b) => {
103
+ const p0 = px(l, t);
104
+ const p1 = px(r, t);
105
+ const p2 = px(r, b);
106
+ const p3 = px(l, b);
107
+ return new PathBuilder().moveTo(p0.x, p0.y).lineTo(p1.x, p1.y).lineTo(p2.x, p2.y).lineTo(p3.x, p3.y).close().build().segments;
108
+ };
109
+ let off = 0;
110
+ let guard = 0;
111
+ while (off + 8 <= bytes.length && guard++ < 2e5) {
112
+ const type = v.getUint32(off, true);
113
+ const size = v.getUint32(off + 4, true);
114
+ if (size < 8 || off + size > bytes.length) break;
115
+ const at = (o) => v.getInt32(off + o, true);
116
+ const u = (o) => v.getUint32(off + o, true);
117
+ switch (type) {
118
+ case 14:
119
+ off = bytes.length;
120
+ continue;
121
+ case 9:
122
+ win = {
123
+ ...win,
124
+ cx: at(8),
125
+ cy: at(12)
126
+ };
127
+ haveWin = true;
128
+ break;
129
+ case 10:
130
+ win = {
131
+ ...win,
132
+ x: at(8),
133
+ y: at(12)
134
+ };
135
+ haveWin = true;
136
+ break;
137
+ case 11:
138
+ view = {
139
+ ...view,
140
+ cx: at(8),
141
+ cy: at(12)
142
+ };
143
+ haveView = true;
144
+ break;
145
+ case 12:
146
+ view = {
147
+ ...view,
148
+ x: at(8),
149
+ y: at(12)
150
+ };
151
+ haveView = true;
152
+ break;
153
+ case 33:
154
+ stack.push(cloneDc(dc));
155
+ break;
156
+ case 34:
157
+ {
158
+ const back = Math.max(1, -at(8));
159
+ for (let i = 0; i < back && stack.length > 0; i++) dc = stack.pop();
160
+ }
161
+ break;
162
+ case 35:
163
+ dc.transform = xform(v, off + 8);
164
+ break;
165
+ case 36:
166
+ {
167
+ const m = xform(v, off + 8);
168
+ const mode = u(32);
169
+ dc.transform = mode === 1 ? [
170
+ 1,
171
+ 0,
172
+ 0,
173
+ 1,
174
+ 0,
175
+ 0
176
+ ] : mode === 2 ? multiply(m, dc.transform) : mode === 3 ? multiply(dc.transform, m) : m;
177
+ }
178
+ break;
179
+ case 37:
180
+ {
181
+ const ih = u(8);
182
+ const obj = stockObject(ih) ?? objects.get(ih);
183
+ if (obj?.kind === "pen") dc.pen = obj;
184
+ else if (obj?.kind === "brush") dc.brush = obj;
185
+ else if (obj?.kind === "font") dc.font = obj;
186
+ }
187
+ break;
188
+ case 38:
189
+ objects.set(u(8), {
190
+ kind: "pen",
191
+ colorHex: colorRef(u(24)),
192
+ widthLu: at(16),
193
+ style: penStyle(u(12))
194
+ });
195
+ break;
196
+ case 95:
197
+ objects.set(u(8), {
198
+ kind: "pen",
199
+ colorHex: colorRef(u(40)),
200
+ widthLu: at(32),
201
+ style: u(36) === 1 ? "none" : penStyle(u(28))
202
+ });
203
+ break;
204
+ case 39:
205
+ {
206
+ const style = u(12);
207
+ objects.set(u(8), {
208
+ kind: "brush",
209
+ colorHex: colorRef(u(16)),
210
+ hollow: style === 1
211
+ });
212
+ }
213
+ break;
214
+ case 82:
215
+ objects.set(u(8), readLogFont(v, bytes, off + 12));
216
+ break;
217
+ case 40:
218
+ objects.delete(u(8));
219
+ break;
220
+ case 18:
221
+ dc.bkOpaque = u(8) === 2;
222
+ break;
223
+ case 19:
224
+ dc.fillRule = u(8) === 2 ? "nonzero" : "evenodd";
225
+ break;
226
+ case 22:
227
+ {
228
+ const f = u(8);
229
+ dc.alignH = (f & 6) === 6 ? "center" : (f & 2) === 2 ? "right" : "left";
230
+ dc.alignBaseline = (f & 24) === 24;
231
+ }
232
+ break;
233
+ case 24:
234
+ dc.textColorHex = colorRef(u(8));
235
+ break;
236
+ case 25:
237
+ dc.bkColorHex = colorRef(u(8));
238
+ break;
239
+ case 27:
240
+ dc.x = at(8);
241
+ dc.y = at(12);
242
+ if (building) {
243
+ const p = px(dc.x, dc.y);
244
+ building.push({
245
+ op: "move",
246
+ x: p.x,
247
+ y: p.y
248
+ });
249
+ }
250
+ break;
251
+ case 54:
252
+ {
253
+ const from = px(dc.x, dc.y);
254
+ dc.x = at(8);
255
+ dc.y = at(12);
256
+ const to = px(dc.x, dc.y);
257
+ if (building) {
258
+ if (building.length === 0) building.push({
259
+ op: "move",
260
+ x: from.x,
261
+ y: from.y
262
+ });
263
+ building.push({
264
+ op: "line",
265
+ x: to.x,
266
+ y: to.y
267
+ });
268
+ } else paint([{
269
+ op: "move",
270
+ x: from.x,
271
+ y: from.y
272
+ }, {
273
+ op: "line",
274
+ x: to.x,
275
+ y: to.y
276
+ }], false, true);
277
+ }
278
+ break;
279
+ case 59:
280
+ building = [];
281
+ break;
282
+ case 61:
283
+ if (building && building.length > 0) building.push({ op: "close" });
284
+ break;
285
+ case 60: break;
286
+ case 62:
287
+ case 63:
288
+ case 64:
289
+ paint(open(), type !== 64, type !== 62);
290
+ building = void 0;
291
+ break;
292
+ case 68:
293
+ building = void 0;
294
+ break;
295
+ case 43:
296
+ paint(rectSegments(at(8), at(12), at(16), at(20)), true, true);
297
+ break;
298
+ case 42:
299
+ paint(ellipseSegments(px, at(8), at(12), at(16), at(20)), true, true);
300
+ break;
301
+ case 44:
302
+ paint(rectSegments(at(8), at(12), at(16), at(20)), true, true);
303
+ break;
304
+ case 3:
305
+ case 4:
306
+ case 2:
307
+ case 5:
308
+ case 6:
309
+ case 86:
310
+ case 87:
311
+ case 85:
312
+ case 88:
313
+ case 89:
314
+ {
315
+ const small = type >= 85;
316
+ const count = u(24);
317
+ const pts = readPoints(v, off + 28, count, small);
318
+ const closed = type === 3 || type === 86;
319
+ const segs = polySegments(px, pts, {
320
+ closed,
321
+ bezier: type === 2 || type === 5 || type === 85 || type === 88,
322
+ ...type === 5 || type === 6 || type === 88 || type === 89 ? { from: {
323
+ x: dc.x,
324
+ y: dc.y
325
+ } } : {}
326
+ });
327
+ if (pts.length > 0) {
328
+ dc.x = pts[pts.length - 1].x;
329
+ dc.y = pts[pts.length - 1].y;
330
+ }
331
+ if (building) building.push(...segs);
332
+ else paint(segs, closed, true);
333
+ }
334
+ break;
335
+ case 90:
336
+ case 91:
337
+ case 7:
338
+ case 8:
339
+ {
340
+ const small = type >= 90;
341
+ const polys = u(24);
342
+ const total = u(28);
343
+ const counts = [];
344
+ for (let i = 0; i < polys; i++) counts.push(v.getUint32(off + 32 + i * 4, true));
345
+ const pts = readPoints(v, off + 32 + polys * 4, total, small);
346
+ const closed = type === 91 || type === 8;
347
+ const segs = [];
348
+ let k = 0;
349
+ for (const c of counts) {
350
+ segs.push(...polySegments(px, pts.slice(k, k + c), {
351
+ closed,
352
+ bezier: false
353
+ }));
354
+ k += c;
355
+ }
356
+ if (building) building.push(...segs);
357
+ else paint(segs, closed, true);
358
+ }
359
+ break;
360
+ case 83:
361
+ case 84:
362
+ {
363
+ const refX = at(36);
364
+ const refY = at(40);
365
+ const chars = u(44);
366
+ const offString = u(48);
367
+ const wide = type === 84;
368
+ const text = readString(bytes, off + offString, chars, wide);
369
+ if (text.trim() !== "") {
370
+ const p = px(refX, refY);
371
+ const font = dc.font;
372
+ prims.push({
373
+ kind: "text",
374
+ text,
375
+ x: p.x,
376
+ y: p.y,
377
+ alignH: dc.alignH,
378
+ alignBaseline: dc.alignBaseline,
379
+ sizeLu: Math.abs(font?.heightLu ?? 12) * Math.abs(sy()),
380
+ colorHex: dc.textColorHex,
381
+ ...font?.family ? { fontFamily: font.family } : {},
382
+ ...font?.bold ? { bold: true } : {},
383
+ ...font?.italic ? { italic: true } : {},
384
+ ...font?.escapement ? { escapement: font.escapement } : {}
385
+ });
386
+ }
387
+ }
388
+ break;
389
+ case 76:
390
+ {
391
+ const cbBmiSrc = u(88);
392
+ const rop = u(40);
393
+ if (cbBmiSrc === 0) {
394
+ const x = at(24);
395
+ const y = at(28);
396
+ const w = at(32);
397
+ const h = at(36);
398
+ const hex = rop === 66 ? "000000" : rop === 16711778 ? "FFFFFF" : void 0;
399
+ const brush = dc.brush;
400
+ if (hex !== void 0) dc.brush = {
401
+ kind: "brush",
402
+ colorHex: hex,
403
+ hollow: false
404
+ };
405
+ paint(rectSegments(x, y, x + w, y + h), true, false);
406
+ dc.brush = brush;
407
+ } else skipped.add("bitmap");
408
+ }
409
+ break;
410
+ default:
411
+ {
412
+ const name = RECORD_NAMES.get(type);
413
+ if (name) skipped.add(name);
414
+ }
415
+ break;
416
+ }
417
+ off += size;
418
+ }
419
+ return {
420
+ left: bounds.left,
421
+ top: bounds.top,
422
+ width: Math.max(1, bounds.right - bounds.left),
423
+ height: Math.max(1, bounds.bottom - bounds.top),
424
+ prims,
425
+ skipped: [...skipped]
426
+ };
427
+ }
428
+ function xform(v, at) {
429
+ return [
430
+ v.getFloat32(at, true),
431
+ v.getFloat32(at + 4, true),
432
+ v.getFloat32(at + 8, true),
433
+ v.getFloat32(at + 12, true),
434
+ v.getFloat32(at + 16, true),
435
+ v.getFloat32(at + 20, true)
436
+ ];
437
+ }
438
+ function multiply(a, b) {
439
+ return [
440
+ a[0] * b[0] + a[1] * b[2],
441
+ a[0] * b[1] + a[1] * b[3],
442
+ a[2] * b[0] + a[3] * b[2],
443
+ a[2] * b[1] + a[3] * b[3],
444
+ a[4] * b[0] + a[5] * b[2] + b[4],
445
+ a[4] * b[1] + a[5] * b[3] + b[5]
446
+ ];
447
+ }
448
+ function penStyle(style) {
449
+ switch (style & 15) {
450
+ case 1: return "dash";
451
+ case 2: return "dot";
452
+ case 3: return "dashdot";
453
+ case 4: return "dashdotdot";
454
+ case 5: return "none";
455
+ default: return "solid";
456
+ }
457
+ }
458
+ function stockObject(ih) {
459
+ if ((ih & 2147483648) === 0) return void 0;
460
+ switch (ih & 2147483647) {
461
+ case 0: return {
462
+ kind: "brush",
463
+ colorHex: "FFFFFF",
464
+ hollow: false
465
+ };
466
+ case 1: return {
467
+ kind: "brush",
468
+ colorHex: "C0C0C0",
469
+ hollow: false
470
+ };
471
+ case 2: return {
472
+ kind: "brush",
473
+ colorHex: "808080",
474
+ hollow: false
475
+ };
476
+ case 3: return {
477
+ kind: "brush",
478
+ colorHex: "404040",
479
+ hollow: false
480
+ };
481
+ case 4: return {
482
+ kind: "brush",
483
+ colorHex: "000000",
484
+ hollow: false
485
+ };
486
+ case 5: return {
487
+ kind: "brush",
488
+ colorHex: "000000",
489
+ hollow: true
490
+ };
491
+ case 6: return {
492
+ kind: "pen",
493
+ colorHex: "FFFFFF",
494
+ widthLu: 1,
495
+ style: "solid"
496
+ };
497
+ case 7: return {
498
+ kind: "pen",
499
+ colorHex: "000000",
500
+ widthLu: 1,
501
+ style: "solid"
502
+ };
503
+ case 8: return {
504
+ kind: "pen",
505
+ colorHex: "000000",
506
+ widthLu: 1,
507
+ style: "none"
508
+ };
509
+ default: return;
510
+ }
511
+ }
512
+ function readLogFont(v, bytes, at) {
513
+ const height = v.getInt32(at, true);
514
+ const escapement = v.getInt32(at + 8, true);
515
+ const weight = v.getInt32(at + 16, true);
516
+ const italic = bytes[at + 20] !== 0;
517
+ const face = readString(bytes, at + 28, 32, true).replace(/\0.*$/u, "");
518
+ return {
519
+ kind: "font",
520
+ heightLu: height,
521
+ ...face ? { family: face } : {},
522
+ ...weight >= 600 ? { bold: true } : {},
523
+ ...italic ? { italic: true } : {},
524
+ ...escapement ? { escapement } : {}
525
+ };
526
+ }
527
+ function readString(bytes, at, count, wide) {
528
+ let out = "";
529
+ for (let i = 0; i < count; i++) {
530
+ const o = at + (wide ? i * 2 : i);
531
+ if (o + (wide ? 1 : 0) >= bytes.length) break;
532
+ const code = wide ? bytes[o] | bytes[o + 1] << 8 : bytes[o];
533
+ if (code === 0) break;
534
+ out += String.fromCharCode(code);
535
+ }
536
+ return out;
537
+ }
538
+ function readPoints(v, at, count, small) {
539
+ const out = [];
540
+ const step = small ? 4 : 8;
541
+ for (let i = 0; i < count; i++) {
542
+ const o = at + i * step;
543
+ if (o + step > v.byteLength) break;
544
+ out.push(small ? {
545
+ x: v.getInt16(o, true),
546
+ y: v.getInt16(o + 2, true)
547
+ } : {
548
+ x: v.getInt32(o, true),
549
+ y: v.getInt32(o + 4, true)
550
+ });
551
+ }
552
+ return out;
553
+ }
554
+ function polySegments(map, pts, o) {
555
+ const segs = [];
556
+ if (pts.length === 0) return segs;
557
+ let i = 0;
558
+ if (o.from) {
559
+ const s = map(o.from.x, o.from.y);
560
+ segs.push({
561
+ op: "move",
562
+ x: s.x,
563
+ y: s.y
564
+ });
565
+ } else {
566
+ const s = map(pts[0].x, pts[0].y);
567
+ segs.push({
568
+ op: "move",
569
+ x: s.x,
570
+ y: s.y
571
+ });
572
+ i = 1;
573
+ }
574
+ if (o.bezier) for (; i + 2 < pts.length + 1 && i + 2 <= pts.length; i += 3) {
575
+ const c1 = map(pts[i].x, pts[i].y);
576
+ const c2 = map(pts[i + 1].x, pts[i + 1].y);
577
+ const to = map(pts[i + 2].x, pts[i + 2].y);
578
+ segs.push({
579
+ op: "cubic",
580
+ x1: c1.x,
581
+ y1: c1.y,
582
+ x2: c2.x,
583
+ y2: c2.y,
584
+ x: to.x,
585
+ y: to.y
586
+ });
587
+ }
588
+ else for (; i < pts.length; i++) {
589
+ const p = map(pts[i].x, pts[i].y);
590
+ segs.push({
591
+ op: "line",
592
+ x: p.x,
593
+ y: p.y
594
+ });
595
+ }
596
+ if (o.closed) segs.push({ op: "close" });
597
+ return segs;
598
+ }
599
+ var KAPPA = .5522847498307936;
600
+ function ellipseSegments(map, l, t, r, b) {
601
+ const cx = (l + r) / 2;
602
+ const cy = (t + b) / 2;
603
+ const rx = (r - l) / 2;
604
+ const ry = (b - t) / 2;
605
+ const k = KAPPA;
606
+ const p = (x, y) => map(x, y);
607
+ const s = p(cx + rx, cy);
608
+ const segs = [{
609
+ op: "move",
610
+ x: s.x,
611
+ y: s.y
612
+ }];
613
+ const arc = (c1x, c1y, c2x, c2y, ex, ey) => {
614
+ const a = p(c1x, c1y);
615
+ const bb = p(c2x, c2y);
616
+ const e = p(ex, ey);
617
+ segs.push({
618
+ op: "cubic",
619
+ x1: a.x,
620
+ y1: a.y,
621
+ x2: bb.x,
622
+ y2: bb.y,
623
+ x: e.x,
624
+ y: e.y
625
+ });
626
+ };
627
+ arc(cx + rx, cy + ry * k, cx + rx * k, cy + ry, cx, cy + ry);
628
+ arc(cx - rx * k, cy + ry, cx - rx, cy + ry * k, cx - rx, cy);
629
+ arc(cx - rx, cy - ry * k, cx - rx * k, cy - ry, cx, cy - ry);
630
+ arc(cx + rx * k, cy - ry, cx + rx, cy - ry * k, cx + rx, cy);
631
+ segs.push({ op: "close" });
632
+ return segs;
633
+ }
634
+ //#endregion
635
+ export { ellipseSegments, isEmf, readEmf };