@pixerate/editor 0.118.0 → 0.120.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 (74) hide show
  1. package/THIRD_PARTY_NOTICES.md +1 -0
  2. package/dist/animation-editor/index.cjs +54 -54
  3. package/dist/animation-editor/index.d.cts +3 -3
  4. package/dist/animation-editor/index.d.ts +3 -3
  5. package/dist/animation-editor/index.js +2 -2
  6. package/dist/{chunk-R2JE6SA7.js → chunk-BOWUU4LJ.js} +42 -7
  7. package/dist/chunk-BOWUU4LJ.js.map +1 -0
  8. package/dist/{chunk-M7O4BJRH.cjs → chunk-DFLJHLKA.cjs} +36 -36
  9. package/dist/{chunk-M7O4BJRH.cjs.map → chunk-DFLJHLKA.cjs.map} +1 -1
  10. package/dist/{chunk-2J3LS7JZ.cjs → chunk-HTAFDTNR.cjs} +221 -186
  11. package/dist/chunk-HTAFDTNR.cjs.map +1 -0
  12. package/dist/{chunk-L2T6EJ5S.cjs → chunk-L3PXFMOF.cjs} +38 -25
  13. package/dist/chunk-L3PXFMOF.cjs.map +1 -0
  14. package/dist/{chunk-IVSNUXW7.js → chunk-T7IZDNSL.js} +37 -24
  15. package/dist/chunk-T7IZDNSL.js.map +1 -0
  16. package/dist/{chunk-BYAWOAST.cjs → chunk-TS5IEUW6.cjs} +26 -25
  17. package/dist/chunk-TS5IEUW6.cjs.map +1 -0
  18. package/dist/{chunk-VD2UDVF7.js → chunk-UMVW2Q66.js} +21 -5
  19. package/dist/chunk-UMVW2Q66.js.map +1 -0
  20. package/dist/{chunk-FODKPD44.cjs → chunk-VYW7JBTM.cjs} +790 -549
  21. package/dist/chunk-VYW7JBTM.cjs.map +1 -0
  22. package/dist/{chunk-T2P5TIZ6.js → chunk-WAI6ATHC.js} +2 -2
  23. package/dist/{chunk-EBSYZRSW.cjs → chunk-WMRIG4XQ.cjs} +21 -5
  24. package/dist/chunk-WMRIG4XQ.cjs.map +1 -0
  25. package/dist/{chunk-7LNZAWSJ.js → chunk-WORWH5K5.js} +699 -458
  26. package/dist/chunk-WORWH5K5.js.map +1 -0
  27. package/dist/{chunk-JHXMNOMF.js → chunk-YHW26LS2.js} +14 -13
  28. package/dist/chunk-YHW26LS2.js.map +1 -0
  29. package/dist/{export-Dul1SbPv.d.ts → export-D2D8hb_u.d.ts} +18 -4
  30. package/dist/{export-DMOuzgZZ.d.cts → export-fP2hZYjm.d.cts} +18 -4
  31. package/dist/{flow-4-OC-UkQ.d.cts → flow-A2Dj-69w.d.cts} +21 -9
  32. package/dist/{flow-Cb7lkPm8.d.ts → flow-C95atNoQ.d.ts} +21 -9
  33. package/dist/image-editor/index.cjs +1104 -979
  34. package/dist/image-editor/index.cjs.map +1 -1
  35. package/dist/image-editor/index.d.cts +5 -5
  36. package/dist/image-editor/index.d.ts +5 -5
  37. package/dist/image-editor/index.js +157 -32
  38. package/dist/image-editor/index.js.map +1 -1
  39. package/dist/paint/index.cjs +5 -3
  40. package/dist/paint/index.cjs.map +1 -1
  41. package/dist/paint/index.d.cts +2 -2
  42. package/dist/paint/index.d.ts +2 -2
  43. package/dist/paint/index.js +4 -2
  44. package/dist/paint-editor/index.cjs +147 -147
  45. package/dist/paint-editor/index.d.cts +4 -4
  46. package/dist/paint-editor/index.d.ts +4 -4
  47. package/dist/paint-editor/index.js +4 -4
  48. package/dist/raster/index.cjs +2 -2
  49. package/dist/raster/index.js +1 -1
  50. package/dist/{svg-CVdFc80-.d.cts → svg-S9zzvqaZ.d.cts} +5 -1
  51. package/dist/{svg-DlEuhwoX.d.ts → svg-leZpRsJB.d.ts} +5 -1
  52. package/dist/{types-CDLGhAZp.d.ts → types-BgwxFWvn.d.ts} +59 -3
  53. package/dist/{types-Tfly4Aya.d.cts → types-DdRTDnza.d.cts} +59 -3
  54. package/dist/vector/index.cjs +1314 -1009
  55. package/dist/vector/index.cjs.map +1 -1
  56. package/dist/vector/index.d.cts +110 -5
  57. package/dist/vector/index.d.ts +110 -5
  58. package/dist/vector/index.js +319 -14
  59. package/dist/vector/index.js.map +1 -1
  60. package/package.json +1 -1
  61. package/skills/pixerate-image-editor/references/photoshop-files.md +5 -2
  62. package/skills/pixerate-vector/SKILL.md +13 -1
  63. package/skills/pixerate-vector/references/commands.md +2 -0
  64. package/dist/chunk-2J3LS7JZ.cjs.map +0 -1
  65. package/dist/chunk-7LNZAWSJ.js.map +0 -1
  66. package/dist/chunk-BYAWOAST.cjs.map +0 -1
  67. package/dist/chunk-EBSYZRSW.cjs.map +0 -1
  68. package/dist/chunk-FODKPD44.cjs.map +0 -1
  69. package/dist/chunk-IVSNUXW7.js.map +0 -1
  70. package/dist/chunk-JHXMNOMF.js.map +0 -1
  71. package/dist/chunk-L2T6EJ5S.cjs.map +0 -1
  72. package/dist/chunk-R2JE6SA7.js.map +0 -1
  73. package/dist/chunk-VD2UDVF7.js.map +0 -1
  74. /package/dist/{chunk-T2P5TIZ6.js.map → chunk-WAI6ATHC.js.map} +0 -0
