@pixerate/editor 0.113.0 → 0.115.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 (125) hide show
  1. package/THIRD_PARTY_NOTICES.md +8 -0
  2. package/dist/animation-editor/index.cjs +60 -54
  3. package/dist/animation-editor/index.cjs.map +1 -1
  4. package/dist/animation-editor/index.d.cts +3 -3
  5. package/dist/animation-editor/index.d.ts +3 -3
  6. package/dist/animation-editor/index.js +14 -8
  7. package/dist/animation-editor/index.js.map +1 -1
  8. package/dist/builtin-CY97ppKM.d.cts +354 -0
  9. package/dist/builtin-CY97ppKM.d.ts +354 -0
  10. package/dist/canvas/index.cjs +3 -3
  11. package/dist/canvas/index.cjs.map +1 -1
  12. package/dist/canvas/index.js +9 -9
  13. package/dist/chunk-26PGXHY7.cjs +753 -0
  14. package/dist/chunk-26PGXHY7.cjs.map +1 -0
  15. package/dist/chunk-2OJACTPR.cjs +929 -0
  16. package/dist/chunk-2OJACTPR.cjs.map +1 -0
  17. package/dist/chunk-3UFGNHSP.js +929 -0
  18. package/dist/chunk-3UFGNHSP.js.map +1 -0
  19. package/dist/chunk-643B2HKC.cjs +534 -0
  20. package/dist/chunk-643B2HKC.cjs.map +1 -0
  21. package/dist/chunk-6FCKOS2B.js +534 -0
  22. package/dist/chunk-6FCKOS2B.js.map +1 -0
  23. package/dist/chunk-BRLYOPLT.js +2574 -0
  24. package/dist/chunk-BRLYOPLT.js.map +1 -0
  25. package/dist/{chunk-LQEEDHOP.js → chunk-C6C5PDKU.js} +759 -761
  26. package/dist/chunk-C6C5PDKU.js.map +1 -0
  27. package/dist/{chunk-4KLT7ZYS.cjs → chunk-DFQEX3AM.cjs} +29 -29
  28. package/dist/{chunk-4KLT7ZYS.cjs.map → chunk-DFQEX3AM.cjs.map} +1 -1
  29. package/dist/chunk-G5NMLUVF.cjs +2574 -0
  30. package/dist/chunk-G5NMLUVF.cjs.map +1 -0
  31. package/dist/{chunk-YGIMK4NX.cjs → chunk-I7FQBWMQ.cjs} +813 -842
  32. package/dist/chunk-I7FQBWMQ.cjs.map +1 -0
  33. package/dist/{chunk-LPYOIVLA.js → chunk-LKCYANMW.js} +3 -3
  34. package/dist/{chunk-W3GXSUSQ.cjs → chunk-LPLCWZTM.cjs} +5087 -1283
  35. package/dist/chunk-LPLCWZTM.cjs.map +1 -0
  36. package/dist/chunk-MMVHBKMM.js +753 -0
  37. package/dist/chunk-MMVHBKMM.js.map +1 -0
  38. package/dist/{chunk-POGBUYWE.cjs → chunk-ST7E3NEE.cjs} +857 -859
  39. package/dist/chunk-ST7E3NEE.cjs.map +1 -0
  40. package/dist/{chunk-7VOHOPLW.cjs → chunk-TCKIXI46.cjs} +59 -59
  41. package/dist/{chunk-7VOHOPLW.cjs.map → chunk-TCKIXI46.cjs.map} +1 -1
  42. package/dist/{chunk-XIOMMGPD.cjs → chunk-TFOPHZ3U.cjs} +1 -1
  43. package/dist/chunk-TFOPHZ3U.cjs.map +1 -0
  44. package/dist/{chunk-Z4BC6M74.js → chunk-UBIXVXPR.js} +2 -2
  45. package/dist/{chunk-BLWCAQCW.js → chunk-VXR7XWMF.js} +4574 -770
  46. package/dist/chunk-VXR7XWMF.js.map +1 -0
  47. package/dist/{chunk-CZOXTEMN.js → chunk-XICA4PVO.js} +392 -421
  48. package/dist/chunk-XICA4PVO.js.map +1 -0
  49. package/dist/{chunk-HNS7UHCM.js → chunk-XK5LZKBD.js} +1 -1
  50. package/dist/chunk-XK5LZKBD.js.map +1 -0
  51. package/dist/cms/index.cjs +146 -0
  52. package/dist/cms/index.cjs.map +1 -0
  53. package/dist/cms/index.d.cts +51 -0
  54. package/dist/cms/index.d.ts +51 -0
  55. package/dist/cms/index.js +146 -0
  56. package/dist/cms/index.js.map +1 -0
  57. package/dist/{export-CEXEzqBf.d.cts → export-BJE8T0YA.d.cts} +279 -191
  58. package/dist/{export-DIkoK8-r.d.ts → export-Con3UKkm.d.ts} +279 -191
  59. package/dist/image-editor/index.cjs +1848 -1218
  60. package/dist/image-editor/index.cjs.map +1 -1
  61. package/dist/image-editor/index.d.cts +85 -93
  62. package/dist/image-editor/index.d.ts +85 -93
  63. package/dist/image-editor/index.js +871 -241
  64. package/dist/image-editor/index.js.map +1 -1
  65. package/dist/opentype-BZEOSOX3.d.ts +188 -0
  66. package/dist/opentype-Dpe75vL5.d.cts +188 -0
  67. package/dist/paint/index.cjs +4 -4
  68. package/dist/paint/index.d.cts +2 -2
  69. package/dist/paint/index.d.ts +2 -2
  70. package/dist/paint/index.js +3 -3
  71. package/dist/paint-editor/index.cjs +147 -145
  72. package/dist/paint-editor/index.cjs.map +1 -1
  73. package/dist/paint-editor/index.d.cts +9 -8
  74. package/dist/paint-editor/index.d.ts +9 -8
  75. package/dist/paint-editor/index.js +7 -5
  76. package/dist/paint-editor/index.js.map +1 -1
  77. package/dist/raster/index.cjs +53 -3
  78. package/dist/raster/index.cjs.map +1 -1
  79. package/dist/raster/index.d.cts +62 -91
  80. package/dist/raster/index.d.ts +62 -91
  81. package/dist/raster/index.js +59 -9
  82. package/dist/{render-BEriFuqK.d.cts → render-B1K_OoLy.d.cts} +87 -2
  83. package/dist/{render-tjzKaik-.d.ts → render-CrmHOgpo.d.ts} +87 -2
  84. package/dist/{retouch-CEIKR22W.d.cts → retouch-Bxkuc0KH.d.cts} +1 -1
  85. package/dist/{retouch-BXmeSCaB.d.ts → retouch-Do6tBs2H.d.ts} +1 -1
  86. package/dist/{surface-C8RRg_Bh.d.cts → surface-Cn30xIV6.d.cts} +6 -1
  87. package/dist/{surface-C8RRg_Bh.d.ts → surface-Cn30xIV6.d.ts} +6 -1
  88. package/dist/{svg-D_cfkhlB.d.cts → svg-BnRj0q8i.d.cts} +16 -4
  89. package/dist/{svg-wIaKLrU0.d.ts → svg-CmmBFfGT.d.ts} +16 -4
  90. package/dist/{types-DtL_qLFz.d.ts → types-1SUQKDAw.d.ts} +273 -4
  91. package/dist/{types-DyQq-WPY.d.cts → types-yINF17Ta.d.cts} +273 -4
  92. package/dist/vector/index.cjs +12170 -7343
  93. package/dist/vector/index.cjs.map +1 -1
  94. package/dist/vector/index.d.cts +1579 -16
  95. package/dist/vector/index.d.ts +1579 -16
  96. package/dist/vector/index.js +6303 -1476
  97. package/dist/vector/index.js.map +1 -1
  98. package/dist/warp-B39VsOtd.d.cts +348 -0
  99. package/dist/warp-DMN30aY6.d.ts +348 -0
  100. package/dist/zlib-dxQdgHyN.d.cts +95 -0
  101. package/dist/zlib-dxQdgHyN.d.ts +95 -0
  102. package/package.json +9 -2
  103. package/skills/pixerate-image-editor/SKILL.md +13 -36
  104. package/skills/pixerate-image-editor/references/color-management.md +42 -0
  105. package/skills/pixerate-image-editor/references/photoshop-files.md +41 -0
  106. package/skills/pixerate-paint-editor/SKILL.md +136 -4
  107. package/skills/pixerate-vector/SKILL.md +72 -2
  108. package/dist/chunk-BLWCAQCW.js.map +0 -1
  109. package/dist/chunk-CZOXTEMN.js.map +0 -1
  110. package/dist/chunk-HNS7UHCM.js.map +0 -1
  111. package/dist/chunk-JLYX4V57.cjs +0 -2001
  112. package/dist/chunk-JLYX4V57.cjs.map +0 -1
  113. package/dist/chunk-KB2YBCVS.js +0 -2001
  114. package/dist/chunk-KB2YBCVS.js.map +0 -1
  115. package/dist/chunk-LQEEDHOP.js.map +0 -1
  116. package/dist/chunk-POGBUYWE.cjs.map +0 -1
  117. package/dist/chunk-W3GXSUSQ.cjs.map +0 -1
  118. package/dist/chunk-XIOMMGPD.cjs.map +0 -1
  119. package/dist/chunk-YGIMK4NX.cjs.map +0 -1
  120. package/dist/homography-CZ-tFjay.d.cts +0 -50
  121. package/dist/homography-Ctfjoc1b.d.ts +0 -50
  122. package/dist/warp-CWHZzE3x.d.ts +0 -118
  123. package/dist/warp-D5jz_tN7.d.cts +0 -118
  124. /package/dist/{chunk-LPYOIVLA.js.map → chunk-LKCYANMW.js.map} +0 -0
  125. /package/dist/{chunk-Z4BC6M74.js.map → chunk-UBIXVXPR.js.map} +0 -0
@@ -26,178 +26,254 @@ import {
26
26
  tilesInRect,
27
27
  translateSurface,
28
28
  writeRegion
29
- } from "./chunk-HNS7UHCM.js";
29
+ } from "./chunk-XK5LZKBD.js";
30
+ import {
31
+ deflate,
32
+ inflate
33
+ } from "./chunk-6FCKOS2B.js";
30
34
 
