rapid-render 1.0.13 → 1.0.16
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.
- package/README.md +104 -19
- package/dist/buffer.d.ts +0 -5
- package/dist/color.d.ts +0 -4
- package/dist/index.d.ts +1 -0
- package/dist/math.d.ts +0 -3
- package/dist/matrix-engine.d.ts +17 -11
- package/dist/particle.d.ts +1 -0
- package/dist/rapid-render.js +542 -1402
- package/dist/rapid-render.umd.cjs +48 -9
- package/dist/region/particleRegion.d.ts +2 -0
- package/dist/render.d.ts +0 -1
- package/dist/texture.d.ts +0 -2
- package/package.json +4 -3
- package/dist/vite.svg +0 -1
package/dist/rapid-render.js
CHANGED
|
@@ -1,34 +1,17 @@
|
|
|
1
|
-
var
|
|
2
|
-
class
|
|
3
|
-
/** The number of elements currently used in the buffer. */
|
|
1
|
+
var S = /* @__PURE__ */ ((n) => (n[n.Float32 = 0] = "Float32", n[n.Uint32 = 1] = "Uint32", n[n.Uint16 = 2] = "Uint16", n))(S || {});
|
|
2
|
+
class A {
|
|
4
3
|
usedElemNum;
|
|
5
|
-
/** The main typed array view corresponding to the specified ArrayType. */
|
|
6
4
|
typedArray;
|
|
7
5
|
arrayType;
|
|
8
|
-
/** The maximum number of elements the buffer can currently hold without resizing. */
|
|
9
6
|
maxElemNum;
|
|
10
|
-
/** The number of bytes per element based on the `ArrayType`. */
|
|
11
7
|
bytePerElem;
|
|
12
8
|
arraybuffer;
|
|
13
|
-
/** `Uint32Array` view of the underlying memory buffer. */
|
|
14
9
|
uint32;
|
|
15
|
-
/** `Float32Array` view of the underlying memory buffer. */
|
|
16
10
|
float32;
|
|
17
|
-
/** `Uint16Array` view of the underlying memory buffer. */
|
|
18
11
|
uint16;
|
|
19
|
-
/**
|
|
20
|
-
* Initializes a new dynamic array buffer.
|
|
21
|
-
* @param arrayType - The type of elements this buffer will store primarily.
|
|
22
|
-
*/
|
|
23
12
|
constructor(t) {
|
|
24
13
|
this.usedElemNum = 0, this.maxElemNum = 512, this.bytePerElem = this.getArrayType(t).BYTES_PER_ELEMENT, this.arrayType = t, this.arraybuffer = new ArrayBuffer(this.maxElemNum * this.bytePerElem), this.updateTypedArray();
|
|
25
14
|
}
|
|
26
|
-
/**
|
|
27
|
-
* Returns the typed array constructor for the corresponding `ArrayType`.
|
|
28
|
-
* @param arrayType - The type of the array.
|
|
29
|
-
* @returns The typed array constructor.
|
|
30
|
-
* @throws Dispatches an error if the specified type is unsupported.
|
|
31
|
-
*/
|
|
32
15
|
getArrayType(t) {
|
|
33
16
|
switch (t) {
|
|
34
17
|
case 0:
|
|
@@ -41,9 +24,6 @@ class _ {
|
|
|
41
24
|
throw new Error("Unsupported ArrayType");
|
|
42
25
|
}
|
|
43
26
|
}
|
|
44
|
-
/**
|
|
45
|
-
* Updates the typed array views when the internal array buffer gets reallocated.
|
|
46
|
-
*/
|
|
47
27
|
updateTypedArray() {
|
|
48
28
|
switch (this.uint32 = new Uint32Array(this.arraybuffer), this.float32 = new Float32Array(this.arraybuffer), this.uint16 = new Uint16Array(this.arraybuffer), this.arrayType) {
|
|
49
29
|
case 0:
|
|
@@ -57,38 +37,30 @@ class _ {
|
|
|
57
37
|
break;
|
|
58
38
|
}
|
|
59
39
|
}
|
|
60
|
-
/**
|
|
61
|
-
* Resets the element usage count to zero. The underlying memory capacity is preserved.
|
|
62
|
-
*/
|
|
63
40
|
clear() {
|
|
64
41
|
this.usedElemNum = 0;
|
|
65
42
|
}
|
|
66
43
|
static removeAtIndices(t, e) {
|
|
67
|
-
const r = Math.max(...e.map((
|
|
68
|
-
(
|
|
69
|
-
).sort((
|
|
44
|
+
const r = Math.max(...e.map((h) => h.usedElemNum)), i = [...new Set(t)].filter(
|
|
45
|
+
(h) => h >= 0 && h < r
|
|
46
|
+
).sort((h, o) => h - o);
|
|
70
47
|
if (i.length === 0)
|
|
71
48
|
return 0;
|
|
72
49
|
let s = 0, a = 0;
|
|
73
|
-
for (let
|
|
74
|
-
if (a < i.length &&
|
|
50
|
+
for (let h = 0; h < r; h++) {
|
|
51
|
+
if (a < i.length && h === i[a]) {
|
|
75
52
|
a++;
|
|
76
53
|
continue;
|
|
77
54
|
}
|
|
78
|
-
if (s !==
|
|
79
|
-
for (const
|
|
80
|
-
|
|
55
|
+
if (s !== h)
|
|
56
|
+
for (const o of e)
|
|
57
|
+
o.typedArray[s] = o.typedArray[h];
|
|
81
58
|
s++;
|
|
82
59
|
}
|
|
83
|
-
for (const
|
|
84
|
-
|
|
60
|
+
for (const h of e)
|
|
61
|
+
h.usedElemNum = s;
|
|
85
62
|
return r - s;
|
|
86
63
|
}
|
|
87
|
-
/**
|
|
88
|
-
* Checks if the buffer has enough space for additional elements and resizes the buffer if necessary.
|
|
89
|
-
* @param size - The number of new elements that need to be accommodated.
|
|
90
|
-
* @returns `true` if the buffer was resized, `false` otherwise.
|
|
91
|
-
*/
|
|
92
64
|
resize(t = 0) {
|
|
93
65
|
if (t += this.usedElemNum, t > this.maxElemNum) {
|
|
94
66
|
for (; t > this.maxElemNum; )
|
|
@@ -97,125 +69,54 @@ class _ {
|
|
|
97
69
|
}
|
|
98
70
|
return !1;
|
|
99
71
|
}
|
|
100
|
-
/**
|
|
101
|
-
* Reallocates the underlying array buffer to a new size and copies existing data.
|
|
102
|
-
* @param size - The new maximum number of elements.
|
|
103
|
-
*/
|
|
104
72
|
setMaxSize(t = this.maxElemNum) {
|
|
105
73
|
const e = this.typedArray;
|
|
106
74
|
this.maxElemNum = t, this.arraybuffer = new ArrayBuffer(t * this.bytePerElem), this.updateTypedArray(), this.typedArray.set(e);
|
|
107
75
|
}
|
|
108
|
-
/**
|
|
109
|
-
* Appends a new 32-bit unsigned integer element to the buffer.
|
|
110
|
-
* @param value - The item to add.
|
|
111
|
-
*/
|
|
112
76
|
pushUint32(t) {
|
|
113
77
|
this.resize(1), this.uint32[this.usedElemNum++] = t;
|
|
114
78
|
}
|
|
115
|
-
/**
|
|
116
|
-
* Appends a new 32-bit floating point element to the buffer.
|
|
117
|
-
* @param value - The item to add.
|
|
118
|
-
*/
|
|
119
79
|
pushFloat32(t) {
|
|
120
80
|
this.resize(1), this.float32[this.usedElemNum++] = t;
|
|
121
81
|
}
|
|
122
|
-
/**
|
|
123
|
-
* Appends an element to the buffer, using the primary typed array view.
|
|
124
|
-
* @param value - The item to add.
|
|
125
|
-
*/
|
|
126
82
|
push(t) {
|
|
127
83
|
this.resize(1), this.typedArray[this.usedElemNum++] = t;
|
|
128
84
|
}
|
|
129
|
-
/**
|
|
130
|
-
* Removes and returns the last element in the buffer.
|
|
131
|
-
* @returns The removed element or undefined if the buffer is empty.
|
|
132
|
-
*/
|
|
133
85
|
pop() {
|
|
134
86
|
return this.typedArray[--this.usedElemNum];
|
|
135
87
|
}
|
|
136
|
-
/**
|
|
137
|
-
* Returns the last element pushed to the buffer without removing it.
|
|
138
|
-
* @returns The last element.
|
|
139
|
-
*/
|
|
140
88
|
top() {
|
|
141
89
|
return this.typedArray[this.usedElemNum - 1];
|
|
142
90
|
}
|
|
143
|
-
/**
|
|
144
|
-
* Gets the value of the element at the specified index.
|
|
145
|
-
* @param index - The index of the element to retrieve.
|
|
146
|
-
* @returns The requested element.
|
|
147
|
-
*/
|
|
148
91
|
get(t) {
|
|
149
92
|
return this.typedArray[t];
|
|
150
93
|
}
|
|
151
|
-
/**
|
|
152
|
-
* Returns a constrained view of the primary typed array up to the specified range.
|
|
153
|
-
* If `end` is omitted, returns the whole reallocated buffer slice.
|
|
154
|
-
* @param begin - The starting index (inclusive). Defaults to 0.
|
|
155
|
-
* @param end - The ending index (exclusive). Optional.
|
|
156
|
-
* @returns A subarray corresponding to the specified range.
|
|
157
|
-
*/
|
|
158
94
|
getArray(t = 0, e) {
|
|
159
95
|
return e === void 0 ? this.typedArray : this.typedArray.subarray(t, e);
|
|
160
96
|
}
|
|
161
|
-
/**
|
|
162
|
-
* The number of elements currently stored in the buffer.
|
|
163
|
-
*/
|
|
164
97
|
get length() {
|
|
165
98
|
return this.usedElemNum;
|
|
166
99
|
}
|
|
167
|
-
/**
|
|
168
|
-
* Resets the buffer's used element count, effectively emptying it.
|
|
169
|
-
* Same behavior as `clear`.
|
|
170
|
-
*/
|
|
171
|
-
reset() {
|
|
172
|
-
this.usedElemNum = 0;
|
|
173
|
-
}
|
|
174
100
|
}
|
|
175
|
-
class it extends
|
|
176
|
-
/** The actual WebGLBuffer object maintained by this instance. */
|
|
101
|
+
class it extends A {
|
|
177
102
|
buffer;
|
|
178
|
-
/** The related WebGL rendering context. */
|
|
179
103
|
gl;
|
|
180
|
-
/** Signifies whether the buffer has been updated and requires resyncing to the GPU. */
|
|
181
104
|
dirty = !0;
|
|
182
|
-
/** The WebGL buffer type, e.g., gl.ARRAY_BUFFER. */
|
|
183
105
|
type;
|
|
184
|
-
/** Size of the allocated buffer block on the GPU side, bounded in elements count. */
|
|
185
106
|
webglBufferSize = 0;
|
|
186
|
-
/** Usage hint for WebGL, e.g., gl.DYNAMIC_DRAW. */
|
|
187
107
|
usage;
|
|
188
|
-
/**
|
|
189
|
-
* Initializes a new WebGL dynamic buffer.
|
|
190
|
-
* @param gl - The active WebGL rendering context state.
|
|
191
|
-
* @param arrayType - Type of the underlying data elements to bind.
|
|
192
|
-
* @param type - Determines the type of WebGLBuffer (defaults to gl.ARRAY_BUFFER).
|
|
193
|
-
* @param usage - Determines the data usage pattern (defaults to gl.DYNAMIC_DRAW).
|
|
194
|
-
*/
|
|
195
108
|
constructor(t, e, r = t.ARRAY_BUFFER, i = t.DYNAMIC_DRAW) {
|
|
196
109
|
super(e), this.gl = t, this.buffer = t.createBuffer(), this.type = r, this.usage = i;
|
|
197
110
|
}
|
|
198
|
-
/**
|
|
199
|
-
* Flags the buffer as dirty, marking it for future data synchronization.
|
|
200
|
-
*/
|
|
201
111
|
makeDirty() {
|
|
202
112
|
this.dirty = !0;
|
|
203
113
|
}
|
|
204
|
-
/**
|
|
205
|
-
* Clears CPU side data usage and marks buffer as synced to stop needless updates.
|
|
206
|
-
*/
|
|
207
114
|
clear() {
|
|
208
115
|
super.clear(), this.dirty = !1;
|
|
209
116
|
}
|
|
210
|
-
/**
|
|
211
|
-
* Binds this buffer object tracking it as the current bound buffer to the GPU.
|
|
212
|
-
*/
|
|
213
117
|
bindBuffer() {
|
|
214
118
|
this.gl.bindBuffer(this.type, this.buffer);
|
|
215
119
|
}
|
|
216
|
-
/**
|
|
217
|
-
* Uploads the local buffer data to the GPU memory synchronously.
|
|
218
|
-
*/
|
|
219
120
|
bufferData() {
|
|
220
121
|
if (this.dirty) {
|
|
221
122
|
const t = this.gl;
|
|
@@ -233,75 +134,36 @@ class x {
|
|
|
233
134
|
static clampByte(t) {
|
|
234
135
|
return t <= 0 ? 0 : t >= 255 ? 255 : Math.round(t);
|
|
235
136
|
}
|
|
236
|
-
/**
|
|
237
|
-
* Creates an instance of Color.
|
|
238
|
-
* @param r - The red component (0-255).
|
|
239
|
-
* @param g - The green component (0-255).
|
|
240
|
-
* @param b - The blue component (0-255).
|
|
241
|
-
* @param a - The alpha component (0-255).
|
|
242
|
-
*/
|
|
243
137
|
constructor(t, e, r, i = 255) {
|
|
244
138
|
this._r = t, this._g = e, this._b = r, this._a = i, this.updateUint();
|
|
245
139
|
}
|
|
246
140
|
setClearColor(t) {
|
|
247
141
|
t.clearColor(this.r / 255, this.g / 255, this.b / 255, this.a / 255);
|
|
248
142
|
}
|
|
249
|
-
/**
|
|
250
|
-
* Gets the red component.
|
|
251
|
-
*/
|
|
252
143
|
get r() {
|
|
253
144
|
return this._r;
|
|
254
145
|
}
|
|
255
|
-
/**
|
|
256
|
-
* Sets the red component and updates the uint32 representation.
|
|
257
|
-
* @param value - The new red component (0-255).
|
|
258
|
-
*/
|
|
259
146
|
set r(t) {
|
|
260
147
|
this._r = t, this.updateUint();
|
|
261
148
|
}
|
|
262
|
-
/**
|
|
263
|
-
* Gets the green component.
|
|
264
|
-
*/
|
|
265
149
|
get g() {
|
|
266
150
|
return this._g;
|
|
267
151
|
}
|
|
268
|
-
/**
|
|
269
|
-
* Sets the green component and updates the uint32 representation.
|
|
270
|
-
* @param value - The new green component (0-255).
|
|
271
|
-
*/
|
|
272
152
|
set g(t) {
|
|
273
153
|
this._g = t, this.updateUint();
|
|
274
154
|
}
|
|
275
|
-
/**
|
|
276
|
-
* Gets the blue component.
|
|
277
|
-
*/
|
|
278
155
|
get b() {
|
|
279
156
|
return this._b;
|
|
280
157
|
}
|
|
281
|
-
/**
|
|
282
|
-
* Sets the blue component and updates the uint32 representation.
|
|
283
|
-
* @param value - The new blue component (0-255).
|
|
284
|
-
*/
|
|
285
158
|
set b(t) {
|
|
286
159
|
this._b = t, this.updateUint();
|
|
287
160
|
}
|
|
288
|
-
/**
|
|
289
|
-
* Gets the alpha component.
|
|
290
|
-
*/
|
|
291
161
|
get a() {
|
|
292
162
|
return this._a;
|
|
293
163
|
}
|
|
294
|
-
/**
|
|
295
|
-
* Sets the alpha component and updates the uint32 representation.
|
|
296
|
-
* @param value - The new alpha component (0-255).
|
|
297
|
-
*/
|
|
298
164
|
set a(t) {
|
|
299
165
|
this._a = t, this.updateUint();
|
|
300
166
|
}
|
|
301
|
-
/**
|
|
302
|
-
* Updates the uint32 representation of the color.
|
|
303
|
-
* @private
|
|
304
|
-
*/
|
|
305
167
|
updateUint() {
|
|
306
168
|
this.uint32 = (this._a << 24 | this._b << 16 | this._g << 8 | this._r) >>> 0;
|
|
307
169
|
const t = x.clampByte(this._a), e = x.clampByte(this._r * t / 255), r = x.clampByte(this._g * t / 255), i = x.clampByte(this._b * t / 255);
|
|
@@ -310,71 +172,28 @@ class x {
|
|
|
310
172
|
reset() {
|
|
311
173
|
this._r = 0, this._g = 0, this._b = 0, this._a = 255, this.updateUint();
|
|
312
174
|
}
|
|
313
|
-
/**
|
|
314
|
-
* Sets the RGBA values of the color and updates the uint32 representation.
|
|
315
|
-
* @param r - The red component (0-255).
|
|
316
|
-
* @param g - The green component (0-255).
|
|
317
|
-
* @param b - The blue component (0-255).
|
|
318
|
-
* @param a - The alpha component (0-255).
|
|
319
|
-
*/
|
|
320
175
|
setRGBA(t, e, r, i) {
|
|
321
|
-
this.
|
|
176
|
+
this._r = t, this._g = e, this._b = r, this._a = i, this.updateUint();
|
|
322
177
|
}
|
|
323
178
|
setHSL(t, e, r) {
|
|
324
179
|
t = (t % 360 + 360) % 360, e = Math.max(0, Math.min(100, e)) / 100, r = Math.max(0, Math.min(100, r)) / 100;
|
|
325
180
|
const i = (1 - Math.abs(2 * r - 1)) * e, s = i * (1 - Math.abs(t / 60 % 2 - 1)), a = r - i / 2;
|
|
326
|
-
let
|
|
327
|
-
return t < 60 ? [
|
|
181
|
+
let h = 0, o = 0, c = 0;
|
|
182
|
+
return t < 60 ? [h, o, c] = [i, s, 0] : t < 120 ? [h, o, c] = [s, i, 0] : t < 180 ? [h, o, c] = [0, i, s] : t < 240 ? [h, o, c] = [0, s, i] : t < 300 ? [h, o, c] = [s, 0, i] : [h, o, c] = [i, 0, s], this.setRGBA((h + a) * 255, (o + a) * 255, (c + a) * 255, 255), this;
|
|
328
183
|
}
|
|
329
|
-
toHex() {
|
|
330
|
-
const t = (e) => Math.max(0, Math.min(255, Math.round(e))).toString(16).padStart(2, "0");
|
|
331
|
-
return `#${t(this._r)}${t(this._g)}${t(this._b)}${t(this._a)}`;
|
|
332
|
-
}
|
|
333
|
-
/**
|
|
334
|
-
* Copies the RGBA values from another color.
|
|
335
|
-
* @param color - The color to copy from.
|
|
336
|
-
*/
|
|
337
184
|
copy(t) {
|
|
338
185
|
this.setRGBA(t.r, t.g, t.b, t.a);
|
|
339
186
|
}
|
|
340
|
-
/**
|
|
341
|
-
* Clone the current color
|
|
342
|
-
* @returns A new `Color` instance with the same RGBA values.
|
|
343
|
-
*/
|
|
344
187
|
clone() {
|
|
345
188
|
return new x(this._r, this._g, this._b, this._a);
|
|
346
189
|
}
|
|
347
|
-
/**
|
|
348
|
-
* Converts the color to a hexadecimal string representation (e.g., '#RRGGBBAA').
|
|
349
|
-
* @param includeAlpha - Whether to include the alpha channel in the hex string.
|
|
350
|
-
* @returns The hexadecimal string representation of the color.
|
|
351
|
-
*/
|
|
352
190
|
toHexString(t = !0) {
|
|
353
191
|
const e = this.r.toString(16).padStart(2, "0"), r = this.g.toString(16).padStart(2, "0"), i = this.b.toString(16).padStart(2, "0"), s = this.a.toString(16).padStart(2, "0");
|
|
354
192
|
return `#${e}${r}${i}${t ? s : ""}`;
|
|
355
193
|
}
|
|
356
|
-
|
|
357
|
-
* Checks if the current color is equal to another color.
|
|
358
|
-
* @param color - The color to compare with.
|
|
359
|
-
* @returns True if the colors are equal, otherwise false.
|
|
360
|
-
*/
|
|
361
|
-
equal(t) {
|
|
194
|
+
equals(t) {
|
|
362
195
|
return t.r === this.r && t.g === this.g && t.b === this.b && t.a === this.a;
|
|
363
196
|
}
|
|
364
|
-
equals(t) {
|
|
365
|
-
return this.equal(t);
|
|
366
|
-
}
|
|
367
|
-
/**
|
|
368
|
-
* Creates a Color instance from normalized float components (0–1 range).
|
|
369
|
-
* Use this instead of `new Color()` when working with shader-style 0.0–1.0 values.
|
|
370
|
-
* @param r - Red channel (0.0–1.0)
|
|
371
|
-
* @param g - Green channel (0.0–1.0)
|
|
372
|
-
* @param b - Blue channel (0.0–1.0)
|
|
373
|
-
* @param a - Alpha channel (0.0–1.0), defaults to 1.0
|
|
374
|
-
* @returns A new Color instance with components scaled to 0–255.
|
|
375
|
-
* @example
|
|
376
|
-
* Color.fromNorm(0.9, 0.87, 0.55, 0.1) // moon glow
|
|
377
|
-
*/
|
|
378
197
|
static FromHSL(t, e, r) {
|
|
379
198
|
return new x(0, 0, 0).setHSL(t, e, r);
|
|
380
199
|
}
|
|
@@ -389,29 +208,16 @@ class x {
|
|
|
389
208
|
Math.round(i * 255)
|
|
390
209
|
);
|
|
391
210
|
}
|
|
392
|
-
static clampColorByte(t) {
|
|
393
|
-
return t <= 0 ? 0 : t >= 255 ? 255 : Math.round(t);
|
|
394
|
-
}
|
|
395
211
|
static packColor(t, e, r, i, s) {
|
|
396
|
-
const a = x.
|
|
397
|
-
return (a << 24 | u << 16 | c << 8 |
|
|
398
|
-
}
|
|
399
|
-
/**
|
|
400
|
-
* Creates a Color instance from a hexadecimal color string.
|
|
401
|
-
* @param hexString - The hexadecimal color string, e.g., '#RRGGBB' or '#RRGGBBAA'.
|
|
402
|
-
* @returns A new Color instance.
|
|
403
|
-
*/
|
|
212
|
+
const a = x.clampByte(i), h = s ? a / 255 : 1, o = x.clampByte(t * h), c = x.clampByte(e * h), u = x.clampByte(r * h);
|
|
213
|
+
return (a << 24 | u << 16 | c << 8 | o) >>> 0;
|
|
214
|
+
}
|
|
404
215
|
static fromHex(t) {
|
|
405
216
|
t.startsWith("#") && (t = t.slice(1));
|
|
406
217
|
const e = parseInt(t.slice(0, 2), 16), r = parseInt(t.slice(2, 4), 16), i = parseInt(t.slice(4, 6), 16);
|
|
407
218
|
let s = 255;
|
|
408
219
|
return t.length >= 8 && (s = parseInt(t.slice(6, 8), 16)), new x(e, r, i, s);
|
|
409
220
|
}
|
|
410
|
-
/**
|
|
411
|
-
* Adds the components of another color to this color, clamping the result to 255.
|
|
412
|
-
* @param color - The color to add.
|
|
413
|
-
* @returns A new Color instance with the result of the addition.
|
|
414
|
-
*/
|
|
415
221
|
add(t) {
|
|
416
222
|
return new x(
|
|
417
223
|
Math.min(this.r + t.r, 255),
|
|
@@ -420,11 +226,6 @@ class x {
|
|
|
420
226
|
Math.min(this.a + t.a, 255)
|
|
421
227
|
);
|
|
422
228
|
}
|
|
423
|
-
/**
|
|
424
|
-
* Subtracts the components of another color from this color, clamping the result to 0.
|
|
425
|
-
* @param color - The color to subtract.
|
|
426
|
-
* @returns A new Color instance with the result of the subtraction.
|
|
427
|
-
*/
|
|
428
229
|
subtract(t) {
|
|
429
230
|
return new x(
|
|
430
231
|
this.r - t.r,
|
|
@@ -460,7 +261,7 @@ class x {
|
|
|
460
261
|
);
|
|
461
262
|
}
|
|
462
263
|
clamp() {
|
|
463
|
-
this.
|
|
264
|
+
this._r = Math.max(0, Math.min(255, this._r)), this._g = Math.max(0, Math.min(255, this._g)), this._b = Math.max(0, Math.min(255, this._b)), this._a = Math.max(0, Math.min(255, this._a)), this.updateUint();
|
|
464
265
|
}
|
|
465
266
|
static Red = new x(255, 0, 0, 255);
|
|
466
267
|
static Green = new x(0, 255, 0, 255);
|
|
@@ -477,549 +278,311 @@ class x {
|
|
|
477
278
|
static White = new x(255, 255, 255, 255);
|
|
478
279
|
static Black = new x(0, 0, 0, 255);
|
|
479
280
|
static Transparent = new x(0, 0, 0, 0);
|
|
480
|
-
static TRANSPARENT = new x(0, 0, 0, 0);
|
|
481
281
|
}
|
|
482
|
-
const
|
|
483
|
-
class
|
|
484
|
-
/** Total number of matrices currently allocated in the store. */
|
|
282
|
+
const T = 6;
|
|
283
|
+
class At {
|
|
485
284
|
matrixCount = 0;
|
|
486
|
-
/** The dynamic buffer used to hold matrix data. */
|
|
487
285
|
buffer;
|
|
488
|
-
/** The raw floating-point data of all matrices. */
|
|
489
286
|
data;
|
|
490
287
|
temporary = -1;
|
|
491
|
-
/**
|
|
492
|
-
* Creates a new MatrixStore.
|
|
493
|
-
* @param capacity - The initial capacity of the matrix store (default is 10).
|
|
494
|
-
*/
|
|
495
288
|
constructor(t = 10) {
|
|
496
|
-
this.buffer = new
|
|
289
|
+
this.buffer = new A(S.Float32), this.buffer.resize(t * T), this.data = this.buffer.getArray(), this.reset();
|
|
497
290
|
}
|
|
498
|
-
/**
|
|
499
|
-
* Allocates a new matrix and initializes it to the identity matrix.
|
|
500
|
-
* @returns The index of the newly allocated matrix.
|
|
501
|
-
*/
|
|
502
291
|
alloc() {
|
|
503
292
|
const t = this.allocDirty();
|
|
504
293
|
return this.identity(t), t;
|
|
505
294
|
}
|
|
506
|
-
/**
|
|
507
|
-
* Allocates a new matrix without initializing its elements.
|
|
508
|
-
* @returns The index of the newly allocated matrix.
|
|
509
|
-
*/
|
|
510
295
|
allocDirty() {
|
|
511
|
-
return this.buffer.resize(
|
|
296
|
+
return this.buffer.resize(T) && (this.data = this.buffer.getArray()), this.buffer.usedElemNum += T, this.matrixCount++;
|
|
512
297
|
}
|
|
513
|
-
/**
|
|
514
|
-
* Resets the store, clearing all allocated matrices.
|
|
515
|
-
*/
|
|
516
298
|
reset() {
|
|
517
299
|
this.matrixCount = 0, this.buffer.usedElemNum = 0, this.temporary = this.alloc();
|
|
518
300
|
}
|
|
519
|
-
/**
|
|
520
|
-
* Sets the matrix at the given index to the identity matrix.
|
|
521
|
-
* @param index - The index of the matrix to modify.
|
|
522
|
-
*/
|
|
523
301
|
identity(t) {
|
|
524
|
-
const e = t *
|
|
302
|
+
const e = t * T, r = this.data;
|
|
525
303
|
r[e] = 1, r[e + 1] = 0, r[e + 2] = 0, r[e + 3] = 1, r[e + 4] = 0, r[e + 5] = 0;
|
|
526
304
|
}
|
|
527
|
-
/**
|
|
528
|
-
* Translates the matrix at the given index by x and y.
|
|
529
|
-
* @param index - The index of the matrix to modify.
|
|
530
|
-
* @param x - The x translation.
|
|
531
|
-
* @param y - The y translation.
|
|
532
|
-
*/
|
|
533
305
|
translate(t, e, r) {
|
|
534
|
-
const i = t *
|
|
306
|
+
const i = t * T, s = this.data;
|
|
535
307
|
s[i + 4] = s[i] * e + s[i + 2] * r + s[i + 4], s[i + 5] = s[i + 1] * e + s[i + 3] * r + s[i + 5];
|
|
536
308
|
}
|
|
537
|
-
/**
|
|
538
|
-
* Scales the matrix at the given index by scaleX and scaleY.
|
|
539
|
-
* @param index - The index of the matrix to modify.
|
|
540
|
-
* @param scaleX - The scale factor along the x-axis.
|
|
541
|
-
* @param scaleY - The scale factor along the y-axis.
|
|
542
|
-
*/
|
|
543
309
|
scale(t, e, r) {
|
|
544
|
-
const i = t *
|
|
310
|
+
const i = t * T, s = this.data;
|
|
545
311
|
s[i] *= e, s[i + 1] *= e, s[i + 2] *= r, s[i + 3] *= r;
|
|
546
312
|
}
|
|
547
|
-
/**
|
|
548
|
-
* Rotates the matrix at the given index by the specified radians.
|
|
549
|
-
* @param index - The index of the matrix to modify.
|
|
550
|
-
* @param radians - The rotation angle in radians.
|
|
551
|
-
*/
|
|
552
313
|
rotate(t, e) {
|
|
553
|
-
const r = t *
|
|
554
|
-
i[r] =
|
|
555
|
-
}
|
|
556
|
-
/**
|
|
557
|
-
* Rotates the matrix at the given index around a local offset point (pivot).
|
|
558
|
-
*
|
|
559
|
-
* This is equivalent to:
|
|
560
|
-
* 1. Translating by `(offsetX, offsetY)` to move the pivot to the origin.
|
|
561
|
-
* 2. Rotating by `radians`.
|
|
562
|
-
* 3. Translating back by `(-offsetX, -offsetY)`.
|
|
563
|
-
*
|
|
564
|
-
* Useful for rotating a sprite around a point other than its own origin,
|
|
565
|
-
* e.g. a character's limb rotating around its joint.
|
|
566
|
-
*
|
|
567
|
-
* @param index - The index of the matrix to modify.
|
|
568
|
-
* @param radians - The rotation angle in radians.
|
|
569
|
-
* @param offsetX - The x component of the pivot point in local space.
|
|
570
|
-
* @param offsetY - The y component of the pivot point in local space.
|
|
571
|
-
*/
|
|
314
|
+
const r = t * T, i = this.data, s = Math.cos(e), a = Math.sin(e), h = i[r], o = i[r + 1], c = i[r + 2], u = i[r + 3];
|
|
315
|
+
i[r] = h * s + c * a, i[r + 1] = o * s + u * a, i[r + 2] = h * -a + c * s, i[r + 3] = o * -a + u * s;
|
|
316
|
+
}
|
|
572
317
|
rotateWithOffset(t, e, r, i) {
|
|
573
318
|
this.translate(t, r, i), this.rotate(t, e), this.translate(t, -r, -i);
|
|
574
319
|
}
|
|
575
|
-
/**
|
|
576
|
-
* Copies the elements from the source matrix to the destination matrix.
|
|
577
|
-
* @param dst - The index of the destination matrix.
|
|
578
|
-
* @param src - The index of the source matrix.
|
|
579
|
-
*/
|
|
580
320
|
copy(t, e) {
|
|
581
|
-
const r = t *
|
|
321
|
+
const r = t * T, i = e * T, s = this.data;
|
|
582
322
|
s[r] = s[i], s[r + 1] = s[i + 1], s[r + 2] = s[i + 2], s[r + 3] = s[i + 3], s[r + 4] = s[i + 4], s[r + 5] = s[i + 5];
|
|
583
323
|
}
|
|
584
|
-
/**
|
|
585
|
-
* Multiplies the destination matrix by the source matrix and stores the result in the destination.
|
|
586
|
-
* @param dst - The index of the destination matrix.
|
|
587
|
-
* @param src - The index of the source matrix.
|
|
588
|
-
*/
|
|
589
324
|
multiply(t, e) {
|
|
590
325
|
this.multiplyOut(t, t, e);
|
|
591
326
|
}
|
|
592
|
-
/**
|
|
593
|
-
* Multiplies matrix A by matrix B and stores the result in the output matrix.
|
|
594
|
-
* @param out - The index of the output matrix.
|
|
595
|
-
* @param aIdx - The index of matrix A.
|
|
596
|
-
* @param bIdx - The index of matrix B.
|
|
597
|
-
*/
|
|
598
327
|
multiplyOut(t, e, r) {
|
|
599
|
-
const i = t *
|
|
600
|
-
|
|
328
|
+
const i = t * T, s = e * T, a = r * T, h = this.data, o = h[s], c = h[s + 1], u = h[s + 2], l = h[s + 3], d = h[s + 4], f = h[s + 5], m = h[a], g = h[a + 1], v = h[a + 2], y = h[a + 3], w = h[a + 4], M = h[a + 5];
|
|
329
|
+
h[i] = o * m + u * g, h[i + 1] = c * m + l * g, h[i + 2] = o * v + u * y, h[i + 3] = c * v + l * y, h[i + 4] = o * w + u * M + d, h[i + 5] = c * w + l * M + f;
|
|
601
330
|
}
|
|
602
|
-
/**
|
|
603
|
-
* Inverts the matrix at the given index. If the matrix is not invertible, it defaults to the identity matrix.
|
|
604
|
-
* @param index - The index of the matrix to invert.
|
|
605
|
-
*/
|
|
606
331
|
invert(t) {
|
|
607
|
-
const e = t *
|
|
608
|
-
let u = i *
|
|
332
|
+
const e = t * T, r = this.data, i = r[e], s = r[e + 1], a = r[e + 2], h = r[e + 3], o = r[e + 4], c = r[e + 5];
|
|
333
|
+
let u = i * h - s * a;
|
|
609
334
|
if (!u) {
|
|
610
335
|
this.identity(t);
|
|
611
336
|
return;
|
|
612
337
|
}
|
|
613
|
-
u = 1 / u, r[e] =
|
|
614
|
-
}
|
|
615
|
-
/**
|
|
616
|
-
* Transforms a point by the matrix at the given index.
|
|
617
|
-
* @param index - The index of the transformation matrix.
|
|
618
|
-
* @param x - The x coordinate of the point.
|
|
619
|
-
* @param y - The y coordinate of the point.
|
|
620
|
-
* @returns The transformed point {x, y}.
|
|
621
|
-
*/
|
|
338
|
+
u = 1 / u, r[e] = h * u, r[e + 1] = -s * u, r[e + 2] = -a * u, r[e + 3] = i * u, r[e + 4] = (a * c - h * o) * u, r[e + 5] = (s * o - i * c) * u;
|
|
339
|
+
}
|
|
622
340
|
transformPoint(t, e, r) {
|
|
623
|
-
const i = t *
|
|
341
|
+
const i = t * T, s = this.data;
|
|
624
342
|
return {
|
|
625
343
|
x: e * s[i] + r * s[i + 2] + s[i + 4],
|
|
626
344
|
y: e * s[i + 1] + r * s[i + 3] + s[i + 5]
|
|
627
345
|
};
|
|
628
346
|
}
|
|
629
|
-
/**
|
|
630
|
-
* Transforms a point from world coordinates to local coordinates using the matrix at the specified index.
|
|
631
|
-
* Useful for hit testing against objects placed in world space.
|
|
632
|
-
* @param index - The index of the world transformation matrix.
|
|
633
|
-
* @param x - World x coordinate.
|
|
634
|
-
* @param y - World y coordinate.
|
|
635
|
-
* @returns The transformed point in local coordinates.
|
|
636
|
-
*/
|
|
637
347
|
worldToLocal(t, e, r) {
|
|
638
348
|
const i = this.allocDirty();
|
|
639
349
|
this.copy(i, t), this.invert(i);
|
|
640
350
|
const s = this.transformPoint(i, e, r);
|
|
641
|
-
return this.matrixCount--, this.buffer.usedElemNum -=
|
|
642
|
-
}
|
|
643
|
-
/**
|
|
644
|
-
* Transforms a point from local coordinates to world coordinates.
|
|
645
|
-
* @param index - The index of the local transformation matrix.
|
|
646
|
-
* @param x - Local x coordinate.
|
|
647
|
-
* @param y - Local y coordinate.
|
|
648
|
-
* @returns The transformed point in world coordinates.
|
|
649
|
-
*/
|
|
351
|
+
return this.matrixCount--, this.buffer.usedElemNum -= T, s;
|
|
352
|
+
}
|
|
650
353
|
localToWorld(t, e, r) {
|
|
651
354
|
return this.transformPoint(t, e, r);
|
|
652
355
|
}
|
|
653
|
-
/**
|
|
654
|
-
* Extracts the global position (translation) from the matrix at the given index.
|
|
655
|
-
* @param index - The index of the matrix.
|
|
656
|
-
* @returns An object containing `x` and `y` global coordinates.
|
|
657
|
-
*/
|
|
658
356
|
getPosition(t) {
|
|
659
|
-
const e = t *
|
|
357
|
+
const e = t * T, r = this.data;
|
|
660
358
|
return { x: r[e + 4], y: r[e + 5] };
|
|
661
359
|
}
|
|
662
|
-
/**
|
|
663
|
-
* Extracts the global scale from the matrix at the given index.
|
|
664
|
-
* @param index - The index of the matrix.
|
|
665
|
-
* @returns An object containing `x` and `y` global scale factors.
|
|
666
|
-
*/
|
|
667
360
|
getScale(t) {
|
|
668
|
-
const e = t *
|
|
361
|
+
const e = t * T, r = this.data, i = Math.sqrt(r[e] * r[e] + r[e + 1] * r[e + 1]), s = Math.sqrt(r[e + 2] * r[e + 2] + r[e + 3] * r[e + 3]);
|
|
669
362
|
return { x: i, y: s };
|
|
670
363
|
}
|
|
671
|
-
/**
|
|
672
|
-
* Extracts the global rotation (in radians) from the matrix at the given index.
|
|
673
|
-
* @param index - The index of the matrix.
|
|
674
|
-
* @returns The global rotation in radians.
|
|
675
|
-
*/
|
|
676
364
|
getRotation(t) {
|
|
677
|
-
const e = t *
|
|
365
|
+
const e = t * T, r = this.data;
|
|
678
366
|
return Math.atan2(r[e + 1], r[e]);
|
|
679
367
|
}
|
|
680
|
-
/**
|
|
681
|
-
* Converts the matrix at the given index to a CSS matrix string.
|
|
682
|
-
* @param index - The index of the matrix.
|
|
683
|
-
* @param scaleX - Extra scale applied to the a/c/tx components (e.g. to convert logic pixels to CSS pixels).
|
|
684
|
-
* @param scaleY - Extra scale applied to the b/d/ty components.
|
|
685
|
-
* @returns A CSS matrix string.
|
|
686
|
-
*/
|
|
687
368
|
toCSSMatrix(t, e = 1, r = 1) {
|
|
688
|
-
const i = t *
|
|
369
|
+
const i = t * T, s = this.data;
|
|
689
370
|
return `matrix(${s[i] * e}, ${s[i + 1] * r}, ${s[i + 2] * e}, ${s[i + 3] * r}, ${s[i + 4] * e}, ${s[i + 5] * r})`;
|
|
690
371
|
}
|
|
691
|
-
/**
|
|
692
|
-
* Retrieves a copy of the 6 elements [a, b, c, d, tx, ty] for the matrix at the specified index.
|
|
693
|
-
* Note: This uses `slice` to return a new Float32Array instance, ensuring the original data remains safely isolated.
|
|
694
|
-
*
|
|
695
|
-
* @param index - The index of the matrix.
|
|
696
|
-
* @returns A new Float32Array containing the 6 elements of the matrix.
|
|
697
|
-
*/
|
|
698
372
|
getMatrix(t) {
|
|
699
|
-
const e = t *
|
|
700
|
-
return this.data.slice(e, e +
|
|
701
|
-
}
|
|
702
|
-
/**
|
|
703
|
-
* Retrieves a direct reference (view) to the 6 elements [a, b, c, d, tx, ty] for the matrix at the specified index.
|
|
704
|
-
* Note: This uses `subarray`. Any modifications made to the returned array will directly affect the underlying MatrixStore data.
|
|
705
|
-
*
|
|
706
|
-
* @param index - The index of the matrix.
|
|
707
|
-
* @returns A Float32Array view pointing directly to the matrix's data in memory.
|
|
708
|
-
*/
|
|
373
|
+
const e = t * T;
|
|
374
|
+
return this.data.slice(e, e + T);
|
|
375
|
+
}
|
|
709
376
|
getMatrixRef(t) {
|
|
710
|
-
const e = t *
|
|
711
|
-
return this.data.subarray(e, e +
|
|
712
|
-
}
|
|
713
|
-
/**
|
|
714
|
-
* Overwrites the matrix at the specified index with the provided 6 elements [a, b, c, d, tx, ty].
|
|
715
|
-
*
|
|
716
|
-
* @param index - The index of the matrix to modify.
|
|
717
|
-
* @param f - An array (Float32Array or standard number array) containing the 6 new elements.
|
|
718
|
-
*/
|
|
377
|
+
const e = t * T;
|
|
378
|
+
return this.data.subarray(e, e + T);
|
|
379
|
+
}
|
|
719
380
|
setMatrix(t, e) {
|
|
720
|
-
const r = t *
|
|
381
|
+
const r = t * T, i = this.data;
|
|
721
382
|
i[r] = e[0], i[r + 1] = e[1], i[r + 2] = e[2], i[r + 3] = e[3], i[r + 4] = e[4], i[r + 5] = e[5];
|
|
722
383
|
}
|
|
723
|
-
multiplyAffineInPlace(t, e, r, i, s, a,
|
|
724
|
-
const
|
|
725
|
-
c[
|
|
384
|
+
multiplyAffineInPlace(t, e, r, i, s, a, h) {
|
|
385
|
+
const o = t * 6, c = this.data, u = c[o], l = c[o + 1], d = c[o + 2], f = c[o + 3], m = c[o + 4], g = c[o + 5];
|
|
386
|
+
c[o] = u * e + d * r, c[o + 1] = l * e + f * r, c[o + 2] = u * i + d * s, c[o + 3] = l * i + f * s, c[o + 4] = u * a + d * h + m, c[o + 5] = l * a + f * h + g;
|
|
726
387
|
}
|
|
727
|
-
multiplyAffine(t, e, r, i, s, a,
|
|
728
|
-
const c = t * 6, u = e * 6, l = this.data, d = l[c], f = l[c + 1], m = l[c + 2],
|
|
729
|
-
l[u] = d * r + m * i, l[u + 1] = f * r +
|
|
388
|
+
multiplyAffine(t, e, r, i, s, a, h, o) {
|
|
389
|
+
const c = t * 6, u = e * 6, l = this.data, d = l[c], f = l[c + 1], m = l[c + 2], g = l[c + 3], v = l[c + 4], y = l[c + 5];
|
|
390
|
+
l[u] = d * r + m * i, l[u + 1] = f * r + g * i, l[u + 2] = d * s + m * a, l[u + 3] = f * s + g * a, l[u + 4] = d * h + m * o + v, l[u + 5] = f * h + g * o + y;
|
|
730
391
|
}
|
|
731
392
|
}
|
|
732
|
-
class
|
|
733
|
-
|
|
734
|
-
matrix = new Ut();
|
|
735
|
-
/** The current step or depth in the transformation hierarchy. */
|
|
393
|
+
class bt {
|
|
394
|
+
matrix = new At();
|
|
736
395
|
step = 0;
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
/** Records the parent world matrix for each step (used by updateMatrixSubtree). */
|
|
744
|
-
stepParentM = new _(b.Uint32);
|
|
745
|
-
/** Buffer used during hierarchy traversal updates. */
|
|
746
|
-
parentStack = new _(b.Uint32);
|
|
747
|
-
/** The index of the current local matrix in the matrix store. */
|
|
396
|
+
stack = new A(S.Uint32);
|
|
397
|
+
stepWorldM = new A(S.Uint32);
|
|
398
|
+
stepAction = new A(S.Uint32);
|
|
399
|
+
stepParentM = new A(S.Uint32);
|
|
400
|
+
stepClose = new A(S.Uint32);
|
|
401
|
+
stepStack = new A(S.Uint32);
|
|
748
402
|
curLocalM = -1;
|
|
749
|
-
/** The index of the current world matrix in the matrix store. */
|
|
750
403
|
curWorldM = -1;
|
|
751
404
|
rapid;
|
|
752
|
-
/**
|
|
753
|
-
* Creates a new MatrixStack and initializes its state.
|
|
754
|
-
*/
|
|
755
405
|
constructor(t) {
|
|
756
406
|
this.reset(), this.rapid = t;
|
|
757
407
|
}
|
|
758
|
-
/**
|
|
759
|
-
* Saves the current matrix state and pushes it onto the stack.
|
|
760
|
-
* Equivalent to context.save().
|
|
761
|
-
* @returns The current step counter before saving.
|
|
762
|
-
*/
|
|
763
408
|
save() {
|
|
764
409
|
this.stack.push(this.curWorldM);
|
|
765
410
|
const t = this.curWorldM;
|
|
766
|
-
return this.curLocalM = this.matrix.alloc(), this.curWorldM = this.matrix.allocDirty(), this.stepWorldM.push(this.curWorldM), this.stepParentM.push(t), this.stepAction.push(1), this.matrix.copy(this.curWorldM, t), { world: this.curWorldM, local: this.curLocalM, step: this.step++ };
|
|
411
|
+
return this.curLocalM = this.matrix.alloc(), this.curWorldM = this.matrix.allocDirty(), this.stepWorldM.push(this.curWorldM), this.stepParentM.push(t), this.stepAction.push(1), this.stepClose.push(0), this.stepStack.push(this.step), this.matrix.copy(this.curWorldM, t), { world: this.curWorldM, local: this.curLocalM, step: this.step++ };
|
|
767
412
|
}
|
|
768
|
-
/**
|
|
769
|
-
* Restores the matrix state from the top of the stack.
|
|
770
|
-
* Equivalent to context.restore().
|
|
771
|
-
*/
|
|
772
413
|
restore() {
|
|
773
|
-
this.stack.length
|
|
414
|
+
this.stack.length == 0 || this.stepStack.length == 0 || (this.curWorldM = this.stack.pop(), this.curLocalM = this.curWorldM - 1, this.stepParentM.push(this.stack.get(this.stack.length - 1)), this.stepWorldM.push(this.curWorldM), this.stepAction.push(0), this.stepClose.push(0), this.stepClose.typedArray[this.stepStack.pop()] = this.step, this.step++);
|
|
415
|
+
}
|
|
416
|
+
restoreAll() {
|
|
417
|
+
for (; this.stack.length > 0 && this.stepStack.length > 0; )
|
|
418
|
+
this.restore();
|
|
419
|
+
}
|
|
420
|
+
getStep(t) {
|
|
421
|
+
return typeof t == "number" ? t : t.step;
|
|
422
|
+
}
|
|
423
|
+
walkSubtree(t, e, r = 1 / 0) {
|
|
424
|
+
let i = 0, s = t;
|
|
425
|
+
for (; s < this.step; ) {
|
|
426
|
+
const a = this.stepAction.get(s);
|
|
427
|
+
if (a === 1) {
|
|
428
|
+
if (i++, i > r) {
|
|
429
|
+
const h = this.stepClose.get(s);
|
|
430
|
+
if (h > s) {
|
|
431
|
+
s = h + 1, i--;
|
|
432
|
+
continue;
|
|
433
|
+
}
|
|
434
|
+
}
|
|
435
|
+
} else
|
|
436
|
+
i--;
|
|
437
|
+
if (e(s, a, i) === !1 || a === 0 && i === 0) return;
|
|
438
|
+
s++;
|
|
439
|
+
}
|
|
440
|
+
}
|
|
441
|
+
getParent(t) {
|
|
442
|
+
const e = this.getStep(t);
|
|
443
|
+
return this.stepParentM.get(e);
|
|
444
|
+
}
|
|
445
|
+
getChildren(t) {
|
|
446
|
+
const e = this.getStep(t), r = this.stepClose.get(e), i = [];
|
|
447
|
+
let s = e + 1;
|
|
448
|
+
for (; s < r; )
|
|
449
|
+
this.stepAction.get(s) === 1 ? (i.push(s), s = this.stepClose.get(s) + 1) : s++;
|
|
450
|
+
return i;
|
|
774
451
|
}
|
|
775
|
-
/**
|
|
776
|
-
* Evaluates and updates matrices from the given step. Used primarily for deferred transformation.
|
|
777
|
-
* @param step - The initial step to update matrices from.
|
|
778
|
-
*/
|
|
779
452
|
updateMatrixSubtree(t) {
|
|
780
|
-
const e =
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
break;
|
|
788
|
-
i++;
|
|
789
|
-
}
|
|
453
|
+
const e = this.getStep(t);
|
|
454
|
+
this.walkSubtree(e, (r, i) => {
|
|
455
|
+
if (i === 1) {
|
|
456
|
+
const s = this.stepWorldM.get(r), a = s - 1, h = this.stepParentM.get(r);
|
|
457
|
+
this.matrix.multiplyOut(s, h, a);
|
|
458
|
+
}
|
|
459
|
+
});
|
|
790
460
|
}
|
|
791
|
-
/**
|
|
792
|
-
* Translates the current local and world matrices by x and y.
|
|
793
|
-
* @param x - Translation along the x-axis.
|
|
794
|
-
* @param y - Translation along the y-axis.
|
|
795
|
-
*/
|
|
796
461
|
translate(t, e) {
|
|
797
462
|
this.matrix.translate(this.curLocalM, t, e), this.matrix.translate(this.curWorldM, t, e);
|
|
798
463
|
}
|
|
799
|
-
/**
|
|
800
|
-
* Scales the current local and world matrices by scaleX and scaleY.
|
|
801
|
-
* @param scaleX - Scaling factor along the x-axis.
|
|
802
|
-
* @param scaleY - Scaling factor along the y-axis.
|
|
803
|
-
*/
|
|
804
464
|
scale(t, e = t) {
|
|
805
465
|
this.matrix.scale(this.curLocalM, t, e), this.matrix.scale(this.curWorldM, t, e);
|
|
806
466
|
}
|
|
807
|
-
/**
|
|
808
|
-
* Rotates the current local and world matrices by the given radians.
|
|
809
|
-
* @param radians - The rotation angle in radians.
|
|
810
|
-
*/
|
|
811
467
|
rotate(t) {
|
|
812
468
|
this.matrix.rotate(this.curLocalM, t), this.matrix.rotate(this.curWorldM, t);
|
|
813
469
|
}
|
|
814
|
-
/**
|
|
815
|
-
* Rotates the current local and world matrices around a pivot point
|
|
816
|
-
* that is offset from the matrix origin by `(offsetX, offsetY)`.
|
|
817
|
-
*
|
|
818
|
-
* This is a convenience wrapper around the common translate → rotate → translate-back
|
|
819
|
-
* pattern, avoiding manual coordinate juggling at the call site.
|
|
820
|
-
*
|
|
821
|
-
* @example
|
|
822
|
-
* ```ts
|
|
823
|
-
* // Rotate a 64×64 sprite around its centre
|
|
824
|
-
* stack.rotateWithOffset(angle, 32, 32);
|
|
825
|
-
* ```
|
|
826
|
-
*
|
|
827
|
-
* @param radians - The rotation angle in radians.
|
|
828
|
-
* @param offsetX - The x component of the pivot point in local space.
|
|
829
|
-
* @param offsetY - The y component of the pivot point in local space.
|
|
830
|
-
*/
|
|
831
470
|
rotateWithOffset(t, e, r) {
|
|
832
471
|
this.matrix.rotateWithOffset(this.curLocalM, t, e, r), this.matrix.rotateWithOffset(this.curWorldM, t, e, r);
|
|
833
472
|
}
|
|
834
|
-
/**
|
|
835
|
-
* Sets the current local and world matrices to the identity matrix.
|
|
836
|
-
*/
|
|
837
473
|
identity() {
|
|
838
474
|
this.matrix.identity(this.curLocalM), this.matrix.identity(this.curWorldM);
|
|
839
475
|
}
|
|
840
|
-
/**
|
|
841
|
-
* Resets the entire stack state context, clearing matrices and step actions.
|
|
842
|
-
*/
|
|
843
476
|
reset() {
|
|
844
|
-
this.matrix.reset(), this.stack.
|
|
845
|
-
}
|
|
846
|
-
/**
|
|
847
|
-
* Transforms a point from local coordinates to world coordinates.
|
|
848
|
-
* Uses the current world matrix to apply the transformation.
|
|
849
|
-
* @param x - Local x coordinate.
|
|
850
|
-
* @param y - Local y coordinate.
|
|
851
|
-
* @returns The transformed point in world coordinates.
|
|
852
|
-
*/
|
|
477
|
+
this.matrix.reset(), this.stack.clear(), this.stepAction.clear(), this.stepWorldM.clear(), this.stepParentM.clear(), this.stepClose.clear(), this.stepStack.clear(), this.step = 0, this.curLocalM = this.matrix.alloc(), this.curWorldM = this.matrix.alloc();
|
|
478
|
+
}
|
|
853
479
|
localToWorld(t, e) {
|
|
854
480
|
return this.matrix.localToWorld(this.curWorldM, t, e);
|
|
855
481
|
}
|
|
856
|
-
/**
|
|
857
|
-
* Transforms a point from world coordinates to local coordinates.
|
|
858
|
-
* Useful for hit testing against objects placed in world space.
|
|
859
|
-
* @param x - World x coordinate.
|
|
860
|
-
* @param y - World y coordinate.
|
|
861
|
-
* @returns The transformed point in local coordinates.
|
|
862
|
-
*/
|
|
863
482
|
worldToLocal(t, e) {
|
|
864
483
|
return this.matrix.worldToLocal(this.curWorldM, t, e);
|
|
865
484
|
}
|
|
866
|
-
/**
|
|
867
|
-
* Extracts the global position (translation) from the current world matrix.
|
|
868
|
-
* @returns An object containing `x` and `y` global coordinates.
|
|
869
|
-
*/
|
|
870
485
|
getGlobalPosition() {
|
|
871
486
|
return this.matrix.getPosition(this.curWorldM);
|
|
872
487
|
}
|
|
873
|
-
/**
|
|
874
|
-
* Extracts the global scale from the current world matrix.
|
|
875
|
-
* @returns An object containing `x` and `y` global scale factors.
|
|
876
|
-
*/
|
|
877
488
|
getGlobalScale() {
|
|
878
489
|
return this.matrix.getScale(this.curWorldM);
|
|
879
490
|
}
|
|
880
|
-
/**
|
|
881
|
-
* Extracts the global rotation (in radians) from the current world matrix.
|
|
882
|
-
* @returns The global rotation in radians.
|
|
883
|
-
*/
|
|
884
491
|
getGlobalRotation() {
|
|
885
492
|
return this.matrix.getRotation(this.curWorldM);
|
|
886
493
|
}
|
|
887
494
|
toCSSMatrix() {
|
|
888
495
|
return this.matrix.toCSSMatrix(this.curWorldM);
|
|
889
496
|
}
|
|
890
|
-
/**
|
|
891
|
-
* Returns the current world matrix as Float32Array [a, b, c, d, tx, ty].
|
|
892
|
-
*/
|
|
893
497
|
getTransform() {
|
|
894
|
-
const t = this.curWorldM *
|
|
895
|
-
return this.matrix.data.slice(t, t +
|
|
498
|
+
const t = this.curWorldM * T;
|
|
499
|
+
return this.matrix.data.slice(t, t + T);
|
|
896
500
|
}
|
|
897
|
-
/**
|
|
898
|
-
* Directly overwrites the current world matrix with the given 6-element 2D transform.
|
|
899
|
-
*/
|
|
900
501
|
setTransform(t) {
|
|
901
|
-
const e = this.curWorldM *
|
|
502
|
+
const e = this.curWorldM * T, r = this.matrix.data;
|
|
902
503
|
r[e] = t[0], r[e + 1] = t[1], r[e + 2] = t[2], r[e + 3] = t[3], r[e + 4] = t[4], r[e + 5] = t[5];
|
|
903
504
|
}
|
|
904
505
|
transformPoint(t, e) {
|
|
905
506
|
return this.matrix.transformPoint(this.curLocalM, t, e);
|
|
906
507
|
}
|
|
907
|
-
/**
|
|
908
|
-
* Applies a transform options object to the current matrix state.
|
|
909
|
-
* Optionally saves the matrix first
|
|
910
|
-
*/
|
|
911
508
|
applyTransform(t, e = 0, r = 0, i = -1) {
|
|
912
509
|
let s = t.x ?? 0, a = t.y ?? 0;
|
|
913
510
|
t.position && (s += t.position.x, a += t.position.y);
|
|
914
|
-
let
|
|
511
|
+
let h = 1, o = 1;
|
|
915
512
|
const c = t.scale;
|
|
916
|
-
c && (typeof c == "number" ? (
|
|
513
|
+
c && (typeof c == "number" ? (h = c, o = c) : (h = c.x, o = c.y));
|
|
917
514
|
const u = t.rotation ?? 0;
|
|
918
515
|
let l = t.offsetX ?? 0, d = t.offsetY ?? 0;
|
|
919
516
|
t.offset && (l += t.offset.x, d += t.offset.y);
|
|
920
517
|
const f = t.origin;
|
|
921
518
|
f !== void 0 && (typeof f == "number" ? (l -= f * e, d -= f * r) : (l -= f.x * e, d -= f.y * r));
|
|
922
|
-
const m = u ? Math.cos(u) : 1,
|
|
519
|
+
const m = u ? Math.cos(u) : 1, g = u ? Math.sin(u) : 0, v = m * h, y = g * h, w = -g * o, M = m * o, _ = s + v * l + w * d, P = a + y * l + M * d;
|
|
923
520
|
if (i !== -1) {
|
|
924
521
|
this.matrix.multiplyAffine(
|
|
925
522
|
this.curWorldM,
|
|
926
523
|
i,
|
|
524
|
+
v,
|
|
927
525
|
y,
|
|
928
|
-
|
|
526
|
+
w,
|
|
929
527
|
M,
|
|
930
|
-
|
|
931
|
-
P
|
|
932
|
-
C
|
|
528
|
+
_,
|
|
529
|
+
P
|
|
933
530
|
);
|
|
934
531
|
return;
|
|
935
532
|
}
|
|
936
533
|
this.matrix.multiplyAffineInPlace(
|
|
937
534
|
this.curLocalM,
|
|
535
|
+
v,
|
|
938
536
|
y,
|
|
939
|
-
|
|
537
|
+
w,
|
|
940
538
|
M,
|
|
941
|
-
|
|
942
|
-
P
|
|
943
|
-
C
|
|
539
|
+
_,
|
|
540
|
+
P
|
|
944
541
|
), this.matrix.multiplyAffineInPlace(
|
|
945
542
|
this.curWorldM,
|
|
543
|
+
v,
|
|
946
544
|
y,
|
|
947
|
-
|
|
545
|
+
w,
|
|
948
546
|
M,
|
|
949
|
-
|
|
950
|
-
P
|
|
951
|
-
C
|
|
547
|
+
_,
|
|
548
|
+
P
|
|
952
549
|
);
|
|
953
550
|
}
|
|
954
551
|
}
|
|
955
|
-
var
|
|
956
|
-
class
|
|
552
|
+
var q = /* @__PURE__ */ ((n) => (n[n.REPEAT = 0] = "REPEAT", n[n.CLAMP = 1] = "CLAMP", n[n.MIRRORED_REPEAT = 2] = "MIRRORED_REPEAT", n))(q || {});
|
|
553
|
+
class Ut {
|
|
957
554
|
render;
|
|
958
555
|
cache = /* @__PURE__ */ new Map();
|
|
959
556
|
constructor(t) {
|
|
960
557
|
this.render = t;
|
|
961
558
|
}
|
|
962
|
-
/**
|
|
963
|
-
* Asynchronously loads a texture from a URL.
|
|
964
|
-
* @param url - The image URL to load.
|
|
965
|
-
* @param options - Optional configuration for the texture.
|
|
966
|
-
* @returns A promise that resolves to the loaded Texture.
|
|
967
|
-
*/
|
|
968
559
|
async load(t, e) {
|
|
969
560
|
let r = this.cache.get(t);
|
|
970
561
|
if (r)
|
|
971
|
-
return new
|
|
562
|
+
return new N(r);
|
|
972
563
|
try {
|
|
973
564
|
const i = await this._fetchImage(t);
|
|
974
|
-
return r =
|
|
565
|
+
return r = V.fromSource(this.render, i, e), r.uid = t, this.cache.set(t, r), new N(r);
|
|
975
566
|
} catch (i) {
|
|
976
567
|
throw console.error(`[TextureManager] Failed to load: ${t}`, i), i;
|
|
977
568
|
}
|
|
978
569
|
}
|
|
979
|
-
/**
|
|
980
|
-
* Creates a texture synchronously from an existing HTML element (Image, Canvas, Video).
|
|
981
|
-
* @param source - The source image element.
|
|
982
|
-
* @param options - Optional configuration for the texture.
|
|
983
|
-
* @returns The newly created Texture.
|
|
984
|
-
*/
|
|
985
570
|
create(t, e) {
|
|
986
571
|
if (e?.key && this.cache.has(e.key))
|
|
987
|
-
return new
|
|
988
|
-
const r =
|
|
989
|
-
return e?.key && (r.uid = e.key, this.cache.set(e.key, r)), new
|
|
990
|
-
}
|
|
991
|
-
/**
|
|
992
|
-
* Creates a generic Render Texture (FrameBuffer).
|
|
993
|
-
* @param width - The width of the render texture.
|
|
994
|
-
* @param height - The height of the render texture.
|
|
995
|
-
* @param options - Optional configuration for the texture.
|
|
996
|
-
* @returns The newly created RenderTexture.
|
|
997
|
-
*/
|
|
572
|
+
return new N(this.cache.get(e.key));
|
|
573
|
+
const r = V.fromSource(this.render, t, e);
|
|
574
|
+
return e?.key && (r.uid = e.key, this.cache.set(e.key, r)), new N(r);
|
|
575
|
+
}
|
|
998
576
|
createRenderTexture(t) {
|
|
999
|
-
return new
|
|
577
|
+
return new Ct(this.render, t);
|
|
1000
578
|
}
|
|
1001
|
-
/**
|
|
1002
|
-
* Creates a TextTexture for rendering text.
|
|
1003
|
-
* @param options - Optional configuration for the texture.
|
|
1004
|
-
* @returns The newly created TextTexture.
|
|
1005
|
-
*/
|
|
1006
579
|
createTextTexture(t) {
|
|
1007
|
-
return new
|
|
1008
|
-
}
|
|
1009
|
-
/**
|
|
1010
|
-
* Destroys a texture and potentially removes its BaseTexture from the cache.
|
|
1011
|
-
* If a Texture instance is provided, it decrements the reference count of the BaseTexture.
|
|
1012
|
-
* The BaseTexture will only be destroyed if its reference count drops to 0, or if `force` is true.
|
|
1013
|
-
* @param textureOrUrl - The texture instance, base texture, or cache key (URL) to destroy.
|
|
1014
|
-
* @param force - If true, destroys the underlying BaseTexture immediately regardless of reference count.
|
|
1015
|
-
*/
|
|
580
|
+
return new Pt(this.render, t);
|
|
581
|
+
}
|
|
1016
582
|
destroy(t, e = !1) {
|
|
1017
583
|
let r, i;
|
|
1018
|
-
typeof t == "string" ? (i = t, r = this.cache.get(i)) : t instanceof
|
|
584
|
+
typeof t == "string" ? (i = t, r = this.cache.get(i)) : t instanceof N ? (r = t.base, i = r?.uid, t.destroy()) : (r = t, i = r.uid), r && (r.refCount <= 0 || e) && (r.destroy(this.render.gl), i && this.cache.delete(i));
|
|
1019
585
|
}
|
|
1020
|
-
/**
|
|
1021
|
-
* Destroys all cached textures and clears the cache, ignoring reference counts.
|
|
1022
|
-
*/
|
|
1023
586
|
destroyAll() {
|
|
1024
587
|
for (const t of this.cache.values())
|
|
1025
588
|
t.destroy(this.render.gl);
|
|
@@ -1032,7 +595,7 @@ class _t {
|
|
|
1032
595
|
});
|
|
1033
596
|
}
|
|
1034
597
|
}
|
|
1035
|
-
class
|
|
598
|
+
class V {
|
|
1036
599
|
glTexture = null;
|
|
1037
600
|
width;
|
|
1038
601
|
height;
|
|
@@ -1041,47 +604,24 @@ class z {
|
|
|
1041
604
|
constructor(t, e, r) {
|
|
1042
605
|
this.glTexture = t, this.width = e, this.height = r;
|
|
1043
606
|
}
|
|
1044
|
-
/**
|
|
1045
|
-
* Creates a BaseTexture from an image source.
|
|
1046
|
-
* @param render - The Rapid renderer instance.
|
|
1047
|
-
* @param source - The image source.
|
|
1048
|
-
* @param options - Optional configuration.
|
|
1049
|
-
* @returns The created BaseTexture.
|
|
1050
|
-
*/
|
|
1051
607
|
static fromSource(t, e, r = {}) {
|
|
1052
|
-
const i =
|
|
1053
|
-
return new
|
|
1054
|
-
}
|
|
1055
|
-
/**
|
|
1056
|
-
* Updates the content of the existing texture (e.g. for Video or dynamic Canvas).
|
|
1057
|
-
* Uses texSubImage2D if dimensions haven't changed for better performance.
|
|
1058
|
-
* @param gl - The WebGL rendering context.
|
|
1059
|
-
* @param source - The new image source.
|
|
1060
|
-
*/
|
|
608
|
+
const i = J(t, e, r);
|
|
609
|
+
return new V(i, e.width, e.height);
|
|
610
|
+
}
|
|
1061
611
|
updateSource(t, e, r = {}) {
|
|
1062
612
|
this.glTexture && (t.bindTexture(t.TEXTURE_2D, this.glTexture), r.textureFilter !== void 0 && nt(t, r.textureFilter), r.wrap !== void 0 && st(t, r.wrap), t.pixelStorei(t.UNPACK_FLIP_Y_WEBGL, 1), t.pixelStorei(t.UNPACK_ALIGNMENT, 1), r.premultipliedAlpha !== void 0 && t.pixelStorei(t.UNPACK_PREMULTIPLY_ALPHA_WEBGL, r.premultipliedAlpha), this.width === e.width && this.height === e.height ? t.texSubImage2D(t.TEXTURE_2D, 0, 0, 0, t.RGBA, t.UNSIGNED_BYTE, e) : (t.texImage2D(t.TEXTURE_2D, 0, t.RGBA, t.RGBA, t.UNSIGNED_BYTE, e), this.width = e.width, this.height = e.height), r.premultipliedAlpha !== void 0 && t.pixelStorei(t.UNPACK_PREMULTIPLY_ALPHA_WEBGL, !1));
|
|
1063
613
|
}
|
|
1064
|
-
/**
|
|
1065
|
-
* Dynamically updates the texture filtering mode.
|
|
1066
|
-
*/
|
|
1067
614
|
setFilterMode(t, e) {
|
|
1068
615
|
this.glTexture && (t.bindTexture(t.TEXTURE_2D, this.glTexture), nt(t, e), t.bindTexture(t.TEXTURE_2D, null));
|
|
1069
616
|
}
|
|
1070
|
-
/**
|
|
1071
|
-
* Dynamically updates the texture wrap mode.
|
|
1072
|
-
*/
|
|
1073
617
|
setWrapMode(t, e) {
|
|
1074
618
|
this.glTexture && (t.bindTexture(t.TEXTURE_2D, this.glTexture), st(t, e), t.bindTexture(t.TEXTURE_2D, null));
|
|
1075
619
|
}
|
|
1076
|
-
/**
|
|
1077
|
-
* Destroys the WebGL texture resource.
|
|
1078
|
-
* @param gl - The WebGL rendering context.
|
|
1079
|
-
*/
|
|
1080
620
|
destroy(t) {
|
|
1081
621
|
this.glTexture && (t.deleteTexture(this.glTexture), this.glTexture = null);
|
|
1082
622
|
}
|
|
1083
623
|
}
|
|
1084
|
-
class
|
|
624
|
+
class N {
|
|
1085
625
|
base;
|
|
1086
626
|
uvX = 0;
|
|
1087
627
|
uvY = 0;
|
|
@@ -1097,121 +637,63 @@ class O {
|
|
|
1097
637
|
isRotated = !1;
|
|
1098
638
|
glTexture = null;
|
|
1099
639
|
get width() {
|
|
1100
|
-
return
|
|
640
|
+
return this.isRotated ? this.rawHeight : this.rawWidth;
|
|
1101
641
|
}
|
|
1102
642
|
get height() {
|
|
1103
|
-
return
|
|
643
|
+
return this.isRotated ? this.rawWidth : this.rawHeight;
|
|
1104
644
|
}
|
|
1105
645
|
// Stored pixel-space region (before UV conversion), used by getSubTexture()
|
|
1106
646
|
_px = 0;
|
|
1107
647
|
_py = 0;
|
|
1108
|
-
_pw = 0;
|
|
1109
|
-
_ph = 0;
|
|
1110
648
|
constructor(t) {
|
|
1111
649
|
t && this.setBase(t);
|
|
1112
650
|
}
|
|
1113
|
-
/**
|
|
1114
|
-
* Sets the base texture and increments its reference count.
|
|
1115
|
-
* @param base - The BaseTexture instance.
|
|
1116
|
-
* @returns The current Texture instance.
|
|
1117
|
-
*/
|
|
1118
651
|
setBase(t) {
|
|
1119
652
|
return this.base === t ? this : (this.base && this.base.refCount--, this.base = t, this.base.refCount++, this.setRegion(0, 0, t.width, t.height), this.glTexture = t.glTexture, this);
|
|
1120
653
|
}
|
|
1121
|
-
/**
|
|
1122
|
-
* Sets the visible region (clipping) in pixels relative to the BaseTexture.
|
|
1123
|
-
* @param x - The x coordinate in pixels.
|
|
1124
|
-
* @param y - The y coordinate in pixels.
|
|
1125
|
-
* @param w - The width in pixels.
|
|
1126
|
-
* @param h - The height in pixels.
|
|
1127
|
-
* @returns The current Texture instance.
|
|
1128
|
-
*/
|
|
1129
654
|
setRegion(t, e, r, i) {
|
|
1130
|
-
return this.base ? (this._px = t, this._py = e, this.
|
|
1131
|
-
}
|
|
1132
|
-
/**
|
|
1133
|
-
* Creates a new Texture representing a sub-region of this Texture.
|
|
1134
|
-
* @param x - The x coordinate in pixels, relative to this texture's logical start.
|
|
1135
|
-
* @param y - The y coordinate in pixels, relative to this texture's logical start.
|
|
1136
|
-
* @param width - The width of the sub-texture in pixels.
|
|
1137
|
-
* @param height - The height of the sub-texture in pixels.
|
|
1138
|
-
* @returns A new Texture pointing to the sub-region.
|
|
1139
|
-
*/
|
|
655
|
+
return this.base ? (this._px = t, this._py = e, this.isAtlas = t !== 0 || e !== 0 || r !== this.base.width || i !== this.base.height, this.uvX = t / this.base.width, this.uvY = e / this.base.height, this.uvW = this.uvX + r / this.base.width, this.uvH = this.uvY + i / this.base.height, this.rawWidth = r * this.scale, this.rawHeight = i * this.scale, this) : this;
|
|
656
|
+
}
|
|
1140
657
|
getSubTexture(t, e, r, i) {
|
|
1141
|
-
if (!this.base) return new
|
|
1142
|
-
const s = this.clone(), a = this._px,
|
|
1143
|
-
return s.setRegion(a + t,
|
|
1144
|
-
}
|
|
1145
|
-
/**
|
|
1146
|
-
* Creates a shallow copy of this Texture, sharing the same BaseTexture.
|
|
1147
|
-
* @returns A new Texture instance.
|
|
1148
|
-
*/
|
|
658
|
+
if (!this.base) return new N();
|
|
659
|
+
const s = this.clone(), a = this._px, h = this._py;
|
|
660
|
+
return s.setRegion(a + t, h + e, r, i), s;
|
|
661
|
+
}
|
|
1149
662
|
clone(t) {
|
|
1150
|
-
const e = t ?? new
|
|
1151
|
-
return t && this.base && t.setBase(this.base), e.scale = this.scale, e.uvX = this.uvX, e.uvY = this.uvY, e.uvW = this.uvW, e.uvH = this.uvH, e.rawWidth = this.rawWidth, e.rawHeight = this.rawHeight, e.offsetX = this.offsetX, e.offsetY = this.offsetY, e.flipY = this.flipY, e.isRotated = this.isRotated, e.isAtlas = this.isAtlas, e._px = this._px, e._py = this._py, e
|
|
1152
|
-
}
|
|
1153
|
-
/**
|
|
1154
|
-
* Utility to split this texture into a grid of sprite textures.
|
|
1155
|
-
* Sub-textures will respect the current UV offsets.
|
|
1156
|
-
* @param cellWidth - The width of each cell in pixels.
|
|
1157
|
-
* @param cellHeight - The height of each cell in pixels.
|
|
1158
|
-
* @param cols - Optional number of columns. Truncates based on texture width if omitted.
|
|
1159
|
-
* @param rows - Optional number of rows. Truncates based on texture height if omitted.
|
|
1160
|
-
* @param gap - Optional pixel gap between cells.
|
|
1161
|
-
* @returns An array of split Textures.
|
|
1162
|
-
*/
|
|
663
|
+
const e = t ?? new N(this.base);
|
|
664
|
+
return t && this.base && t.setBase(this.base), e.scale = this.scale, e.uvX = this.uvX, e.uvY = this.uvY, e.uvW = this.uvW, e.uvH = this.uvH, e.rawWidth = this.rawWidth, e.rawHeight = this.rawHeight, e.offsetX = this.offsetX, e.offsetY = this.offsetY, e.flipY = this.flipY, e.isRotated = this.isRotated, e.isAtlas = this.isAtlas, e._px = this._px, e._py = this._py, e;
|
|
665
|
+
}
|
|
1163
666
|
splitGrid(t, e, r, i, s = 0) {
|
|
1164
667
|
if (!this.base) return [];
|
|
1165
|
-
const a = [],
|
|
668
|
+
const a = [], h = this.rawWidth, o = this.rawHeight, c = Math.max(0, s), u = t + c, l = e + c, d = r ?? Math.floor((h + c) / u), f = i ?? Math.floor((o + c) / l);
|
|
1166
669
|
for (let m = 0; m < f; m++)
|
|
1167
|
-
for (let
|
|
1168
|
-
a.push(this.getSubTexture(
|
|
670
|
+
for (let g = 0; g < d; g++)
|
|
671
|
+
a.push(this.getSubTexture(g * u, m * l, t, e));
|
|
1169
672
|
return a;
|
|
1170
673
|
}
|
|
1171
|
-
/**
|
|
1172
|
-
* Creates a Texture directly from an image source, bypassing the TextureManager.
|
|
1173
|
-
* @param source - The image element, canvas, video, or bitmap.
|
|
1174
|
-
* @param options - Optional antialias and wrap mode settings.
|
|
1175
|
-
*/
|
|
1176
674
|
static fromImageSource(t, e, r = {}) {
|
|
1177
|
-
const i =
|
|
1178
|
-
return new
|
|
675
|
+
const i = J(t, e, r);
|
|
676
|
+
return new N(new V(i, e.width, e.height));
|
|
1179
677
|
}
|
|
1180
|
-
/**
|
|
1181
|
-
* Marks this Texture as destroyed, decrementing the BaseTexture reference count.
|
|
1182
|
-
*/
|
|
1183
678
|
destroy() {
|
|
1184
679
|
this.base && (this.base.refCount--, this.base = void 0), this.glTexture = null;
|
|
1185
680
|
}
|
|
1186
681
|
}
|
|
1187
|
-
class
|
|
682
|
+
class Ct extends N {
|
|
1188
683
|
framebuffer;
|
|
1189
684
|
renderbuffer;
|
|
1190
685
|
gl;
|
|
1191
686
|
flipY = !0;
|
|
1192
687
|
clearColor;
|
|
1193
|
-
/** Actual GPU-allocated dimensions — grow-only, never shrink */
|
|
1194
688
|
_allocW = 0;
|
|
1195
689
|
_allocH = 0;
|
|
1196
690
|
constructor(t, e) {
|
|
1197
691
|
super(), this.gl = t.gl, this.clearColor = e.clearColor ?? x.Black;
|
|
1198
|
-
const r = Math.max(Math.round(e.width), 1), i = Math.max(Math.round(e.height), 1), a =
|
|
1199
|
-
if (this.setBase(new
|
|
692
|
+
const r = Math.max(Math.round(e.width), 1), i = Math.max(Math.round(e.height), 1), a = J(t, { width: r, height: i }, { ...e, onlySize: !0 });
|
|
693
|
+
if (this.setBase(new V(a, r, i)), this.framebuffer = this.gl.createFramebuffer(), this.renderbuffer = this.gl.createRenderbuffer(), !this.framebuffer || !this.renderbuffer)
|
|
1200
694
|
throw new Error("Failed to create Framebuffer or Renderbuffer");
|
|
1201
695
|
this.resize(r, i, !0);
|
|
1202
696
|
}
|
|
1203
|
-
/**
|
|
1204
|
-
* Resizes the render texture using a grow-only GPU allocation strategy.
|
|
1205
|
-
*
|
|
1206
|
-
* - GPU memory is only reallocated when the new size **exceeds** the current allocation.
|
|
1207
|
-
* - Shrinking only updates the logical dimensions and UV sub-region — no GPU work.
|
|
1208
|
-
*
|
|
1209
|
-
* This makes it safe to call every frame with varying sizes (e.g. inside applyFilters).
|
|
1210
|
-
*
|
|
1211
|
-
* @param width - New logical width.
|
|
1212
|
-
* @param height - New logical height.
|
|
1213
|
-
* @param force - Force full GPU reallocation regardless of current allocation size.
|
|
1214
|
-
*/
|
|
1215
697
|
resize(t, e, r = !1) {
|
|
1216
698
|
t = Math.max(Math.round(t), 1), e = Math.max(Math.round(e), 1);
|
|
1217
699
|
const i = this.rawWidth === t && this.rawHeight === e;
|
|
@@ -1219,10 +701,6 @@ class Pt extends O {
|
|
|
1219
701
|
const s = this.gl;
|
|
1220
702
|
(r || t > this._allocW || e > this._allocH) && this.base && (this._allocW = Math.max(this._allocW, t), this._allocH = Math.max(this._allocH, e), this.base.width = this._allocW, this.base.height = this._allocH, s.bindTexture(s.TEXTURE_2D, this.base.glTexture), s.texImage2D(s.TEXTURE_2D, 0, s.RGBA, this._allocW, this._allocH, 0, s.RGBA, s.UNSIGNED_BYTE, null), s.bindRenderbuffer(s.RENDERBUFFER, this.renderbuffer), s.renderbufferStorage(s.RENDERBUFFER, s.STENCIL_INDEX8, this._allocW, this._allocH), s.bindFramebuffer(s.FRAMEBUFFER, this.framebuffer), s.framebufferTexture2D(s.FRAMEBUFFER, s.COLOR_ATTACHMENT0, s.TEXTURE_2D, this.base.glTexture, 0), s.framebufferRenderbuffer(s.FRAMEBUFFER, s.STENCIL_ATTACHMENT, s.RENDERBUFFER, this.renderbuffer), s.bindFramebuffer(s.FRAMEBUFFER, null), s.bindRenderbuffer(s.RENDERBUFFER, null), s.bindTexture(s.TEXTURE_2D, null)), this.rawWidth = t, this.rawHeight = e, this.uvX = 0, this.uvW = t / this._allocW, this.uvY = 0, this.uvH = e / this._allocH;
|
|
1221
703
|
}
|
|
1222
|
-
/**
|
|
1223
|
-
* Activates this texture as the current render target.
|
|
1224
|
-
* @param clear - Whether to clear the render target after activation.
|
|
1225
|
-
*/
|
|
1226
704
|
activate(t = !1) {
|
|
1227
705
|
if (!this.framebuffer) return;
|
|
1228
706
|
const e = this.gl;
|
|
@@ -1233,48 +711,30 @@ class Pt extends O {
|
|
|
1233
711
|
const e = this.gl, r = t ?? this.clearColor;
|
|
1234
712
|
r && (r.setClearColor(e), e.clear(e.COLOR_BUFFER_BIT | e.STENCIL_BUFFER_BIT));
|
|
1235
713
|
}
|
|
1236
|
-
/**
|
|
1237
|
-
* Deactivates this texture, returning rendering to the default frame buffer.
|
|
1238
|
-
*/
|
|
1239
714
|
deactivate() {
|
|
1240
715
|
const t = this.gl;
|
|
1241
716
|
t.bindFramebuffer(t.FRAMEBUFFER, null);
|
|
1242
717
|
}
|
|
1243
|
-
/**
|
|
1244
|
-
* Get raw pixels from the render texture.
|
|
1245
|
-
* @param x - X coordinate in logical pixel space (top-left origin).
|
|
1246
|
-
* @param y - Y coordinate in logical pixel space (top-left origin).
|
|
1247
|
-
* @param width - Width of the region to read.
|
|
1248
|
-
* @param height - Height of the region to read.
|
|
1249
|
-
*/
|
|
1250
718
|
GetPixels(t = 0, e = 0, r = this.rawWidth, i = this.rawHeight) {
|
|
1251
719
|
if (!this.framebuffer) return new Uint8Array(0);
|
|
1252
|
-
const s = Math.floor(t), a = Math.floor(e),
|
|
1253
|
-
if (
|
|
720
|
+
const s = Math.floor(t), a = Math.floor(e), h = Math.floor(r), o = Math.floor(i);
|
|
721
|
+
if (h <= 0 || o <= 0) return new Uint8Array(0);
|
|
1254
722
|
if (s < 0 || a < 0 || s >= this.rawWidth || a >= this.rawHeight)
|
|
1255
723
|
return new Uint8Array(0);
|
|
1256
|
-
const c = Math.min(
|
|
724
|
+
const c = Math.min(h, this.rawWidth - s), u = Math.min(o, this.rawHeight - a), l = this.rawHeight - a - u, d = this.gl, f = d.getParameter(d.FRAMEBUFFER_BINDING);
|
|
1257
725
|
d.bindFramebuffer(d.FRAMEBUFFER, this.framebuffer);
|
|
1258
726
|
const m = new Uint8Array(c * u * 4);
|
|
1259
727
|
return d.readPixels(s, l, c, u, d.RGBA, d.UNSIGNED_BYTE, m), d.bindFramebuffer(d.FRAMEBUFFER, f), m;
|
|
1260
728
|
}
|
|
1261
|
-
/**
|
|
1262
|
-
* Get the color at a pixel in the render texture.
|
|
1263
|
-
* @param x - X coordinate in logical pixel space (top-left origin).
|
|
1264
|
-
* @param y - Y coordinate in logical pixel space (top-left origin).
|
|
1265
|
-
*/
|
|
1266
729
|
GetColorAt(t, e) {
|
|
1267
730
|
const r = this.GetPixels(t, e, 1, 1);
|
|
1268
731
|
return r.length < 4 ? new x(0, 0, 0, 0) : new x(r[0], r[1], r[2], r[3]);
|
|
1269
732
|
}
|
|
1270
|
-
/**
|
|
1271
|
-
* Destroys the framebuffer, renderbuffer, and base texture.
|
|
1272
|
-
*/
|
|
1273
733
|
destroy() {
|
|
1274
734
|
super.destroy(), this.framebuffer && this.gl.deleteFramebuffer(this.framebuffer), this.renderbuffer && this.gl.deleteRenderbuffer(this.renderbuffer), this.base?.destroy(this.gl);
|
|
1275
735
|
}
|
|
1276
736
|
}
|
|
1277
|
-
const
|
|
737
|
+
const _t = {
|
|
1278
738
|
fontFamily: "Arial",
|
|
1279
739
|
fontSize: 24,
|
|
1280
740
|
fontWeight: "normal",
|
|
@@ -1283,7 +743,7 @@ const Nt = {
|
|
|
1283
743
|
align: "left",
|
|
1284
744
|
lineHeight: 1
|
|
1285
745
|
};
|
|
1286
|
-
class
|
|
746
|
+
class Pt extends N {
|
|
1287
747
|
canvas;
|
|
1288
748
|
ctx;
|
|
1289
749
|
render;
|
|
@@ -1292,28 +752,22 @@ class Lt extends O {
|
|
|
1292
752
|
options;
|
|
1293
753
|
flipY = !0;
|
|
1294
754
|
constructor(t, e) {
|
|
1295
|
-
super(), this.render = t, this._style = { ...
|
|
755
|
+
super(), this.render = t, this._style = { ..._t, ...e }, this._text = e?.text ?? "", this.options = { premultipliedAlpha: t.premultipliedAlpha, ...e }, this.scale = 1 / t.dpr, this.canvas = document.createElement("canvas");
|
|
1296
756
|
const r = this.canvas.getContext("2d", { willReadFrequently: !0 });
|
|
1297
757
|
if (!r) throw new Error("Failed to get 2d context for TextTexture");
|
|
1298
758
|
this.ctx = r, this.canvas.width = 1, this.canvas.height = 1;
|
|
1299
|
-
const i =
|
|
1300
|
-
this.setBase(new
|
|
759
|
+
const i = J(t, this.canvas, this.options);
|
|
760
|
+
this.setBase(new V(i, 1, 1)), this.update();
|
|
1301
761
|
}
|
|
1302
762
|
get text() {
|
|
1303
763
|
return this._text;
|
|
1304
764
|
}
|
|
1305
|
-
/**
|
|
1306
|
-
* Set new text and update the texture
|
|
1307
|
-
*/
|
|
1308
765
|
set text(t) {
|
|
1309
766
|
this._text !== t && (this._text = t, this.update());
|
|
1310
767
|
}
|
|
1311
768
|
get style() {
|
|
1312
769
|
return this._style;
|
|
1313
770
|
}
|
|
1314
|
-
/**
|
|
1315
|
-
* Set new style partially and update the texture
|
|
1316
|
-
*/
|
|
1317
771
|
set style(t) {
|
|
1318
772
|
this._style = { ...this._style, ...t }, this.update();
|
|
1319
773
|
}
|
|
@@ -1327,37 +781,34 @@ class Lt extends O {
|
|
|
1327
781
|
return e;
|
|
1328
782
|
}
|
|
1329
783
|
}
|
|
1330
|
-
/**
|
|
1331
|
-
* Updates the internal canvas and uploads it to WebGL
|
|
1332
|
-
*/
|
|
1333
784
|
update() {
|
|
1334
|
-
const t = this.ctx, e = this.style, r = e.fontSize, i = e.fontWeight, s = e.fontFamily, a = e.lineHeight,
|
|
1335
|
-
t.font =
|
|
785
|
+
const t = this.ctx, e = this.style, r = e.fontSize, i = e.fontWeight, s = e.fontFamily, a = e.lineHeight, h = `${i} ${r}px ${s}`, o = this.render.dpr;
|
|
786
|
+
t.font = h, t.textBaseline = "top";
|
|
1336
787
|
const c = this._text.split(`
|
|
1337
788
|
`);
|
|
1338
789
|
let u = 0, l = 0;
|
|
1339
|
-
const
|
|
1340
|
-
for (const
|
|
1341
|
-
const
|
|
1342
|
-
|
|
790
|
+
const m = t.measureText(c[0] || "M").fontBoundingBoxDescent;
|
|
791
|
+
for (const b of c) {
|
|
792
|
+
const R = t.measureText(b);
|
|
793
|
+
R.width > u && (u = R.width), l += m * a;
|
|
1343
794
|
}
|
|
1344
|
-
l -=
|
|
1345
|
-
const
|
|
1346
|
-
(this.canvas.width !==
|
|
1347
|
-
const
|
|
1348
|
-
|
|
1349
|
-
let
|
|
1350
|
-
for (const
|
|
1351
|
-
|
|
1352
|
-
this.base?.updateSource(this.render.gl, this.canvas, this.options), this.setRegion(0, 0,
|
|
795
|
+
l -= m * (a - 1);
|
|
796
|
+
const g = this._style.strokeThickness || 0, v = Math.ceil(u + g * 2) || 1, y = Math.ceil(l + g * 2) || 1, w = Math.ceil(v * o), M = Math.ceil(y * o);
|
|
797
|
+
(this.canvas.width !== w || this.canvas.height !== M) && (this.canvas.width = w, this.canvas.height = M), t.setTransform(o, 0, 0, o, 0, 0), t.clearRect(0, 0, v, y), t.font = h, t.textBaseline = "top", t.textAlign = this._style.align;
|
|
798
|
+
const _ = this.updateOffset(v, g), P = e.strokeThickness, O = P > 0;
|
|
799
|
+
O && (t.lineWidth = P, t.strokeStyle = e.stroke, t.lineJoin = "round"), e.fill && (t.fillStyle = e.fill);
|
|
800
|
+
let W = g;
|
|
801
|
+
for (const b of c)
|
|
802
|
+
O && t.strokeText(b, _, W), e.fill && t.fillText(b, _, W), W += m * a;
|
|
803
|
+
this.base?.updateSource(this.render.gl, this.canvas, this.options), this.setRegion(0, 0, w, M);
|
|
1353
804
|
}
|
|
1354
805
|
}
|
|
1355
|
-
const
|
|
806
|
+
const Lt = (n, t = !1, e = !0) => {
|
|
1356
807
|
const r = n.getContext("webgl2", { stencil: !0, antialias: t, premultipliedAlpha: e });
|
|
1357
808
|
if (!r)
|
|
1358
809
|
throw new Error("WebGL2 is not supported in this browser.");
|
|
1359
810
|
return r;
|
|
1360
|
-
},
|
|
811
|
+
}, ct = (n, t, e) => {
|
|
1361
812
|
const r = n.createShader(e);
|
|
1362
813
|
if (!r)
|
|
1363
814
|
throw new Error("Unable to create webgl shader");
|
|
@@ -1366,21 +817,21 @@ const It = (n, t = !1, e = !0) => {
|
|
|
1366
817
|
throw console.error("Shader compilation failed:", s), new Error("Unable to compile shader: " + s + t);
|
|
1367
818
|
}
|
|
1368
819
|
return r;
|
|
1369
|
-
},
|
|
1370
|
-
var r = n.createProgram(), i =
|
|
820
|
+
}, Nt = (n, t, e) => {
|
|
821
|
+
var r = n.createProgram(), i = ct(n, t, 35633), s = ct(n, e, 35632);
|
|
1371
822
|
if (!r)
|
|
1372
823
|
throw new Error("Unable to create program shader");
|
|
1373
824
|
if (n.attachShader(r, i), n.attachShader(r, s), n.linkProgram(r), !n.getProgramParameter(r, n.LINK_STATUS)) {
|
|
1374
|
-
const
|
|
1375
|
-
throw new Error("Unable to link shader program: " +
|
|
825
|
+
const h = n.getProgramInfoLog(r);
|
|
826
|
+
throw new Error("Unable to link shader program: " + h);
|
|
1376
827
|
}
|
|
1377
828
|
return r;
|
|
1378
829
|
};
|
|
1379
830
|
function st(n, t) {
|
|
1380
831
|
const e = {
|
|
1381
|
-
[
|
|
1382
|
-
[
|
|
1383
|
-
[
|
|
832
|
+
[q.CLAMP]: n.CLAMP_TO_EDGE,
|
|
833
|
+
[q.REPEAT]: n.REPEAT,
|
|
834
|
+
[q.MIRRORED_REPEAT]: n.MIRRORED_REPEAT
|
|
1384
835
|
}[t] || n.CLAMP_TO_EDGE;
|
|
1385
836
|
n.texParameteri(n.TEXTURE_2D, n.TEXTURE_WRAP_S, e), n.texParameteri(n.TEXTURE_2D, n.TEXTURE_WRAP_T, e);
|
|
1386
837
|
}
|
|
@@ -1391,11 +842,11 @@ function nt(n, t) {
|
|
|
1391
842
|
}[t] ?? n.NEAREST;
|
|
1392
843
|
n.texParameteri(n.TEXTURE_2D, n.TEXTURE_MIN_FILTER, e), n.texParameteri(n.TEXTURE_2D, n.TEXTURE_MAG_FILTER, e);
|
|
1393
844
|
}
|
|
1394
|
-
function
|
|
845
|
+
function J(n, t, e) {
|
|
1395
846
|
const r = n.gl, i = r.createTexture();
|
|
1396
847
|
if (!i)
|
|
1397
848
|
throw new Error("Unable to create WebGL texture");
|
|
1398
|
-
if (r.bindTexture(r.TEXTURE_2D, i), r.pixelStorei(r.UNPACK_FLIP_Y_WEBGL, 0), r.pixelStorei(r.UNPACK_ALIGNMENT, 1), st(r, e.wrap ??
|
|
849
|
+
if (r.bindTexture(r.TEXTURE_2D, i), r.pixelStorei(r.UNPACK_FLIP_Y_WEBGL, 0), r.pixelStorei(r.UNPACK_ALIGNMENT, 1), st(r, e.wrap ?? q.CLAMP), nt(r, e.textureFilter ?? n.textureFilter), e.onlySize) {
|
|
1399
850
|
const s = t;
|
|
1400
851
|
r.texImage2D(r.TEXTURE_2D, 0, r.RGBA, s.width, s.height, 0, r.RGBA, r.UNSIGNED_BYTE, null);
|
|
1401
852
|
} else {
|
|
@@ -1404,7 +855,7 @@ function et(n, t, e) {
|
|
|
1404
855
|
}
|
|
1405
856
|
return r.bindTexture(r.TEXTURE_2D, null), i;
|
|
1406
857
|
}
|
|
1407
|
-
function
|
|
858
|
+
function B(n, t) {
|
|
1408
859
|
if (n.includes("%TEXTURE_NUM%") && (n = n.replace("%TEXTURE_NUM%", t.toString())), n.includes("%GET_COLOR%")) {
|
|
1409
860
|
let e = "";
|
|
1410
861
|
for (let r = 0; r < t; r++)
|
|
@@ -1413,76 +864,50 @@ function V(n, t) {
|
|
|
1413
864
|
}
|
|
1414
865
|
return n;
|
|
1415
866
|
}
|
|
1416
|
-
const
|
|
1417
|
-
function
|
|
867
|
+
const It = 5126, at = 5121;
|
|
868
|
+
function Ot(n, t, e) {
|
|
1418
869
|
n.vertexAttribDivisor(t, e);
|
|
1419
870
|
}
|
|
1420
|
-
function
|
|
871
|
+
function yt(n, t, e, r, i) {
|
|
1421
872
|
n.drawArraysInstanced(t, e, r, i);
|
|
1422
873
|
}
|
|
1423
|
-
let
|
|
1424
|
-
class
|
|
874
|
+
let Wt = 0;
|
|
875
|
+
class Tt {
|
|
1425
876
|
program;
|
|
1426
877
|
attributeLoc = {};
|
|
1427
878
|
uniformLoc = {};
|
|
1428
879
|
isCustom = !1;
|
|
1429
|
-
/** Padding in pixels this shader needs beyond the sprite bounds (for outline/glow effects) */
|
|
1430
880
|
padding = 0;
|
|
1431
|
-
/** GLSL type for each uniform, parsed from source */
|
|
1432
881
|
uniformType = {};
|
|
1433
|
-
/** Whether the uniform is an array (e.g. sampler2D uTextures[8]) */
|
|
1434
882
|
uniformIsArray = {};
|
|
1435
883
|
gl;
|
|
1436
|
-
shaderId =
|
|
884
|
+
shaderId = Wt++;
|
|
1437
885
|
// for debug
|
|
1438
886
|
vao;
|
|
1439
887
|
constructor(t, e, r, i) {
|
|
1440
|
-
this.gl = t, this.program =
|
|
888
|
+
this.gl = t, this.program = Nt(t, e, r), this.parseShader(e), this.parseShader(r), this.vao = t.createVertexArray(), i && this.setAttributes(i);
|
|
1441
889
|
}
|
|
1442
|
-
/** Switch GPU to use this shader program */
|
|
1443
890
|
use() {
|
|
1444
891
|
this.gl.useProgram(this.program);
|
|
1445
892
|
}
|
|
1446
|
-
/** Bind this shader's VAO (start recording or replaying attribute state) */
|
|
1447
893
|
bindVAO() {
|
|
1448
894
|
this.gl.bindVertexArray(this.vao);
|
|
1449
895
|
}
|
|
1450
|
-
/** Unbind VAO (finish recording) */
|
|
1451
896
|
unbindVAO() {
|
|
1452
897
|
this.gl.bindVertexArray(null);
|
|
1453
898
|
}
|
|
1454
899
|
// ── Uniforms ─────────────────────────────────────────────────────────────
|
|
1455
|
-
/**
|
|
1456
|
-
* Set a single uniform by name. Type is inferred from the parsed GLSL source.
|
|
1457
|
-
* @example
|
|
1458
|
-
* shader.setUniform("uTime", 1.5);
|
|
1459
|
-
* shader.setUniform("uColor", [1, 0, 0, 1]);
|
|
1460
|
-
* shader.setUniform("uMVP", mat4array);
|
|
1461
|
-
*/
|
|
1462
900
|
setUniform(t, e) {
|
|
1463
901
|
const r = this.uniformLoc[t];
|
|
1464
902
|
if (r === void 0) return;
|
|
1465
903
|
const i = this.uniformType[t], s = this.uniformIsArray[t];
|
|
1466
|
-
|
|
1467
|
-
}
|
|
1468
|
-
/**
|
|
1469
|
-
* Batch-set uniforms via a plain value map.
|
|
1470
|
-
* @example
|
|
1471
|
-
* shader.setUniforms({
|
|
1472
|
-
* uTime: 1.5,
|
|
1473
|
-
* uResolution: [800, 600],
|
|
1474
|
-
* uMVP: mat4,
|
|
1475
|
-
* });
|
|
1476
|
-
*/
|
|
904
|
+
Ft(this.gl, r, i, e, s);
|
|
905
|
+
}
|
|
1477
906
|
setUniforms(t) {
|
|
1478
907
|
for (const e in t)
|
|
1479
908
|
this.setUniform(e, t[e]);
|
|
1480
909
|
}
|
|
1481
910
|
// ── Attributes ────────────────────────────────────────────────────────────
|
|
1482
|
-
/**
|
|
1483
|
-
* Bind a single vertex attribute pointer.
|
|
1484
|
-
* The VBO must already be bound before calling this.
|
|
1485
|
-
*/
|
|
1486
911
|
setAttribute(t) {
|
|
1487
912
|
const e = this.attributeLoc[t.name];
|
|
1488
913
|
if (e === void 0) return;
|
|
@@ -1490,39 +915,37 @@ class wt {
|
|
|
1490
915
|
r.vertexAttribPointer(
|
|
1491
916
|
e,
|
|
1492
917
|
t.size,
|
|
1493
|
-
t.type ??
|
|
918
|
+
t.type ?? It,
|
|
1494
919
|
t.normalized ?? !1,
|
|
1495
920
|
t.stride,
|
|
1496
921
|
t.offset ?? 0
|
|
1497
|
-
), r.enableVertexAttribArray(e),
|
|
922
|
+
), r.enableVertexAttribArray(e), Ot(r, e, t.divisor ?? 0);
|
|
1498
923
|
}
|
|
1499
|
-
/** Bind all vertex attribute pointers at once */
|
|
1500
924
|
setAttributes(t) {
|
|
1501
925
|
for (const e of t)
|
|
1502
926
|
this.setAttribute(e);
|
|
1503
927
|
}
|
|
1504
928
|
// ── Lifecycle ─────────────────────────────────────────────────────────────
|
|
1505
|
-
/** Free GPU resources */
|
|
1506
929
|
destroy() {
|
|
1507
930
|
this.gl.deleteProgram(this.program);
|
|
1508
931
|
}
|
|
1509
|
-
/** Parse attribute/uniform names and GLSL types from raw shader source */
|
|
1510
932
|
parseShader(t) {
|
|
1511
933
|
const e = this.gl, r = t.match(/(?:in|attribute)\s+\w+\s+\w+/g);
|
|
1512
934
|
if (r)
|
|
1513
935
|
for (const s of r) {
|
|
1514
|
-
const
|
|
1515
|
-
|
|
1516
|
-
}
|
|
1517
|
-
const i = t.match(/uniform\s+\w+\s+\w+(?:\[\d+\])?/g);
|
|
1518
|
-
if (i)
|
|
1519
|
-
for (const s of i) {
|
|
1520
|
-
const a = s.split(/\s+/), o = a[1], h = a[2].replace(/\[\d+\]$/, ""), c = e.getUniformLocation(this.program, h);
|
|
1521
|
-
c !== null && (this.uniformLoc[h] = c, this.uniformType[h] = o, this.uniformIsArray[h] = /\[\d+\]$/.test(a[2]));
|
|
936
|
+
const h = s.split(/\s+/)[2], o = e.getAttribLocation(this.program, h);
|
|
937
|
+
o !== -1 && (this.attributeLoc[h] = o);
|
|
1522
938
|
}
|
|
939
|
+
const i = t.matchAll(
|
|
940
|
+
/uniform\s+(?:(?:lowp|mediump|highp)\s+)?(\w+)\s+(\w+)(\s*\[\s*\d+\s*\])?/g
|
|
941
|
+
);
|
|
942
|
+
for (const s of i) {
|
|
943
|
+
const a = s[1], h = s[2], o = e.getUniformLocation(this.program, h);
|
|
944
|
+
o !== null && (this.uniformLoc[h] = o, this.uniformType[h] = a, this.uniformIsArray[h] = s[3] !== void 0);
|
|
945
|
+
}
|
|
1523
946
|
}
|
|
1524
947
|
}
|
|
1525
|
-
function
|
|
948
|
+
function Ft(n, t, e, r, i = !1) {
|
|
1526
949
|
switch (e) {
|
|
1527
950
|
// scalars
|
|
1528
951
|
case "float":
|
|
@@ -1558,10 +981,10 @@ function Dt(n, t, e, r, i = !1) {
|
|
|
1558
981
|
return n.uniformMatrix4fv(t, !1, r);
|
|
1559
982
|
// fallback: guess by value shape
|
|
1560
983
|
default:
|
|
1561
|
-
return
|
|
984
|
+
return Bt(n, t, r);
|
|
1562
985
|
}
|
|
1563
986
|
}
|
|
1564
|
-
function
|
|
987
|
+
function Bt(n, t, e) {
|
|
1565
988
|
if (typeof e == "number")
|
|
1566
989
|
return n.uniform1f(t, e);
|
|
1567
990
|
const r = e;
|
|
@@ -1580,31 +1003,19 @@ function kt(n, t, e) {
|
|
|
1580
1003
|
return n.uniform1fv(t, r);
|
|
1581
1004
|
}
|
|
1582
1005
|
}
|
|
1583
|
-
class
|
|
1584
|
-
/** Custom vertex shader code */
|
|
1006
|
+
class ut {
|
|
1585
1007
|
vs;
|
|
1586
|
-
/** Custom fragment shader code */
|
|
1587
1008
|
fs;
|
|
1588
|
-
/** Map of compiled GLShader instances per region key */
|
|
1589
1009
|
glshader = /* @__PURE__ */ new Map();
|
|
1590
|
-
/** Currently stored uniform values */
|
|
1591
1010
|
uniforms = {};
|
|
1592
|
-
/** Set of region keys that need uniform updates */
|
|
1593
1011
|
uniformDirty = /* @__PURE__ */ new Set();
|
|
1594
|
-
/** Map of textures to be bound to this shader */
|
|
1595
1012
|
uniformTextures = {};
|
|
1596
|
-
/** Number of texture units reserved by this custom shader */
|
|
1597
1013
|
usedTextureUnitNum = 0;
|
|
1598
|
-
/** Padding in pixels this shader needs beyond the sprite bounds (for outline/glow effects) */
|
|
1599
1014
|
padding = 0;
|
|
1600
1015
|
rapid;
|
|
1601
1016
|
constructor(t, e, r, i = 0, s) {
|
|
1602
1017
|
this.vs = e, this.fs = r, this.rapid = t, this.uniforms = s ?? {}, this.usedTextureUnitNum = i;
|
|
1603
1018
|
}
|
|
1604
|
-
/**
|
|
1605
|
-
* Updates uniform values or textures for the custom shader.
|
|
1606
|
-
* @param uniforms Map of uniform values or WebGL textures to apply.
|
|
1607
|
-
*/
|
|
1608
1019
|
setUniforms(t) {
|
|
1609
1020
|
this.rapid.flush();
|
|
1610
1021
|
const e = {}, r = {};
|
|
@@ -1614,34 +1025,16 @@ class ft {
|
|
|
1614
1025
|
for (const i of this.glshader.keys())
|
|
1615
1026
|
this.uniformDirty.add(i);
|
|
1616
1027
|
}
|
|
1617
|
-
/**
|
|
1618
|
-
* Sets the padding (in pixels) for this shader and propagates to all compiled GLShaders.
|
|
1619
|
-
* Must be called before the first draw call if set after construction.
|
|
1620
|
-
* @param pixels - Number of pixels to expand the quad on each side.
|
|
1621
|
-
*/
|
|
1622
1028
|
setPadding(t) {
|
|
1623
1029
|
this.padding = t;
|
|
1624
1030
|
for (const e of this.glshader.values())
|
|
1625
1031
|
e.padding = t;
|
|
1626
1032
|
return this;
|
|
1627
1033
|
}
|
|
1628
|
-
/**
|
|
1629
|
-
* Applies current uniforms and texture unit mappings to the region-specific shader.
|
|
1630
|
-
* @param key The region key.
|
|
1631
|
-
* @param textureUniforms Map of texture uniform names to assigned texture unit indices.
|
|
1632
|
-
*/
|
|
1633
1034
|
applyUniform(t, e) {
|
|
1634
1035
|
const r = this.glshader.get(t);
|
|
1635
1036
|
r && (Object.keys(e).length > 0 && r.setUniforms(e), this.uniformDirty.has(t) && (r.setUniforms(this.uniforms), this.uniformDirty.delete(t)));
|
|
1636
1037
|
}
|
|
1637
|
-
/**
|
|
1638
|
-
* Retrieves or compiles a customized GLShader for a specific region.
|
|
1639
|
-
* @param region The Region requesting the shader.
|
|
1640
|
-
* @param key The region key.
|
|
1641
|
-
* @param baseVS The base vertex shader template.
|
|
1642
|
-
* @param baseFS The base fragment shader template.
|
|
1643
|
-
* @returns The combined and compiled GLShader.
|
|
1644
|
-
*/
|
|
1645
1038
|
getGLShader(t, e, r, i) {
|
|
1646
1039
|
if (this.glshader.has(e))
|
|
1647
1040
|
return this.glshader.get(e);
|
|
@@ -1655,7 +1048,7 @@ class ft {
|
|
|
1655
1048
|
this.glshader.forEach((t) => t.destroy());
|
|
1656
1049
|
}
|
|
1657
1050
|
}
|
|
1658
|
-
class
|
|
1051
|
+
class Et {
|
|
1659
1052
|
constructor(t) {
|
|
1660
1053
|
this.rapid = t, this.gl = t.gl, this.maxTextureUnits = t.maxTextureUnits, this.matrixStore = t.matrix;
|
|
1661
1054
|
}
|
|
@@ -1698,7 +1091,7 @@ class At {
|
|
|
1698
1091
|
return i == -1 ? (this.freeTextureUnitNum === 0 && this.flush(), this.usedTextures.push(t), this.usedTexturePadding.push(e), this.usedTexturePadding.push(r), this.usedTextures.length - 1) : i;
|
|
1699
1092
|
}
|
|
1700
1093
|
createShader(t, e) {
|
|
1701
|
-
return new
|
|
1094
|
+
return new Tt(this.gl, t, e);
|
|
1702
1095
|
}
|
|
1703
1096
|
createCustomShader(t) {
|
|
1704
1097
|
return t.getGLShader(this, this.KEY, this.vs, this.fs);
|
|
@@ -1706,22 +1099,17 @@ class At {
|
|
|
1706
1099
|
getCustomShader(t) {
|
|
1707
1100
|
if (!t)
|
|
1708
1101
|
return this.defaultShader;
|
|
1709
|
-
if (t instanceof
|
|
1102
|
+
if (t instanceof ut) {
|
|
1710
1103
|
const e = this.createCustomShader(t);
|
|
1711
1104
|
return e ?? this.defaultShader;
|
|
1712
1105
|
}
|
|
1713
1106
|
return t;
|
|
1714
1107
|
}
|
|
1715
|
-
/**
|
|
1716
|
-
* Checks if the given shader is the same as the currently bound shader.
|
|
1717
|
-
* @param customShader Optional custom shader.
|
|
1718
|
-
* @returns True if already bound, otherwise false.
|
|
1719
|
-
*/
|
|
1720
1108
|
isSameShader(t) {
|
|
1721
1109
|
return this.isDefaultShader && !t ? !0 : this.getCustomShader(t) == this.currentShader;
|
|
1722
1110
|
}
|
|
1723
1111
|
enter(t) {
|
|
1724
|
-
this.resetRender(), this.currentShader = this.getCustomShader(t), t instanceof
|
|
1112
|
+
this.resetRender(), this.currentShader = this.getCustomShader(t), t instanceof ut ? (this.customShader = t, this.customShaderUsedTextureNum = t.usedTextureUnitNum) : (this.customShader = null, this.customShaderUsedTextureNum = 0), this.isDefaultShader = this.currentShader == this.defaultShader, this.currentShader.use(), this.currentShader.setUniform("u_projection", this.rapid.projection);
|
|
1725
1113
|
}
|
|
1726
1114
|
exit() {
|
|
1727
1115
|
this.hasPendingContent() && this.flush(), this.gl.bindVertexArray(null);
|
|
@@ -1758,7 +1146,7 @@ class At {
|
|
|
1758
1146
|
return !1;
|
|
1759
1147
|
}
|
|
1760
1148
|
}
|
|
1761
|
-
const
|
|
1149
|
+
const Z = `#version 300 es\r
|
|
1762
1150
|
precision highp float;\r
|
|
1763
1151
|
\r
|
|
1764
1152
|
// per-vertex\r
|
|
@@ -1806,7 +1194,7 @@ void main(void) {\r
|
|
|
1806
1194
|
\r
|
|
1807
1195
|
gl_Position = u_projection * position;\r
|
|
1808
1196
|
}\r
|
|
1809
|
-
`,
|
|
1197
|
+
`, lt = `#version 300 es\r
|
|
1810
1198
|
precision mediump float;\r
|
|
1811
1199
|
\r
|
|
1812
1200
|
uniform sampler2D uTextures[%TEXTURE_NUM%];\r
|
|
@@ -1855,8 +1243,8 @@ void main(void) {\r
|
|
|
1855
1243
|
\r
|
|
1856
1244
|
// CUSTOM_CODE_CALL\r
|
|
1857
1245
|
}\r
|
|
1858
|
-
`, $ = 48,
|
|
1859
|
-
class ot extends
|
|
1246
|
+
`, $ = 48, Dt = new Float32Array([0, 0, 1, 0, 0, 1, 1, 1]);
|
|
1247
|
+
class ot extends Et {
|
|
1860
1248
|
instanceBuffer;
|
|
1861
1249
|
quadBuffer;
|
|
1862
1250
|
instanceCount = 0;
|
|
@@ -1868,12 +1256,12 @@ class ot extends At {
|
|
|
1868
1256
|
}
|
|
1869
1257
|
createBuffer() {
|
|
1870
1258
|
const t = this.gl;
|
|
1871
|
-
this.quadBuffer = new it(t,
|
|
1872
|
-
for (const e of
|
|
1873
|
-
this.quadBuffer.makeDirty(), this.quadBuffer.bufferData(), this.instanceBuffer = new it(t,
|
|
1259
|
+
this.quadBuffer = new it(t, S.Float32, t.ARRAY_BUFFER, t.STATIC_DRAW), this.quadBuffer.bindBuffer();
|
|
1260
|
+
for (const e of Dt) this.quadBuffer.pushFloat32(e);
|
|
1261
|
+
this.quadBuffer.makeDirty(), this.quadBuffer.bufferData(), this.instanceBuffer = new it(t, S.Uint32, t.ARRAY_BUFFER, t.DYNAMIC_DRAW);
|
|
1874
1262
|
}
|
|
1875
1263
|
createDefaultShader() {
|
|
1876
|
-
const t = this.rapid, e =
|
|
1264
|
+
const t = this.rapid, e = B(lt, t.maxTextureUnits), r = B(Z, t.maxTextureUnits);
|
|
1877
1265
|
return this.vs = r, this.fs = e, this.defaultShader = this.createShader(r, e), this.defaultShader;
|
|
1878
1266
|
}
|
|
1879
1267
|
createShader(t, e) {
|
|
@@ -1889,22 +1277,10 @@ class ot extends At {
|
|
|
1889
1277
|
]), r.unbindVAO(), this.currentShader && this.currentShader.use(), r;
|
|
1890
1278
|
}
|
|
1891
1279
|
createCustomShader(t) {
|
|
1892
|
-
const e =
|
|
1280
|
+
const e = B(lt, this.rapid.maxTextureUnits - t.usedTextureUnitNum), r = B(Z, this.rapid.maxTextureUnits - t.usedTextureUnitNum);
|
|
1893
1281
|
return t.getGLShader(this, this.KEY, r, e);
|
|
1894
1282
|
}
|
|
1895
|
-
|
|
1896
|
-
* Draws a textured sprite via instanced rendering to significantly improve performance.
|
|
1897
|
-
* @param texture The WebGLTexture to map.
|
|
1898
|
-
* @param matrixIndex The index for the transform matrix in MatrixStore.
|
|
1899
|
-
* @param width Render width.
|
|
1900
|
-
* @param height Render height.
|
|
1901
|
-
* @param u0 Left UV mapped coordinate (default 0).
|
|
1902
|
-
* @param v0 Top UV mapped coordinate (default 0).
|
|
1903
|
-
* @param u1 Right UV mapped coordinate (default 1).
|
|
1904
|
-
* @param v1 Bottom UV mapped coordinate (default 1).
|
|
1905
|
-
* @param color The tint color as packed ABGR uniform uint32 (default 0xFFFFFFFF).
|
|
1906
|
-
*/
|
|
1907
|
-
drawSprite(t, e, r = 0, i = 0, s = 1, a = 1, o = 4294967295, h = 0, c = 0, u = !1, l = !1, d = !1) {
|
|
1283
|
+
drawSprite(t, e, r = 0, i = 0, s = 1, a = 1, h = 4294967295, o = 0, c = 0, u = !1, l = !1, d = !1) {
|
|
1908
1284
|
const f = e * 6, m = this.matrixStore.data;
|
|
1909
1285
|
this.drawSpriteAffine(
|
|
1910
1286
|
t,
|
|
@@ -1918,31 +1294,31 @@ class ot extends At {
|
|
|
1918
1294
|
i,
|
|
1919
1295
|
s,
|
|
1920
1296
|
a,
|
|
1921
|
-
o,
|
|
1922
1297
|
h,
|
|
1298
|
+
o,
|
|
1923
1299
|
c,
|
|
1924
1300
|
u,
|
|
1925
1301
|
l,
|
|
1926
1302
|
d
|
|
1927
1303
|
);
|
|
1928
1304
|
}
|
|
1929
|
-
drawSpriteAffine(t, e, r, i, s, a,
|
|
1930
|
-
const
|
|
1305
|
+
drawSpriteAffine(t, e, r, i, s, a, h, o = 0, c = 0, u = 1, l = 1, d = 4294967295, f = 0, m = 0, g = !1, v = !1, y = !1) {
|
|
1306
|
+
const w = t.base, M = t.rawWidth, _ = t.rawHeight, P = t.offsetX, O = t.offsetY, W = this.useTexture(
|
|
1931
1307
|
t.glTexture,
|
|
1932
|
-
f /
|
|
1933
|
-
m /
|
|
1934
|
-
),
|
|
1935
|
-
|
|
1936
|
-
const
|
|
1937
|
-
|
|
1938
|
-
const
|
|
1939
|
-
|
|
1308
|
+
f / w.width,
|
|
1309
|
+
m / w.height
|
|
1310
|
+
), b = this.instanceBuffer, R = b.usedElemNum;
|
|
1311
|
+
b.resize(12);
|
|
1312
|
+
const C = b.float32, D = b.uint32, k = y ? _ : M, H = y ? M : _, I = k + 2 * f, F = H + 2 * m, Y = P - f, z = O - m, E = this.localSpriteMatrix;
|
|
1313
|
+
y ? (E[0] = 0, E[1] = v ? F : -F, E[2] = g ? -I : I, E[3] = 0, E[4] = Y + (g ? I : 0), E[5] = z + (v ? 0 : F)) : (E[0] = g ? -I : I, E[1] = 0, E[2] = 0, E[3] = v ? -F : F, E[4] = Y + (g ? I : 0), E[5] = z + (v ? F : 0));
|
|
1314
|
+
const U = this.worldSpriteMatrix;
|
|
1315
|
+
U[0] = e * E[0] + i * E[1], U[1] = r * E[0] + s * E[1], U[2] = e * E[2] + i * E[3], U[3] = r * E[2] + s * E[3], U[4] = a + e * E[4] + i * E[5], U[5] = h + r * E[4] + s * E[5], C[R + 6] = o, C[R + 7] = c, C[R + 8] = u, C[R + 9] = l, D[R + 10] = d, D[R + 11] = W, this.rapid.roundPixels && (U[4] = Math.round(U[4]), U[5] = Math.round(U[5])), C[R] = U[0], C[R + 1] = U[2], C[R + 2] = U[4], C[R + 3] = U[1], C[R + 4] = U[3], C[R + 5] = U[5], b.usedElemNum += 12, b.makeDirty(), this.instanceCount++;
|
|
1940
1316
|
}
|
|
1941
1317
|
render() {
|
|
1942
1318
|
if (this.instanceCount === 0) return;
|
|
1943
1319
|
this.prepareRender();
|
|
1944
1320
|
const t = this.gl, e = this.currentShader;
|
|
1945
|
-
this.instanceBuffer.bindBuffer(), this.instanceBuffer.bufferData(), e.bindVAO(),
|
|
1321
|
+
this.instanceBuffer.bindBuffer(), this.instanceBuffer.bufferData(), e.bindVAO(), yt(t, t.TRIANGLE_STRIP, 0, 4, this.instanceCount), this.rapid.drawcallCount++;
|
|
1946
1322
|
}
|
|
1947
1323
|
resetRender() {
|
|
1948
1324
|
super.resetRender(), this.instanceBuffer.clear(), this.instanceCount = 0;
|
|
@@ -1951,7 +1327,7 @@ class ot extends At {
|
|
|
1951
1327
|
return this.instanceCount > 0;
|
|
1952
1328
|
}
|
|
1953
1329
|
}
|
|
1954
|
-
const
|
|
1330
|
+
const kt = `#version 300 es\r
|
|
1955
1331
|
precision highp float;\r
|
|
1956
1332
|
\r
|
|
1957
1333
|
in vec2 aPosition;\r
|
|
@@ -1982,7 +1358,7 @@ void main(void) {\r
|
|
|
1982
1358
|
// CUSTOM_CODE_CALL\r
|
|
1983
1359
|
gl_Position = u_projection * position;\r
|
|
1984
1360
|
}\r
|
|
1985
|
-
`,
|
|
1361
|
+
`, Ht = `#version 300 es\r
|
|
1986
1362
|
precision mediump float;\r
|
|
1987
1363
|
\r
|
|
1988
1364
|
in vec4 vColor;\r
|
|
@@ -2028,7 +1404,7 @@ void main(void) {\r
|
|
|
2028
1404
|
fragColor = sampleTexture(vRegion) * vColor;\r
|
|
2029
1405
|
// CUSTOM_CODE_CALL\r
|
|
2030
1406
|
}\r
|
|
2031
|
-
`,
|
|
1407
|
+
`, Gt = `#version 300 es\r
|
|
2032
1408
|
precision highp float;\r
|
|
2033
1409
|
\r
|
|
2034
1410
|
in vec2 aPosition;\r
|
|
@@ -2051,7 +1427,7 @@ void main(void) {\r
|
|
|
2051
1427
|
);\r
|
|
2052
1428
|
gl_Position = u_projection * position;\r
|
|
2053
1429
|
}\r
|
|
2054
|
-
`,
|
|
1430
|
+
`, Vt = `#version 300 es\r
|
|
2055
1431
|
precision mediump float;\r
|
|
2056
1432
|
\r
|
|
2057
1433
|
in vec2 vRegion;\r
|
|
@@ -2071,8 +1447,8 @@ void main(void) {\r
|
|
|
2071
1447
|
discard;\r
|
|
2072
1448
|
}\r
|
|
2073
1449
|
}\r
|
|
2074
|
-
`,
|
|
2075
|
-
class
|
|
1450
|
+
`, j = 20;
|
|
1451
|
+
class Yt extends Et {
|
|
2076
1452
|
vertexBuffer;
|
|
2077
1453
|
vertexCount = 0;
|
|
2078
1454
|
matrixIndex = -1;
|
|
@@ -2085,50 +1461,33 @@ class Xt extends At {
|
|
|
2085
1461
|
}
|
|
2086
1462
|
createBuffer() {
|
|
2087
1463
|
const t = this.gl;
|
|
2088
|
-
this.vertexBuffer = new it(t,
|
|
1464
|
+
this.vertexBuffer = new it(t, S.Float32, t.ARRAY_BUFFER, t.DYNAMIC_DRAW), this.maskShader = this.createMaskShader(Gt, Vt);
|
|
2089
1465
|
}
|
|
2090
1466
|
createDefaultShader() {
|
|
2091
|
-
return this.vs =
|
|
1467
|
+
return this.vs = kt, this.fs = Ht, this.defaultShader = this.createShader(this.vs, this.fs), this.defaultShader;
|
|
2092
1468
|
}
|
|
2093
1469
|
createMaskShader(t, e) {
|
|
2094
|
-
const r = this.gl, i = new
|
|
1470
|
+
const r = this.gl, i = new Tt(r, t, e);
|
|
2095
1471
|
return i.use(), i.bindVAO(), this.vertexBuffer.bindBuffer(), i.setAttributes([
|
|
2096
|
-
{ name: "aPosition", size: 2, type: r.FLOAT, stride:
|
|
2097
|
-
{ name: "aUV", size: 2, type: r.FLOAT, stride:
|
|
1472
|
+
{ name: "aPosition", size: 2, type: r.FLOAT, stride: j - 4, offset: 0, divisor: 0 },
|
|
1473
|
+
{ name: "aUV", size: 2, type: r.FLOAT, stride: j - 4, offset: 8, divisor: 0 }
|
|
2098
1474
|
]), i.unbindVAO(), this.currentShader && this.currentShader.use(), i;
|
|
2099
1475
|
}
|
|
2100
1476
|
createShader(t, e) {
|
|
2101
1477
|
const r = this.gl, i = super.createShader(t, e);
|
|
2102
1478
|
return i.use(), i.bindVAO(), this.vertexBuffer.bindBuffer(), i.setAttributes([
|
|
2103
|
-
{ name: "aPosition", size: 2, type: r.FLOAT, stride:
|
|
2104
|
-
{ name: "aColor", size: 4, type: r.UNSIGNED_BYTE, normalized: !0, stride:
|
|
2105
|
-
{ name: "aUV", size: 2, type: r.FLOAT, stride:
|
|
1479
|
+
{ name: "aPosition", size: 2, type: r.FLOAT, stride: j, offset: 0, divisor: 0 },
|
|
1480
|
+
{ name: "aColor", size: 4, type: r.UNSIGNED_BYTE, normalized: !0, stride: j, offset: 8, divisor: 0 },
|
|
1481
|
+
{ name: "aUV", size: 2, type: r.FLOAT, stride: j, offset: 12, divisor: 0 }
|
|
2106
1482
|
]), i.unbindVAO(), this.currentShader && this.currentShader.use(), i;
|
|
2107
1483
|
}
|
|
2108
|
-
/**
|
|
2109
|
-
* Begins a new polygon drawing sequence. Must be followed by addVertex() calls and endGraphic().
|
|
2110
|
-
* @param matrixIndex The index targeting a specific transform matrix in the MatrixStore.
|
|
2111
|
-
* @param drawMode The WebGL drawing primitive mode (e.g., gl.TRIANGLES).
|
|
2112
|
-
* @param texture Optional texture to apply over the polygon.
|
|
2113
|
-
*/
|
|
2114
1484
|
startGraphic(t, e = this.gl.TRIANGLES, r) {
|
|
2115
1485
|
this.vertexBuffer.clear(), this.vertexCount = 0, this.matrixIndex = t, this.drawMode = e, this.texture = r, this.texture?.glTexture && this.useTexture(this.texture.glTexture, 0, 0);
|
|
2116
1486
|
}
|
|
2117
|
-
/**
|
|
2118
|
-
* Adds a vertex to the current polygon. Local coordinates and color settings.
|
|
2119
|
-
* @param x Local X coordinate.
|
|
2120
|
-
* @param y Local Y coordinate.
|
|
2121
|
-
* @param u UV mapped X value (0-1, default 0).
|
|
2122
|
-
* @param v UV mapped Y value (0-1, default 0).
|
|
2123
|
-
* @param color Pre-multiplied hex color combined using ABGR byte order (default 0xFFFFFFFF).
|
|
2124
|
-
*/
|
|
2125
1487
|
addVertex(t, e, r = 0, i = 0, s = 4294967295) {
|
|
2126
1488
|
const a = this.vertexBuffer;
|
|
2127
1489
|
a.pushFloat32(t), a.pushFloat32(e), this.currentShader != this.maskShader && a.pushUint32(s), a.pushFloat32(r), a.pushFloat32(i), this.vertexCount++, this.vertexBuffer.makeDirty();
|
|
2128
1490
|
}
|
|
2129
|
-
/**
|
|
2130
|
-
* Finishes the graphic construction and dispatches the rendering call immediately.
|
|
2131
|
-
*/
|
|
2132
1491
|
endGraphic() {
|
|
2133
1492
|
this.flush();
|
|
2134
1493
|
}
|
|
@@ -2167,15 +1526,9 @@ class p {
|
|
|
2167
1526
|
subtract(t) {
|
|
2168
1527
|
return new p(this.x - t.x, this.y - t.y);
|
|
2169
1528
|
}
|
|
2170
|
-
sub(t) {
|
|
2171
|
-
return new p(this.x - t.x, this.y - t.y);
|
|
2172
|
-
}
|
|
2173
1529
|
multiply(t) {
|
|
2174
1530
|
return t instanceof p ? new p(this.x * t.x, this.y * t.y) : new p(this.x * t, this.y * t);
|
|
2175
1531
|
}
|
|
2176
|
-
mul(t) {
|
|
2177
|
-
return this.multiply(t);
|
|
2178
|
-
}
|
|
2179
1532
|
divide(t) {
|
|
2180
1533
|
return t instanceof p ? new p(this.x / t.x, this.y / t.y) : new p(this.x / t, this.y / t);
|
|
2181
1534
|
}
|
|
@@ -2195,9 +1548,6 @@ class p {
|
|
|
2195
1548
|
to(t) {
|
|
2196
1549
|
this.x = t.x, this.y = t.y;
|
|
2197
1550
|
}
|
|
2198
|
-
copy() {
|
|
2199
|
-
return new p(this.x, this.y);
|
|
2200
|
-
}
|
|
2201
1551
|
equals(t) {
|
|
2202
1552
|
return t.x == this.x && t.y == this.y;
|
|
2203
1553
|
}
|
|
@@ -2271,8 +1621,8 @@ class p {
|
|
|
2271
1621
|
return new p(Math.cos(t), Math.sin(t));
|
|
2272
1622
|
}
|
|
2273
1623
|
}
|
|
2274
|
-
const
|
|
2275
|
-
const [e, r, i, s, a,
|
|
1624
|
+
const Xt = (n, t) => {
|
|
1625
|
+
const [e, r, i, s, a, h] = t, o = new Float32Array([
|
|
2276
1626
|
e,
|
|
2277
1627
|
i,
|
|
2278
1628
|
0,
|
|
@@ -2286,12 +1636,12 @@ const jt = (n, t) => {
|
|
|
2286
1636
|
1,
|
|
2287
1637
|
0,
|
|
2288
1638
|
a,
|
|
2289
|
-
|
|
1639
|
+
h,
|
|
2290
1640
|
0,
|
|
2291
1641
|
1
|
|
2292
1642
|
]);
|
|
2293
|
-
return
|
|
2294
|
-
},
|
|
1643
|
+
return zt(o, n);
|
|
1644
|
+
}, zt = (n, t) => {
|
|
2295
1645
|
const e = new Float32Array(16);
|
|
2296
1646
|
for (let r = 0; r < 4; r++)
|
|
2297
1647
|
for (let i = 0; i < 4; i++) {
|
|
@@ -2302,75 +1652,75 @@ const jt = (n, t) => {
|
|
|
2302
1652
|
}
|
|
2303
1653
|
return e;
|
|
2304
1654
|
};
|
|
2305
|
-
var
|
|
2306
|
-
const rt = 10,
|
|
2307
|
-
const a = [],
|
|
1655
|
+
var $t = /* @__PURE__ */ ((n) => (n[n.STRETCH = 0] = "STRETCH", n[n.REPEAT = 1] = "REPEAT", n))($t || {});
|
|
1656
|
+
const rt = 10, dt = (n, t, e, r, i, s) => {
|
|
1657
|
+
const a = [], h = [], o = r ? Math.atan2(t.y, t.x) : Math.atan2(-t.y, -t.x), c = Math.PI, u = new p(t.y, -t.x);
|
|
2308
1658
|
for (let l = 0; l < rt; l++) {
|
|
2309
|
-
const d = l / rt, f = (l + 1) / rt, m =
|
|
2310
|
-
a.push(n),
|
|
1659
|
+
const d = l / rt, f = (l + 1) / rt, m = o + d * c, g = o + f * c, v = new p(Math.cos(m) * e, Math.sin(m) * e), y = new p(Math.cos(g) * e, Math.sin(g) * e);
|
|
1660
|
+
a.push(n), h.push(new p(i, 0.5)), a.push(n.add(v)), h.push(new p(i + v.dot(u) * s, 0.5 - 0.5 * v.dot(t) / e)), a.push(n.add(y)), h.push(new p(i + y.dot(u) * s, 0.5 - 0.5 * y.dot(t) / e));
|
|
2311
1661
|
}
|
|
2312
|
-
return { vertices: a, uv:
|
|
2313
|
-
},
|
|
1662
|
+
return { vertices: a, uv: h };
|
|
1663
|
+
}, jt = (n, t = !1) => {
|
|
2314
1664
|
const e = [];
|
|
2315
1665
|
if (n.length < 2 || t && n.length < 3) return { normals: e, length: 0 };
|
|
2316
1666
|
const r = 4, i = 1e-3, s = n.length;
|
|
2317
1667
|
let a = 0;
|
|
2318
1668
|
if (t)
|
|
2319
|
-
for (let
|
|
2320
|
-
const c = n[
|
|
1669
|
+
for (let o = 0; o < s; o++) {
|
|
1670
|
+
const c = n[o], u = n[(o + 1) % s];
|
|
2321
1671
|
a += c.distanceTo(u);
|
|
2322
1672
|
}
|
|
2323
1673
|
else
|
|
2324
|
-
for (let
|
|
2325
|
-
a += n[
|
|
2326
|
-
const
|
|
2327
|
-
const l = c.subtract(
|
|
1674
|
+
for (let o = 0; o < s - 1; o++)
|
|
1675
|
+
a += n[o].distanceTo(n[o + 1]);
|
|
1676
|
+
const h = (o, c, u) => {
|
|
1677
|
+
const l = c.subtract(o).normalize(), d = c.subtract(u).normalize(), f = d.dot(l);
|
|
2328
1678
|
if (f < -1 + i)
|
|
2329
1679
|
return { normal: l.perpendicular(), miters: 1 };
|
|
2330
1680
|
{
|
|
2331
1681
|
let m = d.add(l).normalize();
|
|
2332
1682
|
l.cross(d) < 0 && (m = m.multiply(-1));
|
|
2333
|
-
let
|
|
2334
|
-
return { normal: m, miters: Math.min(
|
|
1683
|
+
let g = 1 / Math.sqrt((1 - f) / 2);
|
|
1684
|
+
return { normal: m, miters: Math.min(g, r) };
|
|
2335
1685
|
}
|
|
2336
1686
|
};
|
|
2337
1687
|
if (t)
|
|
2338
|
-
for (let
|
|
2339
|
-
const c =
|
|
2340
|
-
e.push(
|
|
1688
|
+
for (let o = 0; o < s; o++) {
|
|
1689
|
+
const c = o === 0 ? n[s - 1] : n[o - 1], u = n[o], l = o === s - 1 ? n[0] : n[o + 1];
|
|
1690
|
+
e.push(h(c, u, l));
|
|
2341
1691
|
}
|
|
2342
1692
|
else
|
|
2343
|
-
for (let
|
|
2344
|
-
if (
|
|
1693
|
+
for (let o = 0; o < s; o++)
|
|
1694
|
+
if (o === 0) {
|
|
2345
1695
|
const c = n[1].subtract(n[0]).normalize();
|
|
2346
1696
|
e.push({ normal: c.perpendicular(), miters: 1 });
|
|
2347
|
-
} else if (
|
|
2348
|
-
const c = n[
|
|
1697
|
+
} else if (o === s - 1) {
|
|
1698
|
+
const c = n[o].subtract(n[o - 1]).normalize();
|
|
2349
1699
|
e.push({ normal: c.perpendicular(), miters: 1 });
|
|
2350
1700
|
} else
|
|
2351
|
-
e.push(
|
|
1701
|
+
e.push(h(n[o - 1], n[o], n[o + 1]));
|
|
2352
1702
|
return { normals: e, length: a };
|
|
2353
|
-
},
|
|
1703
|
+
}, Kt = (n) => {
|
|
2354
1704
|
const t = n.points;
|
|
2355
1705
|
if (t.length < 2) return { vertices: [], uv: [] };
|
|
2356
|
-
const { normals: e, length: r } =
|
|
1706
|
+
const { normals: e, length: r } = jt(t, n.closed), i = (n.width || 1) / 2, s = [], a = [], h = n.roundCap || !1, o = n.textureMode || 0;
|
|
2357
1707
|
let c = 0;
|
|
2358
1708
|
const u = n.texture?.rawWidth || 1, l = n.closed ? t.length : t.length - 1;
|
|
2359
1709
|
for (let d = 0; d < l; d++) {
|
|
2360
|
-
const f = t[d], m = e[d].normal,
|
|
2361
|
-
let
|
|
2362
|
-
|
|
2363
|
-
const
|
|
2364
|
-
s.push(
|
|
2365
|
-
}
|
|
2366
|
-
if (
|
|
2367
|
-
const d = t[0], f = e[0].normal, m =
|
|
2368
|
-
s.push(...
|
|
2369
|
-
const
|
|
2370
|
-
s.push(...
|
|
1710
|
+
const f = t[d], m = e[d].normal, g = e[d].miters, v = (d + 1) % t.length, y = t[v], w = e[v].normal, M = e[v].miters, _ = f.add(m.multiply(g * i)), P = f.subtract(m.multiply(g * i)), O = y.add(w.multiply(M * i)), W = y.subtract(w.multiply(M * i)), b = f.distanceTo(y);
|
|
1711
|
+
let R = 0, C = 0;
|
|
1712
|
+
o === 0 ? (R = c / r, C = (c + b) / r) : (R = c / u, C = R + b / u);
|
|
1713
|
+
const D = new p(R, 0), k = new p(R, 1), H = new p(C, 0), I = new p(C, 1);
|
|
1714
|
+
s.push(_), a.push(D), s.push(P), a.push(k), s.push(O), a.push(H), s.push(O), a.push(H), s.push(W), a.push(I), s.push(P), a.push(k), c += b;
|
|
1715
|
+
}
|
|
1716
|
+
if (h && !n.closed) {
|
|
1717
|
+
const d = t[0], f = e[0].normal, m = o === 0 ? r > 0 ? 1 / r : 0 : 1 / u, g = dt(d, f, i, !0, 0, m);
|
|
1718
|
+
s.push(...g.vertices), a.push(...g.uv);
|
|
1719
|
+
const v = t[t.length - 1], y = e[t.length - 1].normal, w = o === 0 ? 1 : c / u, M = o === 0 ? r > 0 ? 1 / r : 0 : 1 / u, _ = dt(v, y, i, !1, w, M);
|
|
1720
|
+
s.push(..._.vertices), a.push(..._.uv);
|
|
2371
1721
|
}
|
|
2372
1722
|
return { vertices: s, uv: a };
|
|
2373
|
-
},
|
|
1723
|
+
}, Q = (n, t, e, r) => {
|
|
2374
1724
|
if (t.customMatrix !== void 0)
|
|
2375
1725
|
return t.customMatrix;
|
|
2376
1726
|
if (t.modifyStack) {
|
|
@@ -2389,24 +1739,24 @@ const rt = 10, xt = (n, t, e, r, i, s) => {
|
|
|
2389
1739
|
i
|
|
2390
1740
|
), i;
|
|
2391
1741
|
}
|
|
2392
|
-
},
|
|
2393
|
-
const e =
|
|
1742
|
+
}, qt = (n, t) => t ? n ? t.premultipliedUint32 : t.uint32 : 4294967295, Qt = 2, Zt = (n, t) => {
|
|
1743
|
+
const e = Q(n, t, t.texture.rawWidth, t.texture.rawHeight), r = t.texture;
|
|
2394
1744
|
if (!r?.base || n.inCreateMask)
|
|
2395
1745
|
return;
|
|
2396
1746
|
const i = r.isAtlas ? n.atlasSpriteRegion : n.spriteRegion;
|
|
2397
1747
|
n.enterRegion(i, t.shader);
|
|
2398
|
-
let s = r.uvX, a = r.uvY,
|
|
1748
|
+
let s = r.uvX, a = r.uvY, h = r.uvW, o = r.uvH;
|
|
2399
1749
|
const c = !!t.flipX, u = !!t.flipY != !!r.flipY;
|
|
2400
1750
|
let l = t.padding ?? i.currentShader.padding;
|
|
2401
|
-
r.isAtlas && (l +=
|
|
2402
|
-
const d = s <=
|
|
1751
|
+
r.isAtlas && (l += Qt);
|
|
1752
|
+
const d = s <= h ? l : -l, f = a <= o ? l : -l;
|
|
2403
1753
|
i.drawSprite(
|
|
2404
1754
|
r,
|
|
2405
1755
|
e ?? t.customMatrix ?? n.matrixStack.curWorldM,
|
|
2406
1756
|
s,
|
|
2407
1757
|
a,
|
|
2408
|
-
o,
|
|
2409
1758
|
h,
|
|
1759
|
+
o,
|
|
2410
1760
|
n.getColorUint32(t.color),
|
|
2411
1761
|
d,
|
|
2412
1762
|
f,
|
|
@@ -2414,7 +1764,7 @@ const rt = 10, xt = (n, t, e, r, i, s) => {
|
|
|
2414
1764
|
u,
|
|
2415
1765
|
r.isRotated
|
|
2416
1766
|
);
|
|
2417
|
-
},
|
|
1767
|
+
}, Jt = (n, t) => {
|
|
2418
1768
|
const e = n.particleRegion;
|
|
2419
1769
|
n.enterRegion(e, t.shader);
|
|
2420
1770
|
const r = t.texture, i = t.count ?? t.x.length, s = t.color;
|
|
@@ -2440,9 +1790,9 @@ const rt = 10, xt = (n, t, e, r, i, s) => {
|
|
|
2440
1790
|
t.reverseOrder,
|
|
2441
1791
|
t.customMatrix
|
|
2442
1792
|
);
|
|
2443
|
-
},
|
|
1793
|
+
}, Rt = (n, t) => {
|
|
2444
1794
|
if (t.points.length === 0) return;
|
|
2445
|
-
const e =
|
|
1795
|
+
const e = Q(n, t, 0, 0);
|
|
2446
1796
|
n.startGraphic(
|
|
2447
1797
|
t.drawMode ?? n.gl.TRIANGLES,
|
|
2448
1798
|
t.texture,
|
|
@@ -2460,18 +1810,18 @@ const rt = 10, xt = (n, t, e, r, i, s) => {
|
|
|
2460
1810
|
);
|
|
2461
1811
|
}
|
|
2462
1812
|
n.endGraphic();
|
|
2463
|
-
},
|
|
1813
|
+
}, te = (n, t) => {
|
|
2464
1814
|
if (n.inCreateMask)
|
|
2465
1815
|
return;
|
|
2466
|
-
const { vertices: e, uv: r } =
|
|
2467
|
-
|
|
1816
|
+
const { vertices: e, uv: r } = Kt(t);
|
|
1817
|
+
Rt(n, {
|
|
2468
1818
|
...t,
|
|
2469
1819
|
points: e,
|
|
2470
1820
|
uv: r,
|
|
2471
1821
|
drawMode: n.gl.TRIANGLES
|
|
2472
1822
|
});
|
|
2473
|
-
},
|
|
2474
|
-
const e =
|
|
1823
|
+
}, ee = (n, t) => {
|
|
1824
|
+
const e = Q(
|
|
2475
1825
|
n,
|
|
2476
1826
|
t,
|
|
2477
1827
|
t.texture.rawWidth,
|
|
@@ -2482,16 +1832,16 @@ const rt = 10, xt = (n, t, e, r, i, s) => {
|
|
|
2482
1832
|
t.texture,
|
|
2483
1833
|
e ?? t.customMatrix
|
|
2484
1834
|
), n.addRectVertex(t.texture.rawWidth, t.texture.rawHeight), n.endGraphic();
|
|
2485
|
-
},
|
|
2486
|
-
const e =
|
|
1835
|
+
}, re = (n, t) => {
|
|
1836
|
+
const e = Q(n, t, t.width, t.height);
|
|
2487
1837
|
n.startGraphic(
|
|
2488
1838
|
n.gl.TRIANGLE_FAN,
|
|
2489
1839
|
t.texture,
|
|
2490
1840
|
t.shader,
|
|
2491
1841
|
e ?? t.customMatrix
|
|
2492
1842
|
), n.addRectVertex(t.width, t.height, t.color), n.endGraphic();
|
|
2493
|
-
},
|
|
2494
|
-
const e = t.segments ?? 32, r =
|
|
1843
|
+
}, ie = (n, t) => {
|
|
1844
|
+
const e = t.segments ?? 32, r = Q(n, t, 0, 0);
|
|
2495
1845
|
n.startGraphic(
|
|
2496
1846
|
n.gl.TRIANGLE_FAN,
|
|
2497
1847
|
void 0,
|
|
@@ -2500,7 +1850,7 @@ const rt = 10, xt = (n, t, e, r, i, s) => {
|
|
|
2500
1850
|
);
|
|
2501
1851
|
const i = n.getColorUint32(t.color);
|
|
2502
1852
|
n.addGraphicVertex(0, 0, 0.5, 0.5, i), n.addCircleVertex(t.radius, t.color, e), n.addGraphicVertex(t.radius, 0, 1, 0.5, i), n.endGraphic();
|
|
2503
|
-
},
|
|
1853
|
+
}, ft = `#version 300 es\r
|
|
2504
1854
|
precision mediump float;\r
|
|
2505
1855
|
\r
|
|
2506
1856
|
uniform sampler2D uTextures[%TEXTURE_NUM%];\r
|
|
@@ -2550,21 +1900,21 @@ void main(void) {\r
|
|
|
2550
1900
|
// CUSTOM_CODE_CALL\r
|
|
2551
1901
|
}\r
|
|
2552
1902
|
`;
|
|
2553
|
-
class
|
|
1903
|
+
class se extends ot {
|
|
2554
1904
|
KEY = "AtlasSprite";
|
|
2555
1905
|
constructor(t) {
|
|
2556
1906
|
super(t);
|
|
2557
1907
|
}
|
|
2558
1908
|
createCustomShader(t) {
|
|
2559
|
-
const e =
|
|
1909
|
+
const e = B(ft, this.rapid.maxTextureUnits - t.usedTextureUnitNum), r = B(Z, this.rapid.maxTextureUnits - t.usedTextureUnitNum);
|
|
2560
1910
|
return t.getGLShader(this, this.KEY, r, e);
|
|
2561
1911
|
}
|
|
2562
1912
|
createDefaultShader() {
|
|
2563
|
-
const t = this.rapid, e =
|
|
1913
|
+
const t = this.rapid, e = B(ft, t.maxTextureUnits), r = B(Z, t.maxTextureUnits);
|
|
2564
1914
|
return this.vs = r, this.fs = e, this.defaultShader = this.createShader(r, e), this.defaultShader;
|
|
2565
1915
|
}
|
|
2566
1916
|
}
|
|
2567
|
-
const
|
|
1917
|
+
const mt = `#version 300 es\r
|
|
2568
1918
|
precision highp float;\r
|
|
2569
1919
|
\r
|
|
2570
1920
|
// per-vertex\r
|
|
@@ -2605,7 +1955,7 @@ void main(void) {\r
|
|
|
2605
1955
|
\r
|
|
2606
1956
|
gl_Position = u_projection * vec4(v, 0.0, 1.0);\r
|
|
2607
1957
|
}\r
|
|
2608
|
-
`,
|
|
1958
|
+
`, xt = `#version 300 es\r
|
|
2609
1959
|
precision mediump float;\r
|
|
2610
1960
|
\r
|
|
2611
1961
|
uniform sampler2D uTexture;\r
|
|
@@ -2621,19 +1971,20 @@ void main(void) {\r
|
|
|
2621
1971
|
\r
|
|
2622
1972
|
// CUSTOM_CODE_CALL\r
|
|
2623
1973
|
}\r
|
|
2624
|
-
`,
|
|
2625
|
-
class
|
|
1974
|
+
`, G = 48, ne = G / 4;
|
|
1975
|
+
class ae extends ot {
|
|
2626
1976
|
KEY = "ParticleSprite";
|
|
2627
1977
|
texture;
|
|
2628
1978
|
customMatrix;
|
|
1979
|
+
particleLoopCache = /* @__PURE__ */ new Map();
|
|
2629
1980
|
constructor(t) {
|
|
2630
1981
|
super(t);
|
|
2631
1982
|
}
|
|
2632
1983
|
createCustomShader(t) {
|
|
2633
|
-
return t.getGLShader(this, this.KEY,
|
|
1984
|
+
return t.getGLShader(this, this.KEY, mt, xt);
|
|
2634
1985
|
}
|
|
2635
1986
|
createDefaultShader() {
|
|
2636
|
-
const t =
|
|
1987
|
+
const t = xt, e = mt;
|
|
2637
1988
|
return this.vs = e, this.fs = t, this.defaultShader = this.createShader(e, t), this.defaultShader;
|
|
2638
1989
|
}
|
|
2639
1990
|
enter(t) {
|
|
@@ -2642,52 +1993,113 @@ class he extends ot {
|
|
|
2642
1993
|
createShader(t, e) {
|
|
2643
1994
|
const r = super.createShader(t, e);
|
|
2644
1995
|
return r.use(), r.bindVAO(), this.instanceBuffer.bindBuffer(), r.setAttributes([
|
|
2645
|
-
{ name: "aPosition", size: 2, stride:
|
|
2646
|
-
{ name: "aScale", size: 2, stride:
|
|
2647
|
-
{ name: "aRotation", size: 1, stride:
|
|
2648
|
-
{ name: "aUVRect", size: 4, stride:
|
|
2649
|
-
{ name: "aColor", size: 4, type: at, normalized: !0, stride:
|
|
2650
|
-
{ name: "aOrigin", size: 2, stride:
|
|
1996
|
+
{ name: "aPosition", size: 2, stride: G, offset: 0, divisor: 1 },
|
|
1997
|
+
{ name: "aScale", size: 2, stride: G, offset: 8, divisor: 1 },
|
|
1998
|
+
{ name: "aRotation", size: 1, stride: G, offset: 16, divisor: 1 },
|
|
1999
|
+
{ name: "aUVRect", size: 4, stride: G, offset: 20, divisor: 1 },
|
|
2000
|
+
{ name: "aColor", size: 4, type: at, normalized: !0, stride: G, offset: 36, divisor: 1 },
|
|
2001
|
+
{ name: "aOrigin", size: 2, stride: G, offset: 40, divisor: 1 }
|
|
2651
2002
|
]), this.quadBuffer.bindBuffer(), r.setAttributes([
|
|
2652
2003
|
{ name: "aVertex", size: 2, stride: 8, offset: 0, divisor: 0 }
|
|
2653
2004
|
]), r.unbindVAO(), this.currentShader && this.currentShader.use(), r;
|
|
2654
2005
|
}
|
|
2655
|
-
drawParticles(t, e, r, i = 0, s = 4294967295, a,
|
|
2006
|
+
drawParticles(t, e, r, i = 0, s = 4294967295, a, h = 1, o = 1, c = 0, u = 0, l = 1, d = 1, f = !1, m = !1, g = !1, v = 0.5, y = 0.5, w, M = !1, _) {
|
|
2656
2007
|
if (!t.glTexture || a <= 0) return;
|
|
2657
|
-
|
|
2658
|
-
const
|
|
2659
|
-
let
|
|
2660
|
-
|
|
2661
|
-
let
|
|
2662
|
-
|
|
2663
|
-
let
|
|
2664
|
-
|
|
2665
|
-
|
|
2666
|
-
|
|
2667
|
-
|
|
2668
|
-
|
|
2669
|
-
|
|
2670
|
-
|
|
2671
|
-
|
|
2672
|
-
|
|
2673
|
-
|
|
2674
|
-
|
|
2675
|
-
|
|
2676
|
-
|
|
2677
|
-
|
|
2678
|
-
|
|
2679
|
-
|
|
2680
|
-
|
|
2681
|
-
|
|
2682
|
-
|
|
2683
|
-
|
|
2684
|
-
|
|
2685
|
-
|
|
2686
|
-
|
|
2687
|
-
|
|
2688
|
-
|
|
2689
|
-
|
|
2690
|
-
|
|
2008
|
+
this.texture && t !== this.texture && this.flush();
|
|
2009
|
+
const P = typeof h == "number", O = typeof o == "number", W = typeof i == "number", b = typeof s == "number", R = typeof c == "number", C = !b && typeof s[0] == "number", D = t.uvW - t.uvX, k = t.uvH - t.uvY, H = D === 0 ? 0 : 1 / D, I = k === 0 ? 0 : 1 / k;
|
|
2010
|
+
let F = t.rawWidth * (f ? -1 : 1);
|
|
2011
|
+
P && (F *= h);
|
|
2012
|
+
let Y = t.rawHeight * (m ? -1 : 1);
|
|
2013
|
+
O && (Y *= o), R && (F *= (l - c) * H, Y *= (d - u) * I);
|
|
2014
|
+
let z = g ? Math.PI / 2 : 0;
|
|
2015
|
+
W && (z += i);
|
|
2016
|
+
const E = s ?? 4294967295, U = this.getParticleLoop(
|
|
2017
|
+
P,
|
|
2018
|
+
O,
|
|
2019
|
+
W,
|
|
2020
|
+
R,
|
|
2021
|
+
b,
|
|
2022
|
+
C,
|
|
2023
|
+
M,
|
|
2024
|
+
w
|
|
2025
|
+
);
|
|
2026
|
+
this.texture || (this.texture = t, this.useTexture(t.glTexture, 0, 0));
|
|
2027
|
+
const tt = a, X = this.instanceBuffer;
|
|
2028
|
+
let et = X.usedElemNum;
|
|
2029
|
+
X.resize(tt * ne);
|
|
2030
|
+
const Mt = X.float32, St = X.uint32;
|
|
2031
|
+
et = U(
|
|
2032
|
+
e,
|
|
2033
|
+
r,
|
|
2034
|
+
h,
|
|
2035
|
+
o,
|
|
2036
|
+
i,
|
|
2037
|
+
c,
|
|
2038
|
+
u,
|
|
2039
|
+
l,
|
|
2040
|
+
d,
|
|
2041
|
+
s,
|
|
2042
|
+
Mt,
|
|
2043
|
+
St,
|
|
2044
|
+
F,
|
|
2045
|
+
Y,
|
|
2046
|
+
H,
|
|
2047
|
+
I,
|
|
2048
|
+
z,
|
|
2049
|
+
E,
|
|
2050
|
+
v,
|
|
2051
|
+
y,
|
|
2052
|
+
a,
|
|
2053
|
+
tt,
|
|
2054
|
+
et
|
|
2055
|
+
), X.usedElemNum = et, X.makeDirty(), this.instanceCount += tt, this.customMatrix = _, this.flush();
|
|
2056
|
+
}
|
|
2057
|
+
getParticleLoop(t, e, r, i, s, a, h, o) {
|
|
2058
|
+
const c = [...arguments].join("_");
|
|
2059
|
+
if (this.particleLoopCache.has(c))
|
|
2060
|
+
return this.particleLoopCache.get(c);
|
|
2061
|
+
let u = `
|
|
2062
|
+
return function( x, y, scaleX, scaleY, rotation, u0, v0, u1, v1, color, f32, u32, rawWidth, rawHeight, uv2texW, uv2texH, rotationOffset, staticColor, originX, originY, count, batchCount, index ) {
|
|
2063
|
+
${t && i ? "const baseSx = rawWidth;" : ""}
|
|
2064
|
+
${e && i ? "const baseSy = rawHeight;" : ""}
|
|
2065
|
+
|
|
2066
|
+
const endIdx = index + batchCount * 12;
|
|
2067
|
+
let idx = index;
|
|
2068
|
+
if (endIdx > f32.length) return index;
|
|
2069
|
+
|
|
2070
|
+
${h ? "for (let src = count - 1; idx < endIdx; src--, idx += 12) {" : "for (let src = 0; idx < endIdx; src++, idx += 12) {"}
|
|
2071
|
+
f32[idx] = x[src];
|
|
2072
|
+
f32[idx + 1] = y[src];
|
|
2073
|
+
|
|
2074
|
+
${i ? `
|
|
2075
|
+
f32[idx + 2] = ${t ? "baseSx" : "rawWidth * scaleX[src]"};
|
|
2076
|
+
f32[idx + 3] = ${e ? "baseSy" : "rawHeight * scaleY[src]"};
|
|
2077
|
+
f32[idx + 4] = ${r ? "rotationOffset" : "rotation[src] + rotationOffset"};
|
|
2078
|
+
f32[idx + 5] = u0;
|
|
2079
|
+
f32[idx + 6] = v0;
|
|
2080
|
+
f32[idx + 7] = u1;
|
|
2081
|
+
f32[idx + 8] = v1;
|
|
2082
|
+
` : `
|
|
2083
|
+
const cu0 = u0[src], cv0 = v0[src], cu1 = u1[src], cv1 = v1[src];
|
|
2084
|
+
f32[idx + 2] = (rawWidth * (cu1 - cu0) * uv2texW) ${t ? "" : "* scaleX[src]"};
|
|
2085
|
+
f32[idx + 3] = (rawHeight * (cv1 - cv0) * uv2texH) ${e ? "" : "* scaleY[src]"};
|
|
2086
|
+
f32[idx + 4] = ${r ? "rotationOffset" : "rotation[src] + rotationOffset"};
|
|
2087
|
+
f32[idx + 5] = cu0;
|
|
2088
|
+
f32[idx + 6] = cv0;
|
|
2089
|
+
f32[idx + 7] = cu1;
|
|
2090
|
+
f32[idx + 8] = cv1;
|
|
2091
|
+
`}
|
|
2092
|
+
|
|
2093
|
+
u32[idx + 9] = ${s ? "staticColor" : a ? "color[src]" : `color[src].${o ? "premultipliedUint32" : "uint32"}`};
|
|
2094
|
+
|
|
2095
|
+
f32[idx + 10] = originX;
|
|
2096
|
+
f32[idx + 11] = originY;
|
|
2097
|
+
}
|
|
2098
|
+
return idx;
|
|
2099
|
+
}
|
|
2100
|
+
`;
|
|
2101
|
+
const l = new Function(u)();
|
|
2102
|
+
return this.particleLoopCache.set(c, l), l;
|
|
2691
2103
|
}
|
|
2692
2104
|
render() {
|
|
2693
2105
|
if (this.instanceCount === 0) return;
|
|
@@ -2696,186 +2108,106 @@ class he extends ot {
|
|
|
2696
2108
|
this.texture && (t.activeTexture(t.TEXTURE0), t.bindTexture(t.TEXTURE_2D, this.texture.glTexture));
|
|
2697
2109
|
const e = this.currentShader;
|
|
2698
2110
|
this.instanceBuffer.bindBuffer(), this.instanceBuffer.bufferData(), e.bindVAO();
|
|
2699
|
-
const r = this.rapid.matrixStack, s = this.rapid.matrix.getMatrix(this.customMatrix ?? r.curWorldM), a =
|
|
2700
|
-
this.currentShader.setUniform("u_projection", a),
|
|
2111
|
+
const r = this.rapid.matrixStack, s = this.rapid.matrix.getMatrix(this.customMatrix ?? r.curWorldM), a = Xt(this.rapid.projection, s);
|
|
2112
|
+
this.currentShader.setUniform("u_projection", a), yt(t, t.TRIANGLE_STRIP, 0, 4, this.instanceCount), this.rapid.drawcallCount++, this.texture = void 0, this.customMatrix = void 0;
|
|
2701
2113
|
}
|
|
2702
2114
|
}
|
|
2703
|
-
var
|
|
2704
|
-
class
|
|
2705
|
-
/** The active WebGL context. */
|
|
2115
|
+
var he = /* @__PURE__ */ ((n) => (n[n.EQUAL = 0] = "EQUAL", n[n.NOT_EQUAL = 1] = "NOT_EQUAL", n))(he || {}), oe = /* @__PURE__ */ ((n) => (n[n.NORMAL = 0] = "NORMAL", n[n.ADD = 1] = "ADD", n[n.MULTIPLY = 2] = "MULTIPLY", n[n.SCREEN = 3] = "SCREEN", n[n.ERASE = 4] = "ERASE", n))(oe || {}), ht = /* @__PURE__ */ ((n) => (n[n.LINEAR = 0] = "LINEAR", n[n.NEAREST = 1] = "NEAREST", n))(ht || {}), ce = /* @__PURE__ */ ((n) => (n[n.CanvasItem = 0] = "CanvasItem", n[n.Viewport = 1] = "Viewport", n))(ce || {});
|
|
2116
|
+
class de {
|
|
2706
2117
|
gl;
|
|
2707
|
-
/** The target HTMLCanvasElement. */
|
|
2708
2118
|
canvas;
|
|
2709
|
-
/** The current orthographic projection matrix (16 elements). */
|
|
2710
2119
|
projection = new Float32Array(16);
|
|
2711
|
-
/** Indicates if the projection matrix has changed and needs to be uploaded to shaders. */
|
|
2712
2120
|
projectionDirty = !0;
|
|
2713
|
-
/** The current device pixel ratio. */
|
|
2714
2121
|
dpr;
|
|
2715
|
-
/** Background clear color [r, g, b, a], values range from 0 to 255. */
|
|
2716
2122
|
backgroundColor = x.Black;
|
|
2717
|
-
/** Logical width in CSS pixels, used for coordinate system and projection matrix. */
|
|
2718
2123
|
logicWidth = 0;
|
|
2719
|
-
/** Logical height in CSS pixels, used for coordinate system and projection matrix. */
|
|
2720
2124
|
logicHeight = 0;
|
|
2721
|
-
/** Physical width (canvas actual pixels = logical width * dpr). */
|
|
2722
2125
|
physicsWidth = 0;
|
|
2723
|
-
/** Physical height (canvas actual pixels = logical height * dpr). */
|
|
2724
2126
|
physicsHeight = 0;
|
|
2725
|
-
/** The currently active rendering region. */
|
|
2726
2127
|
currentRegion = null;
|
|
2727
|
-
/** Maximum number of texture units supported by the device. */
|
|
2728
2128
|
maxTextureUnits = 0;
|
|
2729
|
-
|
|
2730
|
-
matrixStack = new Ct(this);
|
|
2731
|
-
/** Direct access to the underlying matrix store. */
|
|
2129
|
+
matrixStack = new bt(this);
|
|
2732
2130
|
matrix;
|
|
2733
|
-
/** Region dedicated to fast sprite rendering. */
|
|
2734
2131
|
spriteRegion;
|
|
2735
|
-
/** Region dedicated to arbitrary geometry and shapes rendering. */
|
|
2736
2132
|
graphicRegion;
|
|
2737
2133
|
atlasSpriteRegion;
|
|
2738
2134
|
particleRegion;
|
|
2739
|
-
/** Counts the number of WebGL draw calls made in the current frame. */
|
|
2740
2135
|
drawcallCount = 0;
|
|
2741
|
-
/** Indicates whether we are currently writing to the stencil buffer to create a mask. */
|
|
2742
2136
|
inCreateMask = !1;
|
|
2743
|
-
/** Manager for creating and organizing textures. */
|
|
2744
2137
|
texture;
|
|
2745
|
-
/** Whether textures use premultiplied alpha. Set once at construction. */
|
|
2746
2138
|
premultipliedAlpha;
|
|
2747
|
-
/** Default texture filtering preference and requested canvas MSAA setting. */
|
|
2748
2139
|
antialias;
|
|
2749
2140
|
roundPixels;
|
|
2750
|
-
/** Default filtering mode used when sampling textures. */
|
|
2751
2141
|
textureFilter;
|
|
2752
2142
|
scaleMode;
|
|
2753
|
-
/** Internal ping-pong RenderTextures for multi-filter chains. */
|
|
2754
2143
|
_filterRT = [null, null];
|
|
2755
|
-
_filterInput = new
|
|
2144
|
+
_filterInput = new N();
|
|
2756
2145
|
get height() {
|
|
2757
2146
|
return this.logicHeight;
|
|
2758
2147
|
}
|
|
2759
2148
|
get width() {
|
|
2760
2149
|
return this.logicWidth;
|
|
2761
2150
|
}
|
|
2762
|
-
/**
|
|
2763
|
-
* Creates a new Rapid application instance.
|
|
2764
|
-
* @param options Initialization options including the target canvas.
|
|
2765
|
-
*/
|
|
2766
2151
|
constructor(t) {
|
|
2767
2152
|
this.canvas = t.canvas, this.dpr = window.devicePixelRatio || 1, this.antialias = t.antialias ?? !1, this.textureFilter = t.textureFilter ?? 1, this.premultipliedAlpha = t.premultipliedAlpha ?? !0, this.roundPixels = t.roundPixels ?? !1, this.scaleMode = t.scaleMode ?? 0;
|
|
2768
|
-
const e =
|
|
2769
|
-
this.gl = e, this.maxTextureUnits = e.getParameter(e.MAX_TEXTURE_IMAGE_UNITS), this.matrix = this.matrixStack.matrix, this.spriteRegion = new ot(this), this.graphicRegion = new
|
|
2153
|
+
const e = Lt(this.canvas, this.antialias, this.premultipliedAlpha);
|
|
2154
|
+
this.gl = e, this.maxTextureUnits = e.getParameter(e.MAX_TEXTURE_IMAGE_UNITS), this.matrix = this.matrixStack.matrix, this.spriteRegion = new ot(this), this.graphicRegion = new Yt(this), this.atlasSpriteRegion = new se(this), this.particleRegion = new ae(this);
|
|
2770
2155
|
const r = this.canvas.clientWidth || this.canvas.width, i = this.canvas.clientHeight || this.canvas.height;
|
|
2771
|
-
this.physicsWidth = t.physicsWidth || Math.round(r * this.dpr), this.physicsHeight = t.physicsHeight || Math.round(i * this.dpr), this.logicWidth = t.logicWidth || t.width || this.physicsWidth / this.dpr, this.logicHeight = t.logicHeight || t.height || this.physicsHeight / this.dpr, this.resize(this.logicWidth, this.logicHeight, this.physicsWidth, this.physicsHeight), this.texture = new
|
|
2156
|
+
this.physicsWidth = t.physicsWidth || Math.round(r * this.dpr), this.physicsHeight = t.physicsHeight || Math.round(i * this.dpr), this.logicWidth = t.logicWidth || t.width || this.physicsWidth / this.dpr, this.logicHeight = t.logicHeight || t.height || this.physicsHeight / this.dpr, this.resize(this.logicWidth, this.logicHeight, this.physicsWidth, this.physicsHeight), this.texture = new Ut(this), t.backgroundColor && (this.backgroundColor = t.backgroundColor), e.enable(e.BLEND), this.premultipliedAlpha ? e.blendFunc(e.ONE, e.ONE_MINUS_SRC_ALPHA) : e.blendFunc(e.SRC_ALPHA, e.ONE_MINUS_SRC_ALPHA), e.enable(e.STENCIL_TEST), e.stencilFunc(e.ALWAYS, 1, 255), e.stencilOp(e.KEEP, e.KEEP, e.KEEP);
|
|
2772
2157
|
}
|
|
2773
2158
|
setTextureFilter(t) {
|
|
2774
2159
|
this.textureFilter = t;
|
|
2775
2160
|
}
|
|
2776
|
-
setAntialias(t) {
|
|
2777
|
-
this.antialias = t;
|
|
2778
|
-
}
|
|
2779
2161
|
getColorUint32(t) {
|
|
2780
|
-
return
|
|
2162
|
+
return qt(this.premultipliedAlpha, t);
|
|
2781
2163
|
}
|
|
2782
|
-
/**
|
|
2783
|
-
* Enters a specific rendering region, flushing the previous one if necessary.
|
|
2784
|
-
* @param region The rendering region to enter.
|
|
2785
|
-
* @param customShader An optional custom shader to use for this region.
|
|
2786
|
-
*/
|
|
2787
2164
|
enterRegion(t, e) {
|
|
2788
2165
|
this.currentRegion === t && this.currentRegion.isSameShader(e) || (this.flush(), this.currentRegion = t, t.enter(e));
|
|
2789
2166
|
}
|
|
2790
2167
|
drawParticles(t) {
|
|
2791
|
-
|
|
2168
|
+
Jt(this, t);
|
|
2792
2169
|
}
|
|
2793
2170
|
drawSprite(t) {
|
|
2794
|
-
|
|
2171
|
+
Zt(this, t);
|
|
2795
2172
|
}
|
|
2796
2173
|
drawLine(t) {
|
|
2797
|
-
|
|
2174
|
+
te(this, t);
|
|
2798
2175
|
}
|
|
2799
2176
|
drawGraphic(t) {
|
|
2800
|
-
|
|
2177
|
+
Rt(this, t);
|
|
2801
2178
|
}
|
|
2802
2179
|
drawRect(t) {
|
|
2803
|
-
|
|
2180
|
+
re(this, t);
|
|
2804
2181
|
}
|
|
2805
2182
|
drawCircle(t) {
|
|
2806
|
-
|
|
2807
|
-
}
|
|
2808
|
-
/**
|
|
2809
|
-
* Starts rendering arbitrary graphics geometries.
|
|
2810
|
-
* @param drawMode The WebGL drawing mode (e.g., gl.TRIANGLES, gl.TRIANGLE_FAN).
|
|
2811
|
-
* @param texture An optional texture applied to the graphic vertices.
|
|
2812
|
-
* @param customShader An optional custom shader overriding the region's default shader.
|
|
2813
|
-
*/
|
|
2183
|
+
ie(this, t);
|
|
2184
|
+
}
|
|
2814
2185
|
startGraphic(t = this.gl.TRIANGLES, e, r, i) {
|
|
2815
2186
|
this.enterRegion(this.graphicRegion, r), this.graphicRegion.startGraphic(i ?? this.matrixStack.curWorldM, t, e);
|
|
2816
2187
|
}
|
|
2817
|
-
/**
|
|
2818
|
-
* Starts rendering graphics explicitly for use as a mask, overriding the shader.
|
|
2819
|
-
* @param drawMode The WebGL drawing mode (e.g., gl.TRIANGLES).
|
|
2820
|
-
* @param texture An optional texture whose alpha channel may dictate masking rules.
|
|
2821
|
-
*/
|
|
2822
2188
|
startMaskGraphic(t = this.gl.TRIANGLES, e, r) {
|
|
2823
2189
|
this.startGraphic(t, e, this.graphicRegion.maskShader, r);
|
|
2824
2190
|
}
|
|
2825
|
-
/**
|
|
2826
|
-
* Utility method: Draws an image directly as a mask using a generic rectangle geometry.
|
|
2827
|
-
* @param texture The texture to be used as a mask.
|
|
2828
|
-
*/
|
|
2829
2191
|
drawMaskImage(t) {
|
|
2830
|
-
|
|
2192
|
+
ee(this, t);
|
|
2831
2193
|
}
|
|
2832
|
-
/**
|
|
2833
|
-
* Pushes vertices for a rectangle geometry. Should be enclosed by startGraphic and endGraphic.
|
|
2834
|
-
* @param w The width of the rectangle.
|
|
2835
|
-
* @param h The height of the rectangle.
|
|
2836
|
-
* @param color An optional tint color.
|
|
2837
|
-
*/
|
|
2838
2194
|
addRectVertex(t, e, r) {
|
|
2839
2195
|
const i = this.getColorUint32(r);
|
|
2840
2196
|
this.addGraphicVertex(0, 0, 0, 0, i), this.addGraphicVertex(t, 0, 1, 0, i), this.addGraphicVertex(t, e, 1, 1, i), this.addGraphicVertex(0, e, 0, 1, i);
|
|
2841
2197
|
}
|
|
2842
|
-
/**
|
|
2843
|
-
* Pushes vertices for a circle geometry using TRIANGLES or similar primitives.
|
|
2844
|
-
* @param r The radius of the circle.
|
|
2845
|
-
* @param color An optional tint color.
|
|
2846
|
-
* @param segments The number of segments (polygons) used to approximate the circle.
|
|
2847
|
-
*/
|
|
2848
2198
|
addCircleVertex(t, e, r = 32) {
|
|
2849
2199
|
const i = Math.PI * 2 / r, s = this.getColorUint32(e);
|
|
2850
2200
|
for (let a = 0; a < r; a++) {
|
|
2851
|
-
const
|
|
2852
|
-
this.addGraphicVertex(
|
|
2201
|
+
const h = i * a, o = Math.cos(h) * t, c = Math.sin(h) * t, u = 0.5 + Math.cos(h) * 0.5, l = 0.5 + Math.sin(h) * 0.5;
|
|
2202
|
+
this.addGraphicVertex(o, c, u, l, s);
|
|
2853
2203
|
}
|
|
2854
2204
|
}
|
|
2855
|
-
/**
|
|
2856
|
-
* Adds an individual vertex to the current graphics batch.
|
|
2857
|
-
* @param x The relative X coordinate of the vertex.
|
|
2858
|
-
* @param y The relative Y coordinate of the vertex.
|
|
2859
|
-
* @param u The U texture coordinate (0 to 1).
|
|
2860
|
-
* @param v The V texture coordinate (0 to 1).
|
|
2861
|
-
* @param color The vertex color as a 32-bit unsigned integer.
|
|
2862
|
-
*/
|
|
2863
2205
|
addGraphicVertex(t, e, r = 0, i = 0, s) {
|
|
2864
2206
|
this.graphicRegion.addVertex(t, e, r, i, typeof s == "number" ? s : this.getColorUint32(s));
|
|
2865
2207
|
}
|
|
2866
|
-
/**
|
|
2867
|
-
* Ends the current graphics geometry definition, readying it for rendering.
|
|
2868
|
-
*/
|
|
2869
2208
|
endGraphic() {
|
|
2870
2209
|
this.graphicRegion.endGraphic();
|
|
2871
2210
|
}
|
|
2872
|
-
/**
|
|
2873
|
-
* Resizes the canvas, updates internal viewport values, and recreates projection boundaries.
|
|
2874
|
-
* @param logicWidth The new logical display width.
|
|
2875
|
-
* @param logicHeight The new logical display height.
|
|
2876
|
-
* @param cssWidth Optional CSS display width.
|
|
2877
|
-
* @param cssHeight Optional CSS display height.
|
|
2878
|
-
*/
|
|
2879
2211
|
resize(t, e, r, i) {
|
|
2880
2212
|
this.flush();
|
|
2881
2213
|
const s = r ?? this.canvas.clientWidth ?? this.canvas.width, a = i ?? this.canvas.clientHeight ?? this.canvas.height;
|
|
@@ -2891,100 +2223,51 @@ class fe {
|
|
|
2891
2223
|
}
|
|
2892
2224
|
this.updateProjection(0, this.logicWidth, this.logicHeight, 0);
|
|
2893
2225
|
}
|
|
2894
|
-
/**
|
|
2895
|
-
* Updates the projection matrix using an orthographic mapping.
|
|
2896
|
-
* Automatically sets local flag projectionDirty.
|
|
2897
|
-
*/
|
|
2898
2226
|
updateProjection(t, e, r, i) {
|
|
2899
2227
|
this.updateOrthMatrix(this.projection, t, e, r, i), this.projectionDirty = !0;
|
|
2900
2228
|
}
|
|
2901
|
-
/**
|
|
2902
|
-
* Clears the active framebuffer applying the default background color.
|
|
2903
|
-
*/
|
|
2904
2229
|
clear() {
|
|
2905
2230
|
const t = this.gl;
|
|
2906
2231
|
this.backgroundColor.setClearColor(t), t.clear(t.COLOR_BUFFER_BIT | t.STENCIL_BUFFER_BIT), this.drawcallCount = 0, this.matrixStack.reset();
|
|
2907
2232
|
}
|
|
2908
|
-
/**
|
|
2909
|
-
* Populates an orthographic projection matrix in place.
|
|
2910
|
-
* Avoids continuous Float32Array allocations for performance reasons.
|
|
2911
|
-
*/
|
|
2912
2233
|
updateOrthMatrix(t, e, r, i, s) {
|
|
2913
2234
|
t[0] = 2 / (r - e), t[1] = 0, t[2] = 0, t[3] = 0, t[4] = 0, t[5] = 2 / (s - i), t[6] = 0, t[7] = 0, t[8] = 0, t[9] = 0, t[10] = -1, t[11] = 0, t[12] = -(r + e) / (r - e), t[13] = -(s + i) / (s - i), t[14] = 0, t[15] = 1;
|
|
2914
2235
|
}
|
|
2915
|
-
/**
|
|
2916
|
-
* Flushes currently buffered rendering operations across all active regions.
|
|
2917
|
-
*/
|
|
2918
2236
|
flush() {
|
|
2919
2237
|
this.currentRegion && (this.currentRegion.exit(), this.currentRegion = null);
|
|
2920
2238
|
}
|
|
2921
|
-
/**
|
|
2922
|
-
* Applies a chain of shaders to a texture sequentially using ping-pong RenderTextures.
|
|
2923
|
-
* Each shader receives the output of the previous one as its input.
|
|
2924
|
-
* Two internal RenderTextures are reused across calls (resized as needed).
|
|
2925
|
-
*
|
|
2926
|
-
* @param source The input texture to start the filter chain from.
|
|
2927
|
-
* @param shaders An ordered array of CustomGlShader to apply in sequence.
|
|
2928
|
-
* @returns The RenderTexture containing the final filtered result.
|
|
2929
|
-
* Draw it with `rapid.drawSprite({ texture: result })` to display it on screen.
|
|
2930
|
-
*
|
|
2931
|
-
* @example
|
|
2932
|
-
* const result = rapid.applyFilters(tex, [blurShader, outlineShader]);
|
|
2933
|
-
* rapid.drawSprite({ texture: result });
|
|
2934
|
-
*/
|
|
2935
2239
|
applyFilters(t, e) {
|
|
2936
2240
|
if (e.length === 0)
|
|
2937
2241
|
throw new Error("applyFilters: shaders array must not be empty.");
|
|
2938
2242
|
const r = Math.max(...e.map((c) => c.padding)), i = r, s = t.rawWidth + r * 2, a = t.rawHeight + r * 2;
|
|
2939
2243
|
for (let c = 0; c < 2; c++)
|
|
2940
2244
|
this._filterRT[c] ? this._filterRT[c].resize(s, a) : this._filterRT[c] = this.texture.createRenderTexture({ width: s, height: a });
|
|
2941
|
-
let
|
|
2245
|
+
let h = t.clone(this._filterInput), o = 0;
|
|
2942
2246
|
this.matrixStack.save(), this.matrixStack.identity();
|
|
2943
2247
|
for (let c = 0; c < e.length; c++) {
|
|
2944
|
-
const u = this._filterRT[
|
|
2248
|
+
const u = this._filterRT[o % 2];
|
|
2945
2249
|
u.offsetX = 0, u.offsetY = 0, this.enterRenderTexture(u), this.clearRenderTexture(), this.drawSprite({
|
|
2946
|
-
texture:
|
|
2250
|
+
texture: h,
|
|
2947
2251
|
shader: e[c],
|
|
2948
2252
|
offsetX: c == 0 ? i : 0,
|
|
2949
2253
|
// padding back
|
|
2950
2254
|
offsetY: c == 0 ? i : 0,
|
|
2951
2255
|
padding: r
|
|
2952
|
-
}), this.leaveRenderTexture(),
|
|
2256
|
+
}), this.leaveRenderTexture(), h = u, o++;
|
|
2953
2257
|
}
|
|
2954
|
-
return this.matrixStack.restore(),
|
|
2258
|
+
return this.matrixStack.restore(), h.offsetX = -i, h.offsetY = -i, h;
|
|
2955
2259
|
}
|
|
2956
2260
|
enterRenderTexture(t) {
|
|
2957
2261
|
this.flush(), t.activate(), this.gl.viewport(0, 0, t.rawWidth, t.rawHeight), this.updateProjection(0, t.rawWidth, t.rawHeight, 0);
|
|
2958
2262
|
}
|
|
2959
|
-
/**
|
|
2960
|
-
* Clears a RenderTexture to a solid color.
|
|
2961
|
-
* Must be called while the RT is the active render target (i.e. inside enterRenderTexture/leaveRenderTexture).
|
|
2962
|
-
* Can also be called standalone — it will bind the RT, clear it, but NOT restore the main framebuffer.
|
|
2963
|
-
* @param rt The render texture to clear.
|
|
2964
|
-
* @param color Clear color. Defaults to transparent black (0, 0, 0, 0).
|
|
2965
|
-
*/
|
|
2966
2263
|
clearRenderTexture(t = new x(0, 0, 0, 0)) {
|
|
2967
2264
|
this.flush();
|
|
2968
2265
|
const e = this.gl;
|
|
2969
2266
|
t.setClearColor(e), e.clear(e.COLOR_BUFFER_BIT);
|
|
2970
2267
|
}
|
|
2971
|
-
/**
|
|
2972
|
-
* Completes rendering to an offscreen render texture and reverts rendering back to the main canvas.
|
|
2973
|
-
*/
|
|
2974
2268
|
leaveRenderTexture() {
|
|
2975
2269
|
this.flush(), this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, null), this.gl.viewport(0, 0, this.physicsWidth, this.physicsHeight), this.updateProjection(0, this.logicWidth, this.logicHeight, 0);
|
|
2976
2270
|
}
|
|
2977
|
-
/**
|
|
2978
|
-
* Convenience wrapper: enters a RenderTexture, optionally clears it, runs a callback, then leaves.
|
|
2979
|
-
* @param rt The RenderTexture to render into.
|
|
2980
|
-
* @param cb The callback containing draw calls to execute inside the RT.
|
|
2981
|
-
* @param color Clear color before rendering. Pass `null` to skip clearing. Defaults to transparent black.
|
|
2982
|
-
*
|
|
2983
|
-
* @example
|
|
2984
|
-
* rapid.drawToRenderTexture(myRT, () => {
|
|
2985
|
-
* rapid.drawSprite({ texture: mySprite });
|
|
2986
|
-
* });
|
|
2987
|
-
*/
|
|
2988
2271
|
drawToRenderTexture(t, e, r = new x(0, 0, 0, 0)) {
|
|
2989
2272
|
this.enterRenderTexture(t);
|
|
2990
2273
|
try {
|
|
@@ -2993,19 +2276,6 @@ class fe {
|
|
|
2993
2276
|
this.leaveRenderTexture();
|
|
2994
2277
|
}
|
|
2995
2278
|
}
|
|
2996
|
-
/**
|
|
2997
|
-
* Convenience wrapper: writes a mask using the stencil buffer, then renders within it, then exits the mask.
|
|
2998
|
-
* @param maskCb Callback that defines the mask geometry (drawn to stencil, not visible).
|
|
2999
|
-
* @param drawCb Callback containing the actual draw calls masked by the stencil.
|
|
3000
|
-
* @param type Mask type: EQUAL (draw inside) or NOT_EQUAL (draw outside). Defaults to EQUAL.
|
|
3001
|
-
* @param ref Stencil reference value. Defaults to 1.
|
|
3002
|
-
*
|
|
3003
|
-
* @example
|
|
3004
|
-
* rapid.withMask(
|
|
3005
|
-
* () => rapid.drawRect({ width: 200, height: 200 }),
|
|
3006
|
-
* () => rapid.drawSprite({ texture: myTexture }),
|
|
3007
|
-
* );
|
|
3008
|
-
*/
|
|
3009
2279
|
withMask(t, e, r = 0, i = 1) {
|
|
3010
2280
|
this.clearMask(), this.startDrawMask(i);
|
|
3011
2281
|
try {
|
|
@@ -3020,28 +2290,6 @@ class fe {
|
|
|
3020
2290
|
this.exitMask();
|
|
3021
2291
|
}
|
|
3022
2292
|
}
|
|
3023
|
-
/**
|
|
3024
|
-
* Convenience wrapper: saves the matrix stack, applies an optional transform, runs a callback, then restores.
|
|
3025
|
-
* When `transform` is provided, delegates to `matrixStack.applyTransform()` which handles
|
|
3026
|
-
* position, rotation, scale, offset, and origin automatically.
|
|
3027
|
-
* @param cb The callback to execute within the saved transform context.
|
|
3028
|
-
* @param transform Optional transform options to apply before running the callback.
|
|
3029
|
-
* @param width The logical width used to resolve `origin` anchoring. Defaults to 0.
|
|
3030
|
-
* @param height The logical height used to resolve `origin` anchoring. Defaults to 0.
|
|
3031
|
-
*
|
|
3032
|
-
* @example
|
|
3033
|
-
* // Simple save/restore
|
|
3034
|
-
* rapid.withTransform(() => {
|
|
3035
|
-
* rapid.matrixStack.translate(100, 100);
|
|
3036
|
-
* rapid.drawSprite({ texture: myTexture });
|
|
3037
|
-
* });
|
|
3038
|
-
*
|
|
3039
|
-
* @example
|
|
3040
|
-
* // With a transform applied
|
|
3041
|
-
* rapid.withTransform(() => {
|
|
3042
|
-
* rapid.drawSprite({ texture: myTexture });
|
|
3043
|
-
* }, { x: 100, y: 50, rotation: Math.PI / 4, origin: 0.5 }, myTexture.width, myTexture.height);
|
|
3044
|
-
*/
|
|
3045
2293
|
withTransform(t, e, r = 0, i = 0) {
|
|
3046
2294
|
this.matrixStack.save();
|
|
3047
2295
|
try {
|
|
@@ -3050,19 +2298,6 @@ class fe {
|
|
|
3050
2298
|
this.matrixStack.restore();
|
|
3051
2299
|
}
|
|
3052
2300
|
}
|
|
3053
|
-
/**
|
|
3054
|
-
* Convenience wrapper: enables scissor clipping for a region, runs a callback, then disables it.
|
|
3055
|
-
* @param x Left edge in logical pixels.
|
|
3056
|
-
* @param y Top edge in logical pixels.
|
|
3057
|
-
* @param width Width in logical pixels.
|
|
3058
|
-
* @param height Height in logical pixels.
|
|
3059
|
-
* @param cb The callback to execute within the scissor region.
|
|
3060
|
-
*
|
|
3061
|
-
* @example
|
|
3062
|
-
* rapid.withScissor(50, 50, 300, 200, () => {
|
|
3063
|
-
* rapid.drawSprite({ texture: myTexture });
|
|
3064
|
-
* });
|
|
3065
|
-
*/
|
|
3066
2301
|
withScissor(t, e, r, i, s) {
|
|
3067
2302
|
this.startScissor(t, e, r, i);
|
|
3068
2303
|
try {
|
|
@@ -3071,16 +2306,6 @@ class fe {
|
|
|
3071
2306
|
this.endScissor();
|
|
3072
2307
|
}
|
|
3073
2308
|
}
|
|
3074
|
-
/**
|
|
3075
|
-
* Convenience wrapper: sets a blend mode, runs a callback, then restores NORMAL blend mode.
|
|
3076
|
-
* @param mode The BlendMode to apply for the duration of the callback.
|
|
3077
|
-
* @param cb The callback to execute under the given blend mode.
|
|
3078
|
-
*
|
|
3079
|
-
* @example
|
|
3080
|
-
* rapid.withBlendMode(BlendMode.ADD, () => {
|
|
3081
|
-
* rapid.drawSprite({ texture: glowTexture });
|
|
3082
|
-
* });
|
|
3083
|
-
*/
|
|
3084
2309
|
withBlendMode(t, e) {
|
|
3085
2310
|
this.setBlendMode(t);
|
|
3086
2311
|
try {
|
|
@@ -3092,56 +2317,31 @@ class fe {
|
|
|
3092
2317
|
);
|
|
3093
2318
|
}
|
|
3094
2319
|
}
|
|
3095
|
-
/**
|
|
3096
|
-
* Starts drawing into the stencil buffer to construct a rendering mask.
|
|
3097
|
-
* @param ref The stencil reference value.
|
|
3098
|
-
* @param mask The stencil bitmask.
|
|
3099
|
-
*/
|
|
3100
2320
|
startDrawMask(t = 1, e = 255) {
|
|
3101
2321
|
this.flush();
|
|
3102
2322
|
const r = this.gl;
|
|
3103
2323
|
r.stencilMask(e), r.colorMask(!1, !1, !1, !1), r.stencilFunc(r.ALWAYS, t, e), r.stencilOp(r.KEEP, r.KEEP, r.REPLACE), this.enterRegion(this.graphicRegion, this.graphicRegion.maskShader), this.inCreateMask = !0;
|
|
3104
2324
|
}
|
|
3105
|
-
/**
|
|
3106
|
-
* Finishes the mask drawing phase and restores color buffer writing.
|
|
3107
|
-
*/
|
|
3108
2325
|
endDrawMask() {
|
|
3109
2326
|
this.flush();
|
|
3110
2327
|
const t = this.gl;
|
|
3111
2328
|
t.colorMask(!0, !0, !0, !0), t.stencilMask(0), this.inCreateMask = !1;
|
|
3112
2329
|
}
|
|
3113
|
-
/**
|
|
3114
|
-
* Clears bounds created into the stencil mask.
|
|
3115
|
-
* @param mask The bitmask specifying which stencil layer to clear.
|
|
3116
|
-
*/
|
|
3117
2330
|
clearMask(t = 255) {
|
|
3118
2331
|
this.flush();
|
|
3119
2332
|
const e = this.gl;
|
|
3120
2333
|
e.stencilMask(t), e.clear(e.STENCIL_BUFFER_BIT), this.inCreateMask = !1;
|
|
3121
2334
|
}
|
|
3122
|
-
/**
|
|
3123
|
-
* Enters a constrained rendering phase masked by the existing stencil buffer values.
|
|
3124
|
-
* @param type Equality check type. Use "equal" to draw inside the mask, or "notEqual" to draw outside.
|
|
3125
|
-
* @param ref The reference value to test against.
|
|
3126
|
-
* @param mask The bitmask specifying which stencil bits to consider.
|
|
3127
|
-
*/
|
|
3128
2335
|
enterMask(t, e = 1, r = 255) {
|
|
3129
2336
|
this.flush();
|
|
3130
2337
|
const i = this.gl;
|
|
3131
2338
|
i.colorMask(!0, !0, !0, !0), i.stencilMask(0), i.stencilFunc(t === 0 ? i.EQUAL : i.NOTEQUAL, e, r), i.stencilOp(i.KEEP, i.KEEP, i.KEEP), this.inCreateMask = !1;
|
|
3132
2339
|
}
|
|
3133
|
-
/**
|
|
3134
|
-
* Exits the masked rendering phase, restoring default full-screen stencil values tests.
|
|
3135
|
-
*/
|
|
3136
2340
|
exitMask() {
|
|
3137
2341
|
this.flush();
|
|
3138
2342
|
const t = this.gl;
|
|
3139
2343
|
t.colorMask(!0, !0, !0, !0), t.stencilMask(255), t.stencilFunc(t.ALWAYS, 1, 255), t.stencilOp(t.KEEP, t.KEEP, t.KEEP), this.inCreateMask = !1;
|
|
3140
2344
|
}
|
|
3141
|
-
/**
|
|
3142
|
-
* Configures the global WebGL blending behavior.
|
|
3143
|
-
* @param mode The targeted BlendMode to switch onto.
|
|
3144
|
-
*/
|
|
3145
2345
|
setBlendMode(t) {
|
|
3146
2346
|
this.flush();
|
|
3147
2347
|
const e = this.gl;
|
|
@@ -3163,23 +2363,11 @@ class fe {
|
|
|
3163
2363
|
break;
|
|
3164
2364
|
}
|
|
3165
2365
|
}
|
|
3166
|
-
/**
|
|
3167
|
-
* Enables rectangular scissor clipping. Only pixels within the specified
|
|
3168
|
-
* rectangle (in logical coordinates) will be rendered.
|
|
3169
|
-
* Coordinates use the same system as your drawing calls (top-left origin).
|
|
3170
|
-
* @param x Left edge in logical pixels.
|
|
3171
|
-
* @param y Top edge in logical pixels.
|
|
3172
|
-
* @param width Width in logical pixels.
|
|
3173
|
-
* @param height Height in logical pixels.
|
|
3174
|
-
*/
|
|
3175
2366
|
startScissor(t, e, r, i) {
|
|
3176
2367
|
this.flush();
|
|
3177
|
-
const s = this.gl, a = this.physicsWidth / this.logicWidth,
|
|
3178
|
-
s.enable(s.SCISSOR_TEST), s.scissor(
|
|
2368
|
+
const s = this.gl, a = this.physicsWidth / this.logicWidth, h = this.physicsHeight / this.logicHeight, o = Math.round(t * a), c = Math.round(this.physicsHeight - (e + i) * h), u = Math.round(r * a), l = Math.round(i * h);
|
|
2369
|
+
s.enable(s.SCISSOR_TEST), s.scissor(o, c, u, l);
|
|
3179
2370
|
}
|
|
3180
|
-
/**
|
|
3181
|
-
* Disables scissor clipping, restoring full-canvas rendering.
|
|
3182
|
-
*/
|
|
3183
2371
|
endScissor() {
|
|
3184
2372
|
this.flush(), this.gl.disable(this.gl.SCISSOR_TEST);
|
|
3185
2373
|
}
|
|
@@ -3201,7 +2389,7 @@ class fe {
|
|
|
3201
2389
|
));
|
|
3202
2390
|
}
|
|
3203
2391
|
cssToDevicePixel(t) {
|
|
3204
|
-
return t.
|
|
2392
|
+
return t.multiply(this.dpr);
|
|
3205
2393
|
}
|
|
3206
2394
|
cssToLogic(t) {
|
|
3207
2395
|
const e = this.cssToDevicePixel(t);
|
|
@@ -3210,40 +2398,27 @@ class fe {
|
|
|
3210
2398
|
devicePixelToCss(t) {
|
|
3211
2399
|
return t.divide(this.dpr);
|
|
3212
2400
|
}
|
|
3213
|
-
/**
|
|
3214
|
-
* Exports a world matrix as a CSS `matrix(...)` string, ready to assign
|
|
3215
|
-
* directly to a DOM element's `style.transform`.
|
|
3216
|
-
* Unlike `matrixStack.toCSSMatrix()`, this bakes in the logic-pixel → CSS-pixel
|
|
3217
|
-
* scale (accounting for dpr and a custom `logicWidth`/`logicHeight`), so the
|
|
3218
|
-
* result lines up with the canvas without any extra `scale(...)` on your end.
|
|
3219
|
-
* @param index - Matrix index to export. Defaults to the current world matrix.
|
|
3220
|
-
*/
|
|
3221
2401
|
toCSSMatrix(t) {
|
|
3222
2402
|
const e = this.physicsWidth / this.dpr / this.logicWidth, r = this.physicsHeight / this.dpr / this.logicHeight;
|
|
3223
2403
|
return this.matrix.toCSSMatrix(t ?? this.matrixStack.curWorldM, e, r);
|
|
3224
2404
|
}
|
|
3225
2405
|
}
|
|
3226
|
-
function
|
|
2406
|
+
function ue(n) {
|
|
3227
2407
|
return !(n === null || typeof n != "object" || Array.isArray(n) || n instanceof p || n instanceof x);
|
|
3228
2408
|
}
|
|
3229
2409
|
class L {
|
|
3230
|
-
/** Random float in [min, max). */
|
|
3231
2410
|
static float(t, e) {
|
|
3232
2411
|
return Math.random() * (e - t) + t;
|
|
3233
2412
|
}
|
|
3234
|
-
/** Random integer in [min, max] (inclusive). */
|
|
3235
2413
|
static int(t, e) {
|
|
3236
2414
|
return Math.floor(Math.random() * (e - t + 1)) + t;
|
|
3237
2415
|
}
|
|
3238
|
-
/** Random angle in [0, 2π). */
|
|
3239
2416
|
static angle() {
|
|
3240
2417
|
return Math.random() * Math.PI * 2;
|
|
3241
2418
|
}
|
|
3242
|
-
/** Random Vec2 with components in the supplied per-axis ranges. */
|
|
3243
2419
|
static vector(t, e, r, i) {
|
|
3244
2420
|
return new p(L.float(t, e), L.float(r, i));
|
|
3245
2421
|
}
|
|
3246
|
-
/** Random Color with each component interpolated between minColor and maxColor. */
|
|
3247
2422
|
static randomColor(t, e) {
|
|
3248
2423
|
return new x(
|
|
3249
2424
|
L.float(t.r, e.r),
|
|
@@ -3252,14 +2427,9 @@ class L {
|
|
|
3252
2427
|
L.float(t.a, e.a)
|
|
3253
2428
|
);
|
|
3254
2429
|
}
|
|
3255
|
-
/** Pick a random element from an array with uniform probability. */
|
|
3256
2430
|
static pick(t) {
|
|
3257
2431
|
return t[L.int(0, t.length - 1)];
|
|
3258
2432
|
}
|
|
3259
|
-
/**
|
|
3260
|
-
* Pick a random element using weighted probability.
|
|
3261
|
-
* @param array - Pairs of [item, weight]. Higher weight = more likely.
|
|
3262
|
-
*/
|
|
3263
2433
|
static pickWeight(t) {
|
|
3264
2434
|
if (!t || t.length === 0) return null;
|
|
3265
2435
|
let e = 0;
|
|
@@ -3269,12 +2439,6 @@ class L {
|
|
|
3269
2439
|
if (r -= s, r <= 0) return i;
|
|
3270
2440
|
return t[t.length - 1][0];
|
|
3271
2441
|
}
|
|
3272
|
-
/**
|
|
3273
|
-
* Resolves a scalar-or-range value to a concrete T.
|
|
3274
|
-
* - `undefined` → `defaultValue`
|
|
3275
|
-
* - `T` → `T` (or a clone for objects)
|
|
3276
|
-
* - `[T, T]` → random value between the two bounds
|
|
3277
|
-
*/
|
|
3278
2442
|
static scalarOrRange(t, e) {
|
|
3279
2443
|
if (t == null) return e;
|
|
3280
2444
|
if (Array.isArray(t)) {
|
|
@@ -3289,17 +2453,17 @@ class L {
|
|
|
3289
2453
|
return typeof t == "number" ? t : t.clone();
|
|
3290
2454
|
}
|
|
3291
2455
|
}
|
|
3292
|
-
var
|
|
3293
|
-
const
|
|
3294
|
-
class
|
|
2456
|
+
var le = /* @__PURE__ */ ((n) => (n.POINT = "point", n.CIRCLE = "circle", n.RECT = "rect", n))(le || {});
|
|
2457
|
+
const pt = 10, gt = 0, vt = !0;
|
|
2458
|
+
class K {
|
|
3295
2459
|
components;
|
|
3296
2460
|
constructor(t = 1) {
|
|
3297
2461
|
if (!Number.isInteger(t) || t <= 0)
|
|
3298
2462
|
throw new RangeError("ParticleAttributeStore size must be a positive integer");
|
|
3299
2463
|
this.components = Array.from({ length: t }, () => ({
|
|
3300
|
-
value: new
|
|
3301
|
-
delta: new
|
|
3302
|
-
damping: new
|
|
2464
|
+
value: new A(S.Float32),
|
|
2465
|
+
delta: new A(S.Float32),
|
|
2466
|
+
damping: new A(S.Float32)
|
|
3303
2467
|
}));
|
|
3304
2468
|
}
|
|
3305
2469
|
getArrayBuffer() {
|
|
@@ -3338,46 +2502,41 @@ class q {
|
|
|
3338
2502
|
) : this.getComponent(t, e);
|
|
3339
2503
|
}
|
|
3340
2504
|
create(t, e, r = 1) {
|
|
3341
|
-
const i =
|
|
3342
|
-
let
|
|
3343
|
-
for (let
|
|
3344
|
-
const { value: c, delta: u, damping: l } = this.components[
|
|
3345
|
-
c.push(f), u.push(i?.delta === void 0 ? (m - f) / a : this.getComponent(i.delta,
|
|
2505
|
+
const i = ue(t) ? t : void 0, s = i === void 0 ? t : void 0, a = r > 0 ? r : 1;
|
|
2506
|
+
let h = 0;
|
|
2507
|
+
for (let o = 0; o < this.components.length; o++) {
|
|
2508
|
+
const { value: c, delta: u, damping: l } = this.components[o], d = this.getComponent(e, o), f = s === void 0 ? this.resolveComponent(i?.start, o, d) : this.getComponent(s, o), m = i?.end === void 0 ? f : this.resolveComponent(i.end, o, d);
|
|
2509
|
+
c.push(f), u.push(i?.delta === void 0 ? (m - f) / a : this.getComponent(i.delta, o)), l.push(i?.damping ?? 1), o === 0 && (h = f);
|
|
3346
2510
|
}
|
|
3347
|
-
return
|
|
2511
|
+
return h;
|
|
3348
2512
|
}
|
|
3349
2513
|
}
|
|
3350
|
-
class
|
|
2514
|
+
class wt {
|
|
3351
2515
|
options;
|
|
3352
2516
|
emitting = !1;
|
|
3353
2517
|
emitTimer = 0;
|
|
3354
|
-
emitRate =
|
|
3355
|
-
emitTime =
|
|
2518
|
+
emitRate = pt;
|
|
2519
|
+
emitTime = gt;
|
|
3356
2520
|
emitTimeCounter = 0;
|
|
3357
|
-
|
|
3358
|
-
localSpace = Rt;
|
|
2521
|
+
localSpace = vt;
|
|
3359
2522
|
rapid;
|
|
3360
|
-
x = new
|
|
3361
|
-
y = new
|
|
3362
|
-
scaleX = new
|
|
3363
|
-
scaleY = new
|
|
3364
|
-
rotation = new
|
|
3365
|
-
color = new
|
|
2523
|
+
x = new A(S.Float32);
|
|
2524
|
+
y = new A(S.Float32);
|
|
2525
|
+
scaleX = new A(S.Float32);
|
|
2526
|
+
scaleY = new A(S.Float32);
|
|
2527
|
+
rotation = new A(S.Float32);
|
|
2528
|
+
color = new A(S.Uint32);
|
|
2529
|
+
remainingLife = new A(S.Float32);
|
|
3366
2530
|
animations = {
|
|
3367
|
-
speed: new
|
|
3368
|
-
rotation: new
|
|
3369
|
-
scale: new
|
|
3370
|
-
color: new
|
|
3371
|
-
velocity: new
|
|
2531
|
+
speed: new K(),
|
|
2532
|
+
rotation: new K(),
|
|
2533
|
+
scale: new K(),
|
|
2534
|
+
color: new K(4),
|
|
2535
|
+
velocity: new K(2)
|
|
3372
2536
|
};
|
|
3373
2537
|
count = 0;
|
|
3374
|
-
/**
|
|
3375
|
-
* Creates a new particle emitter.
|
|
3376
|
-
* @param rapid - The Rapid renderer instance
|
|
3377
|
-
* @param options - Emitter configuration options
|
|
3378
|
-
*/
|
|
3379
2538
|
constructor(t, e) {
|
|
3380
|
-
this.rapid = t, this.options = e, this.emitRate = e.emitRate ??
|
|
2539
|
+
this.rapid = t, this.options = e, this.emitRate = e.emitRate ?? pt, this.emitTime = e.emitTime ?? gt, this.localSpace = e.localSpace ?? vt;
|
|
3381
2540
|
}
|
|
3382
2541
|
getAllArrayBuffer() {
|
|
3383
2542
|
return [
|
|
@@ -3387,46 +2546,33 @@ class bt {
|
|
|
3387
2546
|
this.scaleY,
|
|
3388
2547
|
this.rotation,
|
|
3389
2548
|
this.color,
|
|
2549
|
+
this.remainingLife,
|
|
3390
2550
|
...Object.values(this.animations).flatMap((t) => t.getArrayBuffer())
|
|
3391
2551
|
];
|
|
3392
2552
|
}
|
|
3393
|
-
/** Replaces the emitter's texture at runtime. */
|
|
3394
2553
|
setTexture(t) {
|
|
3395
2554
|
this.options.texture = t;
|
|
3396
2555
|
}
|
|
3397
|
-
/**
|
|
3398
|
-
* Creates a new emitter sharing the same options object.
|
|
3399
|
-
* Particle state is NOT copied.
|
|
3400
|
-
*/
|
|
3401
2556
|
clone() {
|
|
3402
|
-
return new
|
|
2557
|
+
return new wt(this.rapid, { ...this.options });
|
|
3403
2558
|
}
|
|
3404
|
-
/** Sets particles-per-second emission rate (continuous mode). */
|
|
3405
2559
|
setEmitRate(t) {
|
|
3406
2560
|
this.emitRate = t;
|
|
3407
2561
|
}
|
|
3408
|
-
/** Sets the burst interval in seconds (0 = continuous). */
|
|
3409
2562
|
setEmitTime(t) {
|
|
3410
2563
|
this.emitTime = t;
|
|
3411
2564
|
}
|
|
3412
|
-
/** Starts continuous particle emission. */
|
|
3413
2565
|
start() {
|
|
3414
2566
|
this.emitting = !0, this.emitTimeCounter = 0;
|
|
3415
2567
|
}
|
|
3416
|
-
/** Stops new particle emission; existing particles finish their lifecycle. */
|
|
3417
2568
|
stop() {
|
|
3418
2569
|
this.emitting = !1;
|
|
3419
2570
|
}
|
|
3420
|
-
/** Removes all particles and resets timers. */
|
|
3421
2571
|
clear() {
|
|
3422
2572
|
for (const t of this.getAllArrayBuffer())
|
|
3423
2573
|
t.clear();
|
|
3424
2574
|
this.count = 0, this.emitTimeCounter = 0;
|
|
3425
2575
|
}
|
|
3426
|
-
/**
|
|
3427
|
-
* Spawns `count` particles immediately.
|
|
3428
|
-
* Respects `maxParticles` if set.
|
|
3429
|
-
*/
|
|
3430
2576
|
emit(t) {
|
|
3431
2577
|
const e = this.options.maxParticles ?? 1 / 0, r = Math.min(t, e - this.count);
|
|
3432
2578
|
for (let i = 0; i < r; i++)
|
|
@@ -3434,6 +2580,7 @@ class bt {
|
|
|
3434
2580
|
}
|
|
3435
2581
|
createParticle() {
|
|
3436
2582
|
const t = L.scalarOrRange(this.options.life, 1);
|
|
2583
|
+
this.remainingLife.push(t);
|
|
3437
2584
|
let e = 0, r = 0;
|
|
3438
2585
|
switch (this.options.emitShape) {
|
|
3439
2586
|
case "circle": {
|
|
@@ -3453,8 +2600,8 @@ class bt {
|
|
|
3453
2600
|
const { x: c, y: u } = i.localToWorld(e, r);
|
|
3454
2601
|
this.x.push(c), this.y.push(u);
|
|
3455
2602
|
}
|
|
3456
|
-
const s = this.options.animation, a = this.animations,
|
|
3457
|
-
a.speed.create(s.speed, 0, t), a.velocity.create(s.velocity, p.ZERO, t), a.color.create(s.color, x.White, t), this.rotation.push(
|
|
2603
|
+
const s = this.options.animation, a = this.animations, h = a.scale.create(s.scale, 1, t), o = a.rotation.create(s.rotation, 0, t);
|
|
2604
|
+
a.speed.create(s.speed, 0, t), a.velocity.create(s.velocity, p.ZERO, t), a.color.create(s.color, x.White, t), this.rotation.push(o), this.scaleX.push(h), this.scaleY.push(h), this.color.pushUint32(x.packColor(
|
|
3458
2605
|
a.color.get(this.count, 0),
|
|
3459
2606
|
a.color.get(this.count, 1),
|
|
3460
2607
|
a.color.get(this.count, 2),
|
|
@@ -3462,10 +2609,6 @@ class bt {
|
|
|
3462
2609
|
this.rapid.premultipliedAlpha
|
|
3463
2610
|
)), this.count += 1;
|
|
3464
2611
|
}
|
|
3465
|
-
/**
|
|
3466
|
-
* Updates the emitter and all live particles.
|
|
3467
|
-
* @param deltaTime - Seconds elapsed since last frame
|
|
3468
|
-
*/
|
|
3469
2612
|
update(t) {
|
|
3470
2613
|
if (this.emitting && this.emitRate > 0)
|
|
3471
2614
|
if (this.emitTime > 0) {
|
|
@@ -3479,27 +2622,27 @@ class bt {
|
|
|
3479
2622
|
r > 0 && (this.emit(r), this.emitTimer -= r / this.emitRate);
|
|
3480
2623
|
}
|
|
3481
2624
|
const e = this.updateParticle(t);
|
|
3482
|
-
this.count -= e.length,
|
|
2625
|
+
this.count -= e.length, A.removeAtIndices(e, this.getAllArrayBuffer());
|
|
3483
2626
|
}
|
|
3484
2627
|
updateParticle(t) {
|
|
3485
2628
|
const e = [], r = this.animations;
|
|
3486
2629
|
Object.values(r).forEach((i) => i.update(t));
|
|
3487
2630
|
for (let i = 0; i < this.count; i++) {
|
|
3488
|
-
|
|
2631
|
+
if (this.remainingLife.typedArray[i] -= t, this.remainingLife.typedArray[i] <= 0) {
|
|
2632
|
+
e.push(i);
|
|
2633
|
+
continue;
|
|
2634
|
+
}
|
|
2635
|
+
const s = r.rotation.get(i), a = r.scale.get(i), h = r.speed.get(i);
|
|
3489
2636
|
this.rotation.typedArray[i] = s, this.scaleX.typedArray[i] = a, this.scaleY.typedArray[i] = a, this.color.uint32[i] = x.packColor(
|
|
3490
2637
|
r.color.get(i, 0),
|
|
3491
2638
|
r.color.get(i, 1),
|
|
3492
2639
|
r.color.get(i, 2),
|
|
3493
2640
|
r.color.get(i, 3),
|
|
3494
2641
|
this.rapid.premultipliedAlpha
|
|
3495
|
-
), this.x.typedArray[i] += (
|
|
2642
|
+
), this.x.typedArray[i] += (h * Math.cos(s) + r.velocity.get(i, 0)) * t, this.y.typedArray[i] += (h * Math.sin(s) + r.velocity.get(i, 1)) * t;
|
|
3496
2643
|
}
|
|
3497
2644
|
return e;
|
|
3498
2645
|
}
|
|
3499
|
-
/**
|
|
3500
|
-
* Renders all live particles.
|
|
3501
|
-
* In local-space mode the emitter's own transform is applied around the batch.
|
|
3502
|
-
*/
|
|
3503
2646
|
render() {
|
|
3504
2647
|
const t = this.options, e = this.localSpace ? void 0 : this.rapid.matrix.alloc();
|
|
3505
2648
|
this.rapid.drawParticles({
|
|
@@ -3518,53 +2661,50 @@ class bt {
|
|
|
3518
2661
|
customMatrix: e
|
|
3519
2662
|
});
|
|
3520
2663
|
}
|
|
3521
|
-
/** Returns `true` if the emitter is running or still has live particles. */
|
|
3522
2664
|
isActive() {
|
|
3523
2665
|
return this.emitting || this.count > 0;
|
|
3524
2666
|
}
|
|
3525
|
-
/**
|
|
3526
|
-
* Convenience: emit `emitRate` particles in one shot (fire-and-forget burst).
|
|
3527
|
-
*/
|
|
3528
2667
|
oneShot() {
|
|
3529
2668
|
this.emit(this.emitRate);
|
|
3530
2669
|
}
|
|
3531
2670
|
}
|
|
3532
2671
|
export {
|
|
3533
|
-
|
|
3534
|
-
|
|
3535
|
-
|
|
3536
|
-
|
|
2672
|
+
S as ArrayType,
|
|
2673
|
+
V as BaseTexture,
|
|
2674
|
+
oe as BlendMode,
|
|
2675
|
+
ce as CanvasScaleMode,
|
|
3537
2676
|
x as Color,
|
|
3538
|
-
|
|
3539
|
-
|
|
3540
|
-
|
|
3541
|
-
|
|
3542
|
-
|
|
3543
|
-
|
|
3544
|
-
|
|
3545
|
-
|
|
3546
|
-
|
|
3547
|
-
|
|
3548
|
-
|
|
3549
|
-
|
|
3550
|
-
|
|
3551
|
-
|
|
2677
|
+
ut as CustomGlShader,
|
|
2678
|
+
A as DynamicArrayBuffer,
|
|
2679
|
+
Tt as GLShader,
|
|
2680
|
+
Yt as GraphicRegion,
|
|
2681
|
+
$t as LineTextureMode,
|
|
2682
|
+
he as MaskType,
|
|
2683
|
+
bt as MatrixStack,
|
|
2684
|
+
At as MatrixStore,
|
|
2685
|
+
wt as ParticleEmitter,
|
|
2686
|
+
ae as ParticleRegion,
|
|
2687
|
+
le as ParticleShape,
|
|
2688
|
+
Dt as QUAD_VERTICES,
|
|
2689
|
+
de as Rapid,
|
|
2690
|
+
Et as Region,
|
|
2691
|
+
Ct as RenderTexture,
|
|
3552
2692
|
ot as SpriteRegion,
|
|
3553
|
-
|
|
3554
|
-
|
|
2693
|
+
Pt as TextTexture,
|
|
2694
|
+
N as Texture,
|
|
3555
2695
|
ht as TextureFilterMode,
|
|
3556
|
-
|
|
3557
|
-
|
|
2696
|
+
Ut as TextureManager,
|
|
2697
|
+
q as TextureWrapMode,
|
|
3558
2698
|
p as Vec2,
|
|
3559
2699
|
it as WebglBufferArray,
|
|
3560
|
-
|
|
3561
|
-
|
|
3562
|
-
|
|
3563
|
-
|
|
3564
|
-
|
|
3565
|
-
|
|
3566
|
-
|
|
3567
|
-
|
|
3568
|
-
|
|
3569
|
-
|
|
2700
|
+
Xt as composeProjectionWithAffine,
|
|
2701
|
+
ie as drawCircle,
|
|
2702
|
+
Rt as drawGraphic,
|
|
2703
|
+
te as drawLine,
|
|
2704
|
+
ee as drawMaskImage,
|
|
2705
|
+
Jt as drawParticles,
|
|
2706
|
+
re as drawRect,
|
|
2707
|
+
Zt as drawSprite,
|
|
2708
|
+
qt as getColorUint32,
|
|
2709
|
+
zt as multiplyMat4
|
|
3570
2710
|
};
|