@taole/giftstage 0.3.2 → 0.3.3

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.
@@ -85,186 +85,186 @@ void main() {\r
85
85
  vec4 c = texture(u_atlas, v_uv);\r
86
86
  fragColor = vec4(c.rgb * v_color.rgb * v_color.a, c.a * v_color.a);\r
87
87
  }\r
88
- `, RE = `#version 300 es
89
- precision highp float;
90
- precision highp int;
91
-
92
- /**
93
- * Table-aware SVGA instanced vertex stage.
94
- *
95
- * The frame table is a RGBA32F/NEAREST texture with three texels per
96
- * (sprite, frame) row:
97
- * texel 0 = layoutW, layoutH, a, b
98
- * texel 1 = c, d, tx, ty
99
- * texel 2 = alpha, 0, 0, 0
100
- *
101
- * Static sprite metadata is a second RGBA32F/NEAREST texture with two texels
102
- * per row:
103
- * texel 0 = atlas UV min.xy / max.xy
104
- * texel 1 = sourceSpriteIndex, atlasPage, flags, reserved
105
- *
106
- * One draw covers a single atlas page of one slot. \`gl_InstanceID\` selects a
107
- * metadata row (\`u_spriteBase + gl_InstanceID\`), so the only per-frame CPU
108
- * state is the slot transform/opacity/clip and the authoritative frame index.
109
- */
110
- layout(location = 0) in vec2 a_corner;
111
- // Optional Hybrid scheduling row. Direct draws leave these attributes disabled
112
- // and use the uniform slot state below.
113
- layout(location = 1) in vec4 a_instanceParent;
114
- layout(location = 2) in vec4 a_instanceTranslateOpacityFrame;
115
- layout(location = 3) in vec4 a_instanceClipRect;
116
- /** x=clipEnabled, y=metadataRow, z=atlasPage, w=present. */
117
- layout(location = 4) in vec4 a_instanceInfo;
118
-
119
- uniform mat4 u_projection;
120
- uniform highp sampler2D u_frameTable;
121
- uniform highp sampler2D u_spriteMetadata;
122
- /**
123
- * Canonical compact state (four RGBA32F texels / 16 floats):
124
- * affine; translate+opacity+frame; clip rect; clipEnabled+metadataBase+atlasPage+track+1.
125
- */
126
- uniform highp sampler2D u_slotStates;
127
- /** x = frameCount, y = spriteCount, z = texels per frame (3), w = default frame. */
128
- uniform ivec4 u_tableInfo;
129
- /** x/y = frame-table texture width/height in texels. */
130
- uniform ivec2 u_frameTableSize;
131
- /** x/y = sprite metadata texture width/height in texels. */
132
- uniform ivec2 u_spriteMetadataSize;
133
- uniform int u_spriteMetadataTexelsPerRow;
134
- uniform ivec2 u_slotStateSize;
135
- /** First static metadata row consumed by this slot/page draw. */
136
- uniform int u_spriteBase;
137
- /** Authoritative SVGA frame selected by RenderManager/PlaybackScope. */
138
- uniform int u_frameIndex;
139
- uniform vec4 u_parentAffine;
140
- uniform vec2 u_parentTranslate;
141
- uniform float u_slotOpacity;
142
- /** Atlas page for this draw; negative means metadata page filtering is disabled. */
143
- uniform int u_atlasPage;
144
- uniform vec4 u_clipRect;
145
- uniform float u_clipEnabled;
146
- /** WebGL's gl_FragCoord has a bottom-left origin; input clip rects are top-left. */
147
- uniform float u_canvasHeight;
148
- uniform float u_instanceStateEnabled;
149
- uniform float u_compactSlotStateEnabled;
150
- uniform int u_spritesPerSlot;
151
-
152
- out vec2 v_uv;
153
- out vec4 v_color;
154
- flat out vec4 v_clipRect;
155
- flat out float v_clipEnabled;
156
- out vec2 v_localPosition;
157
- flat out vec4 v_localClipRect;
158
- flat out float v_localClipEnabled;
159
-
160
- ivec2 texelCoord(int linearIndex, ivec2 textureSize) {
161
- int width = max(textureSize.x, 1);
162
- return ivec2(linearIndex - (linearIndex / width) * width, linearIndex / width);
163
- }
164
-
165
- void main() {
166
- int frameCount = max(u_tableInfo.x, 1);
167
- int spriteCount = max(u_tableInfo.y, 1);
168
- bool instanceState = u_instanceStateEnabled > 0.5;
169
- bool compactSlotState = u_compactSlotStateEnabled > 0.5;
170
- int spritesPerSlot = max(u_spritesPerSlot, 1);
171
- int slotStateIndex = gl_InstanceID / spritesPerSlot;
172
- int spriteWithinSlot = gl_InstanceID - slotStateIndex * spritesPerSlot;
173
- vec4 compactParent = vec4(0.0);
174
- vec4 compactTranslateOpacityFrame = vec4(0.0);
175
- vec4 compactClip = vec4(0.0);
176
- vec4 compactInfo = vec4(0.0);
177
- if (compactSlotState) {
178
- int compactBase = slotStateIndex * 4;
179
- compactParent = texelFetch(u_slotStates, texelCoord(compactBase, u_slotStateSize), 0);
180
- compactTranslateOpacityFrame = texelFetch(u_slotStates, texelCoord(compactBase + 1, u_slotStateSize), 0);
181
- compactClip = texelFetch(u_slotStates, texelCoord(compactBase + 2, u_slotStateSize), 0);
182
- compactInfo = texelFetch(u_slotStates, texelCoord(compactBase + 3, u_slotStateSize), 0);
183
- }
184
- int metadataRow = instanceState
185
- ? max(int(a_instanceInfo.y + 0.5), 0)
186
- : compactSlotState
187
- ? max(u_spriteBase + spriteWithinSlot, 0)
188
- : max(u_spriteBase + gl_InstanceID, 0);
189
- int metadataStride = max(u_spriteMetadataTexelsPerRow, 2);
190
- int metadataTexel = metadataRow * metadataStride;
191
- vec4 metadata0 = texelFetch(
192
- u_spriteMetadata,
193
- texelCoord(metadataTexel, u_spriteMetadataSize),
194
- 0
195
- );
196
- vec4 metadata1 = texelFetch(
197
- u_spriteMetadata,
198
- texelCoord(metadataTexel + 1, u_spriteMetadataSize),
199
- 0
200
- );
201
- vec4 metadata2 = metadataStride >= 3
202
- ? texelFetch(u_spriteMetadata, texelCoord(metadataTexel + 2, u_spriteMetadataSize), 0)
203
- : vec4(0.0);
204
- // Metadata carries the source sprite index so a page-specific range can
205
- // represent non-contiguous atlas pages. Its y component is the atlas page.
206
- int spriteIndex = clamp(int(max(metadata1.x, 0.0) + 0.5), 0, spriteCount - 1);
207
- int frameIndex = instanceState
208
- ? int(a_instanceTranslateOpacityFrame.w + 0.5)
209
- : compactSlotState
210
- ? int(compactTranslateOpacityFrame.w + 0.5)
211
- : u_frameIndex;
212
- if (frameIndex < 0) frameIndex = u_tableInfo.w;
213
- frameIndex = clamp(frameIndex, 0, frameCount - 1);
214
-
215
- int row = spriteIndex * frameCount + frameIndex;
216
- int frameTexel = row * u_tableInfo.z;
217
- vec4 frame0 = texelFetch(u_frameTable, texelCoord(frameTexel, u_frameTableSize), 0);
218
- vec4 frame1 = texelFetch(u_frameTable, texelCoord(frameTexel + 1, u_frameTableSize), 0);
219
- vec4 frame2 = texelFetch(u_frameTable, texelCoord(frameTexel + 2, u_frameTableSize), 0);
220
-
221
- float layoutW = frame0.x;
222
- float layoutH = frame0.y;
223
- vec2 local = vec2(
224
- frame0.z * layoutW * a_corner.x + frame1.x * layoutH * a_corner.y + frame1.z,
225
- frame0.w * layoutW * a_corner.x + frame1.y * layoutH * a_corner.y + frame1.w
226
- );
227
-
228
- vec4 parentAffine = instanceState
229
- ? a_instanceParent
230
- : compactSlotState ? compactParent : u_parentAffine;
231
- vec2 parentTranslate = instanceState
232
- ? a_instanceTranslateOpacityFrame.xy
233
- : compactSlotState ? compactTranslateOpacityFrame.xy : u_parentTranslate;
234
- float slotOpacity = instanceState
235
- ? a_instanceTranslateOpacityFrame.z
236
- : compactSlotState ? compactTranslateOpacityFrame.z : u_slotOpacity;
237
- int atlasPage = instanceState
238
- ? int(a_instanceInfo.z + 0.5)
239
- : compactSlotState
240
- ? (compactInfo.z < -0.5 ? -1 : int(compactInfo.z + 0.5))
241
- : u_atlasPage;
242
- vec4 clipRect = instanceState
243
- ? a_instanceClipRect
244
- : compactSlotState ? compactClip : u_clipRect;
245
- float clipEnabled = instanceState
246
- ? a_instanceInfo.x
247
- : compactSlotState ? compactInfo.x : u_clipEnabled;
248
- vec2 world = vec2(
249
- parentAffine.x * local.x + parentAffine.z * local.y + parentTranslate.x,
250
- parentAffine.y * local.x + parentAffine.w * local.y + parentTranslate.y
251
- );
252
-
253
- gl_Position = u_projection * vec4(world, 0.0, 1.0);
254
- v_uv = mix(metadata0.xy, metadata0.zw, a_corner);
255
- bool pageMatches = atlasPage < 0 || int(max(metadata1.y, 0.0) + 0.5) == atlasPage;
256
- int metadataFlags = int(max(metadata1.z, 0.0) + 0.5);
257
- bool metadataPresent = (metadataFlags & 1) == 0;
258
- float pageAlpha = pageMatches && metadataPresent ? 1.0 : 0.0;
259
- float effectiveAlpha = frame2.x * slotOpacity * pageAlpha;
260
- // Match the CPU reference's strict \`< 0.05\` visibility cutoff.
261
- v_color = vec4(1.0, 1.0, 1.0, effectiveAlpha >= 0.05 ? effectiveAlpha : 0.0);
262
- v_clipRect = clipRect;
263
- v_clipEnabled = clipEnabled;
264
- v_localPosition = vec2(layoutW * a_corner.x, layoutH * a_corner.y);
265
- v_localClipRect = metadata2;
266
- v_localClipEnabled = (metadataFlags & 2) != 0 ? 1.0 : 0.0;
267
- }
88
+ `, RE = `#version 300 es\r
89
+ precision highp float;\r
90
+ precision highp int;\r
91
+ \r
92
+ /**\r
93
+ * Table-aware SVGA instanced vertex stage.\r
94
+ *\r
95
+ * The frame table is a RGBA32F/NEAREST texture with three texels per\r
96
+ * (sprite, frame) row:\r
97
+ * texel 0 = layoutW, layoutH, a, b\r
98
+ * texel 1 = c, d, tx, ty\r
99
+ * texel 2 = alpha, 0, 0, 0\r
100
+ *\r
101
+ * Static sprite metadata is a second RGBA32F/NEAREST texture with two texels\r
102
+ * per row:\r
103
+ * texel 0 = atlas UV min.xy / max.xy\r
104
+ * texel 1 = sourceSpriteIndex, atlasPage, flags, reserved\r
105
+ *\r
106
+ * One draw covers a single atlas page of one slot. \`gl_InstanceID\` selects a\r
107
+ * metadata row (\`u_spriteBase + gl_InstanceID\`), so the only per-frame CPU\r
108
+ * state is the slot transform/opacity/clip and the authoritative frame index.\r
109
+ */\r
110
+ layout(location = 0) in vec2 a_corner;\r
111
+ // Optional Hybrid scheduling row. Direct draws leave these attributes disabled\r
112
+ // and use the uniform slot state below.\r
113
+ layout(location = 1) in vec4 a_instanceParent;\r
114
+ layout(location = 2) in vec4 a_instanceTranslateOpacityFrame;\r
115
+ layout(location = 3) in vec4 a_instanceClipRect;\r
116
+ /** x=clipEnabled, y=metadataRow, z=atlasPage, w=present. */\r
117
+ layout(location = 4) in vec4 a_instanceInfo;\r
118
+ \r
119
+ uniform mat4 u_projection;\r
120
+ uniform highp sampler2D u_frameTable;\r
121
+ uniform highp sampler2D u_spriteMetadata;\r
122
+ /**\r
123
+ * Canonical compact state (four RGBA32F texels / 16 floats):\r
124
+ * affine; translate+opacity+frame; clip rect; clipEnabled+metadataBase+atlasPage+track+1.\r
125
+ */\r
126
+ uniform highp sampler2D u_slotStates;\r
127
+ /** x = frameCount, y = spriteCount, z = texels per frame (3), w = default frame. */\r
128
+ uniform ivec4 u_tableInfo;\r
129
+ /** x/y = frame-table texture width/height in texels. */\r
130
+ uniform ivec2 u_frameTableSize;\r
131
+ /** x/y = sprite metadata texture width/height in texels. */\r
132
+ uniform ivec2 u_spriteMetadataSize;\r
133
+ uniform int u_spriteMetadataTexelsPerRow;\r
134
+ uniform ivec2 u_slotStateSize;\r
135
+ /** First static metadata row consumed by this slot/page draw. */\r
136
+ uniform int u_spriteBase;\r
137
+ /** Authoritative SVGA frame selected by RenderManager/PlaybackScope. */\r
138
+ uniform int u_frameIndex;\r
139
+ uniform vec4 u_parentAffine;\r
140
+ uniform vec2 u_parentTranslate;\r
141
+ uniform float u_slotOpacity;\r
142
+ /** Atlas page for this draw; negative means metadata page filtering is disabled. */\r
143
+ uniform int u_atlasPage;\r
144
+ uniform vec4 u_clipRect;\r
145
+ uniform float u_clipEnabled;\r
146
+ /** WebGL's gl_FragCoord has a bottom-left origin; input clip rects are top-left. */\r
147
+ uniform float u_canvasHeight;\r
148
+ uniform float u_instanceStateEnabled;\r
149
+ uniform float u_compactSlotStateEnabled;\r
150
+ uniform int u_spritesPerSlot;\r
151
+ \r
152
+ out vec2 v_uv;\r
153
+ out vec4 v_color;\r
154
+ flat out vec4 v_clipRect;\r
155
+ flat out float v_clipEnabled;\r
156
+ out vec2 v_localPosition;\r
157
+ flat out vec4 v_localClipRect;\r
158
+ flat out float v_localClipEnabled;\r
159
+ \r
160
+ ivec2 texelCoord(int linearIndex, ivec2 textureSize) {\r
161
+ int width = max(textureSize.x, 1);\r
162
+ return ivec2(linearIndex - (linearIndex / width) * width, linearIndex / width);\r
163
+ }\r
164
+ \r
165
+ void main() {\r
166
+ int frameCount = max(u_tableInfo.x, 1);\r
167
+ int spriteCount = max(u_tableInfo.y, 1);\r
168
+ bool instanceState = u_instanceStateEnabled > 0.5;\r
169
+ bool compactSlotState = u_compactSlotStateEnabled > 0.5;\r
170
+ int spritesPerSlot = max(u_spritesPerSlot, 1);\r
171
+ int slotStateIndex = gl_InstanceID / spritesPerSlot;\r
172
+ int spriteWithinSlot = gl_InstanceID - slotStateIndex * spritesPerSlot;\r
173
+ vec4 compactParent = vec4(0.0);\r
174
+ vec4 compactTranslateOpacityFrame = vec4(0.0);\r
175
+ vec4 compactClip = vec4(0.0);\r
176
+ vec4 compactInfo = vec4(0.0);\r
177
+ if (compactSlotState) {\r
178
+ int compactBase = slotStateIndex * 4;\r
179
+ compactParent = texelFetch(u_slotStates, texelCoord(compactBase, u_slotStateSize), 0);\r
180
+ compactTranslateOpacityFrame = texelFetch(u_slotStates, texelCoord(compactBase + 1, u_slotStateSize), 0);\r
181
+ compactClip = texelFetch(u_slotStates, texelCoord(compactBase + 2, u_slotStateSize), 0);\r
182
+ compactInfo = texelFetch(u_slotStates, texelCoord(compactBase + 3, u_slotStateSize), 0);\r
183
+ }\r
184
+ int metadataRow = instanceState\r
185
+ ? max(int(a_instanceInfo.y + 0.5), 0)\r
186
+ : compactSlotState\r
187
+ ? max(u_spriteBase + spriteWithinSlot, 0)\r
188
+ : max(u_spriteBase + gl_InstanceID, 0);\r
189
+ int metadataStride = max(u_spriteMetadataTexelsPerRow, 2);\r
190
+ int metadataTexel = metadataRow * metadataStride;\r
191
+ vec4 metadata0 = texelFetch(\r
192
+ u_spriteMetadata,\r
193
+ texelCoord(metadataTexel, u_spriteMetadataSize),\r
194
+ 0\r
195
+ );\r
196
+ vec4 metadata1 = texelFetch(\r
197
+ u_spriteMetadata,\r
198
+ texelCoord(metadataTexel + 1, u_spriteMetadataSize),\r
199
+ 0\r
200
+ );\r
201
+ vec4 metadata2 = metadataStride >= 3\r
202
+ ? texelFetch(u_spriteMetadata, texelCoord(metadataTexel + 2, u_spriteMetadataSize), 0)\r
203
+ : vec4(0.0);\r
204
+ // Metadata carries the source sprite index so a page-specific range can\r
205
+ // represent non-contiguous atlas pages. Its y component is the atlas page.\r
206
+ int spriteIndex = clamp(int(max(metadata1.x, 0.0) + 0.5), 0, spriteCount - 1);\r
207
+ int frameIndex = instanceState\r
208
+ ? int(a_instanceTranslateOpacityFrame.w + 0.5)\r
209
+ : compactSlotState\r
210
+ ? int(compactTranslateOpacityFrame.w + 0.5)\r
211
+ : u_frameIndex;\r
212
+ if (frameIndex < 0) frameIndex = u_tableInfo.w;\r
213
+ frameIndex = clamp(frameIndex, 0, frameCount - 1);\r
214
+ \r
215
+ int row = spriteIndex * frameCount + frameIndex;\r
216
+ int frameTexel = row * u_tableInfo.z;\r
217
+ vec4 frame0 = texelFetch(u_frameTable, texelCoord(frameTexel, u_frameTableSize), 0);\r
218
+ vec4 frame1 = texelFetch(u_frameTable, texelCoord(frameTexel + 1, u_frameTableSize), 0);\r
219
+ vec4 frame2 = texelFetch(u_frameTable, texelCoord(frameTexel + 2, u_frameTableSize), 0);\r
220
+ \r
221
+ float layoutW = frame0.x;\r
222
+ float layoutH = frame0.y;\r
223
+ vec2 local = vec2(\r
224
+ frame0.z * layoutW * a_corner.x + frame1.x * layoutH * a_corner.y + frame1.z,\r
225
+ frame0.w * layoutW * a_corner.x + frame1.y * layoutH * a_corner.y + frame1.w\r
226
+ );\r
227
+ \r
228
+ vec4 parentAffine = instanceState\r
229
+ ? a_instanceParent\r
230
+ : compactSlotState ? compactParent : u_parentAffine;\r
231
+ vec2 parentTranslate = instanceState\r
232
+ ? a_instanceTranslateOpacityFrame.xy\r
233
+ : compactSlotState ? compactTranslateOpacityFrame.xy : u_parentTranslate;\r
234
+ float slotOpacity = instanceState\r
235
+ ? a_instanceTranslateOpacityFrame.z\r
236
+ : compactSlotState ? compactTranslateOpacityFrame.z : u_slotOpacity;\r
237
+ int atlasPage = instanceState\r
238
+ ? int(a_instanceInfo.z + 0.5)\r
239
+ : compactSlotState\r
240
+ ? (compactInfo.z < -0.5 ? -1 : int(compactInfo.z + 0.5))\r
241
+ : u_atlasPage;\r
242
+ vec4 clipRect = instanceState\r
243
+ ? a_instanceClipRect\r
244
+ : compactSlotState ? compactClip : u_clipRect;\r
245
+ float clipEnabled = instanceState\r
246
+ ? a_instanceInfo.x\r
247
+ : compactSlotState ? compactInfo.x : u_clipEnabled;\r
248
+ vec2 world = vec2(\r
249
+ parentAffine.x * local.x + parentAffine.z * local.y + parentTranslate.x,\r
250
+ parentAffine.y * local.x + parentAffine.w * local.y + parentTranslate.y\r
251
+ );\r
252
+ \r
253
+ gl_Position = u_projection * vec4(world, 0.0, 1.0);\r
254
+ v_uv = mix(metadata0.xy, metadata0.zw, a_corner);\r
255
+ bool pageMatches = atlasPage < 0 || int(max(metadata1.y, 0.0) + 0.5) == atlasPage;\r
256
+ int metadataFlags = int(max(metadata1.z, 0.0) + 0.5);\r
257
+ bool metadataPresent = (metadataFlags & 1) == 0;\r
258
+ float pageAlpha = pageMatches && metadataPresent ? 1.0 : 0.0;\r
259
+ float effectiveAlpha = frame2.x * slotOpacity * pageAlpha;\r
260
+ // Match the CPU reference's strict \`< 0.05\` visibility cutoff.\r
261
+ v_color = vec4(1.0, 1.0, 1.0, effectiveAlpha >= 0.05 ? effectiveAlpha : 0.0);\r
262
+ v_clipRect = clipRect;\r
263
+ v_clipEnabled = clipEnabled;\r
264
+ v_localPosition = vec2(layoutW * a_corner.x, layoutH * a_corner.y);\r
265
+ v_localClipRect = metadata2;\r
266
+ v_localClipEnabled = (metadataFlags & 2) != 0 ? 1.0 : 0.0;\r
267
+ }\r
268
268
  `, uE = `#version 300 es