31
- // src/raster/blur.ts
32
- function gaussianKernel(sigma) {
33
- const r = Math.ceil(sigma * 3);
34
- const k = new Float32Array(2 * r + 1);
35
- let s = 0;
36
- for (let i = -r; i <= r; i++) {
37
- const v = Math.exp(-(i * i) / (2 * sigma * sigma));
38
- k[i + r] = v;
39
- s += v;
40
- }
41
- for (let i = 0; i < k.length; i++) k[i] /= s;
42
- return k;
35
+ // src/raster/deep.ts
36
+ var BIT_DEPTHS = [8, 16, 32];
37
+ var isBitDepth = (v) => v === 8 || v === 16 || v === 32;
38
+ var TILE_PIXELS = TILE * TILE;
39
+ function srgbDecode(v) {
40
+ return v <= 0.04045 ? v / 12.92 : Math.pow((v + 0.055) / 1.055, 2.4);
41
+ }
42
+ function srgbEncode(v) {
43
+ if (!(v > 0)) return 0;
44
+ return v <= 31308e-7 ? v * 12.92 : 1.055 * Math.pow(v, 1 / 2.4) - 0.055;
45
+ }
46
+ var LIN8 = null;
47
+ var LIN16 = null;
48
+ function lin8() {
49
+ if (!LIN8) {
50
+ LIN8 = new Float32Array(256);
51
+ for (let i = 0; i < 256; i++) LIN8[i] = srgbDecode(i / 255);
52
+ }
53
+ return LIN8;
54
+ }
55
+ function lin16() {
56
+ if (!LIN16) {
57
+ LIN16 = new Float32Array(65536);
58
+ for (let i = 0; i < 65536; i++) LIN16[i] = srgbDecode(i / 65535);
59
+ }
60
+ return LIN16;
61
+ }
62
+ function encode16(v) {
63
+ if (!(v > 0)) return 0;
64
+ if (v >= 1) return 65535;
65
+ return Math.round(srgbEncode(v) * 65535);
66
+ }
67
+ var ENC8 = null;
68
+ function encode8(v) {
69
+ if (!(v > 0)) return 0;
70
+ if (v >= 1) return 255;
71
+ if (!ENC8) {
72
+ ENC8 = new Uint8Array(65536);
73
+ for (let i = 0; i < 65536; i++) ENC8[i] = Math.round(srgbEncode(i / 65535) * 255);
74
+ }
75
+ return ENC8[Math.round(v * 65535)];
76
+ }
77
+ function to16From8(data, out = new Uint16Array(data.length)) {
78
+ for (let i = 0; i < data.length; i++) out[i] = data[i] * 257;
79
+ return out;
43
80
  }
44
- var DIRECT_GAUSSIAN_MAX_SIGMA = 8;
45
- function boxRadii(sigma) {
46
- const n = 3;
47
- const wIdeal = Math.sqrt(12 * sigma * sigma / n + 1);
48
- let wl = Math.floor(wIdeal);
49
- if (wl % 2 === 0) wl--;
50
- const wu = wl + 2;
51
- const mIdeal = (12 * sigma * sigma - n * wl * wl - 4 * n * wl - 3 * n) / (-4 * wl - 4);
52
- const m = Math.round(mIdeal);
53
- const sizes = [0, 1, 2].map((i) => i < m ? wl : wu);
54
- return sizes.map((s) => (s - 1) / 2);
81
+ function to32From8(data, channels, out = new Float32Array(data.length)) {
82
+ if (channels === 1) {
83
+ for (let i = 0; i < data.length; i++) out[i] = data[i] / 255;
84
+ return out;
85
+ }
86
+ const t = lin8();
87
+ for (let i = 0; i < data.length; i += 4) {
88
+ out[i] = t[data[i]];
89
+ out[i + 1] = t[data[i + 1]];
90
+ out[i + 2] = t[data[i + 2]];
91
+ out[i + 3] = data[i + 3] / 255;
92
+ }
93
+ return out;
55
94
  }
56
- function convolveLine(src, off, stride, len, k, edge, dst) {
57
- const r = (k.length - 1) / 2;
58
- for (let i = 0; i < len; i++) {
59
- let a = 0;
60
- const lo = i - r;
61
- for (let j = 0; j < k.length; j++) {
62
- let x = lo + j;
63
- if (x < 0 || x >= len) {
64
- if (edge === "zero") continue;
65
- x = x < 0 ? 0 : len - 1;
66
- }
67
- a += src[off + x * stride] * k[j];
68
- }
69
- dst[i] = a;
95
+ function to32From16(data, channels, out = new Float32Array(data.length)) {
96
+ if (channels === 1) {
97
+ for (let i = 0; i < data.length; i++) out[i] = data[i] / 65535;
98
+ return out;
99
+ }
100
+ const t = lin16();
101
+ for (let i = 0; i < data.length; i += 4) {
102
+ out[i] = t[data[i]];
103
+ out[i + 1] = t[data[i + 1]];
104
+ out[i + 2] = t[data[i + 2]];
105
+ out[i + 3] = data[i + 3] / 65535;
70
106
  }
107
+ return out;
71
108
  }
72
- function boxesLine(src, off, stride, len, radii, edge, a, b, dst) {
73
- const pad = radii.reduce((s, r) => s + r, 0);
74
- const plen = len + 2 * pad;
75
- for (let i = 0; i < plen; i++) {
76
- const j = i - pad;
77
- a[i] = j < 0 ? edge === "zero" ? 0 : src[off] : j >= len ? edge === "zero" ? 0 : src[off + (len - 1) * stride] : src[off + j * stride];
109
+ function to16From32(data, channels, out = new Uint16Array(data.length)) {
110
+ const unit = (v) => v > 0 ? v < 1 ? Math.round(v * 65535) : 65535 : 0;
111
+ if (channels === 1) {
112
+ for (let i = 0; i < data.length; i++) out[i] = unit(data[i]);
113
+ return out;
78
114
  }
79
- let from = a;
80
- let to = b;
81
- for (const r of radii) {
82
- let sum = 0;
83
- for (let i = 0; i <= Math.min(r, plen - 1); i++) sum += from[i];
84
- const k = 2 * r + 1;
85
- for (let i = 0; i < plen; i++) {
86
- to[i] = sum / k;
87
- const add = i + r + 1;
88
- const drop = i - r;
89
- if (add < plen) sum += from[add];
90
- if (drop >= 0) sum -= from[drop];
91
- }
92
- const t = from;
93
- from = to;
94
- to = t;
115
+ for (let i = 0; i < data.length; i += 4) {
116
+ out[i] = encode16(data[i]);
117
+ out[i + 1] = encode16(data[i + 1]);
118
+ out[i + 2] = encode16(data[i + 2]);
119
+ out[i + 3] = unit(data[i + 3]);
95
120
  }
96
- for (let i = 0; i < len; i++) dst[i] = from[i + pad];
121
+ return out;
97
122
  }
98
- function gaussianBlur(src, w, h, sigma, edge = "zero") {
99
- const out = Float32Array.from(src);
100
- if (!(sigma >= 0.1) || w <= 0 || h <= 0) return out;
101
- const s = Math.min(sigma, 4 * Math.max(w, h));
102
- const line = new Float32Array(Math.max(w, h));
103
- const passes = [];
104
- if (s <= DIRECT_GAUSSIAN_MAX_SIGMA) {
105
- const k = gaussianKernel(s);
106
- passes.push((buf, off, stride, len) => convolveLine(buf, off, stride, len, k, edge, line));
107
- } else {
108
- const radii = boxRadii(s);
109
- const plen = Math.max(w, h) + 2 * radii.reduce((a2, r) => a2 + r, 0);
110
- const a = new Float32Array(plen);
111
- const b = new Float32Array(plen);
112
- passes.push((buf, off, stride, len) => boxesLine(buf, off, stride, len, radii, edge, a, b, line));
123
+ function to8From16(data, out = new Uint8ClampedArray(data.length)) {
124
+ for (let i = 0; i < data.length; i++) out[i] = Math.round(data[i] / 257);
125
+ return out;
126
+ }
127
+ function to8From32(data, channels, out = new Uint8ClampedArray(data.length)) {
128
+ if (channels === 1) {
129
+ for (let i = 0; i < data.length; i++) out[i] = Math.round(data[i] * 255);
130
+ return out;
113
131
  }
114
- for (const pass of passes) {
115
- for (let y = 0; y < h; y++) {
116
- pass(out, y * w, 1, w);
117
- out.set(line.subarray(0, w), y * w);
118
- }
132
+ for (let i = 0; i < data.length; i += 4) {
133
+ out[i] = encode8(data[i]);
134
+ out[i + 1] = encode8(data[i + 1]);
135
+ out[i + 2] = encode8(data[i + 2]);
136
+ out[i + 3] = Math.round(Math.min(1, Math.max(0, data[i + 3])) * 255);
119
137
  }
120
- for (const pass of passes) {
121
- for (let x = 0; x < w; x++) {
122
- pass(out, x, w, h);
123
- for (let y = 0; y < h; y++) out[y * w + x] = line[y];
138
+ return out;
139
+ }
140
+ function proxyOf(deep, channels, out) {
141
+ return deep instanceof Uint16Array ? to8From16(deep, out) : to8From32(deep, channels, out);
142
+ }
143
+ var depthOf = (deep) => deep instanceof Uint16Array ? 16 : 32;
144
+ function deepTile(deep, channels, defaultValue = 0) {
145
+ const data = proxyOf(deep, channels);
146
+ if (deep instanceof Uint16Array) {
147
+ let exact = true;
148
+ for (let i = 0; i < deep.length; i++) {
149
+ if (deep[i] % 257 !== 0) {
150
+ exact = false;
151
+ break;
152
+ }
153
+ }
154
+ if (exact) return finishTile(data, channels, defaultValue);
155
+ } else if (channels === 4 && defaultValue === 0) {
156
+ let empty = true;
157
+ for (let i = 3; i < deep.length; i += 4) {
158
+ if (deep[i] !== 0) {
159
+ empty = false;
160
+ break;
161
+ }
124
162
  }
163
+ if (empty) return null;
164
+ }
165
+ return { data, uniform: null, deep };
166
+ }
167
+ function tileSamples16(tile, channels, defaultValue = 0) {
168
+ const deep = tile?.deep;
169
+ if (deep instanceof Uint16Array) return deep;
170
+ if (deep instanceof Float32Array) return to16From32(deep, channels);
171
+ if (tile) return to16From8(tile.data);
172
+ return new Uint16Array(TILE_PIXELS * channels).fill(defaultValue * 257);
173
+ }
174
+ function tileSamples32(tile, channels, defaultValue = 0) {
175
+ const deep = tile?.deep;
176
+ if (deep instanceof Float32Array) return deep;
177
+ if (deep instanceof Uint16Array) return to32From16(deep, channels);
178
+ if (tile) return to32From8(tile.data, channels);
179
+ const out = new Float32Array(TILE_PIXELS * channels);
180
+ if (defaultValue) {
181
+ if (channels === 1) out.fill(defaultValue / 255);
182
+ else to32From8(new Uint8ClampedArray(TILE_PIXELS * 4).fill(defaultValue), 4, out);
125
183
  }
126
184
  return out;
127
185
  }
128
-
129
- // src/raster/layers.ts
130
- var childrenOf = (l) => l.type === "group" ? l.children ?? null : null;
131
- function flattenLayers(layers) {
132
- const out = [];
133
- const walk = (list) => {
134
- for (const l of list) {
135
- out.push(l);
136
- const c = childrenOf(l);
137
- if (c) walk(c);
186
+ function tileSamples(tile, channels, depth, defaultValue = 0) {
187
+ return depth === 16 ? tileSamples16(tile, channels, defaultValue) : tileSamples32(tile, channels, defaultValue);
188
+ }
189
+ function surfaceDepth(surface) {
190
+ let d = 8;
191
+ for (const t of surface.tiles.values()) {
192
+ if (t.deep instanceof Float32Array) return 32;
193
+ if (t.deep) d = 16;
194
+ }
195
+ return d;
196
+ }
197
+ function readDeepRegion(surface, rect, depth) {
198
+ const ch = surface.channels;
199
+ const w = rect.width;
200
+ const h = rect.height;
201
+ const out = depth === 16 ? new Uint16Array(w * h * ch) : new Float32Array(w * h * ch);
202
+ const fill2 = tileSamples(void 0, ch, depth, surface.defaultValue);
203
+ if (surface.defaultValue) for (let i = 0; i < out.length; i += ch) for (let c = 0; c < ch; c++) out[i + c] = fill2[c];
204
+ for (const { tx, ty } of tilesInRect(rect)) {
205
+ const tile = surface.tiles.get(tileKey(tx, ty));
206
+ if (!tile) continue;
207
+ const src = tileSamples(tile, ch, depth, surface.defaultValue);
208
+ const ox = tx * TILE;
209
+ const oy = ty * TILE;
210
+ const x0 = Math.max(rect.x, ox);
211
+ const y0 = Math.max(rect.y, oy);
212
+ const x1 = Math.min(rect.x + w, ox + TILE);
213
+ const y1 = Math.min(rect.y + h, oy + TILE);
214
+ const span = (x1 - x0) * ch;
215
+ for (let yy = y0; yy < y1; yy++) {
216
+ const s = ((yy - oy) * TILE + (x0 - ox)) * ch;
217
+ const d = ((yy - rect.y) * w + (x0 - rect.x)) * ch;
218
+ out.set(src.subarray(s, s + span), d);
138
219
  }
139
- };
140
- walk(layers);
220
+ }
141
221
  return out;
142
222
  }
143
- function findLayer(layers, id) {
144
- const walk = (list, parent, path) => {
145
- for (let i = 0; i < list.length; i++) {
146
- const l = list[i];
147
- if (l.id === id) return { layer: l, parent, index: i, path };
148
- const c = childrenOf(l);
149
- if (c) {
150
- const g = l;
151
- const hit = walk(c, g, [...path, g]);
152
- if (hit) return hit;
153
- }
223
+ function writeDeepRegion(surface, rect, samples) {
224
+ const ch = surface.channels;
225
+ const w = rect.width;
226
+ const h = rect.height;
227
+ if (w <= 0 || h <= 0) return surface;
228
+ if (samples.length < w * h * ch) throw new Error(`writeDeepRegion: expected ${w * h * ch} samples, got ${samples.length}`);
229
+ const depth = depthOf(samples);
230
+ const tiles = new Map(surface.tiles);
231
+ for (const { tx, ty } of tilesInRect(rect)) {
232
+ const key = tileKey(tx, ty);
233
+ const ox = tx * TILE;
234
+ const oy = ty * TILE;
235
+ const x0 = Math.max(rect.x, ox);
236
+ const y0 = Math.max(rect.y, oy);
237
+ const x1 = Math.min(rect.x + w, ox + TILE);
238
+ const y1 = Math.min(rect.y + h, oy + TILE);
239
+ const full = x0 === ox && y0 === oy && x1 === ox + TILE && y1 === oy + TILE;
240
+ const base = full ? null : tileSamples(surface.tiles.get(key), ch, depth, surface.defaultValue);
241
+ const t = base ? base.slice() : depth === 16 ? new Uint16Array(TILE_PIXELS * ch) : new Float32Array(TILE_PIXELS * ch);
242
+ const span = (x1 - x0) * ch;
243
+ for (let yy = y0; yy < y1; yy++) {
244
+ const s = ((yy - rect.y) * w + (x0 - rect.x)) * ch;
245
+ const d = ((yy - oy) * TILE + (x0 - ox)) * ch;
246
+ t.set(samples.subarray(s, s + span), d);
154
247
  }
155
- return null;
156
- };
157
- return walk(layers, null, []);
248
+ const tile = deepTile(t, ch, surface.defaultValue);
249
+ if (tile) tiles.set(key, tile);
250
+ else tiles.delete(key);
251
+ }
252
+ return new TiledSurface(ch, tiles, surface.defaultValue);
158
253
  }
159
- function mapLayer(layers, id, fn) {
160
- let changed = false;
161
- const walk = (list) => {
162
- let out = null;
163
- for (let i = 0; i < list.length; i++) {
164
- const l = list[i];
165
- let next = l;
166
- if (l.id === id) {
167
- next = fn(l);
168
- changed = true;
169
- } else {
170
- const c = childrenOf(l);
171
- if (c) {
172
- const children = walk(c);
173
- if (children !== c) next = { ...l, children };
174
- }
175
- }
176
- if (next !== l) {
177
- if (!out) out = list.slice(0, i);
178
- if (next) out.push(next);
179
- } else if (out) out.push(l);
180
- }
181
- return out ?? list;
182
- };
183
- const result = walk(layers);
184
- return changed ? result : layers;
254
+ function surfaceFromDeepPixels(pixels, channels = 4, x = 0, y = 0, defaultValue = 0) {
255
+ return writeDeepRegion(emptySurface(channels, defaultValue), { x, y, width: pixels.width, height: pixels.height }, pixels.data);
185
256
  }
186
- function insertLayer(layers, layer, parentId, index) {
187
- const put = (list) => {
188
- const at = index === void 0 ? list.length : Math.max(0, Math.min(list.length, index));
189
- const next = list.slice();
190
- next.splice(at, 0, layer);
191
- return next;
192
- };
193
- if (!parentId) return put(layers);
194
- return mapLayer(layers, parentId, (g) => {
195
- const c = childrenOf(g);
196
- return c ? { ...g, children: put(c) } : g;
197
- });
257
+ function convertSurfaceDepth(surface, depth) {
258
+ let changed = false;
259
+ const tiles = new Map(surface.tiles);
260
+ const ch = surface.channels;
261
+ for (const [key, tile] of surface.tiles) {
262
+ const deep = tile.deep;
263
+ if (!deep || depthOf(deep) === depth) continue;
264
+ changed = true;
265
+ let next;
266
+ if (depth === 8) next = finishTile(tile.data, ch, surface.defaultValue);
267
+ else next = deepTile(depth === 16 ? to16From32(deep, ch) : to32From16(deep, ch), ch, surface.defaultValue);
268
+ if (next) tiles.set(key, next);
269
+ else tiles.delete(key);
270
+ }
271
+ return changed ? new TiledSurface(ch, tiles, surface.defaultValue) : surface;
198
272
  }
199
- function isLayerLocked(layer, what) {
200
- return Boolean(layer.locks?.all || layer.locks?.[what]);
273
+ function deepBytes(surface) {
274
+ let n = 0;
275
+ for (const t of surface.tiles.values()) if (t.deep) n += t.deep.byteLength;
276
+ return n;
201
277
  }
202
278
 
203
279
  // src/raster/effects/model.ts
@@ -559,73 +635,502 @@ function validateLayerEffect(v, path = "effect") {
559
635
  break;
560
636
  }
561
637
  }
562
- function mergeLayerEffect(effect, changes) {
563
- if ("kind" in changes && changes.kind !== effect.kind) throw new LayerEffectError(`kind cannot change (${effect.kind}); remove the effect and add a new one.`);
564
- if ("id" in changes && changes.id !== effect.id) throw new LayerEffectError("id cannot change.");
565
- const next = { ...effect };
566
- for (const [k, v] of Object.entries(changes)) {
567
- if (v === null) delete next[k];
568
- else next[k] = v;
638
+ function mergeLayerEffect(effect, changes) {
639
+ if ("kind" in changes && changes.kind !== effect.kind) throw new LayerEffectError(`kind cannot change (${effect.kind}); remove the effect and add a new one.`);
640
+ if ("id" in changes && changes.id !== effect.id) throw new LayerEffectError("id cannot change.");
641
+ const next = { ...effect };
642
+ for (const [k, v] of Object.entries(changes)) {
643
+ if (v === null) delete next[k];
644
+ else next[k] = v;
645
+ }
646
+ validateLayerEffect(next);
647
+ return next;
648
+ }
649
+ function validateLayerEffects(v) {
650
+ if (!v || typeof v !== "object") fail("effects", "must be { enabled, items }.");
651
+ const r = v;
652
+ bool(r, "enabled", "effects");
653
+ if (r.scale !== void 0) num(r, "scale", "effects", 0.01, 10);
654
+ if (!Array.isArray(r.items)) fail("effects.items", "must be a list.");
655
+ const ids = /* @__PURE__ */ new Set();
656
+ r.items.forEach((e, i) => {
657
+ validateLayerEffect(e, `effects.items[${i}]`);
658
+ if (ids.has(e.id)) fail(`effects.items[${i}].id`, `duplicate id ${e.id}.`);
659
+ ids.add(e.id);
660
+ });
661
+ }
662
+ function normalizeLayerEffects(raw) {
663
+ if (!raw || typeof raw !== "object") return void 0;
664
+ const r = raw;
665
+ const items = [];
666
+ const ids = /* @__PURE__ */ new Set();
667
+ if (Array.isArray(r.items)) {
668
+ for (const it of r.items) {
669
+ if (!it || typeof it !== "object" || !isLayerEffectKind(it.kind)) continue;
670
+ const kind = it.kind;
671
+ const merged = { ...defaultLayerEffect(kind), ...it };
672
+ if (typeof merged.id !== "string" || !merged.id || ids.has(merged.id)) merged.id = newEffectId();
673
+ try {
674
+ validateLayerEffect(merged);
675
+ } catch {
676
+ continue;
677
+ }
678
+ ids.add(merged.id);
679
+ items.push(merged);
680
+ }
681
+ }
682
+ const out = { enabled: r.enabled !== false, items };
683
+ if (typeof r.scale === "number" && Number.isFinite(r.scale) && r.scale > 0 && r.scale !== 1) out.scale = r.scale;
684
+ if (r.psd && typeof r.psd === "object") {
685
+ const p = r.psd;
686
+ if (typeof p.key === "string" && p.data instanceof Uint8Array) out.psd = { key: p.key, data: p.data };
687
+ }
688
+ return items.length || out.psd ? out : void 0;
689
+ }
690
+ function effectsFingerprint(effects) {
691
+ if (!effects) return "";
692
+ const items = effects.items.map((e) => {
693
+ const { id: _id, ...rest } = e;
694
+ return rest;
695
+ });
696
+ return stableStringify([effects.enabled, effectsScale(effects), items]);
697
+ }
698
+ function stableStringify(v) {
699
+ if (Array.isArray(v)) return `[${v.map(stableStringify).join(",")}]`;
700
+ if (v && typeof v === "object") {
701
+ const keys = Object.keys(v).filter((k) => v[k] !== void 0).sort();
702
+ return `{${keys.map((k) => `${JSON.stringify(k)}:${stableStringify(v[k])}`).join(",")}}`;
703
+ }
704
+ return JSON.stringify(v);
705
+ }
706
+
707
+ // src/raster/deep-compositor.ts
708
+ var isGroup = (l) => l.type === "group";
709
+ var DeepCompositor = class {
710
+ constructor(base, profile, deep, depth) {
711
+ this.base = base;
712
+ this.profile = profile;
713
+ this.deep = deep;
714
+ this.depth = depth;
715
+ this.linear = depth === 32;
716
+ }
717
+ base;
718
+ profile;
719
+ deep;
720
+ depth;
721
+ sources;
722
+ linear;
723
+ /** The composite of `layers` over `rect` as float RGBA in the working space (`rect.width × rect.height × 4`). */
724
+ composite(layers, rect, sources) {
725
+ this.sources = sources;
726
+ const acc = new Float32Array(Math.max(0, rect.width * rect.height * 4));
727
+ if (rect.width > 0 && rect.height > 0) this.runSteps(this.buildSteps(layers), acc, true, rect);
728
+ return acc;
729
+ }
730
+ // --- Steps (as RasterCompositor.buildSteps) ------------------------------------
731
+ isPixel(l) {
732
+ return l.type === "pixel" || (this.profile.isPixelLike?.(l) ?? false);
733
+ }
734
+ isFilter(l) {
735
+ return this.profile.isFilterLayer?.(l) ?? false;
736
+ }
737
+ buildSteps(layers) {
738
+ const steps = [];
739
+ for (const layer of layers) {
740
+ const last = steps[steps.length - 1];
741
+ if (layer.clipped && last && (last.kind === "content" || last.kind === "group")) {
742
+ last.clipped.push(layer);
743
+ continue;
744
+ }
745
+ if (this.isFilter(layer)) {
746
+ if (last && last.kind === "adjust") last.layers.push(layer);
747
+ else steps.push({ kind: "adjust", layers: [layer] });
748
+ } else if (isGroup(layer)) steps.push({ kind: "group", layer, clipped: [], steps: this.buildSteps(layer.children ?? []) });
749
+ else steps.push({ kind: "content", layer, clipped: [] });
750
+ }
751
+ return steps;
752
+ }
753
+ runSteps(steps, acc, empty, r) {
754
+ for (const s of steps) empty = this.runStep(s, acc, empty, r);
755
+ return empty;
756
+ }
757
+ runStep(step, acc, empty, r) {
758
+ if (step.kind === "adjust") {
759
+ if (empty) return true;
760
+ this.applyFilterRun(step.layers, acc, r);
761
+ return false;
762
+ }
763
+ const layer = step.layer;
764
+ if (!layer.visible) return empty;
765
+ const clipped = step.clipped.filter((l) => l.visible);
766
+ const coverage = this.renderedAlone(layer) ? null : this.base.maskCoverage(layer, r, this.sources);
767
+ if (coverage && coverage.every((v) => v <= 0)) return empty;
768
+ if (step.kind === "group" && !this.renderedAlone(layer)) {
769
+ if (layer.blend === "pass-through" && !clipped.length) {
770
+ if (layer.opacity >= 1 && !coverage) return this.runSteps(step.steps, acc, empty, r);
771
+ const before = acc.slice();
772
+ const stillEmpty = this.runSteps(step.steps, acc, empty, r);
773
+ lerp(acc, before, layer.opacity, coverage);
774
+ return empty && stillEmpty;
775
+ }
776
+ const buf2 = new Float32Array(acc.length);
777
+ if (this.runSteps(step.steps, buf2, true, r)) return empty;
778
+ this.applyClipped(clipped, buf2, r);
779
+ const mode2 = layer.blend === "pass-through" ? "normal" : layer.blend;
780
+ this.blend(acc, buf2, mode2, layer.opacity, coverage);
781
+ return false;
782
+ }
783
+ const content = this.content(layer, r);
784
+ if (!content) return empty;
785
+ const alone = this.renderedAlone(layer);
786
+ const fill2 = !alone && this.isPixel(layer) ? layer.fillOpacity ?? 1 : 1;
787
+ const mode = this.blendOf(layer);
788
+ if (!clipped.length) {
789
+ this.blend(acc, content, mode, layer.opacity * fill2, coverage);
790
+ return false;
791
+ }
792
+ const buf = new Float32Array(acc.length);
793
+ this.blend(buf, content, "normal", fill2, coverage);
794
+ this.applyClipped(clipped, buf, r);
795
+ this.blend(acc, buf, mode, layer.opacity, null);
796
+ return false;
797
+ }
798
+ applyClipped(clipped, buf, r) {
799
+ let run = [];
800
+ const flush = () => {
801
+ if (run.length) this.applyFilterRun(run, buf, r);
802
+ run = [];
803
+ };
804
+ for (const c of clipped) {
805
+ if (this.isFilter(c)) {
806
+ run.push(c);
807
+ continue;
808
+ }
809
+ flush();
810
+ const alone = this.renderedAlone(c);
811
+ const coverage = alone ? null : this.base.maskCoverage(c, r, this.sources);
812
+ let src;
813
+ if (isGroup(c) && !alone) {
814
+ src = new Float32Array(buf.length);
815
+ if (this.runSteps(this.buildSteps(c.children ?? []), src, true, r)) continue;
816
+ } else src = this.content(c, r);
817
+ if (!src) continue;
818
+ const fill2 = !alone && this.isPixel(c) ? c.fillOpacity ?? 1 : 1;
819
+ const keep = new Float32Array(buf.length >> 2);
820
+ for (let i = 3, p = 0; i < buf.length; i += 4, p++) keep[p] = buf[i];
821
+ this.blend(buf, src, c.blend === "pass-through" ? "normal" : this.blendOf(c), c.opacity * fill2, coverage);
822
+ for (let i = 3, p = 0; i < buf.length; i += 4, p++) buf[i] = keep[p];
823
+ }
824
+ flush();
825
+ }
826
+ applyFilterRun(layers, acc, r) {
827
+ const visible = [];
828
+ let masks;
829
+ for (const node of layers) {
830
+ if (!node.visible) continue;
831
+ const cov = this.base.maskCoverage(node, r, this.sources);
832
+ if (cov) {
833
+ if (cov.every((v) => v <= 0)) continue;
834
+ (masks ??= /* @__PURE__ */ new Map()).set(node.id, cov);
835
+ }
836
+ visible.push(node);
837
+ }
838
+ if (!visible.length) return;
839
+ if (this.deep.applyFilterRunDeep) {
840
+ if (this.linear) mapColour(acc, srgbEncode);
841
+ this.deep.applyFilterRunDeep(visible, acc, r, masks, this.sources);
842
+ if (this.linear) mapColour(acc, srgbDecode);
843
+ return;
844
+ }
845
+ const bytes = this.to8(acc);
846
+ this.profile.applyFilterRun?.(visible, bytes, r, masks, this.sources);
847
+ acc.set(this.from8(bytes));
848
+ }
849
+ // --- Layer content ---------------------------------------------------------------
850
+ /** Layers drawn by the 8-bit compositor alone (effects, pixel filters, content the editor draws). */
851
+ renderedAlone(layer) {
852
+ if (hasActiveEffects(layer.effects) && !this.isFilter(layer)) return true;
853
+ if (this.isPixel(layer)) return Boolean(this.profile.pixelFilters?.(layer));
854
+ return !isGroup(layer);
855
+ }
856
+ blendOf(layer) {
857
+ return this.profile.contentBlend?.(layer) ?? layer.blend;
858
+ }
859
+ /** A layer's float RGBA over `r` (straight alpha, working space), or `null` when it has none there. */
860
+ content(layer, r) {
861
+ if (this.renderedAlone(layer)) {
862
+ const solo = { ...layer, blend: isGroup(layer) && layer.blend === "pass-through" ? "pass-through" : "normal", opacity: 1, clipped: false };
863
+ const bytes = this.base.composite([solo], r, this.sources);
864
+ return this.from8(bytes);
865
+ }
866
+ const surface = this.sources.surfaceOf ? this.sources.surfaceOf(layer) : layer.surface;
867
+ if (!surface) return null;
868
+ const ox = layer.offset?.x ?? 0;
869
+ const oy = layer.offset?.y ?? 0;
870
+ const samples = readDeepRegion(surface, { x: r.x - ox, y: r.y - oy, width: r.width, height: r.height }, this.depth);
871
+ if (samples instanceof Float32Array) return samples;
872
+ const out = new Float32Array(samples.length);
873
+ for (let i = 0; i < samples.length; i++) out[i] = samples[i] / 65535;
874
+ return out;
875
+ }
876
+ /** 8-bit RGBA to the working space. */
877
+ from8(bytes) {
878
+ if (this.linear) return to32From8(bytes, 4);
879
+ const out = new Float32Array(bytes.length);
880
+ for (let i = 0; i < bytes.length; i++) out[i] = bytes[i] / 255;
881
+ return out;
882
+ }
883
+ /** The working space to 8-bit RGBA. */
884
+ to8(acc) {
885
+ const out = new Uint8ClampedArray(acc.length);
886
+ for (let i = 0; i < acc.length; i += 4) {
887
+ for (let c = 0; c < 3; c++) out[i + c] = Math.round((this.linear ? srgbEncode(acc[i + c]) : acc[i + c]) * 255);
888
+ out[i + 3] = Math.round(acc[i + 3] * 255);
889
+ }
890
+ return out;
891
+ }
892
+ // --- Blending --------------------------------------------------------------------
893
+ /** `src` over `dst` with `mode` at `alpha` × coverage (straight alpha, float), as `blendTile`. */
894
+ blend(dst, src, mode, alpha, coverage) {
895
+ if (!(alpha > 0)) return;
896
+ const normal = mode === "normal";
897
+ const pigment = mode === "pigment";
898
+ const cb = [0, 0, 0];
899
+ const cs = [0, 0, 0];
900
+ const mix = [0, 0, 0];
901
+ for (let i = 0, p = 0; i < dst.length; i += 4, p++) {
902
+ const sa = src[i + 3];
903
+ if (!(sa > 0)) continue;
904
+ const k = coverage ? alpha * coverage[p] : alpha;
905
+ if (!(k > 0)) continue;
906
+ const as = Math.min(1, sa * k);
907
+ const ab = dst[i + 3];
908
+ const ao = as + ab * (1 - as);
909
+ if (ao <= 0) {
910
+ dst[i] = dst[i + 1] = dst[i + 2] = dst[i + 3] = 0;
911
+ continue;
912
+ }
913
+ if (normal && as >= 1) {
914
+ dst[i] = src[i];
915
+ dst[i + 1] = src[i + 1];
916
+ dst[i + 2] = src[i + 2];
917
+ dst[i + 3] = 1;
918
+ continue;
919
+ }
920
+ for (let c = 0; c < 3; c++) {
921
+ cb[c] = dst[i + c];
922
+ cs[c] = src[i + c];
923
+ }
924
+ if (pigment) {
925
+ if (this.linear) for (let c = 0; c < 3; c++) cb[c] = srgbEncode(cb[c]), cs[c] = srgbEncode(cs[c]);
926
+ mixPigmentRgb(cb, cs, as / ao, mix);
927
+ for (let c = 0; c < 3; c++) dst[i + c] = this.linear ? srgbDecode(mix[c]) : mix[c];
928
+ dst[i + 3] = ao;
929
+ continue;
930
+ }
931
+ const m = normal ? cs : blendRgb(mode, cb, cs);
932
+ const wb = (1 - as) * ab;
933
+ const ws = (1 - ab) * as;
934
+ const wm = as * ab;
935
+ for (let c = 0; c < 3; c++) dst[i + c] = (wb * cb[c] + ws * cs[c] + wm * m[c]) / ao;
936
+ dst[i + 3] = ao;
937
+ }
938
+ }
939
+ };
940
+ function lerp(dst, before, alpha, coverage) {
941
+ for (let i = 0, p = 0; i < dst.length; i += 4, p++) {
942
+ const k = coverage ? alpha * coverage[p] : alpha;
943
+ if (k >= 1) continue;
944
+ for (let c = 0; c < 4; c++) dst[i + c] = before[i + c] + (dst[i + c] - before[i + c]) * k;
945
+ }
946
+ }
947
+ function mapColour(data, f) {
948
+ for (let i = 0; i < data.length; i += 4) {
949
+ data[i] = f(data[i]);
950
+ data[i + 1] = f(data[i + 1]);
951
+ data[i + 2] = f(data[i + 2]);
952
+ }
953
+ }
954
+ function workingToSamples(data, depth) {
955
+ if (depth === 32) return data;
956
+ const out = new Uint16Array(data.length);
957
+ for (let i = 0; i < data.length; i++) {
958
+ const v = data[i];
959
+ out[i] = v > 0 ? v < 1 ? Math.round(v * 65535) : 65535 : 0;
960
+ }
961
+ return out;
962
+ }
963
+
964
+ // src/raster/blur.ts
965
+ function gaussianKernel(sigma) {
966
+ const r = Math.ceil(sigma * 3);
967
+ const k = new Float32Array(2 * r + 1);
968
+ let s = 0;
969
+ for (let i = -r; i <= r; i++) {
970
+ const v = Math.exp(-(i * i) / (2 * sigma * sigma));
971
+ k[i + r] = v;
972
+ s += v;
973
+ }
974
+ for (let i = 0; i < k.length; i++) k[i] /= s;
975
+ return k;
976
+ }
977
+ var DIRECT_GAUSSIAN_MAX_SIGMA = 8;
978
+ function boxRadii(sigma) {
979
+ const n = 3;
980
+ const wIdeal = Math.sqrt(12 * sigma * sigma / n + 1);
981
+ let wl = Math.floor(wIdeal);
982
+ if (wl % 2 === 0) wl--;
983
+ const wu = wl + 2;
984
+ const mIdeal = (12 * sigma * sigma - n * wl * wl - 4 * n * wl - 3 * n) / (-4 * wl - 4);
985
+ const m = Math.round(mIdeal);
986
+ const sizes = [0, 1, 2].map((i) => i < m ? wl : wu);
987
+ return sizes.map((s) => (s - 1) / 2);
988
+ }
989
+ function convolveLine(src, off, stride, len, k, edge, dst) {
990
+ const r = (k.length - 1) / 2;
991
+ for (let i = 0; i < len; i++) {
992
+ let a = 0;
993
+ const lo = i - r;
994
+ for (let j = 0; j < k.length; j++) {
995
+ let x = lo + j;
996
+ if (x < 0 || x >= len) {
997
+ if (edge === "zero") continue;
998
+ x = x < 0 ? 0 : len - 1;
999
+ }
1000
+ a += src[off + x * stride] * k[j];
1001
+ }
1002
+ dst[i] = a;
1003
+ }
1004
+ }
1005
+ function boxesLine(src, off, stride, len, radii, edge, a, b, dst) {
1006
+ const pad = radii.reduce((s, r) => s + r, 0);
1007
+ const plen = len + 2 * pad;
1008
+ for (let i = 0; i < plen; i++) {
1009
+ const j = i - pad;
1010
+ a[i] = j < 0 ? edge === "zero" ? 0 : src[off] : j >= len ? edge === "zero" ? 0 : src[off + (len - 1) * stride] : src[off + j * stride];
1011
+ }
1012
+ let from = a;
1013
+ let to = b;
1014
+ for (const r of radii) {
1015
+ let sum = 0;
1016
+ for (let i = 0; i <= Math.min(r, plen - 1); i++) sum += from[i];
1017
+ const k = 2 * r + 1;
1018
+ for (let i = 0; i < plen; i++) {
1019
+ to[i] = sum / k;
1020
+ const add = i + r + 1;
1021
+ const drop = i - r;
1022
+ if (add < plen) sum += from[add];
1023
+ if (drop >= 0) sum -= from[drop];
1024
+ }
1025
+ const t = from;
1026
+ from = to;
1027
+ to = t;
1028
+ }
1029
+ for (let i = 0; i < len; i++) dst[i] = from[i + pad];
1030
+ }
1031
+ function gaussianBlur(src, w, h, sigma, edge = "zero") {
1032
+ const out = Float32Array.from(src);
1033
+ if (!(sigma >= 0.1) || w <= 0 || h <= 0) return out;
1034
+ const s = Math.min(sigma, 4 * Math.max(w, h));
1035
+ const line = new Float32Array(Math.max(w, h));
1036
+ const passes = [];
1037
+ if (s <= DIRECT_GAUSSIAN_MAX_SIGMA) {
1038
+ const k = gaussianKernel(s);
1039
+ passes.push((buf, off, stride, len) => convolveLine(buf, off, stride, len, k, edge, line));
1040
+ } else {
1041
+ const radii = boxRadii(s);
1042
+ const plen = Math.max(w, h) + 2 * radii.reduce((a2, r) => a2 + r, 0);
1043
+ const a = new Float32Array(plen);
1044
+ const b = new Float32Array(plen);
1045
+ passes.push((buf, off, stride, len) => boxesLine(buf, off, stride, len, radii, edge, a, b, line));
569
1046
  }
570
- validateLayerEffect(next);
571
- return next;
1047
+ for (const pass of passes) {
1048
+ for (let y = 0; y < h; y++) {
1049
+ pass(out, y * w, 1, w);
1050
+ out.set(line.subarray(0, w), y * w);
1051
+ }
1052
+ }
1053
+ for (const pass of passes) {
1054
+ for (let x = 0; x < w; x++) {
1055
+ pass(out, x, w, h);
1056
+ for (let y = 0; y < h; y++) out[y * w + x] = line[y];
1057
+ }
1058
+ }
1059
+ return out;
572
1060
  }
573
- function validateLayerEffects(v) {
574
- if (!v || typeof v !== "object") fail("effects", "must be { enabled, items }.");
575
- const r = v;
576
- bool(r, "enabled", "effects");
577
- if (r.scale !== void 0) num(r, "scale", "effects", 0.01, 10);
578
- if (!Array.isArray(r.items)) fail("effects.items", "must be a list.");
579
- const ids = /* @__PURE__ */ new Set();
580
- r.items.forEach((e, i) => {
581
- validateLayerEffect(e, `effects.items[${i}]`);
582
- if (ids.has(e.id)) fail(`effects.items[${i}].id`, `duplicate id ${e.id}.`);
583
- ids.add(e.id);
584
- });
1061
+
1062
+ // src/raster/layers.ts
1063
+ var childrenOf = (l) => l.type === "group" ? l.children ?? null : null;
1064
+ function flattenLayers(layers) {
1065
+ const out = [];
1066
+ const walk = (list) => {
1067
+ for (const l of list) {
1068
+ out.push(l);
1069
+ const c = childrenOf(l);
1070
+ if (c) walk(c);
1071
+ }
1072
+ };
1073
+ walk(layers);
1074
+ return out;
585
1075
  }
586
- function normalizeLayerEffects(raw) {
587
- if (!raw || typeof raw !== "object") return void 0;
588
- const r = raw;
589
- const items = [];
590
- const ids = /* @__PURE__ */ new Set();
591
- if (Array.isArray(r.items)) {
592
- for (const it of r.items) {
593
- if (!it || typeof it !== "object" || !isLayerEffectKind(it.kind)) continue;
594
- const kind = it.kind;
595
- const merged = { ...defaultLayerEffect(kind), ...it };
596
- if (typeof merged.id !== "string" || !merged.id || ids.has(merged.id)) merged.id = newEffectId();
597
- try {
598
- validateLayerEffect(merged);
599
- } catch {
600
- continue;
1076
+ function findLayer(layers, id) {
1077
+ const walk = (list, parent, path) => {
1078
+ for (let i = 0; i < list.length; i++) {
1079
+ const l = list[i];
1080
+ if (l.id === id) return { layer: l, parent, index: i, path };
1081
+ const c = childrenOf(l);
1082
+ if (c) {
1083
+ const g = l;
1084
+ const hit = walk(c, g, [...path, g]);
1085
+ if (hit) return hit;
601
1086
  }
602
- ids.add(merged.id);
603
- items.push(merged);
604
1087
  }
605
- }
606
- const out = { enabled: r.enabled !== false, items };
607
- if (typeof r.scale === "number" && Number.isFinite(r.scale) && r.scale > 0 && r.scale !== 1) out.scale = r.scale;
608
- if (r.psd && typeof r.psd === "object") {
609
- const p = r.psd;
610
- if (typeof p.key === "string" && p.data instanceof Uint8Array) out.psd = { key: p.key, data: p.data };
611
- }
612
- return items.length || out.psd ? out : void 0;
1088
+ return null;
1089
+ };
1090
+ return walk(layers, null, []);
613
1091
  }
614
- function effectsFingerprint(effects) {
615
- if (!effects) return "";
616
- const items = effects.items.map((e) => {
617
- const { id: _id, ...rest } = e;
618
- return rest;
1092
+ function mapLayer(layers, id, fn) {
1093
+ let changed = false;
1094
+ const walk = (list) => {
1095
+ let out = null;
1096
+ for (let i = 0; i < list.length; i++) {
1097
+ const l = list[i];
1098
+ let next = l;
1099
+ if (l.id === id) {
1100
+ next = fn(l);
1101
+ changed = true;
1102
+ } else {
1103
+ const c = childrenOf(l);
1104
+ if (c) {
1105
+ const children = walk(c);
1106
+ if (children !== c) next = { ...l, children };
1107
+ }
1108
+ }
1109
+ if (next !== l) {
1110
+ if (!out) out = list.slice(0, i);
1111
+ if (next) out.push(next);
1112
+ } else if (out) out.push(l);
1113
+ }
1114
+ return out ?? list;
1115
+ };
1116
+ const result = walk(layers);
1117
+ return changed ? result : layers;
1118
+ }
1119
+ function insertLayer(layers, layer, parentId, index) {
1120
+ const put = (list) => {
1121
+ const at = index === void 0 ? list.length : Math.max(0, Math.min(list.length, index));
1122
+ const next = list.slice();
1123
+ next.splice(at, 0, layer);
1124
+ return next;
1125
+ };
1126
+ if (!parentId) return put(layers);
1127
+ return mapLayer(layers, parentId, (g) => {
1128
+ const c = childrenOf(g);
1129
+ return c ? { ...g, children: put(c) } : g;
619
1130
  });
620
- return stableStringify([effects.enabled, effectsScale(effects), items]);
621
1131
  }
622
- function stableStringify(v) {
623
- if (Array.isArray(v)) return `[${v.map(stableStringify).join(",")}]`;
624
- if (v && typeof v === "object") {
625
- const keys = Object.keys(v).filter((k) => v[k] !== void 0).sort();
626
- return `{${keys.map((k) => `${JSON.stringify(k)}:${stableStringify(v[k])}`).join(",")}}`;
627
- }
628
- return JSON.stringify(v);
1132
+ function isLayerLocked(layer, what) {
1133
+ return Boolean(layer.locks?.all || layer.locks?.[what]);
629
1134
  }
630
1135
 
631
1136
  // src/raster/effects/patterns.ts
@@ -2079,8 +2584,8 @@ function renderLayerEffects(effects, layer, backdrop, canvas, ctx) {
2079
2584
  }
2080
2585
 
2081
2586
  // src/raster/compositor.ts
2082
- var TILE_PIXELS = TILE * TILE;
2083
- var TILE_BYTES = TILE_PIXELS * 4;
2587
+ var TILE_PIXELS2 = TILE * TILE;
2588
+ var TILE_BYTES = TILE_PIXELS2 * 4;
2084
2589
  function sameSig(a, b) {
2085
2590
  if (!a || a.key !== b.key || a.refs.length !== b.refs.length) return false;
2086
2591
  for (let i = 0; i < a.refs.length; i++) if (a.refs[i] !== b.refs[i]) return false;
@@ -2206,7 +2711,7 @@ function lerpTile(dst, before, alpha, coverage) {
2206
2711
  }
2207
2712
  }
2208
2713
  var ZERO_TILE = new Uint8ClampedArray(TILE_BYTES);
2209
- var isGroup = (l) => l.type === "group";
2714
+ var isGroup2 = (l) => l.type === "group";
2210
2715
  var RasterCompositor = class {
2211
2716
  constructor(profile = {}, options = {}) {
2212
2717
  this.profile = profile;
@@ -2345,7 +2850,7 @@ var RasterCompositor = class {
2345
2850
  if (this.isFilter(layer)) {
2346
2851
  if (last && last.kind === "adjust") last.layers.push(layer);
2347
2852
  else steps.push({ kind: "adjust", layers: [layer] });
2348
- } else if (isGroup(layer)) {
2853
+ } else if (isGroup2(layer)) {
2349
2854
  steps.push({ kind: "group", layer, clipped: [], steps: this.buildSteps(layer.children ?? []) });
2350
2855
  } else {
2351
2856
  steps.push({ kind: "content", layer, clipped: [] });
@@ -2356,7 +2861,7 @@ var RasterCompositor = class {
2356
2861
  }
2357
2862
  /** The index of the top-level step that holds layer `id` (searching groups and clipped layers), or -1. */
2358
2863
  stepIndexOf(steps, id) {
2359
- const holds = (l) => l.id === id || isGroup(l) && (l.children ?? []).some(holds);
2864
+ const holds = (l) => l.id === id || isGroup2(l) && (l.children ?? []).some(holds);
2360
2865
  return steps.findIndex((s) => s.kind === "adjust" ? s.layers.some(holds) : holds(s.layer) || s.clipped.some(holds));
2361
2866
  }
2362
2867
  /** Properties of a layer that change pixels, minus its surfaces (memoised per object). */
@@ -2504,7 +3009,7 @@ var RasterCompositor = class {
2504
3009
  }
2505
3010
  layerSig(layer, tx, ty) {
2506
3011
  if (this.isFilter(layer)) return { key: this.propsKey(layer), refs: this.maskRefs(layer, tx, ty, 0, 0) };
2507
- if (isGroup(layer)) return this.groupSig(layer, this.buildSteps(layer.children ?? []), tx, ty);
3012
+ if (isGroup2(layer)) return this.groupSig(layer, this.buildSteps(layer.children ?? []), tx, ty);
2508
3013
  return this.contentSig(layer, tx, ty);
2509
3014
  }
2510
3015
  groupSig(group, steps, tx, ty) {
@@ -2594,7 +3099,7 @@ var RasterCompositor = class {
2594
3099
  shapeSigs(layer, region) {
2595
3100
  const sigs = /* @__PURE__ */ new Map();
2596
3101
  if (region.width <= 0 || region.height <= 0) return sigs;
2597
- const steps = isGroup(layer) ? this.buildSteps(layer.children ?? []) : null;
3102
+ const steps = isGroup2(layer) ? this.buildSteps(layer.children ?? []) : null;
2598
3103
  for (const t of tilesInRect(region)) {
2599
3104
  sigs.set(tileKey(t.tx, t.ty), steps ? this.plainGroupSig(layer, steps, t.tx, t.ty) : this.plainContentSig(layer, t.tx, t.ty));
2600
3105
  }
@@ -2616,7 +3121,7 @@ var RasterCompositor = class {
2616
3121
  * laid out over the layer's bounds.
2617
3122
  */
2618
3123
  effectSig(layer, tx, ty) {
2619
- const key = (isGroup(layer) ? "Gfx" : "Cfx") + this.propsKey(layer) + this.lightKey();
3124
+ const key = (isGroup2(layer) ? "Gfx" : "Cfx") + this.propsKey(layer) + this.lightKey();
2620
3125
  const region = this.effectRegion(layer);
2621
3126
  const m = effectsMargin(layer.effects);
2622
3127
  if (effectsAreLocal(activeEffectItems(layer.effects))) {
@@ -2709,7 +3214,7 @@ var RasterCompositor = class {
2709
3214
  /** A content or group layer's own pixels over `r` with its mask applied to alpha, or `null` when empty. */
2710
3215
  ownPixels(layer, r) {
2711
3216
  let rgba;
2712
- if (isGroup(layer)) {
3217
+ if (isGroup2(layer)) {
2713
3218
  const buf = new Uint8ClampedArray(r.width * r.height * 4);
2714
3219
  rgba = this.runSteps(this.buildSteps(layer.children ?? []), buf, true, r) ? null : buf;
2715
3220
  } else {
@@ -2743,7 +3248,7 @@ var RasterCompositor = class {
2743
3248
  const content = this.ownPixels(layer, a) ?? new Uint8ClampedArray(a.width * a.height * 4);
2744
3249
  if (clipped.length) this.applyClipped(clipped, content, a);
2745
3250
  const keep = keepAlpha ? sub.filter((_, i) => (i & 3) === 3) : null;
2746
- const blend2 = isGroup(layer) ? layer.blend === "pass-through" ? "normal" : layer.blend : this.contentBlend(layer);
3251
+ const blend2 = isGroup2(layer) ? layer.blend === "pass-through" ? "normal" : layer.blend : this.contentBlend(layer);
2747
3252
  compositeLayerEffects({
2748
3253
  backdrop: sub,
2749
3254
  content,
@@ -2970,12 +3475,12 @@ var RasterCompositor = class {
2970
3475
  continue;
2971
3476
  }
2972
3477
  flush();
2973
- if (this.hasEffects(c) && !isGroup(c)) {
3478
+ if (this.hasEffects(c) && !isGroup2(c)) {
2974
3479
  this.compositeEffects(c, [], buf, r, true);
2975
3480
  continue;
2976
3481
  }
2977
3482
  const coverage = this.maskTile(c, r);
2978
- if (isGroup(c)) {
3483
+ if (isGroup2(c)) {
2979
3484
  const inner = new Uint8ClampedArray(buf.length);
2980
3485
  if (this.runSteps(this.buildSteps(c.children ?? []), inner, true, r)) continue;
2981
3486
  const mode = c.blend === "pass-through" ? "normal" : c.blend;
@@ -3782,531 +4287,6 @@ function compositeSurfaceOver(base, top) {
3782
4287
  return new TiledSurface(ch, tiles, base.defaultValue);
3783
4288
  }
3784
4289
 
3785
- // src/raster/zlib.ts
3786
- var LENGTH_BASE = [3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 15, 17, 19, 23, 27, 31, 35, 43, 51, 59, 67, 83, 99, 115, 131, 163, 195, 227, 258];
3787
- var LENGTH_EXTRA = [0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0];
3788
- var DIST_BASE = [1, 2, 3, 4, 5, 7, 9, 13, 17, 25, 33, 49, 65, 97, 129, 193, 257, 385, 513, 769, 1025, 1537, 2049, 3073, 4097, 6145, 8193, 12289, 16385, 24577];
3789
- var DIST_EXTRA = [0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13];
3790
- var CL_ORDER = [16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15];
3791
- var ZlibError = class extends Error {
3792
- constructor(message) {
3793
- super(message);
3794
- this.name = "ZlibError";
3795
- }
3796
- };
3797
- function buildHuffman(lengths, n) {
3798
- const counts = new Uint16Array(16);
3799
- for (let i = 0; i < n; i++) counts[lengths[i]]++;
3800
- counts[0] = 0;
3801
- const offs = new Uint16Array(16);
3802
- for (let i = 1; i < 16; i++) offs[i] = offs[i - 1] + counts[i - 1];
3803
- const symbols = new Uint16Array(n);
3804
- for (let i = 0; i < n; i++) if (lengths[i]) symbols[offs[lengths[i]]++] = i;
3805
- return { counts, symbols };
3806
- }
3807
- var fixedLit = null;
3808
- var fixedDist = null;
3809
- function fixedTables() {
3810
- if (!fixedLit || !fixedDist) {
3811
- const l = new Uint8Array(288);
3812
- for (let i = 0; i < 144; i++) l[i] = 8;
3813
- for (let i = 144; i < 256; i++) l[i] = 9;
3814
- for (let i = 256; i < 280; i++) l[i] = 7;
3815
- for (let i = 280; i < 288; i++) l[i] = 8;
3816
- fixedLit = buildHuffman(l, 288);
3817
- const d = new Uint8Array(30).fill(5);
3818
- fixedDist = buildHuffman(d, 30);
3819
- }
3820
- return [fixedLit, fixedDist];
3821
- }
3822
- var BitReader = class {
3823
- constructor(data) {
3824
- this.data = data;
3825
- }
3826
- data;
3827
- pos = 0;
3828
- bit = 0;
3829
- bits = 0;
3830
- need(n) {
3831
- while (this.bits < n) {
3832
- if (this.pos >= this.data.length) throw new ZlibError("Unexpected end of compressed data");
3833
- this.bit |= this.data[this.pos++] << this.bits;
3834
- this.bits += 8;
3835
- }
3836
- const v = this.bit & (1 << n) - 1;
3837
- this.bit >>>= n;
3838
- this.bits -= n;
3839
- return v;
3840
- }
3841
- decode(h) {
3842
- let code = 0;
3843
- let first = 0;
3844
- let index = 0;
3845
- for (let len = 1; len < 16; len++) {
3846
- code |= this.need(1);
3847
- const count = h.counts[len];
3848
- if (code - count < first) return h.symbols[index + (code - first)];
3849
- index += count;
3850
- first += count;
3851
- first <<= 1;
3852
- code <<= 1;
3853
- }
3854
- throw new ZlibError("Invalid Huffman code");
3855
- }
3856
- align() {
3857
- this.bit = 0;
3858
- this.bits = 0;
3859
- }
3860
- };
3861
- var Output = class {
3862
- constructor(hint, max) {
3863
- this.max = max;
3864
- this.buf = new Uint8Array(Math.max(1024, Math.min(hint, max)));
3865
- }
3866
- max;
3867
- buf;
3868
- len = 0;
3869
- ensure(n) {
3870
- if (this.len + n > this.max) throw new ZlibError(`Decompressed data exceeds ${this.max} bytes`);
3871
- if (this.len + n <= this.buf.length) return;
3872
- let size = this.buf.length * 2;
3873
- while (size < this.len + n) size *= 2;
3874
- const next = new Uint8Array(Math.min(size, Math.max(this.max, this.len + n)));
3875
- next.set(this.buf.subarray(0, this.len));
3876
- this.buf = next;
3877
- }
3878
- };
3879
- function inflateRaw(data, options = {}) {
3880
- const max = options.maxOutput ?? 512 * 1024 * 1024;
3881
- const out = new Output(options.sizeHint ?? data.length * 4, max);
3882
- const br = new BitReader(data);
3883
- let final = 0;
3884
- while (!final) {
3885
- final = br.need(1);
3886
- const type = br.need(2);
3887
- if (type === 0) {
3888
- br.align();
3889
- if (br.pos + 4 > data.length) throw new ZlibError("Unexpected end of compressed data");
3890
- const len = data[br.pos] | data[br.pos + 1] << 8;
3891
- const nlen = data[br.pos + 2] | data[br.pos + 3] << 8;
3892
- br.pos += 4;
3893
- if ((len ^ 65535) !== nlen) throw new ZlibError("Stored block length mismatch");
3894
- if (br.pos + len > data.length) throw new ZlibError("Unexpected end of compressed data");
3895
- out.ensure(len);
3896
- out.buf.set(data.subarray(br.pos, br.pos + len), out.len);
3897
- out.len += len;
3898
- br.pos += len;
3899
- continue;
3900
- }
3901
- let lit;
3902
- let dist;
3903
- if (type === 1) [lit, dist] = fixedTables();
3904
- else if (type === 2) {
3905
- const hlit = br.need(5) + 257;
3906
- const hdist = br.need(5) + 1;
3907
- const hclen = br.need(4) + 4;
3908
- const cl = new Uint8Array(19);
3909
- for (let i2 = 0; i2 < hclen; i2++) cl[CL_ORDER[i2]] = br.need(3);
3910
- const clh = buildHuffman(cl, 19);
3911
- const lengths = new Uint8Array(hlit + hdist);
3912
- let i = 0;
3913
- while (i < hlit + hdist) {
3914
- const sym = br.decode(clh);
3915
- if (sym < 16) lengths[i++] = sym;
3916
- else {
3917
- let rep = 0;
3918
- let val = 0;
3919
- if (sym === 16) {
3920
- if (i === 0) throw new ZlibError("Repeat with no previous length");
3921
- val = lengths[i - 1];
3922
- rep = 3 + br.need(2);
3923
- } else if (sym === 17) rep = 3 + br.need(3);
3924
- else rep = 11 + br.need(7);
3925
- if (i + rep > hlit + hdist) throw new ZlibError("Too many code lengths");
3926
- while (rep--) lengths[i++] = val;
3927
- }
3928
- }
3929
- lit = buildHuffman(lengths.subarray(0, hlit), hlit);
3930
- dist = buildHuffman(lengths.subarray(hlit), hdist);
3931
- } else throw new ZlibError("Invalid block type");
3932
- for (; ; ) {
3933
- const sym = br.decode(lit);
3934
- if (sym < 256) {
3935
- out.ensure(1);
3936
- out.buf[out.len++] = sym;
3937
- } else if (sym === 256) break;
3938
- else {
3939
- const li = sym - 257;
3940
- if (li >= 29) throw new ZlibError("Invalid length symbol");
3941
- const len = LENGTH_BASE[li] + br.need(LENGTH_EXTRA[li]);
3942
- const di = br.decode(dist);
3943
- if (di >= 30) throw new ZlibError("Invalid distance symbol");
3944
- const d = DIST_BASE[di] + br.need(DIST_EXTRA[di]);
3945
- if (d > out.len) throw new ZlibError("Distance too far back");
3946
- out.ensure(len);
3947
- const buf = out.buf;
3948
- let p = out.len;
3949
- for (let k = 0; k < len; k++, p++) buf[p] = buf[p - d];
3950
- out.len = p;
3951
- }
3952
- }
3953
- }
3954
- return out.buf.slice(0, out.len);
3955
- }
3956
- function adler32(data) {
3957
- let a = 1;
3958
- let b = 0;
3959
- const n = data.length;
3960
- let i = 0;
3961
- while (i < n) {
3962
- const end = Math.min(n, i + 3800);
3963
- for (; i < end; i++) {
3964
- a += data[i];
3965
- b += a;
3966
- }
3967
- a %= 65521;
3968
- b %= 65521;
3969
- }
3970
- return (b << 16 | a) >>> 0;
3971
- }
3972
- function inflate(data, options = {}) {
3973
- if (data.length < 6) throw new ZlibError("Truncated zlib stream");
3974
- const cmf = data[0];
3975
- const flg = data[1];
3976
- if ((cmf & 15) !== 8 || (cmf << 8 | flg) % 31 !== 0) throw new ZlibError("Not a zlib stream");
3977
- if (flg & 32) throw new ZlibError("Preset dictionaries are not supported");
3978
- const out = inflateRaw(data.subarray(2), options);
3979
- if (options.verify !== false && data.length >= 6) {
3980
- const t = data.length - 4;
3981
- const want = (data[t] << 24 | data[t + 1] << 16 | data[t + 2] << 8 | data[t + 3]) >>> 0;
3982
- if (adler32(out) !== want) throw new ZlibError("Adler-32 mismatch");
3983
- }
3984
- return out;
3985
- }
3986
- var BitWriter = class {
3987
- buf;
3988
- len = 0;
3989
- bit = 0;
3990
- bits = 0;
3991
- constructor(hint) {
3992
- this.buf = new Uint8Array(Math.max(1024, hint));
3993
- }
3994
- grow() {
3995
- const next = new Uint8Array(this.buf.length * 2);
3996
- next.set(this.buf);
3997
- this.buf = next;
3998
- }
3999
- write(value, n) {
4000
- this.bit |= value << this.bits;
4001
- this.bits += n;
4002
- while (this.bits >= 8) {
4003
- if (this.len >= this.buf.length) this.grow();
4004
- this.buf[this.len++] = this.bit & 255;
4005
- this.bit >>>= 8;
4006
- this.bits -= 8;
4007
- }
4008
- }
4009
- flush() {
4010
- if (this.bits > 0) {
4011
- if (this.len >= this.buf.length) this.grow();
4012
- this.buf[this.len++] = this.bit & 255;
4013
- }
4014
- this.bit = 0;
4015
- this.bits = 0;
4016
- }
4017
- bytes() {
4018
- return this.buf.slice(0, this.len);
4019
- }
4020
- };
4021
- function codeLengths(freqs, maxBits) {
4022
- const n = freqs.length;
4023
- const lengths = new Uint8Array(n);
4024
- const f = Float64Array.from(freqs);
4025
- for (; ; ) {
4026
- const nodes = [];
4027
- for (let i = 0; i < n; i++) if (f[i] > 0) nodes.push({ w: f[i], sym: i });
4028
- lengths.fill(0);
4029
- if (nodes.length === 0) return lengths;
4030
- if (nodes.length === 1) {
4031
- lengths[nodes[0].sym] = 1;
4032
- return lengths;
4033
- }
4034
- const heap = nodes.map((_, i) => i);
4035
- const less = (a, b) => nodes[a].w < nodes[b].w || nodes[a].w === nodes[b].w && a < b;
4036
- const down = (i) => {
4037
- for (; ; ) {
4038
- const l = 2 * i + 1;
4039
- const r = l + 1;
4040
- let m = i;
4041
- if (l < heap.length && less(heap[l], heap[m])) m = l;
4042
- if (r < heap.length && less(heap[r], heap[m])) m = r;
4043
- if (m === i) return;
4044
- [heap[i], heap[m]] = [heap[m], heap[i]];
4045
- i = m;
4046
- }
4047
- };
4048
- const up = (i) => {
4049
- while (i > 0) {
4050
- const p = i - 1 >> 1;
4051
- if (!less(heap[i], heap[p])) return;
4052
- [heap[i], heap[p]] = [heap[p], heap[i]];
4053
- i = p;
4054
- }
4055
- };
4056
- for (let i = (heap.length >> 1) - 1; i >= 0; i--) down(i);
4057
- const pop = () => {
4058
- const top = heap[0];
4059
- const last = heap.pop();
4060
- if (heap.length) {
4061
- heap[0] = last;
4062
- down(0);
4063
- }
4064
- return top;
4065
- };
4066
- while (heap.length > 1) {
4067
- const a = pop();
4068
- const b = pop();
4069
- nodes.push({ w: nodes[a].w + nodes[b].w, sym: -1, left: a, right: b });
4070
- heap.push(nodes.length - 1);
4071
- up(heap.length - 1);
4072
- }
4073
- let maxLen = 0;
4074
- const stack = [[heap[0], 0]];
4075
- while (stack.length) {
4076
- const [i, d] = stack.pop();
4077
- const node = nodes[i];
4078
- if (node.sym >= 0) {
4079
- lengths[node.sym] = d;
4080
- if (d > maxLen) maxLen = d;
4081
- } else {
4082
- stack.push([node.left, d + 1], [node.right, d + 1]);
4083
- }
4084
- }
4085
- if (maxLen <= maxBits) return lengths;
4086
- for (let i = 0; i < n; i++) if (f[i] > 0) f[i] = Math.floor(f[i] / 2) + 1;
4087
- }
4088
- }
4089
- function canonicalCodes(lengths) {
4090
- const blCount = new Uint16Array(16);
4091
- for (const l of lengths) blCount[l]++;
4092
- blCount[0] = 0;
4093
- const next = new Uint16Array(16);
4094
- let code = 0;
4095
- for (let bits = 1; bits < 16; bits++) {
4096
- code = code + blCount[bits - 1] << 1;
4097
- next[bits] = code;
4098
- }
4099
- const codes = new Uint16Array(lengths.length);
4100
- for (let i = 0; i < lengths.length; i++) {
4101
- const len = lengths[i];
4102
- if (!len) continue;
4103
- let c = next[len]++;
4104
- let r = 0;
4105
- for (let k = 0; k < len; k++) {
4106
- r = r << 1 | c & 1;
4107
- c >>= 1;
4108
- }
4109
- codes[i] = r;
4110
- }
4111
- return codes;
4112
- }
4113
- function lengthSymbol(len) {
4114
- let i = 28;
4115
- while (LENGTH_BASE[i] > len) i--;
4116
- return i;
4117
- }
4118
- function distSymbol(d) {
4119
- let i = 29;
4120
- while (DIST_BASE[i] > d) i--;
4121
- return i;
4122
- }
4123
- var WINDOW = 32768;
4124
- var HASH_BITS = 15;
4125
- var HASH_SIZE = 1 << HASH_BITS;
4126
- var MAX_CHAIN = 24;
4127
- var MAX_MATCH = 258;
4128
- var BLOCK_SYMBOLS = 65536;
4129
- function deflateRaw(data, level = 1) {
4130
- const w = new BitWriter(Math.ceil(data.length / 2) + 64);
4131
- const n = data.length;
4132
- if (level === 0 || n === 0) {
4133
- let pos = 0;
4134
- do {
4135
- const len = Math.min(65535, n - pos);
4136
- const final = pos + len >= n ? 1 : 0;
4137
- w.write(final, 1);
4138
- w.write(0, 2);
4139
- w.flush();
4140
- w.write(len & 65535, 16);
4141
- w.write(~len & 65535, 16);
4142
- for (let i2 = 0; i2 < len; i2++) w.write(data[pos + i2], 8);
4143
- pos += len;
4144
- } while (pos < n);
4145
- return w.bytes();
4146
- }
4147
- const head = new Int32Array(HASH_SIZE).fill(-1);
4148
- const prev = new Int32Array(WINDOW);
4149
- const litLen = new Uint16Array(BLOCK_SYMBOLS);
4150
- const dists = new Uint16Array(BLOCK_SYMBOLS);
4151
- let count = 0;
4152
- const hash = (i2) => (data[i2] << 10 ^ data[i2 + 1] << 5 ^ data[i2 + 2]) * 2654435761 >>> 32 - HASH_BITS;
4153
- const insert = (i2) => {
4154
- if (i2 + 2 >= n) return;
4155
- const h = hash(i2);
4156
- prev[i2 & WINDOW - 1] = head[h];
4157
- head[h] = i2;
4158
- };
4159
- const flushBlock = (final) => {
4160
- const litFreq = new Uint32Array(286);
4161
- const distFreq = new Uint32Array(30);
4162
- for (let k = 0; k < count; k++) {
4163
- if (dists[k] === 0) litFreq[litLen[k]]++;
4164
- else {
4165
- litFreq[257 + lengthSymbol(litLen[k])]++;
4166
- distFreq[distSymbol(dists[k])]++;
4167
- }
4168
- }
4169
- litFreq[256] = 1;
4170
- let anyDist = false;
4171
- for (const v of distFreq) if (v) anyDist = true;
4172
- if (!anyDist) distFreq[0] = 1;
4173
- const litLengths = codeLengths(litFreq, 15);
4174
- const distLengths = codeLengths(distFreq, 15);
4175
- let hlit = 286;
4176
- while (hlit > 257 && !litLengths[hlit - 1]) hlit--;
4177
- let hdist = 30;
4178
- while (hdist > 1 && !distLengths[hdist - 1]) hdist--;
4179
- const all = new Uint8Array(hlit + hdist);
4180
- all.set(litLengths.subarray(0, hlit));
4181
- all.set(distLengths.subarray(0, hdist), hlit);
4182
- const clSyms = [];
4183
- const clExtra = [];
4184
- for (let i2 = 0; i2 < all.length; ) {
4185
- const v = all[i2];
4186
- let run = 1;
4187
- while (i2 + run < all.length && all[i2 + run] === v) run++;
4188
- if (v === 0 && run >= 3) {
4189
- const r = Math.min(run, 138);
4190
- if (r >= 11) {
4191
- clSyms.push(18);
4192
- clExtra.push(r - 11);
4193
- } else {
4194
- clSyms.push(17);
4195
- clExtra.push(r - 3);
4196
- }
4197
- i2 += r;
4198
- } else if (v !== 0 && run >= 4) {
4199
- clSyms.push(v);
4200
- clExtra.push(0);
4201
- const r = Math.min(run - 1, 6);
4202
- clSyms.push(16);
4203
- clExtra.push(r - 3);
4204
- i2 += r + 1;
4205
- } else {
4206
- clSyms.push(v);
4207
- clExtra.push(0);
4208
- i2++;
4209
- }
4210
- }
4211
- const clFreq = new Uint32Array(19);
4212
- for (const s of clSyms) clFreq[s]++;
4213
- const clLengths = codeLengths(clFreq, 7);
4214
- let hclen = 19;
4215
- while (hclen > 4 && !clLengths[CL_ORDER[hclen - 1]]) hclen--;
4216
- const clCodes = canonicalCodes(clLengths);
4217
- const litCodes = canonicalCodes(litLengths);
4218
- const distCodes = canonicalCodes(distLengths);
4219
- w.write(final ? 1 : 0, 1);
4220
- w.write(2, 2);
4221
- w.write(hlit - 257, 5);
4222
- w.write(hdist - 1, 5);
4223
- w.write(hclen - 4, 4);
4224
- for (let i2 = 0; i2 < hclen; i2++) w.write(clLengths[CL_ORDER[i2]], 3);
4225
- for (let i2 = 0; i2 < clSyms.length; i2++) {
4226
- const s = clSyms[i2];
4227
- w.write(clCodes[s], clLengths[s]);
4228
- if (s === 16) w.write(clExtra[i2], 2);
4229
- else if (s === 17) w.write(clExtra[i2], 3);
4230
- else if (s === 18) w.write(clExtra[i2], 7);
4231
- }
4232
- for (let k = 0; k < count; k++) {
4233
- const d = dists[k];
4234
- if (d === 0) {
4235
- const s = litLen[k];
4236
- w.write(litCodes[s], litLengths[s]);
4237
- } else {
4238
- const len = litLen[k];
4239
- const li = lengthSymbol(len);
4240
- w.write(litCodes[257 + li], litLengths[257 + li]);
4241
- if (LENGTH_EXTRA[li]) w.write(len - LENGTH_BASE[li], LENGTH_EXTRA[li]);
4242
- const di = distSymbol(d);
4243
- w.write(distCodes[di], distLengths[di]);
4244
- if (DIST_EXTRA[di]) w.write(d - DIST_BASE[di], DIST_EXTRA[di]);
4245
- }
4246
- }
4247
- w.write(litCodes[256], litLengths[256]);
4248
- count = 0;
4249
- };
4250
- let i = 0;
4251
- while (i < n) {
4252
- let bestLen = 0;
4253
- let bestDist = 0;
4254
- if (i + 2 < n) {
4255
- let cand = head[hash(i)];
4256
- let chain = MAX_CHAIN;
4257
- const limit = Math.min(MAX_MATCH, n - i);
4258
- while (cand >= 0 && i - cand <= WINDOW - 1 && chain-- > 0) {
4259
- if (data[cand + bestLen] === data[i + bestLen]) {
4260
- let l = 0;
4261
- while (l < limit && data[cand + l] === data[i + l]) l++;
4262
- if (l > bestLen) {
4263
- bestLen = l;
4264
- bestDist = i - cand;
4265
- if (l === limit) break;
4266
- }
4267
- }
4268
- const next = prev[cand & WINDOW - 1];
4269
- if (next >= cand) break;
4270
- cand = next;
4271
- }
4272
- }
4273
- if (bestLen >= 3) {
4274
- litLen[count] = bestLen;
4275
- dists[count] = bestDist;
4276
- count++;
4277
- const end = i + bestLen;
4278
- const insertEnd = bestLen > 64 ? i + 64 : end;
4279
- for (let k = i; k < insertEnd; k++) insert(k);
4280
- for (let k = Math.max(insertEnd, end - 3); k < end; k++) insert(k);
4281
- i = end;
4282
- } else {
4283
- litLen[count] = data[i];
4284
- dists[count] = 0;
4285
- count++;
4286
- insert(i);
4287
- i++;
4288
- }
4289
- if (count >= BLOCK_SYMBOLS - 1 && i < n) flushBlock(false);
4290
- }
4291
- flushBlock(true);
4292
- w.flush();
4293
- return w.bytes();
4294
- }
4295
- function deflate(data, level = 1) {
4296
- const raw = deflateRaw(data, level);
4297
- const out = new Uint8Array(raw.length + 6);
4298
- out[0] = 120;
4299
- out[1] = 1;
4300
- out.set(raw, 2);
4301
- const a = adler32(data);
4302
- const t = out.length - 4;
4303
- out[t] = a >>> 24;
4304
- out[t + 1] = a >>> 16 & 255;
4305
- out[t + 2] = a >>> 8 & 255;
4306
- out[t + 3] = a & 255;
4307
- return out;
4308
- }
4309
-
4310
4290
  // src/raster/png.ts
4311
4291
  var SIGNATURE = [137, 80, 78, 71, 13, 10, 26, 10];
4312
4292
  var crcTable = null;
@@ -4616,13 +4596,28 @@ function pngDataUrl(width, height, data, channels = 4) {
4616
4596
  }
4617
4597
 
4618
4598
  export {
4619
- DIRECT_GAUSSIAN_MAX_SIGMA,
4620
- gaussianBlur,
4621
- flattenLayers,
4622
- findLayer,
4623
- mapLayer,
4624
- insertLayer,
4625
- isLayerLocked,
4599
+ BIT_DEPTHS,
4600
+ isBitDepth,
4601
+ srgbDecode,
4602
+ srgbEncode,
4603
+ to16From8,
4604
+ to32From8,
4605
+ to32From16,
4606
+ to16From32,
4607
+ to8From16,
4608
+ to8From32,
4609
+ proxyOf,
4610
+ depthOf,
4611
+ deepTile,
4612
+ tileSamples16,
4613
+ tileSamples32,
4614
+ tileSamples,
4615
+ surfaceDepth,
4616
+ readDeepRegion,
4617
+ writeDeepRegion,
4618
+ surfaceFromDeepPixels,
4619
+ convertSurfaceDepth,
4620
+ deepBytes,
4626
4621
  DEFAULT_GLOBAL_LIGHT,
4627
4622
  LAYER_EFFECT_KINDS,
4628
4623
  layerEffectLabel,
@@ -4646,6 +4641,15 @@ export {
4646
4641
  validateLayerEffects,
4647
4642
  normalizeLayerEffects,
4648
4643
  effectsFingerprint,
4644
+ DeepCompositor,
4645
+ workingToSamples,
4646
+ DIRECT_GAUSSIAN_MAX_SIGMA,
4647
+ gaussianBlur,
4648
+ flattenLayers,
4649
+ findLayer,
4650
+ mapLayer,
4651
+ insertLayer,
4652
+ isLayerLocked,
4649
4653
  PatternTile,
4650
4654
  PatternPlacement,
4651
4655
  builtinPatternIds,
@@ -4676,12 +4680,6 @@ export {
4676
4680
  transformSurface,
4677
4681
  warpSurface,
4678
4682
  compositeSurfaceOver,
4679
- ZlibError,
4680
- inflateRaw,
4681
- adler32,
4682
- inflate,
4683
- deflateRaw,
4684
- deflate,
4685
4683
  encodePng,
4686
4684
  isPng,
4687
4685
  decodePng,
@@ -4690,4 +4688,4 @@ export {
4690
4688
  parseDataUrl,
4691
4689
  pngDataUrl
4692
4690
  };
4693
- //# sourceMappingURL=chunk-LQEEDHOP.js.map
4691
+ //# sourceMappingURL=chunk-C6C5PDKU.js.map