@@ -75,6 +75,7 @@ var VECTOR_CONNECTOR_SIDES = ["auto", "top", "right", "bottom", "left", "center"
75
75
  var VECTOR_CONNECTOR_ROUTES = ["straight", "elbow", "curved"];
76
76
  var VECTOR_BLEND_SPACINGS = ["steps", "distance", "smoothColor"];
77
77
  var VECTOR_MASK_TYPES = ["clip", "alpha", "luminance"];
78
+ var VECTOR_SYMMETRY_MODES = ["vertical", "horizontal", "dual", "diagonal", "radial"];
78
79
  var VECTOR_TEXT_ALIGNS = ["left", "center", "right", "justify"];
79
80
  var VECTOR_PATH_TEXT_BASELINES = ["baseline", "ascender", "descender", "center"];
80
81
  var VECTOR_CONSTRAINT_KINDS = [
@@ -121,7 +122,7 @@ var VECTOR_TOOLS = [
121
122
  ];
122
123
  var VECTOR_TRANSFORM_HANDLES = ["nw", "n", "ne", "e", "se", "s", "sw", "w", "rotate"];
123
124
  var VECTOR_PATHFINDER_OPERATIONS = ["divide", "trim", "merge", "crop", "outline", "minusBack"];
124
- var VECTOR_EFFECT_TYPES = ["trim", "roundCorners", "puckerBloat", "twist", "zigzag", "wiggle", "offset", "merge", "repeater", "envelope"];
125
+ var VECTOR_EFFECT_TYPES = ["trim", "roundCorners", "puckerBloat", "twist", "zigzag", "wiggle", "offset", "merge", "repeater", "envelope", "contour", "blockShadow"];
125
126
  var VECTOR_MERGE_MODES = ["merge", "add", "subtract", "intersect", "exclude"];
126
127
  var VECTOR_FILTER_TYPES = ["dropShadow", "innerShadow", "outerGlow", "innerGlow", "layerBlur", "feather"];
127
128
 
@@ -465,8 +466,8 @@ function vectorGradientParam(type, q, focal) {
465
466
  case "diamond":
466
467
  return Math.abs(q.x) + Math.abs(q.y);
467
468
  case "conic": {
468
- const turn = Math.atan2(q.y, q.x) / (2 * Math.PI);
469
- return turn - Math.floor(turn);
469
+ const turn2 = Math.atan2(q.y, q.x) / (2 * Math.PI);
470
+ return turn2 - Math.floor(turn2);
470
471
  }
471
472
  case "radial":
472
473
  return focal ? vectorGradientFocalParam(q, focal.f, focal.fr) : Math.hypot(q.x, q.y);
@@ -1451,12 +1452,12 @@ function squareTo(a, b) {
1451
1452
  return l > EPS ? mul2(w, 1 / l) : { x: 0, y: 0 };
1452
1453
  }
1453
1454
  function smoothCut(c, radius, smoothing) {
1454
- const turn = Math.PI - Math.acos(Math.max(-1, Math.min(1, c.cos)));
1455
+ const turn2 = Math.PI - Math.acos(Math.max(-1, Math.min(1, c.cos)));
1455
1456
  const t = cornerSetback(c, radius);
1456
1457
  const room = Math.min(c.lu, c.lv) / 2;
1457
1458
  let s = Math.max(0, Math.min(1, smoothing));
1458
1459
  if ((1 + s) * t > room) s = Math.max(0, Math.min(s, room / t - 1));
1459
- const beta = turn * s / 2;
1460
+ const beta = turn2 * s / 2;
1460
1461
  if (!(beta > 1e-6) || !(t > EPS)) return null;
1461
1462
  const p = Math.min((1 + s) * t, room);
1462
1463
  const qa = radius * Math.tan(beta / 2);
@@ -1471,7 +1472,7 @@ function smoothCut(c, radius, smoothing) {
1471
1472
  };
1472
1473
  const U = side(c.u, c.v);
1473
1474
  const V2 = side(c.v, c.u);
1474
- const sweep = turn * (1 - s);
1475
+ const sweep = turn2 * (1 - s);
1475
1476
  const h = radius * (4 / 3) * Math.tan(sweep / 4);
1476
1477
  const tanU = sub2(U.a, U.q);
1477
1478
  const tanV = sub2(V2.a, V2.q);
@@ -1510,9 +1511,9 @@ function cutCorner(c, radius, kind, smoothing = 0) {
1510
1511
  }
1511
1512
  const d1 = mul2(a.dir, -1);
1512
1513
  const d2 = mul2(b.dir, -1);
1513
- const turn = Math.acos(Math.max(-1, Math.min(1, -dot2(d1, d2))));
1514
+ const turn2 = Math.acos(Math.max(-1, Math.min(1, -dot2(d1, d2))));
1514
1515
  const chord = len(sub2(b.p, a.p));
1515
- const k = turn < 1e-9 ? chord / 3 : 4 / 3 * Math.tan(turn / 4) * chord / (2 * Math.sin(turn / 2));
1516
+ const k = turn2 < 1e-9 ? chord / 3 : 4 / 3 * Math.tan(turn2 / 4) * chord / (2 * Math.sin(turn2 / 2));
1516
1517
  if (!Number.isFinite(k)) return null;
1517
1518
  return { tu: a.t, tv: b.t, start: a.p, out: add2(a.p, mul2(d1, k)), in: add2(b.p, mul2(d2, k)), end: b.p };
1518
1519
  }
@@ -2649,6 +2650,398 @@ function withVectorTargetPaint(node, target, layer, paint) {
2649
2650
  return target === "fill" ? withVectorFills(node, next) : withVectorStrokes(node, next);
2650
2651
  }
2651
2652
 
2653
+ // src/vector/pathEffects.ts
2654
+ var EPS2 = 1e-9;
2655
+ var degenerate = (s) => s.every((p) => Math.abs(p[0] - s[0][0]) < EPS2 && Math.abs(p[1] - s[0][1]) < EPS2);
2656
+ function raise(seg) {
2657
+ if (seg.length !== 3) return seg.map((p) => [p[0], p[1]]);
2658
+ const [p0, p1, p2] = seg;
2659
+ return [p0, [p0[0] + 2 / 3 * (p1[0] - p0[0]), p0[1] + 2 / 3 * (p1[1] - p0[1])], [p2[0] + 2 / 3 * (p1[0] - p2[0]), p2[1] + 2 / 3 * (p1[1] - p2[1])], p2];
2660
+ }
2661
+ function subsOf(path) {
2662
+ return _chunkXGD3FSNCcjs.pathToContours.call(void 0, path).map((c) => ({ segs: _chunkXGD3FSNCcjs.closeContour.call(void 0, c).filter((s) => !degenerate(s)).map(raise), closed: c.closed })).filter((s) => s.segs.length > 0);
2663
+ }
2664
+ var subsToPath = (subs) => _chunkXGD3FSNCcjs.contoursToPath.call(void 0, subs.map((s) => ({ segments: s.segs, closed: s.closed })));
2665
+ var unit2 = (x, y) => {
2666
+ const l = Math.hypot(x, y);
2667
+ return l > 1e-12 && Number.isFinite(l) ? [x / l, y / l] : null;
2668
+ };
2669
+ function startTangent(s) {
2670
+ for (let i = 1; i < s.length; i++) {
2671
+ const u = unit2(s[i][0] - s[0][0], s[i][1] - s[0][1]);
2672
+ if (u) return u;
2673
+ }
2674
+ return [1, 0];
2675
+ }
2676
+ function endTangent(s) {
2677
+ const end = s[s.length - 1];
2678
+ for (let i = s.length - 2; i >= 0; i--) {
2679
+ const u = unit2(end[0] - s[i][0], end[1] - s[i][1]);
2680
+ if (u) return u;
2681
+ }
2682
+ return [1, 0];
2683
+ }
2684
+ function tangentAt(s, t) {
2685
+ if (t <= 1e-9) return startTangent(s);
2686
+ if (t >= 1 - 1e-9) return endTangent(s);
2687
+ const d = _chunkXGD3FSNCcjs.segmentDerivative.call(void 0, s, t);
2688
+ return _nullishCoalesce(unit2(d[0], d[1]), () => ( startTangent(s)));
2689
+ }
2690
+ var perp2 = (v2) => [-v2[1], v2[0]];
2691
+ function effectPathLength(path) {
2692
+ let total = 0;
2693
+ for (const s of subsOf(path)) for (const seg of s.segs) total += _chunkXGD3FSNCcjs.segmentLength.call(void 0, seg);
2694
+ return total;
2695
+ }
2696
+ function effectPathVertexCount(path) {
2697
+ return subsOf(path).reduce((n, s) => n + s.segs.length + (s.closed ? 0 : 1), 0);
2698
+ }
2699
+ var Measured = class {
2700
+
2701
+
2702
+
2703
+ constructor(path) {
2704
+ this.segs = subsOf(path).flatMap((s) => s.segs);
2705
+ this.lens = this.segs.map((s) => _chunkXGD3FSNCcjs.segmentLength.call(void 0, s));
2706
+ this.total = this.lens.reduce((a, b) => a + b, 0);
2707
+ }
2708
+ /**
2709
+ * Appends the part between lengths `sa` and `sb`, continuing the last piece when this one
2710
+ * starts where it ends (across the start of a closed path).
2711
+ */
2712
+ append(sa, sb, out) {
2713
+ for (const piece of _chunkXGD3FSNCcjs.trimSegments.call(void 0, this.segs, sa, sb, this.lens)) {
2714
+ if (degenerate(piece)) continue;
2715
+ const last = _optionalChain([out, 'access', _55 => _55[out.length - 1], 'optionalAccess', _56 => _56.segs]);
2716
+ const end = _optionalChain([last, 'optionalAccess', _57 => _57[last.length - 1], 'optionalAccess', _58 => _58.at, 'call', _59 => _59(-1)]);
2717
+ if (!end || Math.hypot(end[0] - piece[0][0], end[1] - piece[0][1]) > 1e-6) out.push({ segs: [piece], closed: false });
2718
+ else last.push(piece);
2719
+ }
2720
+ }
2721
+ };
2722
+ function trimIntervals(start, end, offsetDegrees) {
2723
+ let s = start / 100;
2724
+ let e = end / 100;
2725
+ if (!Number.isFinite(s) || !Number.isFinite(e)) return null;
2726
+ if (s > e) [s, e] = [e, s];
2727
+ s = Math.min(1, Math.max(0, s));
2728
+ e = Math.min(1, Math.max(0, e));
2729
+ if (e - s >= 1 - 1e-9) return null;
2730
+ if (e - s <= 1e-9) return [];
2731
+ const off = Number.isFinite(offsetDegrees) ? (offsetDegrees / 360 % 1 + 1) % 1 : 0;
2732
+ s += off;
2733
+ e += off;
2734
+ if (e <= 1) return [[s, e]];
2735
+ if (s >= 1) return [[s - 1, e - 1]];
2736
+ return [
2737
+ [s, 1],
2738
+ [0, e - 1]
2739
+ ];
2740
+ }
2741
+ function trimPaths(paths, start, end, offsetDegrees = 0) {
2742
+ const iv = trimIntervals(start, end, offsetDegrees);
2743
+ if (!iv) return paths.slice();
2744
+ return paths.map((p) => {
2745
+ const m = new Measured(p);
2746
+ const out = [];
2747
+ if (m.total > 0) for (const [a, b] of iv) m.append(a * m.total, b * m.total, out);
2748
+ return subsToPath(out);
2749
+ });
2750
+ }
2751
+ function trimPathsIndividually(paths, start, end, offsetDegrees = 0) {
2752
+ const iv = trimIntervals(start, end, offsetDegrees);
2753
+ if (!iv) return paths.slice();
2754
+ const ms = paths.map((p) => new Measured(p));
2755
+ const total = ms.reduce((n, m) => n + m.total, 0);
2756
+ let base = 0;
2757
+ return ms.map((m) => {
2758
+ const out = [];
2759
+ for (const [a, b] of iv) {
2760
+ const la = Math.max(0, a * total - base);
2761
+ const lb = Math.min(m.total, b * total - base);
2762
+ if (lb > la) m.append(la, lb, out);
2763
+ }
2764
+ base += m.total;
2765
+ return subsToPath(out);
2766
+ });
2767
+ }
2768
+ function puckerBloatPaths(paths, amount) {
2769
+ const a = amount / 100;
2770
+ if (!a || !Number.isFinite(a)) return paths.slice();
2771
+ return paths.map((p) => {
2772
+ const verts = p.filter((c) => c.type !== "Z");
2773
+ if (!verts.length) return p;
2774
+ const cx = verts.reduce((s, c) => s + c.x, 0) / verts.length;
2775
+ const cy = verts.reduce((s, c) => s + c.y, 0) / verts.length;
2776
+ const mv = (x, y) => ({ x: x + (cx - x) * a, y: y + (cy - y) * a });
2777
+ const mvh = (x, y) => ({ x: x + (x - cx) * a, y: y + (y - cy) * a });
2778
+ const out = [];
2779
+ let prev = { x: 0, y: 0 };
2780
+ let start = { x: 0, y: 0 };
2781
+ const curve = (c1, c2, q) => {
2782
+ const h1 = mvh(c1.x, c1.y);
2783
+ const h2 = mvh(c2.x, c2.y);
2784
+ const e = mv(q.x, q.y);
2785
+ out.push({ type: "C", x1: h1.x, y1: h1.y, x2: h2.x, y2: h2.y, x: e.x, y: e.y });
2786
+ };
2787
+ for (const c of p) {
2788
+ switch (c.type) {
2789
+ case "M": {
2790
+ const e = mv(c.x, c.y);
2791
+ out.push({ type: "M", x: e.x, y: e.y });
2792
+ prev = start = { x: c.x, y: c.y };
2793
+ break;
2794
+ }
2795
+ case "L":
2796
+ curve(prev, c, c);
2797
+ prev = { x: c.x, y: c.y };
2798
+ break;
2799
+ case "Q": {
2800
+ const c1 = { x: prev.x + 2 / 3 * (c.x1 - prev.x), y: prev.y + 2 / 3 * (c.y1 - prev.y) };
2801
+ const c2 = { x: c.x + 2 / 3 * (c.x1 - c.x), y: c.y + 2 / 3 * (c.y1 - c.y) };
2802
+ curve(c1, c2, c);
2803
+ prev = { x: c.x, y: c.y };
2804
+ break;
2805
+ }
2806
+ case "C":
2807
+ curve({ x: c.x1, y: c.y1 }, { x: c.x2, y: c.y2 }, c);
2808
+ prev = { x: c.x, y: c.y };
2809
+ break;
2810
+ case "Z":
2811
+ if (Math.hypot(prev.x - start.x, prev.y - start.y) > EPS2) curve(prev, start, start);
2812
+ out.push({ type: "Z" });
2813
+ prev = start;
2814
+ break;
2815
+ }
2816
+ }
2817
+ return out;
2818
+ });
2819
+ }
2820
+ function roundCornerPaths(paths, radius) {
2821
+ if (!(radius > 0) || !Number.isFinite(radius)) return paths.slice();
2822
+ return paths.map((p) => subpathsToBezier(bezierToSubpaths(p).map((sp) => setSubpathCorners(sp, radius))));
2823
+ }
2824
+ function offsetPaths(paths, amount, join = "miter", miterLimit = 4, copies = 1, copyOffset = 0) {
2825
+ const n = Math.min(1e3, Math.max(1, Math.round(Number.isFinite(copies) ? copies : 1)));
2826
+ return paths.map((p) => {
2827
+ const out = [];
2828
+ for (let i = 0; i < n; i++) out.push(..._chunkXGD3FSNCcjs.offsetPath.call(void 0, p, amount * (i + 1 + copyOffset), { join, miterLimit }));
2829
+ return out;
2830
+ });
2831
+ }
2832
+ function sweepPath(path, dx, dy, fillRule = "nonzero", tolerance = 0.25) {
2833
+ if (!path.length) return [];
2834
+ if (!Number.isFinite(dx) || !Number.isFinite(dy) || Math.hypot(dx, dy) < 1e-9) return path.slice();
2835
+ const bands = [];
2836
+ for (const contour of _chunkXGD3FSNCcjs.pathToContours.call(void 0, path)) {
2837
+ const ring = _chunkXGD3FSNCcjs.flattenChain.call(void 0, _chunkXGD3FSNCcjs.closeContour.call(void 0, contour, true), Math.max(1e-3, tolerance));
2838
+ for (let i = 0; i < ring.length; i++) {
2839
+ let p = ring[i];
2840
+ let q = ring[(i + 1) % ring.length];
2841
+ const turn2 = (q[0] - p[0]) * dy - (q[1] - p[1]) * dx;
2842
+ if (Math.abs(turn2) < 1e-9) continue;
2843
+ if (turn2 < 0) [p, q] = [q, p];
2844
+ bands.push({ type: "M", x: p[0], y: p[1] }, { type: "L", x: q[0], y: q[1] }, { type: "L", x: q[0] + dx, y: q[1] + dy }, { type: "L", x: p[0] + dx, y: p[1] + dy }, { type: "Z" });
2845
+ }
2846
+ }
2847
+ const moved = _chunkXGD3FSNCcjs.transformBezierPath.call(void 0, path, [1, 0, 0, 1, dx, dy]);
2848
+ return _chunkXGD3FSNCcjs.pathBoolean.call(void 0, "union", [{ path, fillRule }, { path: moved, fillRule }, ...bands.length ? [{ path: bands, fillRule: "nonzero" }] : []]).path;
2849
+ }
2850
+ function twistPaths(paths, angle, center) {
2851
+ let rmax = 0;
2852
+ for (const p of paths) for (const c of p) if (c.type !== "Z") rmax = Math.max(rmax, Math.hypot(c.x - center.x, c.y - center.y));
2853
+ const a = angle * Math.PI / 180;
2854
+ if (!a || rmax <= 1e-9 || !Number.isFinite(a)) return paths.slice();
2855
+ const k = a / rmax;
2856
+ const rot = (v2, th) => {
2857
+ const s = Math.sin(th);
2858
+ const co = Math.cos(th);
2859
+ return [v2[0] * co - v2[1] * s, v2[0] * s + v2[1] * co];
2860
+ };
2861
+ const map = (p) => {
2862
+ const v2 = [p[0] - center.x, p[1] - center.y];
2863
+ const r = rot(v2, k * Math.hypot(v2[0], v2[1]));
2864
+ return [center.x + r[0], center.y + r[1]];
2865
+ };
2866
+ const jac = (p, dv) => {
2867
+ const v2 = [p[0] - center.x, p[1] - center.y];
2868
+ const r = Math.hypot(v2[0], v2[1]);
2869
+ let w = dv;
2870
+ if (r > 1e-12) {
2871
+ const f = k * (v2[0] * dv[0] + v2[1] * dv[1]) / r;
2872
+ w = [dv[0] - v2[1] * f, dv[1] + v2[0] * f];
2873
+ }
2874
+ return rot(w, k * r);
2875
+ };
2876
+ return paths.map((p) => {
2877
+ const out = [];
2878
+ for (const sub5 of subsOf(p)) {
2879
+ const segs = [];
2880
+ for (const seg of sub5.segs) {
2881
+ const cubic = seg.length === 2 ? [seg[0], seg[0], seg[1], seg[1]] : seg;
2882
+ const len2 = _chunkXGD3FSNCcjs.segmentLength.call(void 0, seg);
2883
+ const m = Math.min(64, Math.max(1, Math.ceil(Math.abs(a) * len2 / rmax / 0.15 + len2 / 50)));
2884
+ for (let i = 0; i < m; i++) {
2885
+ const q = _chunkXGD3FSNCcjs.subSegment.call(void 0, cubic, i / m, (i + 1) / m);
2886
+ const p0 = map(q[0]);
2887
+ const p3 = map(q[3]);
2888
+ const h1 = jac(q[0], [q[1][0] - q[0][0], q[1][1] - q[0][1]]);
2889
+ const h2 = jac(q[3], [q[2][0] - q[3][0], q[2][1] - q[3][1]]);
2890
+ segs.push([p0, [p0[0] + h1[0], p0[1] + h1[1]], [p3[0] + h2[0], p3[1] + h2[1]], p3]);
2891
+ }
2892
+ }
2893
+ out.push({ segs, closed: sub5.closed });
2894
+ }
2895
+ return subsToPath(out);
2896
+ });
2897
+ }
2898
+ function resample(sub5, m) {
2899
+ const segs = sub5.segs;
2900
+ const n = segs.length;
2901
+ const lens = segs.map((s) => _chunkXGD3FSNCcjs.segmentLength.call(void 0, s));
2902
+ const out = [];
2903
+ for (let j = 0; j < n; j++) {
2904
+ const piece = lens[j] / m;
2905
+ for (let k = 0; k < m; k++) {
2906
+ if (k === 0) {
2907
+ const tout = startTangent(segs[j]);
2908
+ const prev = sub5.closed || j > 0 ? (j + n - 1) % n : null;
2909
+ let tan = tout;
2910
+ if (prev !== null) {
2911
+ const tin = endTangent(segs[prev]);
2912
+ tan = _nullishCoalesce(unit2(tin[0] + tout[0], tin[1] + tout[1]), () => ( tout));
2913
+ }
2914
+ out.push({ p: segs[j][0], tan, lenPrev: prev === null ? 0 : lens[prev] / m, lenNext: piece });
2915
+ } else {
2916
+ const t = _chunkXGD3FSNCcjs.segmentParamAtLength.call(void 0, segs[j], piece * k, lens[j]);
2917
+ out.push({ p: _chunkXGD3FSNCcjs.segmentPoint.call(void 0, segs[j], t), tan: tangentAt(segs[j], t), lenPrev: piece, lenNext: piece });
2918
+ }
2919
+ }
2920
+ }
2921
+ if (!sub5.closed) {
2922
+ const last = segs[n - 1];
2923
+ out.push({ p: last[last.length - 1], tan: endTangent(last), lenPrev: lens[n - 1] / m, lenNext: 0 });
2924
+ }
2925
+ return out;
2926
+ }
2927
+ function emit(samples, disp, closed, smooth, handle) {
2928
+ const n = samples.length;
2929
+ if (!n) return null;
2930
+ const pt2 = (i) => [samples[i].p[0] + disp[i][0], samples[i].p[1] + disp[i][1]];
2931
+ const segs = [];
2932
+ const count = closed ? n : n - 1;
2933
+ for (let i = 0; i < count; i++) {
2934
+ const j = (i + 1) % n;
2935
+ const a = samples[i];
2936
+ const b = samples[j];
2937
+ const p = pt2(i);
2938
+ const q = pt2(j);
2939
+ if (smooth) segs.push([p, [p[0] + a.tan[0] * a.lenNext * handle, p[1] + a.tan[1] * a.lenNext * handle], [q[0] - b.tan[0] * b.lenPrev * handle, q[1] - b.tan[1] * b.lenPrev * handle], q]);
2940
+ else segs.push([p, q]);
2941
+ }
2942
+ if (!segs.length) return null;
2943
+ return { segs, closed };
2944
+ }
2945
+ function zigzagPaths(paths, size, ridges, smooth = false) {
2946
+ const m = Math.min(1e3, Math.max(0, Math.round(Number.isFinite(ridges) ? ridges : 0))) + 1;
2947
+ return paths.map((p) => {
2948
+ const out = [];
2949
+ for (const sub5 of subsOf(p)) {
2950
+ const s = resample(sub5, m);
2951
+ const disp = s.map((x, i) => {
2952
+ const n = perp2(x.tan);
2953
+ const d = i % 2 === 0 ? size : -size;
2954
+ return [n[0] * d, n[1] * d];
2955
+ });
2956
+ const e = emit(s, disp, sub5.closed, smooth, 0.36);
2957
+ if (e) out.push(e);
2958
+ }
2959
+ return subsToPath(out);
2960
+ });
2961
+ }
2962
+ var MASK64 = (1n << 64n) - 1n;
2963
+ function splitmix(x) {
2964
+ x = x + 0x9e3779b97f4a7c15n & MASK64;
2965
+ let z = x;
2966
+ z = (z ^ z >> 30n) * 0xbf58476d1ce4e5b9n & MASK64;
2967
+ z = (z ^ z >> 27n) * 0x94d049bb133111ebn & MASK64;
2968
+ return z ^ z >> 31n;
2969
+ }
2970
+ function hash(seed, idx, t) {
2971
+ const h = splitmix(splitmix(splitmix(seed) ^ idx) ^ BigInt.asUintN(64, BigInt(t)));
2972
+ return Number(h >> 11n) / 2 ** 53 * 2 - 1;
2973
+ }
2974
+ function noise(seed, idx, t) {
2975
+ const i = Math.floor(t);
2976
+ const f = t - i;
2977
+ const p0 = hash(seed, idx, i - 1);
2978
+ const p1 = hash(seed, idx, i);
2979
+ const p2 = hash(seed, idx, i + 1);
2980
+ const p3 = hash(seed, idx, i + 2);
2981
+ const v2 = 0.5 * (2 * p1 + (-p0 + p2) * f + (2 * p0 - 5 * p1 + 4 * p2 - p3) * f * f + (-p0 + 3 * p1 - 3 * p2 + p3) * f * f * f);
2982
+ return Math.min(1, Math.max(-1, v2));
2983
+ }
2984
+ function wigglePaths(paths, w) {
2985
+ if (!w.size || !Number.isFinite(w.size)) return paths.slice();
2986
+ const m = Math.min(1e3, Math.max(0, Math.round(Number.isFinite(w.detail) ? w.detail : 0))) + 1;
2987
+ const seed = BigInt.asUintN(64, BigInt(Math.round(Number.isFinite(w.seed) ? w.seed : 0)));
2988
+ const t = (Number.isFinite(w.time) ? w.time : 0) * (Number.isFinite(w.speed) ? w.speed : 0) + (Number.isFinite(w.phase) ? w.phase : 0) / 360;
2989
+ const corr = Math.min(1, Math.max(0, (Number.isFinite(w.correlation) ? w.correlation : 0) / 100));
2990
+ const sx = noise(seed, MASK64, t);
2991
+ const sy = noise(seed, MASK64 - 1n, t);
2992
+ let idx = 0;
2993
+ return paths.map((p) => {
2994
+ const out = [];
2995
+ for (const sub5 of subsOf(p)) {
2996
+ const s = resample(sub5, m);
2997
+ const disp = s.map(() => {
2998
+ const i = BigInt(idx);
2999
+ const ox = noise(seed, i * 2n, t + idx * 0.37);
3000
+ const oy = noise(seed, i * 2n + 1n, t + idx * 0.61);
3001
+ idx++;
3002
+ return [(sx * corr + ox * (1 - corr)) * w.size, (sy * corr + oy * (1 - corr)) * w.size];
3003
+ });
3004
+ const e = emit(s, disp, sub5.closed, w.smooth, 1 / 3);
3005
+ if (e) out.push(e);
3006
+ }
3007
+ return subsToPath(out);
3008
+ });
3009
+ }
3010
+ var MERGE_OPS = { add: "union", subtract: "difference", intersect: "intersection", exclude: "xor" };
3011
+ function mergePaths(paths, mode = "merge") {
3012
+ if (mode === "merge" || !(mode in MERGE_OPS)) return paths.flat();
3013
+ const inputs = paths.filter((p) => p.length > 0).map((path) => ({ path, fillRule: "nonzero" }));
3014
+ if (!inputs.length) return [];
3015
+ return _chunkXGD3FSNCcjs.pathBoolean.call(void 0, MERGE_OPS[mode], inputs).path;
3016
+ }
3017
+ function vectorRepeaterCopies(r, pivot) {
3018
+ const copies = Math.max(0, Number.isFinite(r.copies) ? Math.min(r.copies, 1e3) : 0);
3019
+ const n = Math.ceil(copies);
3020
+ const offset = Number.isFinite(r.offset) ? r.offset : 0;
3021
+ const so = (_nullishCoalesce(r.startOpacity, () => ( 100))) / 100;
3022
+ const eo = (_nullishCoalesce(r.endOpacity, () => ( 100))) / 100;
3023
+ const fract = copies - Math.floor(copies);
3024
+ const out = [];
3025
+ for (let i = 0; i < n; i++) {
3026
+ const k = i + offset;
3027
+ let m = translateMatrix(-pivot.x, -pivot.y);
3028
+ m = multiplyMatrices(m, scaleMatrix(Math.pow((_nullishCoalesce(_optionalChain([r, 'access', _60 => _60.scale, 'optionalAccess', _61 => _61.x]), () => ( 100))) / 100, k), Math.pow((_nullishCoalesce(_optionalChain([r, 'access', _62 => _62.scale, 'optionalAccess', _63 => _63.y]), () => ( 100))) / 100, k)));
3029
+ m = multiplyMatrices(m, rotateMatrix((_nullishCoalesce(r.rotation, () => ( 0))) * k));
3030
+ m = multiplyMatrices(m, translateMatrix(pivot.x + (_nullishCoalesce(_optionalChain([r, 'access', _64 => _64.position, 'optionalAccess', _65 => _65.x]), () => ( 0))) * k, pivot.y + (_nullishCoalesce(_optionalChain([r, 'access', _66 => _66.position, 'optionalAccess', _67 => _67.y]), () => ( 0))) * k));
3031
+ const t = n > 1 ? i / (n - 1) : 0;
3032
+ const partial = i + 1 === n && fract > 0 ? fract : 1;
3033
+ out.push({ index: i, matrix: m, opacity: Math.min(1, Math.max(0, (so + (eo - so) * t) * partial)) });
3034
+ }
3035
+ return out;
3036
+ }
3037
+ function repeatPaths(paths, r, pivot) {
3038
+ return vectorRepeaterCopies(r, pivot).map((copy) => ({ copy, paths: paths.map((p) => _chunkXGD3FSNCcjs.transformBezierPath.call(void 0, p, copy.matrix)) }));
3039
+ }
3040
+ function pathsCenter(paths) {
3041
+ const b = _chunkXGD3FSNCcjs.bezierPathBounds.call(void 0, paths.flat());
3042
+ return b ? { x: (b.minX + b.maxX) / 2, y: (b.minY + b.maxY) / 2 } : { x: 0, y: 0 };
3043
+ }
3044
+
2652
3045
  // src/vector/pathMap.ts
2653
3046
  var MAX_PIECES = 1 << 20;
2654
3047
  var MAX_DEPTH = 6;
@@ -2798,7 +3191,7 @@ function mapBezierPath(path, f, tolerance = 0.1, options = {}) {
2798
3191
 
2799
3192
  // src/vector/frames.ts
2800
3193
  function isVectorFrame(node) {
2801
- return _optionalChain([node, 'optionalAccess', _55 => _55.type]) === "group" && !!node.frame && !node.blend && !node.liveBoolean && !node.mask;
3194
+ return _optionalChain([node, 'optionalAccess', _68 => _68.type]) === "group" && !!node.frame && !node.blend && !node.liveBoolean && !node.mask;
2802
3195
  }
2803
3196
  function vectorFrameRectPath(frame) {
2804
3197
  const { x, y, width: w, height: h } = frame;
@@ -2842,8 +3235,8 @@ function placeSpan(rule, a0, a1, f0, f1, g0, g1) {
2842
3235
  }
2843
3236
  }
2844
3237
  function vectorFrameChildMatrix(resizing, box, from, to) {
2845
- const [x0, x1] = placeSpan(_nullishCoalesce(H[_nullishCoalesce(_optionalChain([resizing, 'optionalAccess', _56 => _56.horizontal]), () => ( "left"))], () => ( "start")), box.x, box.x + box.width, from.x, from.x + from.width, to.x, to.x + to.width);
2846
- const [y0, y1] = placeSpan(_nullishCoalesce(V[_nullishCoalesce(_optionalChain([resizing, 'optionalAccess', _57 => _57.vertical]), () => ( "top"))], () => ( "start")), box.y, box.y + box.height, from.y, from.y + from.height, to.y, to.y + to.height);
3238
+ const [x0, x1] = placeSpan(_nullishCoalesce(H[_nullishCoalesce(_optionalChain([resizing, 'optionalAccess', _69 => _69.horizontal]), () => ( "left"))], () => ( "start")), box.x, box.x + box.width, from.x, from.x + from.width, to.x, to.x + to.width);
3239
+ const [y0, y1] = placeSpan(_nullishCoalesce(V[_nullishCoalesce(_optionalChain([resizing, 'optionalAccess', _70 => _70.vertical]), () => ( "top"))], () => ( "start")), box.y, box.y + box.height, from.y, from.y + from.height, to.y, to.y + to.height);
2847
3240
  const sx = box.width > 1e-9 ? (x1 - x0) / box.width : 1;
2848
3241
  const sy = box.height > 1e-9 ? (y1 - y0) / box.height : 1;
2849
3242
  return [sx, 0, 0, sy, x0 - sx * box.x, y0 - sy * box.y];
@@ -2897,7 +3290,7 @@ function vectorFrameDocument(doc, id, find) {
2897
3290
  height,
2898
3291
  ...doc.background ? { background: doc.background } : {},
2899
3292
  nodes: [placed],
2900
- ..._optionalChain([doc, 'access', _58 => _58.symbols, 'optionalAccess', _59 => _59.length]) ? { symbols: doc.symbols } : {}
3293
+ ..._optionalChain([doc, 'access', _71 => _71.symbols, 'optionalAccess', _72 => _72.length]) ? { symbols: doc.symbols } : {}
2901
3294
  };
2902
3295
  }
2903
3296
  function getVectorFramePanel(state) {
@@ -2917,7 +3310,7 @@ function getVectorFramePanel(state) {
2917
3310
  const one = (values) => values.every((v2) => v2 === values[0]) ? values[0] : "mixed";
2918
3311
  return {
2919
3312
  frame: f ? { id: f.id, name: _nullishCoalesce(f.name, () => ( "Frame")), artboard: parents.get(f.id) === null, frame: f.frame } : null,
2920
- resizing: children.length ? { ids: children.map((c) => c.id), horizontal: one(children.map((c) => _nullishCoalesce(_optionalChain([c, 'access', _60 => _60.resizing, 'optionalAccess', _61 => _61.horizontal]), () => ( "left")))), vertical: one(children.map((c) => _nullishCoalesce(_optionalChain([c, 'access', _62 => _62.resizing, 'optionalAccess', _63 => _63.vertical]), () => ( "top")))) } : null
3313
+ resizing: children.length ? { ids: children.map((c) => c.id), horizontal: one(children.map((c) => _nullishCoalesce(_optionalChain([c, 'access', _73 => _73.resizing, 'optionalAccess', _74 => _74.horizontal]), () => ( "left")))), vertical: one(children.map((c) => _nullishCoalesce(_optionalChain([c, 'access', _75 => _75.resizing, 'optionalAccess', _76 => _76.vertical]), () => ( "top")))) } : null
2921
3314
  };
2922
3315
  }
2923
3316
 
@@ -3025,14 +3418,14 @@ function lineHits(p, q, seg) {
3025
3418
  return out;
3026
3419
  }
3027
3420
  var near = (a, b, eps) => Math.abs(a[0] - b[0]) <= eps && Math.abs(a[1] - b[1]) <= eps;
3028
- var degenerate = (seg, eps) => seg.every((p) => near(p, seg[0], eps));
3421
+ var degenerate2 = (seg, eps) => seg.every((p) => near(p, seg[0], eps));
3029
3422
  function arc(l, a, b, eps) {
3030
3423
  const n = l.segs.length;
3031
3424
  const segs = [];
3032
3425
  const chord = [];
3033
3426
  const push = (k, t0, t1) => {
3034
3427
  const piece = t0 <= 0 && t1 >= 1 ? l.segs[k].slice() : _chunkXGD3FSNCcjs.subSegment.call(void 0, l.segs[k], t0, t1);
3035
- if (!degenerate(piece, eps)) {
3428
+ if (!degenerate2(piece, eps)) {
3036
3429
  segs.push(piece);
3037
3430
  chord.push(l.chord[k]);
3038
3431
  }
@@ -3303,7 +3696,7 @@ function normalizeVectorFilterParams(type, params, base) {
3303
3696
  if (!isVectorFilterType(type)) return null;
3304
3697
  const out = { ...VECTOR_FILTER_DEFAULTS[type], ..._nullishCoalesce(base, () => ( {})) };
3305
3698
  for (const spec of VECTOR_FILTER_PARAM_SPECS[type]) {
3306
- const v2 = _optionalChain([params, 'optionalAccess', _64 => _64[spec.key]]);
3699
+ const v2 = _optionalChain([params, 'optionalAccess', _77 => _77[spec.key]]);
3307
3700
  if (v2 === void 0) continue;
3308
3701
  if (spec.kind === "number" && typeof v2 === "number" && Number.isFinite(v2)) out[spec.key] = Math.min(_nullishCoalesce(spec.max, () => ( Infinity)), Math.max(_nullishCoalesce(spec.min, () => ( -Infinity)), v2));
3309
3702
  else if (spec.kind === "color" && typeof v2 === "string" && v2.trim()) out[spec.key] = v2.trim();
@@ -3435,7 +3828,7 @@ function vectorFilterSvg(filters, id, bounds) {
3435
3828
  primitives.push(fe("feGaussianBlur", { in: body, stdDeviation: round(f.params.radius / 2), result: name("body") }));
3436
3829
  body = name("body");
3437
3830
  }
3438
- const lastResult = _optionalChain([primitives, 'access', _65 => _65[primitives.length - 1], 'optionalAccess', _66 => _66.attrs, 'access', _67 => _67.result]);
3831
+ const lastResult = _optionalChain([primitives, 'access', _78 => _78[primitives.length - 1], 'optionalAccess', _79 => _79.attrs, 'access', _80 => _80.result]);
3439
3832
  if (lastResult !== body) primitives.push(fe("feMerge", {}, [fe("feMergeNode", { in: body })]));
3440
3833
  const pad = vectorFilterReach(active) + 2;
3441
3834
  return {
@@ -3450,7 +3843,7 @@ function vectorFilterSvg(filters, id, bounds) {
3450
3843
  var escapeAttr = (value) => value.replace(/&/g, "&amp;").replace(/"/g, "&quot;").replace(/</g, "&lt;").replace(/>/g, "&gt;");
3451
3844
  function primitiveMarkup(p) {
3452
3845
  const attrs = Object.entries(p.attrs).map(([k, v2]) => ` ${k}="${escapeAttr(String(v2))}"`).join("");
3453
- return _optionalChain([p, 'access', _68 => _68.children, 'optionalAccess', _69 => _69.length]) ? `<${p.tag}${attrs}>${p.children.map(primitiveMarkup).join("")}</${p.tag}>` : `<${p.tag}${attrs}/>`;
3846
+ return _optionalChain([p, 'access', _81 => _81.children, 'optionalAccess', _82 => _82.length]) ? `<${p.tag}${attrs}>${p.children.map(primitiveMarkup).join("")}</${p.tag}>` : `<${p.tag}${attrs}/>`;
3454
3847
  }
3455
3848
  function vectorFilterMarkup(filter, extra = "") {
3456
3849
  return `<filter id="${escapeAttr(filter.id)}" filterUnits="userSpaceOnUse" x="${filter.x}" y="${filter.y}" width="${filter.width}" height="${filter.height}" color-interpolation-filters="sRGB"${extra}>${filter.primitives.map(primitiveMarkup).join("")}</filter>`;
@@ -3468,7 +3861,7 @@ function sanitizeVectorMask(value) {
3468
3861
  return r.invert === true ? { type: r.type, invert: true } : { type: r.type };
3469
3862
  }
3470
3863
  function isVectorMaskGroup(node) {
3471
- return _optionalChain([node, 'optionalAccess', _70 => _70.type]) === "group" && !!node.mask && isVectorMaskType(node.mask.type) && !node.blend && !node.liveBoolean && node.children.length > 0;
3864
+ return _optionalChain([node, 'optionalAccess', _83 => _83.type]) === "group" && !!node.mask && isVectorMaskType(node.mask.type) && !node.blend && !node.liveBoolean && node.children.length > 0;
3472
3865
  }
3473
3866
  function isVectorMaskActive(node) {
3474
3867
  return isVectorMaskGroup(node) && node.children[0].visible !== false;
@@ -3503,7 +3896,7 @@ function vectorMaskRegionShapes(node, type, parent = IDENTITY_MATRIX, self = tru
3503
3896
  if (!self && node.visible === false) return [];
3504
3897
  if (isVectorFrame(node)) node = vectorFrameDrawn(node);
3505
3898
  const m = multiplyMatrices(nodeMatrix(node), parent);
3506
- if (isVectorMaskActive(node) || node.type === "group" && _optionalChain([node, 'access', _71 => _71.effects, 'optionalAccess', _72 => _72.length])) {
3899
+ if (isVectorMaskActive(node) || node.type === "group" && _optionalChain([node, 'access', _84 => _84.effects, 'optionalAccess', _85 => _85.length])) {
3507
3900
  return vectorAppearanceShapes(node).flatMap((s) => regionOfPath(s.path, s.source, type, m));
3508
3901
  }
3509
3902
  const drawn = expandVectorAppearance(node);
@@ -3708,7 +4101,7 @@ function fitRuns(runs, length2, fallback) {
3708
4101
  }
3709
4102
  if (left2 > 0) {
3710
4103
  if (out.length) out[out.length - 1] = { ...out[out.length - 1], length: out[out.length - 1].length + left2 };
3711
- else out.push({ length: left2, style: _nullishCoalesce(_optionalChain([runs, 'access', _73 => _73[runs.length - 1], 'optionalAccess', _74 => _74.style]), () => ( fallback)) });
4104
+ else out.push({ length: left2, style: _nullishCoalesce(_optionalChain([runs, 'access', _86 => _86[runs.length - 1], 'optionalAccess', _87 => _87.style]), () => ( fallback)) });
3712
4105
  }
3713
4106
  return compact(out);
3714
4107
  }
@@ -3718,7 +4111,7 @@ function styleAt(runs, index, fallback) {
3718
4111
  if (index < at2 + r.length) return r.style;
3719
4112
  at2 += r.length;
3720
4113
  }
3721
- return _nullishCoalesce(_optionalChain([runs, 'access', _75 => _75[runs.length - 1], 'optionalAccess', _76 => _76.style]), () => ( fallback));
4114
+ return _nullishCoalesce(_optionalChain([runs, 'access', _88 => _88[runs.length - 1], 'optionalAccess', _89 => _89.style]), () => ( fallback));
3722
4115
  }
3723
4116
  function restyleRange(runs, start, end, patch) {
3724
4117
  const out = [];
@@ -3774,7 +4167,7 @@ function paragraphRanges(text) {
3774
4167
  return out;
3775
4168
  }
3776
4169
  function fitParagraphRuns(runs, text) {
3777
- const fallback = _nullishCoalesce(_optionalChain([runs, 'access', _77 => _77[0], 'optionalAccess', _78 => _78.style]), () => ( {}));
4170
+ const fallback = _nullishCoalesce(_optionalChain([runs, 'access', _90 => _90[0], 'optionalAccess', _91 => _91.style]), () => ( {}));
3778
4171
  const out = compact(paragraphRanges(text).map((p) => ({ length: p.end - p.start, style: styleAt(runs, p.start, fallback) })));
3779
4172
  return out.length ? out : [{ length: 0, style: fallback }];
3780
4173
  }
@@ -3790,7 +4183,7 @@ var isWide = (code) => code >= 11904 && code <= 40959 || code >= 44032 && code <
3790
4183
  var layoutCache = /* @__PURE__ */ new WeakMap();
3791
4184
  function layoutText(layer, shaper) {
3792
4185
  let byShaper = layoutCache.get(layer);
3793
- const hit = _optionalChain([byShaper, 'optionalAccess', _79 => _79.get, 'call', _80 => _80(shaper.id)]);
4186
+ const hit = _optionalChain([byShaper, 'optionalAccess', _92 => _92.get, 'call', _93 => _93(shaper.id)]);
3794
4187
  if (hit) return hit;
3795
4188
  const out = computeLayout(layer, shaper);
3796
4189
  if (!byShaper) {
@@ -4027,7 +4420,7 @@ function createCanvasTextShaper(options = {}) {
4027
4420
  return null;
4028
4421
  })));
4029
4422
  const canvas = make(1, 1);
4030
- const ctx = _optionalChain([canvas, 'optionalAccess', _81 => _81.getContext, 'call', _82 => _82("2d")]);
4423
+ const ctx = _optionalChain([canvas, 'optionalAccess', _94 => _94.getContext, 'call', _95 => _95("2d")]);
4031
4424
  if (!ctx || typeof ctx.measureText !== "function") return null;
4032
4425
  const fallback = _nullishCoalesce(options.fallbackFamily, () => ( "sans-serif"));
4033
4426
  const available = /* @__PURE__ */ new Map();
@@ -4100,17 +4493,17 @@ function createOutlineTextShaper(fonts, options = {}) {
4100
4493
  const entries = fonts.map((f) => {
4101
4494
  const e = "face" in f ? f : { face: f };
4102
4495
  const names = e.face.names;
4103
- const family = _nullishCoalesce(_nullishCoalesce(_nullishCoalesce(e.family, () => ( _optionalChain([names, 'optionalAccess', _83 => _83.fontFamily, 'optionalAccess', _84 => _84.en]))), () => ( Object.values(_nullishCoalesce(_optionalChain([names, 'optionalAccess', _85 => _85.fontFamily]), () => ( {})))[0])), () => ( "Font"));
4104
- const weight = _nullishCoalesce(_nullishCoalesce(e.weight, () => ( _optionalChain([e, 'access', _86 => _86.face, 'access', _87 => _87.tables, 'optionalAccess', _88 => _88.os2, 'optionalAccess', _89 => _89.usWeightClass]))), () => ( 400));
4105
- const italic = _nullishCoalesce(e.italic, () => ( Boolean((_nullishCoalesce(_optionalChain([e, 'access', _90 => _90.face, 'access', _91 => _91.tables, 'optionalAccess', _92 => _92.os2, 'optionalAccess', _93 => _93.fsSelection]), () => ( 0))) & 1)));
4106
- const postScript = _nullishCoalesce(_optionalChain([names, 'optionalAccess', _94 => _94.postScriptName, 'optionalAccess', _95 => _95.en]), () => ( Object.values(_nullishCoalesce(_optionalChain([names, 'optionalAccess', _96 => _96.postScriptName]), () => ( {})))[0]));
4496
+ const family = _nullishCoalesce(_nullishCoalesce(_nullishCoalesce(e.family, () => ( _optionalChain([names, 'optionalAccess', _96 => _96.fontFamily, 'optionalAccess', _97 => _97.en]))), () => ( Object.values(_nullishCoalesce(_optionalChain([names, 'optionalAccess', _98 => _98.fontFamily]), () => ( {})))[0])), () => ( "Font"));
4497
+ const weight = _nullishCoalesce(_nullishCoalesce(e.weight, () => ( _optionalChain([e, 'access', _99 => _99.face, 'access', _100 => _100.tables, 'optionalAccess', _101 => _101.os2, 'optionalAccess', _102 => _102.usWeightClass]))), () => ( 400));
4498
+ const italic = _nullishCoalesce(e.italic, () => ( Boolean((_nullishCoalesce(_optionalChain([e, 'access', _103 => _103.face, 'access', _104 => _104.tables, 'optionalAccess', _105 => _105.os2, 'optionalAccess', _106 => _106.fsSelection]), () => ( 0))) & 1)));
4499
+ const postScript = _nullishCoalesce(_optionalChain([names, 'optionalAccess', _107 => _107.postScriptName, 'optionalAccess', _108 => _108.en]), () => ( Object.values(_nullishCoalesce(_optionalChain([names, 'optionalAccess', _109 => _109.postScriptName]), () => ( {})))[0]));
4107
4500
  return { face: e.face, family, key: family.toLowerCase(), weight, italic, postScript };
4108
4501
  });
4109
4502
  const fallbackKey = (_nullishCoalesce(options.fallback, () => ( entries[0].family))).toLowerCase();
4110
4503
  const pick = (font) => {
4111
4504
  if (font.postScriptName) {
4112
- const exact = entries.find((e) => e.postScript === font.postScriptName);
4113
- if (exact) return { entry: exact, available: true };
4505
+ const exact2 = entries.find((e) => e.postScript === font.postScriptName);
4506
+ if (exact2) return { entry: exact2, available: true };
4114
4507
  }
4115
4508
  const key = font.family.trim().toLowerCase();
4116
4509
  let pool = entries.filter((e) => e.key === key);
@@ -4209,7 +4602,7 @@ function vectorTextHasOutlines() {
4209
4602
  return typeof getVectorTextShaper().outline === "function";
4210
4603
  }
4211
4604
  function vectorTextFamilies() {
4212
- return _nullishCoalesce(_optionalChain([getVectorTextShaper, 'call', _97 => _97(), 'access', _98 => _98.families, 'optionalCall', _99 => _99()]), () => ( ["sans-serif", "serif", "monospace"]));
4605
+ return _nullishCoalesce(_optionalChain([getVectorTextShaper, 'call', _110 => _110(), 'access', _111 => _111.families, 'optionalCall', _112 => _112()]), () => ( ["sans-serif", "serif", "monospace"]));
4213
4606
  }
4214
4607
  var DEFAULT_VECTOR_FONT = { fontFamily: "sans-serif", fontWeight: 400, fontSize: 24 };
4215
4608
  var VECTOR_CHARACTER_STYLE_KEYS = ["fontFamily", "fontWeight", "italic", "fontSize", "tracking", "leading", "baselineShift", "underline", "strikethrough"];
@@ -4384,7 +4777,7 @@ function computeLayout2(node, shaper) {
4384
4777
  const fragments = [];
4385
4778
  const lines = [];
4386
4779
  let overflow = false;
4387
- const fillOf = (f) => _optionalChain([runs, 'access', _100 => _100.find, 'call', _101 => _101((r) => f.start >= r.start && f.start < r.end), 'optionalAccess', _102 => _102.fill]);
4780
+ const fillOf = (f) => _optionalChain([runs, 'access', _113 => _113.find, 'call', _114 => _114((r) => f.start >= r.start && f.start < r.end), 'optionalAccess', _115 => _115.fill]);
4388
4781
  const styleOf = (f) => {
4389
4782
  const { color: _c, opacity: _o, postScriptName: _p, ...style } = f.style;
4390
4783
  return style;
@@ -4415,11 +4808,11 @@ function computeLayout2(node, shaper) {
4415
4808
  } else {
4416
4809
  const line = text.lines[0];
4417
4810
  const measure = measureVectorPath(subpathPath(frame.path), !!frame.flip);
4418
- const align = _nullishCoalesce(_optionalChain([node, 'access', _103 => _103.paragraph, 'optionalAccess', _104 => _104.align]), () => ( "left"));
4811
+ const align = _nullishCoalesce(_optionalChain([node, 'access', _116 => _116.paragraph, 'optionalAccess', _117 => _117.align]), () => ( "left"));
4419
4812
  const start = Math.max(0, _nullishCoalesce(frame.start, () => ( 0)));
4420
4813
  const end = Math.max(0, _nullishCoalesce(frame.end, () => ( 0)));
4421
4814
  const upright = frame.orientation === "upright";
4422
- const baselineOffset = pathBaselineOffset(_nullishCoalesce(frame.baseline, () => ( "baseline")), _nullishCoalesce(_optionalChain([line, 'optionalAccess', _105 => _105.ascent]), () => ( 0)), _nullishCoalesce(_optionalChain([line, 'optionalAccess', _106 => _106.descent]), () => ( 0)));
4815
+ const baselineOffset = pathBaselineOffset(_nullishCoalesce(frame.baseline, () => ( "baseline")), _nullishCoalesce(_optionalChain([line, 'optionalAccess', _118 => _118.ascent]), () => ( 0)), _nullishCoalesce(_optionalChain([line, 'optionalAccess', _119 => _119.descent]), () => ( 0)));
4423
4816
  if (line) {
4424
4817
  const chars = line.chars.filter((c) => {
4425
4818
  const lo = block.text.charCodeAt(c.index);
@@ -4428,7 +4821,7 @@ function computeLayout2(node, shaper) {
4428
4821
  const advanceOf = (c) => {
4429
4822
  const pair = charAt(block.text, c.index).length === 2;
4430
4823
  const low = pair ? line.chars.find((d) => d.index === c.index + 1) : void 0;
4431
- return c.advance + (_nullishCoalesce(_optionalChain([low, 'optionalAccess', _107 => _107.advance]), () => ( 0)));
4824
+ return c.advance + (_nullishCoalesce(_optionalChain([low, 'optionalAccess', _120 => _120.advance]), () => ( 0)));
4432
4825
  };
4433
4826
  const pivots = chars.map((c) => c.x + advanceOf(c) / 2);
4434
4827
  const positions = vectorPathTextPositions(pivots, [line.x, line.x + line.width], align, measure.length, start, end);
@@ -4483,7 +4876,7 @@ function computeLayout2(node, shaper) {
4483
4876
  if (x0 < Infinity) bounds = { x: x0, y: y0, width: x1 - x0, height: y1 - y0 };
4484
4877
  else if (frame.kind === "point") {
4485
4878
  const l = text.lines[0];
4486
- bounds = { x: frame.x, y: frame.y - (_nullishCoalesce(_optionalChain([l, 'optionalAccess', _108 => _108.ascent]), () => ( 0))), width: 0, height: (_nullishCoalesce(_optionalChain([l, 'optionalAccess', _109 => _109.ascent]), () => ( 0))) + (_nullishCoalesce(_optionalChain([l, 'optionalAccess', _110 => _110.descent]), () => ( 0))) };
4879
+ bounds = { x: frame.x, y: frame.y - (_nullishCoalesce(_optionalChain([l, 'optionalAccess', _121 => _121.ascent]), () => ( 0))), width: 0, height: (_nullishCoalesce(_optionalChain([l, 'optionalAccess', _122 => _122.ascent]), () => ( 0))) + (_nullishCoalesce(_optionalChain([l, 'optionalAccess', _123 => _123.descent]), () => ( 0))) };
4487
4880
  }
4488
4881
  }
4489
4882
  return { shaper: shaper.id, glyphs, fragments, lines, origin, text, bounds, overflow, missingFonts: text.missingFonts };
@@ -4604,7 +4997,7 @@ function vectorTextCaret(node, index) {
4604
4997
  const t = { x: Math.cos(r), y: Math.sin(r) };
4605
4998
  const n2 = { x: -t.y, y: t.x };
4606
4999
  const o = { x: g2.x + t.x * u, y: g2.y + t.y * u };
4607
- return { top: { x: o.x - n2.x * g2.ascent, y: o.y - n2.y * g2.ascent }, bottom: { x: o.x + n2.x * g2.descent, y: o.y + n2.y * g2.descent }, line: _nullishCoalesce(_optionalChain([layout, 'access', _111 => _111.fragments, 'access', _112 => _112[g2.fragment], 'optionalAccess', _113 => _113.line]), () => ( 0)) };
5000
+ return { top: { x: o.x - n2.x * g2.ascent, y: o.y - n2.y * g2.ascent }, bottom: { x: o.x + n2.x * g2.descent, y: o.y + n2.y * g2.descent }, line: _nullishCoalesce(_optionalChain([layout, 'access', _124 => _124.fragments, 'access', _125 => _125[g2.fragment], 'optionalAccess', _126 => _126.line]), () => ( 0)) };
4608
5001
  };
4609
5002
  if (node.frame.kind !== "path") {
4610
5003
  const c = caretAt(layout.text, index);
@@ -4739,7 +5132,7 @@ function sanitizeVectorTextFrame(value, path = "frame") {
4739
5132
  return { kind: "area", x: num2(f.x, `${path}.x`, -1e7, 1e7), y: num2(f.y, `${path}.y`, -1e7, 1e7), width: num2(f.width, `${path}.width`, 0, 1e7), height: num2(f.height, `${path}.height`, 0, 1e7) };
4740
5133
  if (f.kind === "path") {
4741
5134
  const sp = f.path;
4742
- if (!sp || !Array.isArray(sp.anchors) || sp.anchors.length < 2 || !sp.anchors.every((a) => isNum(_optionalChain([a, 'optionalAccess', _114 => _114.x])) && isNum(_optionalChain([a, 'optionalAccess', _115 => _115.y])))) fail(`${path}.path must be a subpath with at least two anchors.`);
5135
+ if (!sp || !Array.isArray(sp.anchors) || sp.anchors.length < 2 || !sp.anchors.every((a) => isNum(_optionalChain([a, 'optionalAccess', _127 => _127.x])) && isNum(_optionalChain([a, 'optionalAccess', _128 => _128.y])))) fail(`${path}.path must be a subpath with at least two anchors.`);
4743
5136
  const out = { kind: "path", path: { closed: !!sp.closed, anchors: sp.anchors.map((a) => ({ ...a })) } };
4744
5137
  if (f.start !== void 0 && f.start !== 0) out.start = num2(f.start, `${path}.start`, 0, 1e7);
4745
5138
  if (f.end !== void 0 && f.end !== 0) out.end = num2(f.end, `${path}.end`, 0, 1e7);
@@ -4757,7 +5150,7 @@ function sanitizeVectorTextFrame(value, path = "frame") {
4757
5150
  return fail(`${path}.kind must be point, area or path, got ${JSON.stringify(f.kind)}.`);
4758
5151
  }
4759
5152
  function normalizeVectorTextRuns(text, runs) {
4760
- if (!_optionalChain([runs, 'optionalAccess', _116 => _116.length])) return null;
5153
+ if (!_optionalChain([runs, 'optionalAccess', _129 => _129.length])) return null;
4761
5154
  const cleaned = fitVectorTextRuns(
4762
5155
  runs.map((r) => ({ length: r.length, style: stripUndefined(r.style) })),
4763
5156
  text.length
@@ -4791,7 +5184,7 @@ function replaceVectorText(node, start, end, insert) {
4791
5184
  const clean2 = insert.replace(/\r\n?/g, "\n");
4792
5185
  const text = node.text.slice(0, start) + clean2 + node.text.slice(end);
4793
5186
  let runs = null;
4794
- if (_optionalChain([node, 'access', _117 => _117.runs, 'optionalAccess', _118 => _118.length])) {
5187
+ if (_optionalChain([node, 'access', _130 => _130.runs, 'optionalAccess', _131 => _131.length])) {
4795
5188
  const fitted = fitVectorTextRuns(node.runs, node.text.length);
4796
5189
  const style = styleAt(fitted, start > 0 ? start - 1 : start, {});
4797
5190
  runs = normalizeVectorTextRuns(text, spliceRuns(fitted, start, end, clean2.length, style));
@@ -4807,7 +5200,7 @@ function styleVectorText(node, start, end, patch) {
4807
5200
  if (whole) {
4808
5201
  let next2 = { ...node, font: patchVectorCharacterStyle(node.font, fields, "style") };
4809
5202
  const keys = Object.keys(fields).filter((k) => fields[k] !== void 0);
4810
- if (_optionalChain([next2, 'access', _119 => _119.runs, 'optionalAccess', _120 => _120.length]) && (keys.length || fill !== void 0)) {
5203
+ if (_optionalChain([next2, 'access', _132 => _132.runs, 'optionalAccess', _133 => _133.length]) && (keys.length || fill !== void 0)) {
4811
5204
  const runs2 = normalizeVectorTextRuns(
4812
5205
  next2.text,
4813
5206
  next2.runs.map((r) => {
@@ -4852,7 +5245,7 @@ function bakeVectorTextGeometry(node, m) {
4852
5245
  ...s.baselineShift !== void 0 ? { baselineShift: s.baselineShift * k } : {}
4853
5246
  });
4854
5247
  const font = scaleStyle(node.font);
4855
- const runs = _optionalChain([node, 'access', _121 => _121.runs, 'optionalAccess', _122 => _122.map, 'call', _123 => _123((r) => ({ length: r.length, style: scaleStyle(r.style) }))]);
5248
+ const runs = _optionalChain([node, 'access', _134 => _134.runs, 'optionalAccess', _135 => _135.map, 'call', _136 => _136((r) => ({ length: r.length, style: scaleStyle(r.style) }))]);
4856
5249
  const p = node.paragraph;
4857
5250
  const paragraph = p ? {
4858
5251
  ...p,
@@ -5134,7 +5527,7 @@ function vectorInstanceGroup(node, bake) {
5134
5527
  const m = _nullishCoalesce(node.transform, () => ( [1, 0, 0, 1, 0, 0]));
5135
5528
  const { rigid, residual } = decomposeRigid(m);
5136
5529
  const k = Math.sqrt(Math.abs(residual[0] * residual[3] - residual[1] * residual[2]));
5137
- const hidden = new Set(_nullishCoalesce(_optionalChain([node, 'access', _124 => _124.overrides, 'optionalAccess', _125 => _125.hidden]), () => ( [])));
5530
+ const hidden = new Set(_nullishCoalesce(_optionalChain([node, 'access', _137 => _137.overrides, 'optionalAccess', _138 => _138.hidden]), () => ( [])));
5138
5531
  const keep = (list) => list.filter((n) => !hidden.has(n.id)).map((n) => n.type === "group" ? { ...n, children: keep(n.children) } : n);
5139
5532
  let children = prefixVectorIds(keep(_nullishCoalesce(node.art, () => ( []))), node.id);
5140
5533
  if (!isIdentityMatrix(residual)) children = children.map((c) => bake(c, residual));
@@ -5147,8 +5540,8 @@ function vectorInstanceGroup(node, bake) {
5147
5540
  if (node.locked) group.locked = true;
5148
5541
  if (node.opacity !== void 0) group.opacity = node.opacity;
5149
5542
  if (node.blendMode) group.blendMode = node.blendMode;
5150
- if (_optionalChain([node, 'access', _126 => _126.filters, 'optionalAccess', _127 => _127.length])) group.filters = node.filters;
5151
- if (_optionalChain([node, 'access', _128 => _128.effects, 'optionalAccess', _129 => _129.length])) group.effects = node.effects;
5543
+ if (_optionalChain([node, 'access', _139 => _139.filters, 'optionalAccess', _140 => _140.length])) group.filters = node.filters;
5544
+ if (_optionalChain([node, 'access', _141 => _141.effects, 'optionalAccess', _142 => _142.length])) group.effects = node.effects;
5152
5545
  if (node.booleanOperation) group.booleanOperation = node.booleanOperation;
5153
5546
  if (node.blendStep) group.blendStep = true;
5154
5547
  return group;
@@ -5872,7 +6265,9 @@ var VECTOR_EFFECT_DEFAULTS = {
5872
6265
  endOpacity: 100,
5873
6266
  composite: "below"
5874
6267
  },
5875
- envelope: { style: "arc", bend: 50, horizontal: 0, vertical: 0, orientation: "horizontal", rows: 2, columns: 2, mesh: null }
6268
+ envelope: { style: "arc", bend: 50, horizontal: 0, vertical: 0, orientation: "horizontal", rows: 2, columns: 2, mesh: null },
6269
+ contour: { direction: "inside", steps: 4, offset: 6, join: "round", miterLimit: 4, fillColor: "#ffffff", strokeColor: null, acceleration: 0 },
6270
+ blockShadow: { angle: 45, distance: 20, color: "#1e293b", opacity: 100, endOpacity: 100 }
5876
6271
  };
5877
6272
  var VECTOR_EFFECT_LABELS = {
5878
6273
  trim: "Trim Paths",
@@ -5884,7 +6279,9 @@ var VECTOR_EFFECT_LABELS = {
5884
6279
  offset: "Offset Paths",
5885
6280
  merge: "Merge Paths",
5886
6281
  repeater: "Repeater",
5887
- envelope: "Envelope"
6282
+ envelope: "Envelope",
6283
+ contour: "Contour",
6284
+ blockShadow: "Block Shadow"
5888
6285
  };
5889
6286
  var VECTOR_EFFECT_PARAM_SPECS = {
5890
6287
  trim: [
@@ -5952,6 +6349,40 @@ var VECTOR_EFFECT_PARAM_SPECS = {
5952
6349
  ]
5953
6350
  }
5954
6351
  ],
6352
+ contour: [
6353
+ {
6354
+ key: "direction",
6355
+ label: "Direction",
6356
+ kind: "select",
6357
+ options: [
6358
+ { value: "inside", label: "Inside" },
6359
+ { value: "outside", label: "Outside" },
6360
+ { value: "center", label: "To centre" }
6361
+ ]
6362
+ },
6363
+ { key: "steps", label: "Steps", kind: "number", min: 1, max: 200, step: 1, slider: true },
6364
+ { key: "offset", label: "Offset", kind: "number", min: 0.1, max: 200, step: 0.5, slider: true },
6365
+ { key: "fillColor", label: "Fill to", kind: "color" },
6366
+ { key: "strokeColor", label: "Stroke to", kind: "color" },
6367
+ { key: "acceleration", label: "Acceleration", kind: "number", min: -100, max: 100, step: 1, slider: true },
6368
+ {
6369
+ key: "join",
6370
+ label: "Join",
6371
+ kind: "select",
6372
+ options: [
6373
+ { value: "miter", label: "Miter" },
6374
+ { value: "round", label: "Round" },
6375
+ { value: "bevel", label: "Bevel" }
6376
+ ]
6377
+ }
6378
+ ],
6379
+ blockShadow: [
6380
+ { key: "angle", label: "Angle \xB0", kind: "number", min: -360, max: 360, step: 1, slider: true },
6381
+ { key: "distance", label: "Distance", kind: "number", min: 0, max: 2e3, step: 1, slider: true },
6382
+ { key: "color", label: "Colour", kind: "color" },
6383
+ { key: "opacity", label: "Opacity %", kind: "number", min: 0, max: 100, step: 1, slider: true },
6384
+ { key: "endOpacity", label: "End opacity %", kind: "number", min: 0, max: 100, step: 1, slider: true }
6385
+ ],
5955
6386
  repeater: [
5956
6387
  { key: "copies", label: "Copies", kind: "number", min: 0, max: 50, step: 0.1, slider: true },
5957
6388
  { key: "offset", label: "Offset", kind: "number", min: -10, max: 10, step: 0.1, slider: true },
@@ -6035,18 +6466,19 @@ function normalizeVectorEffectParams(type, params, base) {
6035
6466
  if (!defaults) return null;
6036
6467
  const out = { ...defaults, ..._nullishCoalesce(base, () => ( {})) };
6037
6468
  for (const spec of VECTOR_EFFECT_PARAM_SPECS[type]) {
6038
- const v2 = _optionalChain([params, 'optionalAccess', _130 => _130[spec.key]]);
6469
+ const v2 = _optionalChain([params, 'optionalAccess', _143 => _143[spec.key]]);
6039
6470
  if (v2 === void 0) continue;
6040
6471
  if (spec.kind === "number" && typeof v2 === "number" && Number.isFinite(v2)) out[spec.key] = Math.min(_nullishCoalesce(spec.max, () => ( Infinity)), Math.max(_nullishCoalesce(spec.min, () => ( -Infinity)), v2));
6041
6472
  else if (spec.kind === "boolean" && typeof v2 === "boolean") out[spec.key] = v2;
6042
6473
  else if (spec.kind === "vec2" && isVec2(v2)) out[spec.key] = { x: v2.x, y: v2.y };
6043
6474
  else if (spec.kind === "select" && spec.options.some((o) => o.value === v2)) out[spec.key] = v2;
6475
+ else if (spec.kind === "color" && (v2 === null || typeof v2 === "string" && parseVectorColor(v2))) out[spec.key] = v2;
6044
6476
  }
6045
6477
  if (type === "envelope") {
6046
6478
  const o = out;
6047
6479
  o.rows = Math.round(o.rows);
6048
6480
  o.columns = Math.round(o.columns);
6049
- const given = _optionalChain([params, 'optionalAccess', _131 => _131.mesh]);
6481
+ const given = _optionalChain([params, 'optionalAccess', _144 => _144.mesh]);
6050
6482
  let mesh = given !== void 0 ? isValidWarpMesh(given) ? cloneMesh(given) : null : o.mesh;
6051
6483
  if (o.style !== "mesh") mesh = null;
6052
6484
  if (mesh && given !== void 0) {
@@ -6063,10 +6495,10 @@ function createVectorEffect(type, id, params) {
6063
6495
  }
6064
6496
  var isEnabled = (e) => e.enabled !== false && !!VECTOR_EFFECT_DEFAULTS[e.type];
6065
6497
  function activeVectorEffects(node) {
6066
- return _nullishCoalesce(_optionalChain([node, 'access', _132 => _132.effects, 'optionalAccess', _133 => _133.filter, 'call', _134 => _134(isEnabled)]), () => ( []));
6498
+ return _nullishCoalesce(_optionalChain([node, 'access', _145 => _145.effects, 'optionalAccess', _146 => _146.filter, 'call', _147 => _147(isEnabled)]), () => ( []));
6067
6499
  }
6068
6500
  function hasOwnVectorAppearance(node) {
6069
- return node.type === "text" || node.type === "instance" || node.type === "group" && !!node.liveBoolean || isVectorFrame(node) || !!_optionalChain([node, 'access', _135 => _135.effects, 'optionalAccess', _136 => _136.some, 'call', _137 => _137(isEnabled)]);
6501
+ return node.type === "text" || node.type === "instance" || node.type === "group" && !!node.liveBoolean || isVectorFrame(node) || isVectorSymmetryGroup(node) || !!_optionalChain([node, 'access', _148 => _148.effects, 'optionalAccess', _149 => _149.some, 'call', _150 => _150(isEnabled)]);
6070
6502
  }
6071
6503
  var liveCache = /* @__PURE__ */ new WeakMap();
6072
6504
  function hasVectorAppearance(node) {
@@ -6078,7 +6510,7 @@ function hasVectorAppearance(node) {
6078
6510
  return v2;
6079
6511
  }
6080
6512
  function isVectorLiveBoolean(node) {
6081
- return _optionalChain([node, 'optionalAccess', _138 => _138.type]) === "group" && !!node.liveBoolean;
6513
+ return _optionalChain([node, 'optionalAccess', _151 => _151.type]) === "group" && !!node.liveBoolean;
6082
6514
  }
6083
6515
  function vectorOperandOperation(group, child) {
6084
6516
  return _nullishCoalesce(_nullishCoalesce(child.booleanOperation, () => ( group.liveBoolean)), () => ( "union"));
@@ -6195,11 +6627,78 @@ var compareOrder = (a, b) => {
6195
6627
  for (let i = 0; i < n; i++) if (a[i] !== b[i]) return a[i] - b[i];
6196
6628
  return a.length - b.length;
6197
6629
  };
6198
- var add3 = (a, b) => ({ x: a.x + (_nullishCoalesce(_optionalChain([b, 'optionalAccess', _139 => _139.x]), () => ( 0))), y: a.y + (_nullishCoalesce(_optionalChain([b, 'optionalAccess', _140 => _140.y]), () => ( 0))) });
6630
+ var add3 = (a, b) => ({ x: a.x + (_nullishCoalesce(_optionalChain([b, 'optionalAccess', _152 => _152.x]), () => ( 0))), y: a.y + (_nullishCoalesce(_optionalChain([b, 'optionalAccess', _153 => _153.y]), () => ( 0))) });
6199
6631
  var mapPaths = (shapes, fn) => {
6200
6632
  const out = fn(shapes.map((s) => s.path));
6201
6633
  return shapes.map((s, i) => ({ ...s, path: _nullishCoalesce(out[i], () => ( [])) }));
6202
6634
  };
6635
+ function blendPaint(from, to, t) {
6636
+ if (to === null || typeof from !== "string") return from;
6637
+ const a = parseVectorColor(from);
6638
+ const b = parseVectorColor(to);
6639
+ if (!a || !b) return from;
6640
+ const h = (v2) => Math.round(Math.min(1, Math.max(0, v2)) * 255).toString(16).padStart(2, "0");
6641
+ const m = a.map((v2, k) => v2 + (b[k] - v2) * t);
6642
+ return `#${h(m[0])}${h(m[1])}${h(m[2])}`;
6643
+ }
6644
+ function contourShapes(shapes, c) {
6645
+ const out = [];
6646
+ const step = Math.max(0.01, c.offset);
6647
+ const outside = c.direction === "outside";
6648
+ for (const s of shapes) {
6649
+ let n = Math.min(200, Math.max(1, Math.round(c.steps)));
6650
+ if (c.direction === "center") {
6651
+ const b = _chunkXGD3FSNCcjs.bezierPathBounds.call(void 0, s.path);
6652
+ n = b ? Math.min(200, Math.max(1, Math.ceil(Math.min(b.maxX - b.minX, b.maxY - b.minY) / 2 / step))) : 0;
6653
+ }
6654
+ out.push({ ...s, order: [outside ? n : 0, ...s.order] });
6655
+ const power = 2 ** (Math.min(100, Math.max(-100, c.acceleration)) / 50);
6656
+ for (let k = 1; k <= n; k++) {
6657
+ const [path] = offsetPaths([s.path], (outside ? 1 : -1) * step * k, c.join, c.miterLimit, 1, 0);
6658
+ if (!_optionalChain([path, 'optionalAccess', _154 => _154.length])) break;
6659
+ const t = (k / n) ** power;
6660
+ const source = { ...s.source, fill: _nullishCoalesce(blendPaint(s.source.fill, c.fillColor, t), () => ( null)), stroke: _nullishCoalesce(blendPaint(s.source.stroke, c.strokeColor, t), () => ( null)), fills: void 0, strokes: void 0 };
6661
+ out.push({ source, path, opacity: s.opacity, order: [outside ? n - k : k, ...s.order] });
6662
+ }
6663
+ }
6664
+ return out;
6665
+ }
6666
+ function blockShadowShapes(shapes, b) {
6667
+ const rad2 = b.angle * Math.PI / 180;
6668
+ const u = { x: Math.cos(rad2), y: Math.sin(rad2) };
6669
+ const distance = Math.max(0, b.distance);
6670
+ const shadows = [];
6671
+ for (const s of shapes) {
6672
+ const color2 = _nullishCoalesce(b.color, () => ( (typeof s.source.fill === "string" && s.source.fill !== "none" ? s.source.fill : "#000000")));
6673
+ const path = sweepPath(s.path, u.x * distance, u.y * distance, s.source.fillRule === "evenodd" ? "evenodd" : "nonzero");
6674
+ const box = _chunkXGD3FSNCcjs.bezierPathBounds.call(void 0, s.path);
6675
+ if (!path.length || !box) continue;
6676
+ let fill = color2;
6677
+ const near3 = Math.min(100, Math.max(0, b.opacity));
6678
+ const far = Math.min(100, Math.max(0, b.endOpacity));
6679
+ const top = Math.max(near3, far);
6680
+ if (near3 !== far && distance > 0) {
6681
+ const along2 = [box.minX * u.x + box.minY * u.y, box.maxX * u.x + box.minY * u.y, box.minX * u.x + box.maxY * u.y, box.maxX * u.x + box.maxY * u.y];
6682
+ const t0 = Math.min(...along2);
6683
+ const t1 = Math.max(...along2) + distance;
6684
+ const c = { x: (box.minX + box.maxX) / 2, y: (box.minY + box.maxY) / 2 };
6685
+ const k = c.x * u.x + c.y * u.y;
6686
+ fill = {
6687
+ type: "linear",
6688
+ units: "userSpaceOnUse",
6689
+ start: { x: c.x + u.x * (t0 - k), y: c.y + u.y * (t0 - k) },
6690
+ end: { x: c.x + u.x * (t1 - k), y: c.y + u.y * (t1 - k) },
6691
+ stops: [
6692
+ { offset: 0, color: color2, opacity: near3 / top },
6693
+ { offset: 1, color: color2, opacity: far / top }
6694
+ ]
6695
+ };
6696
+ }
6697
+ const source = { ...s.source, fill, stroke: null, fills: void 0, strokes: void 0, fillRule: "nonzero" };
6698
+ shadows.push({ source, path, opacity: s.opacity * top / 100, order: [0, ...s.order] });
6699
+ }
6700
+ return [...shadows, ...shapes.map((s) => ({ ...s, order: [1, ...s.order] }))];
6701
+ }
6203
6702
  function applyVectorEffects(shapes, effects) {
6204
6703
  let list = shapes.slice();
6205
6704
  for (const e of _nullishCoalesce(effects, () => ( []))) {
@@ -6240,6 +6739,12 @@ function applyVectorEffects(shapes, effects) {
6240
6739
  list = mapPaths(list, (p) => envelopePaths(p, params));
6241
6740
  break;
6242
6741
  }
6742
+ case "contour":
6743
+ list = contourShapes(list, e.params);
6744
+ break;
6745
+ case "blockShadow":
6746
+ list = blockShadowShapes(list, e.params);
6747
+ break;
6243
6748
  case "repeater": {
6244
6749
  const r = e.params;
6245
6750
  const copies = repeatPaths(
@@ -6316,10 +6821,10 @@ function vectorEffectInputBounds(node, effectId) {
6316
6821
  return paths ? pathsBounds(paths) : null;
6317
6822
  }
6318
6823
  function vectorNodeEnvelope(node) {
6319
- return _nullishCoalesce(_optionalChain([node, 'optionalAccess', _141 => _141.effects, 'optionalAccess', _142 => _142.find, 'call', _143 => _143((e) => e.type === "envelope" && e.enabled !== false)]), () => ( null));
6824
+ return _nullishCoalesce(_optionalChain([node, 'optionalAccess', _155 => _155.effects, 'optionalAccess', _156 => _156.find, 'call', _157 => _157((e) => e.type === "envelope" && e.enabled !== false)]), () => ( null));
6320
6825
  }
6321
6826
  function vectorEnvelopeFrame(node, effectId) {
6322
- const e = effectId ? _optionalChain([node, 'access', _144 => _144.effects, 'optionalAccess', _145 => _145.find, 'call', _146 => _146((x) => x.id === effectId)]) : vectorNodeEnvelope(node);
6827
+ const e = effectId ? _optionalChain([node, 'access', _158 => _158.effects, 'optionalAccess', _159 => _159.find, 'call', _160 => _160((x) => x.id === effectId)]) : vectorNodeEnvelope(node);
6323
6828
  if (!e || e.type !== "envelope") return null;
6324
6829
  const bounds = vectorEffectInputBounds(node, e.id);
6325
6830
  if (!bounds || !(bounds.width > 0 && bounds.height > 0)) return null;
@@ -6333,8 +6838,8 @@ function vectorAppearanceShapes(node) {
6333
6838
  shapeCache.set(node, [vectorTextShaperGeneration(), shapes]);
6334
6839
  return shapes;
6335
6840
  }
6336
- if (isVectorFrame(node)) {
6337
- const shapes = vectorAppearanceShapes(vectorFrameDrawn(node));
6841
+ if (isVectorFrame(node) || isVectorSymmetryGroup(node)) {
6842
+ const shapes = vectorAppearanceShapes(isVectorFrame(node) ? vectorFrameDrawn(node) : vectorSymmetryDrawn(node));
6338
6843
  shapeCache.set(node, [vectorTextShaperGeneration(), shapes]);
6339
6844
  return shapes;
6340
6845
  }
@@ -6380,7 +6885,7 @@ function placement(node) {
6380
6885
  ...node.blendStep ? { blendStep: true } : {},
6381
6886
  ...node.booleanOperation ? { booleanOperation: node.booleanOperation } : {},
6382
6887
  ...node.blendMode ? { blendMode: node.blendMode } : {},
6383
- ..._optionalChain([node, 'access', _147 => _147.filters, 'optionalAccess', _148 => _148.length]) ? { filters: node.filters } : {}
6888
+ ..._optionalChain([node, 'access', _161 => _161.filters, 'optionalAccess', _162 => _162.length]) ? { filters: node.filters } : {}
6384
6889
  };
6385
6890
  }
6386
6891
  function vectorAppearanceNodes(node) {
@@ -6396,8 +6901,8 @@ function expandVectorAppearance(node) {
6396
6901
  expandCache.set(node, [vectorTextShaperGeneration(), drawn]);
6397
6902
  return drawn;
6398
6903
  }
6399
- if (isVectorFrame(node)) {
6400
- const drawn = vectorFrameDrawn(node);
6904
+ if (isVectorFrame(node) || isVectorSymmetryGroup(node)) {
6905
+ const drawn = isVectorFrame(node) ? vectorFrameDrawn(node) : vectorSymmetryDrawn(node);
6401
6906
  const out2 = hasVectorAppearance(drawn) ? expandVectorAppearance(drawn) : drawn;
6402
6907
  expandCache.set(node, [vectorTextShaperGeneration(), out2]);
6403
6908
  return out2;
@@ -6502,7 +7007,7 @@ function vectorEnteredGroups(nodes, ids) {
6502
7007
  // src/vector/connectors.ts
6503
7008
  var SIDES = ["top", "right", "bottom", "left", "center"];
6504
7009
  function isVectorConnector(node) {
6505
- return _optionalChain([node, 'optionalAccess', _149 => _149.type]) === "path" && !!node.connector;
7010
+ return _optionalChain([node, 'optionalAccess', _163 => _163.type]) === "path" && !!node.connector;
6506
7011
  }
6507
7012
  function vectorConnectionSites(nodes, id) {
6508
7013
  const node = findVectorNode(nodes, id);
@@ -6559,7 +7064,7 @@ function facingSite(sites, toward) {
6559
7064
  }
6560
7065
  function storedEnds(node, world) {
6561
7066
  const sp = node.subpaths[0];
6562
- if (!_optionalChain([sp, 'optionalAccess', _150 => _150.anchors, 'access', _151 => _151.length])) return null;
7067
+ if (!_optionalChain([sp, 'optionalAccess', _164 => _164.anchors, 'access', _165 => _165.length])) return null;
6563
7068
  const a = sp.anchors[0];
6564
7069
  const b = sp.anchors[sp.anchors.length - 1];
6565
7070
  return [applyMatrix(world, a), applyMatrix(world, b)];
@@ -6666,8 +7171,8 @@ function routeVectorConnector(nodes, id) {
6666
7171
  }));
6667
7172
  return {
6668
7173
  subpaths: [{ closed: false, anchors: local }],
6669
- startSide: _nullishCoalesce(_optionalChain([s, 'optionalAccess', _152 => _152.side]), () => ( null)),
6670
- endSide: _nullishCoalesce(_optionalChain([e, 'optionalAccess', _153 => _153.side]), () => ( null)),
7174
+ startSide: _nullishCoalesce(_optionalChain([s, 'optionalAccess', _166 => _166.side]), () => ( null)),
7175
+ endSide: _nullishCoalesce(_optionalChain([e, 'optionalAccess', _167 => _167.side]), () => ( null)),
6671
7176
  dropped: { start: !!startGlue && !s, end: !!endGlue && !e }
6672
7177
  };
6673
7178
  }
@@ -6679,7 +7184,7 @@ function sameSubpaths(a, b) {
6679
7184
  const o = b[i];
6680
7185
  return sp.closed === o.closed && sp.anchors.length === o.anchors.length && sp.anchors.every((p, k) => {
6681
7186
  const q = o.anchors[k];
6682
- return samePoint(p, q) && samePoint(p.in, q.in) && samePoint(p.out, q.out) && (_nullishCoalesce(_optionalChain([p, 'access', _154 => _154.corner, 'optionalAccess', _155 => _155.radius]), () => ( 0))) === (_nullishCoalesce(_optionalChain([q, 'access', _156 => _156.corner, 'optionalAccess', _157 => _157.radius]), () => ( 0)));
7187
+ return samePoint(p, q) && samePoint(p.in, q.in) && samePoint(p.out, q.out) && (_nullishCoalesce(_optionalChain([p, 'access', _168 => _168.corner, 'optionalAccess', _169 => _169.radius]), () => ( 0))) === (_nullishCoalesce(_optionalChain([q, 'access', _170 => _170.corner, 'optionalAccess', _171 => _171.radius]), () => ( 0)));
6683
7188
  });
6684
7189
  });
6685
7190
  }
@@ -6789,7 +7294,7 @@ var add4 = (a, b) => ({ x: a.x + b.x, y: a.y + b.y });
6789
7294
  var sub4 = (a, b) => ({ x: a.x - b.x, y: a.y - b.y });
6790
7295
  var scale2 = (a, k) => ({ x: a.x * k, y: a.y * k });
6791
7296
  var left = (d) => ({ x: d.y, y: -d.x });
6792
- var unit2 = (v2) => {
7297
+ var unit3 = (v2) => {
6793
7298
  const l = Math.hypot(v2.x, v2.y);
6794
7299
  return l > 1e-12 ? { x: v2.x / l, y: v2.y / l } : { x: 1, y: 0 };
6795
7300
  };
@@ -6846,7 +7351,7 @@ function vectorStrokeGradientDefs(g, id, node, options = {}) {
6846
7351
  for (let i = 0; i < segCount; i++) {
6847
7352
  const a = pts[i];
6848
7353
  const b = pts[(i + 1) % n];
6849
- dirs.push(unit2(sub4(b, a)));
7354
+ dirs.push(unit3(sub4(b, a)));
6850
7355
  lengths.push(lengths[i] + Math.hypot(b.x - a.x, b.y - a.y));
6851
7356
  }
6852
7357
  const total = lengths[segCount];
@@ -6958,7 +7463,7 @@ function applyVectorCornersAttribute(subpaths, value) {
6958
7463
  for (const item of value.trim().split(/\s+/)) {
6959
7464
  const m = /^(\d+)\.(\d+):([\d.eE+-]+)(?::([a-z]+))?$/.exec(item);
6960
7465
  if (!m) continue;
6961
- const a = _optionalChain([subpaths, 'access', _158 => _158[+m[1]], 'optionalAccess', _159 => _159.anchors, 'access', _160 => _160[+m[2]]]);
7466
+ const a = _optionalChain([subpaths, 'access', _172 => _172[+m[1]], 'optionalAccess', _173 => _173.anchors, 'access', _174 => _174[+m[2]]]);
6962
7467
  const radius = parseFloat(m[3]);
6963
7468
  if (!a || !(radius > 0)) continue;
6964
7469
  const kind = VECTOR_CORNER_KINDS.includes(m[4]) ? m[4] : void 0;
@@ -6983,7 +7488,7 @@ function vectorPaintToSvg(paint, gradientId, options = {}) {
6983
7488
  const area2 = bounds2 ? { x: bounds2.x - reach2, y: bounds2.y - reach2, width: bounds2.width + 2 * reach2, height: bounds2.height + 2 * reach2 } : null;
6984
7489
  const key2 = `${gradientId}|${_nullishCoalesce(options.role, () => ( "fill"))}|${_nullishCoalesce(options.precision, () => ( 3))}|${area2 ? [area2.x, area2.y, area2.width, area2.height].join(",") : ""}`;
6985
7490
  let byKey2 = paintCache.get(paint);
6986
- const hit = _optionalChain([byKey2, 'optionalAccess', _161 => _161.get, 'call', _162 => _162(key2)]);
7491
+ const hit = _optionalChain([byKey2, 'optionalAccess', _175 => _175.get, 'call', _176 => _176(key2)]);
6987
7492
  if (hit) return { value: `url(#${gradientId})`, defs: hit };
6988
7493
  const defs2 = vectorShadedSvgDefs(paint, gradientId, { bounds: bounds2, area: area2, precision: _nullishCoalesce(options.precision, () => ( 3)) });
6989
7494
  if (!byKey2) paintCache.set(paint, byKey2 = /* @__PURE__ */ new Map());
@@ -6995,7 +7500,7 @@ function vectorPaintToSvg(paint, gradientId, options = {}) {
6995
7500
  const precision = _nullishCoalesce(options.precision, () => ( 3));
6996
7501
  const key = `${gradientId}|${role}|${precision}`;
6997
7502
  const owner = _nullishCoalesce(options.node, () => ( paint));
6998
- const cached = _optionalChain([paintCache, 'access', _163 => _163.get, 'call', _164 => _164(owner), 'optionalAccess', _165 => _165.get, 'call', _166 => _166(key)]);
7503
+ const cached = _optionalChain([paintCache, 'access', _177 => _177.get, 'call', _178 => _178(owner), 'optionalAccess', _179 => _179.get, 'call', _180 => _180(key)]);
6999
7504
  if (cached && (!options.node || (role === "fill" ? options.node.fill : options.node.stroke) === paint)) return { value: `url(#${gradientId})`, defs: cached };
7000
7505
  const node = options.node;
7001
7506
  const bounds = node ? vectorPathLocalBounds(node) : null;
@@ -7049,7 +7554,7 @@ function vectorNodeLocalPaintBounds(node) {
7049
7554
  }
7050
7555
  var filterCache = /* @__PURE__ */ new WeakMap();
7051
7556
  function vectorNodeFilterSvg(node, id) {
7052
- if (!_optionalChain([node, 'access', _167 => _167.filters, 'optionalAccess', _168 => _168.length])) return null;
7557
+ if (!_optionalChain([node, 'access', _181 => _181.filters, 'optionalAccess', _182 => _182.length])) return null;
7053
7558
  const hit = filterCache.get(node);
7054
7559
  if (hit && hit.id === id) return hit.filter;
7055
7560
  const active = activeVectorFilters(node);
@@ -7133,7 +7638,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7133
7638
  if (node.type === "path" && node.connector) out2 += ` data-vector-connector="${escapeAttr2(JSON.stringify(node.connector))}"`;
7134
7639
  const blend = vectorBlendModeCss(node.blendMode);
7135
7640
  if (blend) out2 += ` style="mix-blend-mode:${blend}"`;
7136
- if (_optionalChain([node, 'access', _169 => _169.filters, 'optionalAccess', _170 => _170.length])) {
7641
+ if (_optionalChain([node, 'access', _183 => _183.filters, 'optionalAccess', _184 => _184.length])) {
7137
7642
  const filter = vectorNodeFilterSvg(node, `${prefix}filter-${node.id}`);
7138
7643
  const data = ` data-vector-filters="${escapeAttr2(JSON.stringify(node.filters))}"`;
7139
7644
  if (filter) {
@@ -7180,7 +7685,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7180
7685
  let out2 = ` stroke="${escapeAttr2(strokeValue)}" stroke-width="${num3(width)}"`;
7181
7686
  if (node.strokeLinecap && node.strokeLinecap !== "butt") out2 += ` stroke-linecap="${node.strokeLinecap}"`;
7182
7687
  if (node.strokeLinejoin && node.strokeLinejoin !== "miter") out2 += ` stroke-linejoin="${node.strokeLinejoin}"`;
7183
- if (_optionalChain([node, 'access', _171 => _171.strokeDasharray, 'optionalAccess', _172 => _172.length])) out2 += ` stroke-dasharray="${node.strokeDasharray.map(num3).join(" ")}"`;
7688
+ if (_optionalChain([node, 'access', _185 => _185.strokeDasharray, 'optionalAccess', _186 => _186.length])) out2 += ` stroke-dasharray="${node.strokeDasharray.map(num3).join(" ")}"`;
7184
7689
  return out2;
7185
7690
  };
7186
7691
  const liveCorners = (node) => {
@@ -7223,7 +7728,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7223
7728
  };
7224
7729
  const emit2 = (node, depth) => {
7225
7730
  if (node.visible === false && !options.includeHidden) return;
7226
- const wrappers = _nullishCoalesce(_optionalChain([options, 'access', _173 => _173.wrap, 'optionalAccess', _174 => _174[node.id]]), () => ( []));
7731
+ const wrappers = _nullishCoalesce(_optionalChain([options, 'access', _187 => _187.wrap, 'optionalAccess', _188 => _188[node.id]]), () => ( []));
7227
7732
  wrappers.forEach((w2, i) => {
7228
7733
  let attrs = w2.id !== void 0 ? ` id="${escapeAttr2(w2.id)}"` : "";
7229
7734
  if (w2.transform) attrs += ` transform="${escapeAttr2(w2.transform)}"`;
@@ -7244,7 +7749,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7244
7749
  };
7245
7750
  const emitMaskGroup = (node, depth) => {
7246
7751
  const [source, ...contents] = node.children;
7247
- const body = _optionalChain([node, 'access', _175 => _175.effects, 'optionalAccess', _176 => _176.length]) && contents.length ? [{ id: `${node.id}~content`, type: "group", effects: node.effects, children: contents }] : contents;
7752
+ const body = _optionalChain([node, 'access', _189 => _189.effects, 'optionalAccess', _190 => _190.length]) && contents.length ? [{ id: `${node.id}~content`, type: "group", effects: node.effects, children: contents }] : contents;
7248
7753
  const settings = { type: node.mask.type, ...node.mask.invert ? { invert: true } : {} };
7249
7754
  lines.push(`${indent(depth)}<g${common(node)} data-vector-mask="${escapeAttr2(JSON.stringify(settings))}">`);
7250
7755
  const mask = vectorMaskRenderData(node, `${prefix}mask-${node.id}`, `${prefix}mask-filter-${node.id}`, precision);
@@ -7261,7 +7766,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7261
7766
  lines.push(`${indent(depth + 1)}<g data-vector-part="mask-source" display="none">`);
7262
7767
  emitNode(source, depth + 2);
7263
7768
  lines.push(`${indent(depth + 1)}</g>`);
7264
- if (_optionalChain([mask, 'optionalAccess', _177 => _177.clip])) {
7769
+ if (_optionalChain([mask, 'optionalAccess', _191 => _191.clip])) {
7265
7770
  defs.push(`<clipPath id="${escapeAttr2(mask.id)}">${mask.clip.map((c) => `<path d="${c.d}" clip-rule="${c.clipRule}"/>`).join("")}</clipPath>`);
7266
7771
  ref = ` clip-path="url(#${escapeAttr2(mask.id)})"`;
7267
7772
  }
@@ -7273,7 +7778,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7273
7778
  };
7274
7779
  const emitTextElement = (node, depth, attrs) => {
7275
7780
  const geometry = vectorTextGeometryNode(node);
7276
- const fields = { text: node.text, font: node.font, ..._optionalChain([node, 'access', _178 => _178.runs, 'optionalAccess', _179 => _179.length]) ? { runs: node.runs } : {}, ...node.paragraph ? { paragraph: node.paragraph } : {}, frame: node.frame, ..._optionalChain([node, 'access', _180 => _180.effects, 'optionalAccess', _181 => _181.length]) ? { effects: node.effects } : {} };
7781
+ const fields = { text: node.text, font: node.font, ..._optionalChain([node, 'access', _192 => _192.runs, 'optionalAccess', _193 => _193.length]) ? { runs: node.runs } : {}, ...node.paragraph ? { paragraph: node.paragraph } : {}, frame: node.frame, ..._optionalChain([node, 'access', _194 => _194.effects, 'optionalAccess', _195 => _195.length]) ? { effects: node.effects } : {} };
7277
7782
  let data = ` data-vector-text="${escapeAttr2(JSON.stringify(fields))}"`;
7278
7783
  if (hasVectorPaintStacks(node)) data += ` data-vector-fills="${escapeAttr2(JSON.stringify(vectorFills(node)))}" data-vector-strokes="${escapeAttr2(JSON.stringify(vectorStrokes(node)))}"`;
7279
7784
  else {
@@ -7315,12 +7820,12 @@ function vectorDocumentToSvg(doc, options = {}) {
7315
7820
  };
7316
7821
  const emitText = (node, depth) => {
7317
7822
  const outlines = vectorTextPaths(node).outlines;
7318
- const effects = !!_optionalChain([node, 'access', _182 => _182.effects, 'optionalAccess', _183 => _183.some, 'call', _184 => _184((e) => e.enabled !== false)]);
7823
+ const effects = !!_optionalChain([node, 'access', _196 => _196.effects, 'optionalAccess', _197 => _197.some, 'call', _198 => _198((e) => e.enabled !== false)]);
7319
7824
  if (!outlines || !effects && options.text !== "outlines") {
7320
7825
  emitTextElement(node, depth, common(node));
7321
7826
  return;
7322
7827
  }
7323
- lines.push(`${indent(depth)}<g${common(node)} data-vector-live="${escapeAttr2(JSON.stringify({ kind: "text", ..._optionalChain([node, 'access', _185 => _185.effects, 'optionalAccess', _186 => _186.length]) ? { effects: node.effects } : {} }))}">`);
7828
+ lines.push(`${indent(depth)}<g${common(node)} data-vector-live="${escapeAttr2(JSON.stringify({ kind: "text", ..._optionalChain([node, 'access', _199 => _199.effects, 'optionalAccess', _200 => _200.length]) ? { effects: node.effects } : {} }))}">`);
7324
7829
  lines.push(`${indent(depth + 1)}<g data-vector-part="appearance">`);
7325
7830
  for (const shape of vectorAppearanceNodes(node)) emit2(shape, depth + 2);
7326
7831
  lines.push(`${indent(depth + 1)}</g>`);
@@ -7334,7 +7839,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7334
7839
  const symbolRef = (symbolId) => {
7335
7840
  const hit = symbolIds.get(symbolId);
7336
7841
  if (hit) return hit;
7337
- const sym2 = _optionalChain([doc, 'access', _187 => _187.symbols, 'optionalAccess', _188 => _188.find, 'call', _189 => _189((x) => x.id === symbolId)]);
7842
+ const sym2 = _optionalChain([doc, 'access', _201 => _201.symbols, 'optionalAccess', _202 => _202.find, 'call', _203 => _203((x) => x.id === symbolId)]);
7338
7843
  if (!sym2) return null;
7339
7844
  const id = `${prefix}symbol-${symbolId}`;
7340
7845
  symbolIds.set(symbolId, id);
@@ -7344,20 +7849,20 @@ function vectorDocumentToSvg(doc, options = {}) {
7344
7849
  };
7345
7850
  const emitInstance = (node, depth) => {
7346
7851
  const data = { symbolId: node.symbolId, ...node.scaleStrokes === false ? { scaleStrokes: false } : {}, ...node.overrides ? { overrides: node.overrides } : {} };
7347
- const exact = !node.overrides && node.scaleStrokes !== false && !_optionalChain([node, 'access', _190 => _190.effects, 'optionalAccess', _191 => _191.length]) && !_optionalChain([node, 'access', _192 => _192.filters, 'optionalAccess', _193 => _193.length]);
7852
+ const exact2 = !node.overrides && node.scaleStrokes !== false && !_optionalChain([node, 'access', _204 => _204.effects, 'optionalAccess', _205 => _205.length]) && !_optionalChain([node, 'access', _206 => _206.filters, 'optionalAccess', _207 => _207.length]);
7348
7853
  const ref = symbolRef(node.symbolId);
7349
- if (exact && ref) {
7854
+ if (exact2 && ref) {
7350
7855
  lines.push(`${indent(depth)}<use${common(node)} href="#${escapeAttr2(ref)}" data-vector-instance="${escapeAttr2(JSON.stringify(data))}"/>`);
7351
7856
  return;
7352
7857
  }
7353
- const full = { ...data, ...node.transform ? { transform: node.transform } : {}, ..._optionalChain([node, 'access', _194 => _194.effects, 'optionalAccess', _195 => _195.length]) ? { effects: node.effects } : {} };
7858
+ const full = { ...data, ...node.transform ? { transform: node.transform } : {}, ..._optionalChain([node, 'access', _208 => _208.effects, 'optionalAccess', _209 => _209.length]) ? { effects: node.effects } : {} };
7354
7859
  lines.push(`${indent(depth)}<g data-vector-instance="${escapeAttr2(JSON.stringify(full))}">`);
7355
7860
  emitNode(vectorInstanceDrawn(node), depth + 1);
7356
7861
  lines.push(`${indent(depth)}</g>`);
7357
7862
  };
7358
7863
  const emitFrame = (node, depth) => {
7359
7864
  const f = node.frame;
7360
- const data = { ...f, ..._optionalChain([node, 'access', _196 => _196.effects, 'optionalAccess', _197 => _197.length]) ? { effects: node.effects } : {} };
7865
+ const data = { ...f, ..._optionalChain([node, 'access', _210 => _210.effects, 'optionalAccess', _211 => _211.length]) ? { effects: node.effects } : {} };
7361
7866
  lines.push(`${indent(depth)}<g${common(node)} data-vector-frame="${escapeAttr2(JSON.stringify(data))}">`);
7362
7867
  const rect = vectorFrameRectPath(f);
7363
7868
  if (f.fill !== void 0 && f.fill !== null && f.fill !== "none") {
@@ -7396,8 +7901,9 @@ function vectorDocumentToSvg(doc, options = {}) {
7396
7901
  if (hasOwnVectorAppearance(node)) {
7397
7902
  const live2 = {
7398
7903
  kind: node.type,
7399
- ..._optionalChain([node, 'access', _198 => _198.effects, 'optionalAccess', _199 => _199.length]) ? { effects: node.effects } : {},
7400
- ...node.type === "group" && node.liveBoolean ? { liveBoolean: node.liveBoolean } : {}
7904
+ ..._optionalChain([node, 'access', _212 => _212.effects, 'optionalAccess', _213 => _213.length]) ? { effects: node.effects } : {},
7905
+ ...node.type === "group" && node.liveBoolean ? { liveBoolean: node.liveBoolean } : {},
7906
+ ...node.type === "group" && node.symmetry ? { symmetry: node.symmetry } : {}
7401
7907
  };
7402
7908
  lines.push(`${indent(depth)}<g${common(node)} data-vector-live="${escapeAttr2(JSON.stringify(live2))}">`);
7403
7909
  lines.push(`${indent(depth + 1)}<g data-vector-part="appearance">`);
@@ -7446,7 +7952,7 @@ function vectorDocumentToSvg(doc, options = {}) {
7446
7952
  data += ` data-vector-width-profile="${widthProfileToAttribute(profile)}"`;
7447
7953
  if (node.strokeLinecap && node.strokeLinecap !== "butt") data += ` data-vector-stroke-linecap="${node.strokeLinecap}"`;
7448
7954
  if (node.strokeLinejoin && node.strokeLinejoin !== "miter") data += ` data-vector-stroke-linejoin="${node.strokeLinejoin}"`;
7449
- if (_optionalChain([node, 'access', _200 => _200.strokeDasharray, 'optionalAccess', _201 => _201.length])) data += ` data-vector-stroke-dasharray="${node.strokeDasharray.map(num3).join(" ")}"`;
7955
+ if (_optionalChain([node, 'access', _214 => _214.strokeDasharray, 'optionalAccess', _215 => _215.length])) data += ` data-vector-stroke-dasharray="${node.strokeDasharray.map(num3).join(" ")}"`;
7450
7956
  }
7451
7957
  lines.push(`${indent(depth)}<g${common(node)}${data}>`);
7452
7958
  lines.push(`${indent(depth + 1)}<path data-vector-part="fill" d="${d}"${fillAttrs}${live}/>`);
@@ -7614,7 +8120,7 @@ function attrOrStyle(el, name) {
7614
8120
  return el.attrs[name];
7615
8121
  }
7616
8122
  function urlId(value) {
7617
- return _nullishCoalesce(_optionalChain([/^url\(\s*['"]?#([^'")\s]+)['"]?\s*\)/, 'access', _202 => _202.exec, 'call', _203 => _203((_nullishCoalesce(value, () => ( ""))).trim()), 'optionalAccess', _204 => _204[1]]), () => ( null));
8123
+ return _nullishCoalesce(_optionalChain([/^url\(\s*['"]?#([^'")\s]+)['"]?\s*\)/, 'access', _216 => _216.exec, 'call', _217 => _217((_nullishCoalesce(value, () => ( ""))).trim()), 'optionalAccess', _218 => _218[1]]), () => ( null));
7618
8124
  }
7619
8125
  function clipRulesAsFillRules(el) {
7620
8126
  const attrs = { ...el.attrs };
@@ -7679,9 +8185,9 @@ function resolveGradient(id, raw) {
7679
8185
  for (let el = first; el && !chain.includes(el) && chain.length < 32; ) {
7680
8186
  chain.push(el);
7681
8187
  const href = _nullishCoalesce(el.attrs.href, () => ( el.attrs["xlink:href"]));
7682
- el = _optionalChain([href, 'optionalAccess', _205 => _205.startsWith, 'call', _206 => _206("#")]) ? raw.get(href.slice(1)) : void 0;
8188
+ el = _optionalChain([href, 'optionalAccess', _219 => _219.startsWith, 'call', _220 => _220("#")]) ? raw.get(href.slice(1)) : void 0;
7683
8189
  }
7684
- const attr = (name) => _optionalChain([chain, 'access', _207 => _207.find, 'call', _208 => _208((el) => el.attrs[name] !== void 0), 'optionalAccess', _209 => _209.attrs, 'access', _210 => _210[name]]);
8190
+ const attr = (name) => _optionalChain([chain, 'access', _221 => _221.find, 'call', _222 => _222((el) => el.attrs[name] !== void 0), 'optionalAccess', _223 => _223.attrs, 'access', _224 => _224[name]]);
7685
8191
  const stops = _nullishCoalesce(chain.map(readStops).find((s) => s.length), () => ( []));
7686
8192
  if (!stops.length) return null;
7687
8193
  const user = attr("gradientUnits") === "userSpaceOnUse";
@@ -7851,7 +8357,7 @@ function parseVectorSvg(svg, options = {}) {
7851
8357
  const stackedPath = (g, _style, m, meta) => {
7852
8358
  const fillEl = g.children.find((c) => c.name === "path" && c.attrs["data-vector-part"] === "fill");
7853
8359
  const subpaths = fillEl ? shapeOf(fillEl) : null;
7854
- if (!_optionalChain([subpaths, 'optionalAccess', _211 => _211.length])) return null;
8360
+ if (!_optionalChain([subpaths, 'optionalAccess', _225 => _225.length])) return null;
7855
8361
  const parse = (v2) => {
7856
8362
  try {
7857
8363
  return v2 ? JSON.parse(v2) : [];
@@ -7870,7 +8376,7 @@ function parseVectorSvg(svg, options = {}) {
7870
8376
  const key = (n) => JSON.stringify([n.subpaths, _nullishCoalesce(n.transform, () => ( null)), _nullishCoalesce(n.opacity, () => ( 1)), n.visible !== false, _nullishCoalesce(n.filters, () => ( null)), _nullishCoalesce(n.blendMode, () => ( "normal")), _nullishCoalesce(n.fillRule, () => ( "nonzero")), _nullishCoalesce(n.booleanOperation, () => ( null))]);
7871
8377
  for (const n of nodes2) {
7872
8378
  const prev = out[out.length - 1];
7873
- if (_optionalChain([prev, 'optionalAccess', _212 => _212.type]) === "path" && n.type === "path" && key(prev) === key(n)) {
8379
+ if (_optionalChain([prev, 'optionalAccess', _226 => _226.type]) === "path" && n.type === "path" && key(prev) === key(n)) {
7874
8380
  const fills = vectorFills(n);
7875
8381
  const strokesBefore = vectorStrokes(prev);
7876
8382
  if (!(fills.length && strokesBefore.length)) {
@@ -7888,7 +8394,7 @@ function parseVectorSvg(svg, options = {}) {
7888
8394
  const part = (name) => g.children.find((c) => c.name === "path" && c.attrs["data-vector-part"] === name);
7889
8395
  const fillEl = part("fill");
7890
8396
  const subpaths = fillEl ? shapeOf(fillEl) : null;
7891
- if (!fillEl || !_optionalChain([subpaths, 'optionalAccess', _213 => _213.length])) return null;
8397
+ if (!fillEl || !_optionalChain([subpaths, 'optionalAccess', _227 => _227.length])) return null;
7892
8398
  const a = g.attrs;
7893
8399
  const fs = readStyle(fillEl, style);
7894
8400
  const strokeEl = part("stroke");
@@ -7925,7 +8431,7 @@ function parseVectorSvg(svg, options = {}) {
7925
8431
  ...profile.length ? { strokeWidthProfile: profile } : {},
7926
8432
  ...keptCap ? { strokeLinecap: keptCap } : {},
7927
8433
  ...keptJoin ? { strokeLinejoin: keptJoin } : {},
7928
- ..._optionalChain([keptDash, 'optionalAccess', _214 => _214.length]) ? { strokeDasharray: keptDash } : {}
8434
+ ..._optionalChain([keptDash, 'optionalAccess', _228 => _228.length]) ? { strokeDasharray: keptDash } : {}
7929
8435
  };
7930
8436
  return placed(node, m);
7931
8437
  };
@@ -7960,6 +8466,8 @@ function parseVectorSvg(svg, options = {}) {
7960
8466
  const group = { id, type: "group", ...meta, children: inner };
7961
8467
  if (effects.length) group.effects = transformVectorEffects(effects, m);
7962
8468
  if (liveBoolean) group.liveBoolean = liveBoolean;
8469
+ const symmetry = sanitizeVectorSymmetry(raw.symmetry);
8470
+ if (symmetry) group.symmetry = transformVectorSymmetry(symmetry, m);
7963
8471
  const blend = blendFromAttribute(g.attrs["data-vector-blend"], m);
7964
8472
  if (blend) group.blend = blend;
7965
8473
  return group;
@@ -7988,8 +8496,8 @@ function parseVectorSvg(svg, options = {}) {
7988
8496
  } else {
7989
8497
  const fill = json2(g.attrs["data-vector-fill"]);
7990
8498
  const stroke = json2(g.attrs["data-vector-stroke"]);
7991
- node.fill = fill == null ? null : _nullishCoalesce(_optionalChain([sanitizeVectorFills, 'call', _215 => _215([{ paint: fill }]), 'access', _216 => _216[0], 'optionalAccess', _217 => _217.paint]), () => ( null));
7992
- node.stroke = stroke == null ? null : _nullishCoalesce(_optionalChain([sanitizeVectorFills, 'call', _218 => _218([{ paint: stroke }]), 'access', _219 => _219[0], 'optionalAccess', _220 => _220.paint]), () => ( null));
8499
+ node.fill = fill == null ? null : _nullishCoalesce(_optionalChain([sanitizeVectorFills, 'call', _229 => _229([{ paint: fill }]), 'access', _230 => _230[0], 'optionalAccess', _231 => _231.paint]), () => ( null));
8500
+ node.stroke = stroke == null ? null : _nullishCoalesce(_optionalChain([sanitizeVectorFills, 'call', _232 => _232([{ paint: stroke }]), 'access', _233 => _233[0], 'optionalAccess', _234 => _234.paint]), () => ( null));
7993
8501
  const settings = json2(g.attrs["data-vector-stroke-settings"]);
7994
8502
  if (settings && typeof settings === "object") {
7995
8503
  const strokes = sanitizeVectorStrokes([{ paint: _nullishCoalesce(node.stroke, () => ( "#000")), ...settings }]);
@@ -8025,8 +8533,8 @@ function parseVectorSvg(svg, options = {}) {
8025
8533
  const anchor = attrOrStyle(el, "text-anchor");
8026
8534
  const first0 = (v2) => _nullishCoalesce(numberList(v2)[0], () => ( 0));
8027
8535
  const tspan = el.children.find((c) => c.name === "tspan");
8028
- const x = el.attrs.x !== void 0 ? first0(el.attrs.x) : first0(_optionalChain([tspan, 'optionalAccess', _221 => _221.attrs, 'access', _222 => _222.x]));
8029
- const y = el.attrs.y !== void 0 ? first0(el.attrs.y) : first0(_optionalChain([tspan, 'optionalAccess', _223 => _223.attrs, 'access', _224 => _224.y]));
8536
+ const x = el.attrs.x !== void 0 ? first0(el.attrs.x) : first0(_optionalChain([tspan, 'optionalAccess', _235 => _235.attrs, 'access', _236 => _236.x]));
8537
+ const y = el.attrs.y !== void 0 ? first0(el.attrs.y) : first0(_optionalChain([tspan, 'optionalAccess', _237 => _237.attrs, 'access', _238 => _238.y]));
8030
8538
  const fillValue = _nullishCoalesce(attrOrStyle(el, "fill"), () => ( style.fill));
8031
8539
  let node = {
8032
8540
  id: idFor(el),
@@ -8057,12 +8565,12 @@ function parseVectorSvg(svg, options = {}) {
8057
8565
  if (symbolOfElement.has(el)) return symbolOfElement.get(el);
8058
8566
  symbolOfElement.set(el, null);
8059
8567
  const own = json2(el.attrs["data-vector-symbol"]);
8060
- let id = typeof _optionalChain([own, 'optionalAccess', _225 => _225.id]) === "string" && own.id ? own.id : _nullishCoalesce(el.attrs.id, () => ( createId()));
8568
+ let id = typeof _optionalChain([own, 'optionalAccess', _239 => _239.id]) === "string" && own.id ? own.id : _nullishCoalesce(el.attrs.id, () => ( createId()));
8061
8569
  while (usedSymbolIds.has(id)) id = `${id}-${usedSymbolIds.size}`;
8062
8570
  usedSymbolIds.add(id);
8063
8571
  const style = readStyle(el, rootStyle);
8064
8572
  const nodes2 = el.name === "symbol" ? visit2(el, style, IDENTITY_MATRIX) : visitOne({ ...el, attrs: { ...el.attrs, transform: "" } }, rootStyle, parseSvgTransform(el.attrs.transform));
8065
- symbols.push({ id, name: typeof _optionalChain([own, 'optionalAccess', _226 => _226.name]) === "string" && own.name ? own.name : _nullishCoalesce(el.attrs.id, () => ( "Symbol")), nodes: nodes2 });
8573
+ symbols.push({ id, name: typeof _optionalChain([own, 'optionalAccess', _240 => _240.name]) === "string" && own.name ? own.name : _nullishCoalesce(el.attrs.id, () => ( "Symbol")), nodes: nodes2 });
8066
8574
  symbolOfElement.set(el, id);
8067
8575
  return id;
8068
8576
  };
@@ -8074,13 +8582,13 @@ function parseVectorSvg(svg, options = {}) {
8074
8582
  if (!symbolId) return null;
8075
8583
  const own = json2(el.attrs["data-vector-instance"]);
8076
8584
  const place2 = multiplyMatrices(translateMatrix(length(el.attrs.x), length(el.attrs.y)), m);
8077
- const node = { id: idFor(el), type: "instance", ...meta, symbolId, ..._optionalChain([own, 'optionalAccess', _227 => _227.scaleStrokes]) === false ? { scaleStrokes: false } : {}, ..._optionalChain([own, 'optionalAccess', _228 => _228.overrides]) ? { overrides: own.overrides } : {} };
8585
+ const node = { id: idFor(el), type: "instance", ...meta, symbolId, ..._optionalChain([own, 'optionalAccess', _241 => _241.scaleStrokes]) === false ? { scaleStrokes: false } : {}, ..._optionalChain([own, 'optionalAccess', _242 => _242.overrides]) ? { overrides: own.overrides } : {} };
8078
8586
  return isIdentityMatrix(place2) ? node : { ...node, transform: place2 };
8079
8587
  };
8080
8588
  const ownInstance = (g, m, meta) => {
8081
8589
  const raw = json2(g.attrs["data-vector-instance"]);
8082
8590
  if (!raw || typeof raw.symbolId !== "string") return null;
8083
- const sym2 = [...byId.values()].find((e) => e.name === "symbol" && _optionalChain([json2, 'call', _229 => _229(e.attrs["data-vector-symbol"]), 'optionalAccess', _230 => _230.id]) === raw.symbolId);
8591
+ const sym2 = [...byId.values()].find((e) => e.name === "symbol" && _optionalChain([json2, 'call', _243 => _243(e.attrs["data-vector-symbol"]), 'optionalAccess', _244 => _244.id]) === raw.symbolId);
8084
8592
  const symbolId = sym2 ? symbolFor(sym2) : raw.symbolId;
8085
8593
  if (!symbolId) return null;
8086
8594
  const t = Array.isArray(raw.transform) && raw.transform.length === 6 && raw.transform.every(Number.isFinite) ? raw.transform : IDENTITY_MATRIX;
@@ -8088,7 +8596,7 @@ function parseVectorSvg(svg, options = {}) {
8088
8596
  const drawn = g.children.find((c) => c.name === "g");
8089
8597
  const effects = sanitizeVectorEffects(raw.effects);
8090
8598
  const node = {
8091
- id: _nullishCoalesce(_optionalChain([drawn, 'optionalAccess', _231 => _231.attrs, 'access', _232 => _232.id]), () => ( idFor(g))),
8599
+ id: _nullishCoalesce(_optionalChain([drawn, 'optionalAccess', _245 => _245.attrs, 'access', _246 => _246.id]), () => ( idFor(g))),
8092
8600
  type: "instance",
8093
8601
  ...meta,
8094
8602
  symbolId,
@@ -8145,12 +8653,12 @@ function parseVectorSvg(svg, options = {}) {
8145
8653
  const masked = (el, nodes2, m) => {
8146
8654
  let out = nodes2;
8147
8655
  const clipEl = rawMasks.get(_nullishCoalesce(urlId(attrOrStyle(el, "clip-path")), () => ( "")));
8148
- if (_optionalChain([clipEl, 'optionalAccess', _233 => _233.name]) === "clipPath") {
8656
+ if (_optionalChain([clipEl, 'optionalAccess', _247 => _247.name]) === "clipPath") {
8149
8657
  const source = maskNode(clipEl, m, out, clipEl.attrs.clipPathUnits);
8150
8658
  if (source) out = [{ id: idFor({ name: "g", attrs: {}, children: [] }), type: "group", name: "Clip Group", mask: { type: "clip" }, children: [source, ...out] }];
8151
8659
  }
8152
8660
  const maskEl = rawMasks.get(_nullishCoalesce(urlId(attrOrStyle(el, "mask")), () => ( "")));
8153
- if (_optionalChain([maskEl, 'optionalAccess', _234 => _234.name]) === "mask") {
8661
+ if (_optionalChain([maskEl, 'optionalAccess', _248 => _248.name]) === "mask") {
8154
8662
  const source = maskNode(maskEl, m, out, maskEl.attrs.maskContentUnits);
8155
8663
  const type = attrOrStyle(maskEl, "mask-type") === "alpha" ? "alpha" : "luminance";
8156
8664
  if (source) out = [{ id: idFor({ name: "g", attrs: {}, children: [] }), type: "group", name: "Opacity Mask", mask: { type }, children: [source, ...out] }];
@@ -8172,19 +8680,19 @@ function parseVectorSvg(svg, options = {}) {
8172
8680
  let sourceEl = part("mask-source");
8173
8681
  if (!sourceEl) {
8174
8682
  const el = rawMasks.get(_nullishCoalesce(urlId(maskedEl.attrs.mask), () => ( "")));
8175
- const invert2 = _optionalChain([el, 'optionalAccess', _235 => _235.children, 'access', _236 => _236.find, 'call', _237 => _237((c) => c.name === "g" && c.attrs["data-vector-part"] === "mask-invert")]);
8683
+ const invert2 = _optionalChain([el, 'optionalAccess', _249 => _249.children, 'access', _250 => _250.find, 'call', _251 => _251((c) => c.name === "g" && c.attrs["data-vector-part"] === "mask-invert")]);
8176
8684
  sourceEl = _nullishCoalesce(invert2, () => ( el));
8177
8685
  }
8178
8686
  const source = sourceEl ? visit2(sourceEl, style, m)[0] : void 0;
8179
8687
  let contents = visit2(maskedEl, style, m);
8180
8688
  let effects;
8181
8689
  const wrapper = contents.length === 1 && contents[0].type === "group" && contents[0].id === `${id}~content` ? contents[0] : null;
8182
- if (_optionalChain([wrapper, 'optionalAccess', _238 => _238.type]) === "group") {
8690
+ if (_optionalChain([wrapper, 'optionalAccess', _252 => _252.type]) === "group") {
8183
8691
  effects = _nullishCoalesce(wrapper.effects, () => ( void 0));
8184
8692
  contents = wrapper.children;
8185
8693
  }
8186
8694
  if (!source) return contents.length ? { id, type: "group", ...meta, children: contents } : null;
8187
- return { id, type: "group", ...meta, mask, ..._optionalChain([effects, 'optionalAccess', _239 => _239.length]) ? { effects } : {}, children: [source, ...contents] };
8695
+ return { id, type: "group", ...meta, mask, ..._optionalChain([effects, 'optionalAccess', _253 => _253.length]) ? { effects } : {}, children: [source, ...contents] };
8188
8696
  };
8189
8697
  const frameGroup = (g, style, m, meta) => {
8190
8698
  const raw = parseJson(g.attrs["data-vector-frame"]);
@@ -8196,7 +8704,7 @@ function parseVectorSvg(svg, options = {}) {
8196
8704
  const { rigid, residual } = decomposeRigid(m);
8197
8705
  const r = _chunkXGD3FSNCcjs.bezierPathBounds.call(void 0, _chunkXGD3FSNCcjs.transformBezierPath.call(void 0, subpathsToBezier(vectorFrameRectPath(frame)), residual));
8198
8706
  const back = invertMatrix(rigid);
8199
- const effects = sanitizeVectorEffects(_optionalChain([raw, 'optionalAccess', _240 => _240.effects]));
8707
+ const effects = sanitizeVectorEffects(_optionalChain([raw, 'optionalAccess', _254 => _254.effects]));
8200
8708
  return {
8201
8709
  id,
8202
8710
  type: "group",
@@ -8424,7 +8932,7 @@ function vectorNodesNear(nodes, rect, pad = 0) {
8424
8932
  }
8425
8933
 
8426
8934
  // src/vector/geometry.ts
8427
- var EPS2 = 1e-9;
8935
+ var EPS3 = 1e-9;
8428
8936
  var cloneAnchor = (a) => ({
8429
8937
  x: a.x,
8430
8938
  y: a.y,
@@ -8450,7 +8958,7 @@ function hasPaint(paint) {
8450
8958
  return true;
8451
8959
  }
8452
8960
  var handleOf = (a, side) => _nullishCoalesce(a[side], () => ( { x: a.x, y: a.y }));
8453
- var isOnAnchor = (a, h) => !h || Math.abs(h.x - a.x) < EPS2 && Math.abs(h.y - a.y) < EPS2;
8961
+ var isOnAnchor = (a, h) => !h || Math.abs(h.x - a.x) < EPS3 && Math.abs(h.y - a.y) < EPS3;
8454
8962
  function subpathSegmentCount(sp) {
8455
8963
  const n = sp.anchors.length;
8456
8964
  if (n < 2) return 0;
@@ -8660,13 +9168,13 @@ function hitTestVectorNode(node, p, tolerance = 0, parent = IDENTITY_MATRIX, opt
8660
9168
  }
8661
9169
  if (isVectorMaskGroup(node)) {
8662
9170
  const m = multiplyMatrices(nodeMatrix(node), parent);
8663
- const entered = !!_optionalChain([options, 'access', _241 => _241.entered, 'optionalAccess', _242 => _242.has, 'call', _243 => _243(node.id)]);
9171
+ const entered = !!_optionalChain([options, 'access', _255 => _255.entered, 'optionalAccess', _256 => _256.has, 'call', _257 => _257(node.id)]);
8664
9172
  if (!entered && isVectorMaskActive(node) && !vectorMaskContains(node, applyMatrix(invertMatrix(m), p), tolerance)) return false;
8665
9173
  const shown = !entered && hasOwnVectorAppearance(node) ? expandVectorAppearance(node).children : node.children;
8666
9174
  for (let i = shown.length - 1; i >= 1; i--) if (hitTestVectorNode(shown[i], p, tolerance, m, options)) return true;
8667
9175
  return entered && hitTestVectorMaskSource(node, p, tolerance, m, options);
8668
9176
  }
8669
- if (!(node.type === "group" && (!hasOwnVectorAppearance(node) || _optionalChain([options, 'access', _244 => _244.entered, 'optionalAccess', _245 => _245.has, 'call', _246 => _246(node.id)])))) node = expandVectorAppearance(node);
9177
+ if (!(node.type === "group" && (!hasOwnVectorAppearance(node) || _optionalChain([options, 'access', _258 => _258.entered, 'optionalAccess', _259 => _259.has, 'call', _260 => _260(node.id)])))) node = expandVectorAppearance(node);
8670
9178
  if (node.type === "group") {
8671
9179
  const m = multiplyMatrices(nodeMatrix(node), parent);
8672
9180
  return node.children.some((c) => hitTestVectorNode(c, p, tolerance, m, options));
@@ -8678,7 +9186,7 @@ function hitTestVectorNode(node, p, tolerance = 0, parent = IDENTITY_MATRIX, opt
8678
9186
  function hitTestVectorMaskSource(group, p, tolerance, m, options) {
8679
9187
  const source = group.children[0];
8680
9188
  if (source.visible === false) return false;
8681
- if (_optionalChain([group, 'access', _247 => _247.mask, 'optionalAccess', _248 => _248.type]) !== "clip") return hitTestVectorNode(source, p, tolerance, m, options);
9189
+ if (_optionalChain([group, 'access', _261 => _261.mask, 'optionalAccess', _262 => _262.type]) !== "clip") return hitTestVectorNode(source, p, tolerance, m, options);
8682
9190
  const paths = collectPathNodes(source).filter((n) => n.visible !== false);
8683
9191
  const pt2 = [p.x, p.y];
8684
9192
  return paths.some((n) => {
@@ -8727,23 +9235,24 @@ function mapAnchor(a, m) {
8727
9235
  }
8728
9236
  function bakeIntoGeometry(node, m) {
8729
9237
  if (isIdentityMatrix(m)) return node;
8730
- if (_optionalChain([node, 'access', _249 => _249.effects, 'optionalAccess', _250 => _250.length])) node = { ...node, effects: transformVectorEffects(node.effects, m, node) };
9238
+ if (_optionalChain([node, 'access', _263 => _263.effects, 'optionalAccess', _264 => _264.length])) node = { ...node, effects: transformVectorEffects(node.effects, m, node) };
8731
9239
  if (isVectorFrame(node)) return bakeFrame(node, m);
8732
9240
  if (node.type === "group") {
8733
9241
  const group = node;
8734
9242
  const children = group.children.map((c) => transformVectorNode(c, m));
8735
- const spine = _optionalChain([group, 'access', _251 => _251.blend, 'optionalAccess', _252 => _252.spine]);
8736
- if (!spine) return { ...group, children };
9243
+ const sym2 = group.symmetry ? { symmetry: transformVectorSymmetry(group.symmetry, m) } : {};
9244
+ const spine = _optionalChain([group, 'access', _265 => _265.blend, 'optionalAccess', _266 => _266.spine]);
9245
+ if (!spine) return { ...group, ...sym2, children };
8737
9246
  const moved = { closed: spine.closed, anchors: spine.anchors.map((a) => mapAnchor(a, m)) };
8738
9247
  return { ...group, children, blend: { ...group.blend, spine: moved } };
8739
9248
  }
8740
9249
  const path = node.type === "text" ? bakeVectorTextGeometry(node, m) : node;
8741
9250
  const flips = m[0] * m[3] - m[1] * m[2] < 0;
8742
- const mirrored = flips && _optionalChain([path, 'access', _253 => _253.strokeWidthProfile, 'optionalAccess', _254 => _254.length]);
9251
+ const mirrored = flips && _optionalChain([path, 'access', _267 => _267.strokeWidthProfile, 'optionalAccess', _268 => _268.length]);
8743
9252
  const layer = (l) => ({
8744
9253
  ...l,
8745
9254
  ...isVectorGradient(l.paint) || isVectorShadedPaint(l.paint) ? { paint: transformVectorPaint(l.paint, m) } : {},
8746
- ...flips && _optionalChain([l, 'access', _255 => _255.strokeWidthProfile, 'optionalAccess', _256 => _256.length]) ? { strokeWidthProfile: mirrorWidthProfile(l.strokeWidthProfile) } : {}
9255
+ ...flips && _optionalChain([l, 'access', _269 => _269.strokeWidthProfile, 'optionalAccess', _270 => _270.length]) ? { strokeWidthProfile: mirrorWidthProfile(l.strokeWidthProfile) } : {}
8747
9256
  });
8748
9257
  return {
8749
9258
  ...path,
@@ -8837,7 +9346,7 @@ function moveAnchorHandle(a, side, pos, breakHandles = false) {
8837
9346
  const dy = pos.y - a.y;
8838
9347
  const len2 = Math.hypot(dx, dy);
8839
9348
  if (type === "symmetric") next[other] = { x: a.x - dx, y: a.y - dy };
8840
- else if (type === "smooth" && len2 > EPS2) {
9349
+ else if (type === "smooth" && len2 > EPS3) {
8841
9350
  const o = a[other];
8842
9351
  const olen = o ? Math.hypot(o.x - a.x, o.y - a.y) : len2;
8843
9352
  next[other] = { x: a.x - dx / len2 * olen, y: a.y - dy / len2 * olen };
@@ -8867,15 +9376,15 @@ function convertAnchor(sp, index, type) {
8867
9376
  else if (prev && next) dir = { x: next.x - prev.x, y: next.y - prev.y };
8868
9377
  else if (next) dir = { x: next.x - a.x, y: next.y - a.y };
8869
9378
  else if (prev) dir = { x: a.x - prev.x, y: a.y - prev.y };
8870
- if (!dir || Math.hypot(dir.x, dir.y) < EPS2) return { anchors, closed: sp.closed };
9379
+ if (!dir || Math.hypot(dir.x, dir.y) < EPS3) return { anchors, closed: sp.closed };
8871
9380
  const dl = Math.hypot(dir.x, dir.y);
8872
9381
  const ux = dir.x / dl;
8873
9382
  const uy = dir.y / dl;
8874
9383
  lenIn = a.in && !isOnAnchor(a, a.in) ? Math.hypot(a.in.x - a.x, a.in.y - a.y) : prev ? Math.hypot(prev.x - a.x, prev.y - a.y) / 3 : 0;
8875
9384
  lenOut = a.out && !isOnAnchor(a, a.out) ? Math.hypot(a.out.x - a.x, a.out.y - a.y) : next ? Math.hypot(next.x - a.x, next.y - a.y) / 3 : 0;
8876
9385
  if (type === "symmetric") lenIn = lenOut = (lenIn + lenOut) / 2 || Math.max(lenIn, lenOut);
8877
- if (lenIn > EPS2) a.in = { x: a.x - ux * lenIn, y: a.y - uy * lenIn };
8878
- if (lenOut > EPS2) a.out = { x: a.x + ux * lenOut, y: a.y + uy * lenOut };
9386
+ if (lenIn > EPS3) a.in = { x: a.x - ux * lenIn, y: a.y - uy * lenIn };
9387
+ if (lenOut > EPS3) a.out = { x: a.x + ux * lenOut, y: a.y + uy * lenOut };
8879
9388
  a.type = type;
8880
9389
  return { anchors, closed: sp.closed };
8881
9390
  }
@@ -8906,448 +9415,171 @@ function removeAnchors(sp, indices) {
8906
9415
  return { anchors: sp.anchors.filter((_, i) => !drop.has(i)).map(cloneAnchor), closed: sp.closed };
8907
9416
  }
8908
9417
  function reverseSubpath(sp) {
8909
- const anchors = sp.anchors.slice().reverse().map((a) => {
8910
- const next = { x: a.x, y: a.y };
8911
- if (a.out) next.in = { ...a.out };
8912
- if (a.in) next.out = { ...a.in };
8913
- if (a.type) next.type = a.type;
8914
- if (a.corner) next.corner = { ...a.corner };
8915
- if (a.id) next.id = a.id;
8916
- return next;
8917
- });
8918
- return { anchors, closed: sp.closed };
8919
- }
8920
- var KAPPA2 = 0.5522847498307936;
8921
- function rectSubpath(b, radius = 0, kind) {
8922
- const { x, y, width: w, height: h } = b;
8923
- const sp = { anchors: [{ x, y }, { x: x + w, y }, { x: x + w, y: y + h }, { x, y: y + h }], closed: true };
8924
- return radius > 0 ? setSubpathCorners(sp, radius, kind) : sp;
8925
- }
8926
- function ellipseSubpath(b) {
8927
- const rx = b.width / 2;
8928
- const ry = b.height / 2;
8929
- const cx = b.x + rx;
8930
- const cy = b.y + ry;
8931
- const kx = rx * KAPPA2;
8932
- const ky = ry * KAPPA2;
8933
- return {
8934
- closed: true,
8935
- anchors: [
8936
- { x: cx, y: cy - ry, in: { x: cx - kx, y: cy - ry }, out: { x: cx + kx, y: cy - ry }, type: "symmetric" },
8937
- { x: cx + rx, y: cy, in: { x: cx + rx, y: cy - ky }, out: { x: cx + rx, y: cy + ky }, type: "symmetric" },
8938
- { x: cx, y: cy + ry, in: { x: cx + kx, y: cy + ry }, out: { x: cx - kx, y: cy + ry }, type: "symmetric" },
8939
- { x: cx - rx, y: cy, in: { x: cx - rx, y: cy + ky }, out: { x: cx - rx, y: cy - ky }, type: "symmetric" }
8940
- ]
8941
- };
8942
- }
8943
- function polygonSubpath(b, sides = 6) {
8944
- const n = Math.max(3, Math.round(sides));
8945
- const cx = b.x + b.width / 2;
8946
- const cy = b.y + b.height / 2;
8947
- const anchors = [];
8948
- for (let i = 0; i < n; i++) {
8949
- const t = -Math.PI / 2 + i * 2 * Math.PI / n;
8950
- anchors.push({ x: cx + Math.cos(t) * b.width / 2, y: cy + Math.sin(t) * b.height / 2 });
8951
- }
8952
- return { anchors, closed: true };
8953
- }
8954
- function starSubpath(b, points = 5, innerRatio = 0.5) {
8955
- const n = Math.max(3, Math.round(points));
8956
- const cx = b.x + b.width / 2;
8957
- const cy = b.y + b.height / 2;
8958
- const anchors = [];
8959
- for (let i = 0; i < n * 2; i++) {
8960
- const t = -Math.PI / 2 + i * Math.PI / n;
8961
- const r = i % 2 === 0 ? 1 : innerRatio;
8962
- anchors.push({ x: cx + Math.cos(t) * r * b.width / 2, y: cy + Math.sin(t) * r * b.height / 2 });
8963
- }
8964
- return { anchors, closed: true };
8965
- }
8966
- function lineSubpath(a, b) {
8967
- return { anchors: [{ x: a.x, y: a.y }, { x: b.x, y: b.y }], closed: false };
8968
- }
8969
- function roundSubpaths(subpaths, precision = 3) {
8970
- const f = 10 ** precision;
8971
- const r = (n) => Math.round(n * f) / f;
8972
- const rp = (p) => ({ x: r(p.x), y: r(p.y) });
8973
- return subpaths.map((sp) => ({
8974
- closed: sp.closed,
8975
- anchors: sp.anchors.map((a) => ({ ...cloneAnchor(a), x: r(a.x), y: r(a.y), ...a.in ? { in: rp(a.in) } : {}, ...a.out ? { out: rp(a.out) } : {} }))
8976
- }));
8977
- }
8978
-
8979
- // src/vector/pathEffects.ts
8980
- var EPS3 = 1e-9;
8981
- var degenerate2 = (s) => s.every((p) => Math.abs(p[0] - s[0][0]) < EPS3 && Math.abs(p[1] - s[0][1]) < EPS3);
8982
- function raise(seg) {
8983
- if (seg.length !== 3) return seg.map((p) => [p[0], p[1]]);
8984
- const [p0, p1, p2] = seg;
8985
- return [p0, [p0[0] + 2 / 3 * (p1[0] - p0[0]), p0[1] + 2 / 3 * (p1[1] - p0[1])], [p2[0] + 2 / 3 * (p1[0] - p2[0]), p2[1] + 2 / 3 * (p1[1] - p2[1])], p2];
8986
- }
8987
- function subsOf(path) {
8988
- return _chunkXGD3FSNCcjs.pathToContours.call(void 0, path).map((c) => ({ segs: _chunkXGD3FSNCcjs.closeContour.call(void 0, c).filter((s) => !degenerate2(s)).map(raise), closed: c.closed })).filter((s) => s.segs.length > 0);
8989
- }
8990
- var subsToPath = (subs) => _chunkXGD3FSNCcjs.contoursToPath.call(void 0, subs.map((s) => ({ segments: s.segs, closed: s.closed })));
8991
- var unit3 = (x, y) => {
8992
- const l = Math.hypot(x, y);
8993
- return l > 1e-12 && Number.isFinite(l) ? [x / l, y / l] : null;
8994
- };
8995
- function startTangent(s) {
8996
- for (let i = 1; i < s.length; i++) {
8997
- const u = unit3(s[i][0] - s[0][0], s[i][1] - s[0][1]);
8998
- if (u) return u;
8999
- }
9000
- return [1, 0];
9001
- }
9002
- function endTangent(s) {
9003
- const end = s[s.length - 1];
9004
- for (let i = s.length - 2; i >= 0; i--) {
9005
- const u = unit3(end[0] - s[i][0], end[1] - s[i][1]);
9006
- if (u) return u;
9007
- }
9008
- return [1, 0];
9009
- }
9010
- function tangentAt(s, t) {
9011
- if (t <= 1e-9) return startTangent(s);
9012
- if (t >= 1 - 1e-9) return endTangent(s);
9013
- const d = _chunkXGD3FSNCcjs.segmentDerivative.call(void 0, s, t);
9014
- return _nullishCoalesce(unit3(d[0], d[1]), () => ( startTangent(s)));
9015
- }
9016
- var perp2 = (v2) => [-v2[1], v2[0]];
9017
- function effectPathLength(path) {
9018
- let total = 0;
9019
- for (const s of subsOf(path)) for (const seg of s.segs) total += _chunkXGD3FSNCcjs.segmentLength.call(void 0, seg);
9020
- return total;
9021
- }
9022
- function effectPathVertexCount(path) {
9023
- return subsOf(path).reduce((n, s) => n + s.segs.length + (s.closed ? 0 : 1), 0);
9024
- }
9025
- var Measured = class {
9026
-
9027
-
9028
-
9029
- constructor(path) {
9030
- this.segs = subsOf(path).flatMap((s) => s.segs);
9031
- this.lens = this.segs.map((s) => _chunkXGD3FSNCcjs.segmentLength.call(void 0, s));
9032
- this.total = this.lens.reduce((a, b) => a + b, 0);
9033
- }
9034
- /**
9035
- * Appends the part between lengths `sa` and `sb`, continuing the last piece when this one
9036
- * starts where it ends (across the start of a closed path).
9037
- */
9038
- append(sa, sb, out) {
9039
- for (const piece of _chunkXGD3FSNCcjs.trimSegments.call(void 0, this.segs, sa, sb, this.lens)) {
9040
- if (degenerate2(piece)) continue;
9041
- const last = _optionalChain([out, 'access', _257 => _257[out.length - 1], 'optionalAccess', _258 => _258.segs]);
9042
- const end = _optionalChain([last, 'optionalAccess', _259 => _259[last.length - 1], 'optionalAccess', _260 => _260.at, 'call', _261 => _261(-1)]);
9043
- if (!end || Math.hypot(end[0] - piece[0][0], end[1] - piece[0][1]) > 1e-6) out.push({ segs: [piece], closed: false });
9044
- else last.push(piece);
9045
- }
9046
- }
9047
- };
9048
- function trimIntervals(start, end, offsetDegrees) {
9049
- let s = start / 100;
9050
- let e = end / 100;
9051
- if (!Number.isFinite(s) || !Number.isFinite(e)) return null;
9052
- if (s > e) [s, e] = [e, s];
9053
- s = Math.min(1, Math.max(0, s));
9054
- e = Math.min(1, Math.max(0, e));
9055
- if (e - s >= 1 - 1e-9) return null;
9056
- if (e - s <= 1e-9) return [];
9057
- const off = Number.isFinite(offsetDegrees) ? (offsetDegrees / 360 % 1 + 1) % 1 : 0;
9058
- s += off;
9059
- e += off;
9060
- if (e <= 1) return [[s, e]];
9061
- if (s >= 1) return [[s - 1, e - 1]];
9062
- return [
9063
- [s, 1],
9064
- [0, e - 1]
9065
- ];
9066
- }
9067
- function trimPaths(paths, start, end, offsetDegrees = 0) {
9068
- const iv = trimIntervals(start, end, offsetDegrees);
9069
- if (!iv) return paths.slice();
9070
- return paths.map((p) => {
9071
- const m = new Measured(p);
9072
- const out = [];
9073
- if (m.total > 0) for (const [a, b] of iv) m.append(a * m.total, b * m.total, out);
9074
- return subsToPath(out);
9075
- });
9076
- }
9077
- function trimPathsIndividually(paths, start, end, offsetDegrees = 0) {
9078
- const iv = trimIntervals(start, end, offsetDegrees);
9079
- if (!iv) return paths.slice();
9080
- const ms = paths.map((p) => new Measured(p));
9081
- const total = ms.reduce((n, m) => n + m.total, 0);
9082
- let base = 0;
9083
- return ms.map((m) => {
9084
- const out = [];
9085
- for (const [a, b] of iv) {
9086
- const la = Math.max(0, a * total - base);
9087
- const lb = Math.min(m.total, b * total - base);
9088
- if (lb > la) m.append(la, lb, out);
9089
- }
9090
- base += m.total;
9091
- return subsToPath(out);
9092
- });
9093
- }
9094
- function puckerBloatPaths(paths, amount) {
9095
- const a = amount / 100;
9096
- if (!a || !Number.isFinite(a)) return paths.slice();
9097
- return paths.map((p) => {
9098
- const verts = p.filter((c) => c.type !== "Z");
9099
- if (!verts.length) return p;
9100
- const cx = verts.reduce((s, c) => s + c.x, 0) / verts.length;
9101
- const cy = verts.reduce((s, c) => s + c.y, 0) / verts.length;
9102
- const mv = (x, y) => ({ x: x + (cx - x) * a, y: y + (cy - y) * a });
9103
- const mvh = (x, y) => ({ x: x + (x - cx) * a, y: y + (y - cy) * a });
9104
- const out = [];
9105
- let prev = { x: 0, y: 0 };
9106
- let start = { x: 0, y: 0 };
9107
- const curve = (c1, c2, q) => {
9108
- const h1 = mvh(c1.x, c1.y);
9109
- const h2 = mvh(c2.x, c2.y);
9110
- const e = mv(q.x, q.y);
9111
- out.push({ type: "C", x1: h1.x, y1: h1.y, x2: h2.x, y2: h2.y, x: e.x, y: e.y });
9112
- };
9113
- for (const c of p) {
9114
- switch (c.type) {
9115
- case "M": {
9116
- const e = mv(c.x, c.y);
9117
- out.push({ type: "M", x: e.x, y: e.y });
9118
- prev = start = { x: c.x, y: c.y };
9119
- break;
9120
- }
9121
- case "L":
9122
- curve(prev, c, c);
9123
- prev = { x: c.x, y: c.y };
9124
- break;
9125
- case "Q": {
9126
- const c1 = { x: prev.x + 2 / 3 * (c.x1 - prev.x), y: prev.y + 2 / 3 * (c.y1 - prev.y) };
9127
- const c2 = { x: c.x + 2 / 3 * (c.x1 - c.x), y: c.y + 2 / 3 * (c.y1 - c.y) };
9128
- curve(c1, c2, c);
9129
- prev = { x: c.x, y: c.y };
9130
- break;
9131
- }
9132
- case "C":
9133
- curve({ x: c.x1, y: c.y1 }, { x: c.x2, y: c.y2 }, c);
9134
- prev = { x: c.x, y: c.y };
9135
- break;
9136
- case "Z":
9137
- if (Math.hypot(prev.x - start.x, prev.y - start.y) > EPS3) curve(prev, start, start);
9138
- out.push({ type: "Z" });
9139
- prev = start;
9140
- break;
9141
- }
9142
- }
9143
- return out;
9144
- });
9145
- }
9146
- function roundCornerPaths(paths, radius) {
9147
- if (!(radius > 0) || !Number.isFinite(radius)) return paths.slice();
9148
- return paths.map((p) => subpathsToBezier(bezierToSubpaths(p).map((sp) => setSubpathCorners(sp, radius))));
9149
- }
9150
- function offsetPaths(paths, amount, join = "miter", miterLimit = 4, copies = 1, copyOffset = 0) {
9151
- const n = Math.min(1e3, Math.max(1, Math.round(Number.isFinite(copies) ? copies : 1)));
9152
- return paths.map((p) => {
9153
- const out = [];
9154
- for (let i = 0; i < n; i++) out.push(..._chunkXGD3FSNCcjs.offsetPath.call(void 0, p, amount * (i + 1 + copyOffset), { join, miterLimit }));
9155
- return out;
9418
+ const anchors = sp.anchors.slice().reverse().map((a) => {
9419
+ const next = { x: a.x, y: a.y };
9420
+ if (a.out) next.in = { ...a.out };
9421
+ if (a.in) next.out = { ...a.in };
9422
+ if (a.type) next.type = a.type;
9423
+ if (a.corner) next.corner = { ...a.corner };
9424
+ if (a.id) next.id = a.id;
9425
+ return next;
9156
9426
  });
9427
+ return { anchors, closed: sp.closed };
9157
9428
  }
9158
- function twistPaths(paths, angle, center) {
9159
- let rmax = 0;
9160
- for (const p of paths) for (const c of p) if (c.type !== "Z") rmax = Math.max(rmax, Math.hypot(c.x - center.x, c.y - center.y));
9161
- const a = angle * Math.PI / 180;
9162
- if (!a || rmax <= 1e-9 || !Number.isFinite(a)) return paths.slice();
9163
- const k = a / rmax;
9164
- const rot = (v2, th) => {
9165
- const s = Math.sin(th);
9166
- const co = Math.cos(th);
9167
- return [v2[0] * co - v2[1] * s, v2[0] * s + v2[1] * co];
9168
- };
9169
- const map = (p) => {
9170
- const v2 = [p[0] - center.x, p[1] - center.y];
9171
- const r = rot(v2, k * Math.hypot(v2[0], v2[1]));
9172
- return [center.x + r[0], center.y + r[1]];
9173
- };
9174
- const jac = (p, dv) => {
9175
- const v2 = [p[0] - center.x, p[1] - center.y];
9176
- const r = Math.hypot(v2[0], v2[1]);
9177
- let w = dv;
9178
- if (r > 1e-12) {
9179
- const f = k * (v2[0] * dv[0] + v2[1] * dv[1]) / r;
9180
- w = [dv[0] - v2[1] * f, dv[1] + v2[0] * f];
9181
- }
9182
- return rot(w, k * r);
9429
+ var KAPPA2 = 0.5522847498307936;
9430
+ function rectSubpath(b, radius = 0, kind) {
9431
+ const { x, y, width: w, height: h } = b;
9432
+ const sp = { anchors: [{ x, y }, { x: x + w, y }, { x: x + w, y: y + h }, { x, y: y + h }], closed: true };
9433
+ return radius > 0 ? setSubpathCorners(sp, radius, kind) : sp;
9434
+ }
9435
+ function ellipseSubpath(b) {
9436
+ const rx = b.width / 2;
9437
+ const ry = b.height / 2;
9438
+ const cx = b.x + rx;
9439
+ const cy = b.y + ry;
9440
+ const kx = rx * KAPPA2;
9441
+ const ky = ry * KAPPA2;
9442
+ return {
9443
+ closed: true,
9444
+ anchors: [
9445
+ { x: cx, y: cy - ry, in: { x: cx - kx, y: cy - ry }, out: { x: cx + kx, y: cy - ry }, type: "symmetric" },
9446
+ { x: cx + rx, y: cy, in: { x: cx + rx, y: cy - ky }, out: { x: cx + rx, y: cy + ky }, type: "symmetric" },
9447
+ { x: cx, y: cy + ry, in: { x: cx + kx, y: cy + ry }, out: { x: cx - kx, y: cy + ry }, type: "symmetric" },
9448
+ { x: cx - rx, y: cy, in: { x: cx - rx, y: cy + ky }, out: { x: cx - rx, y: cy - ky }, type: "symmetric" }
9449
+ ]
9183
9450
  };
9184
- return paths.map((p) => {
9185
- const out = [];
9186
- for (const sub5 of subsOf(p)) {
9187
- const segs = [];
9188
- for (const seg of sub5.segs) {
9189
- const cubic = seg.length === 2 ? [seg[0], seg[0], seg[1], seg[1]] : seg;
9190
- const len2 = _chunkXGD3FSNCcjs.segmentLength.call(void 0, seg);
9191
- const m = Math.min(64, Math.max(1, Math.ceil(Math.abs(a) * len2 / rmax / 0.15 + len2 / 50)));
9192
- for (let i = 0; i < m; i++) {
9193
- const q = _chunkXGD3FSNCcjs.subSegment.call(void 0, cubic, i / m, (i + 1) / m);
9194
- const p0 = map(q[0]);
9195
- const p3 = map(q[3]);
9196
- const h1 = jac(q[0], [q[1][0] - q[0][0], q[1][1] - q[0][1]]);
9197
- const h2 = jac(q[3], [q[2][0] - q[3][0], q[2][1] - q[3][1]]);
9198
- segs.push([p0, [p0[0] + h1[0], p0[1] + h1[1]], [p3[0] + h2[0], p3[1] + h2[1]], p3]);
9199
- }
9200
- }
9201
- out.push({ segs, closed: sub5.closed });
9202
- }
9203
- return subsToPath(out);
9204
- });
9205
9451
  }
9206
- function resample(sub5, m) {
9207
- const segs = sub5.segs;
9208
- const n = segs.length;
9209
- const lens = segs.map((s) => _chunkXGD3FSNCcjs.segmentLength.call(void 0, s));
9210
- const out = [];
9211
- for (let j = 0; j < n; j++) {
9212
- const piece = lens[j] / m;
9213
- for (let k = 0; k < m; k++) {
9214
- if (k === 0) {
9215
- const tout = startTangent(segs[j]);
9216
- const prev = sub5.closed || j > 0 ? (j + n - 1) % n : null;
9217
- let tan = tout;
9218
- if (prev !== null) {
9219
- const tin = endTangent(segs[prev]);
9220
- tan = _nullishCoalesce(unit3(tin[0] + tout[0], tin[1] + tout[1]), () => ( tout));
9221
- }
9222
- out.push({ p: segs[j][0], tan, lenPrev: prev === null ? 0 : lens[prev] / m, lenNext: piece });
9223
- } else {
9224
- const t = _chunkXGD3FSNCcjs.segmentParamAtLength.call(void 0, segs[j], piece * k, lens[j]);
9225
- out.push({ p: _chunkXGD3FSNCcjs.segmentPoint.call(void 0, segs[j], t), tan: tangentAt(segs[j], t), lenPrev: piece, lenNext: piece });
9226
- }
9227
- }
9228
- }
9229
- if (!sub5.closed) {
9230
- const last = segs[n - 1];
9231
- out.push({ p: last[last.length - 1], tan: endTangent(last), lenPrev: lens[n - 1] / m, lenNext: 0 });
9452
+ function polygonSubpath(b, sides = 6) {
9453
+ const n = Math.max(3, Math.round(sides));
9454
+ const cx = b.x + b.width / 2;
9455
+ const cy = b.y + b.height / 2;
9456
+ const anchors = [];
9457
+ for (let i = 0; i < n; i++) {
9458
+ const t = -Math.PI / 2 + i * 2 * Math.PI / n;
9459
+ anchors.push({ x: cx + Math.cos(t) * b.width / 2, y: cy + Math.sin(t) * b.height / 2 });
9232
9460
  }
9233
- return out;
9461
+ return { anchors, closed: true };
9234
9462
  }
9235
- function emit(samples, disp, closed, smooth, handle) {
9236
- const n = samples.length;
9237
- if (!n) return null;
9238
- const pt2 = (i) => [samples[i].p[0] + disp[i][0], samples[i].p[1] + disp[i][1]];
9239
- const segs = [];
9240
- const count = closed ? n : n - 1;
9241
- for (let i = 0; i < count; i++) {
9242
- const j = (i + 1) % n;
9243
- const a = samples[i];
9244
- const b = samples[j];
9245
- const p = pt2(i);
9246
- const q = pt2(j);
9247
- if (smooth) segs.push([p, [p[0] + a.tan[0] * a.lenNext * handle, p[1] + a.tan[1] * a.lenNext * handle], [q[0] - b.tan[0] * b.lenPrev * handle, q[1] - b.tan[1] * b.lenPrev * handle], q]);
9248
- else segs.push([p, q]);
9463
+ function starSubpath(b, points = 5, innerRatio = 0.5) {
9464
+ const n = Math.max(3, Math.round(points));
9465
+ const cx = b.x + b.width / 2;
9466
+ const cy = b.y + b.height / 2;
9467
+ const anchors = [];
9468
+ for (let i = 0; i < n * 2; i++) {
9469
+ const t = -Math.PI / 2 + i * Math.PI / n;
9470
+ const r = i % 2 === 0 ? 1 : innerRatio;
9471
+ anchors.push({ x: cx + Math.cos(t) * r * b.width / 2, y: cy + Math.sin(t) * r * b.height / 2 });
9249
9472
  }
9250
- if (!segs.length) return null;
9251
- return { segs, closed };
9252
- }
9253
- function zigzagPaths(paths, size, ridges, smooth = false) {
9254
- const m = Math.min(1e3, Math.max(0, Math.round(Number.isFinite(ridges) ? ridges : 0))) + 1;
9255
- return paths.map((p) => {
9256
- const out = [];
9257
- for (const sub5 of subsOf(p)) {
9258
- const s = resample(sub5, m);
9259
- const disp = s.map((x, i) => {
9260
- const n = perp2(x.tan);
9261
- const d = i % 2 === 0 ? size : -size;
9262
- return [n[0] * d, n[1] * d];
9263
- });
9264
- const e = emit(s, disp, sub5.closed, smooth, 0.36);
9265
- if (e) out.push(e);
9266
- }
9267
- return subsToPath(out);
9268
- });
9473
+ return { anchors, closed: true };
9269
9474
  }
9270
- var MASK64 = (1n << 64n) - 1n;
9271
- function splitmix(x) {
9272
- x = x + 0x9e3779b97f4a7c15n & MASK64;
9273
- let z = x;
9274
- z = (z ^ z >> 30n) * 0xbf58476d1ce4e5b9n & MASK64;
9275
- z = (z ^ z >> 27n) * 0x94d049bb133111ebn & MASK64;
9276
- return z ^ z >> 31n;
9475
+ function lineSubpath(a, b) {
9476
+ return { anchors: [{ x: a.x, y: a.y }, { x: b.x, y: b.y }], closed: false };
9277
9477
  }
9278
- function hash(seed, idx, t) {
9279
- const h = splitmix(splitmix(splitmix(seed) ^ idx) ^ BigInt.asUintN(64, BigInt(t)));
9280
- return Number(h >> 11n) / 2 ** 53 * 2 - 1;
9478
+ function roundSubpaths(subpaths, precision = 3) {
9479
+ const f = 10 ** precision;
9480
+ const r = (n) => Math.round(n * f) / f;
9481
+ const rp = (p) => ({ x: r(p.x), y: r(p.y) });
9482
+ return subpaths.map((sp) => ({
9483
+ closed: sp.closed,
9484
+ anchors: sp.anchors.map((a) => ({ ...cloneAnchor(a), x: r(a.x), y: r(a.y), ...a.in ? { in: rp(a.in) } : {}, ...a.out ? { out: rp(a.out) } : {} }))
9485
+ }));
9281
9486
  }
9282
- function noise(seed, idx, t) {
9283
- const i = Math.floor(t);
9284
- const f = t - i;
9285
- const p0 = hash(seed, idx, i - 1);
9286
- const p1 = hash(seed, idx, i);
9287
- const p2 = hash(seed, idx, i + 1);
9288
- const p3 = hash(seed, idx, i + 2);
9289
- const v2 = 0.5 * (2 * p1 + (-p0 + p2) * f + (2 * p0 - 5 * p1 + 4 * p2 - p3) * f * f + (-p0 + 3 * p1 - 3 * p2 + p3) * f * f * f);
9290
- return Math.min(1, Math.max(-1, v2));
9487
+
9488
+ // src/vector/symmetry.ts
9489
+ function isVectorSymmetryGroup(node) {
9490
+ return _optionalChain([node, 'optionalAccess', _271 => _271.type]) === "group" && !!node.symmetry && !node.blend && !node.liveBoolean && !node.mask && !node.frame;
9291
9491
  }
9292
- function wigglePaths(paths, w) {
9293
- if (!w.size || !Number.isFinite(w.size)) return paths.slice();
9294
- const m = Math.min(1e3, Math.max(0, Math.round(Number.isFinite(w.detail) ? w.detail : 0))) + 1;
9295
- const seed = BigInt.asUintN(64, BigInt(Math.round(Number.isFinite(w.seed) ? w.seed : 0)));
9296
- const t = (Number.isFinite(w.time) ? w.time : 0) * (Number.isFinite(w.speed) ? w.speed : 0) + (Number.isFinite(w.phase) ? w.phase : 0) / 360;
9297
- const corr = Math.min(1, Math.max(0, (Number.isFinite(w.correlation) ? w.correlation : 0) / 100));
9298
- const sx = noise(seed, MASK64, t);
9299
- const sy = noise(seed, MASK64 - 1n, t);
9300
- let idx = 0;
9301
- return paths.map((p) => {
9492
+ var rad = (deg) => deg * Math.PI / 180;
9493
+ var exact = (v2) => Math.abs(v2) < 1e-12 ? 0 : v2;
9494
+ var around = (c, m) => multiplyMatrices(multiplyMatrices([1, 0, 0, 1, -c.x, -c.y], m), [1, 0, 0, 1, c.x, c.y]);
9495
+ var reflect = (c, deg) => {
9496
+ const a = 2 * rad(deg);
9497
+ return around(c, [exact(Math.cos(a)), exact(Math.sin(a)), exact(Math.sin(a)), exact(-Math.cos(a)), 0, 0]);
9498
+ };
9499
+ var turn = (c, deg) => around(c, [exact(Math.cos(rad(deg))), exact(Math.sin(rad(deg))), exact(-Math.sin(rad(deg))), exact(Math.cos(rad(deg))), 0, 0]);
9500
+ var AXIS = { horizontal: [0], vertical: [90], diagonal: [45], dual: [90, 0] };
9501
+ function vectorSymmetryMatrices(s) {
9502
+ const c = s.center;
9503
+ const r = _nullishCoalesce(s.rotation, () => ( 0));
9504
+ if (s.mode === "radial") {
9505
+ const n = Math.min(64, Math.max(2, Math.round(_nullishCoalesce(s.copies, () => ( 6)))));
9302
9506
  const out = [];
9303
- for (const sub5 of subsOf(p)) {
9304
- const s = resample(sub5, m);
9305
- const disp = s.map(() => {
9306
- const i = BigInt(idx);
9307
- const ox = noise(seed, i * 2n, t + idx * 0.37);
9308
- const oy = noise(seed, i * 2n + 1n, t + idx * 0.61);
9309
- idx++;
9310
- return [(sx * corr + ox * (1 - corr)) * w.size, (sy * corr + oy * (1 - corr)) * w.size];
9311
- });
9312
- const e = emit(s, disp, sub5.closed, w.smooth, 1 / 3);
9313
- if (e) out.push(e);
9314
- }
9315
- return subsToPath(out);
9316
- });
9507
+ for (let k = 1; k < n; k++) out.push(turn(c, 360 * k / n));
9508
+ if (s.mirror) for (let k = 0; k < n; k++) out.push(reflect(c, r + 180 * k / n));
9509
+ return out;
9510
+ }
9511
+ const axes = AXIS[s.mode].map((a) => reflect(c, a + r));
9512
+ return s.mode === "dual" ? [...axes, turn(c, 180)] : axes;
9317
9513
  }
9318
- var MERGE_OPS = { add: "union", subtract: "difference", intersect: "intersection", exclude: "xor" };
9319
- function mergePaths(paths, mode = "merge") {
9320
- if (mode === "merge" || !(mode in MERGE_OPS)) return paths.flat();
9321
- const inputs = paths.filter((p) => p.length > 0).map((path) => ({ path, fillRule: "nonzero" }));
9322
- if (!inputs.length) return [];
9323
- return _chunkXGD3FSNCcjs.pathBoolean.call(void 0, MERGE_OPS[mode], inputs).path;
9514
+ function renamed(node, k) {
9515
+ const id = `${node.id}~sym${k}`;
9516
+ if (node.type === "group") return { ...node, id, children: node.children.map((c) => renamed(c, k)) };
9517
+ return { ...node, id };
9324
9518
  }
9325
- function vectorRepeaterCopies(r, pivot) {
9326
- const copies = Math.max(0, Number.isFinite(r.copies) ? Math.min(r.copies, 1e3) : 0);
9327
- const n = Math.ceil(copies);
9328
- const offset = Number.isFinite(r.offset) ? r.offset : 0;
9329
- const so = (_nullishCoalesce(r.startOpacity, () => ( 100))) / 100;
9330
- const eo = (_nullishCoalesce(r.endOpacity, () => ( 100))) / 100;
9331
- const fract = copies - Math.floor(copies);
9519
+ var drawnCache2 = /* @__PURE__ */ new WeakMap();
9520
+ function vectorSymmetryDrawn(node) {
9521
+ let hit = drawnCache2.get(node);
9522
+ if (hit) return hit;
9523
+ const { symmetry, ...group } = node;
9524
+ const copies = vectorSymmetryMatrices(symmetry).flatMap((m, k) => node.children.map((c) => ({ ...renamed(transformVectorNode(c, m), k + 1), locked: true })));
9525
+ hit = { ...group, children: [...node.children, ...copies] };
9526
+ drawnCache2.set(node, hit);
9527
+ return hit;
9528
+ }
9529
+ function vectorSymmetryAxes(s, box) {
9530
+ const r = _nullishCoalesce(s.rotation, () => ( 0));
9531
+ const dirs = s.mode === "radial" ? Array.from({ length: Math.min(64, Math.max(2, Math.round(_nullishCoalesce(s.copies, () => ( 6))))) }, (_, k) => r - 90 + 360 * k / Math.min(64, Math.max(2, Math.round(_nullishCoalesce(s.copies, () => ( 6)))))) : AXIS[s.mode].map((a) => a + r);
9332
9532
  const out = [];
9333
- for (let i = 0; i < n; i++) {
9334
- const k = i + offset;
9335
- let m = translateMatrix(-pivot.x, -pivot.y);
9336
- m = multiplyMatrices(m, scaleMatrix(Math.pow((_nullishCoalesce(_optionalChain([r, 'access', _262 => _262.scale, 'optionalAccess', _263 => _263.x]), () => ( 100))) / 100, k), Math.pow((_nullishCoalesce(_optionalChain([r, 'access', _264 => _264.scale, 'optionalAccess', _265 => _265.y]), () => ( 100))) / 100, k)));
9337
- m = multiplyMatrices(m, rotateMatrix((_nullishCoalesce(r.rotation, () => ( 0))) * k));
9338
- m = multiplyMatrices(m, translateMatrix(pivot.x + (_nullishCoalesce(_optionalChain([r, 'access', _266 => _266.position, 'optionalAccess', _267 => _267.x]), () => ( 0))) * k, pivot.y + (_nullishCoalesce(_optionalChain([r, 'access', _268 => _268.position, 'optionalAccess', _269 => _269.y]), () => ( 0))) * k));
9339
- const t = n > 1 ? i / (n - 1) : 0;
9340
- const partial = i + 1 === n && fract > 0 ? fract : 1;
9341
- out.push({ index: i, matrix: m, opacity: Math.min(1, Math.max(0, (so + (eo - so) * t) * partial)) });
9533
+ for (const deg of dirs) {
9534
+ const d = { x: Math.cos(rad(deg)), y: Math.sin(rad(deg)) };
9535
+ let lo = s.mode === "radial" ? 0 : -Infinity;
9536
+ let hi = Infinity;
9537
+ let inside = true;
9538
+ for (const [o, dv, min, max] of [
9539
+ [s.center.x, d.x, box.x, box.x + box.width],
9540
+ [s.center.y, d.y, box.y, box.y + box.height]
9541
+ ]) {
9542
+ if (Math.abs(dv) < 1e-12) {
9543
+ if (o < min || o > max) inside = false;
9544
+ } else {
9545
+ const a = (min - o) / dv;
9546
+ const b = (max - o) / dv;
9547
+ lo = Math.max(lo, Math.min(a, b));
9548
+ hi = Math.min(hi, Math.max(a, b));
9549
+ }
9550
+ }
9551
+ if (inside && Number.isFinite(lo) && Number.isFinite(hi) && hi > lo) out.push([{ x: s.center.x + lo * d.x, y: s.center.y + lo * d.y }, { x: s.center.x + hi * d.x, y: s.center.y + hi * d.y }]);
9342
9552
  }
9343
9553
  return out;
9344
9554
  }
9345
- function repeatPaths(paths, r, pivot) {
9346
- return vectorRepeaterCopies(r, pivot).map((copy) => ({ copy, paths: paths.map((p) => _chunkXGD3FSNCcjs.transformBezierPath.call(void 0, p, copy.matrix)) }));
9555
+ function sanitizeVectorSymmetry(value) {
9556
+ if (!value || typeof value !== "object") return null;
9557
+ const r = value;
9558
+ if (!VECTOR_SYMMETRY_MODES.includes(r.mode)) return null;
9559
+ const c = r.center;
9560
+ if (!c || !Number.isFinite(c.x) || !Number.isFinite(c.y)) return null;
9561
+ const out = { mode: r.mode, center: { x: c.x, y: c.y } };
9562
+ if (typeof r.rotation === "number" && Number.isFinite(r.rotation) && r.rotation % 360 !== 0) out.rotation = (r.rotation % 360 + 360) % 360;
9563
+ if (out.mode === "radial") {
9564
+ if (typeof r.copies === "number" && Number.isFinite(r.copies)) out.copies = Math.min(64, Math.max(2, Math.round(r.copies)));
9565
+ if (r.mirror === true) out.mirror = true;
9566
+ }
9567
+ return out;
9347
9568
  }
9348
- function pathsCenter(paths) {
9349
- const b = _chunkXGD3FSNCcjs.bezierPathBounds.call(void 0, paths.flat());
9350
- return b ? { x: (b.minX + b.maxX) / 2, y: (b.minY + b.maxY) / 2 } : { x: 0, y: 0 };
9569
+ var VECTOR_SYMMETRY_MODE_LABELS = {
9570
+ vertical: "Mirror left / right",
9571
+ horizontal: "Mirror top / bottom",
9572
+ dual: "Four quarters",
9573
+ diagonal: "Mirror diagonally",
9574
+ radial: "Radial"
9575
+ };
9576
+ function transformVectorSymmetry(s, m) {
9577
+ const center = { x: m[0] * s.center.x + m[2] * s.center.y + m[4], y: m[1] * s.center.x + m[3] * s.center.y + m[5] };
9578
+ const det = m[0] * m[3] - m[1] * m[2];
9579
+ const angle = Math.atan2(m[1], m[0]) * 180 / Math.PI;
9580
+ const rotation = det < 0 ? -(_nullishCoalesce(s.rotation, () => ( 0))) + 2 * angle : (_nullishCoalesce(s.rotation, () => ( 0))) + angle;
9581
+ const norm = (rotation % 360 + 360) % 360;
9582
+ return { ...s, center, ...Math.abs(norm) > 1e-9 && Math.abs(norm - 360) > 1e-9 ? { rotation: norm } : { rotation: void 0 } };
9351
9583
  }
9352
9584
 
9353
9585
 
@@ -9793,5 +10025,14 @@ function pathsCenter(paths) {
9793
10025
 
9794
10026
 
9795
10027
 
9796
- exports.isVectorMeshGradient = isVectorMeshGradient; exports.isVectorFreeformGradient = isVectorFreeformGradient; exports.isVectorShadedPaint = isVectorShadedPaint; exports.vectorRgbaToCss = vectorRgbaToCss; exports.VECTOR_MESH_MAX = VECTOR_MESH_MAX; exports.createVectorMeshGradient = createVectorMeshGradient; exports.vectorMeshPointAt = vectorMeshPointAt; exports.vectorMeshColorAt = vectorMeshColorAt; exports.vectorMeshLines = vectorMeshLines; exports.vectorFreeformSpreadScale = vectorFreeformSpreadScale; exports.vectorFreeformLineSegments = vectorFreeformLineSegments; exports.vectorFreeformField = vectorFreeformField; exports.sampleVectorFreeform = sampleVectorFreeform; exports.autoVectorFreeformGradient = autoVectorFreeformGradient; exports.vectorShadedSvgDefs = vectorShadedSvgDefs; exports.mapVectorShadedPaint = mapVectorShadedPaint; exports.transformVectorShadedPaint = transformVectorShadedPaint; exports.sanitizeVectorShadedPaint = sanitizeVectorShadedPaint; exports.removeVectorFreeformPoint = removeVectorFreeformPoint; exports.nearestVectorShadingPoint = nearestVectorShadingPoint; exports.VECTOR_CORNER_KINDS = VECTOR_CORNER_KINDS; exports.VECTOR_GRADIENT_TYPES = VECTOR_GRADIENT_TYPES; exports.VECTOR_GRADIENT_SPREADS = VECTOR_GRADIENT_SPREADS; exports.VECTOR_GRADIENT_INTERPOLATIONS = VECTOR_GRADIENT_INTERPOLATIONS; exports.VECTOR_STROKE_GRADIENT_MODES = VECTOR_STROKE_GRADIENT_MODES; exports.VECTOR_ARROWHEADS = VECTOR_ARROWHEADS; exports.VECTOR_BLEND_MODES = VECTOR_BLEND_MODES; exports.VECTOR_HORIZONTAL_RESIZING = VECTOR_HORIZONTAL_RESIZING; exports.VECTOR_VERTICAL_RESIZING = VECTOR_VERTICAL_RESIZING; exports.VECTOR_CONNECTOR_SIDES = VECTOR_CONNECTOR_SIDES; exports.VECTOR_CONNECTOR_ROUTES = VECTOR_CONNECTOR_ROUTES; exports.VECTOR_BLEND_SPACINGS = VECTOR_BLEND_SPACINGS; exports.VECTOR_MASK_TYPES = VECTOR_MASK_TYPES; exports.VECTOR_TEXT_ALIGNS = VECTOR_TEXT_ALIGNS; exports.VECTOR_PATH_TEXT_BASELINES = VECTOR_PATH_TEXT_BASELINES; exports.VECTOR_CONSTRAINT_KINDS = VECTOR_CONSTRAINT_KINDS; exports.VECTOR_TOOLS = VECTOR_TOOLS; exports.VECTOR_TRANSFORM_HANDLES = VECTOR_TRANSFORM_HANDLES; exports.VECTOR_PATHFINDER_OPERATIONS = VECTOR_PATHFINDER_OPERATIONS; exports.VECTOR_EFFECT_TYPES = VECTOR_EFFECT_TYPES; exports.VECTOR_MERGE_MODES = VECTOR_MERGE_MODES; exports.VECTOR_FILTER_TYPES = VECTOR_FILTER_TYPES; exports.isVectorGradient = isVectorGradient; exports.parseVectorColor = parseVectorColor; exports.VECTOR_GRADIENT_MIN_STOPS = VECTOR_GRADIENT_MIN_STOPS; exports.gradientMidpointRemap = gradientMidpointRemap; exports.sortedVectorGradientStops = sortedVectorGradientStops; exports.vectorGradientNeedsExpansion = vectorGradientNeedsExpansion; exports.vectorGradientRamp = vectorGradientRamp; exports.sampleVectorGradient = sampleVectorGradient; exports.expandVectorGradientStops = expandVectorGradientStops; exports.samplePlainStops = samplePlainStops; exports.reverseVectorGradient = reverseVectorGradient; exports.insertVectorGradientStop = insertVectorGradientStop; exports.moveVectorGradientStop = moveVectorGradientStop; exports.removeVectorGradientStop = removeVectorGradientStop; exports.vectorGradientMidpointPosition = vectorGradientMidpointPosition; exports.vectorGradientMidpointFromPosition = vectorGradientMidpointFromPosition; exports.spanVectorGradientStops = spanVectorGradientStops; exports.hasExplicitGradientGeometry = hasExplicitGradientGeometry; exports.vectorGradientPoints = vectorGradientPoints; exports.vectorBoxMatrix = vectorBoxMatrix; exports.vectorGradientUnitsMatrix = vectorGradientUnitsMatrix; exports.vectorGradientMatrix = vectorGradientMatrix; exports.vectorGradientFocalParam = vectorGradientFocalParam; exports.vectorGradientParam = vectorGradientParam; exports.applyVectorGradientSpread = applyVectorGradientSpread; exports.vectorGradientTAt = vectorGradientTAt; exports.sampleVectorGradientAt = sampleVectorGradientAt; exports.vectorGradientAspect = vectorGradientAspect; exports.explicitVectorGradient = explicitVectorGradient; exports.pinVectorGradient = pinVectorGradient; exports.transformVectorGradient = transformVectorGradient; exports.mapVectorGradient = mapVectorGradient; exports.mapVectorPaint = mapVectorPaint; exports.transformVectorPaint = transformVectorPaint; exports.isCentredVectorGradient = isCentredVectorGradient; exports.vectorGradientHandles = vectorGradientHandles; exports.moveVectorGradientHandle = moveVectorGradientHandle; exports.setVectorGradientVector = setVectorGradientVector; exports.VECTOR_GRADIENT_MAX_PERIODS = VECTOR_GRADIENT_MAX_PERIODS; exports.periodicVectorGradientStops = periodicVectorGradientStops; exports.expandVectorGradientSpread = expandVectorGradientSpread; exports.vectorGradientArea = vectorGradientArea; exports.patternAttrs = patternAttrs; exports.vectorGradientSvgDefs = vectorGradientSvgDefs; exports.sampleVectorPaintDefAt = sampleVectorPaintDefAt; exports.sanitizeVectorGradient = sanitizeVectorGradient; exports.convertVectorGradient = convertVectorGradient; exports.defaultVectorGradient = defaultVectorGradient; exports.applyVectorGradientPatch = applyVectorGradientPatch; exports.IDENTITY_MATRIX = IDENTITY_MATRIX; exports.multiplyMatrices = multiplyMatrices; exports.translateMatrix = translateMatrix; exports.scaleMatrix = scaleMatrix; exports.rotateMatrix = rotateMatrix; exports.matrixAbout = matrixAbout; exports.skewMatrix = skewMatrix; exports.applyMatrix = applyMatrix; exports.isIdentityMatrix = isIdentityMatrix; exports.invertMatrix = invertMatrix; exports.applyMatrixLinear = applyMatrixLinear; exports.matrixRotation = matrixRotation; exports.decomposeRigid = decomposeRigid; exports.vectorCornerAt = vectorCornerAt; exports.vectorCorners = vectorCorners; exports.cornerSetback = cornerSetback; exports.fitCornerRadius = fitCornerRadius; exports.cornerBisectorPoint = cornerBisectorPoint; exports.cornerRadiusChange = cornerRadiusChange; exports.hasVectorCorners = hasVectorCorners; exports.expandVectorCornersOf = expandVectorCornersOf; exports.expandVectorCorners = expandVectorCorners; exports.setAnchorCorner = setAnchorCorner; exports.nextVectorCornerKind = nextVectorCornerKind; exports.setSubpathCorners = setSubpathCorners; exports.VECTOR_WIDTH_PROFILE_MAX_POINTS = VECTOR_WIDTH_PROFILE_MAX_POINTS; exports.VECTOR_WIDTH_PROFILE_MAX_SCALE = VECTOR_WIDTH_PROFILE_MAX_SCALE; exports.VECTOR_WIDTH_SAME_T = VECTOR_WIDTH_SAME_T; exports.VECTOR_WIDTH_PRESETS = VECTOR_WIDTH_PRESETS; exports.VECTOR_WIDTH_PRESET_IDS = VECTOR_WIDTH_PRESET_IDS; exports.sanitizeWidthProfile = sanitizeWidthProfile; exports.isUniformWidthProfile = isUniformWidthProfile; exports.widthProfileAt = widthProfileAt; exports.widthProfileMaxScale = widthProfileMaxScale; exports.widthProfilePreset = widthProfilePreset; exports.widthProfilePresetId = widthProfilePresetId; exports.reverseWidthProfile = reverseWidthProfile; exports.mirrorWidthProfile = mirrorWidthProfile; exports.insertWidthPoint = insertWidthPoint; exports.setWidthPoint = setWidthPoint; exports.removeWidthPoints = removeWidthPoints; exports.taperWaveFactor = taperWaveFactor; exports.generateWidthProfile = generateWidthProfile; exports.VECTOR_PRESSURE_NOMINAL = VECTOR_PRESSURE_NOMINAL; exports.pressureWidthProfile = pressureWidthProfile; exports.dashIntervals = dashIntervals; exports.variableStrokeRings = variableStrokeRings; exports.variableStrokeOutline = variableStrokeOutline; exports.nearestStrokePosition = nearestStrokePosition; exports.strokePositionPoint = strokePositionPoint; exports.isClosedBezierShape = isClosedBezierShape; exports.effectiveStrokeAlign = effectiveStrokeAlign; exports.strokeWidthProfileOf = strokeWidthProfileOf; exports.hasStrokeExtras = hasStrokeExtras; exports.vectorStrokeLineArea = vectorStrokeLineArea; exports.arrowheadWeight = arrowheadWeight; exports.arrowheadInset = arrowheadInset; exports.arrowheadPath = arrowheadPath; exports.vectorStrokeParts = vectorStrokeParts; exports.vectorStrokeOutlinePath = vectorStrokeOutlinePath; exports.hitTestVectorStroke = hitTestVectorStroke; exports.vectorStrokeReach = vectorStrokeReach; exports.VECTOR_STROKE_SETTING_KEYS = VECTOR_STROKE_SETTING_KEYS; exports.VECTOR_BLEND_MODE_LABELS = VECTOR_BLEND_MODE_LABELS; exports.isVectorBlendMode = isVectorBlendMode; exports.vectorBlendModeCss = vectorBlendModeCss; exports.vectorBlendModeFromCss = vectorBlendModeFromCss; exports.isPlainVectorPaintLayer = isPlainVectorPaintLayer; exports.isDrawnVectorPaintLayer = isDrawnVectorPaintLayer; exports.vectorFills = vectorFills; exports.vectorStrokeSettings = vectorStrokeSettings; exports.vectorStrokes = vectorStrokes; exports.hasVectorPaintStacks = hasVectorPaintStacks; exports.withVectorFills = withVectorFills; exports.withVectorStrokes = withVectorStrokes; exports.normalizeVectorPaintStacks = normalizeVectorPaintStacks; exports.sanitizeVectorFills = sanitizeVectorFills; exports.sanitizeVectorStrokeSettings = sanitizeVectorStrokeSettings; exports.sanitizeVectorStrokes = sanitizeVectorStrokes; exports.vectorPaintLayerNodes = vectorPaintLayerNodes; exports.needsVectorPaintLayers = needsVectorPaintLayers; exports.vectorStrokeStackReach = vectorStrokeStackReach; exports.hitTestVectorPaintLayer = hitTestVectorPaintLayer; exports.hitTestVectorPaintStack = hitTestVectorPaintStack; exports.vectorStacksHaveGradient = vectorStacksHaveGradient; exports.newVectorStrokeLayer = newVectorStrokeLayer; exports.vectorTargetPaint = vectorTargetPaint; exports.withVectorTargetPaint = withVectorTargetPaint; exports.effectPathLength = effectPathLength; exports.effectPathVertexCount = effectPathVertexCount; exports.trimIntervals = trimIntervals; exports.trimPaths = trimPaths; exports.trimPathsIndividually = trimPathsIndividually; exports.puckerBloatPaths = puckerBloatPaths; exports.roundCornerPaths = roundCornerPaths; exports.offsetPaths = offsetPaths; exports.twistPaths = twistPaths; exports.zigzagPaths = zigzagPaths; exports.wigglePaths = wigglePaths; exports.mergePaths = mergePaths; exports.vectorRepeaterCopies = vectorRepeaterCopies; exports.repeatPaths = repeatPaths; exports.pathsCenter = pathsCenter; exports.mapVectorPoints = mapVectorPoints; exports.mapVectorSubpaths = mapVectorSubpaths; exports.mapBezierPath = mapBezierPath; exports.isVectorFrame = isVectorFrame; exports.vectorFrameRectPath = vectorFrameRectPath; exports.vectorFrameDrawn = vectorFrameDrawn; exports.vectorFrameContains = vectorFrameContains; exports.vectorFrameChildMatrix = vectorFrameChildMatrix; exports.sanitizeVectorFrame = sanitizeVectorFrame; exports.sanitizeVectorResizing = sanitizeVectorResizing; exports.VECTOR_HORIZONTAL_RESIZING_LABELS = VECTOR_HORIZONTAL_RESIZING_LABELS; exports.VECTOR_VERTICAL_RESIZING_LABELS = VECTOR_VERTICAL_RESIZING_LABELS; exports.vectorBoundsInside = vectorBoundsInside; exports.vectorArtboards = vectorArtboards; exports.vectorFrameDocument = vectorFrameDocument; exports.getVectorFramePanel = getVectorFramePanel; exports.splitIntoFaces = splitIntoFaces; exports.knifePath = knifePath; exports.eraserRegion = eraserRegion; exports.eraseFromFill = eraseFromFill; exports.eraseFromOutline = eraseFromOutline; exports.polylineBounds = polylineBounds; exports.simplifyPolyline = simplifyPolyline; exports.VECTOR_FILTER_DEFAULTS = VECTOR_FILTER_DEFAULTS; exports.VECTOR_FILTER_LABELS = VECTOR_FILTER_LABELS; exports.VECTOR_FILTER_PARAM_SPECS = VECTOR_FILTER_PARAM_SPECS; exports.isVectorFilterType = isVectorFilterType; exports.normalizeVectorFilterParams = normalizeVectorFilterParams; exports.vectorFilterParamKeys = vectorFilterParamKeys; exports.createVectorFilter = createVectorFilter; exports.sanitizeVectorFilters = sanitizeVectorFilters; exports.activeVectorFilters = activeVectorFilters; exports.vectorFilterReach = vectorFilterReach; exports.vectorFilterSvg = vectorFilterSvg; exports.vectorFilterMarkup = vectorFilterMarkup; exports.VECTOR_FILTER_MENU = VECTOR_FILTER_MENU; exports.isVectorMaskType = isVectorMaskType; exports.sanitizeVectorMask = sanitizeVectorMask; exports.isVectorMaskGroup = isVectorMaskGroup; exports.isVectorMaskActive = isVectorMaskActive; exports.vectorMaskSource = vectorMaskSource; exports.vectorMaskContents = vectorMaskContents; exports.vectorMaskOwner = vectorMaskOwner; exports.vectorMaskSummary = vectorMaskSummary; exports.vectorMaskRegionShapes = vectorMaskRegionShapes; exports.vectorMaskRegion = vectorMaskRegion; exports.vectorMaskRegionPath = vectorMaskRegionPath; exports.vectorMaskContains = vectorMaskContains; exports.vectorMaskedShapes = vectorMaskedShapes; exports.vectorMaskedGeometry = vectorMaskedGeometry; exports.vectorMaskedLocalBounds = vectorMaskedLocalBounds; exports.vectorMaskContentBounds = vectorMaskContentBounds; exports.vectorMaskRenderData = vectorMaskRenderData; exports.DEFAULT_TEXT_STYLE = DEFAULT_TEXT_STYLE; exports.DEFAULT_AUTO_LEADING = DEFAULT_AUTO_LEADING; exports.fitRuns = fitRuns; exports.styleAt = styleAt; exports.restyleRange = restyleRange; exports.spliceRuns = spliceRuns; exports.paragraphRanges = paragraphRanges; exports.fitParagraphRuns = fitParagraphRuns; exports.fontOf = fontOf; exports.isTextSpace = isTextSpace; exports.layoutText = layoutText; exports.textIndexAt = textIndexAt; exports.caretAt = caretAt; exports.textDecorations = textDecorations; exports.textRectPath = textRectPath; exports.textFragmentOutline = textFragmentOutline; exports.cssFontFamily = cssFontFamily; exports.cssFont = cssFont; exports.createCanvasTextShaper = createCanvasTextShaper; exports.createOutlineTextShaper = createOutlineTextShaper; exports.createMetricTextShaper = createMetricTextShaper; exports.setVectorTextShaper = setVectorTextShaper; exports.getVectorTextShaper = getVectorTextShaper; exports.vectorTextShaperGeneration = vectorTextShaperGeneration; exports.vectorTextHasOutlines = vectorTextHasOutlines; exports.vectorTextFamilies = vectorTextFamilies; exports.DEFAULT_VECTOR_FONT = DEFAULT_VECTOR_FONT; exports.VECTOR_CHARACTER_STYLE_KEYS = VECTOR_CHARACTER_STYLE_KEYS; exports.VECTOR_PARAGRAPH_STYLE_KEYS = VECTOR_PARAGRAPH_STYLE_KEYS; exports.VectorTextError = VectorTextError; exports.fitVectorTextRuns = fitVectorTextRuns; exports.vectorTextRuns = vectorTextRuns; exports.vectorTextStyleAt = vectorTextStyleAt; exports.measureVectorPath = measureVectorPath; exports.vectorPathAt = vectorPathAt; exports.vectorPathTextPositions = vectorPathTextPositions; exports.layoutVectorText = layoutVectorText; exports.glyphBox = glyphBox; exports.vectorTextPaths = vectorTextPaths; exports.vectorTextPaintSource = vectorTextPaintSource; exports.vectorTextCaret = vectorTextCaret; exports.vectorTextIndexAt = vectorTextIndexAt; exports.vectorTextSelectionQuads = vectorTextSelectionQuads; exports.patchVectorCharacterStyle = patchVectorCharacterStyle; exports.patchVectorParagraphStyle = patchVectorParagraphStyle; exports.sanitizeVectorTextFrame = sanitizeVectorTextFrame; exports.normalizeVectorTextRuns = normalizeVectorTextRuns; exports.sanitizeVectorTextFields = sanitizeVectorTextFields; exports.vectorTextRange = vectorTextRange; exports.replaceVectorText = replaceVectorText; exports.styleVectorText = styleVectorText; exports.bakeVectorTextGeometry = bakeVectorTextGeometry; exports.vectorTextName = vectorTextName; exports.pathTextFrameFromBezier = pathTextFrameFromBezier; exports.vectorTextBoxOutline = vectorTextBoxOutline; exports.vectorTextSpans = vectorTextSpans; exports.vectorTextGeometryNode = vectorTextGeometryNode; exports.vectorTextSpanSvg = vectorTextSpanSvg; exports.VECTOR_SYMBOL_MAX_DEPTH = VECTOR_SYMBOL_MAX_DEPTH; exports.vectorSymbolsUsedIn = vectorSymbolsUsedIn; exports.vectorSymbolUses = vectorSymbolUses; exports.resolveVectorSymbols = resolveVectorSymbols; exports.stripVectorSymbolArt = stripVectorSymbolArt; exports.scaleVectorStrokeWidths = scaleVectorStrokeWidths; exports.tintVectorNode = tintVectorNode; exports.prefixVectorIds = prefixVectorIds; exports.vectorInstanceGroup = vectorInstanceGroup; exports.composeVectorMatrices = composeVectorMatrices; exports.WARP_STYLES = WARP_STYLES; exports.WARP_STYLE_LABELS = WARP_STYLE_LABELS; exports.warpPresetGrid = warpPresetGrid; exports.warpPresetMesh = warpPresetMesh; exports.warpMeshColumns = warpMeshColumns; exports.warpMeshRows = warpMeshRows; exports.isValidWarpMesh = isValidWarpMesh; exports.fitWarpMesh = fitWarpMesh; exports.identityWarpMesh = identityWarpMesh; exports.evalWarpMesh = evalWarpMesh; exports.splitWarpMeshU = splitWarpMeshU; exports.splitWarpMeshV = splitWarpMeshV; exports.removeWarpMeshSplitU = removeWarpMeshSplitU; exports.removeWarpMeshSplitV = removeWarpMeshSplitV; exports.mapWarpMeshPoints = mapWarpMeshPoints; exports.resizeWarpMesh = resizeWarpMesh; exports.warpMeshControlBounds = warpMeshControlBounds; exports.warpMeshParamAt = warpMeshParamAt; exports.dragWarpMeshPoint = dragWarpMeshPoint; exports.pullWarpMesh = pullWarpMesh; exports.warpMeshEditPoints = warpMeshEditPoints; exports.warpMeshGridCurves = warpMeshGridCurves; exports.vectorMeshFromOutline = vectorMeshFromOutline; exports.vectorMeshOutline = vectorMeshOutline; exports.VECTOR_EFFECT_DEFAULTS = VECTOR_EFFECT_DEFAULTS; exports.VECTOR_EFFECT_LABELS = VECTOR_EFFECT_LABELS; exports.VECTOR_EFFECT_PARAM_SPECS = VECTOR_EFFECT_PARAM_SPECS; exports.vectorEnvelopeMesh = vectorEnvelopeMesh; exports.vectorEnvelopeMap = vectorEnvelopeMap; exports.normalizeVectorEffectParams = normalizeVectorEffectParams; exports.createVectorEffect = createVectorEffect; exports.activeVectorEffects = activeVectorEffects; exports.hasOwnVectorAppearance = hasOwnVectorAppearance; exports.hasVectorAppearance = hasVectorAppearance; exports.isVectorLiveBoolean = isVectorLiveBoolean; exports.vectorOperandOperation = vectorOperandOperation; exports.vectorLiveBooleanSteps = vectorLiveBooleanSteps; exports.clearVectorLiveBooleanCache = clearVectorLiveBooleanCache; exports.foldVectorBooleanOperands = foldVectorBooleanOperands; exports.applyVectorEffects = applyVectorEffects; exports.vectorInstanceDrawn = vectorInstanceDrawn; exports.vectorChildAppearanceShapes = vectorChildAppearanceShapes; exports.vectorEffectInputPaths = vectorEffectInputPaths; exports.vectorEffectInputBounds = vectorEffectInputBounds; exports.vectorNodeEnvelope = vectorNodeEnvelope; exports.vectorEnvelopeFrame = vectorEnvelopeFrame; exports.vectorAppearanceShapes = vectorAppearanceShapes; exports.vectorAppearanceOutline = vectorAppearanceOutline; exports.vectorAppearanceNodes = vectorAppearanceNodes; exports.expandVectorAppearance = expandVectorAppearance; exports.expandVectorAppearances = expandVectorAppearances; exports.sanitizeVectorEffects = sanitizeVectorEffects; exports.transformVectorEffects = transformVectorEffects; exports.vectorEnteredGroups = vectorEnteredGroups; exports.isVectorConnector = isVectorConnector; exports.vectorConnectionSites = vectorConnectionSites; exports.nearestVectorConnectionSite = nearestVectorConnectionSite; exports.vectorConnectorWorldAnchors = vectorConnectorWorldAnchors; exports.routeVectorConnector = routeVectorConnector; exports.rerouteVectorConnectors = rerouteVectorConnectors; exports.sanitizeVectorConnector = sanitizeVectorConnector; exports.VECTOR_CONNECTOR_ROUTE_LABELS = VECTOR_CONNECTOR_ROUTE_LABELS; exports.VECTOR_CONNECTOR_SIDE_LABELS = VECTOR_CONNECTOR_SIDE_LABELS; exports.getVectorConnectorPanel = getVectorConnectorPanel; exports.vectorConnectorTargetAt = vectorConnectorTargetAt; exports.vectorStrokeGradientDefs = vectorStrokeGradientDefs; exports.vectorCornersAttribute = vectorCornersAttribute; exports.applyVectorCornersAttribute = applyVectorCornersAttribute; exports.vectorPathLocalBounds = vectorPathLocalBounds; exports.vectorPaintToSvg = vectorPaintToSvg; exports.vectorStrokeSvgParts = vectorStrokeSvgParts; exports.vectorNodeLocalPaintBounds = vectorNodeLocalPaintBounds; exports.vectorNodeFilterSvg = vectorNodeFilterSvg; exports.widthProfileToAttribute = widthProfileToAttribute; exports.widthProfileFromAttribute = widthProfileFromAttribute; exports.vectorDocumentToSvg = vectorDocumentToSvg; exports.parseSvgTransform = parseSvgTransform; exports.parseVectorSvg = parseVectorSvg; exports.VECTOR_SPATIAL_MIN = VECTOR_SPATIAL_MIN; exports.VectorRTree = VectorRTree; exports.vectorNodePaintBox = vectorNodePaintBox; exports.vectorSpatialIndex = vectorSpatialIndex; exports.vectorNodesNear = vectorNodesNear; exports.cloneAnchor = cloneAnchor; exports.cloneSubpath = cloneSubpath; exports.cloneVectorNode = cloneVectorNode; exports.cloneVectorDocument = cloneVectorDocument; exports.hasPaint = hasPaint; exports.subpathSegmentCount = subpathSegmentCount; exports.subpathSegment = subpathSegment; exports.subpathsToBezier = subpathsToBezier; exports.vectorNodeToBezier = vectorNodeToBezier; exports.vectorPathData = vectorPathData; exports.inferAnchorType = inferAnchorType; exports.bezierToSubpaths = bezierToSubpaths; exports.walkVectorNodes = walkVectorNodes; exports.findVectorNode = findVectorNode; exports.locateVectorNode = locateVectorNode; exports.collectPaintedNodes = collectPaintedNodes; exports.collectPathNodes = collectPathNodes; exports.nodeMatrix = nodeMatrix; exports.vectorPathWorldBezier = vectorPathWorldBezier; exports.vectorNodeBounds = vectorNodeBounds; exports.unionBounds = unionBounds; exports.boundsIntersect = boundsIntersect; exports.boundsFromPoints = boundsFromPoints; exports.hitTestVectorNode = hitTestVectorNode; exports.vectorStrokeOutline = vectorStrokeOutline; exports.hitTestVectorNodes = hitTestVectorNodes; exports.nearestSegment = nearestSegment; exports.transformVectorNode = transformVectorNode; exports.vectorNodeRotation = vectorNodeRotation; exports.vectorWorldMatrix = vectorWorldMatrix; exports.vectorParentMatrix = vectorParentMatrix; exports.translateAnchor = translateAnchor; exports.moveAnchorHandle = moveAnchorHandle; exports.convertAnchor = convertAnchor; exports.insertAnchor = insertAnchor; exports.removeAnchors = removeAnchors; exports.reverseSubpath = reverseSubpath; exports.KAPPA = KAPPA2; exports.rectSubpath = rectSubpath; exports.ellipseSubpath = ellipseSubpath; exports.polygonSubpath = polygonSubpath; exports.starSubpath = starSubpath; exports.lineSubpath = lineSubpath; exports.roundSubpaths = roundSubpaths;
9797
- //# sourceMappingURL=chunk-FODKPD44.cjs.map
10028
+
10029
+
10030
+
10031
+
10032
+
10033
+
10034
+
10035
+
10036
+
10037
+ exports.isVectorMeshGradient = isVectorMeshGradient; exports.isVectorFreeformGradient = isVectorFreeformGradient; exports.isVectorShadedPaint = isVectorShadedPaint; exports.vectorRgbaToCss = vectorRgbaToCss; exports.VECTOR_MESH_MAX = VECTOR_MESH_MAX; exports.createVectorMeshGradient = createVectorMeshGradient; exports.vectorMeshPointAt = vectorMeshPointAt; exports.vectorMeshColorAt = vectorMeshColorAt; exports.vectorMeshLines = vectorMeshLines; exports.vectorFreeformSpreadScale = vectorFreeformSpreadScale; exports.vectorFreeformLineSegments = vectorFreeformLineSegments; exports.vectorFreeformField = vectorFreeformField; exports.sampleVectorFreeform = sampleVectorFreeform; exports.autoVectorFreeformGradient = autoVectorFreeformGradient; exports.vectorShadedSvgDefs = vectorShadedSvgDefs; exports.mapVectorShadedPaint = mapVectorShadedPaint; exports.transformVectorShadedPaint = transformVectorShadedPaint; exports.sanitizeVectorShadedPaint = sanitizeVectorShadedPaint; exports.removeVectorFreeformPoint = removeVectorFreeformPoint; exports.nearestVectorShadingPoint = nearestVectorShadingPoint; exports.VECTOR_CORNER_KINDS = VECTOR_CORNER_KINDS; exports.VECTOR_GRADIENT_TYPES = VECTOR_GRADIENT_TYPES; exports.VECTOR_GRADIENT_SPREADS = VECTOR_GRADIENT_SPREADS; exports.VECTOR_GRADIENT_INTERPOLATIONS = VECTOR_GRADIENT_INTERPOLATIONS; exports.VECTOR_STROKE_GRADIENT_MODES = VECTOR_STROKE_GRADIENT_MODES; exports.VECTOR_ARROWHEADS = VECTOR_ARROWHEADS; exports.VECTOR_BLEND_MODES = VECTOR_BLEND_MODES; exports.VECTOR_HORIZONTAL_RESIZING = VECTOR_HORIZONTAL_RESIZING; exports.VECTOR_VERTICAL_RESIZING = VECTOR_VERTICAL_RESIZING; exports.VECTOR_CONNECTOR_SIDES = VECTOR_CONNECTOR_SIDES; exports.VECTOR_CONNECTOR_ROUTES = VECTOR_CONNECTOR_ROUTES; exports.VECTOR_BLEND_SPACINGS = VECTOR_BLEND_SPACINGS; exports.VECTOR_MASK_TYPES = VECTOR_MASK_TYPES; exports.VECTOR_SYMMETRY_MODES = VECTOR_SYMMETRY_MODES; exports.VECTOR_TEXT_ALIGNS = VECTOR_TEXT_ALIGNS; exports.VECTOR_PATH_TEXT_BASELINES = VECTOR_PATH_TEXT_BASELINES; exports.VECTOR_CONSTRAINT_KINDS = VECTOR_CONSTRAINT_KINDS; exports.VECTOR_TOOLS = VECTOR_TOOLS; exports.VECTOR_TRANSFORM_HANDLES = VECTOR_TRANSFORM_HANDLES; exports.VECTOR_PATHFINDER_OPERATIONS = VECTOR_PATHFINDER_OPERATIONS; exports.VECTOR_EFFECT_TYPES = VECTOR_EFFECT_TYPES; exports.VECTOR_MERGE_MODES = VECTOR_MERGE_MODES; exports.VECTOR_FILTER_TYPES = VECTOR_FILTER_TYPES; exports.isVectorGradient = isVectorGradient; exports.parseVectorColor = parseVectorColor; exports.VECTOR_GRADIENT_MIN_STOPS = VECTOR_GRADIENT_MIN_STOPS; exports.gradientMidpointRemap = gradientMidpointRemap; exports.sortedVectorGradientStops = sortedVectorGradientStops; exports.vectorGradientNeedsExpansion = vectorGradientNeedsExpansion; exports.vectorGradientRamp = vectorGradientRamp; exports.sampleVectorGradient = sampleVectorGradient; exports.expandVectorGradientStops = expandVectorGradientStops; exports.samplePlainStops = samplePlainStops; exports.reverseVectorGradient = reverseVectorGradient; exports.insertVectorGradientStop = insertVectorGradientStop; exports.moveVectorGradientStop = moveVectorGradientStop; exports.removeVectorGradientStop = removeVectorGradientStop; exports.vectorGradientMidpointPosition = vectorGradientMidpointPosition; exports.vectorGradientMidpointFromPosition = vectorGradientMidpointFromPosition; exports.spanVectorGradientStops = spanVectorGradientStops; exports.hasExplicitGradientGeometry = hasExplicitGradientGeometry; exports.vectorGradientPoints = vectorGradientPoints; exports.vectorBoxMatrix = vectorBoxMatrix; exports.vectorGradientUnitsMatrix = vectorGradientUnitsMatrix; exports.vectorGradientMatrix = vectorGradientMatrix; exports.vectorGradientFocalParam = vectorGradientFocalParam; exports.vectorGradientParam = vectorGradientParam; exports.applyVectorGradientSpread = applyVectorGradientSpread; exports.vectorGradientTAt = vectorGradientTAt; exports.sampleVectorGradientAt = sampleVectorGradientAt; exports.vectorGradientAspect = vectorGradientAspect; exports.explicitVectorGradient = explicitVectorGradient; exports.pinVectorGradient = pinVectorGradient; exports.transformVectorGradient = transformVectorGradient; exports.mapVectorGradient = mapVectorGradient; exports.mapVectorPaint = mapVectorPaint; exports.transformVectorPaint = transformVectorPaint; exports.isCentredVectorGradient = isCentredVectorGradient; exports.vectorGradientHandles = vectorGradientHandles; exports.moveVectorGradientHandle = moveVectorGradientHandle; exports.setVectorGradientVector = setVectorGradientVector; exports.VECTOR_GRADIENT_MAX_PERIODS = VECTOR_GRADIENT_MAX_PERIODS; exports.periodicVectorGradientStops = periodicVectorGradientStops; exports.expandVectorGradientSpread = expandVectorGradientSpread; exports.vectorGradientArea = vectorGradientArea; exports.patternAttrs = patternAttrs; exports.vectorGradientSvgDefs = vectorGradientSvgDefs; exports.sampleVectorPaintDefAt = sampleVectorPaintDefAt; exports.sanitizeVectorGradient = sanitizeVectorGradient; exports.convertVectorGradient = convertVectorGradient; exports.defaultVectorGradient = defaultVectorGradient; exports.applyVectorGradientPatch = applyVectorGradientPatch; exports.IDENTITY_MATRIX = IDENTITY_MATRIX; exports.multiplyMatrices = multiplyMatrices; exports.translateMatrix = translateMatrix; exports.scaleMatrix = scaleMatrix; exports.rotateMatrix = rotateMatrix; exports.matrixAbout = matrixAbout; exports.skewMatrix = skewMatrix; exports.applyMatrix = applyMatrix; exports.isIdentityMatrix = isIdentityMatrix; exports.invertMatrix = invertMatrix; exports.applyMatrixLinear = applyMatrixLinear; exports.matrixRotation = matrixRotation; exports.decomposeRigid = decomposeRigid; exports.isVectorSymmetryGroup = isVectorSymmetryGroup; exports.vectorSymmetryMatrices = vectorSymmetryMatrices; exports.vectorSymmetryDrawn = vectorSymmetryDrawn; exports.vectorSymmetryAxes = vectorSymmetryAxes; exports.sanitizeVectorSymmetry = sanitizeVectorSymmetry; exports.VECTOR_SYMMETRY_MODE_LABELS = VECTOR_SYMMETRY_MODE_LABELS; exports.transformVectorSymmetry = transformVectorSymmetry; exports.vectorCornerAt = vectorCornerAt; exports.vectorCorners = vectorCorners; exports.cornerSetback = cornerSetback; exports.fitCornerRadius = fitCornerRadius; exports.cornerBisectorPoint = cornerBisectorPoint; exports.cornerRadiusChange = cornerRadiusChange; exports.hasVectorCorners = hasVectorCorners; exports.expandVectorCornersOf = expandVectorCornersOf; exports.expandVectorCorners = expandVectorCorners; exports.setAnchorCorner = setAnchorCorner; exports.nextVectorCornerKind = nextVectorCornerKind; exports.setSubpathCorners = setSubpathCorners; exports.VECTOR_WIDTH_PROFILE_MAX_POINTS = VECTOR_WIDTH_PROFILE_MAX_POINTS; exports.VECTOR_WIDTH_PROFILE_MAX_SCALE = VECTOR_WIDTH_PROFILE_MAX_SCALE; exports.VECTOR_WIDTH_SAME_T = VECTOR_WIDTH_SAME_T; exports.VECTOR_WIDTH_PRESETS = VECTOR_WIDTH_PRESETS; exports.VECTOR_WIDTH_PRESET_IDS = VECTOR_WIDTH_PRESET_IDS; exports.sanitizeWidthProfile = sanitizeWidthProfile; exports.isUniformWidthProfile = isUniformWidthProfile; exports.widthProfileAt = widthProfileAt; exports.widthProfileMaxScale = widthProfileMaxScale; exports.widthProfilePreset = widthProfilePreset; exports.widthProfilePresetId = widthProfilePresetId; exports.reverseWidthProfile = reverseWidthProfile; exports.mirrorWidthProfile = mirrorWidthProfile; exports.insertWidthPoint = insertWidthPoint; exports.setWidthPoint = setWidthPoint; exports.removeWidthPoints = removeWidthPoints; exports.taperWaveFactor = taperWaveFactor; exports.generateWidthProfile = generateWidthProfile; exports.VECTOR_PRESSURE_NOMINAL = VECTOR_PRESSURE_NOMINAL; exports.pressureWidthProfile = pressureWidthProfile; exports.dashIntervals = dashIntervals; exports.variableStrokeRings = variableStrokeRings; exports.variableStrokeOutline = variableStrokeOutline; exports.nearestStrokePosition = nearestStrokePosition; exports.strokePositionPoint = strokePositionPoint; exports.isClosedBezierShape = isClosedBezierShape; exports.effectiveStrokeAlign = effectiveStrokeAlign; exports.strokeWidthProfileOf = strokeWidthProfileOf; exports.hasStrokeExtras = hasStrokeExtras; exports.vectorStrokeLineArea = vectorStrokeLineArea; exports.arrowheadWeight = arrowheadWeight; exports.arrowheadInset = arrowheadInset; exports.arrowheadPath = arrowheadPath; exports.vectorStrokeParts = vectorStrokeParts; exports.vectorStrokeOutlinePath = vectorStrokeOutlinePath; exports.hitTestVectorStroke = hitTestVectorStroke; exports.vectorStrokeReach = vectorStrokeReach; exports.VECTOR_STROKE_SETTING_KEYS = VECTOR_STROKE_SETTING_KEYS; exports.VECTOR_BLEND_MODE_LABELS = VECTOR_BLEND_MODE_LABELS; exports.isVectorBlendMode = isVectorBlendMode; exports.vectorBlendModeCss = vectorBlendModeCss; exports.vectorBlendModeFromCss = vectorBlendModeFromCss; exports.isPlainVectorPaintLayer = isPlainVectorPaintLayer; exports.isDrawnVectorPaintLayer = isDrawnVectorPaintLayer; exports.vectorFills = vectorFills; exports.vectorStrokeSettings = vectorStrokeSettings; exports.vectorStrokes = vectorStrokes; exports.hasVectorPaintStacks = hasVectorPaintStacks; exports.withVectorFills = withVectorFills; exports.withVectorStrokes = withVectorStrokes; exports.normalizeVectorPaintStacks = normalizeVectorPaintStacks; exports.sanitizeVectorFills = sanitizeVectorFills; exports.sanitizeVectorStrokeSettings = sanitizeVectorStrokeSettings; exports.sanitizeVectorStrokes = sanitizeVectorStrokes; exports.vectorPaintLayerNodes = vectorPaintLayerNodes; exports.needsVectorPaintLayers = needsVectorPaintLayers; exports.vectorStrokeStackReach = vectorStrokeStackReach; exports.hitTestVectorPaintLayer = hitTestVectorPaintLayer; exports.hitTestVectorPaintStack = hitTestVectorPaintStack; exports.vectorStacksHaveGradient = vectorStacksHaveGradient; exports.newVectorStrokeLayer = newVectorStrokeLayer; exports.vectorTargetPaint = vectorTargetPaint; exports.withVectorTargetPaint = withVectorTargetPaint; exports.effectPathLength = effectPathLength; exports.effectPathVertexCount = effectPathVertexCount; exports.trimIntervals = trimIntervals; exports.trimPaths = trimPaths; exports.trimPathsIndividually = trimPathsIndividually; exports.puckerBloatPaths = puckerBloatPaths; exports.roundCornerPaths = roundCornerPaths; exports.offsetPaths = offsetPaths; exports.sweepPath = sweepPath; exports.twistPaths = twistPaths; exports.zigzagPaths = zigzagPaths; exports.wigglePaths = wigglePaths; exports.mergePaths = mergePaths; exports.vectorRepeaterCopies = vectorRepeaterCopies; exports.repeatPaths = repeatPaths; exports.pathsCenter = pathsCenter; exports.mapVectorPoints = mapVectorPoints; exports.mapVectorSubpaths = mapVectorSubpaths; exports.mapBezierPath = mapBezierPath; exports.isVectorFrame = isVectorFrame; exports.vectorFrameRectPath = vectorFrameRectPath; exports.vectorFrameDrawn = vectorFrameDrawn; exports.vectorFrameContains = vectorFrameContains; exports.vectorFrameChildMatrix = vectorFrameChildMatrix; exports.sanitizeVectorFrame = sanitizeVectorFrame; exports.sanitizeVectorResizing = sanitizeVectorResizing; exports.VECTOR_HORIZONTAL_RESIZING_LABELS = VECTOR_HORIZONTAL_RESIZING_LABELS; exports.VECTOR_VERTICAL_RESIZING_LABELS = VECTOR_VERTICAL_RESIZING_LABELS; exports.vectorBoundsInside = vectorBoundsInside; exports.vectorArtboards = vectorArtboards; exports.vectorFrameDocument = vectorFrameDocument; exports.getVectorFramePanel = getVectorFramePanel; exports.splitIntoFaces = splitIntoFaces; exports.knifePath = knifePath; exports.eraserRegion = eraserRegion; exports.eraseFromFill = eraseFromFill; exports.eraseFromOutline = eraseFromOutline; exports.polylineBounds = polylineBounds; exports.simplifyPolyline = simplifyPolyline; exports.VECTOR_FILTER_DEFAULTS = VECTOR_FILTER_DEFAULTS; exports.VECTOR_FILTER_LABELS = VECTOR_FILTER_LABELS; exports.VECTOR_FILTER_PARAM_SPECS = VECTOR_FILTER_PARAM_SPECS; exports.isVectorFilterType = isVectorFilterType; exports.normalizeVectorFilterParams = normalizeVectorFilterParams; exports.vectorFilterParamKeys = vectorFilterParamKeys; exports.createVectorFilter = createVectorFilter; exports.sanitizeVectorFilters = sanitizeVectorFilters; exports.activeVectorFilters = activeVectorFilters; exports.vectorFilterReach = vectorFilterReach; exports.vectorFilterSvg = vectorFilterSvg; exports.vectorFilterMarkup = vectorFilterMarkup; exports.VECTOR_FILTER_MENU = VECTOR_FILTER_MENU; exports.isVectorMaskType = isVectorMaskType; exports.sanitizeVectorMask = sanitizeVectorMask; exports.isVectorMaskGroup = isVectorMaskGroup; exports.isVectorMaskActive = isVectorMaskActive; exports.vectorMaskSource = vectorMaskSource; exports.vectorMaskContents = vectorMaskContents; exports.vectorMaskOwner = vectorMaskOwner; exports.vectorMaskSummary = vectorMaskSummary; exports.vectorMaskRegionShapes = vectorMaskRegionShapes; exports.vectorMaskRegion = vectorMaskRegion; exports.vectorMaskRegionPath = vectorMaskRegionPath; exports.vectorMaskContains = vectorMaskContains; exports.vectorMaskedShapes = vectorMaskedShapes; exports.vectorMaskedGeometry = vectorMaskedGeometry; exports.vectorMaskedLocalBounds = vectorMaskedLocalBounds; exports.vectorMaskContentBounds = vectorMaskContentBounds; exports.vectorMaskRenderData = vectorMaskRenderData; exports.DEFAULT_TEXT_STYLE = DEFAULT_TEXT_STYLE; exports.DEFAULT_AUTO_LEADING = DEFAULT_AUTO_LEADING; exports.fitRuns = fitRuns; exports.styleAt = styleAt; exports.restyleRange = restyleRange; exports.spliceRuns = spliceRuns; exports.paragraphRanges = paragraphRanges; exports.fitParagraphRuns = fitParagraphRuns; exports.fontOf = fontOf; exports.isTextSpace = isTextSpace; exports.layoutText = layoutText; exports.textIndexAt = textIndexAt; exports.caretAt = caretAt; exports.textDecorations = textDecorations; exports.textRectPath = textRectPath; exports.textFragmentOutline = textFragmentOutline; exports.cssFontFamily = cssFontFamily; exports.cssFont = cssFont; exports.createCanvasTextShaper = createCanvasTextShaper; exports.createOutlineTextShaper = createOutlineTextShaper; exports.createMetricTextShaper = createMetricTextShaper; exports.setVectorTextShaper = setVectorTextShaper; exports.getVectorTextShaper = getVectorTextShaper; exports.vectorTextShaperGeneration = vectorTextShaperGeneration; exports.vectorTextHasOutlines = vectorTextHasOutlines; exports.vectorTextFamilies = vectorTextFamilies; exports.DEFAULT_VECTOR_FONT = DEFAULT_VECTOR_FONT; exports.VECTOR_CHARACTER_STYLE_KEYS = VECTOR_CHARACTER_STYLE_KEYS; exports.VECTOR_PARAGRAPH_STYLE_KEYS = VECTOR_PARAGRAPH_STYLE_KEYS; exports.VectorTextError = VectorTextError; exports.fitVectorTextRuns = fitVectorTextRuns; exports.vectorTextRuns = vectorTextRuns; exports.vectorTextStyleAt = vectorTextStyleAt; exports.measureVectorPath = measureVectorPath; exports.vectorPathAt = vectorPathAt; exports.vectorPathTextPositions = vectorPathTextPositions; exports.layoutVectorText = layoutVectorText; exports.glyphBox = glyphBox; exports.vectorTextPaths = vectorTextPaths; exports.vectorTextPaintSource = vectorTextPaintSource; exports.vectorTextCaret = vectorTextCaret; exports.vectorTextIndexAt = vectorTextIndexAt; exports.vectorTextSelectionQuads = vectorTextSelectionQuads; exports.patchVectorCharacterStyle = patchVectorCharacterStyle; exports.patchVectorParagraphStyle = patchVectorParagraphStyle; exports.sanitizeVectorTextFrame = sanitizeVectorTextFrame; exports.normalizeVectorTextRuns = normalizeVectorTextRuns; exports.sanitizeVectorTextFields = sanitizeVectorTextFields; exports.vectorTextRange = vectorTextRange; exports.replaceVectorText = replaceVectorText; exports.styleVectorText = styleVectorText; exports.bakeVectorTextGeometry = bakeVectorTextGeometry; exports.vectorTextName = vectorTextName; exports.pathTextFrameFromBezier = pathTextFrameFromBezier; exports.vectorTextBoxOutline = vectorTextBoxOutline; exports.vectorTextSpans = vectorTextSpans; exports.vectorTextGeometryNode = vectorTextGeometryNode; exports.vectorTextSpanSvg = vectorTextSpanSvg; exports.VECTOR_SYMBOL_MAX_DEPTH = VECTOR_SYMBOL_MAX_DEPTH; exports.vectorSymbolsUsedIn = vectorSymbolsUsedIn; exports.vectorSymbolUses = vectorSymbolUses; exports.resolveVectorSymbols = resolveVectorSymbols; exports.stripVectorSymbolArt = stripVectorSymbolArt; exports.scaleVectorStrokeWidths = scaleVectorStrokeWidths; exports.tintVectorNode = tintVectorNode; exports.prefixVectorIds = prefixVectorIds; exports.vectorInstanceGroup = vectorInstanceGroup; exports.composeVectorMatrices = composeVectorMatrices; exports.WARP_STYLES = WARP_STYLES; exports.WARP_STYLE_LABELS = WARP_STYLE_LABELS; exports.warpPresetGrid = warpPresetGrid; exports.warpPresetMesh = warpPresetMesh; exports.warpMeshColumns = warpMeshColumns; exports.warpMeshRows = warpMeshRows; exports.isValidWarpMesh = isValidWarpMesh; exports.fitWarpMesh = fitWarpMesh; exports.identityWarpMesh = identityWarpMesh; exports.evalWarpMesh = evalWarpMesh; exports.splitWarpMeshU = splitWarpMeshU; exports.splitWarpMeshV = splitWarpMeshV; exports.removeWarpMeshSplitU = removeWarpMeshSplitU; exports.removeWarpMeshSplitV = removeWarpMeshSplitV; exports.mapWarpMeshPoints = mapWarpMeshPoints; exports.resizeWarpMesh = resizeWarpMesh; exports.warpMeshControlBounds = warpMeshControlBounds; exports.warpMeshParamAt = warpMeshParamAt; exports.dragWarpMeshPoint = dragWarpMeshPoint; exports.pullWarpMesh = pullWarpMesh; exports.warpMeshEditPoints = warpMeshEditPoints; exports.warpMeshGridCurves = warpMeshGridCurves; exports.vectorMeshFromOutline = vectorMeshFromOutline; exports.vectorMeshOutline = vectorMeshOutline; exports.VECTOR_EFFECT_DEFAULTS = VECTOR_EFFECT_DEFAULTS; exports.VECTOR_EFFECT_LABELS = VECTOR_EFFECT_LABELS; exports.VECTOR_EFFECT_PARAM_SPECS = VECTOR_EFFECT_PARAM_SPECS; exports.vectorEnvelopeMesh = vectorEnvelopeMesh; exports.vectorEnvelopeMap = vectorEnvelopeMap; exports.normalizeVectorEffectParams = normalizeVectorEffectParams; exports.createVectorEffect = createVectorEffect; exports.activeVectorEffects = activeVectorEffects; exports.hasOwnVectorAppearance = hasOwnVectorAppearance; exports.hasVectorAppearance = hasVectorAppearance; exports.isVectorLiveBoolean = isVectorLiveBoolean; exports.vectorOperandOperation = vectorOperandOperation; exports.vectorLiveBooleanSteps = vectorLiveBooleanSteps; exports.clearVectorLiveBooleanCache = clearVectorLiveBooleanCache; exports.foldVectorBooleanOperands = foldVectorBooleanOperands; exports.applyVectorEffects = applyVectorEffects; exports.vectorInstanceDrawn = vectorInstanceDrawn; exports.vectorChildAppearanceShapes = vectorChildAppearanceShapes; exports.vectorEffectInputPaths = vectorEffectInputPaths; exports.vectorEffectInputBounds = vectorEffectInputBounds; exports.vectorNodeEnvelope = vectorNodeEnvelope; exports.vectorEnvelopeFrame = vectorEnvelopeFrame; exports.vectorAppearanceShapes = vectorAppearanceShapes; exports.vectorAppearanceOutline = vectorAppearanceOutline; exports.vectorAppearanceNodes = vectorAppearanceNodes; exports.expandVectorAppearance = expandVectorAppearance; exports.expandVectorAppearances = expandVectorAppearances; exports.sanitizeVectorEffects = sanitizeVectorEffects; exports.transformVectorEffects = transformVectorEffects; exports.vectorEnteredGroups = vectorEnteredGroups; exports.isVectorConnector = isVectorConnector; exports.vectorConnectionSites = vectorConnectionSites; exports.nearestVectorConnectionSite = nearestVectorConnectionSite; exports.vectorConnectorWorldAnchors = vectorConnectorWorldAnchors; exports.routeVectorConnector = routeVectorConnector; exports.rerouteVectorConnectors = rerouteVectorConnectors; exports.sanitizeVectorConnector = sanitizeVectorConnector; exports.VECTOR_CONNECTOR_ROUTE_LABELS = VECTOR_CONNECTOR_ROUTE_LABELS; exports.VECTOR_CONNECTOR_SIDE_LABELS = VECTOR_CONNECTOR_SIDE_LABELS; exports.getVectorConnectorPanel = getVectorConnectorPanel; exports.vectorConnectorTargetAt = vectorConnectorTargetAt; exports.vectorStrokeGradientDefs = vectorStrokeGradientDefs; exports.vectorCornersAttribute = vectorCornersAttribute; exports.applyVectorCornersAttribute = applyVectorCornersAttribute; exports.vectorPathLocalBounds = vectorPathLocalBounds; exports.vectorPaintToSvg = vectorPaintToSvg; exports.vectorStrokeSvgParts = vectorStrokeSvgParts; exports.vectorNodeLocalPaintBounds = vectorNodeLocalPaintBounds; exports.vectorNodeFilterSvg = vectorNodeFilterSvg; exports.widthProfileToAttribute = widthProfileToAttribute; exports.widthProfileFromAttribute = widthProfileFromAttribute; exports.vectorDocumentToSvg = vectorDocumentToSvg; exports.parseSvgTransform = parseSvgTransform; exports.parseVectorSvg = parseVectorSvg; exports.VECTOR_SPATIAL_MIN = VECTOR_SPATIAL_MIN; exports.VectorRTree = VectorRTree; exports.vectorNodePaintBox = vectorNodePaintBox; exports.vectorSpatialIndex = vectorSpatialIndex; exports.vectorNodesNear = vectorNodesNear; exports.cloneAnchor = cloneAnchor; exports.cloneSubpath = cloneSubpath; exports.cloneVectorNode = cloneVectorNode; exports.cloneVectorDocument = cloneVectorDocument; exports.hasPaint = hasPaint; exports.subpathSegmentCount = subpathSegmentCount; exports.subpathSegment = subpathSegment; exports.subpathsToBezier = subpathsToBezier; exports.vectorNodeToBezier = vectorNodeToBezier; exports.vectorPathData = vectorPathData; exports.inferAnchorType = inferAnchorType; exports.bezierToSubpaths = bezierToSubpaths; exports.walkVectorNodes = walkVectorNodes; exports.findVectorNode = findVectorNode; exports.locateVectorNode = locateVectorNode; exports.collectPaintedNodes = collectPaintedNodes; exports.collectPathNodes = collectPathNodes; exports.nodeMatrix = nodeMatrix; exports.vectorPathWorldBezier = vectorPathWorldBezier; exports.vectorNodeBounds = vectorNodeBounds; exports.unionBounds = unionBounds; exports.boundsIntersect = boundsIntersect; exports.boundsFromPoints = boundsFromPoints; exports.hitTestVectorNode = hitTestVectorNode; exports.vectorStrokeOutline = vectorStrokeOutline; exports.hitTestVectorNodes = hitTestVectorNodes; exports.nearestSegment = nearestSegment; exports.transformVectorNode = transformVectorNode; exports.vectorNodeRotation = vectorNodeRotation; exports.vectorWorldMatrix = vectorWorldMatrix; exports.vectorParentMatrix = vectorParentMatrix; exports.translateAnchor = translateAnchor; exports.moveAnchorHandle = moveAnchorHandle; exports.convertAnchor = convertAnchor; exports.insertAnchor = insertAnchor; exports.removeAnchors = removeAnchors; exports.reverseSubpath = reverseSubpath; exports.KAPPA = KAPPA2; exports.rectSubpath = rectSubpath; exports.ellipseSubpath = ellipseSubpath; exports.polygonSubpath = polygonSubpath; exports.starSubpath = starSubpath; exports.lineSubpath = lineSubpath; exports.roundSubpaths = roundSubpaths;
10038
+ //# sourceMappingURL=chunk-VYW7JBTM.cjs.map