269
269
  precision highp float;
270
270
 
@@ -791,67 +791,67 @@ void main() {\r
791
791
  float coverage = 1.0 - smoothstep(0.45, 1.0, distanceToCenter);\r
792
792
  outColor = v_color * coverage;\r
793
793
  }\r
794
- `, TE = `#version 300 es
795
- precision highp float;
796
-
797
- layout(location = 0) in vec2 a_corner;
798
- layout(location = 1) in vec4 a_birthLifePosition;
799
- layout(location = 2) in vec4 a_velocityAcceleration;
800
- layout(location = 3) in vec4 a_scaleRotation;
801
- layout(location = 4) in vec4 a_color;
802
- layout(location = 5) in vec4 a_sizeAnchor;
803
- layout(location = 6) in vec4 a_uvRect;
804
-
805
- uniform mat4 u_projection;
806
- uniform float u_time;
807
- uniform float u_globalAlpha;
808
- uniform float u_sizeEnvelope;
809
- uniform float u_fadeMode;
810
- uniform vec2 u_cssScale;
811
-
812
- out vec2 v_uv;
813
- out vec4 v_modulation;
814
-
815
- void main() {
816
- float age = u_time - a_birthLifePosition.x;
817
- float life = max(a_birthLifePosition.y, 0.0001);
818
- bool alive = age >= 0.0 && age <= life;
819
- float safeAge = max(age, 0.0);
820
- vec2 position = a_birthLifePosition.zw
821
- + a_velocityAcceleration.xy * safeAge
822
- + 0.5 * a_velocityAcceleration.zw * safeAge * safeAge;
823
- float scale = max(0.04, a_scaleRotation.x + a_scaleRotation.y * safeAge) * u_sizeEnvelope;
824
- vec2 unitCorner = a_corner + 0.5;
825
- vec2 local = (unitCorner - a_sizeAnchor.zw) * a_sizeAnchor.xy * scale;
826
- float angle = a_scaleRotation.z + a_scaleRotation.w * safeAge;
827
- float c = cos(angle);
828
- float s = sin(angle);
829
- vec2 rotated = vec2(c * local.x - s * local.y, s * local.x + c * local.y);
830
- float progress = clamp(safeAge / life, 0.0, 1.0);
831
- float fade = u_fadeMode > 0.5
832
- ? min(safeAge / 0.04, 1.0) * pow(1.0 - progress, 0.78)
833
- : 1.0;
834
- if (!alive) {
835
- position = vec2(-100000.0);
836
- fade = 0.0;
837
- }
838
- gl_Position = u_projection * vec4((position + rotated) * u_cssScale, 0.0, 1.0);
839
- v_uv = mix(a_uvRect.xy, a_uvRect.zw, unitCorner);
840
- float alpha = a_color.a * fade * u_globalAlpha;
841
- v_modulation = vec4(a_color.rgb * alpha, alpha);
842
- }
843
- `, vE = `#version 300 es
844
- precision highp float;
845
-
846
- uniform sampler2D u_atlas;
847
- in vec2 v_uv;
848
- in vec4 v_modulation;
849
- out vec4 outColor;
850
-
851
- void main() {
852
- vec4 sampled = texture(u_atlas, v_uv);
853
- outColor = vec4(sampled.rgb * v_modulation.rgb, sampled.a * v_modulation.a);
854
- }
794
+ `, TE = `#version 300 es\r
795
+ precision highp float;\r
796
+ \r
797
+ layout(location = 0) in vec2 a_corner;\r
798
+ layout(location = 1) in vec4 a_birthLifePosition;\r
799
+ layout(location = 2) in vec4 a_velocityAcceleration;\r
800
+ layout(location = 3) in vec4 a_scaleRotation;\r
801
+ layout(location = 4) in vec4 a_color;\r
802
+ layout(location = 5) in vec4 a_sizeAnchor;\r
803
+ layout(location = 6) in vec4 a_uvRect;\r
804
+ \r
805
+ uniform mat4 u_projection;\r
806
+ uniform float u_time;\r
807
+ uniform float u_globalAlpha;\r
808
+ uniform float u_sizeEnvelope;\r
809
+ uniform float u_fadeMode;\r
810
+ uniform vec2 u_cssScale;\r
811
+ \r
812
+ out vec2 v_uv;\r
813
+ out vec4 v_modulation;\r
814
+ \r
815
+ void main() {\r
816
+ float age = u_time - a_birthLifePosition.x;\r
817
+ float life = max(a_birthLifePosition.y, 0.0001);\r
818
+ bool alive = age >= 0.0 && age <= life;\r
819
+ float safeAge = max(age, 0.0);\r
820
+ vec2 position = a_birthLifePosition.zw\r
821
+ + a_velocityAcceleration.xy * safeAge\r
822
+ + 0.5 * a_velocityAcceleration.zw * safeAge * safeAge;\r
823
+ float scale = max(0.04, a_scaleRotation.x + a_scaleRotation.y * safeAge) * u_sizeEnvelope;\r
824
+ vec2 unitCorner = a_corner + 0.5;\r
825
+ vec2 local = (unitCorner - a_sizeAnchor.zw) * a_sizeAnchor.xy * scale;\r
826
+ float angle = a_scaleRotation.z + a_scaleRotation.w * safeAge;\r
827
+ float c = cos(angle);\r
828
+ float s = sin(angle);\r
829
+ vec2 rotated = vec2(c * local.x - s * local.y, s * local.x + c * local.y);\r
830
+ float progress = clamp(safeAge / life, 0.0, 1.0);\r
831
+ float fade = u_fadeMode > 0.5\r
832
+ ? min(safeAge / 0.04, 1.0) * pow(1.0 - progress, 0.78)\r
833
+ : 1.0;\r
834
+ if (!alive) {\r
835
+ position = vec2(-100000.0);\r
836
+ fade = 0.0;\r
837
+ }\r
838
+ gl_Position = u_projection * vec4((position + rotated) * u_cssScale, 0.0, 1.0);\r
839
+ v_uv = mix(a_uvRect.xy, a_uvRect.zw, unitCorner);\r
840
+ float alpha = a_color.a * fade * u_globalAlpha;\r
841
+ v_modulation = vec4(a_color.rgb * alpha, alpha);\r
842
+ }\r
843
+ `, vE = `#version 300 es\r
844
+ precision highp float;\r
845
+ \r
846
+ uniform sampler2D u_atlas;\r
847
+ in vec2 v_uv;\r
848
+ in vec4 v_modulation;\r
849
+ out vec4 outColor;\r
850
+ \r
851
+ void main() {\r
852
+ vec4 sampled = texture(u_atlas, v_uv);\r
853
+ outColor = vec4(sampled.rgb * v_modulation.rgb, sampled.a * v_modulation.a);\r
854
+ }\r
855
855
  `, WE = `/** SVGA atlas variant for premultiplied RGBA atlas textures. */\r
856
856
  struct Uniforms {\r
857
857
  projection: mat4x4f,\r
@@ -1357,78 +1357,78 @@ fn fs(input: VOut) -> @location(0) vec4f {\r
1357
1357
  let coverage = 1.0 - smoothstep(0.45, 1.0, distanceToCenter);\r
1358
1358
  return input.color * coverage;\r
1359
1359
  }\r
1360
- `, gi = `struct Globals {
1361
- projection: mat4x4f,
1362
- }
1363
-
1364
- @group(0) @binding(0) var<uniform> globals: Globals;
1365
- @group(0) @binding(1) var<storage, read> instanceData: array<f32>;
1366
- @group(1) @binding(0) var atlasTexture: texture_2d<f32>;
1367
- @group(1) @binding(1) var atlasSampler: sampler;
1368
-
1369
- struct VIn {
1370
- @location(0) corner: vec2f,
1371
- }
1372
-
1373
- struct VOut {
1374
- @builtin(position) position: vec4f,
1375
- @location(0) uv: vec2f,
1376
- @location(1) modulation: vec4f,
1377
- }
1378
-
1379
- @vertex
1380
- fn vs(input: VIn, @builtin(instance_index) instance: u32) -> VOut {
1381
- let base = 8u + instance * 24u;
1382
- let birth = instanceData[base];
1383
- let life = max(instanceData[base + 1u], 0.0001);
1384
- let age = instanceData[0] - birth;
1385
- let safeAge = max(age, 0.0);
1386
- var position = vec2f(instanceData[base + 2u], instanceData[base + 3u])
1387
- + vec2f(instanceData[base + 4u], instanceData[base + 5u]) * safeAge
1388
- + 0.5 * vec2f(instanceData[base + 6u], instanceData[base + 7u]) * safeAge * safeAge;
1389
- let scale = max(0.04, instanceData[base + 8u] + instanceData[base + 9u] * safeAge)
1390
- * instanceData[2];
1391
- let unitCorner = input.corner + vec2f(0.5);
1392
- let anchor = vec2f(instanceData[base + 18u], instanceData[base + 19u]);
1393
- let spriteSize = vec2f(instanceData[base + 16u], instanceData[base + 17u]);
1394
- let local = (unitCorner - anchor) * spriteSize * scale;
1395
- let angle = instanceData[base + 10u] + instanceData[base + 11u] * safeAge;
1396
- let c = cos(angle);
1397
- let s = sin(angle);
1398
- let rotated = vec2f(c * local.x - s * local.y, s * local.x + c * local.y);
1399
- let progress = clamp(safeAge / life, 0.0, 1.0);
1400
- var fade = select(
1401
- 1.0,
1402
- min(safeAge / 0.04, 1.0) * pow(1.0 - progress, 0.78),
1403
- instanceData[3] > 0.5,
1404
- );
1405
- if (age < 0.0 || age > life) {
1406
- position = vec2f(-100000.0);
1407
- fade = 0.0;
1408
- }
1409
- let cssScale = vec2f(instanceData[4], instanceData[5]);
1410
- let alpha = instanceData[base + 15u] * fade * instanceData[1];
1411
- var output: VOut;
1412
- output.position = globals.projection * vec4f((position + rotated) * cssScale, 0.0, 1.0);
1413
- output.uv = mix(
1414
- vec2f(instanceData[base + 20u], instanceData[base + 21u]),
1415
- vec2f(instanceData[base + 22u], instanceData[base + 23u]),
1416
- unitCorner,
1417
- );
1418
- output.modulation = vec4f(
1419
- instanceData[base + 12u] * alpha,
1420
- instanceData[base + 13u] * alpha,
1421
- instanceData[base + 14u] * alpha,
1422
- alpha,
1423
- );
1424
- return output;
1425
- }
1426
-
1427
- @fragment
1428
- fn fs(input: VOut) -> @location(0) vec4f {
1429
- let sampled = textureSample(atlasTexture, atlasSampler, input.uv);
1430
- return vec4f(sampled.rgb * input.modulation.rgb, sampled.a * input.modulation.a);
1431
- }
1360
+ `, gi = `struct Globals {\r
1361
+ projection: mat4x4f,\r
1362
+ }\r
1363
+ \r
1364
+ @group(0) @binding(0) var<uniform> globals: Globals;\r
1365
+ @group(0) @binding(1) var<storage, read> instanceData: array<f32>;\r
1366
+ @group(1) @binding(0) var atlasTexture: texture_2d<f32>;\r
1367
+ @group(1) @binding(1) var atlasSampler: sampler;\r
1368
+ \r
1369
+ struct VIn {\r
1370
+ @location(0) corner: vec2f,\r
1371
+ }\r
1372
+ \r
1373
+ struct VOut {\r
1374
+ @builtin(position) position: vec4f,\r
1375
+ @location(0) uv: vec2f,\r
1376
+ @location(1) modulation: vec4f,\r
1377
+ }\r
1378
+ \r
1379
+ @vertex\r
1380
+ fn vs(input: VIn, @builtin(instance_index) instance: u32) -> VOut {\r
1381
+ let base = 8u + instance * 24u;\r
1382
+ let birth = instanceData[base];\r
1383
+ let life = max(instanceData[base + 1u], 0.0001);\r
1384
+ let age = instanceData[0] - birth;\r
1385
+ let safeAge = max(age, 0.0);\r
1386
+ var position = vec2f(instanceData[base + 2u], instanceData[base + 3u])\r
1387
+ + vec2f(instanceData[base + 4u], instanceData[base + 5u]) * safeAge\r
1388
+ + 0.5 * vec2f(instanceData[base + 6u], instanceData[base + 7u]) * safeAge * safeAge;\r
1389
+ let scale = max(0.04, instanceData[base + 8u] + instanceData[base + 9u] * safeAge)\r
1390
+ * instanceData[2];\r
1391
+ let unitCorner = input.corner + vec2f(0.5);\r
1392
+ let anchor = vec2f(instanceData[base + 18u], instanceData[base + 19u]);\r
1393
+ let spriteSize = vec2f(instanceData[base + 16u], instanceData[base + 17u]);\r
1394
+ let local = (unitCorner - anchor) * spriteSize * scale;\r
1395
+ let angle = instanceData[base + 10u] + instanceData[base + 11u] * safeAge;\r
1396
+ let c = cos(angle);\r
1397
+ let s = sin(angle);\r
1398
+ let rotated = vec2f(c * local.x - s * local.y, s * local.x + c * local.y);\r
1399
+ let progress = clamp(safeAge / life, 0.0, 1.0);\r
1400
+ var fade = select(\r
1401
+ 1.0,\r
1402
+ min(safeAge / 0.04, 1.0) * pow(1.0 - progress, 0.78),\r
1403
+ instanceData[3] > 0.5,\r
1404
+ );\r
1405
+ if (age < 0.0 || age > life) {\r
1406
+ position = vec2f(-100000.0);\r
1407
+ fade = 0.0;\r
1408
+ }\r
1409
+ let cssScale = vec2f(instanceData[4], instanceData[5]);\r
1410
+ let alpha = instanceData[base + 15u] * fade * instanceData[1];\r
1411
+ var output: VOut;\r
1412
+ output.position = globals.projection * vec4f((position + rotated) * cssScale, 0.0, 1.0);\r
1413
+ output.uv = mix(\r
1414
+ vec2f(instanceData[base + 20u], instanceData[base + 21u]),\r
1415
+ vec2f(instanceData[base + 22u], instanceData[base + 23u]),\r
1416
+ unitCorner,\r
1417
+ );\r
1418
+ output.modulation = vec4f(\r
1419
+ instanceData[base + 12u] * alpha,\r
1420
+ instanceData[base + 13u] * alpha,\r
1421
+ instanceData[base + 14u] * alpha,\r
1422
+ alpha,\r
1423
+ );\r
1424
+ return output;\r
1425
+ }\r
1426
+ \r
1427
+ @fragment\r
1428
+ fn fs(input: VOut) -> @location(0) vec4f {\r
1429
+ let sampled = textureSample(atlasTexture, atlasSampler, input.uv);\r
1430
+ return vec4f(sampled.rgb * input.modulation.rgb, sampled.a * input.modulation.a);\r
1431
+ }\r
1432
1432
  `, Ii = `struct Globals {\r
1433
1433
  projection: mat4x4f,\r
1434
1434
  }\r
@@ -1773,292 +1773,292 @@ fn applyMotionPoint(point: vec2f, center: vec2f, scale: vec2f, cosine: f32, sine
1773
1773
  svgaMotionInstancedPremul: Ii,
1774
1774
  svgaFrameTableShape: Bi,
1775
1775
  svgaFrameTableClipMask: Ci
1776
- }, Qi = `/// SVGA timeline/table variant for premultiplied RGBA atlas textures.
1777
- ///
1778
- /// The frame table and sprite metadata are resident storage buffers. A draw
1779
- /// submits one instance per sprite. Direct draws derive the sprite index from
1780
- /// the GPU instance index and only upload the slot/global uniform. Hybrid
1781
- /// draws can additionally bind compact CPU-precompiled scheduling rows that
1782
- /// omit the SVGA child matrix and alpha fetched from the frame table.
1783
- ///
1784
- /// Frame table: three vec4 values per (sprite, frame):
1785
- /// 0: layoutW, layoutH, a, b
1786
- /// 1: c, d, tx, ty
1787
- /// 2: alpha, reserved, reserved, reserved
1788
- ///
1789
- /// Sprite metadata: two vec4 values per draw sprite:
1790
- /// 0: atlas UV min.xy / max.xy
1791
- /// 1: source sprite index, atlas page, flags, reserved
1792
- ///
1793
- /// Uniform layout:
1794
- /// projection mat4x4f (64 bytes)
1795
- /// parentAffine vec4f (a, b, c, d)
1796
- /// translateOpacityFrame vec4f (tx, ty, opacity, frameIndex)
1797
- /// clipRect vec4f (top-left x0, y0, x1, y1)
1798
- /// drawInfo vec4u (metadataBase, drawSpriteCount, clipEnabled, trackIndex+1)
1799
- /// tableInfo vec4u (frameCount, spriteCount, vec4sPerFrame, 0)
1800
- /// batchInfo vec4u (spritesPerSlot, metadataVec4Stride, stateMode, 0)
1801
-
1802
- struct Globals {
1803
- projection: mat4x4f,
1804
- parentAffine: vec4f,
1805
- translateOpacityFrame: vec4f,
1806
- clipRect: vec4f,
1807
- drawInfo: vec4u,
1808
- tableInfo: vec4u,
1809
- batchInfo: vec4u,
1810
- }
1811
-
1812
- struct MotionGlobals {
1813
- timeMs: f32,
1814
- sampleIntervalMs: f32,
1815
- sampleCount: f32,
1816
- cssScaleX: f32,
1817
- cssScaleY: f32,
1818
- pad0: f32,
1819
- pad1: f32,
1820
- pad2: f32,
1821
- }
1822
-
1823
- @group(0) @binding(0) var<uniform> globals: Globals;
1824
- @group(0) @binding(1) var<storage, read> frameTable: array<vec4f>;
1825
- @group(0) @binding(2) var<storage, read> spriteMetadata: array<vec4f>;
1826
- @group(0) @binding(3) var<storage, read> motionData: array<f32>;
1827
- @group(0) @binding(4) var<uniform> motionGlobals: MotionGlobals;
1828
- // Canonical four-vec4 / 16-float slot row: affine; translate+opacity+frame;
1829
- // clip rect; clipEnabled+metadataBase+atlasPage+motionTrack+1.
1830
- // Optional Hybrid scheduling rows use this exact schema per draw instance.
1831
- // Direct draws bind a harmless dummy slice and leave drawInfo bit 1 clear.
1832
- @group(0) @binding(5) var<storage, read> hybridInstances: array<vec4f>;
1833
- @group(1) @binding(0) var atlasTex: texture_2d<f32>;
1834
- @group(1) @binding(1) var atlasSampler: sampler;
1835
-
1836
- struct VIn {
1837
- @location(0) corner: vec2f,
1838
- }
1839
-
1840
- struct VOut {
1841
- @builtin(position) pos: vec4f,
1842
- @location(0) uv: vec2f,
1843
- @location(1) color: vec4f,
1844
- @location(2) @interpolate(flat) clipRect: vec4f,
1845
- @location(3) @interpolate(flat) clipEnabled: f32,
1846
- @location(4) localPosition: vec2f,
1847
- @location(5) @interpolate(flat) localClipRect: vec4f,
1848
- @location(6) @interpolate(flat) localClipEnabled: f32,
1849
- }
1850
-
1851
- fn readFrameValue(index: u32) -> vec4f {
1852
- return frameTable[index];
1853
- }
1854
-
1855
- fn sampleMotion(track: u32, channel: u32) -> f32 {
1856
- let sampleCount = max(u32(motionGlobals.sampleCount), 1u);
1857
- let samplePosition = clamp(
1858
- motionGlobals.timeMs / max(motionGlobals.sampleIntervalMs, 0.001),
1859
- 0.0,
1860
- f32(sampleCount - 1u),
1861
- );
1862
- let left = u32(floor(samplePosition));
1863
- let right = min(sampleCount - 1u, left + 1u);
1864
- let trackBase = track * sampleCount * 8u;
1865
- let leftBase = trackBase + left * 8u;
1866
- let rightBase = trackBase + right * 8u;
1867
- let interpolate = left != right && motionData[leftBase + 7u] > 0.5 && channel < 6u;
1868
- if (!interpolate) {
1869
- return motionData[leftBase + channel];
1870
- }
1871
- let progress = samplePosition - f32(left);
1872
- return mix(motionData[leftBase + channel], motionData[rightBase + channel], progress);
1873
- }
1874
-
1875
- fn applyMotionPoint(
1876
- point: vec2f,
1877
- center: vec2f,
1878
- scale: vec2f,
1879
- cosine: f32,
1880
- sine: f32,
1881
- ) -> vec2f {
1882
- let scaled = point * scale;
1883
- return center + vec2f(
1884
- cosine * scaled.x - sine * scaled.y,
1885
- sine * scaled.x + cosine * scaled.y,
1886
- );
1887
- }
1888
-
1889
- @vertex
1890
- fn vs(input: VIn, @builtin(instance_index) instance: u32) -> VOut {
1891
- let safeInstance = min(instance, max(globals.drawInfo.y, 1u) - 1u);
1892
- let hybrid = (globals.drawInfo.z & 2u) != 0u;
1893
- let compactSlots = (globals.drawInfo.z & 4u) != 0u;
1894
- let spritesPerSlot = max(globals.batchInfo.x, 1u);
1895
- let slotStateIndex = select(safeInstance, safeInstance / spritesPerSlot, compactSlots);
1896
- let hybridBase = slotStateIndex * 4u;
1897
- var hybridParent = vec4f(0.0);
1898
- var hybridTranslateOpacityFrame = vec4f(0.0);
1899
- var hybridClip = vec4f(0.0);
1900
- var hybridInfo = vec4f(0.0);
1901
- if (hybrid || compactSlots) {
1902
- hybridParent = hybridInstances[hybridBase];
1903
- hybridTranslateOpacityFrame = hybridInstances[hybridBase + 1u];
1904
- hybridClip = hybridInstances[hybridBase + 2u];
1905
- hybridInfo = hybridInstances[hybridBase + 3u];
1906
- }
1907
- let spriteWithinSlot = select(safeInstance, safeInstance % spritesPerSlot, compactSlots);
1908
- let metadataIndex = select(
1909
- globals.drawInfo.x + spriteWithinSlot,
1910
- u32(max(hybridInfo.y, 0.0)),
1911
- hybrid,
1912
- );
1913
- let metadataStride = max(globals.batchInfo.y, 2u);
1914
- let metadataBase = metadataIndex * metadataStride;
1915
- let metadataUv = spriteMetadata[metadataBase];
1916
- let metadataSprite = spriteMetadata[metadataBase + 1u];
1917
- var metadataClip = vec4f(0.0);
1918
- if (metadataStride >= 3u) {
1919
- metadataClip = spriteMetadata[metadataBase + 2u];
1920
- }
1921
- let metadataPage = metadataSprite.y;
1922
- let metadataFlags = u32(max(metadataSprite.z, 0.0));
1923
- // The source sprite index is explicit so a page-specific metadata range
1924
- // can represent non-contiguous atlas pages without duplicating frame rows.
1925
- // A page mismatch is made transparent so an invalid plan cannot sample a
1926
- // sprite into the wrong atlas page.
1927
- let spriteIndex = u32(max(metadataSprite.x, 0.0));
1928
-
1929
- let frameCount = max(globals.tableInfo.x, 1u);
1930
- let spriteCount = max(globals.tableInfo.y, 1u);
1931
- let safeSprite = min(spriteIndex, spriteCount - 1u);
1932
- let selectedFrame = select(
1933
- globals.translateOpacityFrame.w,
1934
- hybridTranslateOpacityFrame.w,
1935
- hybrid || compactSlots,
1936
- );
1937
- let safeFrame = min(
1938
- u32(max(selectedFrame, 0.0)),
1939
- frameCount - 1u,
1940
- );
1941
- let tableBase = (safeSprite * frameCount + safeFrame) * globals.tableInfo.z;
1942
- let frame0 = readFrameValue(tableBase);
1943
- let frame1 = readFrameValue(tableBase + 1u);
1944
- let frame2 = readFrameValue(tableBase + 2u);
1945
-
1946
- let layoutW = frame0.x;
1947
- let layoutH = frame0.y;
1948
- let local = vec2f(
1949
- frame0.z * layoutW * input.corner.x + frame1.x * layoutH * input.corner.y + frame1.z,
1950
- frame0.w * layoutW * input.corner.x + frame1.y * layoutH * input.corner.y + frame1.w,
1951
- );
1952
-
1953
- let instanceSlotState = hybrid || compactSlots;
1954
- let parent = select(globals.parentAffine, hybridParent, instanceSlotState);
1955
- let parentTranslate = select(
1956
- globals.translateOpacityFrame.xy,
1957
- hybridTranslateOpacityFrame.xy,
1958
- instanceSlotState,
1959
- );
1960
- let parentLocal = vec2f(
1961
- parent.x * local.x + parent.z * local.y + parentTranslate.x,
1962
- parent.y * local.x + parent.w * local.y + parentTranslate.y,
1963
- );
1964
- let instanceTrack = u32(max(hybridInfo.w, 0.0));
1965
- let selectedTrack = select(globals.drawInfo.w, instanceTrack, compactSlots);
1966
- let hasParentMotion = selectedTrack > 0u;
1967
- var world = parentLocal;
1968
- var outerClip = select(globals.clipRect, hybridClip, instanceSlotState);
1969
- let outerClipEnabled = select(
1970
- f32(globals.drawInfo.z & 1u),
1971
- hybridInfo.x,
1972
- instanceSlotState,
1973
- );
1974
- var parentOpacity = select(
1975
- globals.translateOpacityFrame.z,
1976
- hybridTranslateOpacityFrame.z,
1977
- instanceSlotState,
1978
- );
1979
- if (hasParentMotion) {
1980
- let track = selectedTrack - 1u;
1981
- let scale = vec2f(sampleMotion(track, 2u), sampleMotion(track, 3u));
1982
- let angle = sampleMotion(track, 4u);
1983
- let cosine = cos(angle);
1984
- let sine = sin(angle);
1985
- let center = vec2f(
1986
- sampleMotion(track, 0u) * motionGlobals.cssScaleX,
1987
- sampleMotion(track, 1u) * motionGlobals.cssScaleY,
1988
- );
1989
- world = applyMotionPoint(parentLocal, center, scale, cosine, sine);
1990
- let clip0 = applyMotionPoint(outerClip.xy, center, scale, cosine, sine);
1991
- let clip1 = applyMotionPoint(vec2f(outerClip.z, outerClip.y), center, scale, cosine, sine);
1992
- let clip2 = applyMotionPoint(outerClip.zw, center, scale, cosine, sine);
1993
- let clip3 = applyMotionPoint(vec2f(outerClip.x, outerClip.w), center, scale, cosine, sine);
1994
- outerClip = vec4f(
1995
- min(min(clip0.x, clip1.x), min(clip2.x, clip3.x)),
1996
- min(min(clip0.y, clip1.y), min(clip2.y, clip3.y)),
1997
- max(max(clip0.x, clip1.x), max(clip2.x, clip3.x)),
1998
- max(max(clip0.y, clip1.y), max(clip2.y, clip3.y)),
1999
- );
2000
- let visible = sampleMotion(track, 6u);
2001
- parentOpacity = sampleMotion(track, 5u) * select(0.0, 1.0, visible > 0.5);
2002
- }
2003
-
2004
- var output: VOut;
2005
- output.pos = globals.projection * vec4f(world, 0.0, 1.0);
2006
- output.uv = mix(metadataUv.xy, metadataUv.zw, input.corner);
2007
- var pageMatchesValue = globals.tableInfo.w == 0xffffffffu ||
2008
- u32(max(metadataPage, 0.0)) == globals.tableInfo.w;
2009
- if (hybrid || compactSlots) {
2010
- pageMatchesValue = hybridInfo.z < -0.5 ||
2011
- i32(round(metadataPage)) == i32(round(hybridInfo.z));
2012
- }
2013
- let pageMatches = select(
2014
- 0.0,
2015
- 1.0,
2016
- pageMatchesValue,
2017
- );
2018
- let metadataPresent = select(1.0, 0.0, (metadataFlags & 1u) != 0u);
2019
- // Keep the table path's visibility cutoff identical to the CPU reference
2020
- // renderer: rows below 0.05 are culled before issuing meaningful color.
2021
- // Exactly 0.05 remains visible (the reference uses a strict \`< 0.05\` test).
2022
- let effectiveAlpha = frame2.x * parentOpacity * pageMatches * metadataPresent;
2023
- let visibleAlpha = select(0.0, effectiveAlpha, effectiveAlpha >= 0.05);
2024
- output.color = vec4f(visibleAlpha);
2025
- output.clipRect = outerClip;
2026
- output.clipEnabled = outerClipEnabled;
2027
- output.localPosition = vec2f(layoutW * input.corner.x, layoutH * input.corner.y);
2028
- output.localClipRect = metadataClip;
2029
- output.localClipEnabled = select(0.0, 1.0, (metadataFlags & 2u) != 0u);
2030
- return output;
2031
- }
2032
-
2033
- @fragment
2034
- fn fs(input: VOut) -> @location(0) vec4f {
2035
- if (input.color.a < 0.05) {
2036
- discard;
2037
- }
2038
- if (input.clipEnabled > 0.5) {
2039
- if (
2040
- input.pos.x < input.clipRect.x ||
2041
- input.pos.y < input.clipRect.y ||
2042
- input.pos.x >= input.clipRect.z ||
2043
- input.pos.y >= input.clipRect.w
2044
- ) {
2045
- discard;
2046
- }
2047
- }
2048
- if (
2049
- input.localClipEnabled > 0.5 &&
2050
- (
2051
- input.localPosition.x < input.localClipRect.x ||
2052
- input.localPosition.y < input.localClipRect.y ||
2053
- input.localPosition.x >= input.localClipRect.z ||
2054
- input.localPosition.y >= input.localClipRect.w
2055
- )
2056
- ) {
2057
- discard;
2058
- }
2059
- let color = textureSample(atlasTex, atlasSampler, input.uv);
2060
- return vec4f(color.rgb * input.color.a, color.a * input.color.a);
2061
- }
1776
+ }, Qi = `/// SVGA timeline/table variant for premultiplied RGBA atlas textures.\r
1777
+ ///\r
1778
+ /// The frame table and sprite metadata are resident storage buffers. A draw\r
1779
+ /// submits one instance per sprite. Direct draws derive the sprite index from\r
1780
+ /// the GPU instance index and only upload the slot/global uniform. Hybrid\r
1781
+ /// draws can additionally bind compact CPU-precompiled scheduling rows that\r
1782
+ /// omit the SVGA child matrix and alpha fetched from the frame table.\r
1783
+ ///\r
1784
+ /// Frame table: three vec4 values per (sprite, frame):\r
1785
+ /// 0: layoutW, layoutH, a, b\r
1786
+ /// 1: c, d, tx, ty\r
1787
+ /// 2: alpha, reserved, reserved, reserved\r
1788
+ ///\r
1789
+ /// Sprite metadata: two vec4 values per draw sprite:\r
1790
+ /// 0: atlas UV min.xy / max.xy\r
1791
+ /// 1: source sprite index, atlas page, flags, reserved\r
1792
+ ///\r
1793
+ /// Uniform layout:\r
1794
+ /// projection mat4x4f (64 bytes)\r
1795
+ /// parentAffine vec4f (a, b, c, d)\r
1796
+ /// translateOpacityFrame vec4f (tx, ty, opacity, frameIndex)\r
1797
+ /// clipRect vec4f (top-left x0, y0, x1, y1)\r
1798
+ /// drawInfo vec4u (metadataBase, drawSpriteCount, clipEnabled, trackIndex+1)\r
1799
+ /// tableInfo vec4u (frameCount, spriteCount, vec4sPerFrame, 0)\r
1800
+ /// batchInfo vec4u (spritesPerSlot, metadataVec4Stride, stateMode, 0)\r
1801
+ \r
1802
+ struct Globals {\r
1803
+ projection: mat4x4f,\r
1804
+ parentAffine: vec4f,\r
1805
+ translateOpacityFrame: vec4f,\r
1806
+ clipRect: vec4f,\r
1807
+ drawInfo: vec4u,\r
1808
+ tableInfo: vec4u,\r
1809
+ batchInfo: vec4u,\r
1810
+ }\r
1811
+ \r
1812
+ struct MotionGlobals {\r
1813
+ timeMs: f32,\r
1814
+ sampleIntervalMs: f32,\r
1815
+ sampleCount: f32,\r
1816
+ cssScaleX: f32,\r
1817
+ cssScaleY: f32,\r
1818
+ pad0: f32,\r
1819
+ pad1: f32,\r
1820
+ pad2: f32,\r
1821
+ }\r
1822
+ \r
1823
+ @group(0) @binding(0) var<uniform> globals: Globals;\r
1824
+ @group(0) @binding(1) var<storage, read> frameTable: array<vec4f>;\r
1825
+ @group(0) @binding(2) var<storage, read> spriteMetadata: array<vec4f>;\r
1826
+ @group(0) @binding(3) var<storage, read> motionData: array<f32>;\r
1827
+ @group(0) @binding(4) var<uniform> motionGlobals: MotionGlobals;\r
1828
+ // Canonical four-vec4 / 16-float slot row: affine; translate+opacity+frame;\r
1829
+ // clip rect; clipEnabled+metadataBase+atlasPage+motionTrack+1.\r
1830
+ // Optional Hybrid scheduling rows use this exact schema per draw instance.\r
1831
+ // Direct draws bind a harmless dummy slice and leave drawInfo bit 1 clear.\r
1832
+ @group(0) @binding(5) var<storage, read> hybridInstances: array<vec4f>;\r
1833
+ @group(1) @binding(0) var atlasTex: texture_2d<f32>;\r
1834
+ @group(1) @binding(1) var atlasSampler: sampler;\r
1835
+ \r
1836
+ struct VIn {\r
1837
+ @location(0) corner: vec2f,\r
1838
+ }\r
1839
+ \r
1840
+ struct VOut {\r
1841
+ @builtin(position) pos: vec4f,\r
1842
+ @location(0) uv: vec2f,\r
1843
+ @location(1) color: vec4f,\r
1844
+ @location(2) @interpolate(flat) clipRect: vec4f,\r
1845
+ @location(3) @interpolate(flat) clipEnabled: f32,\r
1846
+ @location(4) localPosition: vec2f,\r
1847
+ @location(5) @interpolate(flat) localClipRect: vec4f,\r
1848
+ @location(6) @interpolate(flat) localClipEnabled: f32,\r
1849
+ }\r
1850
+ \r
1851
+ fn readFrameValue(index: u32) -> vec4f {\r
1852
+ return frameTable[index];\r
1853
+ }\r
1854
+ \r
1855
+ fn sampleMotion(track: u32, channel: u32) -> f32 {\r
1856
+ let sampleCount = max(u32(motionGlobals.sampleCount), 1u);\r
1857
+ let samplePosition = clamp(\r
1858
+ motionGlobals.timeMs / max(motionGlobals.sampleIntervalMs, 0.001),\r
1859
+ 0.0,\r
1860
+ f32(sampleCount - 1u),\r
1861
+ );\r
1862
+ let left = u32(floor(samplePosition));\r
1863
+ let right = min(sampleCount - 1u, left + 1u);\r
1864
+ let trackBase = track * sampleCount * 8u;\r
1865
+ let leftBase = trackBase + left * 8u;\r
1866
+ let rightBase = trackBase + right * 8u;\r
1867
+ let interpolate = left != right && motionData[leftBase + 7u] > 0.5 && channel < 6u;\r
1868
+ if (!interpolate) {\r
1869
+ return motionData[leftBase + channel];\r
1870
+ }\r
1871
+ let progress = samplePosition - f32(left);\r
1872
+ return mix(motionData[leftBase + channel], motionData[rightBase + channel], progress);\r
1873
+ }\r
1874
+ \r
1875
+ fn applyMotionPoint(\r
1876
+ point: vec2f,\r
1877
+ center: vec2f,\r
1878
+ scale: vec2f,\r
1879
+ cosine: f32,\r
1880
+ sine: f32,\r
1881
+ ) -> vec2f {\r
1882
+ let scaled = point * scale;\r
1883
+ return center + vec2f(\r
1884
+ cosine * scaled.x - sine * scaled.y,\r
1885
+ sine * scaled.x + cosine * scaled.y,\r
1886
+ );\r
1887
+ }\r
1888
+ \r
1889
+ @vertex\r
1890
+ fn vs(input: VIn, @builtin(instance_index) instance: u32) -> VOut {\r
1891
+ let safeInstance = min(instance, max(globals.drawInfo.y, 1u) - 1u);\r
1892
+ let hybrid = (globals.drawInfo.z & 2u) != 0u;\r
1893
+ let compactSlots = (globals.drawInfo.z & 4u) != 0u;\r
1894
+ let spritesPerSlot = max(globals.batchInfo.x, 1u);\r
1895
+ let slotStateIndex = select(safeInstance, safeInstance / spritesPerSlot, compactSlots);\r
1896
+ let hybridBase = slotStateIndex * 4u;\r
1897
+ var hybridParent = vec4f(0.0);\r
1898
+ var hybridTranslateOpacityFrame = vec4f(0.0);\r
1899
+ var hybridClip = vec4f(0.0);\r
1900
+ var hybridInfo = vec4f(0.0);\r
1901
+ if (hybrid || compactSlots) {\r
1902
+ hybridParent = hybridInstances[hybridBase];\r
1903
+ hybridTranslateOpacityFrame = hybridInstances[hybridBase + 1u];\r
1904
+ hybridClip = hybridInstances[hybridBase + 2u];\r
1905
+ hybridInfo = hybridInstances[hybridBase + 3u];\r
1906
+ }\r
1907
+ let spriteWithinSlot = select(safeInstance, safeInstance % spritesPerSlot, compactSlots);\r
1908
+ let metadataIndex = select(\r
1909
+ globals.drawInfo.x + spriteWithinSlot,\r
1910
+ u32(max(hybridInfo.y, 0.0)),\r
1911
+ hybrid,\r
1912
+ );\r
1913
+ let metadataStride = max(globals.batchInfo.y, 2u);\r
1914
+ let metadataBase = metadataIndex * metadataStride;\r
1915
+ let metadataUv = spriteMetadata[metadataBase];\r
1916
+ let metadataSprite = spriteMetadata[metadataBase + 1u];\r
1917
+ var metadataClip = vec4f(0.0);\r
1918
+ if (metadataStride >= 3u) {\r
1919
+ metadataClip = spriteMetadata[metadataBase + 2u];\r
1920
+ }\r
1921
+ let metadataPage = metadataSprite.y;\r
1922
+ let metadataFlags = u32(max(metadataSprite.z, 0.0));\r
1923
+ // The source sprite index is explicit so a page-specific metadata range\r
1924
+ // can represent non-contiguous atlas pages without duplicating frame rows.\r
1925
+ // A page mismatch is made transparent so an invalid plan cannot sample a\r
1926
+ // sprite into the wrong atlas page.\r
1927
+ let spriteIndex = u32(max(metadataSprite.x, 0.0));\r
1928
+ \r
1929
+ let frameCount = max(globals.tableInfo.x, 1u);\r
1930
+ let spriteCount = max(globals.tableInfo.y, 1u);\r
1931
+ let safeSprite = min(spriteIndex, spriteCount - 1u);\r
1932
+ let selectedFrame = select(\r
1933
+ globals.translateOpacityFrame.w,\r
1934
+ hybridTranslateOpacityFrame.w,\r
1935
+ hybrid || compactSlots,\r
1936
+ );\r
1937
+ let safeFrame = min(\r
1938
+ u32(max(selectedFrame, 0.0)),\r
1939
+ frameCount - 1u,\r
1940
+ );\r
1941
+ let tableBase = (safeSprite * frameCount + safeFrame) * globals.tableInfo.z;\r
1942
+ let frame0 = readFrameValue(tableBase);\r
1943
+ let frame1 = readFrameValue(tableBase + 1u);\r
1944
+ let frame2 = readFrameValue(tableBase + 2u);\r
1945
+ \r
1946
+ let layoutW = frame0.x;\r
1947
+ let layoutH = frame0.y;\r
1948
+ let local = vec2f(\r
1949
+ frame0.z * layoutW * input.corner.x + frame1.x * layoutH * input.corner.y + frame1.z,\r
1950
+ frame0.w * layoutW * input.corner.x + frame1.y * layoutH * input.corner.y + frame1.w,\r
1951
+ );\r
1952
+ \r
1953
+ let instanceSlotState = hybrid || compactSlots;\r
1954
+ let parent = select(globals.parentAffine, hybridParent, instanceSlotState);\r
1955
+ let parentTranslate = select(\r
1956
+ globals.translateOpacityFrame.xy,\r
1957
+ hybridTranslateOpacityFrame.xy,\r
1958
+ instanceSlotState,\r
1959
+ );\r
1960
+ let parentLocal = vec2f(\r
1961
+ parent.x * local.x + parent.z * local.y + parentTranslate.x,\r
1962
+ parent.y * local.x + parent.w * local.y + parentTranslate.y,\r
1963
+ );\r
1964
+ let instanceTrack = u32(max(hybridInfo.w, 0.0));\r
1965
+ let selectedTrack = select(globals.drawInfo.w, instanceTrack, compactSlots);\r
1966
+ let hasParentMotion = selectedTrack > 0u;\r
1967
+ var world = parentLocal;\r
1968
+ var outerClip = select(globals.clipRect, hybridClip, instanceSlotState);\r
1969
+ let outerClipEnabled = select(\r
1970
+ f32(globals.drawInfo.z & 1u),\r
1971
+ hybridInfo.x,\r
1972
+ instanceSlotState,\r
1973
+ );\r
1974
+ var parentOpacity = select(\r
1975
+ globals.translateOpacityFrame.z,\r
1976
+ hybridTranslateOpacityFrame.z,\r
1977
+ instanceSlotState,\r
1978
+ );\r
1979
+ if (hasParentMotion) {\r
1980
+ let track = selectedTrack - 1u;\r
1981
+ let scale = vec2f(sampleMotion(track, 2u), sampleMotion(track, 3u));\r
1982
+ let angle = sampleMotion(track, 4u);\r
1983
+ let cosine = cos(angle);\r
1984
+ let sine = sin(angle);\r
1985
+ let center = vec2f(\r
1986
+ sampleMotion(track, 0u) * motionGlobals.cssScaleX,\r
1987
+ sampleMotion(track, 1u) * motionGlobals.cssScaleY,\r
1988
+ );\r
1989
+ world = applyMotionPoint(parentLocal, center, scale, cosine, sine);\r
1990
+ let clip0 = applyMotionPoint(outerClip.xy, center, scale, cosine, sine);\r
1991
+ let clip1 = applyMotionPoint(vec2f(outerClip.z, outerClip.y), center, scale, cosine, sine);\r
1992
+ let clip2 = applyMotionPoint(outerClip.zw, center, scale, cosine, sine);\r
1993
+ let clip3 = applyMotionPoint(vec2f(outerClip.x, outerClip.w), center, scale, cosine, sine);\r
1994
+ outerClip = vec4f(\r
1995
+ min(min(clip0.x, clip1.x), min(clip2.x, clip3.x)),\r
1996
+ min(min(clip0.y, clip1.y), min(clip2.y, clip3.y)),\r
1997
+ max(max(clip0.x, clip1.x), max(clip2.x, clip3.x)),\r
1998
+ max(max(clip0.y, clip1.y), max(clip2.y, clip3.y)),\r
1999
+ );\r
2000
+ let visible = sampleMotion(track, 6u);\r
2001
+ parentOpacity = sampleMotion(track, 5u) * select(0.0, 1.0, visible > 0.5);\r
2002
+ }\r
2003
+ \r
2004
+ var output: VOut;\r
2005
+ output.pos = globals.projection * vec4f(world, 0.0, 1.0);\r
2006
+ output.uv = mix(metadataUv.xy, metadataUv.zw, input.corner);\r
2007
+ var pageMatchesValue = globals.tableInfo.w == 0xffffffffu ||\r
2008
+ u32(max(metadataPage, 0.0)) == globals.tableInfo.w;\r
2009
+ if (hybrid || compactSlots) {\r
2010
+ pageMatchesValue = hybridInfo.z < -0.5 ||\r
2011
+ i32(round(metadataPage)) == i32(round(hybridInfo.z));\r
2012
+ }\r
2013
+ let pageMatches = select(\r
2014
+ 0.0,\r
2015
+ 1.0,\r
2016
+ pageMatchesValue,\r
2017
+ );\r
2018
+ let metadataPresent = select(1.0, 0.0, (metadataFlags & 1u) != 0u);\r
2019
+ // Keep the table path's visibility cutoff identical to the CPU reference\r
2020
+ // renderer: rows below 0.05 are culled before issuing meaningful color.\r
2021
+ // Exactly 0.05 remains visible (the reference uses a strict \`< 0.05\` test).\r
2022
+ let effectiveAlpha = frame2.x * parentOpacity * pageMatches * metadataPresent;\r
2023
+ let visibleAlpha = select(0.0, effectiveAlpha, effectiveAlpha >= 0.05);\r
2024
+ output.color = vec4f(visibleAlpha);\r
2025
+ output.clipRect = outerClip;\r
2026
+ output.clipEnabled = outerClipEnabled;\r
2027
+ output.localPosition = vec2f(layoutW * input.corner.x, layoutH * input.corner.y);\r
2028
+ output.localClipRect = metadataClip;\r
2029
+ output.localClipEnabled = select(0.0, 1.0, (metadataFlags & 2u) != 0u);\r
2030
+ return output;\r
2031
+ }\r
2032
+ \r
2033
+ @fragment\r
2034
+ fn fs(input: VOut) -> @location(0) vec4f {\r
2035
+ if (input.color.a < 0.05) {\r
2036
+ discard;\r
2037
+ }\r
2038
+ if (input.clipEnabled > 0.5) {\r
2039
+ if (\r
2040
+ input.pos.x < input.clipRect.x ||\r
2041
+ input.pos.y < input.clipRect.y ||\r
2042
+ input.pos.x >= input.clipRect.z ||\r
2043
+ input.pos.y >= input.clipRect.w\r
2044
+ ) {\r
2045
+ discard;\r
2046
+ }\r
2047
+ }\r
2048
+ if (\r
2049
+ input.localClipEnabled > 0.5 &&\r
2050
+ (\r
2051
+ input.localPosition.x < input.localClipRect.x ||\r
2052
+ input.localPosition.y < input.localClipRect.y ||\r
2053
+ input.localPosition.x >= input.localClipRect.z ||\r
2054
+ input.localPosition.y >= input.localClipRect.w\r
2055
+ )\r
2056
+ ) {\r
2057
+ discard;\r
2058
+ }\r
2059
+ let color = textureSample(atlasTex, atlasSampler, input.uv);\r
2060
+ return vec4f(color.rgb * input.color.a, color.a * input.color.a);\r
2061
+ }\r
2062
2062
  `, tg = Object.freeze({
2063
2063
  submitted: !0
2064
2064
  });
@@ -17052,18 +17052,18 @@ async function I(t, e, n, o, s) {
17052
17052
  }
17053
17053
  function v(t, e, n, o, s, i) {
17054
17054
  if (n.w <= 0 || n.h <= 0 || i <= 0) return;
17055
- const l = Math.max(1, Math.floor(i * 0.5)), a = n.x, c = n.y, h = n.w, r = n.h, f = Math.min(l, a), u = Math.min(l, c), d = Math.min(l, o - (a + h)), w = Math.min(l, s - (c + r)), H = e.imageSmoothingEnabled;
17056
- e.imageSmoothingEnabled = !1, f > 0 && e.drawImage(t, a, c, 1, r, a - f, c, f, r), d > 0 && e.drawImage(t, a + h - 1, c, 1, r, a + h, c, d, r), u > 0 && e.drawImage(t, a, c, h, 1, a, c - u, h, u), w > 0 && e.drawImage(t, a, c + r - 1, h, 1, a, c + r, h, w), f > 0 && u > 0 && e.drawImage(t, a, c, 1, 1, a - f, c - u, f, u), d > 0 && u > 0 && e.drawImage(t, a + h - 1, c, 1, 1, a + h, c - u, d, u), f > 0 && w > 0 && e.drawImage(t, a, c + r - 1, 1, 1, a - f, c + r, f, w), d > 0 && w > 0 && e.drawImage(t, a + h - 1, c + r - 1, 1, 1, a + h, c + r, d, w), e.imageSmoothingEnabled = H;
17055
+ const l = Math.max(1, Math.floor(i * 0.5)), a = n.x, c = n.y, h = n.w, r = n.h, f = Math.min(l, a), u = Math.min(l, c), w = Math.min(l, o - (a + h)), d = Math.min(l, s - (c + r)), H = e.imageSmoothingEnabled;
17056
+ e.imageSmoothingEnabled = !1, f > 0 && e.drawImage(t, a, c, 1, r, a - f, c, f, r), w > 0 && e.drawImage(t, a + h - 1, c, 1, r, a + h, c, w, r), u > 0 && e.drawImage(t, a, c, h, 1, a, c - u, h, u), d > 0 && e.drawImage(t, a, c + r - 1, h, 1, a, c + r, h, d), f > 0 && u > 0 && e.drawImage(t, a, c, 1, 1, a - f, c - u, f, u), w > 0 && u > 0 && e.drawImage(t, a + h - 1, c, 1, 1, a + h, c - u, w, u), f > 0 && d > 0 && e.drawImage(t, a, c + r - 1, 1, 1, a - f, c + r, f, d), w > 0 && d > 0 && e.drawImage(t, a + h - 1, c + r - 1, 1, 1, a + h, c + r, w, d), e.imageSmoothingEnabled = H;
17057
17057
  }
17058
17058
  var E = Object.defineProperty, C = (t, e, n) => e in t ? E(t, e, { enumerable: !0, configurable: !0, writable: !0, value: n }) : t[e] = n, M = (t, e, n) => C(t, typeof e != "symbol" ? e + "" : e, n);
17059
17059
  function g() {
17060
17060
  return typeof performance != "undefined" ? performance.now() : Date.now();
17061
17061
  }
17062
- function S(t) {
17062
+ function A(t) {
17063
17063
  const e = t != null ? t : 4;
17064
17064
  return Number.isFinite(e) ? Math.max(1, Math.min(8, e)) : 4;
17065
17065
  }
17066
- class T {
17066
+ class S {
17067
17067
  constructor(e = 4) {
17068
17068
  this.maxSliceMs = e, M(this, "sliceStartedAt", g());
17069
17069
  }
@@ -17071,7 +17071,7 @@ class T {
17071
17071
  g() - this.sliceStartedAt < this.maxSliceMs || (await new Promise((e) => setTimeout(e, 0)), this.sliceStartedAt = g());
17072
17072
  }
17073
17073
  }
17074
- class A {
17074
+ class T {
17075
17075
  constructor() {
17076
17076
  M(this, "running", !1), M(this, "tasks", []);
17077
17077
  }
@@ -17090,7 +17090,7 @@ class A {
17090
17090
  }
17091
17091
  }
17092
17092
  }
17093
- const m = self, Y = new A();
17093
+ const m = self, Y = new T();
17094
17094
  async function _(t, e, n, o) {
17095
17095
  const s = new OffscreenCanvas(t.atlasW, t.atlasH), i = s.getContext("2d");
17096
17096
  if (!i) throw new Error("Atlas worker: 2d context unavailable");
@@ -17127,7 +17127,7 @@ async function X(t, e) {
17127
17127
  }
17128
17128
  async function $(t) {
17129
17129
  var e;
17130
- const n = [], o = new T(S(t.workerTimeSliceMs));
17130
+ const n = [], o = new S(A(t.workerTimeSliceMs));
17131
17131
  try {
17132
17132
  if (typeof OffscreenCanvas == "undefined")
17133
17133
  throw new Error("OffscreenCanvas unavailable in atlas worker");
@@ -17154,7 +17154,7 @@ async function $(t) {
17154
17154
  for (const r of l) {
17155
17155
  const f = await _(r, s, t.padding, o);
17156
17156
  t.captureEncodedPng && c.push(B(f));
17157
- const u = f.transferToImageBitmap();
17157
+ const u = await createImageBitmap(f, { premultiplyAlpha: "premultiply" });
17158
17158
  a.push({
17159
17159
  width: r.atlasW,
17160
17160
  height: r.atlasH,
@@ -17202,7 +17202,7 @@ m.onmessage = (t) => {
17202
17202
  const e = t.data;
17203
17203
  !e || e.type !== "build-svga-atlas" || Y.push(() => $(e));
17204
17204
  };
17205
- //# sourceMappingURL=svga-atlas-worker-B7n5WXUn.js.map
17205
+ //# sourceMappingURL=svga-atlas-worker-CkVFsaPa.js.map
17206
17206
  `, lQ = typeof self != "undefined" && self.Blob && new Blob(["URL.revokeObjectURL(import.meta.url);", sE], { type: "text/javascript;charset=utf-8" });
17207
17207
  function no(C) {
17208
17208
  let A;
@@ -17318,7 +17318,7 @@ function ho() {
17318
17318
  return NI;
17319
17319
  }
17320
17320
  function nE() {
17321
- return typeof Worker != "undefined" && UQ() && typeof OffscreenCanvas.prototype.transferToImageBitmap == "function";
17321
+ return typeof Worker != "undefined" && UQ() && typeof createImageBitmap == "function";
17322
17322
  }
17323
17323
  async function co(C, A) {
17324
17324
  if (!nE())
@@ -17524,7 +17524,8 @@ async function yo(C, A, g, I, B) {
17524
17524
  width: o.width,
17525
17525
  height: o.height,
17526
17526
  filter: "linear",
17527
- premultiplyAlpha: !0
17527
+ premultiplyAlpha: !0,
17528
+ sourcePremultiplied: !0
17528
17529
  });
17529
17530
  try {
17530
17531
  o.bitmap.close();