@kalyptos/narcissus 0.2.0 → 0.2.1
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.
|
@@ -116,7 +116,7 @@ function S(e, t, n, r) {
|
|
|
116
116
|
}
|
|
117
117
|
//#endregion
|
|
118
118
|
//#region src/engine/gpu/masks.ts
|
|
119
|
-
var C = 8, w = 3e38, T = class {
|
|
119
|
+
var C = 8, w = 3e38, T = 4, E = class {
|
|
120
120
|
layout;
|
|
121
121
|
#e;
|
|
122
122
|
#t;
|
|
@@ -129,8 +129,9 @@ var C = 8, w = 3e38, T = class {
|
|
|
129
129
|
0
|
|
130
130
|
];
|
|
131
131
|
#o = [];
|
|
132
|
+
#s = null;
|
|
132
133
|
constructor(e) {
|
|
133
|
-
this.#e = e, this.layout = x(e, "masks", GPUShaderStage.COMPUTE, ["read-only-storage"]), this.#t = this.#
|
|
134
|
+
this.#e = e, this.layout = x(e, "masks", GPUShaderStage.COMPUTE, ["read-only-storage"]), this.#t = this.#c(64);
|
|
134
135
|
}
|
|
135
136
|
get group() {
|
|
136
137
|
return this.#n ??= S(this.#e, "masks", this.layout, [this.#t]);
|
|
@@ -151,20 +152,21 @@ var C = 8, w = 3e38, T = class {
|
|
|
151
152
|
targets: t,
|
|
152
153
|
enabled: !0,
|
|
153
154
|
area: r
|
|
154
|
-
}), this.#i;
|
|
155
|
+
}), this.#s = null, this.#i;
|
|
155
156
|
}
|
|
156
157
|
enable(e, t) {
|
|
157
158
|
let n = this.#r.get(e);
|
|
158
159
|
n && (n.enabled = t);
|
|
159
160
|
}
|
|
160
161
|
delete(e) {
|
|
161
|
-
this.#r.delete(e);
|
|
162
|
+
this.#r.delete(e) && (this.#s = null);
|
|
162
163
|
}
|
|
163
164
|
area(e) {
|
|
164
165
|
return this.#r.get(e)?.area;
|
|
165
166
|
}
|
|
166
167
|
relate(e, t, n, r) {
|
|
167
|
-
for (let
|
|
168
|
+
for (let i of (this.#s ??= new D(this.#r)).near(t, n)) {
|
|
169
|
+
let { prism: a, targets: o, enabled: s, area: c } = this.#r.get(i);
|
|
168
170
|
if (!s || !o.has(e) || n[0] < c[0] || n[1] < c[1] || t[0] > c[2] || t[1] > c[3]) continue;
|
|
169
171
|
let l = y(a, t, n);
|
|
170
172
|
if (l === 1) return !0;
|
|
@@ -195,19 +197,55 @@ var C = 8, w = 3e38, T = class {
|
|
|
195
197
|
o.set(e, c++);
|
|
196
198
|
}
|
|
197
199
|
for (let n = 0; n < e.length; n++) t[s + n] = o.get(e[n]) ?? 0;
|
|
198
|
-
t.byteLength > this.#t.size && (this.#t.destroy(), this.#t = this.#
|
|
200
|
+
t.byteLength > this.#t.size && (this.#t.destroy(), this.#t = this.#c(t.byteLength), this.#n = null), t.length && this.#e.queue.writeBuffer(this.#t, 0, t);
|
|
199
201
|
}
|
|
200
202
|
destroy() {
|
|
201
203
|
this.#t.destroy();
|
|
202
204
|
}
|
|
203
|
-
#
|
|
205
|
+
#c(e) {
|
|
204
206
|
return this.#e.createBuffer({
|
|
205
207
|
label: "masks",
|
|
206
208
|
size: Math.max(256, 2 ** Math.ceil(Math.log2(e))),
|
|
207
209
|
usage: GPUBufferUsage.STORAGE | GPUBufferUsage.COPY_DST
|
|
208
210
|
});
|
|
209
211
|
}
|
|
210
|
-
},
|
|
212
|
+
}, D = class {
|
|
213
|
+
#e;
|
|
214
|
+
#t;
|
|
215
|
+
#n = /* @__PURE__ */ new Map();
|
|
216
|
+
#r = [];
|
|
217
|
+
constructor(e) {
|
|
218
|
+
this.#e = [...e.keys()];
|
|
219
|
+
let t = [...e.values()].map(({ area: e }) => Math.max(e[2] - e[0], e[3] - e[1])).sort((e, t) => e - t);
|
|
220
|
+
this.#t = Math.max(t[t.length >> 1] ?? 1, .001);
|
|
221
|
+
for (let [t, { area: n }] of e) {
|
|
222
|
+
let [e, r, i, a] = O(n[0], n[1], n[2], n[3], this.#t);
|
|
223
|
+
if (i - e >= T || a - r >= T) this.#r.push(t);
|
|
224
|
+
else for (let n = e; n <= i; n++) for (let e = r; e <= a; e++) {
|
|
225
|
+
let r = this.#n.get(`${n},${e}`);
|
|
226
|
+
r ? r.push(t) : this.#n.set(`${n},${e}`, [t]);
|
|
227
|
+
}
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
near(e, t) {
|
|
231
|
+
let [n, r, i, a] = O(e[0], e[1], t[0], t[1], this.#t);
|
|
232
|
+
if ((i - n + 1) * (a - r + 1) > this.#e.length) return this.#e;
|
|
233
|
+
let o = new Set(this.#r);
|
|
234
|
+
for (let e = n; e <= i; e++) for (let t = r; t <= a; t++) for (let n of this.#n.get(`${e},${t}`) ?? []) o.add(n);
|
|
235
|
+
return o;
|
|
236
|
+
}
|
|
237
|
+
};
|
|
238
|
+
function O(e, t, n, r, i) {
|
|
239
|
+
return [
|
|
240
|
+
Math.floor(e / i),
|
|
241
|
+
Math.floor(t / i),
|
|
242
|
+
Math.floor(n / i),
|
|
243
|
+
Math.floor(r / i)
|
|
244
|
+
];
|
|
245
|
+
}
|
|
246
|
+
//#endregion
|
|
247
|
+
//#region src/engine/gpu/pool.ts
|
|
248
|
+
var k = 19, A = 23, j = 7, M = 11, N = [], ee = 1024, te = class {
|
|
211
249
|
#e = [];
|
|
212
250
|
mark(e, t) {
|
|
213
251
|
this.#e.push([e, t]);
|
|
@@ -220,11 +258,11 @@ var C = 8, w = 3e38, T = class {
|
|
|
220
258
|
this.#e = [];
|
|
221
259
|
for (let i = 0; i < r.length;) {
|
|
222
260
|
let a = r[i][0], o = r[i++][1];
|
|
223
|
-
for (; i < r.length && r[i][0] <= o +
|
|
261
|
+
for (; i < r.length && r[i][0] <= o + ee;) o = Math.max(o, r[i++][1]);
|
|
224
262
|
e.writeBuffer(t, a * 4, n, a, o - a);
|
|
225
263
|
}
|
|
226
264
|
}
|
|
227
|
-
},
|
|
265
|
+
}, ne = class {
|
|
228
266
|
geometry;
|
|
229
267
|
colour;
|
|
230
268
|
pages;
|
|
@@ -249,25 +287,26 @@ var C = 8, w = 3e38, T = class {
|
|
|
249
287
|
];
|
|
250
288
|
#u;
|
|
251
289
|
#d;
|
|
252
|
-
#f = new
|
|
290
|
+
#f = new te();
|
|
253
291
|
#p;
|
|
254
292
|
#m;
|
|
255
|
-
#h = new
|
|
293
|
+
#h = new te();
|
|
256
294
|
#g;
|
|
257
295
|
#_ = [];
|
|
258
296
|
#v;
|
|
259
297
|
#y;
|
|
260
298
|
#b = !1;
|
|
299
|
+
#x = null;
|
|
261
300
|
constructor(e, t) {
|
|
262
|
-
this.capacity = t, this.masks = new
|
|
301
|
+
this.capacity = t, this.masks = new E(e), this.#e = e;
|
|
263
302
|
let n = this.slots;
|
|
264
|
-
this.#
|
|
303
|
+
this.#w(), this.#a = new Uint8Array(n), this.#o = n, this.#c = Array.from({ length: n }, (e, t) => n - 1 - t), this.#u = new Uint32Array(n * 36), this.#d = new Float32Array(this.#u.buffer), this.#p = new Uint32Array(n * 12), this.#m = new Float32Array(this.#p.buffer), this.#g = new Uint32Array(n), this.#v = new Uint8Array(n), this.#y = Array(n).fill(N);
|
|
265
304
|
}
|
|
266
305
|
get slots() {
|
|
267
306
|
return this.capacity / 256;
|
|
268
307
|
}
|
|
269
308
|
get bytes() {
|
|
270
|
-
return this.#
|
|
309
|
+
return this.#C().reduce((e, t) => e + t.size, 0);
|
|
271
310
|
}
|
|
272
311
|
has(e) {
|
|
273
312
|
let t = this.#t.get(e);
|
|
@@ -282,13 +321,13 @@ var C = 8, w = 3e38, T = class {
|
|
|
282
321
|
add(t, n, r, i, a = 0) {
|
|
283
322
|
if (this.#t.has(t)) return !0;
|
|
284
323
|
let o = d(n.count) / 256;
|
|
285
|
-
if (!this.#
|
|
324
|
+
if (!this.#D(o, i)) return !1;
|
|
286
325
|
let s = e.origin, c = {
|
|
287
326
|
id: t,
|
|
288
327
|
previous: null,
|
|
289
328
|
next: null,
|
|
290
329
|
page: n,
|
|
291
|
-
slots: this.#
|
|
330
|
+
slots: this.#F(o),
|
|
292
331
|
active: [],
|
|
293
332
|
mask: 0,
|
|
294
333
|
table: this.#c.pop(),
|
|
@@ -300,14 +339,14 @@ var C = 8, w = 3e38, T = class {
|
|
|
300
339
|
factors: 0,
|
|
301
340
|
layer: a
|
|
302
341
|
};
|
|
303
|
-
return this.#t.set(t, c), this.#
|
|
342
|
+
return this.#t.set(t, c), this.#E(c), this.#i.add(t), !0;
|
|
304
343
|
}
|
|
305
344
|
remove(e) {
|
|
306
345
|
let t = this.#t.get(e);
|
|
307
346
|
if (t) {
|
|
308
|
-
this.#
|
|
309
|
-
for (let e of t.slots) this.#a[e] = 0, this.#v[e] = 0, this.#y[e].length && (this.#b = !0), this.#y[e] =
|
|
310
|
-
this.#s = Math.min(this.#s, t.slots[0]), this.#o += t.slots.length, this.#c.push(t.table), t.page === null && t.factors !== 0 && this.#
|
|
347
|
+
this.#T(t), this.#t.delete(e), this.#i.delete(e);
|
|
348
|
+
for (let e of t.slots) this.#a[e] = 0, this.#v[e] = 0, this.#y[e].length && (this.#b = !0), this.#y[e] = N;
|
|
349
|
+
this.#s = Math.min(this.#s, t.slots[0]), this.#o += t.slots.length, this.#c.push(t.table), t.page === null && t.factors !== 0 && this.#A(t, 0);
|
|
311
350
|
}
|
|
312
351
|
}
|
|
313
352
|
clear() {
|
|
@@ -320,19 +359,20 @@ var C = 8, w = 3e38, T = class {
|
|
|
320
359
|
let t = 0;
|
|
321
360
|
for (let n of this.#i) {
|
|
322
361
|
if (t >= e) break;
|
|
323
|
-
t += this.#
|
|
362
|
+
t += this.#O(this.#t.get(n)), this.#i.delete(n);
|
|
324
363
|
}
|
|
325
364
|
return t;
|
|
326
365
|
}
|
|
327
366
|
draw(e) {
|
|
367
|
+
this.#x &&= (this.#j(this.#x), null);
|
|
328
368
|
let t = 0, n = 0, r = !1;
|
|
329
369
|
for (let { id: i, factors: a } of e) {
|
|
330
370
|
let e = this.#t.get(i);
|
|
331
371
|
if (!e || e.page !== null) continue;
|
|
332
372
|
let o = e.active;
|
|
333
|
-
(e.factors !== a || e.mask < 0) && this.#
|
|
373
|
+
(e.factors !== a || e.mask < 0) && this.#A(e, a), r ||= o !== e.active, this.#E(e), r ||= this.#_[n] !== e, this.#_[n++] = e, r && this.#g.set(e.active, t), t += e.active.length;
|
|
334
374
|
}
|
|
335
|
-
r ||= this.#_.length !== n, this.#_.length = n, this.listed = t, this.#b && this.#
|
|
375
|
+
r ||= this.#_.length !== n, this.#_.length = n, this.listed = t, this.#b && this.#P();
|
|
336
376
|
let i = this.#e.queue;
|
|
337
377
|
this.#f.flush(i, this.pages, this.#u), this.#h.flush(i, this.clusters, this.#p), r && t && i.writeBuffer(this.list, 0, this.#g, 0, t);
|
|
338
378
|
}
|
|
@@ -342,26 +382,35 @@ var C = 8, w = 3e38, T = class {
|
|
|
342
382
|
e[1],
|
|
343
383
|
e[2]
|
|
344
384
|
];
|
|
345
|
-
for (let e of this.#t.values()) e.page === null && this.#
|
|
385
|
+
for (let e of this.#t.values()) e.page === null && this.#k(e);
|
|
346
386
|
this.#e.queue.writeBuffer(this.pages, 0, this.#u), this.#f.clear(), this.masks.setOrigin(this.#l), this.masks.size && this.masks.write();
|
|
347
387
|
}
|
|
348
388
|
addMask(e, t) {
|
|
349
389
|
let n = this.masks.add(e, t);
|
|
350
|
-
return this.#
|
|
390
|
+
return this.#S(this.masks.area(n)), n;
|
|
351
391
|
}
|
|
352
392
|
enableMask(e, t) {
|
|
353
|
-
this.masks.enable(e, t), this.#
|
|
393
|
+
this.masks.enable(e, t), this.#S(this.masks.area(e));
|
|
354
394
|
}
|
|
355
395
|
deleteMask(e) {
|
|
356
396
|
let t = this.masks.area(e);
|
|
357
|
-
this.masks.delete(e), this.#
|
|
397
|
+
this.masks.delete(e), this.#S(t);
|
|
398
|
+
}
|
|
399
|
+
#S(e) {
|
|
400
|
+
let t = this.#x ??= [
|
|
401
|
+
Infinity,
|
|
402
|
+
Infinity,
|
|
403
|
+
-Infinity,
|
|
404
|
+
-Infinity
|
|
405
|
+
];
|
|
406
|
+
t[0] = Math.min(t[0], e[0]), t[1] = Math.min(t[1], e[1]), t[2] = Math.max(t[2], e[2]), t[3] = Math.max(t[3], e[3]);
|
|
358
407
|
}
|
|
359
408
|
grow(e) {
|
|
360
409
|
if (e <= this.capacity) return;
|
|
361
|
-
let t = this.slots, n = this.#
|
|
362
|
-
this.capacity = e, this.#
|
|
410
|
+
let t = this.slots, n = this.#C();
|
|
411
|
+
this.capacity = e, this.#w();
|
|
363
412
|
let r = this.#e.createCommandEncoder({ label: "pool grow" });
|
|
364
|
-
this.#
|
|
413
|
+
this.#C().forEach((e, t) => r.copyBufferToBuffer(n[t], 0, e, 0, n[t].size)), this.#e.queue.submit([r.finish()]);
|
|
365
414
|
for (let e of n) e.destroy();
|
|
366
415
|
let i = this.slots, a = new Uint8Array(i);
|
|
367
416
|
a.set(this.#a), this.#a = a, this.#o += i - t;
|
|
@@ -374,13 +423,13 @@ var C = 8, w = 3e38, T = class {
|
|
|
374
423
|
c.set(this.#g), this.#g = c;
|
|
375
424
|
let l = new Uint8Array(i);
|
|
376
425
|
l.set(this.#v), this.#v = l;
|
|
377
|
-
for (let e = t; e < i; e++) this.#y.push(
|
|
426
|
+
for (let e = t; e < i; e++) this.#y.push(N);
|
|
378
427
|
}
|
|
379
428
|
destroy() {
|
|
380
|
-
for (let e of this.#
|
|
429
|
+
for (let e of this.#C()) e.destroy();
|
|
381
430
|
this.masks.destroy();
|
|
382
431
|
}
|
|
383
|
-
#
|
|
432
|
+
#C() {
|
|
384
433
|
return [
|
|
385
434
|
this.geometry,
|
|
386
435
|
this.colour,
|
|
@@ -389,7 +438,7 @@ var C = 8, w = 3e38, T = class {
|
|
|
389
438
|
this.list
|
|
390
439
|
];
|
|
391
440
|
}
|
|
392
|
-
#
|
|
441
|
+
#w() {
|
|
393
442
|
let { capacity: e, slots: t } = this, n = GPUBufferUsage.STORAGE | GPUBufferUsage.COPY_DST | GPUBufferUsage.COPY_SRC, r = (e, t) => this.#e.createBuffer({
|
|
394
443
|
label: e,
|
|
395
444
|
size: t,
|
|
@@ -397,13 +446,13 @@ var C = 8, w = 3e38, T = class {
|
|
|
397
446
|
});
|
|
398
447
|
this.geometry = r("pool geometry", e * 4 * 4), this.colour = r("pool colour", e * 3 * 4), this.pages = r("pool pages", t * 36 * 4), this.clusters = r("pool clusters", t * 12 * 4), this.list = r("pool list", t * 4);
|
|
399
448
|
}
|
|
400
|
-
#
|
|
449
|
+
#T(e) {
|
|
401
450
|
e.previous ? e.previous.next = e.next : this.#n === e && (this.#n = e.next), e.next ? e.next.previous = e.previous : this.#r === e && (this.#r = e.previous), e.previous = null, e.next = null;
|
|
402
451
|
}
|
|
403
|
-
#
|
|
404
|
-
this.#r !== e && (this.#
|
|
452
|
+
#E(e) {
|
|
453
|
+
this.#r !== e && (this.#T(e), e.previous = this.#r, this.#r ? this.#r.next = e : this.#n = e, this.#r = e);
|
|
405
454
|
}
|
|
406
|
-
#
|
|
455
|
+
#D(e, t) {
|
|
407
456
|
let n = this.#o;
|
|
408
457
|
if (n >= e) return !0;
|
|
409
458
|
let r = [];
|
|
@@ -412,7 +461,7 @@ var C = 8, w = 3e38, T = class {
|
|
|
412
461
|
for (let e of r) this.remove(e);
|
|
413
462
|
return !0;
|
|
414
463
|
}
|
|
415
|
-
#
|
|
464
|
+
#O(t) {
|
|
416
465
|
let n = t.page, { slots: r } = t, i = this.#e.queue, a = r.length, o = this.#p, s = this.#m;
|
|
417
466
|
for (let e = 0; e < a; e++) {
|
|
418
467
|
let i = r[e] * 12;
|
|
@@ -426,13 +475,13 @@ var C = 8, w = 3e38, T = class {
|
|
|
426
475
|
i.writeBuffer(this.geometry, c * 4 * 4, n.geometry, o * 4, s * 4), i.writeBuffer(this.colour, c * 3 * 4, n.colour, o * 3, s * 3), this.#h.mark(r[e] * 12, (r[e] + t) * 12), e += t;
|
|
427
476
|
}
|
|
428
477
|
let c = t.table * 36, l = this.#u, u = this.#d, d = n.params, [f, p, m] = n.quadrants;
|
|
429
|
-
return l.fill(0, c, c + 36), this.#
|
|
478
|
+
return l.fill(0, c, c + 36), this.#k(t), l[c + 3] = n.count, u.set(d.subarray(e.step, e.step + 3), c + 4), l[c + 7] = f, u.set(d.subarray(e.scaleMin, e.scaleMin + 3), c + 8), l[c + 11] = p, u.set(d.subarray(e.scaleMax, e.scaleMax + 3), c + 12), l[c + 15] = m, u.set(d.subarray(e.dcMin, e.dcMin + 3), c + 16), u.set(d.subarray(e.dcMax, e.dcMax + 3), c + 20), l[c + A] = t.layer, u.set(d.subarray(e.shScale, e.shScale + 9), c + 24), this.#f.mark(c, c + 36), t.page = null, this.masks.size && this.#N(t), n.count * 7 * 4 + a * 12 * 4 + 144;
|
|
430
479
|
}
|
|
431
|
-
#
|
|
480
|
+
#k(e) {
|
|
432
481
|
let t = e.table * 36;
|
|
433
482
|
for (let n = 0; n < 3; n++) this.#d[t + n] = e.base[n] - this.#l[n];
|
|
434
483
|
}
|
|
435
|
-
#
|
|
484
|
+
#A(e, t) {
|
|
436
485
|
let n = 0;
|
|
437
486
|
for (let e = 0; e < 4; e++) t >>> 8 * e & 255 && (n |= 1 << e);
|
|
438
487
|
if (n !== e.mask) {
|
|
@@ -450,10 +499,10 @@ var C = 8, w = 3e38, T = class {
|
|
|
450
499
|
}
|
|
451
500
|
}
|
|
452
501
|
e.factors = t;
|
|
453
|
-
let r = e.table * 36 +
|
|
502
|
+
let r = e.table * 36 + k;
|
|
454
503
|
this.#u[r] = t, this.#f.mark(r, r + 1);
|
|
455
504
|
}
|
|
456
|
-
#
|
|
505
|
+
#j(e) {
|
|
457
506
|
let t = [
|
|
458
507
|
0,
|
|
459
508
|
0,
|
|
@@ -463,14 +512,14 @@ var C = 8, w = 3e38, T = class {
|
|
|
463
512
|
0,
|
|
464
513
|
0
|
|
465
514
|
];
|
|
466
|
-
for (let r of this.#t.values()) r.page === null && r.slots.some((i) => (this.#
|
|
515
|
+
for (let r of this.#t.values()) r.page === null && r.slots.some((i) => (this.#M(r, i, t, n), n[0] >= e[0] && n[1] >= e[1] && t[0] <= e[2] && t[1] <= e[3])) && this.#N(r);
|
|
467
516
|
this.#b = !0;
|
|
468
517
|
}
|
|
469
|
-
#
|
|
518
|
+
#M(e, t, n, r) {
|
|
470
519
|
let i = this.#m, a = t * 12;
|
|
471
520
|
for (let t = 0; t < 3; t++) n[t] = e.base[t] + i[a + 4 + t], r[t] = e.base[t] + i[a + 8 + t];
|
|
472
521
|
}
|
|
473
|
-
#
|
|
522
|
+
#N(e) {
|
|
474
523
|
let t = [
|
|
475
524
|
0,
|
|
476
525
|
0,
|
|
@@ -481,23 +530,23 @@ var C = 8, w = 3e38, T = class {
|
|
|
481
530
|
0
|
|
482
531
|
];
|
|
483
532
|
for (let r of e.slots) {
|
|
484
|
-
this.#
|
|
533
|
+
this.#M(e, r, t, n);
|
|
485
534
|
let i = [], a = +!!this.masks.relate(e.layer, t, n, i), o = this.#y[r];
|
|
486
|
-
a !== this.#v[r] && (e.mask = -1), this.#v[r] = a, (o.length || i.length) && (this.#b = !0), this.#y[r] = i.length ? i :
|
|
535
|
+
a !== this.#v[r] && (e.mask = -1), this.#v[r] = a, (o.length || i.length) && (this.#b = !0), this.#y[r] = i.length ? i : N;
|
|
487
536
|
}
|
|
488
537
|
}
|
|
489
|
-
#
|
|
538
|
+
#P() {
|
|
490
539
|
this.#b = !1;
|
|
491
540
|
let e = this.#p, t = [], n = this.masks.listBase;
|
|
492
541
|
for (let r = 0; r < this.#y.length; r++) {
|
|
493
542
|
let i = this.#y[r], a = r * 12, o = i.length ? n : 0;
|
|
494
|
-
(e[a +
|
|
543
|
+
(e[a + j] !== o || e[a + M] !== i.length) && (e[a + j] = o, e[a + M] = i.length, this.#h.mark(a, a + 12));
|
|
495
544
|
for (let e of i) t.push(e);
|
|
496
545
|
n += i.length;
|
|
497
546
|
}
|
|
498
547
|
this.masks.write(t);
|
|
499
548
|
}
|
|
500
|
-
#
|
|
549
|
+
#F(e) {
|
|
501
550
|
let t = this.#a, n = -1;
|
|
502
551
|
for (let r = this.#s; r <= t.length - e;) {
|
|
503
552
|
let i = r;
|
|
@@ -518,7 +567,7 @@ var C = 8, w = 3e38, T = class {
|
|
|
518
567
|
};
|
|
519
568
|
//#endregion
|
|
520
569
|
//#region src/engine/math/mat4.ts
|
|
521
|
-
function
|
|
570
|
+
function re(e, t) {
|
|
522
571
|
let n = Math.cos(t);
|
|
523
572
|
return [
|
|
524
573
|
Math.sin(e) * n,
|
|
@@ -526,30 +575,30 @@ function te(e, t) {
|
|
|
526
575
|
Math.sin(t)
|
|
527
576
|
];
|
|
528
577
|
}
|
|
529
|
-
function
|
|
530
|
-
let [i, a, o] =
|
|
578
|
+
function ie(e, t, n, r) {
|
|
579
|
+
let [i, a, o] = re(n, r), s = Math.cos(n), c = -Math.sin(n), l = c * o, u = -s * o, d = s * a - c * i;
|
|
531
580
|
return e[0] = s, e[1] = l, e[2] = -i, e[3] = 0, e[4] = c, e[5] = u, e[6] = -a, e[7] = 0, e[8] = 0, e[9] = d, e[10] = -o, e[11] = 0, e[12] = -(s * t[0] + c * t[1]), e[13] = -(l * t[0] + u * t[1] + d * t[2]), e[14] = i * t[0] + a * t[1] + o * t[2], e[15] = 1, e;
|
|
532
581
|
}
|
|
533
|
-
function
|
|
582
|
+
function ae(e, t, n, r, i) {
|
|
534
583
|
let a = 1 / Math.tan(t / 2);
|
|
535
584
|
return e.fill(0), e[0] = a / n, e[5] = a, e[10] = i / (r - i), e[11] = -1, e[14] = r * i / (r - i), e;
|
|
536
585
|
}
|
|
537
|
-
var
|
|
538
|
-
function
|
|
586
|
+
var oe = /* @__PURE__ */ new Float64Array(16);
|
|
587
|
+
function P(e, t, n) {
|
|
539
588
|
for (let e = 0; e < 4; e++) for (let r = 0; r < 4; r++) {
|
|
540
589
|
let i = 0;
|
|
541
590
|
for (let a = 0; a < 4; a++) i += t[a * 4 + r] * n[e * 4 + a];
|
|
542
|
-
|
|
591
|
+
oe[e * 4 + r] = i;
|
|
543
592
|
}
|
|
544
|
-
return e.set(
|
|
593
|
+
return e.set(oe), e;
|
|
545
594
|
}
|
|
546
|
-
function
|
|
595
|
+
function se(e, t) {
|
|
547
596
|
let [n, r, i, a, o, s, c, l, u, d, f, p, m, h, g, _] = t, v = n * s - r * o, y = n * c - i * o, b = n * l - a * o, x = r * c - i * s, S = r * l - a * s, C = i * l - a * c, w = u * h - d * m, T = u * g - f * m, E = u * _ - p * m, D = d * g - f * h, O = d * _ - p * h, k = f * _ - p * g, A = v * k - y * O + b * D + x * E - S * T + C * w;
|
|
548
597
|
if (!A) return null;
|
|
549
598
|
let j = 1 / A;
|
|
550
599
|
return e[0] = (s * k - c * O + l * D) * j, e[1] = (i * O - r * k - a * D) * j, e[2] = (h * C - g * S + _ * x) * j, e[3] = (f * S - d * C - p * x) * j, e[4] = (c * E - o * k - l * T) * j, e[5] = (n * k - i * E + a * T) * j, e[6] = (g * b - m * C - _ * y) * j, e[7] = (u * C - f * b + p * y) * j, e[8] = (o * O - s * E + l * w) * j, e[9] = (r * E - n * O - a * w) * j, e[10] = (m * S - h * b + _ * v) * j, e[11] = (d * b - u * S - p * v) * j, e[12] = (s * T - o * D - c * w) * j, e[13] = (n * D - r * T + i * w) * j, e[14] = (h * y - m * x - g * v) * j, e[15] = (u * x - d * y + f * v) * j, e;
|
|
551
600
|
}
|
|
552
|
-
function
|
|
601
|
+
function ce(e, t) {
|
|
553
602
|
let [n, r, i] = t;
|
|
554
603
|
return [
|
|
555
604
|
e[0] * n + e[4] * r + e[8] * i + e[12],
|
|
@@ -560,7 +609,7 @@ function oe(e, t) {
|
|
|
560
609
|
}
|
|
561
610
|
//#endregion
|
|
562
611
|
//#region src/engine/gpu/common.wgsl?raw
|
|
563
|
-
var
|
|
612
|
+
var F = "// shared by every engine pass; sizes and word offsets mirror format/spec.ts\n\nconst KEY_BITS: u32 = 24u;\n// word offsets in the work buffer, layout.ts WORK\nconst WORK_VISIBLE: u32 = 0u;\nconst WORK_PROJECTED: u32 = 4u;\nconst WORK_LIST: u32 = 16u;\n// workgroups a dispatch row holds\nconst GROUPS_X: u32 = 65535u;\nconst C0: f32 = 0.28209479177387814;\nconst C1: f32 = 0.4886025119029199;\n\n// floating-origin ENU frame; camera looks down -z of view space\nstruct FrameUniforms {\n view: mat4x4f,\n proj: mat4x4f,\n viewProj: mat4x4f,\n // inside when dot(plane.xyz, p) + plane.w >= 0\n planes: array<vec4f, 6>,\n camera: vec3f,\n time: f32,\n // render target pixels\n viewport: vec2f,\n focal: vec2f,\n near: f32,\n far: f32,\n lowPass: f32,\n // drawn cluster ids in the pool's list\n clusters: u32,\n}\n\n// one resident page; dc and sh ranges are after the colour correction\nstruct Page {\n origin: vec3f,\n count: u32,\n step: vec3f,\n q1: u32,\n scaleMin: vec3f,\n q2: u32,\n scaleMax: vec3f,\n q3: u32,\n dcMin: vec3f,\n // quadrant k opacity 0-255 at bits 8k\n factors: u32,\n dcMax: vec3f,\n // 0 for the world, else the layer that holds the page\n layer: u32,\n shScale: array<vec4f, 3>,\n}\n\n// up to CLUSTER consecutive splats of one page in one pool slot\nstruct Cluster {\n page: u32,\n // first pool record\n slot: u32,\n // index in the page of its first splat\n first: u32,\n count: u32,\n // extents relative to the page origin\n boxMin: vec3f,\n // word in masks.wgsl's buffer of the list of masks that may hide some of its splats\n maskList: u32,\n boxMax: vec3f,\n maskCount: u32,\n}\n\n// a splat on screen; pixels with y up from the bottom-left of the target\nstruct Projected {\n centre: vec2f,\n // pack2x16float: 1-sigma major axis xy, 1-sigma minor axis xy\n axes: vec2u,\n // pack2x16float: r g, b opacity\n colour: vec2u,\n}\n\n// what a shade hook may change; position in the floating-origin frame, depth in view metres\nstruct Splat {\n position: vec3f,\n depth: f32,\n colour: vec3f,\n opacity: f32,\n scale: vec3f,\n}\n\n// the byte of word at bit, 0 to 1\nfn fraction(word: u32, bit: u32) -> f32 {\n return f32(extractBits(word, bit, 8u)) / 255.0;\n}\n\n// sigmas out to where a gaussian of opacity falls under 1/255, at most 3; the quad raster draws\nfn reach(opacity: f32) -> f32 {\n return min(3.0, sqrt(max(2.0 * log(255.0 * opacity), 0.0)));\n}\n", le = "// one thread per listed cluster\n\n@group(0) @binding(0) var<uniform> uniforms: FrameUniforms;\n@group(0) @binding(1) var<storage, read> pages: array<Page>;\n@group(0) @binding(2) var<storage, read> clusters: array<Cluster>;\n@group(0) @binding(3) var<storage, read> list: array<u32>;\n@group(0) @binding(4) var<storage, read_write> work: array<atomic<u32>>;\n\n// false only when the box lies wholly outside one plane\nfn inside(lo: vec3f, hi: vec3f) -> bool {\n for (var p = 0u; p < 6u; p++) {\n let plane = uniforms.planes[p];\n let corner = select(lo, hi, plane.xyz >= vec3f(0.0));\n if (dot(plane.xyz, corner) + plane.w < 0.0) {\n return false;\n }\n }\n return true;\n}\n\n@compute @workgroup_size(64)\nfn cull(@builtin(global_invocation_id) id: vec3u) {\n if (id.x >= uniforms.clusters) {\n return;\n }\n let slot = list[id.x];\n let cluster = clusters[slot];\n let page = pages[cluster.page];\n if (!inside(page.origin + cluster.boxMin, page.origin + cluster.boxMax)) {\n return;\n }\n atomicStore(&work[WORK_LIST + atomicAdd(&work[WORK_VISIBLE], 1u)], slot);\n}\n", ue = 64, de = class {
|
|
564
613
|
#e;
|
|
565
614
|
#t;
|
|
566
615
|
#n;
|
|
@@ -574,7 +623,7 @@ var P = "// shared by every engine pass; sizes and word offsets mirror format/sp
|
|
|
574
623
|
"storage"
|
|
575
624
|
]), i = e.createShaderModule({
|
|
576
625
|
label: "cull",
|
|
577
|
-
code: `${
|
|
626
|
+
code: `${F}\n${le}`
|
|
578
627
|
});
|
|
579
628
|
this.#t = e.createComputePipeline({
|
|
580
629
|
label: "cull",
|
|
@@ -598,10 +647,10 @@ var P = "// shared by every engine pass; sizes and word offsets mirror format/sp
|
|
|
598
647
|
label: "cull",
|
|
599
648
|
timestampWrites: t
|
|
600
649
|
});
|
|
601
|
-
n.setBindGroup(0, this.#n), n.setPipeline(this.#t), this.#e.listed && n.dispatchWorkgroups(Math.ceil(this.#e.listed /
|
|
650
|
+
n.setBindGroup(0, this.#n), n.setPipeline(this.#t), this.#e.listed && n.dispatchWorkgroups(Math.ceil(this.#e.listed / ue)), n.end();
|
|
602
651
|
}
|
|
603
|
-
},
|
|
604
|
-
function
|
|
652
|
+
}, fe = "// prisms that hide splats by centre; masks.ts writes the records, their vertices, then the clusters' lists\n\n// words of a record: min x y, max x y, min z, max z (f32), first vertex word, vertices\nconst MASK_WORDS: u32 = 8u;\n\n@group(1) @binding(0) var<storage, read> masks: array<u32>;\n\nfn maskFloat(k: u32) -> f32 {\n return bitcast<f32>(masks[k]);\n}\n\n// p, floating-origin frame, inside a mask of the cluster's list: its polygon by the even-odd rule and its z range\nfn masked(cluster: Cluster, p: vec3f) -> bool {\n for (var k = 0u; k < cluster.maskCount; k++) {\n let m = masks[cluster.maskList + k] * MASK_WORDS;\n if (p.x < maskFloat(m) || p.y < maskFloat(m + 1u) || p.x > maskFloat(m + 2u) ||\n p.y > maskFloat(m + 3u) || p.z < maskFloat(m + 4u) || p.z > maskFloat(m + 5u)) {\n continue;\n }\n let first = masks[m + 6u];\n let n = masks[m + 7u];\n var odd = false;\n var b = vec2f(maskFloat(first + 2u * n - 2u), maskFloat(first + 2u * n - 1u));\n for (var i = 0u; i < n; i++) {\n let a = vec2f(maskFloat(first + 2u * i), maskFloat(first + 2u * i + 1u));\n if ((a.y > p.y) != (b.y > p.y) && p.x < (b.x - a.x) * (p.y - a.y) / (b.y - a.y) + a.x) {\n odd = !odd;\n }\n b = a;\n }\n if (odd) {\n return true;\n }\n }\n return false;\n}\n", pe = "// the top of the solid drawn splats over a square of 1 m cells; one workgroup per listed cluster\n\nconst GROUP: u32 = 64u;\n\nstruct Area {\n // south-west corner, floating-origin frame\n corner: vec2f,\n cells: u32,\n clusters: u32,\n // least opacity and largest scale in metres of a splat that counts\n opacity: f32,\n scale: f32,\n}\n\n@group(0) @binding(0) var<uniform> area: Area;\n@group(0) @binding(1) var<storage, read> pages: array<Page>;\n@group(0) @binding(2) var<storage, read> clusters: array<Cluster>;\n@group(0) @binding(3) var<storage, read> list: array<u32>;\n@group(0) @binding(4) var<storage, read> geometry: array<vec4u>;\n@group(0) @binding(5) var<storage, read_write> tops: array<atomic<u32>>;\n\n// order-preserving bits of z, never 0, which marks an empty cell\nfn ordered(z: f32) -> u32 {\n let bits = bitcast<u32>(z);\n return select(bits | 0x80000000u, ~bits, z < 0.0);\n}\n\n@compute @workgroup_size(64)\nfn heights(@builtin(workgroup_id) wid: vec3u, @builtin(local_invocation_index) t: u32) {\n let index = wid.y * GROUPS_X + wid.x;\n if (index >= area.clusters) {\n return;\n }\n let cluster = clusters[list[index]];\n let page = pages[cluster.page];\n let size = f32(area.cells);\n let lo = page.origin.xy + cluster.boxMin.xy - area.corner;\n let hi = page.origin.xy + cluster.boxMax.xy - area.corner;\n if (any(hi < vec2f(0.0)) || any(lo >= vec2f(size))) {\n return;\n }\n for (var k = t; k < cluster.count; k += GROUP) {\n let g = geometry[cluster.slot + k];\n let i = cluster.first + k;\n let quadrant = u32(i >= page.q1) + u32(i >= page.q2) + u32(i >= page.q3);\n let opacity = fraction(g.y, 16u) * fraction(page.factors, 8u * quadrant);\n let level = vec3f(fraction(g.z, 24u), fraction(g.w, 0u), fraction(g.w, 8u));\n let scale = exp(mix(page.scaleMin, page.scaleMax, level));\n if (opacity < area.opacity || max(scale.x, max(scale.y, scale.z)) > area.scale) {\n continue;\n }\n let q = vec3f(f32(g.x & 0xffffu), f32(g.x >> 16u), f32(g.y & 0xffffu));\n let p = page.origin + q * page.step;\n if (masked(cluster, p)) {\n continue;\n }\n let cell = floor(p.xy - area.corner);\n if (any(cell < vec2f(0.0)) || any(cell >= vec2f(size))) {\n continue;\n }\n let c = vec2u(cell);\n atomicMax(&tops[c.y * area.cells + c.x], ordered(p.z));\n }\n}\n", me = 32, he = .5, ge = 1;
|
|
653
|
+
function _e(e) {
|
|
605
654
|
let t = new Uint32Array(e.length);
|
|
606
655
|
for (let n = 0; n < e.length; n++) {
|
|
607
656
|
let r = e[n];
|
|
@@ -609,7 +658,7 @@ function he(e) {
|
|
|
609
658
|
}
|
|
610
659
|
return new Float32Array(t.buffer);
|
|
611
660
|
}
|
|
612
|
-
var
|
|
661
|
+
var ve = class {
|
|
613
662
|
#e;
|
|
614
663
|
#t;
|
|
615
664
|
#n;
|
|
@@ -623,7 +672,7 @@ var ge = class {
|
|
|
623
672
|
"read-only-storage",
|
|
624
673
|
"storage"
|
|
625
674
|
]);
|
|
626
|
-
let n = `${
|
|
675
|
+
let n = `${F}\n${fe}\n${pe}`, r = e.createShaderModule({
|
|
627
676
|
label: "heights",
|
|
628
677
|
code: n
|
|
629
678
|
});
|
|
@@ -639,7 +688,7 @@ var ge = class {
|
|
|
639
688
|
encode(e, t, n, r, i) {
|
|
640
689
|
let a = this.#e, o = this.#t, { listed: s } = o, c = r * r * 4, l = a.createBuffer({
|
|
641
690
|
label: "heights area",
|
|
642
|
-
size:
|
|
691
|
+
size: me,
|
|
643
692
|
usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST
|
|
644
693
|
}), u = a.createBuffer({
|
|
645
694
|
label: "heights",
|
|
@@ -649,14 +698,14 @@ var ge = class {
|
|
|
649
698
|
label: "heights readback",
|
|
650
699
|
size: c,
|
|
651
700
|
usage: GPUBufferUsage.COPY_DST | GPUBufferUsage.MAP_READ
|
|
652
|
-
}), f = /* @__PURE__ */ new ArrayBuffer(
|
|
701
|
+
}), f = /* @__PURE__ */ new ArrayBuffer(me);
|
|
653
702
|
new Float32Array(f).set([
|
|
654
703
|
t,
|
|
655
704
|
n,
|
|
656
705
|
0,
|
|
657
706
|
0,
|
|
658
|
-
|
|
659
|
-
|
|
707
|
+
he,
|
|
708
|
+
ge
|
|
660
709
|
]), new Uint32Array(f).set([r, s], 2), a.queue.writeBuffer(l, 0, f);
|
|
661
710
|
let p = [
|
|
662
711
|
l,
|
|
@@ -669,11 +718,11 @@ var ge = class {
|
|
|
669
718
|
label: "heights",
|
|
670
719
|
timestampWrites: i
|
|
671
720
|
});
|
|
672
|
-
return g.setPipeline(this.#r), g.setBindGroup(0, h), g.setBindGroup(1, o.masks.group), s > 0 && g.dispatchWorkgroups(...m(s)), g.end(), e.copyBufferToBuffer(u, 0, d, 0, c), () => d.mapAsync(GPUMapMode.READ).then(() =>
|
|
721
|
+
return g.setPipeline(this.#r), g.setBindGroup(0, h), g.setBindGroup(1, o.masks.group), s > 0 && g.dispatchWorkgroups(...m(s)), g.end(), e.copyBufferToBuffer(u, 0, d, 0, c), () => d.mapAsync(GPUMapMode.READ).then(() => _e(new Uint32Array(d.getMappedRange())), () => null).finally(() => {
|
|
673
722
|
l.destroy(), u.destroy(), d.destroy();
|
|
674
723
|
});
|
|
675
724
|
}
|
|
676
|
-
},
|
|
725
|
+
}, ye = "@vertex\nfn vs(@builtin(vertex_index) i: u32) -> @builtin(position) vec4f {\n // one triangle over the whole target\n let p = vec2f(f32((i << 1u) & 2u), f32(i & 2u));\n return vec4f(p * 2.0 - 1.0, 0.0, 1.0);\n}\n", be = class {
|
|
677
726
|
#e;
|
|
678
727
|
#t;
|
|
679
728
|
#n;
|
|
@@ -682,7 +731,7 @@ var ge = class {
|
|
|
682
731
|
constructor(e, t, n, r) {
|
|
683
732
|
let i = e.createShaderModule({
|
|
684
733
|
label: t,
|
|
685
|
-
code:
|
|
734
|
+
code: ye + n
|
|
686
735
|
});
|
|
687
736
|
this.#e = e, this.#t = t, this.#n = e.createRenderPipeline({
|
|
688
737
|
label: t,
|
|
@@ -717,7 +766,7 @@ var ge = class {
|
|
|
717
766
|
});
|
|
718
767
|
r.setPipeline(this.#n), r.setBindGroup(0, this.#i), r.draw(3), r.end();
|
|
719
768
|
}
|
|
720
|
-
},
|
|
769
|
+
}, xe = "// the finished colour target onto the canvas, opaque\n\n@group(0) @binding(0) var scene: texture_2d<f32>;\n\n@fragment\nfn fs(@builtin(position) coord: vec4f) -> @location(0) vec4f {\n return vec4f(textureLoad(scene, vec2i(coord.xy), 0).rgb, 1.0);\n}\n", Se = (e, t) => new be(e, "present", xe, t), Ce = "// workgroups loop over visible clusters, one thread per splat\n\n@group(0) @binding(0) var<uniform> uniforms: FrameUniforms;\n@group(0) @binding(1) var<uniform> plugins: array<vec4f, 16>;\n@group(0) @binding(2) var<storage, read> geometry: array<vec4u>;\n@group(0) @binding(3) var<storage, read> colours: array<u32>;\n@group(0) @binding(4) var<storage, read> pages: array<Page>;\n@group(0) @binding(5) var<storage, read> clusters: array<Cluster>;\n@group(0) @binding(6) var<storage, read_write> work: array<atomic<u32>>;\n@group(0) @binding(7) var<storage, read_write> projected: array<Projected>;\n// keys in [0, capacity), values in [capacity, 2 capacity)\n@group(0) @binding(8) var<storage, read_write> sort: array<u32>;\n\n@group(0) @binding(9) var<uniform> visible: u32;\nvar<workgroup> kept: atomic<u32>;\nvar<workgroup> base: u32;\n\n// false when splat t of the cluster cannot show; else its Projected and sort key\nfn shown(cluster: Cluster, t: u32, dest: ptr<function, Projected>, key: ptr<function, u32>) -> bool {\n var s: Splat;\n var g: vec4u;\n if (!decode(cluster, t, &s, &g)) {\n return false;\n }\n shade(&s);\n var d: Drawn;\n if (!drawn(s, g, &d)) {\n return false;\n }\n *dest = Projected(\n d.centre,\n vec2u(pack2x16float(d.axis * d.major), pack2x16float(vec2f(-d.axis.y, d.axis.x) * d.minor)),\n vec2u(pack2x16float(s.colour.rg), pack2x16float(vec2f(s.colour.b, s.opacity)))\n );\n let span = clamp(log(d.depth / uniforms.near) / log(uniforms.far / uniforms.near), 0.0, 1.0);\n *key = u32((1.0 - span) * f32((1u << KEY_BITS) - 1u));\n return true;\n}\n\n@compute @workgroup_size(256)\nfn project(\n @builtin(workgroup_id) wid: vec3u,\n @builtin(num_workgroups) groups: vec3u,\n @builtin(local_invocation_index) t: u32\n) {\n for (var index = wid.y * groups.x + wid.x; index < visible; index += groups.x * groups.y) {\n let cluster = clusters[atomicLoad(&work[WORK_LIST + index])];\n var splat: Projected;\n var key = 0u;\n var keep = false;\n if (t < cluster.count) {\n keep = shown(cluster, t, &splat, &key);\n }\n\n // one global atomic per cluster\n var rank = 0u;\n if (keep) {\n rank = atomicAdd(&kept, 1u);\n }\n workgroupBarrier();\n if (t == 0u) {\n base = atomicAdd(&work[WORK_PROJECTED], atomicExchange(&kept, 0u));\n }\n let i = workgroupUniformLoad(&base) + rank;\n let capacity = arrayLength(&projected);\n if (keep && i < capacity) {\n projected[i] = splat;\n sort[i] = key;\n sort[capacity + i] = i;\n }\n }\n}\n", we = "// a pool splat decoded, its screen covariance and how the frame draws it, shared by project and\n// pick; each declares the uniforms, geometry, colours and pages bindings these read\n\n// ndc reach past the frustum, so splats centred just outside still cover the edge\nconst GUARD: f32 = 1.3;\n\n// i8 over 127, sign-extended by extractBits on i32\nfn code(word: u32, bit: u32) -> f32 {\n return f32(extractBits(i32(word), bit, 8u)) / 127.0;\n}\n\n// smallest three: w x y z with the largest at the stored index\nfn rotation(g: vec4u) -> vec4f {\n let v = (vec3f(fraction(g.z, 0u), fraction(g.z, 8u), fraction(g.z, 16u)) - 0.5) * sqrt(2.0);\n let big = sqrt(max(0.0, 1.0 - dot(v, v)));\n switch extractBits(g.y, 24u, 8u) {\n case 0u: {\n return normalize(vec4f(big, v));\n }\n case 1u: {\n return normalize(vec4f(v.x, big, v.yz));\n }\n case 2u: {\n return normalize(vec4f(v.xy, big, v.z));\n }\n default: {\n return normalize(vec4f(v, big));\n }\n }\n}\n\nfn rotate(q: vec4f) -> mat3x3f {\n let w = q.x;\n let x = q.y;\n let y = q.z;\n let z = q.w;\n return mat3x3f(\n 1.0 - 2.0 * (y * y + z * z), 2.0 * (x * y + w * z), 2.0 * (x * z - w * y),\n 2.0 * (x * y - w * z), 1.0 - 2.0 * (x * x + z * z), 2.0 * (y * z + w * x),\n 2.0 * (x * z + w * y), 2.0 * (y * z - w * x), 1.0 - 2.0 * (x * x + y * y)\n );\n}\n\n// splat t of a cluster in the floating-origin frame, its record in g; false when a mask hides it\nfn decode(cluster: Cluster, t: u32, s: ptr<function, Splat>, g: ptr<function, vec4u>) -> bool {\n let page = pages[cluster.page];\n let rec = cluster.slot + t;\n *g = geometry[rec];\n let w0 = colours[rec * 3u];\n let w1 = colours[rec * 3u + 1u];\n let w2 = colours[rec * 3u + 2u];\n let i = cluster.first + t;\n let quadrant = u32(i >= page.q1) + u32(i >= page.q2) + u32(i >= page.q3);\n\n var d: Splat;\n let q = vec3f(f32((*g).x & 0xffffu), f32((*g).x >> 16u), f32((*g).y & 0xffffu));\n d.position = page.origin + q * page.step;\n if (masked(cluster, d.position)) {\n return false;\n }\n d.opacity = fraction((*g).y, 16u) * fraction(page.factors, 8u * quadrant);\n let level = vec3f(fraction((*g).z, 24u), fraction((*g).w, 0u), fraction((*g).w, 8u));\n d.scale = exp(mix(page.scaleMin, page.scaleMax, level));\n let dc = mix(page.dcMin, page.dcMax, vec3f(fraction(w0, 0u), fraction(w0, 8u), fraction(w0, 16u)));\n // sh[c][m] at 3c + m, gathered per m across the colours\n let k = page.shScale;\n let m0 = vec3f(code(w0, 24u), code(w1, 16u), code(w2, 8u)) * vec3f(k[0].x, k[0].w, k[1].z);\n let m1 = vec3f(code(w1, 0u), code(w1, 24u), code(w2, 16u)) * vec3f(k[0].y, k[1].x, k[1].w);\n let m2 = vec3f(code(w1, 8u), code(w2, 0u), code(w2, 24u)) * vec3f(k[0].z, k[1].y, k[2].x);\n let toward = normalize(d.position - uniforms.camera);\n d.colour = max(0.5 + C0 * dc + C1 * (-toward.y * m0 + toward.z * m1 - toward.x * m2), vec3f(0.0));\n d.depth = -(uniforms.view * vec4f(d.position, 1.0)).z;\n *s = d;\n return true;\n}\n\n// ewa: view-space covariance wm wm^T through the jacobian of the pixel projection, as a b c in px²\nfn covariance(g: vec4u, scale: vec3f, viewPos: vec3f) -> vec3f {\n let depth = -viewPos.z;\n let r = rotate(rotation(g));\n let m = mat3x3f(r[0] * scale.x, r[1] * scale.y, r[2] * scale.z);\n let w = mat3x3f(uniforms.view[0].xyz, uniforms.view[1].xyz, uniforms.view[2].xyz);\n let wm = w * m;\n let focal = uniforms.focal;\n let j0 = vec3f(focal.x / depth, 0.0, focal.x * viewPos.x / (depth * depth));\n let j1 = vec3f(0.0, focal.y / depth, focal.y * viewPos.y / (depth * depth));\n let u = j0 * wm;\n let v = j1 * wm;\n return vec3f(dot(u, u) + uniforms.lowPass, dot(u, v), dot(v, v) + uniforms.lowPass);\n}\n\n// a splat as the frame draws it: its view depth, its centre in pixels from the bottom-left, and\n// its quad's axis with the sigmas along it and across\nstruct Drawn {\n depth: f32,\n centre: vec2f,\n axis: vec2f,\n major: f32,\n minor: f32,\n}\n\n// false where the frame draws none of the shaded splat: too faint, out of range, centred past the\n// guard band, under half a pixel, or off the screen\nfn drawn(s: Splat, g: vec4u, d: ptr<function, Drawn>) -> bool {\n if (s.opacity < 1.0 / 255.0) {\n return false;\n }\n let viewPos = (uniforms.view * vec4f(s.position, 1.0)).xyz;\n let depth = -viewPos.z;\n if (depth < uniforms.near || depth > uniforms.far) {\n return false;\n }\n let clip = uniforms.proj * vec4f(viewPos, 1.0);\n let ndc = clip.xy / clip.w;\n if (any(abs(ndc) > vec2f(GUARD))) {\n return false;\n }\n\n let cov = covariance(g, s.scale, viewPos);\n let mid = 0.5 * (cov.x + cov.z);\n let rad = length(vec2f(0.5 * (cov.x - cov.z), cov.y));\n let major = sqrt(mid + rad);\n if (3.0 * major < 0.5) {\n return false;\n }\n let minor = sqrt(max(mid - rad, 0.0));\n let angle = 0.5 * atan2(2.0 * cov.y, cov.x - cov.z);\n let axis = vec2f(cos(angle), sin(angle));\n // the quad raster draws; a centre inside the guard band can still miss the screen\n let centre = (ndc * 0.5 + 0.5) * uniforms.viewport;\n let extent = reach(s.opacity) * (abs(axis) * major + abs(axis.yx) * minor);\n if (any(centre + extent < vec2f(0.0)) || any(centre - extent > uniforms.viewport)) {\n return false;\n }\n *d = Drawn(depth, centre, axis, major, minor);\n return true;\n}\n", Te = class {
|
|
721
770
|
#e;
|
|
722
771
|
#t;
|
|
723
772
|
#n;
|
|
@@ -767,11 +816,11 @@ var ge = class {
|
|
|
767
816
|
i.setPipeline(this.#n ??= this.#c()), i.setBindGroup(0, this.#i), i.setBindGroup(1, this.#a.masks.group), i.dispatchWorkgroups(r), i.end();
|
|
768
817
|
}
|
|
769
818
|
#c() {
|
|
770
|
-
let e =
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
819
|
+
let e = Ee([
|
|
820
|
+
F,
|
|
821
|
+
fe,
|
|
822
|
+
we,
|
|
823
|
+
Ce
|
|
775
824
|
], this.#r), t = this.#e.createShaderModule({
|
|
776
825
|
label: "project",
|
|
777
826
|
code: e
|
|
@@ -786,7 +835,7 @@ var ge = class {
|
|
|
786
835
|
});
|
|
787
836
|
}
|
|
788
837
|
};
|
|
789
|
-
function
|
|
838
|
+
function Ee(e, t) {
|
|
790
839
|
let n = t.map(({ shade: e, slot: t }) => {
|
|
791
840
|
let n = Array.from({ length: e.uniforms }, (e, n) => `plugins[${t + n}]`);
|
|
792
841
|
return `\t${e.name}(s, array<vec4f, ${e.uniforms}>(${n.join(", ")}));`;
|
|
@@ -801,10 +850,10 @@ function we(e, t) {
|
|
|
801
850
|
}
|
|
802
851
|
//#endregion
|
|
803
852
|
//#region src/engine/gpu/overlay.wgsl?raw
|
|
804
|
-
var
|
|
853
|
+
var De = "// host graphics over the frame: capsules in screen space from a to b, a marker where a is b\n\n// share of the view depth an occluding fragment may lie behind the splats, so a line on the ground clears their fringe\nconst SLACK: f32 = 0.02;\n\nstruct Capsule {\n @location(0) a: vec3f,\n @location(1) b: vec3f,\n // pixels\n @location(2) radius: f32,\n @location(3) colour: vec4f,\n @location(4) occlude: u32,\n}\n\nstruct Fragment {\n @builtin(position) position: vec4f,\n // target pixels from the top-left, of the ends\n @location(0) @interpolate(flat) a: vec2f,\n @location(1) @interpolate(flat) b: vec2f,\n // view depth of the ends\n @location(2) @interpolate(flat) depths: vec2f,\n @location(3) @interpolate(flat) radius: f32,\n @location(4) @interpolate(flat) colour: vec4f,\n @location(5) @interpolate(flat) occlude: u32,\n}\n\n@group(0) @binding(0) var<uniform> uniforms: FrameUniforms;\n@group(0) @binding(1) var depth: texture_depth_2d;\n\nfn pixel(view: vec3f) -> vec2f {\n let clip = uniforms.proj * vec4f(view, 1.0);\n let ndc = clip.xy / clip.w;\n return vec2f(ndc.x * 0.5 + 0.5, 0.5 - ndc.y * 0.5) * uniforms.viewport;\n}\n\n@vertex\nfn vs(@builtin(vertex_index) v: u32, c: Capsule) -> Fragment {\n var a = (uniforms.view * vec4f(c.a, 1.0)).xyz;\n var b = (uniforms.view * vec4f(c.b, 1.0)).xyz;\n var out: Fragment;\n // cut the part behind the near plane; nothing left draws nothing\n let near = -uniforms.near;\n if (a.z > near && b.z > near) {\n out.position = vec4f(2.0, 2.0, 0.0, 1.0);\n return out;\n }\n if (a.z > near) {\n a = mix(b, a, (near - b.z) / (a.z - b.z));\n } else if (b.z > near) {\n b = mix(a, b, (near - a.z) / (b.z - a.z));\n }\n let pa = pixel(a);\n let pb = pixel(b);\n let span = pb - pa;\n let along = select(vec2f(1.0, 0.0), normalize(span), dot(span, span) > 1e-6);\n let across = vec2f(-along.y, along.x);\n let r = c.radius + 1.0;\n let corner = select(pa - along * r, pb + along * r, (v & 1u) == 1u) + across * r * select(-1.0, 1.0, v > 1u);\n out.position = vec4f(corner.x / uniforms.viewport.x * 2.0 - 1.0, 1.0 - corner.y / uniforms.viewport.y * 2.0, 0.0, 1.0);\n out.a = pa;\n out.b = pb;\n out.depths = vec2f(-a.z, -b.z);\n out.radius = c.radius;\n out.colour = c.colour;\n out.occlude = c.occlude;\n return out;\n}\n\n@fragment\nfn fs(f: Fragment) -> @location(0) vec4f {\n let p = f.position.xy;\n let span = f.b - f.a;\n let t = select(0.0, clamp(dot(p - f.a, span) / dot(span, span), 0.0, 1.0), dot(span, span) > 1e-6);\n let coverage = clamp(f.radius - distance(p, f.a + span * t) + 0.5, 0.0, 1.0);\n if (coverage <= 0.0) {\n discard;\n }\n if (f.occlude != 0u) {\n // screen-linear in 1 / depth along a segment\n let here = 1.0 / mix(1.0 / f.depths.x, 1.0 / f.depths.y, t);\n let stored = textureLoad(depth, vec2i(p), 0);\n let scene = uniforms.near * pow(uniforms.far / uniforms.near, stored);\n if (stored < 1.0 && here > scene * (1.0 + SLACK)) {\n discard;\n }\n }\n let a = f.colour.a * coverage;\n return vec4f(f.colour.rgb * a, a);\n}\n", Oe = 36, ke = {
|
|
805
854
|
srcFactor: "one",
|
|
806
855
|
dstFactor: "one-minus-src-alpha"
|
|
807
|
-
},
|
|
856
|
+
}, Ae = class {
|
|
808
857
|
#e;
|
|
809
858
|
#t;
|
|
810
859
|
#n;
|
|
@@ -816,7 +865,7 @@ var Te = "// host graphics over the frame: capsules in screen space from a to b,
|
|
|
816
865
|
this.#e = e, this.#t = n;
|
|
817
866
|
let r = e.createShaderModule({
|
|
818
867
|
label: "overlay",
|
|
819
|
-
code:
|
|
868
|
+
code: F + De
|
|
820
869
|
}), i = [
|
|
821
870
|
{
|
|
822
871
|
shaderLocation: 0,
|
|
@@ -851,7 +900,7 @@ var Te = "// host graphics over the frame: capsules in screen space from a to b,
|
|
|
851
900
|
module: r,
|
|
852
901
|
entryPoint: "vs",
|
|
853
902
|
buffers: [{
|
|
854
|
-
arrayStride:
|
|
903
|
+
arrayStride: Oe,
|
|
855
904
|
stepMode: "instance",
|
|
856
905
|
attributes: i
|
|
857
906
|
}]
|
|
@@ -862,8 +911,8 @@ var Te = "// host graphics over the frame: capsules in screen space from a to b,
|
|
|
862
911
|
targets: [{
|
|
863
912
|
format: t,
|
|
864
913
|
blend: {
|
|
865
|
-
color:
|
|
866
|
-
alpha:
|
|
914
|
+
color: ke,
|
|
915
|
+
alpha: ke
|
|
867
916
|
}
|
|
868
917
|
}]
|
|
869
918
|
},
|
|
@@ -875,9 +924,9 @@ var Te = "// host graphics over the frame: capsules in screen space from a to b,
|
|
|
875
924
|
}
|
|
876
925
|
set(e, t) {
|
|
877
926
|
if (this.#i = e.length, !e.length) return;
|
|
878
|
-
let n = /* @__PURE__ */ new ArrayBuffer(e.length *
|
|
927
|
+
let n = /* @__PURE__ */ new ArrayBuffer(e.length * Oe), r = new Float32Array(n), i = new Uint32Array(n), a = new Uint8Array(n);
|
|
879
928
|
e.forEach(({ a: e, b: n, radius: o, colour: s, occlude: c }, l) => {
|
|
880
|
-
let u = l *
|
|
929
|
+
let u = l * Oe / 4;
|
|
881
930
|
for (let i = 0; i < 3; i++) r[u + i] = e[i] - t[i], r[u + 3 + i] = n[i] - t[i];
|
|
882
931
|
r[u + 6] = o, s.forEach((e, t) => a[(u + 7) * 4 + t] = Math.round(Math.min(1, Math.max(0, e)) * 255)), i[u + 8] = +!!c;
|
|
883
932
|
}), (!this.#r || this.#r.size < n.byteLength) && (this.#r?.destroy(), this.#r = this.#e.createBuffer({
|
|
@@ -912,7 +961,7 @@ var Te = "// host graphics over the frame: capsules in screen space from a to b,
|
|
|
912
961
|
destroy() {
|
|
913
962
|
this.#r?.destroy();
|
|
914
963
|
}
|
|
915
|
-
},
|
|
964
|
+
}, je = [
|
|
916
965
|
[
|
|
917
966
|
0,
|
|
918
967
|
-1,
|
|
@@ -944,15 +993,15 @@ var Te = "// host graphics over the frame: capsules in screen space from a to b,
|
|
|
944
993
|
-1
|
|
945
994
|
]
|
|
946
995
|
];
|
|
947
|
-
function
|
|
948
|
-
return
|
|
996
|
+
function Me(e, t, n) {
|
|
997
|
+
return je.forEach(([r, i, a], o) => {
|
|
949
998
|
let s = n?.[o] ?? i;
|
|
950
999
|
for (let n = 0; n < 4; n++) e[o * 4 + n] = a * (t[n * 4 + r] - s * t[n * 4 + 3]);
|
|
951
1000
|
let c = Math.hypot(e[o * 4], e[o * 4 + 1], e[o * 4 + 2]) || 1;
|
|
952
1001
|
for (let t = 0; t < 4; t++) e[o * 4 + t] /= c;
|
|
953
1002
|
}), e;
|
|
954
1003
|
}
|
|
955
|
-
function
|
|
1004
|
+
function Ne(e, t, n) {
|
|
956
1005
|
for (let r = 0; r < 24; r += 4) {
|
|
957
1006
|
let i = e[r] >= 0 ? n[0] : t[0], a = e[r + 1] >= 0 ? n[1] : t[1], o = e[r + 2] >= 0 ? n[2] : t[2];
|
|
958
1007
|
if (e[r] * i + e[r + 1] * a + e[r + 2] * o + e[r + 3] < 0) return !1;
|
|
@@ -961,13 +1010,7 @@ function je(e, t, n) {
|
|
|
961
1010
|
}
|
|
962
1011
|
//#endregion
|
|
963
1012
|
//#region src/engine/gpu/pick.wgsl?raw
|
|
964
|
-
var
|
|
965
|
-
Fe,
|
|
966
|
-
0,
|
|
967
|
-
0,
|
|
968
|
-
0,
|
|
969
|
-
0
|
|
970
|
-
]), Le = class {
|
|
1013
|
+
var Pe = "// every splat the last frame drew over one pixel, with its alpha there, over the frame's visible\n// clusters; the host blends them front to back as the frame did\n\n// workgroups of the dispatch, pick.ts's GROUPS; each loops over the visible clusters\nconst PICK_GROUPS: u32 = 256u;\n\nstruct Probe {\n // target pixel, y up from the bottom-left\n pixel: vec2f,\n // the pixel's frustum sides; inside when dot(plane.xyz, p) + plane.w >= 0\n planes: array<vec4f, 4>,\n}\n\n// a splat over the pixel: its face toward the camera, its view depth, which orders the blend, the\n// view depth where the pixel's ray meets its plane, its alpha at the pixel and its layer\nstruct Entry {\n normal: vec3f,\n depth: f32,\n meets: f32,\n alpha: f32,\n layer: u32,\n}\n\n// entries past the buffer's length are counted and not kept\nstruct Hits {\n count: atomic<u32>,\n entries: array<Entry>,\n}\n\n@group(0) @binding(0) var<uniform> uniforms: FrameUniforms;\n@group(0) @binding(1) var<uniform> plugins: array<vec4f, 16>;\n@group(0) @binding(2) var<storage, read> geometry: array<vec4u>;\n@group(0) @binding(3) var<storage, read> colours: array<u32>;\n@group(0) @binding(4) var<storage, read> pages: array<Page>;\n@group(0) @binding(5) var<storage, read> clusters: array<Cluster>;\n@group(0) @binding(6) var<storage, read> work: array<u32>;\n@group(0) @binding(7) var<uniform> probe: Probe;\n@group(0) @binding(8) var<storage, read_write> hits: Hits;\n\n// false only when the box lies wholly outside one side of the pixel\nfn under(lo: vec3f, hi: vec3f) -> bool {\n for (var p = 0u; p < 4u; p++) {\n let plane = probe.planes[p];\n let corner = select(lo, hi, plane.xyz >= vec3f(0.0));\n if (dot(plane.xyz, corner) + plane.w < 0.0) {\n return false;\n }\n }\n return true;\n}\n\n// the cluster of visible index under the pixel, or none\nfn candidate(index: u32, cluster: ptr<function, Cluster>) -> bool {\n *cluster = clusters[work[WORK_LIST + index]];\n let page = pages[(*cluster).page];\n return under(page.origin + (*cluster).boxMin, page.origin + (*cluster).boxMax);\n}\n\n// the alpha a drawn splat gives the pixel as raster.wgsl blends it: its quad stops at reach\n// sigmas along each axis, and a fragment under 1/255 is discarded\nfn coverage(s: Splat, d: Drawn) -> f32 {\n let off = probe.pixel - d.centre;\n let uv = vec2f(dot(off, d.axis) / d.major, dot(off, vec2f(-d.axis.y, d.axis.x)) / d.minor);\n if (any(abs(uv) > vec2f(reach(s.opacity)))) {\n return 0.0;\n }\n let a = s.opacity * exp(-0.5 * dot(uv, uv));\n return select(0.0, a, a >= 1.0 / 255.0);\n}\n\n// the splat's thinnest axis, toward the camera\nfn face(s: Splat, g: vec4u) -> vec3f {\n let r = rotate(rotation(g));\n let k = select(select(2u, 1u, s.scale.y <= s.scale.z), 0u,\n s.scale.x <= s.scale.y && s.scale.x <= s.scale.z);\n return r[k] * sign(dot(r[k], uniforms.camera - s.position) + 1e-20);\n}\n\n// the view depth where the pixel's ray meets the plane of the splat's face, kept within its\n// reach of the centre: a splat seen edge on meets the ray far off\nfn meets(s: Splat, d: Drawn, normal: vec3f) -> f32 {\n let ndc = probe.pixel / uniforms.viewport * 2.0 - 1.0;\n let ray = vec3f(ndc.x / uniforms.proj[0].x, ndc.y / uniforms.proj[1].y, -1.0);\n let n = (uniforms.view * vec4f(normal, 0.0)).xyz;\n let centre = (uniforms.view * vec4f(s.position, 1.0)).xyz;\n let across = dot(n, ray);\n if (abs(across) < 1e-6) {\n return d.depth;\n }\n let spread = reach(s.opacity) * max(s.scale.x, max(s.scale.y, s.scale.z));\n return clamp(dot(n, centre) / across, d.depth - spread, d.depth + spread);\n}\n\n@compute @workgroup_size(256)\nfn gather(@builtin(workgroup_id) wid: vec3u, @builtin(local_invocation_index) t: u32) {\n for (var index = wid.x; index < work[WORK_VISIBLE]; index += PICK_GROUPS) {\n var cluster: Cluster;\n var s: Splat;\n var g: vec4u;\n if (!candidate(index, &cluster) || t >= cluster.count || !decode(cluster, t, &s, &g)) {\n continue;\n }\n shade(&s);\n var d: Drawn;\n if (!drawn(s, g, &d)) {\n continue;\n }\n let a = coverage(s, d);\n if (a == 0.0) {\n continue;\n }\n let normal = face(s, g);\n let slot = atomicAdd(&hits.count, 1u);\n if (slot < arrayLength(&hits.entries)) {\n hits.entries[slot] = Entry(normal, d.depth, meets(s, d, normal), a, pages[cluster.page].layer);\n }\n }\n}\n", Fe = 256, Ie = 80, I = 16, Le = 32, Re = 4096, ze = new Uint32Array([0]), Be = class {
|
|
971
1014
|
#e;
|
|
972
1015
|
#t;
|
|
973
1016
|
#n;
|
|
@@ -976,10 +1019,12 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
976
1019
|
#a = [];
|
|
977
1020
|
#o = /* @__PURE__ */ new Float32Array(16);
|
|
978
1021
|
#s = /* @__PURE__ */ new Float32Array(24);
|
|
979
|
-
#c = new Float32Array(
|
|
1022
|
+
#c = new Float32Array(Ie / 4);
|
|
980
1023
|
#l;
|
|
981
1024
|
#u;
|
|
982
|
-
#d;
|
|
1025
|
+
#d = 0;
|
|
1026
|
+
#f;
|
|
1027
|
+
#p;
|
|
983
1028
|
constructor(e, t, n) {
|
|
984
1029
|
this.#e = e, this.#t = t, this.#n = x(e, "pick", GPUShaderStage.COMPUTE, [
|
|
985
1030
|
"uniform",
|
|
@@ -993,12 +1038,8 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
993
1038
|
"storage"
|
|
994
1039
|
]), this.#r = e.createPipelineLayout({ bindGroupLayouts: [this.#n, t.masks.layout] }), this.#l = e.createBuffer({
|
|
995
1040
|
label: "pick probe",
|
|
996
|
-
size:
|
|
1041
|
+
size: Ie,
|
|
997
1042
|
usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST
|
|
998
|
-
}), this.#u = e.createBuffer({
|
|
999
|
-
label: "pick",
|
|
1000
|
-
size: 20,
|
|
1001
|
-
usage: GPUBufferUsage.STORAGE | GPUBufferUsage.COPY_SRC | GPUBufferUsage.COPY_DST
|
|
1002
1043
|
});
|
|
1003
1044
|
let { uniforms: r, plugins: i, work: a } = n, o = [
|
|
1004
1045
|
r,
|
|
@@ -1008,77 +1049,90 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1008
1049
|
t.pages,
|
|
1009
1050
|
t.clusters
|
|
1010
1051
|
];
|
|
1011
|
-
this.#
|
|
1052
|
+
this.#u = [
|
|
1012
1053
|
...o,
|
|
1013
1054
|
a,
|
|
1014
|
-
this.#l
|
|
1015
|
-
|
|
1016
|
-
]);
|
|
1055
|
+
this.#l
|
|
1056
|
+
], this.#m(Re);
|
|
1017
1057
|
}
|
|
1018
1058
|
hooks(e) {
|
|
1019
1059
|
this.#a = e, this.#i = void 0;
|
|
1020
1060
|
}
|
|
1021
1061
|
run(e, t, n) {
|
|
1022
|
-
let r = this.#e, i = this.#t, a = r.createBuffer({
|
|
1062
|
+
let r = this.#e, i = this.#t, a = this.#d, o = I + a * Le, s = r.createBuffer({
|
|
1023
1063
|
label: "pick readback",
|
|
1024
|
-
size:
|
|
1064
|
+
size: o,
|
|
1025
1065
|
usage: GPUBufferUsage.COPY_DST | GPUBufferUsage.MAP_READ
|
|
1026
|
-
}),
|
|
1027
|
-
|
|
1028
|
-
let
|
|
1029
|
-
return
|
|
1030
|
-
let e = new Uint32Array(
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
t[2],
|
|
1034
|
-
t[3],
|
|
1035
|
-
t[4]
|
|
1036
|
-
];
|
|
1037
|
-
return {
|
|
1038
|
-
depth: t[0],
|
|
1039
|
-
layer: e[1],
|
|
1040
|
-
normal: n
|
|
1041
|
-
};
|
|
1042
|
-
}, () => null).finally(() => a.destroy());
|
|
1066
|
+
}), c = this.#c, l = n.height - t;
|
|
1067
|
+
c.set([e, l], 0), c.set(this.#h(e, l, n), 4), r.queue.writeBuffer(this.#l, 0, c), r.queue.writeBuffer(this.#f, 0, ze);
|
|
1068
|
+
let u = r.createCommandEncoder({ label: "pick" }), d = u.beginComputePass({ label: "pick" });
|
|
1069
|
+
return d.setBindGroup(0, this.#p), d.setBindGroup(1, i.masks.group), d.setPipeline(this.#i ??= this.#g()), d.dispatchWorkgroups(Fe), d.end(), u.copyBufferToBuffer(this.#f, 0, s, 0, o), r.queue.submit([u.finish()]), s.mapAsync(GPUMapMode.READ).then(() => {
|
|
1070
|
+
let e = s.getMappedRange(), t = new Uint32Array(e, 0, 1)[0];
|
|
1071
|
+
return t > a ? (this.#m(2 ** Math.ceil(Math.log2(t))), null) : Ve(new Float32Array(e, I), new Uint32Array(e, I), t);
|
|
1072
|
+
}, () => null).finally(() => s.destroy());
|
|
1043
1073
|
}
|
|
1044
1074
|
destroy() {
|
|
1045
|
-
this.#l.destroy(), this.#
|
|
1075
|
+
this.#l.destroy(), this.#f.destroy();
|
|
1076
|
+
}
|
|
1077
|
+
#m(e) {
|
|
1078
|
+
let t = this.#f;
|
|
1079
|
+
this.#d = e, this.#f = this.#e.createBuffer({
|
|
1080
|
+
label: "pick",
|
|
1081
|
+
size: I + e * Le,
|
|
1082
|
+
usage: GPUBufferUsage.STORAGE | GPUBufferUsage.COPY_SRC | GPUBufferUsage.COPY_DST
|
|
1083
|
+
}), this.#p = S(this.#e, "pick", this.#n, [...this.#u, this.#f]), t?.destroy();
|
|
1046
1084
|
}
|
|
1047
|
-
#
|
|
1048
|
-
let r = (e, t) => 2 * e / t - 1, i =
|
|
1085
|
+
#h(e, t, n) {
|
|
1086
|
+
let r = (e, t) => 2 * e / t - 1, i = P(this.#o, n.proj, n.view), a = [
|
|
1049
1087
|
r(e - .5, n.width),
|
|
1050
1088
|
r(e + .5, n.width),
|
|
1051
1089
|
r(t - .5, n.height),
|
|
1052
1090
|
r(t + .5, n.height)
|
|
1053
1091
|
];
|
|
1054
|
-
return
|
|
1055
|
-
}
|
|
1056
|
-
#
|
|
1057
|
-
let e =
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
|
|
1061
|
-
|
|
1092
|
+
return Me(this.#s, i, a), this.#s.subarray(0, 16);
|
|
1093
|
+
}
|
|
1094
|
+
#g() {
|
|
1095
|
+
let e = Ee([
|
|
1096
|
+
F,
|
|
1097
|
+
fe,
|
|
1098
|
+
we,
|
|
1099
|
+
Pe
|
|
1062
1100
|
], this.#a), t = this.#e.createShaderModule({
|
|
1063
1101
|
label: "pick",
|
|
1064
1102
|
code: e
|
|
1065
|
-
})
|
|
1066
|
-
|
|
1103
|
+
});
|
|
1104
|
+
return this.#e.createComputePipeline({
|
|
1105
|
+
label: "pick",
|
|
1067
1106
|
layout: this.#r,
|
|
1068
1107
|
compute: {
|
|
1069
1108
|
module: t,
|
|
1070
|
-
entryPoint:
|
|
1109
|
+
entryPoint: "gather"
|
|
1071
1110
|
}
|
|
1072
1111
|
});
|
|
1073
|
-
|
|
1074
|
-
|
|
1075
|
-
|
|
1112
|
+
}
|
|
1113
|
+
};
|
|
1114
|
+
function Ve(e, t, n) {
|
|
1115
|
+
let r = Le / 4, i = Array.from({ length: n }, (e, t) => t).sort((t, n) => e[t * r + 3] - e[n * r + 3]), a = 1;
|
|
1116
|
+
for (let n of i) {
|
|
1117
|
+
let i = n * r;
|
|
1118
|
+
if (a *= 1 - e[i + 5], a <= .5) return {
|
|
1119
|
+
depth: e[i + 4],
|
|
1120
|
+
layer: t[i + 6],
|
|
1121
|
+
normal: [
|
|
1122
|
+
e[i],
|
|
1123
|
+
e[i + 1],
|
|
1124
|
+
e[i + 2]
|
|
1125
|
+
]
|
|
1076
1126
|
};
|
|
1077
1127
|
}
|
|
1078
|
-
|
|
1128
|
+
return null;
|
|
1129
|
+
}
|
|
1130
|
+
//#endregion
|
|
1131
|
+
//#region src/engine/gpu/raster.wgsl?raw
|
|
1132
|
+
var He = "// sorted splats as screen quads, premultiplied over what lies behind them\n\n// word offsets of the sorted keys and values in the sort buffer\nstruct Sorted {\n keys: u32,\n values: u32,\n}\n\nstruct Corner {\n @builtin(position) position: vec4f,\n // offset from the centre in sigmas\n @location(0) uv: vec2f,\n @location(1) colour: vec4f,\n}\n\n@group(0) @binding(0) var<uniform> frame: FrameUniforms;\n@group(0) @binding(1) var<storage, read> projected: array<Projected>;\n@group(0) @binding(2) var<storage, read> sort: array<u32>;\n@group(0) @binding(3) var<uniform> sorted: Sorted;\n\nfn corner(v: u32, i: u32) -> Corner {\n let p = projected[sort[sorted.values + i]];\n let major = unpack2x16float(p.axes.x);\n let minor = unpack2x16float(p.axes.y);\n let colour = vec4f(unpack2x16float(p.colour.x), unpack2x16float(p.colour.y));\n let r = reach(colour.a);\n let uv = vec2f(f32(v & 1u), f32(v >> 1u)) * 2.0 - 1.0;\n let pixel = p.centre + (major * uv.x + minor * uv.y) * r;\n return Corner(vec4f(pixel / frame.viewport * 2.0 - 1.0, 0.0, 1.0), uv * r, colour);\n}\n\nfn alpha(uv: vec2f, opacity: f32) -> f32 {\n return opacity * exp(-0.5 * dot(uv, uv));\n}\n\n@vertex\nfn vsColour(@builtin(vertex_index) v: u32, @builtin(instance_index) i: u32) -> Corner {\n return corner(v, i);\n}\n\n@vertex\nfn vsDepth(@builtin(vertex_index) v: u32, @builtin(instance_index) i: u32) -> Corner {\n var c = corner(v, i);\n // inverse of the key: the span from near to far in log depth\n c.position.z = 1.0 - f32(sort[sorted.keys + i]) / f32((1u << KEY_BITS) - 1u);\n return c;\n}\n\n@fragment\nfn fs(c: Corner) -> @location(0) vec4f {\n let a = alpha(c.uv, c.colour.a);\n if (a < 1.0 / 255.0) {\n discard;\n }\n return vec4f(c.colour.rgb * a, a);\n}\n", Ue = "rgb10a2unorm", We = "depth16unorm", Ge = {
|
|
1079
1133
|
srcFactor: "one",
|
|
1080
1134
|
dstFactor: "one-minus-src-alpha"
|
|
1081
|
-
},
|
|
1135
|
+
}, Ke = class {
|
|
1082
1136
|
#e;
|
|
1083
1137
|
#t;
|
|
1084
1138
|
#n;
|
|
@@ -1111,7 +1165,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1111
1165
|
]);
|
|
1112
1166
|
let a = e.createShaderModule({
|
|
1113
1167
|
label: "raster",
|
|
1114
|
-
code:
|
|
1168
|
+
code: F + He
|
|
1115
1169
|
}), o = e.createPipelineLayout({ bindGroupLayouts: [i] }), s = (t, n) => e.createRenderPipeline({
|
|
1116
1170
|
label: `raster ${t}`,
|
|
1117
1171
|
layout: o,
|
|
@@ -1123,10 +1177,10 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1123
1177
|
module: a,
|
|
1124
1178
|
entryPoint: "fs",
|
|
1125
1179
|
targets: [{
|
|
1126
|
-
format:
|
|
1180
|
+
format: Ue,
|
|
1127
1181
|
blend: {
|
|
1128
|
-
color:
|
|
1129
|
-
alpha:
|
|
1182
|
+
color: Ge,
|
|
1183
|
+
alpha: Ge
|
|
1130
1184
|
}
|
|
1131
1185
|
}]
|
|
1132
1186
|
},
|
|
@@ -1134,7 +1188,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1134
1188
|
depthStencil: n
|
|
1135
1189
|
});
|
|
1136
1190
|
this.#n = s("Colour"), this.#r = s("Depth", {
|
|
1137
|
-
format:
|
|
1191
|
+
format: We,
|
|
1138
1192
|
depthWriteEnabled: !0,
|
|
1139
1193
|
depthCompare: "always"
|
|
1140
1194
|
});
|
|
@@ -1161,7 +1215,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1161
1215
|
destroy() {
|
|
1162
1216
|
this.#t.destroy();
|
|
1163
1217
|
}
|
|
1164
|
-
},
|
|
1218
|
+
}, qe = "// lsd radix sort, 8 bits a pass: block digit counts, a two-level scan, a stable scatter; no spin-waits\n\nconst THREADS: u32 = 128u;\nconst ITEMS: u32 = 8u;\nconst BLOCK: u32 = 1024u;\n// blocks per scan chunk\nconst CHUNK: u32 = 64u;\nconst DIGITS: u32 = 256u;\n\nstruct SortParams {\n shift: u32,\n // word offsets of the keys read and written; their values follow capacity words later\n src: u32,\n dst: u32,\n capacity: u32,\n // word offsets in the work buffer\n projected: u32,\n drawArgs: u32,\n}\n\nstruct SortState {\n count: u32,\n blocks: u32,\n chunks: u32,\n}\n\n@group(0) @binding(0) var<uniform> params: SortParams;\n@group(0) @binding(1) var<storage, read_write> data: array<u32>;\n// block-major: count, then exclusive global offset, of digit d in block b at b DIGITS + d\n@group(0) @binding(2) var<storage, read_write> hist: array<u32>;\n// chunk-major sums of hist, then their exclusive global offsets\n@group(0) @binding(3) var<storage, read_write> sums: array<u32>;\n@group(0) @binding(4) var<storage, read> state: SortState;\n@group(0) @binding(5) var<storage, read_write> stateOut: SortState;\n@group(0) @binding(6) var<storage, read_write> work: array<u32>;\n\nvar<workgroup> bins: array<atomic<u32>, DIGITS>;\nvar<workgroup> totals: array<u32, DIGITS>;\nvar<workgroup> bitValues: atomic<u32>;\nvar<workgroup> activeBits: u32;\nvar<workgroup> sk: array<u32, BLOCK>;\nvar<workgroup> sv: array<u32, BLOCK>;\n// three 10-bit counts; the fourth follows from the number of items\nvar<workgroup> counts: array<u32, THREADS * 2u>;\nvar<workgroup> tail: u32;\nvar<workgroup> starts: array<u32, DIGITS>;\nvar<workgroup> offsets: array<u32, DIGITS>;\n\nfn unpack(packed: u32, count: u32) -> vec4u {\n let a = packed & 1023u;\n let b = (packed >> 10u) & 1023u;\n let c = (packed >> 20u) & 1023u;\n return vec4u(a, b, c, count - a - b - c);\n}\n\nfn digit(key: u32) -> u32 {\n return (key >> params.shift) & 0xffu;\n}\n\n@compute @workgroup_size(1)\nfn prepare() {\n let count = min(work[params.projected], params.capacity);\n let blocks = (count + BLOCK - 1u) / BLOCK;\n work[params.drawArgs] = 4u;\n work[params.drawArgs + 1u] = count;\n work[params.drawArgs + 2u] = 0u;\n work[params.drawArgs + 3u] = 0u;\n stateOut = SortState(count, blocks, (blocks + CHUNK - 1u) / CHUNK);\n}\n\n@compute @workgroup_size(THREADS)\nfn histogram(\n @builtin(workgroup_id) wid: vec3u,\n @builtin(num_workgroups) groups: vec3u,\n @builtin(local_invocation_index) t: u32\n) {\n for (var block = wid.y * groups.x + wid.x; block < state.blocks; block += groups.x * groups.y) {\n let head = block * BLOCK;\n for (var k = 0u; k < ITEMS; k++) {\n let i = head + k * THREADS + t;\n if (i < state.count) {\n atomicAdd(&bins[digit(data[params.src + i])], 1u);\n }\n }\n workgroupBarrier();\n for (var d = t; d < DIGITS; d += THREADS) {\n hist[block * DIGITS + d] = atomicExchange(&bins[d], 0u);\n }\n workgroupBarrier();\n }\n}\n\n@compute @workgroup_size(DIGITS)\nfn reduce(@builtin(workgroup_id) wid: vec3u, @builtin(local_invocation_index) t: u32) {\n let end = min((wid.x + 1u) * CHUNK, state.blocks);\n var sum = 0u;\n for (var b = wid.x * CHUNK; b < end; b++) {\n sum += hist[b * DIGITS + t];\n }\n sums[wid.x * DIGITS + t] = sum;\n}\n\n@compute @workgroup_size(DIGITS)\nfn top(@builtin(local_invocation_index) t: u32) {\n var run = 0u;\n for (var c = 0u; c < state.chunks; c++) {\n let x = sums[c * DIGITS + t];\n sums[c * DIGITS + t] = run;\n run += x;\n }\n totals[t] = run;\n // a bit varies only when both zero and one occur in nonempty digits\n if (run > 0u) {\n atomicOr(&bitValues, t | ((255u ^ t) << 8u));\n }\n workgroupBarrier();\n if (t == 0u) {\n let values = atomicLoad(&bitValues);\n sums[arrayLength(&sums) - 1u] = values & (values >> 8u);\n }\n for (var o = 1u; o < DIGITS; o *= 2u) {\n var x = 0u;\n if (t >= o) {\n x = totals[t - o];\n }\n workgroupBarrier();\n totals[t] += x;\n workgroupBarrier();\n }\n let base = totals[t] - run;\n for (var c = 0u; c < state.chunks; c++) {\n sums[c * DIGITS + t] += base;\n }\n}\n\n@compute @workgroup_size(DIGITS)\nfn down(@builtin(workgroup_id) wid: vec3u, @builtin(local_invocation_index) t: u32) {\n let end = min((wid.x + 1u) * CHUNK, state.blocks);\n var run = sums[wid.x * DIGITS + t];\n for (var b = wid.x * CHUNK; b < end; b++) {\n let x = hist[b * DIGITS + t];\n hist[b * DIGITS + t] = run;\n run += x;\n }\n}\n\n@compute @workgroup_size(THREADS)\nfn scatter(\n @builtin(workgroup_id) wid: vec3u,\n @builtin(num_workgroups) groups: vec3u,\n @builtin(local_invocation_index) t: u32\n) {\n let first = wid.y * groups.x + wid.x;\n if (first >= state.blocks) {\n return;\n }\n if (t == 0u) {\n activeBits = sums[arrayLength(&sums) - 1u];\n }\n let bits = workgroupUniformLoad(&activeBits);\n for (var block = first; block < state.blocks; block += groups.x * groups.y) {\n let head = block * BLOCK;\n let valid = min(BLOCK, state.count - head);\n // padding has digit 255 at every shift, so it sorts behind the valid keys and is never written\n for (var k = 0u; k < ITEMS; k++) {\n let i = k * THREADS + t;\n var key = 0xffffffffu;\n var value = 0u;\n if (i < valid) {\n key = data[params.src + head + i];\n value = data[params.src + params.capacity + head + i];\n }\n sk[i] = key;\n sv[i] = value;\n }\n for (var d = t; d < DIGITS; d += THREADS) {\n offsets[d] = hist[block * DIGITS + d];\n }\n workgroupBarrier();\n\n // stable local sort by the digit, two bits a split; thread t owns positions t ITEMS + k\n for (var bit = 0u; bit < 8u; bit += 2u) {\n if ((bits & (3u << bit)) == 0u) {\n continue;\n }\n var keys: array<u32, ITEMS>;\n var values: array<u32, ITEMS>;\n var before: array<u32, ITEMS>;\n var mine = vec4u(0u);\n for (var k = 0u; k < ITEMS; k++) {\n keys[k] = sk[t * ITEMS + k];\n values[k] = sv[t * ITEMS + k];\n let b = (keys[k] >> (params.shift + bit)) & 3u;\n before[k] = mine[b];\n mine[b] += 1u;\n }\n counts[t] = mine.x | (mine.y << 10u) | (mine.z << 20u);\n if (t == THREADS - 1u) {\n tail = counts[t];\n }\n workgroupBarrier();\n // separate reads and writes need only one barrier per scan step\n var source = 0u;\n for (var o = 1u; o < THREADS; o *= 2u) {\n var x = counts[source + t];\n if (t >= o) {\n x += counts[source + t - o];\n }\n let dest = source ^ THREADS;\n counts[dest + t] = x;\n workgroupBarrier();\n source = dest;\n }\n // prefixes stop at 1016 items, so no count carries into its neighbour\n let total = unpack(counts[source + THREADS - 2u], BLOCK - ITEMS) + unpack(tail, ITEMS);\n var prior = vec4u(0u);\n if (t > 0u) {\n prior = unpack(counts[source + t - 1u], t * ITEMS);\n }\n let base = vec4u(0u, total.x, total.x + total.y, total.x + total.y + total.z);\n for (var k = 0u; k < ITEMS; k++) {\n let b = (keys[k] >> (params.shift + bit)) & 3u;\n let p = base[b] + prior[b] + before[k];\n sk[p] = keys[k];\n sv[p] = values[k];\n }\n workgroupBarrier();\n }\n\n for (var k = 0u; k < ITEMS; k++) {\n let i = t * ITEMS + k;\n let d = digit(sk[i]);\n if (i == 0u || digit(sk[i - 1u]) != d) {\n starts[d] = i;\n }\n }\n workgroupBarrier();\n for (var k = 0u; k < ITEMS; k++) {\n let i = k * THREADS + t;\n if (i < valid) {\n let d = digit(sk[i]);\n let slot = offsets[d] + i - starts[d];\n data[params.dst + slot] = sk[i];\n data[params.dst + params.capacity + slot] = sv[i];\n }\n }\n workgroupBarrier();\n }\n}\n", Je = 1024, Ye = 64, Xe = 256, L = 3, R = 256, Ze = 32, Qe = class {
|
|
1165
1219
|
keys;
|
|
1166
1220
|
values;
|
|
1167
1221
|
bytes;
|
|
@@ -1174,21 +1228,21 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1174
1228
|
constructor(e, t) {
|
|
1175
1229
|
let { capacity: n } = t;
|
|
1176
1230
|
this.keys = n * 8, this.values = n * 12;
|
|
1177
|
-
let r = Math.max(1, Math.ceil(n /
|
|
1231
|
+
let r = Math.max(1, Math.ceil(n / Je));
|
|
1178
1232
|
this.#a = r;
|
|
1179
|
-
let i = Math.ceil(r /
|
|
1233
|
+
let i = Math.ceil(r / Ye), a = (t, n, r) => e.createBuffer({
|
|
1180
1234
|
label: t,
|
|
1181
1235
|
size: n,
|
|
1182
1236
|
usage: r
|
|
1183
|
-
}), o = GPUBufferUsage.STORAGE, s = a("sort params",
|
|
1237
|
+
}), o = GPUBufferUsage.STORAGE, s = a("sort params", L * R, GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST), c = a("sort histograms", r * Xe * 4, o), l = a("sort chunk sums", (i * Xe + 1) * 4, o), u = a("sort state", 12, o);
|
|
1184
1238
|
this.#e = [
|
|
1185
1239
|
s,
|
|
1186
1240
|
c,
|
|
1187
1241
|
l,
|
|
1188
1242
|
u
|
|
1189
1243
|
], this.bytes = this.#e.reduce((e, t) => e + t.size, 0);
|
|
1190
|
-
let d = new Uint32Array(
|
|
1191
|
-
for (let e = 0; e <
|
|
1244
|
+
let d = new Uint32Array(L * R / 4);
|
|
1245
|
+
for (let e = 0; e < L; e++) {
|
|
1192
1246
|
let [t, r] = e % 2 ? [2 * n, 0] : [0, 2 * n];
|
|
1193
1247
|
d.set([
|
|
1194
1248
|
8 * e,
|
|
@@ -1197,7 +1251,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1197
1251
|
n,
|
|
1198
1252
|
f.projected,
|
|
1199
1253
|
f.drawArgs
|
|
1200
|
-
], e *
|
|
1254
|
+
], e * R / 4);
|
|
1201
1255
|
}
|
|
1202
1256
|
e.queue.writeBuffer(s, 0, d);
|
|
1203
1257
|
let p = (e, t) => ({
|
|
@@ -1219,7 +1273,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1219
1273
|
]
|
|
1220
1274
|
}), g = e.createShaderModule({
|
|
1221
1275
|
label: "sort",
|
|
1222
|
-
code:
|
|
1276
|
+
code: F + qe
|
|
1223
1277
|
}), _ = (t, n) => e.createComputePipeline({
|
|
1224
1278
|
label: `sort ${t}`,
|
|
1225
1279
|
layout: e.createPipelineLayout({ bindGroupLayouts: [n] }),
|
|
@@ -1237,8 +1291,8 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1237
1291
|
].map((e) => _(e, m));
|
|
1238
1292
|
let v = (e) => ({
|
|
1239
1293
|
buffer: s,
|
|
1240
|
-
offset: e *
|
|
1241
|
-
size:
|
|
1294
|
+
offset: e * R,
|
|
1295
|
+
size: Ze
|
|
1242
1296
|
});
|
|
1243
1297
|
this.#r = e.createBindGroup({
|
|
1244
1298
|
label: "sort prepare",
|
|
@@ -1257,7 +1311,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1257
1311
|
resource: { buffer: t.work }
|
|
1258
1312
|
}
|
|
1259
1313
|
]
|
|
1260
|
-
}), this.#i = Array.from({ length:
|
|
1314
|
+
}), this.#i = Array.from({ length: L }, (n, r) => e.createBindGroup({
|
|
1261
1315
|
label: `sort pass ${r}`,
|
|
1262
1316
|
layout: m,
|
|
1263
1317
|
entries: [
|
|
@@ -1285,7 +1339,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1285
1339
|
}));
|
|
1286
1340
|
}
|
|
1287
1341
|
encode(e, t, n, r) {
|
|
1288
|
-
let [i, a, o, s, c] = this.#n, l = Math.max(1, Math.min(this.#a, Math.ceil(t /
|
|
1342
|
+
let [i, a, o, s, c] = this.#n, l = Math.max(1, Math.min(this.#a, Math.ceil(t / Je))), u = Math.max(l / 16, (n || t) / Je), d = m(Math.min(Math.ceil(l / 4), Math.ceil(u))), f = Math.ceil(l / Ye), p = e.beginComputePass({
|
|
1289
1343
|
label: "sort",
|
|
1290
1344
|
timestampWrites: r
|
|
1291
1345
|
});
|
|
@@ -1296,7 +1350,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1296
1350
|
destroy() {
|
|
1297
1351
|
for (let e of this.#e) e.destroy();
|
|
1298
1352
|
}
|
|
1299
|
-
},
|
|
1353
|
+
}, $e = class {
|
|
1300
1354
|
ms = {};
|
|
1301
1355
|
#e;
|
|
1302
1356
|
#t;
|
|
@@ -1347,14 +1401,14 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1347
1401
|
destroy() {
|
|
1348
1402
|
this.#t?.destroy(), this.#n?.destroy(), this.#r?.destroy();
|
|
1349
1403
|
}
|
|
1350
|
-
},
|
|
1404
|
+
}, et = [
|
|
1351
1405
|
"cull",
|
|
1352
1406
|
"project",
|
|
1353
1407
|
"sort",
|
|
1354
1408
|
"raster",
|
|
1355
1409
|
"heights",
|
|
1356
1410
|
"post"
|
|
1357
|
-
],
|
|
1411
|
+
], z = {
|
|
1358
1412
|
view: 0,
|
|
1359
1413
|
proj: 16,
|
|
1360
1414
|
viewProj: 32,
|
|
@@ -1367,7 +1421,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1367
1421
|
far: 81,
|
|
1368
1422
|
lowPass: 82,
|
|
1369
1423
|
clusters: 83
|
|
1370
|
-
},
|
|
1424
|
+
}, tt = class {
|
|
1371
1425
|
#e;
|
|
1372
1426
|
#t;
|
|
1373
1427
|
#n;
|
|
@@ -1398,7 +1452,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1398
1452
|
#D = 0;
|
|
1399
1453
|
constructor(e, t, n, r) {
|
|
1400
1454
|
let { device: i } = e;
|
|
1401
|
-
this.#e = i, this.#t = t, this.#n = e.format, this.#r = n, this.#i = b(i, r, n.slots), this.#a = new
|
|
1455
|
+
this.#e = i, this.#t = t, this.#n = e.format, this.#r = n, this.#i = b(i, r, n.slots), this.#a = new de(i, n, this.#i), this.#o = new Te(i, n, this.#i), this.#s = new Qe(i, this.#i), this.#c = new Ke(i, this.#i, this.#s), this.#u = new ve(i, n), this.#d = new Be(i, n, this.#i), this.#f = new Ae(i, e.format, this.#i.uniforms), this.#p = new $e(i, e.timestamps, et), this.#w = i.createBuffer({
|
|
1402
1456
|
label: "counts readback",
|
|
1403
1457
|
size: (f.projected + 1) * 4,
|
|
1404
1458
|
usage: GPUBufferUsage.COPY_DST | GPUBufferUsage.MAP_READ
|
|
@@ -1435,7 +1489,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1435
1489
|
this.#f.set(e, t);
|
|
1436
1490
|
}
|
|
1437
1491
|
render(e, t, n, r) {
|
|
1438
|
-
let i = this.#e, a = this.#p, o = this.#y, s = this.#j(this.#A("colour",
|
|
1492
|
+
let i = this.#e, a = this.#p, o = this.#y, s = this.#j(this.#A("colour", Ue)), c = this.#f.count > 0, l = c || o.some(({ post: e }) => e.depth), u = this.#M("depth", We, l), d = u ? this.#j(u) : null, p = [this.#M("ping", this.#n, o.length > 1), this.#M("pong", this.#n, o.length > 2)];
|
|
1439
1493
|
this.#k(e, t);
|
|
1440
1494
|
let m = i.createCommandEncoder({ label: "frame" });
|
|
1441
1495
|
m.clearBuffer(this.#i.work, 0, f.list * 4), this.#a.encode(m, a.writes("cull")), this.#o.encode(m, this.#D, a.writes("project")), this.#s.encode(m, this.#r.listed * 256, this.#E, a.writes("sort")), this.#c.encode(m, s, d, n, a.writes("raster"));
|
|
@@ -1451,7 +1505,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1451
1505
|
} }).end();
|
|
1452
1506
|
}
|
|
1453
1507
|
let _ = this.#t.getCurrentTexture().createView();
|
|
1454
|
-
if (!o.length) this.#l ??=
|
|
1508
|
+
if (!o.length) this.#l ??= Se(i, this.#n), this.#l.encode(m, [s], _);
|
|
1455
1509
|
else {
|
|
1456
1510
|
let t = s;
|
|
1457
1511
|
o.forEach(({ post: n, pass: r }, i) => {
|
|
@@ -1493,7 +1547,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1493
1547
|
}
|
|
1494
1548
|
#k(e, t) {
|
|
1495
1549
|
let n = this.#m, [r, i] = [this.#S, this.#C];
|
|
1496
|
-
n.set(e.view,
|
|
1550
|
+
n.set(e.view, z.view), n.set(e.proj, z.proj), n.set(P(this.#g, e.proj, e.view), z.viewProj), n.set(t, z.planes), n.set(e.camera.subarray(0, 3), z.camera), n[z.time] = e.time, n.set([r, i], z.viewport), n.set([e.proj[0] * r / 2, e.proj[5] * i / 2], z.focal), n[z.near] = e.near, n[z.far] = e.far, n[z.lowPass] = h, this.#h[z.clusters] = this.#r.listed, this.#e.queue.writeBuffer(this.#i.uniforms, 0, n);
|
|
1497
1551
|
for (let { shade: t, slot: n } of this.#v) t.update(e, this.#_.subarray(n * 4, (n + t.uniforms) * 4));
|
|
1498
1552
|
this.#v.length && this.#e.queue.writeBuffer(this.#i.plugins, 0, this.#_);
|
|
1499
1553
|
}
|
|
@@ -1529,7 +1583,7 @@ var Me = "// the nearest solid splat under one pixel, over the last frame's visi
|
|
|
1529
1583
|
};
|
|
1530
1584
|
//#endregion
|
|
1531
1585
|
//#region src/engine/layer.ts
|
|
1532
|
-
async function
|
|
1586
|
+
async function nt(e, n) {
|
|
1533
1587
|
let i = await r(async (t, n) => e.subarray(t, n), e.length);
|
|
1534
1588
|
if (i.length === 0) throw Error("the pack holds no pages");
|
|
1535
1589
|
let a = Math.min(...i.map((e) => e.g));
|
|
@@ -1541,7 +1595,7 @@ async function Qe(e, n) {
|
|
|
1541
1595
|
};
|
|
1542
1596
|
}));
|
|
1543
1597
|
}
|
|
1544
|
-
function
|
|
1598
|
+
function rt(e) {
|
|
1545
1599
|
let t = (t) => [Math.min(...e.map((e) => e[t])), Math.max(...e.map((e) => e[t + 3]))];
|
|
1546
1600
|
return {
|
|
1547
1601
|
e: t(0),
|
|
@@ -1549,19 +1603,19 @@ function $e(e) {
|
|
|
1549
1603
|
h: t(2)
|
|
1550
1604
|
};
|
|
1551
1605
|
}
|
|
1552
|
-
var
|
|
1606
|
+
var it = class {
|
|
1553
1607
|
#e = /* @__PURE__ */ new Map();
|
|
1554
1608
|
update(e, t, n, r) {
|
|
1555
|
-
let i = this.#e, a =
|
|
1556
|
-
for (let [e, r] of i) t(r.page.id) ? (o = Math.max(o, r.level), !r.held && (r.start !== null && n - r.start >= 250 && (r.start = null), a.has(e) || (r.frozen =
|
|
1609
|
+
let i = this.#e, a = at(e, t), o = -1;
|
|
1610
|
+
for (let [e, r] of i) t(r.page.id) ? (o = Math.max(o, r.level), !r.held && (r.start !== null && n - r.start >= 250 && (r.start = null), a.has(e) || (r.frozen = B(r, n), r.start = null, r.out = null, r.covered = !1, r.held = !0))) : i.delete(e);
|
|
1557
1611
|
let s = /* @__PURE__ */ new Set();
|
|
1558
1612
|
for (let [e, t] of a) {
|
|
1559
1613
|
let r = i.get(e);
|
|
1560
1614
|
if (!r) {
|
|
1561
|
-
let r =
|
|
1615
|
+
let r = ot(t, e % 4, n);
|
|
1562
1616
|
o = Math.max(o, r.level), i.set(e, r), s.add(r);
|
|
1563
1617
|
} else if (r.held) {
|
|
1564
|
-
let e =
|
|
1618
|
+
let e = B(r, n);
|
|
1565
1619
|
r.held = !1, r.out = null, e < 255 && (r.start = n - e / 255 * 250, s.add(r));
|
|
1566
1620
|
}
|
|
1567
1621
|
}
|
|
@@ -1569,14 +1623,14 @@ var et = class {
|
|
|
1569
1623
|
for (let e of i.values()) if (e.held) {
|
|
1570
1624
|
c.set(e.cell, e);
|
|
1571
1625
|
for (let t = e.level, n = e.col, r = e.row; t <= o; t++, n >>= 1, r >>= 1) {
|
|
1572
|
-
let i =
|
|
1626
|
+
let i = st(t, n, r), a = l.get(i);
|
|
1573
1627
|
a ? a.push(e) : l.set(i, [e]);
|
|
1574
1628
|
}
|
|
1575
1629
|
}
|
|
1576
1630
|
let u = (e) => {
|
|
1577
1631
|
let t = [...l.get(e.cell) ?? []];
|
|
1578
1632
|
for (let n = e.level + 1, r = e.col >> 1, i = e.row >> 1; n <= o; n++, r >>= 1, i >>= 1) {
|
|
1579
|
-
let e = c.get(
|
|
1633
|
+
let e = c.get(st(n, r, i));
|
|
1580
1634
|
e && t.push(e);
|
|
1581
1635
|
}
|
|
1582
1636
|
return t;
|
|
@@ -1600,13 +1654,13 @@ var et = class {
|
|
|
1600
1654
|
}
|
|
1601
1655
|
let v = /* @__PURE__ */ new Map(), y = !1;
|
|
1602
1656
|
for (let [e, t] of i) {
|
|
1603
|
-
if (t.held && f.has(t)) t.out !== null && (t.frozen =
|
|
1604
|
-
else if (t.held && (t.covered && t.out === null && (t.out = n), !t.covered ||
|
|
1657
|
+
if (t.held && f.has(t)) t.out !== null && (t.frozen = B(t, n)), t.out = null, t.covered = !0;
|
|
1658
|
+
else if (t.held && (t.covered && t.out === null && (t.out = n), !t.covered || B(t, n) === 0)) {
|
|
1605
1659
|
i.delete(e);
|
|
1606
1660
|
continue;
|
|
1607
1661
|
}
|
|
1608
1662
|
(t.held || t.start !== null) && (y = !0);
|
|
1609
|
-
let r =
|
|
1663
|
+
let r = B(t, n);
|
|
1610
1664
|
if (!r) continue;
|
|
1611
1665
|
let a = v.get(t.page.id);
|
|
1612
1666
|
a ? a.factors = (a.factors | r << 8 * t.q) >>> 0 : v.set(t.page.id, {
|
|
@@ -1620,7 +1674,7 @@ var et = class {
|
|
|
1620
1674
|
};
|
|
1621
1675
|
}
|
|
1622
1676
|
};
|
|
1623
|
-
function
|
|
1677
|
+
function at(e, t) {
|
|
1624
1678
|
let n = new Set(e), r = /* @__PURE__ */ new Set(), i = [];
|
|
1625
1679
|
for (let t of e) for (let e = t; e && !r.has(e); e = e.parent) r.add(e), e.parent || i.push(e);
|
|
1626
1680
|
let a = /* @__PURE__ */ new Map(), o = (e) => {
|
|
@@ -1632,7 +1686,7 @@ function tt(e, t) {
|
|
|
1632
1686
|
for (let e of i) t(e.id) && o(e);
|
|
1633
1687
|
return a;
|
|
1634
1688
|
}
|
|
1635
|
-
function
|
|
1689
|
+
function ot(e, t, n) {
|
|
1636
1690
|
let r = c * 2 ** e.g, i = e.g - 1, a = 2 * (Math.round(e.unit.e / r) + e.row.i) + (t & 1), o = 2 * (Math.round(e.unit.n / r) + e.row.j) + (t >> 1);
|
|
1637
1691
|
return {
|
|
1638
1692
|
page: e,
|
|
@@ -1640,8 +1694,8 @@ function nt(e, t, n) {
|
|
|
1640
1694
|
level: i,
|
|
1641
1695
|
col: a,
|
|
1642
1696
|
row: o,
|
|
1643
|
-
cell:
|
|
1644
|
-
splats:
|
|
1697
|
+
cell: st(i, a, o),
|
|
1698
|
+
splats: ct(e.row, t),
|
|
1645
1699
|
start: n,
|
|
1646
1700
|
frozen: 0,
|
|
1647
1701
|
out: null,
|
|
@@ -1649,56 +1703,56 @@ function nt(e, t, n) {
|
|
|
1649
1703
|
held: !1
|
|
1650
1704
|
};
|
|
1651
1705
|
}
|
|
1652
|
-
var
|
|
1653
|
-
function
|
|
1706
|
+
var st = (e, t, n) => ((e + 1) * 2 ** 21 + t) * 2 ** 21 + n;
|
|
1707
|
+
function ct({ count: e, quadrants: t }, n) {
|
|
1654
1708
|
return (n < 3 ? t[n] : e) - (n > 0 ? t[n - 1] : 0);
|
|
1655
1709
|
}
|
|
1656
|
-
function
|
|
1710
|
+
function B(e, t) {
|
|
1657
1711
|
return e.held ? e.out === null ? e.frozen : Math.max(0, Math.round(e.frozen * (1 - (t - e.out) / 250))) : e.start === null ? 255 : Math.min(255, Math.round((t - e.start) / 250 * 255));
|
|
1658
1712
|
}
|
|
1659
1713
|
//#endregion
|
|
1660
1714
|
//#region src/engine/plan/footprint.ts
|
|
1661
|
-
var
|
|
1715
|
+
var lt = [
|
|
1662
1716
|
0,
|
|
1663
1717
|
0,
|
|
1664
1718
|
0
|
|
1665
1719
|
];
|
|
1666
|
-
function
|
|
1720
|
+
function ut(e, t, n, r) {
|
|
1667
1721
|
let i = (e * e + e * t + t * t + n * n + n * r + r * r) / 3;
|
|
1668
1722
|
return 1 + 15 * Math.max(0, 1 - i) ** 2;
|
|
1669
1723
|
}
|
|
1670
|
-
function
|
|
1724
|
+
function dt(e, t, n, r, i, a, o, s = 1, c = {
|
|
1671
1725
|
shown: !1,
|
|
1672
1726
|
pixels: 0,
|
|
1673
1727
|
weight: 1
|
|
1674
|
-
}, l =
|
|
1728
|
+
}, l = lt) {
|
|
1675
1729
|
let u = (e[0] + e[3]) / 2 - l[0], d = (e[1] + e[4]) / 2 - l[1], f = (e[2] + e[5]) / 2 - l[2], p = (e[3] - e[0]) / 2, m = (e[4] - e[1]) / 2, h = (e[5] - e[2]) / 2, g = t[0] * u + t[4] * d + t[8] * f + t[12], _ = t[1] * u + t[5] * d + t[9] * f + t[13], v = -(t[2] * u + t[6] * d + t[10] * f + t[14]), y = Math.abs(t[0]) * p + Math.abs(t[4]) * m + Math.abs(t[8]) * h, b = Math.abs(t[1]) * p + Math.abs(t[5]) * m + Math.abs(t[9]) * h, x = Math.abs(t[2]) * p + Math.abs(t[6]) * m + Math.abs(t[10]) * h;
|
|
1676
1730
|
if (c.pixels = 0, c.weight = 1, c.shown = !1, v + x < a || v - x > o) return c;
|
|
1677
1731
|
let S = Math.max(a, v - x), C = Math.max(a, v + x), w = i * n / r;
|
|
1678
1732
|
if (Math.abs(g) - y > s * w * C || Math.abs(_) - b > s * i * C) return c;
|
|
1679
1733
|
let T = Math.min((g - y) / S, (g - y) / C) / w, E = Math.max((g + y) / S, (g + y) / C) / w, D = Math.min((_ - b) / S, (_ - b) / C) / i, O = Math.max((_ + b) / S, (_ + b) / C) / i;
|
|
1680
1734
|
if (E < -s || T > s || O < -s || D > s) return c;
|
|
1681
|
-
let k = Math.max(-s, T), A = Math.min(s, E), j = Math.max(-s, D), M = Math.min(s, O),
|
|
1682
|
-
return
|
|
1735
|
+
let k = Math.max(-s, T), A = Math.min(s, E), j = Math.max(-s, D), M = Math.min(s, O), N = (E - T) * (O - D), ee = (A - k) * (M - j);
|
|
1736
|
+
return N <= 0 || ee <= 0 || (c.shown = E > -1 && T < 1 && O > -1 && D < 1, c.pixels = N * n * r / 4, c.weight = ut(k, A, j, M)), c;
|
|
1683
1737
|
}
|
|
1684
|
-
var
|
|
1738
|
+
var V = /* @__PURE__ */ new Float64Array(6), ft = {
|
|
1685
1739
|
shown: !1,
|
|
1686
1740
|
pixels: 0,
|
|
1687
1741
|
weight: 1
|
|
1688
1742
|
};
|
|
1689
|
-
function
|
|
1743
|
+
function pt(e, [t, n, r], i, a, o, s, c, l, u = lt) {
|
|
1690
1744
|
let d = r / 2, f = Math.max(0, t - e[0], n - e[1], e[3] - t - r, e[4] - n - r);
|
|
1691
|
-
|
|
1745
|
+
V[2] = e[2], V[5] = e[5];
|
|
1692
1746
|
let p = 0;
|
|
1693
1747
|
for (let r = 0; r < 4; r++) {
|
|
1694
1748
|
let m = t + (r & 1) * d, h = n + (r >> 1) * d;
|
|
1695
|
-
|
|
1749
|
+
V[0] = Math.max(e[0], m - f), V[1] = Math.max(e[1], h - f), V[3] = Math.min(e[3], m + d + f), V[4] = Math.min(e[4], h + d + f), !(V[0] > V[3] || V[1] > V[4]) && dt(V, i, a, o, s, c, l, 1, ft, u).shown && (p |= 1 << r);
|
|
1696
1750
|
}
|
|
1697
1751
|
return p;
|
|
1698
1752
|
}
|
|
1699
1753
|
//#endregion
|
|
1700
1754
|
//#region src/engine/world/tree.ts
|
|
1701
|
-
var
|
|
1755
|
+
var H = (e, t, n) => (e * 256 + t) * 256 + n, mt = class {
|
|
1702
1756
|
roots = [];
|
|
1703
1757
|
pages = /* @__PURE__ */ new Map();
|
|
1704
1758
|
units = /* @__PURE__ */ new Map();
|
|
@@ -1708,10 +1762,10 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1708
1762
|
#r = /* @__PURE__ */ new Map();
|
|
1709
1763
|
#i = /* @__PURE__ */ new Map();
|
|
1710
1764
|
constructor(e) {
|
|
1711
|
-
this.#e = new Set(e.roots.map(
|
|
1765
|
+
this.#e = new Set(e.roots.map(U)), this.#t = Math.max(...e.roots.map((e) => e.level));
|
|
1712
1766
|
}
|
|
1713
1767
|
add(e, t) {
|
|
1714
|
-
let n =
|
|
1768
|
+
let n = U(e), r = this.units.get(n);
|
|
1715
1769
|
if (r) return r;
|
|
1716
1770
|
let a = /* @__PURE__ */ new Map(), o = {
|
|
1717
1771
|
level: e.level,
|
|
@@ -1738,34 +1792,34 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1738
1792
|
null
|
|
1739
1793
|
]
|
|
1740
1794
|
};
|
|
1741
|
-
this.pages.set(r.id, r), o.pages.push(r), a.set(
|
|
1795
|
+
this.pages.set(r.id, r), o.pages.push(r), a.set(H(t.g, t.i, t.j), r);
|
|
1742
1796
|
}
|
|
1743
1797
|
this.units.set(n, o), this.#r.delete(n);
|
|
1744
1798
|
for (let t = e.level + 1; t <= this.#t; t++) {
|
|
1745
|
-
let n =
|
|
1799
|
+
let n = U(W(e, t));
|
|
1746
1800
|
this.#i.set(n, (this.#i.get(n) ?? 0) + 1);
|
|
1747
1801
|
}
|
|
1748
1802
|
let c = new Set(e.rows.map((e) => e.g)), l = Math.max(...c), u = e.level === 0 ? 0 : e.level + 1, d = new Set(e.children.map((e) => e.quadrant));
|
|
1749
1803
|
for (let e of o.pages) {
|
|
1750
1804
|
let { g: t, i: n, j: r } = e.row;
|
|
1751
|
-
c.has(t + 1) && (e.parent = a.get(
|
|
1805
|
+
c.has(t + 1) && (e.parent = a.get(H(t + 1, n >> 1, r >> 1)) ?? null);
|
|
1752
1806
|
for (let i = 0; i < 4; i++) {
|
|
1753
1807
|
let o = 2 * n + (i & 1), s = 2 * r + (i >> 1);
|
|
1754
|
-
c.has(t - 1) ? e.children[i] = a.get(
|
|
1808
|
+
c.has(t - 1) ? e.children[i] = a.get(H(t - 1, o, s)) ?? null : t === u && t > 0 && (e.children[i] = d.has((o >> 3) + 2 * (s >> 3)) ? void 0 : null);
|
|
1755
1809
|
}
|
|
1756
1810
|
}
|
|
1757
1811
|
if (this.#e.has(n)) for (let e of o.pages) e.g === l && this.roots.push(e);
|
|
1758
1812
|
else {
|
|
1759
|
-
let t = this.units.get(
|
|
1813
|
+
let t = this.units.get(U(W(e, e.level + 1)));
|
|
1760
1814
|
t && this.#o(t, o);
|
|
1761
1815
|
}
|
|
1762
1816
|
let f = i(o.idx);
|
|
1763
1817
|
for (let { key: t } of f) {
|
|
1764
|
-
let n = t.level === e.level - 1 ? this.units.get(
|
|
1818
|
+
let n = t.level === e.level - 1 ? this.units.get(U(t)) : void 0;
|
|
1765
1819
|
n && this.#o(o, n);
|
|
1766
1820
|
}
|
|
1767
1821
|
for (let { key: e, hash: t } of f) {
|
|
1768
|
-
let n =
|
|
1822
|
+
let n = U(e);
|
|
1769
1823
|
if (this.units.has(n)) continue;
|
|
1770
1824
|
let r = this.#r.get(n);
|
|
1771
1825
|
if (r && r.from <= o.level) continue;
|
|
@@ -1786,19 +1840,19 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1786
1840
|
}
|
|
1787
1841
|
ground(e, t) {
|
|
1788
1842
|
for (let n of this.roots) {
|
|
1789
|
-
let [r, i, a] =
|
|
1843
|
+
let [r, i, a] = gt(n);
|
|
1790
1844
|
if (e < r || e >= r + a || t < i || t >= i + a) continue;
|
|
1791
1845
|
let o = n;
|
|
1792
1846
|
for (;;) {
|
|
1793
1847
|
let n = +(e >= r + a / 2), s = +(t >= i + a / 2), c = o.children[n + 2 * s];
|
|
1794
1848
|
if (!c) return o.box[2];
|
|
1795
|
-
o = c, [r, i, a] =
|
|
1849
|
+
o = c, [r, i, a] = gt(o);
|
|
1796
1850
|
}
|
|
1797
1851
|
}
|
|
1798
1852
|
}
|
|
1799
1853
|
async load(e, t, n) {
|
|
1800
1854
|
for (;;) {
|
|
1801
|
-
let r = this.wanted().filter((n) =>
|
|
1855
|
+
let r = this.wanted().filter((n) => ht(n, e, t));
|
|
1802
1856
|
if (r.length === 0) return;
|
|
1803
1857
|
(await Promise.all(r.map((e) => n(e.path)))).forEach((e, t) => this.add(e, r[t].path));
|
|
1804
1858
|
}
|
|
@@ -1806,7 +1860,7 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1806
1860
|
prune(e) {
|
|
1807
1861
|
let t = [], n = [...this.units.values()].sort((e, t) => e.level - t.level);
|
|
1808
1862
|
for (let r of n) {
|
|
1809
|
-
let n =
|
|
1863
|
+
let n = U(r);
|
|
1810
1864
|
if (this.#e.has(n) || this.#i.has(n) || r.pages.some((t) => e.has(t.id))) continue;
|
|
1811
1865
|
for (let e of r.pages) this.pages.delete(e.id), t.push(e.id);
|
|
1812
1866
|
let a = r.parent;
|
|
@@ -1816,7 +1870,7 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1816
1870
|
}
|
|
1817
1871
|
this.units.delete(n);
|
|
1818
1872
|
for (let e = r.level + 1; e <= this.#t; e++) {
|
|
1819
|
-
let t =
|
|
1873
|
+
let t = U(W(r, e)), n = this.#i.get(t) - 1;
|
|
1820
1874
|
n ? this.#i.set(t, n) : this.#i.delete(t);
|
|
1821
1875
|
}
|
|
1822
1876
|
for (let { key: e } of i(r.idx)) this.#a(e);
|
|
@@ -1825,12 +1879,12 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1825
1879
|
return t;
|
|
1826
1880
|
}
|
|
1827
1881
|
#a(e) {
|
|
1828
|
-
let t =
|
|
1882
|
+
let t = U(e);
|
|
1829
1883
|
this.#r.delete(t);
|
|
1830
1884
|
for (let n = e.level + 1; n <= e.level + 3; n++) {
|
|
1831
|
-
let r = this.units.get(
|
|
1885
|
+
let r = this.units.get(U(W(e, n)));
|
|
1832
1886
|
if (!r) continue;
|
|
1833
|
-
let a = i(r.idx).find((e) =>
|
|
1887
|
+
let a = i(r.idx).find((e) => U(e.key) === t);
|
|
1834
1888
|
if (!a) continue;
|
|
1835
1889
|
let o = {
|
|
1836
1890
|
level: e.level,
|
|
@@ -1852,23 +1906,23 @@ var B = (e, t, n) => (e * 256 + t) * 256 + n, ut = class {
|
|
|
1852
1906
|
for (let n of this.#s(e, t)) n.children.fill(null);
|
|
1853
1907
|
for (let e of t.pages) {
|
|
1854
1908
|
if (e.g !== n) continue;
|
|
1855
|
-
let t = 8 * i + e.row.i, r = 8 * a + e.row.j, s = o.get(
|
|
1909
|
+
let t = 8 * i + e.row.i, r = 8 * a + e.row.j, s = o.get(H(n + 1, t >> 1, r >> 1)) ?? null;
|
|
1856
1910
|
e.parent = s, s && (s.children[(t & 1) + 2 * (r & 1)] = e);
|
|
1857
1911
|
}
|
|
1858
1912
|
}
|
|
1859
1913
|
#s(e, t) {
|
|
1860
1914
|
let n = e.level + 1, r = c * 2 ** n, i = (t.e - e.e) / r, a = (t.n - e.n) / r, o = 250 * 2 ** t.level / r, s = [];
|
|
1861
1915
|
for (let t = a; t < a + o; t++) for (let r = i; r < i + o; r++) {
|
|
1862
|
-
let i = e.grid.get(
|
|
1916
|
+
let i = e.grid.get(H(n, r, t));
|
|
1863
1917
|
i && s.push(i);
|
|
1864
1918
|
}
|
|
1865
1919
|
return s;
|
|
1866
1920
|
}
|
|
1867
1921
|
};
|
|
1868
|
-
function
|
|
1922
|
+
function U(e) {
|
|
1869
1923
|
return `${e.level}/${e.e}/${e.n}`;
|
|
1870
1924
|
}
|
|
1871
|
-
function
|
|
1925
|
+
function W(e, t) {
|
|
1872
1926
|
let n = 250 * 2 ** t;
|
|
1873
1927
|
return {
|
|
1874
1928
|
level: t,
|
|
@@ -1876,11 +1930,11 @@ function H(e, t) {
|
|
|
1876
1930
|
n: Math.floor(e.n / n) * n
|
|
1877
1931
|
};
|
|
1878
1932
|
}
|
|
1879
|
-
function
|
|
1933
|
+
function ht(e, t, n) {
|
|
1880
1934
|
let r = 250 * 2 ** e.level;
|
|
1881
1935
|
return t >= e.e && t < e.e + r && n >= e.n && n < e.n + r;
|
|
1882
1936
|
}
|
|
1883
|
-
function
|
|
1937
|
+
function gt(e) {
|
|
1884
1938
|
let t = c * 2 ** e.g;
|
|
1885
1939
|
return [
|
|
1886
1940
|
e.unit.e + e.row.i * t,
|
|
@@ -1890,7 +1944,7 @@ function ft(e) {
|
|
|
1890
1944
|
}
|
|
1891
1945
|
//#endregion
|
|
1892
1946
|
//#region src/engine/plan/cut.ts
|
|
1893
|
-
var
|
|
1947
|
+
var _t = 1 / .8 ** 2, vt = 1.1, yt = class {
|
|
1894
1948
|
#e = /* @__PURE__ */ new Map();
|
|
1895
1949
|
#t = /* @__PURE__ */ new Map();
|
|
1896
1950
|
#n = {
|
|
@@ -1899,13 +1953,13 @@ var pt = 1 / .8 ** 2, mt = 1.1, ht = class {
|
|
|
1899
1953
|
weight: 1
|
|
1900
1954
|
};
|
|
1901
1955
|
plan(e, t, n, r) {
|
|
1902
|
-
let { budget: i, capacity: a, now: o, predicted: s } = r, c = [], l = [], u = [], f = /* @__PURE__ */ new Map(), p = /* @__PURE__ */ new Map(), m = e.wanted(), h = /* @__PURE__ */ new Map(), g = new
|
|
1956
|
+
let { budget: i, capacity: a, now: o, predicted: s } = r, c = [], l = [], u = [], f = /* @__PURE__ */ new Map(), p = /* @__PURE__ */ new Map(), m = e.wanted(), h = /* @__PURE__ */ new Map(), g = new St(), _ = 0, v = 0, y = (e) => {
|
|
1903
1957
|
let t = e.page, r = t.row.count;
|
|
1904
1958
|
c.push(t), l.push(e.visible), u.push(e.near), v += d(r), _ += e.visible;
|
|
1905
1959
|
let i = this.#e.get(t.id), a = i !== void 0, s = e.pixels * e.weight, f = s / Math.max(1, r);
|
|
1906
1960
|
m.length && e.pixels > 0 && h.set(t.id, f);
|
|
1907
1961
|
let p = a && !e.shown && o - (this.#t.get(t.id) ?? -Infinity) <= 1500 ? i : null;
|
|
1908
|
-
(r < s * (a ?
|
|
1962
|
+
(r < s * (a ? _t : 1) || p !== null) && xt(t, n) && g.push({
|
|
1909
1963
|
page: t,
|
|
1910
1964
|
shown: e.shown,
|
|
1911
1965
|
held: p,
|
|
@@ -1965,35 +2019,35 @@ var pt = 1 / .8 ** 2, mt = 1.1, ht = class {
|
|
|
1965
2019
|
};
|
|
1966
2020
|
}
|
|
1967
2021
|
#r(e, t, n) {
|
|
1968
|
-
let r = this.#i(e, t,
|
|
2022
|
+
let r = this.#i(e, t, vt), i = r.shown, { pixels: a, weight: o } = r, s = i;
|
|
1969
2023
|
if (n) {
|
|
1970
|
-
let t = this.#i(e, n,
|
|
2024
|
+
let t = this.#i(e, n, vt);
|
|
1971
2025
|
t.pixels > a && ({pixels: a, weight: o} = t), s ||= t.shown;
|
|
1972
2026
|
}
|
|
1973
2027
|
return {
|
|
1974
2028
|
page: e,
|
|
1975
2029
|
shown: i,
|
|
1976
2030
|
near: s,
|
|
1977
|
-
visible: i ?
|
|
2031
|
+
visible: i ? bt(e, t) : 0,
|
|
1978
2032
|
pixels: a,
|
|
1979
2033
|
weight: o
|
|
1980
2034
|
};
|
|
1981
2035
|
}
|
|
1982
2036
|
#i(e, t, n) {
|
|
1983
2037
|
let { width: r, height: i, tan: a, near: o, far: s } = t;
|
|
1984
|
-
return
|
|
2038
|
+
return dt(e.box, t.view, r, i, a, o, s, n, this.#n, t.origin);
|
|
1985
2039
|
}
|
|
1986
2040
|
};
|
|
1987
|
-
function
|
|
1988
|
-
let { width: n, height: r, tan: i, near: a, far: o, origin: s } = t, c =
|
|
1989
|
-
for (let t = 0; t < 4; t++) c & 1 << t && (l +=
|
|
2041
|
+
function bt(e, t) {
|
|
2042
|
+
let { width: n, height: r, tan: i, near: a, far: o, origin: s } = t, c = pt(e.box, gt(e), t.view, n, r, i, a, o, s), l = 0;
|
|
2043
|
+
for (let t = 0; t < 4; t++) c & 1 << t && (l += ct(e.row, t));
|
|
1990
2044
|
return l;
|
|
1991
2045
|
}
|
|
1992
|
-
function
|
|
2046
|
+
function xt(e, t) {
|
|
1993
2047
|
let { children: n } = e;
|
|
1994
2048
|
return e.g > 0 && t(e.id) && !n.includes(void 0) && n.some((e) => e !== null);
|
|
1995
2049
|
}
|
|
1996
|
-
var
|
|
2050
|
+
var St = class {
|
|
1997
2051
|
#e = [];
|
|
1998
2052
|
get size() {
|
|
1999
2053
|
return this.#e.length;
|
|
@@ -2004,7 +2058,7 @@ var vt = class {
|
|
|
2004
2058
|
let n = t.length - 1;
|
|
2005
2059
|
for (; n > 0;) {
|
|
2006
2060
|
let r = n - 1 >> 1;
|
|
2007
|
-
if (!
|
|
2061
|
+
if (!Ct(e, t[r])) break;
|
|
2008
2062
|
t[n] = t[r], n = r;
|
|
2009
2063
|
}
|
|
2010
2064
|
t[n] = e;
|
|
@@ -2015,7 +2069,7 @@ var vt = class {
|
|
|
2015
2069
|
let t = 0;
|
|
2016
2070
|
for (; 2 * t + 1 < e.length;) {
|
|
2017
2071
|
let r = 2 * t + 1;
|
|
2018
|
-
if (r + 1 < e.length &&
|
|
2072
|
+
if (r + 1 < e.length && Ct(e[r + 1], e[r]) && r++, !Ct(e[r], n)) break;
|
|
2019
2073
|
e[t] = e[r], t = r;
|
|
2020
2074
|
}
|
|
2021
2075
|
e[t] = n;
|
|
@@ -2023,21 +2077,21 @@ var vt = class {
|
|
|
2023
2077
|
return t;
|
|
2024
2078
|
}
|
|
2025
2079
|
};
|
|
2026
|
-
function
|
|
2080
|
+
function Ct(e, t) {
|
|
2027
2081
|
return e.shown === t.shown ? e.ratio > t.ratio : e.shown;
|
|
2028
2082
|
}
|
|
2029
2083
|
//#endregion
|
|
2030
2084
|
//#region src/engine/quality.ts
|
|
2031
|
-
var
|
|
2032
|
-
function
|
|
2033
|
-
return Math.min(n, Math.sqrt(
|
|
2085
|
+
var wt = 5e5, Tt = 2073600, Et = [1, .85], Dt = 30, Ot = 55, kt = 2e3, At = 5e3, jt = 5e5, Mt = .9;
|
|
2086
|
+
function Nt(e, t, n, r) {
|
|
2087
|
+
return Math.min(n, Math.sqrt(Tt / Math.max(1, e * t))) * r;
|
|
2034
2088
|
}
|
|
2035
|
-
function
|
|
2089
|
+
function Pt(e, t) {
|
|
2036
2090
|
if (!e.length) return 0;
|
|
2037
2091
|
let n = [...e].sort((e, t) => e - t);
|
|
2038
2092
|
return n[Math.ceil(n.length * t) - 1];
|
|
2039
2093
|
}
|
|
2040
|
-
var
|
|
2094
|
+
var Ft = class {
|
|
2041
2095
|
#e = 0;
|
|
2042
2096
|
#t;
|
|
2043
2097
|
#n;
|
|
@@ -2050,7 +2104,7 @@ var At = class {
|
|
|
2050
2104
|
this.#n = t, this.#r = Math.max(t, n), this.#t = Math.min(this.#r, Math.max(this.#n, e));
|
|
2051
2105
|
}
|
|
2052
2106
|
get scale() {
|
|
2053
|
-
return
|
|
2107
|
+
return Et[this.#e];
|
|
2054
2108
|
}
|
|
2055
2109
|
get budget() {
|
|
2056
2110
|
return this.#t;
|
|
@@ -2069,19 +2123,19 @@ var At = class {
|
|
|
2069
2123
|
ms: e
|
|
2070
2124
|
}), this.#i = this.#i.filter((n) => t - n.time <= Math.max(1e3, 2 * e)), t - this.#i[0].time < 300) return !1;
|
|
2071
2125
|
let a = this.#i.reduce((e, t) => e + t.ms, 0) / this.#i.length;
|
|
2072
|
-
if (this.#o = a > 1e3 /
|
|
2073
|
-
let e = Math.floor(Math.min(.9, 1e3 /
|
|
2126
|
+
if (this.#o = a > 1e3 / Dt ? this.#o + i : 0, this.#s = a <= 1e3 / Ot ? this.#s + i : 0, this.#o >= kt) {
|
|
2127
|
+
let e = Math.floor(Math.min(.9, 1e3 / Dt / a) * this.#t);
|
|
2074
2128
|
if (this.#t > this.#n) this.#t = Math.max(this.#n, e);
|
|
2075
|
-
else if (this.#e <
|
|
2129
|
+
else if (this.#e < Et.length - 1) this.#e++;
|
|
2076
2130
|
else return !1;
|
|
2077
|
-
} else if (this.#s >=
|
|
2131
|
+
} else if (this.#s >= At) {
|
|
2078
2132
|
if (this.#e > 0) this.#e--;
|
|
2079
|
-
else if (this.#t < this.#r && r >=
|
|
2133
|
+
else if (this.#t < this.#r && r >= Mt * this.#t) this.#t = Math.min(this.#r, this.#t + jt);
|
|
2080
2134
|
else return !1;
|
|
2081
2135
|
} else return !1;
|
|
2082
2136
|
return this.#c(), !0;
|
|
2083
2137
|
}
|
|
2084
|
-
},
|
|
2138
|
+
}, It = class {
|
|
2085
2139
|
#e;
|
|
2086
2140
|
#t = [];
|
|
2087
2141
|
#n = /* @__PURE__ */ new Set();
|
|
@@ -2160,12 +2214,12 @@ var At = class {
|
|
|
2160
2214
|
pages: o
|
|
2161
2215
|
};
|
|
2162
2216
|
}
|
|
2163
|
-
},
|
|
2217
|
+
}, Lt = {
|
|
2164
2218
|
idx: 8,
|
|
2165
2219
|
concurrency: 8,
|
|
2166
2220
|
gap: 65536,
|
|
2167
2221
|
span: 2097152
|
|
2168
|
-
},
|
|
2222
|
+
}, Rt = 1e3, zt = 3e4, Bt = 1e3, Vt = 2e3, Ht = class {
|
|
2169
2223
|
#e;
|
|
2170
2224
|
#t;
|
|
2171
2225
|
#n;
|
|
@@ -2195,8 +2249,8 @@ var At = class {
|
|
|
2195
2249
|
#y = -Infinity;
|
|
2196
2250
|
#b = !1;
|
|
2197
2251
|
#x = !1;
|
|
2198
|
-
constructor(e, t, n, r, i, a =
|
|
2199
|
-
this.#e = e, this.#t = t, this.#n = n, this.#r = r, this.#i = i, this.#a = a, this.#o = new
|
|
2252
|
+
constructor(e, t, n, r, i, a = Lt) {
|
|
2253
|
+
this.#e = e, this.#t = t, this.#n = n, this.#r = r, this.#i = i, this.#a = a, this.#o = new It(a);
|
|
2200
2254
|
}
|
|
2201
2255
|
update(e, t, n) {
|
|
2202
2256
|
if (!this.#x) {
|
|
@@ -2262,7 +2316,7 @@ var At = class {
|
|
|
2262
2316
|
#T = ({ id: e, page: t }) => {
|
|
2263
2317
|
if (this.#x) return;
|
|
2264
2318
|
let n = this.#e.pages.get(e);
|
|
2265
|
-
n && (this.#n.add(e, t, [n.unit.e, n.unit.n], this.protects) ? (this.#g.add(e), this.#m.delete(e) && this.#j(e)) : (this.#m.set(e, this.#u +
|
|
2319
|
+
n && (this.#n.add(e, t, [n.unit.e, n.unit.n], this.protects) ? (this.#g.add(e), this.#m.delete(e) && this.#j(e)) : (this.#m.set(e, this.#u + Bt), this.#A(e, Bt)), this.#r());
|
|
2266
2320
|
};
|
|
2267
2321
|
#E(e) {
|
|
2268
2322
|
this.#x || (this.#f.delete(e), this.#k(e.pack), this.#l = this.#l.filter((e) => this.#N(e.id, e.pack)), this.#o.want(this.#l), this.#o.done(e), this.#w(), this.#r());
|
|
@@ -2276,7 +2330,7 @@ var At = class {
|
|
|
2276
2330
|
this.#b = !0, this.#i();
|
|
2277
2331
|
return;
|
|
2278
2332
|
}
|
|
2279
|
-
let n = this.#p.get(e), r = n ? Math.min(2 * n.delay,
|
|
2333
|
+
let n = this.#p.get(e), r = n ? Math.min(2 * n.delay, zt) : Rt;
|
|
2280
2334
|
this.#p.set(e, {
|
|
2281
2335
|
delay: r,
|
|
2282
2336
|
until: this.#u + r
|
|
@@ -2297,11 +2351,11 @@ var At = class {
|
|
|
2297
2351
|
}
|
|
2298
2352
|
#M() {
|
|
2299
2353
|
let e = this.#u;
|
|
2300
|
-
if (e - this.#y <
|
|
2354
|
+
if (e - this.#y < Vt) return;
|
|
2301
2355
|
this.#y = e;
|
|
2302
2356
|
for (let e of this.#g) this.#n.holds(e) || this.#g.delete(e);
|
|
2303
2357
|
for (let [t, n] of this.#m) n <= e && this.#m.delete(t);
|
|
2304
|
-
for (let [t, n] of this.#_) e - n >=
|
|
2358
|
+
for (let [t, n] of this.#_) e - n >= Vt && this.#_.delete(t);
|
|
2305
2359
|
let { keep: t } = this.#s;
|
|
2306
2360
|
if (this.#e.pages.size <= 2 * (this.#g.size + t.size)) return;
|
|
2307
2361
|
let n = /* @__PURE__ */ new Set([
|
|
@@ -2326,7 +2380,7 @@ var At = class {
|
|
|
2326
2380
|
};
|
|
2327
2381
|
//#endregion
|
|
2328
2382
|
//#region src/engine/stream/remote.ts
|
|
2329
|
-
function
|
|
2383
|
+
function Ut(e, t) {
|
|
2330
2384
|
let n = /* @__PURE__ */ new Map();
|
|
2331
2385
|
return (r) => {
|
|
2332
2386
|
if ("unfetch" in r) return void n.get(r.unfetch)?.abort();
|
|
@@ -2349,29 +2403,29 @@ function Rt(e, t) {
|
|
|
2349
2403
|
}
|
|
2350
2404
|
//#endregion
|
|
2351
2405
|
//#region src/engine/stream/worker.ts?worker&inline
|
|
2352
|
-
var zt = "(function(){var e=class extends Error{name=`Missing`};let t=async(t,n,r)=>{let i=await fetch(t,n?{signal:r,headers:{Range:`bytes=${n[0]}-${n[1]-1}`}}:{signal:r});if(i.status===404)throw new e(`http 404 for ${t}`);if(i.status!==200&&i.status!==206)throw Error(`http ${i.status} for ${t}`);let a=new Uint8Array(await i.arrayBuffer());return n&&i.status===200?a.slice(n[0],n[1]):a},n=.28209479177387814,r=15.625,i=`GMIX`,a={position:0,alpha:6,rotationIndex:7,rotation:8,scale:11,dc:14,label:17},o={origin:0,step:3,scaleMin:6,scaleMax:9,dcMin:12,dcMax:15,shScale:18};async function s(e,t){let n=new ReadableStream({start(t){t.enqueue(e),t.close()}}).pipeThrough(t);return new Uint8Array(await new Response(n).arrayBuffer())}function c(e){return s(e,new DecompressionStream(`deflate-raw`))}function l(e){return s(e,new CompressionStream(`deflate-raw`))}async function u(e,t,n){let r=new DataView(e.buffer,e.byteOffset,e.byteLength);if(e.length<8||String.fromCharCode(...e.subarray(0,4))!==t)throw Error(`not a ${n} file`);let i=r.getUint16(4,!0);if(i!==1)throw Error(`${n} version ${i}; narcissus reads 1`);let a;try{a=await c(e.subarray(8))}catch{throw Error(`${n} body is not a valid deflate stream`)}return new DataView(a.buffer,a.byteOffset,a.byteLength)}function d(e,t){let n=``;for(let r=0;r<8;r++){let i=e.getUint8(t+r);n+=i.toString(16).padStart(2,`0`)}return n}function f(e,t){let n=/* @__PURE__ */ new Float32Array(6);for(let r=0;r<6;r++)n[r]=e.getFloat32(t+20+4*r,!0);return{g:e.getUint8(t),i:e.getUint8(t+1),j:e.getUint8(t+2),count:e.getUint32(t+4,!0),quadrants:[e.getUint32(t+8,!0),e.getUint32(t+12,!0),e.getUint32(t+16,!0)],box:n,offset:e.getUint32(t+44,!0),length:e.getUint32(t+48,!0)}}async function p(e){let t=await u(e,i,`.idx`);if(t.byteLength<40)throw Error(`.idx header is cut off`);let n=t.getUint16(32,!0),r=t.getUint8(34),a=t.getUint16(36,!0),o=40+n*52+r*9+a*11;if(t.byteLength!==o)throw Error(`.idx holds ${t.byteLength} bytes, its counts need ${o}`);let s=d(t,24),c={level:t.getUint8(0),e:t.getInt32(4,!0),n:t.getInt32(8,!0),pack:d(t,12),packSize:t.getUint32(20,!0),col:s===`0000000000000000`?null:s,rows:[],children:[],descendants:[]},l=40;for(let e=0;e<n;e++,l+=52)c.rows.push(f(t,l));for(let e=0;e<r;e++,l+=9)c.children.push({quadrant:t.getUint8(l),idx:d(t,l+1)});for(let e=0;e<a;e++,l+=11)c.descendants.push({depth:t.getUint8(l),column:t.getUint8(l+1),row:t.getUint8(l+2),idx:d(t,l+3)});return c}function m(e,t,n){return`u/${e.level}/${e.e}/${e.n}.${t}.${n}`}let h=/(?:^|\\/)u\\/(\\d+)\\/(-?\\d+)\\/(-?\\d+)\\.([0-9a-f]{16})\\.(?:idx|pack|col)$/;function g(e){let t=h.exec(e);return t?{level:Number(t[1]),e:Number(t[2]),n:Number(t[3]),hash:t[4]}:null}async function _(e){let t=await u(e,`GMCL`,`.col`);if(t.byteLength<60)throw Error(`.col header is cut off`);let n=t.getUint16(0,!0),r=60+12*n*n;if(t.byteLength!==r)throw Error(`.col holds ${t.byteLength} bytes, ${n} nodes need ${r}`);let i=new Float32Array(12*n*n),a=60;for(let e=0;e<12;e++){let r=t.getFloat32(12+4*e,!0)/127;for(let o=0;o<n;o++){let s=0;for(let c=0;c<n;c++,a++)s=s+t.getInt8(a)<<24>>24,i[(e*n+o)*n+c]=s*r}}return{n,pitch:t.getFloat32(4,!0),margin:t.getFloat32(8,!0),values:i}}function v(e,t,n,r){let{n:i,pitch:a,margin:o,values:s}=e,c=i-1,l=Math.min(Math.max((t+o)/a-.5,0),c),u=Math.min(Math.max((n+o)/a-.5,0),c),d=Math.min(Math.floor(l),Math.max(c-1,0)),f=Math.min(Math.floor(u),Math.max(c-1,0)),p=Math.min(d+1,c),m=Math.min(f+1,c),h=l-d,g=u-f,_=(1-h)*(1-g),v=h*(1-g),y=(1-h)*g,b=h*g,x=i*i;for(let e=0,t=0;e<12;e++,t+=x)r[e]=s[t+f*i+d]*_+s[t+f*i+p]*v+s[t+m*i+d]*y+s[t+m*i+p]*b;return r}let y=Float64Array.from({length:256},(e,t)=>(t/255-.5)*Math.SQRT2);function b(e,t,n,r,i){let a=y[t],o=y[n],s=y[r];i[e]=Math.sqrt(Math.max(0,1-a*a-o*o-s*s)),i[e>0?0:1]=a,i[e>1?1:2]=o,i[e>2?2:3]=s}function x(e,t,n,r,i){let a=e[0],o=e[1],s=e[2],c=e[3],l=t*t,u=n*n,d=r*r,f=1-2*(s*s+c*c),p=2*(o*s-a*c),m=2*(o*c+a*s),h=2*(o*s+a*c),g=1-2*(o*o+c*c),_=2*(s*c-a*o),v=2*(o*c-a*s),y=2*(s*c+a*o),b=1-2*(o*o+s*s);i[0]=3*Math.sqrt(f*f*l+p*p*u+m*m*d),i[1]=3*Math.sqrt(h*h*l+g*g*u+_*_*d),i[2]=3*Math.sqrt(v*v*l+y*y*u+b*b*d)}function S(e){if(e.length<128)throw Error(`page payload is shorter than its header`);return new DataView(e.buffer,e.byteOffset,e.byteLength)}function C(e){let t=S(e),n=t.getUint32(0,!0),r=t.getUint16(16,!0),i=128+(17+(r>0?2:0))*n,a=i+r*9;if(e.length!==a)throw Error(`page payload holds ${e.length} bytes, its header needs ${a}`);return{view:t,count:n,k:r,book:i}}function w(e){return[e.getUint32(4,!0),e.getUint32(8,!0),e.getUint32(12,!0)]}function T(e,t){let{view:n,count:r,k:i,book:s}=C(e),c=/* @__PURE__ */ new Float32Array(27);for(let e=0;e<27;e++)c[e]=n.getFloat32(20+4*e,!0);i===0&&c.fill(0,o.shScale);let l=new Uint32Array(r*4),u=new Float32Array(Math.ceil(r/256)*6),d=/* @__PURE__ */ new Float64Array(768);for(let e=0;e<3;e++){let t=c[o.scaleMin+e],n=c[o.scaleMax+e]-t;for(let r=0;r<256;r++)d[e*256+r]=Math.exp(t+r/255*n)}let f=c[o.step],p=c[o.step+1],m=c[o.step+2],h=128+a.position*r,g=128+a.alpha*r,_=128+a.rotationIndex*r,v=128+a.rotation*r,y=128+a.scale*r,S=/* @__PURE__ */ new Float64Array(4),T=/* @__PURE__ */ new Float64Array(3),O=0,k=0,A=0;for(let t=0,n=0;n<r;t++){let i=1/0,a=1/0,o=1/0,s=-1/0,c=-1/0,C=-1/0;for(let t=Math.min(n+256,r);n<t;n++){let t=e[h+n]|e[h+r+n]<<8;O=O+(t>>>1^-(t&1))&65535,t=e[h+2*r+n]|e[h+3*r+n]<<8,k=k+(t>>>1^-(t&1))&65535,t=e[h+4*r+n]|e[h+5*r+n]<<8,A=A+(t>>>1^-(t&1))&65535;let u=e[_+n],w=e[v+n],E=e[v+r+n],D=e[v+2*r+n],j=e[y+n],M=e[y+r+n],N=e[y+2*r+n],P=n*4;l[P]=O|k<<16,l[P+1]=A|e[g+n]<<16|u<<24,l[P+2]=w|E<<8|D<<16|j<<24,l[P+3]=M|N<<8,b(u,w,E,D,S),x(S,d[j],d[256+M],d[512+N],T);let F=O*f,I=k*p,L=A*m;i=Math.min(i,F-T[0]),a=Math.min(a,I-T[1]),o=Math.min(o,L-T[2]),s=Math.max(s,F+T[0]),c=Math.max(c,I+T[1]),C=Math.max(C,L+T[2])}u.set([i,a,o,s,c,C],t*6)}let j=t?D(e,r,i,s,l,c,t):E(e,r,i,s);return{count:r,quadrants:w(n),geometry:l,colour:j,params:c,clusters:u}}function E(e,t,n,r){let i=new Uint32Array(t*3),o=128+a.dc*t,s=128+a.label*t;for(let a=0;a<t;a++){let c=a*3;if(i[c]=e[o+a]|e[o+t+a]<<8|e[o+2*t+a]<<16,n===0)continue;let l=r+(e[s+a]|e[s+t+a]<<8)*9;i[c]|=e[l]<<24,i[c+1]=e[l+1]|e[l+2]<<8|e[l+3]<<16|e[l+4]<<24,i[c+2]=e[l+5]|e[l+6]<<8|e[l+7]<<16|e[l+8]<<24}return i}function D(e,t,r,i,s,c,l){let u=128+a.dc*t,d=128+a.label*t,f=new Int8Array(e.buffer,e.byteOffset+i,r*9),p=new Float32Array(t*3),m=new Float32Array(t*9),h=[1/0,1/0,1/0],g=[-1/0,-1/0,-1/0],_=/* @__PURE__ */ new Float32Array(9),y=/* @__PURE__ */ new Float32Array(12),b=c[o.origin],x=c[o.origin+1],S=c[o.step],C=c[o.step+1],w=/* @__PURE__ */ new Float64Array(768);for(let e=0;e<3;e++){let t=c[o.dcMin+e],n=c[o.dcMax+e]-t;for(let r=0;r<256;r++)w[e*256+r]=t+r/255*n}let T=new Float64Array(Math.max(r,1)*9);for(let e=0;e<r*9;e++)T[e]=f[e]/127*c[o.shScale+e%9];for(let i=0;i<t;i++){let a=s[i*4];v(l,b+(a&65535)*S,x+(a>>>16)*C,y);for(let r=0;r<3;r++){let a=i*3+r;p[a]=w[r*256+e[u+r*t+i]]+y[r]/n,h[r]=Math.min(h[r],p[a]),g[r]=Math.max(g[r],p[a])}let o=r>0?(e[d+i]|e[d+t+i]<<8)*9:0;for(let e=0;e<9;e++){let t=i*9+e;m[t]=T[o+e]+y[3+e],_[e]=Math.max(_[e],Math.abs(m[t]))}}for(let e=0;e<3;e++)c[o.dcMin+e]=t>0?h[e]:0,c[o.dcMax+e]=t>0?g[e]:0;c.set(_,o.shScale);let E=[0,1,2].map(e=>{let t=c[o.dcMax+e]-c[o.dcMin+e];return t>0?255/t:0}),D=Array.from(_,e=>e>0?127/e:0),O=[0,1,2].map(e=>c[o.dcMin+e]),k=new Uint32Array(t*3),A=new Uint8Array(k.buffer);for(let e=0;e<t;e++){let t=e*4*3;for(let n=0;n<3;n++){let r=Math.round((p[e*3+n]-O[n])*E[n]);A[t+n]=Math.min(255,Math.max(0,r))}for(let n=0;n<9;n++){let r=Math.round(m[e*9+n]*D[n]);A[t+3+n]=Math.min(127,Math.max(-127,r))}}return k}let O=(e,t,n)=>Math.min(n,Math.max(t,e));function k(e,t,n){return n>t?O(Math.round((e-t)/(n-t)*255),0,255):0}function A(e,t){return t>0?O(Math.round(e/t*127),-127,127):0}function j(e){return e&=1023,e=(e|e<<16)&50331903,e=(e|e<<8)&50393103,e=(e|e<<4)&51130563,(e|e<<2)&153391689}function M(e,t,n){return j(e>>6)|j(t>>6)<<1|j(n>>6)<<2}function N(e,t){let n=/* @__PURE__ */ new Float32Array(9);for(let r=0;r<t;r++)for(let t=0;t<9;t++)n[t]=Math.max(n[t],Math.abs(e[r*9+t]));return n}function P(e,t,n){let r=new Int8Array(t*9);for(let i=0;i<t;i++)for(let t=0;t<9;t++)r[i*9+t]=A(e[i*9+t],n[t]);let i=e=>r.subarray(e*9,(e+1)*9),a=/* @__PURE__ */ new Map,o=[],s=new Uint16Array(t);for(let e=0;e<t;e++){let t=i(e).join(),n=a.get(t);n===void 0&&(n=o.length,a.set(t,n),o.push(e)),s[e]=n}if(o.length>2048){let e=o.length/256,n=Array.from({length:256},(t,n)=>o[Math.floor(n*e)]);o.splice(0,o.length,...n);for(let e=0;e<t;e++){let t=1/0;for(let n=0;n<256;n++){let i=0;for(let t=0;t<9;t++)i+=(r[e*9+t]-r[o[n]*9+t])**2;i<t&&(t=i,s[e]=n)}}}let c=new Int8Array(o.length*9);return o.forEach((e,t)=>c.set(i(e),t*9)),{book:c,labels:s}}function F(e,t){let{count:n,position:i,rotation:o,scale:s,alpha:c,dc:l,sh:u}=e,d=[1/0,1/0,1/0],f=[-1/0,-1/0,-1/0],p=[...d],m=[...f],h=[...d],g=[...f];for(let e=0;e<n;e++)for(let t=0;t<3;t++)d[t]=Math.min(d[t],i[e*3+t]),f[t]=Math.max(f[t],i[e*3+t]),p[t]=Math.min(p[t],s[e*3+t]),m[t]=Math.max(m[t],s[e*3+t]),h[t]=Math.min(h[t],l[e*3+t]),g[t]=Math.max(g[t],l[e*3+t]);let _=5e-4*2**t.g,v=Float32Array.from(d),y=Float32Array.from(d,(e,t)=>Math.max(_,(f[t]-e)/65535)),b=new Uint16Array(n*3);for(let e=0;e<n;e++)for(let t=0;t<3;t++){let n=(i[e*3+t]-v[t])/y[t];b[e*3+t]=O(Math.round(n),0,65535)}let S=r*2**t.g,C=(t.i+.5)*S,w=(t.j+.5)*S,T=new Uint8Array(n),E=new Float64Array(n);for(let e=0;e<n;e++){let t=+(i[e*3]>=C),n=+(i[e*3+1]>=w);T[e]=t+2*n,E[e]=T[e]*2**30+M(b[e*3],b[e*3+1],b[e*3+2])}let D=Uint32Array.from({length:n},(e,t)=>t).sort((e,t)=>E[e]-E[t]),A=[0,0,0];for(let e=1;e<4;e++)A[e-1]=T.filter(t=>t<e).length;let j=u?N(u,n):/* @__PURE__ */ new Float32Array(9),{book:F,labels:I}=u?P(u,n,j):{book:null,labels:null},L=F?F.length/9:0,R=17+(L>0?2:0),z=new Uint8Array(128+R*n+L*9),B=new DataView(z.buffer);B.setUint32(0,n,!0),A.forEach((e,t)=>B.setUint32(4+4*t,e,!0)),B.setUint16(16,L,!0),[...v,...y,...p,...m,...h,...g,...j].forEach((e,t)=>B.setFloat32(20+4*t,e,!0));let V=e=>128+e*n,H=new Float32Array([...d,...f]),U=/* @__PURE__ */ new Float64Array(4),W=/* @__PURE__ */ new Float64Array(3),G=[0,0,0];for(let e=0;e<n;e++){let t=D[e];for(let n=0;n<3;n++){let r=b[t*3+n]-G[n]<<16>>16,i=r<0?-2*r-1:2*r;G[n]=b[t*3+n],z[V(a.position+2*n)+e]=i&255,z[V(a.position+2*n+1)+e]=i>>8}z[V(a.alpha)+e]=O(Math.round(c[t]*255),0,255);let n=Math.hypot(...o.subarray(t*4,t*4+4));for(let e=0;e<4;e++)U[e]=o[t*4+e]/n;let r=0;for(let e=1;e<4;e++)Math.abs(U[e])>Math.abs(U[r])&&(r=e);let u=U[r]<0?-1:1;z[V(a.rotationIndex)+e]=r;for(let t=0,n=0;t<4;t++){if(t===r)continue;let i=Math.round((u*U[t]/Math.SQRT2+.5)*255);z[V(a.rotation+n++)+e]=O(i,0,255)}for(let n=0;n<3;n++)z[V(a.scale+n)+e]=k(s[t*3+n],p[n],m[n]),z[V(a.dc+n)+e]=k(l[t*3+n],h[n],g[n]);I&&(z[V(a.label)+e]=I[t]&255,z[V(a.label+1)+e]=I[t]>>8);let[d,f,_]=[0,1,2].map(e=>Math.exp(s[t*3+e]));x(U,d,f,_,W);for(let e=0;e<3;e++)H[e]=Math.min(H[e],i[t*3+e]-W[e]),H[3+e]=Math.max(H[3+e],i[t*3+e]+W[e])}return F&&z.set(new Uint8Array(F.buffer),V(R)),{payload:z,row:{g:t.g,i:t.i,j:t.j,count:n,quadrants:A,box:H,offset:0,length:0}}}function I(e,t,n){e.setUint8(t,n.g),e.setUint8(t+1,n.i),e.setUint8(t+2,n.j),e.setUint32(t+4,n.count,!0),n.quadrants.forEach((n,r)=>e.setUint32(t+8+4*r,n,!0)),n.box.forEach((n,r)=>e.setFloat32(t+20+4*r,n,!0)),e.setUint32(t+44,n.offset,!0),e.setUint32(t+48,n.length,!0)}function L(e,t,n){for(let r=0;r<4;r++)e[t+r]=n.charCodeAt(r)}function R(e){return Uint8Array.from({length:8},(t,n)=>parseInt(e.slice(2*n,2*n+2),16))}async function z(e,t){let n=await l(e),r=new Uint8Array(8+n.length);return L(r,0,t),new DataView(r.buffer).setUint16(4,1,!0),r.set(n,8),r}async function B(e){let{rows:t,children:n,descendants:r}=e,a=new Uint8Array(40+t.length*52+n.length*9+r.length*11),o=new DataView(a.buffer);o.setUint8(0,e.level),o.setInt32(4,e.e,!0),o.setInt32(8,e.n,!0),a.set(R(e.pack),12),o.setUint32(20,e.packSize,!0),e.col&&a.set(R(e.col),24),o.setUint16(32,t.length,!0),o.setUint8(34,n.length),o.setUint16(36,r.length,!0);let s=40;for(let e of t)I(o,s,e),s+=52;for(let e of n)o.setUint8(s,e.quadrant),a.set(R(e.idx),s+1),s+=9;for(let e of r)o.setUint8(s,e.depth),o.setUint8(s+1,e.column),o.setUint8(s+2,e.row),a.set(R(e.idx),s+3),s+=11;return z(a,i)}function V(e){let t=3421674724,n=2216829733;for(let r=0;r<e.length;r++){n=(n^e[r])>>>0;let i=n*435;t=t*435+(n<<8>>>0)+Math.floor(i/4294967296)>>>0,n=i>>>0}return t.toString(16).padStart(8,`0`)+n.toString(16).padStart(8,`0`)}function H(e){return()=>{e=e+1831565813|0;let t=Math.imul(e^e>>>15,1|e);return t=t+Math.imul(t^t>>>7,61|t)^t,((t^t>>>14)>>>0)/2**32}}async function U(e,t){return p(await G(e,t))}async function*W(e,t,n,r){let i=t.col===null?null:te(e,t.col,n),a=await ee(e,t,r),o=await i;for(let[e,n]of t.pages.entries()){let t=await c(a[e]);r?.throwIfAborted(),yield{id:n.id,page:T(t,o)}}}async function G(e,t){let n=await e.cache.get(t);if(n)return n;let r=await e.fetch(e.base+t,null);return e.cache.put(t,r),r}async function ee(e,t,n){let r=t.pages.map(e=>`${t.pack}#${e.offset}+${e.length}`),i=await Promise.all(r.map(t=>e.cache.get(t)));if(n?.throwIfAborted(),i.every(e=>e!==void 0))return i;let a=await e.fetch(e.base+t.pack,[t.start,t.end],n);if(a.length!==t.end-t.start)throw Error(`${t.pack}: ${a.length} bytes for ${t.start}-${t.end}`);return t.pages.map((n,o)=>{let s=a.slice(n.offset-t.start,n.offset-t.start+n.length);return i[o]||e.cache.put(r[o],s),s})}function te(e,t,n){let r=n.get(t);if(r)n.delete(t);else{let i=G(e,t).then(_);i.catch(()=>{n.get(t)===i&&n.delete(t)}),r=i}if(n.set(t,r),n.size>64){let[e]=n.keys();n.delete(e)}return r}function ne(e){let t=/* @__PURE__ */ new Map,n=0;return{async get(e){let n=t.get(e);return n&&(t.delete(e),t.set(e,n)),n},async put(r,i){let a=t.get(r);if(a&&(t.delete(r),n-=a.length),!(i.length>e)){t.set(r,i),n+=i.length;for(let[r,i]of t){if(n<=e)break;t.delete(r),n-=i.length}}}}}async function re(e,t){let n;try{n=await(await ae()).getDirectoryHandle(String(t),{create:!0})}catch{return null}let r=/* @__PURE__ */ new Map,i=0,a=!1,o=(e,t)=>{i+=t-(r.get(e)??0),r.delete(e),r.set(e,t)},s=e=>{i-=r.get(e)??0,r.delete(e)},c=()=>{if(a)for(let[t,a]of r){if(i<=e)break;r.delete(t),i-=a,n.removeEntry(t).catch(()=>void 0)}};return ce(n).then(e=>{let t=[...r];r.clear(),i=0;for(let{name:t,size:n}of e.sort((e,t)=>e.time-t.time))o(t,n);for(let[e,n]of t)o(e,n);a=!0,c()}),{async get(e){let t=encodeURIComponent(e);if(a&&!r.has(t))return;let i=await oe(n,t);return i?o(t,i.length):s(t),i},async put(t,r){if(r.length===0||r.length>e)return;let i=encodeURIComponent(t);await se(n,i,r)&&(o(i,r.length),c())}}}async function ie(e){let t=new Set(Array.from({length:e},(e,t)=>String(t)));try{let e=await ae(),n=[];for await(let[r,i]of e.entries())(i.kind!==`directory`||!t.has(r))&&n.push(r);let r={recursive:!0};for(let t of n)await e.removeEntry(t,r).catch(()=>void 0)}catch{}}async function ae(){return(await navigator.storage.getDirectory()).getDirectoryHandle(`cache`,{create:!0})}async function oe(e,t){try{let n=await(await e.getFileHandle(t)).getFile();return n.size>0?new Uint8Array(await n.arrayBuffer()):void 0}catch{return}}async function se(e,t,n){let r;try{return r=await(await e.getFileHandle(t,{create:!0})).createWritable(),await r.write(n),await r.close(),!0}catch{return r?.abort().catch(()=>void 0),!1}}async function ce(e){let t=[];try{for await(let[n,r]of e.entries()){if(r.kind!==`file`)continue;let e=await r.getFile().catch(()=>null);e&&t.push({name:n,size:e.size,time:e.lastModified})}}catch{}return t}function le(t){let n=/* @__PURE__ */ new Map,r=0;return{fetch:(i,a,o)=>new Promise((s,c)=>{if(o?.aborted)return c(o.reason);let l=++r,u=()=>{n.delete(l),t({unfetch:l}),c(o.reason)};n.set(l,t=>{o?.removeEventListener(`abort`,u),`bytes`in t?s(t.bytes):c(t.missing?new e(t.error):Error(t.error))}),o?.addEventListener(`abort`,u,{once:!0}),t({fetch:l,url:i,range:a})}),take(e){let t=n.get(e.fetched);n.delete(e.fetched),t?.(e)}}}let K=16384,ue=1408,de=65535,q=324121,fe=.4,pe=[[12,1/7e3,0,1/9e3,.7],[9,1/2300,1.1,1/3100,.4],[6,1/800,.3,1/1100,2],[3,1/150,.9,1/210,1.7]],me=pe.reduce((e,[t,n,,r])=>e+t*(n+r),0),he=Float32Array.from({length:ue*9},(e,t)=>{let n=Math.floor(t/9),r=t%9,i=(n*(37+2*r)+11*r)%255-127;return r===0&&(i=n%255-127),r===1&&(i=20*Math.floor(n/255)-50),i/127*.04}),J=new TextEncoder,ge={version:1,crs:`synthetic`,height:`synthetic`,leaf:250,roots:[512e4,6144e3].map(e=>({level:12,e:0,n:e})).map(e=>({...e,idx:m(e,Y(e,`idx`),`idx`)})),extent:{e:[44e4,9e5],n:[605e4,641e4],h:[0,80]}},_e=J.encode(JSON.stringify(ge));function ve(){return async(t,n)=>{if(t.endsWith(`world.json`))return be(_e,n);let r=g(t),i=t.slice(t.lastIndexOf(`.`)+1);if(!r||i!==`idx`&&i!==`pack`||!xe(r)||r.hash!==Y(r,i))throw new e(`no file ${t}`);return i===`idx`?be(await De(r),n):Oe(r,n,t)}}function ye(e,t){let n=30;for(let[r,i,a,o,s]of pe)n+=r*Math.sin(i*e+a)*Math.sin(o*t+s);return n}function be(e,t){return t?e.slice(t[0],t[1]):e.slice()}function Y(e,t){return V(J.encode(`${e.level}/${e.e}/${e.n}.${t}`))}function X(e,t,n){let{e:r,n:i}=ge.extent;return e<r[1]&&e+n>r[0]&&t<i[1]&&t+n>i[0]}function xe({level:e,e:t,n}){let r=250*2**e;return e<=12&&t%r===0&&n%r===0&&X(t,n,r)}function Se(e){return e===0?[1,0]:e===12?[16,15,14,13]:[e+1]}function Ce(e){let t=0;for(let n=0;n<8;n++)t|=(e>>2*n&1)<<n;return t}function we(e){let t=[];for(let n of Se(e.level)){let i=r*2**n,a=250*2**e.level/i;for(let r=0;r<a*a;r++){let a=Ce(r),o=Ce(r>>1);X(e.e+a*i,e.n+o*i,i)&&t.push({g:n,i:a,j:o})}}return t}function Te(e,t){let n=e.level-t,r=250*2**n,i=[];for(let a=0;n>=0&&a<2**t;a++)for(let o=0;o<2**t;o++){let t={level:n,e:e.e+o*r,n:e.n+a*r};X(t.e,t.n,r)&&i.push({column:o,row:a,unit:t})}return i}function Ee(e,{g:t,i:n,j:i},a){let o=r*2**t,s=o/128,c=3*1.2*s,l=1.17*s,u=ye(e.e+(n+.5)*o,e.n+(i+.5)*o),d=me*o/2,f=Float32Array.of(n*o-c,i*o-c,Math.max(0,u-d)-l,(n+1)*o+c,(i+1)*o+c,Math.min(60,u+d)+l),p=K/4;return{g:t,i:n,j:i,count:K,quadrants:[p,2*p,3*p],box:f,offset:a,length:q}}function De(e){let t=we(e),n=[];for(let{column:t,row:r,unit:i}of Te(e,1))n.push({quadrant:t+2*r,idx:Y(i,`idx`)});let r=[];for(let t of[2,3])for(let{column:n,row:i,unit:a}of Te(e,t))r.push({depth:t,column:n,row:i,idx:Y(a,`idx`)});return B({level:e.level,e:e.e,n:e.n,pack:Y(e,`pack`),packSize:t.length*324173+16,col:null,rows:t.map((t,n)=>Ee(e,t,n*q)),children:n,descendants:r})}function Oe(e,t,n){let r=we(e);if(!t||t[0]%q!=0||t[1]%q!=0||t[0]>=t[1]||t[1]>r.length*q)throw Error(`${n}: the synthetic world serves whole pages only`);let i=new Uint8Array(t[1]-t[0]);for(let n=0;n<i.length;n+=q)ke(je(e,r[(t[0]+n)/q]),i,n);return i}function ke(e,t,n){let r=n;for(let n=0;n<e.length;n+=de){let i=Math.min(de,e.length-n);t[r]=+(n+i===e.length),t[r+1]=i&255,t[r+2]=i>>8,t[r+3]=~i&255,t[r+4]=~i>>8&255,t.set(e.subarray(n,n+i),r+5),r+=5+i}}let Ae=e=>H(parseInt(V(J.encode(e)).slice(8),16));function je(e,{g:t,i,j:a}){let o=K,s=r*2**t/128,c=Ae(`${e.level}/${e.e}/${e.n}/${t}/${i}/${a}`),l=new Float64Array(3*o),u=new Float32Array(4*o),d=new Float32Array(3*o),f=new Float32Array(o),p=new Float32Array(3*o),m=new Float32Array(9*o);for(let t=0;t<o;t++){let r=(i*128+t%128+.5+fe*(2*c()-1))*s,o=(a*128+Math.floor(t/128)+.5+fe*(2*c()-1))*s,h=ye(e.e+r,e.n+o);l[3*t]=r,l[3*t+1]=o,l[3*t+2]=h;let g=Math.PI*c(),_=.1/2*(2*c()-1);u[4*t]=Math.cos(g)*Math.cos(_),u[4*t+1]=Math.cos(g)*Math.sin(_),u[4*t+2]=Math.sin(g)*Math.sin(_),u[4*t+3]=Math.sin(g)*Math.cos(_);for(let e=0;e<2;e++)d[3*t+e]=Math.log(s*(.6+.6*c()));d[3*t+2]=Math.log(s*.15*(.5+.5*c())),f[t]=.35+.65*c();let v=h/60,y=.5+.5*Math.sin((e.e+r)/410)*Math.sin((e.n+o)/330);p[3*t]=(.32+.2*v+.1*y-.5)/n,p[3*t+1]=(.42+.15*y-.1*v-.5)/n,p[3*t+2]=(.25+.1*v+.04*c()-.5)/n;let b=t%ue;m.set(he.subarray(9*b,9*(b+1)),9*t)}return F({count:o,position:l,rotation:u,scale:d,alpha:f,dc:p,sh:m},{g:t,i,j:a}).payload}let Z=2**20,Q=self,$,Me=/* @__PURE__ */ new Map,Ne=/* @__PURE__ */ new Map,Pe=le(e=>Q.postMessage(e,[]));Q.onmessage=({data:e})=>{`fetched`in e?Pe.take(e):e.type===`init`?($=Fe(e),$.catch(()=>void 0)):e.type===`abort`?Ne.get(e.id)?.abort():Re(e)};async function Fe(e){return e.source===`synthetic`?{fetch:ve(),cache:await Ie({...e,cache:`none`}),base:e.base}:{fetch:e.source===`page`?Pe.fetch:t,cache:await Ie(e),base:e.base}}async function Ie({cache:e,shard:t,shards:n}){return e===`memory`?ne(256*Z):e===`none`?{get:async()=>void 0,put:async()=>void 0}:(t===0&&ie(n),await re(await Le()/n,t)??ne(256*Z))}async function Le(){try{let{quota:e}=await navigator.storage.estimate();return Math.min(4096*Z,e===void 0?1/0:e/2)}catch{return 4096*Z}}async function Re(t){let{id:n}=t,r=new AbortController;Ne.set(n,r);try{if(!$)throw Error(`stream worker used before init`);let e=await $;if(t.type===`idx`)Q.postMessage({id:n,value:await U(e,t.path)},[]);else{for await(let i of W(e,t.batch,Me,r.signal))Q.postMessage({id:n,page:i},ze(i));Q.postMessage({id:n,done:!0},[])}}catch(t){let r=t instanceof Error?t.message:String(t);Q.postMessage({id:n,error:r,missing:t instanceof e},[])}finally{Ne.delete(n)}}function ze({page:e}){let t=/* @__PURE__ */ new Set;for(let n of[e.geometry,e.colour,e.params,e.clusters])t.add(n.buffer);return[...t]}})();", Bt = typeof self < "u" && self.Blob && new Blob(["(self.URL || self.webkitURL).revokeObjectURL(self.location.href);", zt], { type: "text/javascript;charset=utf-8" });
|
|
2353
|
-
function
|
|
2406
|
+
var Wt = "(function(){var e=class extends Error{name=`Missing`};let t=async(t,n,r)=>{let i=await fetch(t,n?{signal:r,headers:{Range:`bytes=${n[0]}-${n[1]-1}`}}:{signal:r});if(i.status===404)throw new e(`http 404 for ${t}`);if(i.status!==200&&i.status!==206)throw Error(`http ${i.status} for ${t}`);let a=new Uint8Array(await i.arrayBuffer());return n&&i.status===200?a.slice(n[0],n[1]):a},n=.28209479177387814,r=15.625,i=`GMIX`,a={position:0,alpha:6,rotationIndex:7,rotation:8,scale:11,dc:14,label:17},o={origin:0,step:3,scaleMin:6,scaleMax:9,dcMin:12,dcMax:15,shScale:18};async function s(e,t){let n=new ReadableStream({start(t){t.enqueue(e),t.close()}}).pipeThrough(t);return new Uint8Array(await new Response(n).arrayBuffer())}function c(e){return s(e,new DecompressionStream(`deflate-raw`))}function l(e){return s(e,new CompressionStream(`deflate-raw`))}async function u(e,t,n){let r=new DataView(e.buffer,e.byteOffset,e.byteLength);if(e.length<8||String.fromCharCode(...e.subarray(0,4))!==t)throw Error(`not a ${n} file`);let i=r.getUint16(4,!0);if(i!==1)throw Error(`${n} version ${i}; narcissus reads 1`);let a;try{a=await c(e.subarray(8))}catch{throw Error(`${n} body is not a valid deflate stream`)}return new DataView(a.buffer,a.byteOffset,a.byteLength)}function d(e,t){let n=``;for(let r=0;r<8;r++){let i=e.getUint8(t+r);n+=i.toString(16).padStart(2,`0`)}return n}function f(e,t){let n=/* @__PURE__ */ new Float32Array(6);for(let r=0;r<6;r++)n[r]=e.getFloat32(t+20+4*r,!0);return{g:e.getUint8(t),i:e.getUint8(t+1),j:e.getUint8(t+2),count:e.getUint32(t+4,!0),quadrants:[e.getUint32(t+8,!0),e.getUint32(t+12,!0),e.getUint32(t+16,!0)],box:n,offset:e.getUint32(t+44,!0),length:e.getUint32(t+48,!0)}}async function p(e){let t=await u(e,i,`.idx`);if(t.byteLength<40)throw Error(`.idx header is cut off`);let n=t.getUint16(32,!0),r=t.getUint8(34),a=t.getUint16(36,!0),o=40+n*52+r*9+a*11;if(t.byteLength!==o)throw Error(`.idx holds ${t.byteLength} bytes, its counts need ${o}`);let s=d(t,24),c={level:t.getUint8(0),e:t.getInt32(4,!0),n:t.getInt32(8,!0),pack:d(t,12),packSize:t.getUint32(20,!0),col:s===`0000000000000000`?null:s,rows:[],children:[],descendants:[]},l=40;for(let e=0;e<n;e++,l+=52)c.rows.push(f(t,l));for(let e=0;e<r;e++,l+=9)c.children.push({quadrant:t.getUint8(l),idx:d(t,l+1)});for(let e=0;e<a;e++,l+=11)c.descendants.push({depth:t.getUint8(l),column:t.getUint8(l+1),row:t.getUint8(l+2),idx:d(t,l+3)});return c}function m(e,t,n){return`u/${e.level}/${e.e}/${e.n}.${t}.${n}`}let h=/(?:^|\\/)u\\/(\\d+)\\/(-?\\d+)\\/(-?\\d+)\\.([0-9a-f]{16})\\.(?:idx|pack|col)$/;function g(e){let t=h.exec(e);return t?{level:Number(t[1]),e:Number(t[2]),n:Number(t[3]),hash:t[4]}:null}async function _(e){let t=await u(e,`GMCL`,`.col`);if(t.byteLength<60)throw Error(`.col header is cut off`);let n=t.getUint16(0,!0),r=60+12*n*n;if(t.byteLength!==r)throw Error(`.col holds ${t.byteLength} bytes, ${n} nodes need ${r}`);let i=new Float32Array(12*n*n),a=60;for(let e=0;e<12;e++){let r=t.getFloat32(12+4*e,!0)/127;for(let o=0;o<n;o++){let s=0;for(let c=0;c<n;c++,a++)s=s+t.getInt8(a)<<24>>24,i[(e*n+o)*n+c]=s*r}}return{n,pitch:t.getFloat32(4,!0),margin:t.getFloat32(8,!0),values:i}}function v(e,t,n,r){let{n:i,pitch:a,margin:o,values:s}=e,c=i-1,l=Math.min(Math.max((t+o)/a-.5,0),c),u=Math.min(Math.max((n+o)/a-.5,0),c),d=Math.min(Math.floor(l),Math.max(c-1,0)),f=Math.min(Math.floor(u),Math.max(c-1,0)),p=Math.min(d+1,c),m=Math.min(f+1,c),h=l-d,g=u-f,_=(1-h)*(1-g),v=h*(1-g),y=(1-h)*g,b=h*g,x=i*i;for(let e=0,t=0;e<12;e++,t+=x)r[e]=s[t+f*i+d]*_+s[t+f*i+p]*v+s[t+m*i+d]*y+s[t+m*i+p]*b;return r}let y=Float64Array.from({length:256},(e,t)=>(t/255-.5)*Math.SQRT2);function b(e,t,n,r,i){let a=y[t],o=y[n],s=y[r];i[e]=Math.sqrt(Math.max(0,1-a*a-o*o-s*s)),i[e>0?0:1]=a,i[e>1?1:2]=o,i[e>2?2:3]=s}function x(e,t,n,r,i){let a=e[0],o=e[1],s=e[2],c=e[3],l=t*t,u=n*n,d=r*r,f=1-2*(s*s+c*c),p=2*(o*s-a*c),m=2*(o*c+a*s),h=2*(o*s+a*c),g=1-2*(o*o+c*c),_=2*(s*c-a*o),v=2*(o*c-a*s),y=2*(s*c+a*o),b=1-2*(o*o+s*s);i[0]=3*Math.sqrt(f*f*l+p*p*u+m*m*d),i[1]=3*Math.sqrt(h*h*l+g*g*u+_*_*d),i[2]=3*Math.sqrt(v*v*l+y*y*u+b*b*d)}function S(e){if(e.length<128)throw Error(`page payload is shorter than its header`);return new DataView(e.buffer,e.byteOffset,e.byteLength)}function C(e){let t=S(e),n=t.getUint32(0,!0),r=t.getUint16(16,!0),i=128+(17+(r>0?2:0))*n,a=i+r*9;if(e.length!==a)throw Error(`page payload holds ${e.length} bytes, its header needs ${a}`);return{view:t,count:n,k:r,book:i}}function w(e){return[e.getUint32(4,!0),e.getUint32(8,!0),e.getUint32(12,!0)]}function T(e,t){let{view:n,count:r,k:i,book:s}=C(e),c=/* @__PURE__ */ new Float32Array(27);for(let e=0;e<27;e++)c[e]=n.getFloat32(20+4*e,!0);i===0&&c.fill(0,o.shScale);let l=new Uint32Array(r*4),u=new Float32Array(Math.ceil(r/256)*6),d=/* @__PURE__ */ new Float64Array(768);for(let e=0;e<3;e++){let t=c[o.scaleMin+e],n=c[o.scaleMax+e]-t;for(let r=0;r<256;r++)d[e*256+r]=Math.exp(t+r/255*n)}let f=c[o.step],p=c[o.step+1],m=c[o.step+2],h=128+a.position*r,g=128+a.alpha*r,_=128+a.rotationIndex*r,v=128+a.rotation*r,y=128+a.scale*r,S=/* @__PURE__ */ new Float64Array(4),T=/* @__PURE__ */ new Float64Array(3),O=0,k=0,A=0;for(let t=0,n=0;n<r;t++){let i=1/0,a=1/0,o=1/0,s=-1/0,c=-1/0,C=-1/0;for(let t=Math.min(n+256,r);n<t;n++){let t=e[h+n]|e[h+r+n]<<8;O=O+(t>>>1^-(t&1))&65535,t=e[h+2*r+n]|e[h+3*r+n]<<8,k=k+(t>>>1^-(t&1))&65535,t=e[h+4*r+n]|e[h+5*r+n]<<8,A=A+(t>>>1^-(t&1))&65535;let u=e[_+n],w=e[v+n],E=e[v+r+n],D=e[v+2*r+n],j=e[y+n],M=e[y+r+n],N=e[y+2*r+n],P=n*4;l[P]=O|k<<16,l[P+1]=A|e[g+n]<<16|u<<24,l[P+2]=w|E<<8|D<<16|j<<24,l[P+3]=M|N<<8,b(u,w,E,D,S),x(S,d[j],d[256+M],d[512+N],T);let F=O*f,I=k*p,L=A*m;i=Math.min(i,F-T[0]),a=Math.min(a,I-T[1]),o=Math.min(o,L-T[2]),s=Math.max(s,F+T[0]),c=Math.max(c,I+T[1]),C=Math.max(C,L+T[2])}u.set([i,a,o,s,c,C],t*6)}let j=t?D(e,r,i,s,l,c,t):E(e,r,i,s);return{count:r,quadrants:w(n),geometry:l,colour:j,params:c,clusters:u}}function E(e,t,n,r){let i=new Uint32Array(t*3),o=128+a.dc*t,s=128+a.label*t;for(let a=0;a<t;a++){let c=a*3;if(i[c]=e[o+a]|e[o+t+a]<<8|e[o+2*t+a]<<16,n===0)continue;let l=r+(e[s+a]|e[s+t+a]<<8)*9;i[c]|=e[l]<<24,i[c+1]=e[l+1]|e[l+2]<<8|e[l+3]<<16|e[l+4]<<24,i[c+2]=e[l+5]|e[l+6]<<8|e[l+7]<<16|e[l+8]<<24}return i}function D(e,t,r,i,s,c,l){let u=128+a.dc*t,d=128+a.label*t,f=new Int8Array(e.buffer,e.byteOffset+i,r*9),p=new Float32Array(t*3),m=new Float32Array(t*9),h=[1/0,1/0,1/0],g=[-1/0,-1/0,-1/0],_=/* @__PURE__ */ new Float32Array(9),y=/* @__PURE__ */ new Float32Array(12),b=c[o.origin],x=c[o.origin+1],S=c[o.step],C=c[o.step+1],w=/* @__PURE__ */ new Float64Array(768);for(let e=0;e<3;e++){let t=c[o.dcMin+e],n=c[o.dcMax+e]-t;for(let r=0;r<256;r++)w[e*256+r]=t+r/255*n}let T=new Float64Array(Math.max(r,1)*9);for(let e=0;e<r*9;e++)T[e]=f[e]/127*c[o.shScale+e%9];for(let i=0;i<t;i++){let a=s[i*4];v(l,b+(a&65535)*S,x+(a>>>16)*C,y);for(let r=0;r<3;r++){let a=i*3+r;p[a]=w[r*256+e[u+r*t+i]]+y[r]/n,h[r]=Math.min(h[r],p[a]),g[r]=Math.max(g[r],p[a])}let o=r>0?(e[d+i]|e[d+t+i]<<8)*9:0;for(let e=0;e<9;e++){let t=i*9+e;m[t]=T[o+e]+y[3+e],_[e]=Math.max(_[e],Math.abs(m[t]))}}for(let e=0;e<3;e++)c[o.dcMin+e]=t>0?h[e]:0,c[o.dcMax+e]=t>0?g[e]:0;c.set(_,o.shScale);let E=[0,1,2].map(e=>{let t=c[o.dcMax+e]-c[o.dcMin+e];return t>0?255/t:0}),D=Array.from(_,e=>e>0?127/e:0),O=[0,1,2].map(e=>c[o.dcMin+e]),k=new Uint32Array(t*3),A=new Uint8Array(k.buffer);for(let e=0;e<t;e++){let t=e*4*3;for(let n=0;n<3;n++){let r=Math.round((p[e*3+n]-O[n])*E[n]);A[t+n]=Math.min(255,Math.max(0,r))}for(let n=0;n<9;n++){let r=Math.round(m[e*9+n]*D[n]);A[t+3+n]=Math.min(127,Math.max(-127,r))}}return k}let O=(e,t,n)=>Math.min(n,Math.max(t,e));function k(e,t,n){return n>t?O(Math.round((e-t)/(n-t)*255),0,255):0}function A(e,t){return t>0?O(Math.round(e/t*127),-127,127):0}function j(e){return e&=1023,e=(e|e<<16)&50331903,e=(e|e<<8)&50393103,e=(e|e<<4)&51130563,(e|e<<2)&153391689}function M(e,t,n){return j(e>>6)|j(t>>6)<<1|j(n>>6)<<2}function N(e,t){let n=/* @__PURE__ */ new Float32Array(9);for(let r=0;r<t;r++)for(let t=0;t<9;t++)n[t]=Math.max(n[t],Math.abs(e[r*9+t]));return n}function P(e,t,n){let r=new Int8Array(t*9);for(let i=0;i<t;i++)for(let t=0;t<9;t++)r[i*9+t]=A(e[i*9+t],n[t]);let i=e=>r.subarray(e*9,(e+1)*9),a=/* @__PURE__ */ new Map,o=[],s=new Uint16Array(t);for(let e=0;e<t;e++){let t=i(e).join(),n=a.get(t);n===void 0&&(n=o.length,a.set(t,n),o.push(e)),s[e]=n}if(o.length>2048){let e=o.length/256,n=Array.from({length:256},(t,n)=>o[Math.floor(n*e)]);o.splice(0,o.length,...n);for(let e=0;e<t;e++){let t=1/0;for(let n=0;n<256;n++){let i=0;for(let t=0;t<9;t++)i+=(r[e*9+t]-r[o[n]*9+t])**2;i<t&&(t=i,s[e]=n)}}}let c=new Int8Array(o.length*9);return o.forEach((e,t)=>c.set(i(e),t*9)),{book:c,labels:s}}function F(e,t){let{count:n,position:i,rotation:o,scale:s,alpha:c,dc:l,sh:u}=e,d=[1/0,1/0,1/0],f=[-1/0,-1/0,-1/0],p=[...d],m=[...f],h=[...d],g=[...f];for(let e=0;e<n;e++)for(let t=0;t<3;t++)d[t]=Math.min(d[t],i[e*3+t]),f[t]=Math.max(f[t],i[e*3+t]),p[t]=Math.min(p[t],s[e*3+t]),m[t]=Math.max(m[t],s[e*3+t]),h[t]=Math.min(h[t],l[e*3+t]),g[t]=Math.max(g[t],l[e*3+t]);let _=5e-4*2**t.g,v=Float32Array.from(d),y=Float32Array.from(d,(e,t)=>Math.max(_,(f[t]-e)/65535)),b=new Uint16Array(n*3);for(let e=0;e<n;e++)for(let t=0;t<3;t++){let n=(i[e*3+t]-v[t])/y[t];b[e*3+t]=O(Math.round(n),0,65535)}let S=r*2**t.g,C=(t.i+.5)*S,w=(t.j+.5)*S,T=new Uint8Array(n),E=new Float64Array(n);for(let e=0;e<n;e++){let t=+(i[e*3]>=C),n=+(i[e*3+1]>=w);T[e]=t+2*n,E[e]=T[e]*2**30+M(b[e*3],b[e*3+1],b[e*3+2])}let D=Uint32Array.from({length:n},(e,t)=>t).sort((e,t)=>E[e]-E[t]),A=[0,0,0];for(let e=1;e<4;e++)A[e-1]=T.filter(t=>t<e).length;let j=u?N(u,n):/* @__PURE__ */ new Float32Array(9),{book:F,labels:I}=u?P(u,n,j):{book:null,labels:null},L=F?F.length/9:0,R=17+(L>0?2:0),z=new Uint8Array(128+R*n+L*9),B=new DataView(z.buffer);B.setUint32(0,n,!0),A.forEach((e,t)=>B.setUint32(4+4*t,e,!0)),B.setUint16(16,L,!0),[...v,...y,...p,...m,...h,...g,...j].forEach((e,t)=>B.setFloat32(20+4*t,e,!0));let V=e=>128+e*n,H=new Float32Array([...d,...f]),U=/* @__PURE__ */ new Float64Array(4),W=/* @__PURE__ */ new Float64Array(3),G=[0,0,0];for(let e=0;e<n;e++){let t=D[e];for(let n=0;n<3;n++){let r=b[t*3+n]-G[n]<<16>>16,i=r<0?-2*r-1:2*r;G[n]=b[t*3+n],z[V(a.position+2*n)+e]=i&255,z[V(a.position+2*n+1)+e]=i>>8}z[V(a.alpha)+e]=O(Math.round(c[t]*255),0,255);let n=Math.hypot(...o.subarray(t*4,t*4+4));for(let e=0;e<4;e++)U[e]=o[t*4+e]/n;let r=0;for(let e=1;e<4;e++)Math.abs(U[e])>Math.abs(U[r])&&(r=e);let u=U[r]<0?-1:1;z[V(a.rotationIndex)+e]=r;for(let t=0,n=0;t<4;t++){if(t===r)continue;let i=Math.round((u*U[t]/Math.SQRT2+.5)*255);z[V(a.rotation+n++)+e]=O(i,0,255)}for(let n=0;n<3;n++)z[V(a.scale+n)+e]=k(s[t*3+n],p[n],m[n]),z[V(a.dc+n)+e]=k(l[t*3+n],h[n],g[n]);I&&(z[V(a.label)+e]=I[t]&255,z[V(a.label+1)+e]=I[t]>>8);let[d,f,_]=[0,1,2].map(e=>Math.exp(s[t*3+e]));x(U,d,f,_,W);for(let e=0;e<3;e++)H[e]=Math.min(H[e],i[t*3+e]-W[e]),H[3+e]=Math.max(H[3+e],i[t*3+e]+W[e])}return F&&z.set(new Uint8Array(F.buffer),V(R)),{payload:z,row:{g:t.g,i:t.i,j:t.j,count:n,quadrants:A,box:H,offset:0,length:0}}}function I(e,t,n){e.setUint8(t,n.g),e.setUint8(t+1,n.i),e.setUint8(t+2,n.j),e.setUint32(t+4,n.count,!0),n.quadrants.forEach((n,r)=>e.setUint32(t+8+4*r,n,!0)),n.box.forEach((n,r)=>e.setFloat32(t+20+4*r,n,!0)),e.setUint32(t+44,n.offset,!0),e.setUint32(t+48,n.length,!0)}function L(e,t,n){for(let r=0;r<4;r++)e[t+r]=n.charCodeAt(r)}function R(e){return Uint8Array.from({length:8},(t,n)=>parseInt(e.slice(2*n,2*n+2),16))}async function z(e,t){let n=await l(e),r=new Uint8Array(8+n.length);return L(r,0,t),new DataView(r.buffer).setUint16(4,1,!0),r.set(n,8),r}async function B(e){let{rows:t,children:n,descendants:r}=e,a=new Uint8Array(40+t.length*52+n.length*9+r.length*11),o=new DataView(a.buffer);o.setUint8(0,e.level),o.setInt32(4,e.e,!0),o.setInt32(8,e.n,!0),a.set(R(e.pack),12),o.setUint32(20,e.packSize,!0),e.col&&a.set(R(e.col),24),o.setUint16(32,t.length,!0),o.setUint8(34,n.length),o.setUint16(36,r.length,!0);let s=40;for(let e of t)I(o,s,e),s+=52;for(let e of n)o.setUint8(s,e.quadrant),a.set(R(e.idx),s+1),s+=9;for(let e of r)o.setUint8(s,e.depth),o.setUint8(s+1,e.column),o.setUint8(s+2,e.row),a.set(R(e.idx),s+3),s+=11;return z(a,i)}function V(e){let t=3421674724,n=2216829733;for(let r=0;r<e.length;r++){n=(n^e[r])>>>0;let i=n*435;t=t*435+(n<<8>>>0)+Math.floor(i/4294967296)>>>0,n=i>>>0}return t.toString(16).padStart(8,`0`)+n.toString(16).padStart(8,`0`)}function H(e){return()=>{e=e+1831565813|0;let t=Math.imul(e^e>>>15,1|e);return t=t+Math.imul(t^t>>>7,61|t)^t,((t^t>>>14)>>>0)/2**32}}async function U(e,t){return p(await G(e,t))}async function*W(e,t,n,r){let i=t.col===null?null:te(e,t.col,n),a=await ee(e,t,r),o=await i;for(let[e,n]of t.pages.entries()){let t=await c(a[e]);r?.throwIfAborted(),yield{id:n.id,page:T(t,o)}}}async function G(e,t){let n=await e.cache.get(t);if(n)return n;let r=await e.fetch(e.base+t,null);return e.cache.put(t,r),r}async function ee(e,t,n){let r=t.pages.map(e=>`${t.pack}#${e.offset}+${e.length}`),i=await Promise.all(r.map(t=>e.cache.get(t)));if(n?.throwIfAborted(),i.every(e=>e!==void 0))return i;let a=await e.fetch(e.base+t.pack,[t.start,t.end],n);if(a.length!==t.end-t.start)throw Error(`${t.pack}: ${a.length} bytes for ${t.start}-${t.end}`);return t.pages.map((n,o)=>{let s=a.slice(n.offset-t.start,n.offset-t.start+n.length);return i[o]||e.cache.put(r[o],s),s})}function te(e,t,n){let r=n.get(t);if(r)n.delete(t);else{let i=G(e,t).then(_);i.catch(()=>{n.get(t)===i&&n.delete(t)}),r=i}if(n.set(t,r),n.size>64){let[e]=n.keys();n.delete(e)}return r}function ne(e){let t=/* @__PURE__ */ new Map,n=0;return{async get(e){let n=t.get(e);return n&&(t.delete(e),t.set(e,n)),n},async put(r,i){let a=t.get(r);if(a&&(t.delete(r),n-=a.length),!(i.length>e)){t.set(r,i),n+=i.length;for(let[r,i]of t){if(n<=e)break;t.delete(r),n-=i.length}}}}}async function re(e,t){let n;try{n=await(await ae()).getDirectoryHandle(String(t),{create:!0})}catch{return null}let r=/* @__PURE__ */ new Map,i=0,a=!1,o=(e,t)=>{i+=t-(r.get(e)??0),r.delete(e),r.set(e,t)},s=e=>{i-=r.get(e)??0,r.delete(e)},c=()=>{if(a)for(let[t,a]of r){if(i<=e)break;r.delete(t),i-=a,n.removeEntry(t).catch(()=>void 0)}};return ce(n).then(e=>{let t=[...r];r.clear(),i=0;for(let{name:t,size:n}of e.sort((e,t)=>e.time-t.time))o(t,n);for(let[e,n]of t)o(e,n);a=!0,c()}),{async get(e){let t=encodeURIComponent(e);if(a&&!r.has(t))return;let i=await oe(n,t);return i?o(t,i.length):s(t),i},async put(t,r){if(r.length===0||r.length>e)return;let i=encodeURIComponent(t);await se(n,i,r)&&(o(i,r.length),c())}}}async function ie(e){let t=new Set(Array.from({length:e},(e,t)=>String(t)));try{let e=await ae(),n=[];for await(let[r,i]of e.entries())(i.kind!==`directory`||!t.has(r))&&n.push(r);let r={recursive:!0};for(let t of n)await e.removeEntry(t,r).catch(()=>void 0)}catch{}}async function ae(){return(await navigator.storage.getDirectory()).getDirectoryHandle(`cache`,{create:!0})}async function oe(e,t){try{let n=await(await e.getFileHandle(t)).getFile();return n.size>0?new Uint8Array(await n.arrayBuffer()):void 0}catch{return}}async function se(e,t,n){let r;try{return r=await(await e.getFileHandle(t,{create:!0})).createWritable(),await r.write(n),await r.close(),!0}catch{return r?.abort().catch(()=>void 0),!1}}async function ce(e){let t=[];try{for await(let[n,r]of e.entries()){if(r.kind!==`file`)continue;let e=await r.getFile().catch(()=>null);e&&t.push({name:n,size:e.size,time:e.lastModified})}}catch{}return t}function le(t){let n=/* @__PURE__ */ new Map,r=0;return{fetch:(i,a,o)=>new Promise((s,c)=>{if(o?.aborted)return c(o.reason);let l=++r,u=()=>{n.delete(l),t({unfetch:l}),c(o.reason)};n.set(l,t=>{o?.removeEventListener(`abort`,u),`bytes`in t?s(t.bytes):c(t.missing?new e(t.error):Error(t.error))}),o?.addEventListener(`abort`,u,{once:!0}),t({fetch:l,url:i,range:a})}),take(e){let t=n.get(e.fetched);n.delete(e.fetched),t?.(e)}}}let K=16384,ue=1408,de=65535,q=324121,fe=.4,pe=[[12,1/7e3,0,1/9e3,.7],[9,1/2300,1.1,1/3100,.4],[6,1/800,.3,1/1100,2],[3,1/150,.9,1/210,1.7]],me=pe.reduce((e,[t,n,,r])=>e+t*(n+r),0),he=Float32Array.from({length:ue*9},(e,t)=>{let n=Math.floor(t/9),r=t%9,i=(n*(37+2*r)+11*r)%255-127;return r===0&&(i=n%255-127),r===1&&(i=20*Math.floor(n/255)-50),i/127*.04}),J=new TextEncoder,ge={version:1,crs:`synthetic`,height:`synthetic`,leaf:250,roots:[512e4,6144e3].map(e=>({level:12,e:0,n:e})).map(e=>({...e,idx:m(e,Y(e,`idx`),`idx`)})),extent:{e:[44e4,9e5],n:[605e4,641e4],h:[0,80]}},_e=J.encode(JSON.stringify(ge));function ve(){return async(t,n)=>{if(t.endsWith(`world.json`))return be(_e,n);let r=g(t),i=t.slice(t.lastIndexOf(`.`)+1);if(!r||i!==`idx`&&i!==`pack`||!xe(r)||r.hash!==Y(r,i))throw new e(`no file ${t}`);return i===`idx`?be(await De(r),n):Oe(r,n,t)}}function ye(e,t){let n=30;for(let[r,i,a,o,s]of pe)n+=r*Math.sin(i*e+a)*Math.sin(o*t+s);return n}function be(e,t){return t?e.slice(t[0],t[1]):e.slice()}function Y(e,t){return V(J.encode(`${e.level}/${e.e}/${e.n}.${t}`))}function X(e,t,n){let{e:r,n:i}=ge.extent;return e<r[1]&&e+n>r[0]&&t<i[1]&&t+n>i[0]}function xe({level:e,e:t,n}){let r=250*2**e;return e<=12&&t%r===0&&n%r===0&&X(t,n,r)}function Se(e){return e===0?[1,0]:e===12?[16,15,14,13]:[e+1]}function Ce(e){let t=0;for(let n=0;n<8;n++)t|=(e>>2*n&1)<<n;return t}function we(e){let t=[];for(let n of Se(e.level)){let i=r*2**n,a=250*2**e.level/i;for(let r=0;r<a*a;r++){let a=Ce(r),o=Ce(r>>1);X(e.e+a*i,e.n+o*i,i)&&t.push({g:n,i:a,j:o})}}return t}function Te(e,t){let n=e.level-t,r=250*2**n,i=[];for(let a=0;n>=0&&a<2**t;a++)for(let o=0;o<2**t;o++){let t={level:n,e:e.e+o*r,n:e.n+a*r};X(t.e,t.n,r)&&i.push({column:o,row:a,unit:t})}return i}function Ee(e,{g:t,i:n,j:i},a){let o=r*2**t,s=o/128,c=3*1.2*s,l=1.17*s,u=ye(e.e+(n+.5)*o,e.n+(i+.5)*o),d=me*o/2,f=Float32Array.of(n*o-c,i*o-c,Math.max(0,u-d)-l,(n+1)*o+c,(i+1)*o+c,Math.min(60,u+d)+l),p=K/4;return{g:t,i:n,j:i,count:K,quadrants:[p,2*p,3*p],box:f,offset:a,length:q}}function De(e){let t=we(e),n=[];for(let{column:t,row:r,unit:i}of Te(e,1))n.push({quadrant:t+2*r,idx:Y(i,`idx`)});let r=[];for(let t of[2,3])for(let{column:n,row:i,unit:a}of Te(e,t))r.push({depth:t,column:n,row:i,idx:Y(a,`idx`)});return B({level:e.level,e:e.e,n:e.n,pack:Y(e,`pack`),packSize:t.length*324173+16,col:null,rows:t.map((t,n)=>Ee(e,t,n*q)),children:n,descendants:r})}function Oe(e,t,n){let r=we(e);if(!t||t[0]%q!=0||t[1]%q!=0||t[0]>=t[1]||t[1]>r.length*q)throw Error(`${n}: the synthetic world serves whole pages only`);let i=new Uint8Array(t[1]-t[0]);for(let n=0;n<i.length;n+=q)ke(je(e,r[(t[0]+n)/q]),i,n);return i}function ke(e,t,n){let r=n;for(let n=0;n<e.length;n+=de){let i=Math.min(de,e.length-n);t[r]=+(n+i===e.length),t[r+1]=i&255,t[r+2]=i>>8,t[r+3]=~i&255,t[r+4]=~i>>8&255,t.set(e.subarray(n,n+i),r+5),r+=5+i}}let Ae=e=>H(parseInt(V(J.encode(e)).slice(8),16));function je(e,{g:t,i,j:a}){let o=K,s=r*2**t/128,c=Ae(`${e.level}/${e.e}/${e.n}/${t}/${i}/${a}`),l=new Float64Array(3*o),u=new Float32Array(4*o),d=new Float32Array(3*o),f=new Float32Array(o),p=new Float32Array(3*o),m=new Float32Array(9*o);for(let t=0;t<o;t++){let r=(i*128+t%128+.5+fe*(2*c()-1))*s,o=(a*128+Math.floor(t/128)+.5+fe*(2*c()-1))*s,h=ye(e.e+r,e.n+o);l[3*t]=r,l[3*t+1]=o,l[3*t+2]=h;let g=Math.PI*c(),_=.1/2*(2*c()-1);u[4*t]=Math.cos(g)*Math.cos(_),u[4*t+1]=Math.cos(g)*Math.sin(_),u[4*t+2]=Math.sin(g)*Math.sin(_),u[4*t+3]=Math.sin(g)*Math.cos(_);for(let e=0;e<2;e++)d[3*t+e]=Math.log(s*(.6+.6*c()));d[3*t+2]=Math.log(s*.15*(.5+.5*c())),f[t]=.35+.65*c();let v=h/60,y=.5+.5*Math.sin((e.e+r)/410)*Math.sin((e.n+o)/330);p[3*t]=(.32+.2*v+.1*y-.5)/n,p[3*t+1]=(.42+.15*y-.1*v-.5)/n,p[3*t+2]=(.25+.1*v+.04*c()-.5)/n;let b=t%ue;m.set(he.subarray(9*b,9*(b+1)),9*t)}return F({count:o,position:l,rotation:u,scale:d,alpha:f,dc:p,sh:m},{g:t,i,j:a}).payload}let Z=2**20,Q=self,$,Me=/* @__PURE__ */ new Map,Ne=/* @__PURE__ */ new Map,Pe=le(e=>Q.postMessage(e,[]));Q.onmessage=({data:e})=>{`fetched`in e?Pe.take(e):e.type===`init`?($=Fe(e),$.catch(()=>void 0)):e.type===`abort`?Ne.get(e.id)?.abort():Re(e)};async function Fe(e){return e.source===`synthetic`?{fetch:ve(),cache:await Ie({...e,cache:`none`}),base:e.base}:{fetch:e.source===`page`?Pe.fetch:t,cache:await Ie(e),base:e.base}}async function Ie({cache:e,shard:t,shards:n}){return e===`memory`?ne(256*Z):e===`none`?{get:async()=>void 0,put:async()=>void 0}:(t===0&&ie(n),await re(await Le()/n,t)??ne(256*Z))}async function Le(){try{let{quota:e}=await navigator.storage.estimate();return Math.min(4096*Z,e===void 0?1/0:e/2)}catch{return 4096*Z}}async function Re(t){let{id:n}=t,r=new AbortController;Ne.set(n,r);try{if(!$)throw Error(`stream worker used before init`);let e=await $;if(t.type===`idx`)Q.postMessage({id:n,value:await U(e,t.path)},[]);else{for await(let i of W(e,t.batch,Me,r.signal))Q.postMessage({id:n,page:i},ze(i));Q.postMessage({id:n,done:!0},[])}}catch(t){let r=t instanceof Error?t.message:String(t);Q.postMessage({id:n,error:r,missing:t instanceof e},[])}finally{Ne.delete(n)}}function ze({page:e}){let t=/* @__PURE__ */ new Set;for(let n of[e.geometry,e.colour,e.params,e.clusters])t.add(n.buffer);return[...t]}})();", Gt = typeof self < "u" && self.Blob && new Blob(["(self.URL || self.webkitURL).revokeObjectURL(self.location.href);", Wt], { type: "text/javascript;charset=utf-8" });
|
|
2407
|
+
function Kt(e) {
|
|
2354
2408
|
let t;
|
|
2355
2409
|
try {
|
|
2356
|
-
if (t =
|
|
2410
|
+
if (t = Gt && (self.URL || self.webkitURL).createObjectURL(Gt), !t) throw "";
|
|
2357
2411
|
let n = new Worker(t, { name: e?.name });
|
|
2358
2412
|
return n.addEventListener("error", () => {
|
|
2359
2413
|
(self.URL || self.webkitURL).revokeObjectURL(t);
|
|
2360
2414
|
}), n;
|
|
2361
2415
|
} catch {
|
|
2362
|
-
return new Worker("data:text/javascript;charset=utf-8," + encodeURIComponent(
|
|
2416
|
+
return new Worker("data:text/javascript;charset=utf-8," + encodeURIComponent(Wt), { name: e?.name });
|
|
2363
2417
|
}
|
|
2364
2418
|
}
|
|
2365
2419
|
//#endregion
|
|
2366
2420
|
//#region src/engine/stream/loader.ts
|
|
2367
|
-
var
|
|
2421
|
+
var qt = class {
|
|
2368
2422
|
#e;
|
|
2369
2423
|
#t = /* @__PURE__ */ new Map();
|
|
2370
2424
|
#n = 0;
|
|
2371
2425
|
constructor(e) {
|
|
2372
2426
|
let { base: t, cache: n, source: r, workers: i } = e;
|
|
2373
2427
|
this.#e = Array.from({ length: i }, (e, a) => {
|
|
2374
|
-
let o = new
|
|
2428
|
+
let o = new Kt(), s = { worker: o }, c = typeof r == "function" ? Ut(r, (e, t) => o.postMessage(e, t)) : void 0;
|
|
2375
2429
|
o.onmessage = ({ data: e }) => {
|
|
2376
2430
|
"id" in e ? this.#i(e) : c?.(e);
|
|
2377
2431
|
}, o.onerror = () => this.#a(s);
|
|
@@ -2395,8 +2449,8 @@ var Ht = class {
|
|
|
2395
2449
|
return this.#r(this.#e[0], t);
|
|
2396
2450
|
}
|
|
2397
2451
|
batch(e, t, n) {
|
|
2398
|
-
if (t.aborted) return Promise.reject(
|
|
2399
|
-
let r = this.#e[
|
|
2452
|
+
if (t.aborted) return Promise.reject(Yt());
|
|
2453
|
+
let r = this.#e[Jt(`${e.pack}#${e.window}`, this.#e.length)], i = {
|
|
2400
2454
|
type: "batch",
|
|
2401
2455
|
id: ++this.#n,
|
|
2402
2456
|
batch: e
|
|
@@ -2405,7 +2459,7 @@ var Ht = class {
|
|
|
2405
2459
|
}
|
|
2406
2460
|
destroy() {
|
|
2407
2461
|
for (let { worker: e } of this.#e) e.terminate();
|
|
2408
|
-
for (let e of this.#t.values()) e.reject(
|
|
2462
|
+
for (let e of this.#t.values()) e.reject(Yt());
|
|
2409
2463
|
}
|
|
2410
2464
|
#r(e, t, n, r) {
|
|
2411
2465
|
if (e.error) return Promise.reject(e.error);
|
|
@@ -2417,7 +2471,7 @@ var Ht = class {
|
|
|
2417
2471
|
s(), e.worker.postMessage({
|
|
2418
2472
|
type: "abort",
|
|
2419
2473
|
id: i
|
|
2420
|
-
}), o(
|
|
2474
|
+
}), o(Yt());
|
|
2421
2475
|
};
|
|
2422
2476
|
this.#t.set(i, {
|
|
2423
2477
|
slot: e,
|
|
@@ -2440,90 +2494,90 @@ var Ht = class {
|
|
|
2440
2494
|
for (let t of this.#t.values()) t.slot === e && t.reject(e.error);
|
|
2441
2495
|
}
|
|
2442
2496
|
};
|
|
2443
|
-
function
|
|
2497
|
+
function Jt(e, t) {
|
|
2444
2498
|
let n = 2166136261;
|
|
2445
2499
|
for (let t = 0; t < e.length; t++) n = Math.imul(n ^ e.charCodeAt(t), 16777619);
|
|
2446
2500
|
return (n >>> 0) % t;
|
|
2447
2501
|
}
|
|
2448
|
-
function
|
|
2502
|
+
function Yt() {
|
|
2449
2503
|
return new DOMException("The request was aborted.", "AbortError");
|
|
2450
2504
|
}
|
|
2451
2505
|
//#endregion
|
|
2452
2506
|
//#region src/engine/engine.ts
|
|
2453
|
-
var
|
|
2507
|
+
var Xt = class extends Error {
|
|
2454
2508
|
constructor() {
|
|
2455
2509
|
super("This viewer needs WebGPU. Update to the latest Chrome, Edge, Safari or Firefox."), this.name = "NoWebGpu";
|
|
2456
2510
|
}
|
|
2457
2511
|
};
|
|
2458
|
-
async function
|
|
2512
|
+
async function Zt(e, t) {
|
|
2459
2513
|
let n = await g();
|
|
2460
|
-
if (!n) throw new
|
|
2514
|
+
if (!n) throw new Xt();
|
|
2461
2515
|
let r = e.getContext("webgpu");
|
|
2462
|
-
if (!r) throw n.device.destroy(), new
|
|
2516
|
+
if (!r) throw n.device.destroy(), new Xt();
|
|
2463
2517
|
r.configure({
|
|
2464
2518
|
device: n.device,
|
|
2465
2519
|
format: n.format,
|
|
2466
2520
|
alphaMode: "opaque"
|
|
2467
2521
|
}), (t.cache ?? "opfs") === "opfs" && navigator.storage?.persist().catch(() => !1);
|
|
2468
2522
|
let { source: i = "http" } = t;
|
|
2469
|
-
return new
|
|
2523
|
+
return new Cn(e, n, r, t, i === "synthetic" ? (await import("./synthetic-DO8oIw_x.js")).synthetic() : i === "http" ? u : i);
|
|
2470
2524
|
}
|
|
2471
|
-
var
|
|
2525
|
+
var G = .2, Qt = 25165824, $t = 3.25, en = 2, tn = 1024, nn = 2048, rn = 100, an = 2, on = 300, sn = 100, cn = 250, ln = 300, un = 1e3, dn = 400, fn = 5e3, pn = 60, K = Math.PI / 180, q = "The viewer was closed.", mn = "The layers hold more splats than this device can.", hn = [
|
|
2472
2526
|
1,
|
|
2473
2527
|
1,
|
|
2474
2528
|
1,
|
|
2475
2529
|
1
|
|
2476
|
-
],
|
|
2477
|
-
function
|
|
2530
|
+
], gn = "Another world was opened.";
|
|
2531
|
+
function J(e, t) {
|
|
2478
2532
|
let n = Math.min(t.maxStorageBufferBindingSize, t.maxBufferSize), r = (t, r) => {
|
|
2479
2533
|
let i = Math.ceil(e * t / 256) * 256;
|
|
2480
2534
|
return Math.min(i, Math.floor(n / r / 256) * 256);
|
|
2481
2535
|
};
|
|
2482
2536
|
return {
|
|
2483
|
-
pool: r(
|
|
2484
|
-
frame: r(
|
|
2537
|
+
pool: r($t, 16),
|
|
2538
|
+
frame: r(en, 24)
|
|
2485
2539
|
};
|
|
2486
2540
|
}
|
|
2487
|
-
function
|
|
2541
|
+
function _n(e, t) {
|
|
2488
2542
|
let [n, r, i] = t;
|
|
2489
|
-
if (Math.hypot(n - e[0], r - e[1], i - e[2]) <=
|
|
2490
|
-
let a = (e) => Math.round(e /
|
|
2543
|
+
if (Math.hypot(n - e[0], r - e[1], i - e[2]) <= nn) return e;
|
|
2544
|
+
let a = (e) => Math.round(e / tn) * tn;
|
|
2491
2545
|
return [
|
|
2492
2546
|
a(n),
|
|
2493
2547
|
a(r),
|
|
2494
2548
|
a(i)
|
|
2495
2549
|
];
|
|
2496
2550
|
}
|
|
2497
|
-
function
|
|
2551
|
+
function vn(e, t, n, r, i, a) {
|
|
2498
2552
|
let o = 2 * e[0] / t[0] - 1, s = 1 - 2 * e[1] / t[1], c = [
|
|
2499
2553
|
n * o / r[0],
|
|
2500
2554
|
n * s / r[5],
|
|
2501
2555
|
-n
|
|
2502
|
-
], [l, u, d] =
|
|
2556
|
+
], [l, u, d] = ce(se(/* @__PURE__ */ new Float64Array(16), i), c);
|
|
2503
2557
|
return [
|
|
2504
2558
|
l + a[0],
|
|
2505
2559
|
u + a[1],
|
|
2506
2560
|
d + a[2]
|
|
2507
2561
|
];
|
|
2508
2562
|
}
|
|
2509
|
-
function
|
|
2563
|
+
function yn(e) {
|
|
2510
2564
|
if (!e.length || !e.every((e) => e.length === 3 && e.every(Number.isFinite))) throw Error("Give at least one point, each three finite numbers.");
|
|
2511
2565
|
return e;
|
|
2512
2566
|
}
|
|
2513
|
-
function
|
|
2567
|
+
function bn(e, t) {
|
|
2514
2568
|
return [
|
|
2515
2569
|
e.e - t[0],
|
|
2516
2570
|
e.n - t[1],
|
|
2517
2571
|
e.h - t[2]
|
|
2518
2572
|
];
|
|
2519
2573
|
}
|
|
2520
|
-
function
|
|
2521
|
-
e.push(t), e.length >
|
|
2574
|
+
function xn(e, t) {
|
|
2575
|
+
e.push(t), e.length > pn && e.shift();
|
|
2522
2576
|
}
|
|
2523
|
-
function
|
|
2577
|
+
function Sn({ visible: e, opacity: t }) {
|
|
2524
2578
|
return e ? Math.round(t * 255) * 16843009 >>> 0 : 0;
|
|
2525
2579
|
}
|
|
2526
|
-
var
|
|
2580
|
+
var Cn = class {
|
|
2527
2581
|
#e;
|
|
2528
2582
|
#t;
|
|
2529
2583
|
#n;
|
|
@@ -2534,8 +2588,8 @@ var vn = class {
|
|
|
2534
2588
|
#s;
|
|
2535
2589
|
#c;
|
|
2536
2590
|
#l;
|
|
2537
|
-
#u = new
|
|
2538
|
-
#d = new
|
|
2591
|
+
#u = new yt();
|
|
2592
|
+
#d = new it();
|
|
2539
2593
|
#f = (e) => this.#s.has(e);
|
|
2540
2594
|
#p = null;
|
|
2541
2595
|
#m = null;
|
|
@@ -2617,8 +2671,8 @@ var vn = class {
|
|
|
2617
2671
|
e.height,
|
|
2618
2672
|
1
|
|
2619
2673
|
], this.#R = [Math.max(1, e.width), Math.max(1, e.height)];
|
|
2620
|
-
let { pool: a, frame: o } =
|
|
2621
|
-
this.#s = new
|
|
2674
|
+
let { pool: a, frame: o } = J(this.#me, t.device.limits);
|
|
2675
|
+
this.#s = new ne(t.device, a), this.#c = new tt(t, n, this.#s, o), this.#l = o, t.device.lost.then((e) => {
|
|
2622
2676
|
if (!this.#fe) {
|
|
2623
2677
|
this.#pe = !0, cancelAnimationFrame(this.#z);
|
|
2624
2678
|
for (let t of this.#se) t(e.message || e.reason);
|
|
@@ -2626,34 +2680,34 @@ var vn = class {
|
|
|
2626
2680
|
});
|
|
2627
2681
|
}
|
|
2628
2682
|
async open(e) {
|
|
2629
|
-
if (this.#fe) throw Error(
|
|
2683
|
+
if (this.#fe) throw Error(q);
|
|
2630
2684
|
let t = ++this.#_, r = () => {
|
|
2631
|
-
if (this.#fe) throw Error(
|
|
2632
|
-
if (t !== this.#_) throw Error(
|
|
2685
|
+
if (this.#fe) throw Error(q);
|
|
2686
|
+
if (t !== this.#_) throw Error(gn);
|
|
2633
2687
|
}, { cache: i = "opfs", source: o = "http" } = this.#r;
|
|
2634
2688
|
o === "http" && (e = new URL(e, document.baseURI).href);
|
|
2635
2689
|
let s = await this.#i(e, null), c = a(JSON.parse(new TextDecoder().decode(s)));
|
|
2636
2690
|
r();
|
|
2637
|
-
let l = new
|
|
2691
|
+
let l = new qt({
|
|
2638
2692
|
base: n(e),
|
|
2639
2693
|
workers: Math.min(6, Math.max(2, navigator.hardwareConcurrency - 2)),
|
|
2640
2694
|
cache: i,
|
|
2641
2695
|
source: o
|
|
2642
|
-
}), u = new
|
|
2696
|
+
}), u = new mt(c);
|
|
2643
2697
|
try {
|
|
2644
2698
|
let e = await Promise.all(c.roots.map((e) => l.idx(e.idx)));
|
|
2645
2699
|
r(), e.forEach((e, t) => u.add(e, c.roots[t].idx));
|
|
2646
2700
|
} catch (e) {
|
|
2647
2701
|
throw l.destroy(), e;
|
|
2648
2702
|
}
|
|
2649
|
-
return this.#g?.destroy(), this.#g = null, this.#h?.destroy(), this.#p = e, this.#m = u, this.#h = l, this.#H = null, this.#u = new
|
|
2703
|
+
return this.#g?.destroy(), this.#g = null, this.#h?.destroy(), this.#p = e, this.#m = u, this.#h = l, this.#H = null, this.#u = new yt(), this.#d = new it(), this.#s.clear(), this.#g = this.#ve(u, l), this.#G = !0, this.requestFrame(), c;
|
|
2650
2704
|
}
|
|
2651
2705
|
async addLayer(e, t) {
|
|
2652
|
-
if (this.#fe) throw Error(
|
|
2653
|
-
let n = await
|
|
2654
|
-
if (this.#fe) throw Error(
|
|
2706
|
+
if (this.#fe) throw Error(q);
|
|
2707
|
+
let n = await nt("bytes" in e ? e.bytes : await this.#i(e.url, null), t);
|
|
2708
|
+
if (this.#fe) throw Error(q);
|
|
2655
2709
|
let r = n.reduce((e, { page: t }) => e + d(t.count), 0), i = this.#t.device.limits;
|
|
2656
|
-
if (
|
|
2710
|
+
if (J(this.#me, i).pool + this.#S + r > J(Infinity, i).pool) throw Error(mn);
|
|
2657
2711
|
this.#S += r, this.#ge();
|
|
2658
2712
|
let a = ++this.#b, o = (e) => this.#g?.protects(e) ?? !1, s = () => this.#be(), c = !0, l = 1, u = () => {
|
|
2659
2713
|
if (!(this.#fe || !this.#y.delete(a))) {
|
|
@@ -2662,7 +2716,7 @@ var vn = class {
|
|
|
2662
2716
|
}
|
|
2663
2717
|
}, f = {
|
|
2664
2718
|
splats: n.reduce((e, { page: t }) => e + t.count, 0),
|
|
2665
|
-
box:
|
|
2719
|
+
box: rt(n.map(({ box: e }) => e)),
|
|
2666
2720
|
get visible() {
|
|
2667
2721
|
return c;
|
|
2668
2722
|
},
|
|
@@ -2683,7 +2737,7 @@ var vn = class {
|
|
|
2683
2737
|
this.#y.set(a, p);
|
|
2684
2738
|
for (let { page: e, box: r } of n) {
|
|
2685
2739
|
let n = --this.#x;
|
|
2686
|
-
if (!this.#s.add(n, e, t, o, a)) throw u(), Error(
|
|
2740
|
+
if (!this.#s.add(n, e, t, o, a)) throw u(), Error(mn);
|
|
2687
2741
|
p.pages.push({
|
|
2688
2742
|
id: n,
|
|
2689
2743
|
count: e.count,
|
|
@@ -2693,7 +2747,7 @@ var vn = class {
|
|
|
2693
2747
|
return s(), this.#C.set(f, a), f;
|
|
2694
2748
|
}
|
|
2695
2749
|
addMask({ polygon: e, z: t = [-Infinity, Infinity], targets: n }) {
|
|
2696
|
-
if (this.#fe) throw Error(
|
|
2750
|
+
if (this.#fe) throw Error(q);
|
|
2697
2751
|
if (e.length < 3 || !e.flat().every(Number.isFinite)) throw Error("A mask needs three or more corners, each two finite numbers.");
|
|
2698
2752
|
let r = new Set(n.map((e) => e === "world" ? 0 : this.#C.get(e) ?? -1)), i = this.#s, a = {
|
|
2699
2753
|
polygon: Float64Array.from(e.flat()),
|
|
@@ -2714,8 +2768,8 @@ var vn = class {
|
|
|
2714
2768
|
};
|
|
2715
2769
|
}
|
|
2716
2770
|
addLine(e, t = {}) {
|
|
2717
|
-
let { colour: n =
|
|
2718
|
-
|
|
2771
|
+
let { colour: n = hn, width: r = 2, closed: i = !1, occlude: a = !0 } = t, o = (e) => {
|
|
2772
|
+
yn(e);
|
|
2719
2773
|
let t = i && e.length > 2 ? [...e, e[0]] : e;
|
|
2720
2774
|
return (t.length > 1 ? t.slice(1).map((e, n) => [t[n], e]) : [[t[0], t[0]]]).map(([e, t]) => ({
|
|
2721
2775
|
a: e,
|
|
@@ -2748,7 +2802,7 @@ var vn = class {
|
|
|
2748
2802
|
};
|
|
2749
2803
|
}
|
|
2750
2804
|
toScreen([e, t, n]) {
|
|
2751
|
-
let r = this.#O, [i, a] = this.#L, o = this.#j, s =
|
|
2805
|
+
let r = this.#O, [i, a] = this.#L, o = this.#j, s = ie(/* @__PURE__ */ new Float64Array(16), bn(r, o), r.yaw * K, r.pitch * K), c = ae(/* @__PURE__ */ new Float64Array(16), r.fov * K, i / Math.max(1, a), G, this.#a.viewDistance), [l, u, , d] = ce(P(/* @__PURE__ */ new Float64Array(16), c, s), [
|
|
2752
2806
|
e - o[0],
|
|
2753
2807
|
t - o[1],
|
|
2754
2808
|
n - o[2]
|
|
@@ -2758,9 +2812,9 @@ var vn = class {
|
|
|
2758
2812
|
setCamera(e) {
|
|
2759
2813
|
if (this.#fe) return;
|
|
2760
2814
|
let t = performance.now(), n = t - this.#k, r = this.#O, i = this.#A;
|
|
2761
|
-
if (n >
|
|
2815
|
+
if (n > cn) i.fill(0);
|
|
2762
2816
|
else if (n > 0) {
|
|
2763
|
-
let t = 1 - Math.exp(-n /
|
|
2817
|
+
let t = 1 - Math.exp(-n / sn);
|
|
2764
2818
|
i[0] += t * ((e.e - r.e) / n - i[0]), i[1] += t * ((e.n - r.n) / n - i[1]), i[2] += t * ((e.h - r.h) / n - i[2]);
|
|
2765
2819
|
}
|
|
2766
2820
|
this.#k = t, this.#O = { ...e }, this.#W = !0, this.#de || this.requestFrame();
|
|
@@ -2811,8 +2865,8 @@ var vn = class {
|
|
|
2811
2865
|
stats() {
|
|
2812
2866
|
let e = this.#s, t = this.#g, n = this.#c.stats();
|
|
2813
2867
|
return {
|
|
2814
|
-
frameMs:
|
|
2815
|
-
cpuMs:
|
|
2868
|
+
frameMs: Pt(this.#$, .5),
|
|
2869
|
+
cpuMs: Pt(this.#ee, .5),
|
|
2816
2870
|
gpuMs: n.gpuMs,
|
|
2817
2871
|
passes: n.passes,
|
|
2818
2872
|
drawn: n.drawn,
|
|
@@ -2849,7 +2903,7 @@ var vn = class {
|
|
|
2849
2903
|
}
|
|
2850
2904
|
warm() {
|
|
2851
2905
|
let e = performance.now();
|
|
2852
|
-
e - this.#X <
|
|
2906
|
+
e - this.#X < un || (this.#Z = e + dn, this.requestFrame());
|
|
2853
2907
|
}
|
|
2854
2908
|
onFrame(e) {
|
|
2855
2909
|
return this.#ce.add(e), () => this.#ce.delete(e);
|
|
@@ -2891,30 +2945,30 @@ var vn = class {
|
|
|
2891
2945
|
return this.#o.budget;
|
|
2892
2946
|
}
|
|
2893
2947
|
#he() {
|
|
2894
|
-
let { budget: e, budgetRange: t = [e, e] } = this.#a, n = Math.floor(
|
|
2895
|
-
return new
|
|
2948
|
+
let { budget: e, budgetRange: t = [e, e] } = this.#a, n = Math.floor(J(Infinity, this.#t.device.limits).frame / en), r = (e) => Math.max(1, Math.min(e, n));
|
|
2949
|
+
return new Ft(r(e), [r(t[0]), r(t[1])]);
|
|
2896
2950
|
}
|
|
2897
2951
|
#ge() {
|
|
2898
|
-
let { pool: e, frame: t } =
|
|
2952
|
+
let { pool: e, frame: t } = J(this.#me, this.#t.device.limits), n = e + this.#S;
|
|
2899
2953
|
(n > this.#s.capacity || t > this.#l) && this.#_e(n, t), this.#G = !0, this.requestFrame();
|
|
2900
2954
|
}
|
|
2901
2955
|
#_e(e, t) {
|
|
2902
2956
|
this.#s.grow(e), this.#c.destroy();
|
|
2903
|
-
let n = new
|
|
2957
|
+
let n = new tt(this.#t, this.#n, this.#s, t);
|
|
2904
2958
|
n.resize(...this.#R);
|
|
2905
2959
|
for (let e of this.#te) e.off = n.shade(e.hook);
|
|
2906
2960
|
for (let e of this.#ne) e.off = n.post(e.hook);
|
|
2907
2961
|
this.#c = n, this.#l = t, this.#ie = null, this.#D = !0;
|
|
2908
2962
|
}
|
|
2909
2963
|
#ve(e, t) {
|
|
2910
|
-
return new
|
|
2964
|
+
return new Ht(e, t, this.#s, () => {
|
|
2911
2965
|
this.#q = !0, this.requestFrame();
|
|
2912
2966
|
}, this.#ye);
|
|
2913
2967
|
}
|
|
2914
2968
|
#ye = () => {
|
|
2915
2969
|
let e = this.#p, t = this.#m;
|
|
2916
2970
|
this.#v || this.#fe || e === null || (this.#v = !0, this.open(e).then(() => this.#v = !1, () => {
|
|
2917
|
-
this.#v = !1, this.#m === t && setTimeout(this.#ye,
|
|
2971
|
+
this.#v = !1, this.#m === t && setTimeout(this.#ye, fn);
|
|
2918
2972
|
}));
|
|
2919
2973
|
};
|
|
2920
2974
|
#be() {
|
|
@@ -2930,16 +2984,16 @@ var vn = class {
|
|
|
2930
2984
|
0,
|
|
2931
2985
|
0
|
|
2932
2986
|
], r = 0;
|
|
2933
|
-
for (let { layer: i, pages: a } of this.#y.values()) if (
|
|
2987
|
+
for (let { layer: i, pages: a } of this.#y.values()) if (Sn(i)) for (let { count: i, box: o } of a) {
|
|
2934
2988
|
for (let r = 0; r < 3; r++) t[r] = o[r] - e[r], n[r] = o[r + 3] - e[r];
|
|
2935
|
-
|
|
2989
|
+
Ne(this.#I, t, n) && (r += i);
|
|
2936
2990
|
}
|
|
2937
2991
|
return r;
|
|
2938
2992
|
}
|
|
2939
2993
|
#Se() {
|
|
2940
2994
|
let e = [];
|
|
2941
2995
|
for (let { layer: t, pages: n } of this.#y.values()) {
|
|
2942
|
-
let r =
|
|
2996
|
+
let r = Sn(t);
|
|
2943
2997
|
if (r) for (let { id: t } of n) e.push({
|
|
2944
2998
|
id: t,
|
|
2945
2999
|
factors: r
|
|
@@ -2958,12 +3012,12 @@ var vn = class {
|
|
|
2958
3012
|
};
|
|
2959
3013
|
}
|
|
2960
3014
|
#we() {
|
|
2961
|
-
let [e, t, n] = this.#L, r =
|
|
3015
|
+
let [e, t, n] = this.#L, r = Nt(e, t, n, this.#o.scale), i = Math.max(1, Math.round(e * r)), a = Math.max(1, Math.round(t * r));
|
|
2962
3016
|
(i !== this.#R[0] || a !== this.#R[1]) && (this.#R = [i, a], this.#e.width = i, this.#e.height = a, this.#c.resize(i, a), this.#G = !0, this.#D = !0, this.requestFrame());
|
|
2963
3017
|
}
|
|
2964
3018
|
#Te = (e) => {
|
|
2965
3019
|
if (this.#z = 0, !(this.#fe || this.#pe)) {
|
|
2966
|
-
if (this.#B >=
|
|
3020
|
+
if (this.#B >= an) this.#V = !0;
|
|
2967
3021
|
else {
|
|
2968
3022
|
this.#de = !0;
|
|
2969
3023
|
for (let t of this.#ce) t(e);
|
|
@@ -2976,33 +3030,33 @@ var vn = class {
|
|
|
2976
3030
|
#Ee(e) {
|
|
2977
3031
|
let t = performance.now(), n = this.#o, r = this.#s, i = this.#O, [a, o] = this.#R, s = this.#a.viewDistance, c = this.#W;
|
|
2978
3032
|
this.#W = !1;
|
|
2979
|
-
let l =
|
|
3033
|
+
let l = _n(this.#j, [
|
|
2980
3034
|
i.e,
|
|
2981
3035
|
i.n,
|
|
2982
3036
|
i.h
|
|
2983
3037
|
]);
|
|
2984
3038
|
l !== this.#j && (this.#j = l, r.setOrigin(l), this.#D = !0);
|
|
2985
|
-
let u =
|
|
2986
|
-
|
|
3039
|
+
let u = bn(i, l);
|
|
3040
|
+
ie(this.#M, u, i.yaw * K, i.pitch * K), ae(this.#N, i.fov * K, a / o, G, s);
|
|
2987
3041
|
let d = {
|
|
2988
3042
|
time: t,
|
|
2989
3043
|
width: a,
|
|
2990
3044
|
height: o,
|
|
2991
3045
|
view: new Float32Array(this.#M),
|
|
2992
3046
|
proj: new Float32Array(this.#N),
|
|
2993
|
-
near:
|
|
3047
|
+
near: G,
|
|
2994
3048
|
far: s,
|
|
2995
3049
|
camera: Float32Array.from(u),
|
|
2996
3050
|
origin: l
|
|
2997
3051
|
};
|
|
2998
|
-
|
|
3052
|
+
Me(this.#I, P(this.#F, d.proj, d.view));
|
|
2999
3053
|
let f = this.#m, p = this.#g, m = this.#q || this.#G || this.#J, h = this.#H, g = h;
|
|
3000
3054
|
if (f && p) {
|
|
3001
|
-
let e = !p.idle && t - this.#U >=
|
|
3055
|
+
let e = !p.idle && t - this.#U >= rn, n = this.#G || this.#q || this.#J || this.#K;
|
|
3002
3056
|
(!g || c || e || n) && (g = this.#De(f, t, c));
|
|
3003
3057
|
}
|
|
3004
3058
|
let _ = this.#Y, v = this.#J;
|
|
3005
|
-
if (g && p && (g !== h && (m || !h || g.cut.length !== h.cut.length || g.cut.some((e, t) => e !== h.cut[t])) && ({drawn: _, fading: v} = this.#d.update(g.cut, this.#f, t, this.#me)), p.update(g, new Set(_.map((e) => e.id)), t)), r.upload(
|
|
3059
|
+
if (g && p && (g !== h && (m || !h || g.cut.length !== h.cut.length || g.cut.some((e, t) => e !== h.cut[t])) && ({drawn: _, fading: v} = this.#d.update(g.cut, this.#f, t, this.#me)), p.update(g, new Set(_.map((e) => e.id)), t)), r.upload(Qt) > 0 && (this.#q = !0), _ !== this.#Y || this.#q || this.#w) {
|
|
3006
3060
|
this.#w = !1;
|
|
3007
3061
|
let e = this.#Se();
|
|
3008
3062
|
r.draw(e.length ? _.concat(e) : _);
|
|
@@ -3034,8 +3088,8 @@ var vn = class {
|
|
|
3034
3088
|
origin: this.#j,
|
|
3035
3089
|
width: a / s,
|
|
3036
3090
|
height: o / s,
|
|
3037
|
-
tan: Math.tan(r.fov *
|
|
3038
|
-
near:
|
|
3091
|
+
tan: Math.tan(r.fov * K / 2),
|
|
3092
|
+
near: G,
|
|
3039
3093
|
far: this.#a.viewDistance
|
|
3040
3094
|
}, u = {
|
|
3041
3095
|
...l,
|
|
@@ -3052,20 +3106,20 @@ var vn = class {
|
|
|
3052
3106
|
let t = this.#A;
|
|
3053
3107
|
if (t.every((e) => e === 0)) return;
|
|
3054
3108
|
let n = this.#O, r = [
|
|
3055
|
-
n.e + t[0] *
|
|
3056
|
-
n.n + t[1] *
|
|
3057
|
-
n.h + t[2] *
|
|
3109
|
+
n.e + t[0] * on - e.origin[0],
|
|
3110
|
+
n.n + t[1] * on - e.origin[1],
|
|
3111
|
+
n.h + t[2] * on - e.origin[2]
|
|
3058
3112
|
];
|
|
3059
3113
|
return {
|
|
3060
3114
|
...e,
|
|
3061
|
-
view:
|
|
3115
|
+
view: ie(this.#P, r, n.yaw * K, n.pitch * K)
|
|
3062
3116
|
};
|
|
3063
3117
|
}
|
|
3064
3118
|
#ke() {
|
|
3065
3119
|
let e = this.#ie, t = this.#M.slice(), [n, r] = this.#L, i = [e.width, e.height];
|
|
3066
3120
|
for (let { x: a, y: o, resolve: s } of this.#re.splice(0)) {
|
|
3067
3121
|
let c = [a * i[0] / Math.max(1, n), o * i[1] / Math.max(1, r)], l = (n) => n && {
|
|
3068
|
-
point:
|
|
3122
|
+
point: vn(c, i, n.depth, e.proj, t, e.origin),
|
|
3069
3123
|
normal: n.normal,
|
|
3070
3124
|
layer: this.#y.get(n.layer)?.layer ?? null
|
|
3071
3125
|
};
|
|
@@ -3099,22 +3153,22 @@ var vn = class {
|
|
|
3099
3153
|
};
|
|
3100
3154
|
}
|
|
3101
3155
|
#Ne(e, t, n) {
|
|
3102
|
-
let r = this.#o, { gpuMs: i } = this.#c.stats(), a = e - this.#X, o = a <= Math.max(
|
|
3103
|
-
o &&
|
|
3156
|
+
let r = this.#o, { gpuMs: i } = this.#c.stats(), a = e - this.#X, o = a <= Math.max(cn, 2 * i, 2 * t);
|
|
3157
|
+
o && xn(this.#$, a), xn(this.#ee, t), this.#X = e;
|
|
3104
3158
|
let s = r.budget;
|
|
3105
|
-
r.sample(a, e, o && n, this.#H?.planned ?? 0) && (this.#we(), r.budget !== s && this.#ge()), n ? this.#Q = e : r.scale < 1 && e - this.#Q >
|
|
3159
|
+
r.sample(a, e, o && n, this.#H?.planned ?? 0) && (this.#we(), r.budget !== s && this.#ge()), n ? this.#Q = e : r.scale < 1 && e - this.#Q > ln && (r.full(), this.#we());
|
|
3106
3160
|
}
|
|
3107
|
-
},
|
|
3161
|
+
}, wn = 45, Tn = {
|
|
3108
3162
|
yaw: 0,
|
|
3109
3163
|
pitch: -35,
|
|
3110
3164
|
dist: 300
|
|
3111
|
-
},
|
|
3165
|
+
}, Y = {
|
|
3112
3166
|
pitch: [-90, -20],
|
|
3113
3167
|
dist: [1, 2485],
|
|
3114
3168
|
clearance: 10,
|
|
3115
3169
|
floor: 50
|
|
3116
|
-
},
|
|
3117
|
-
function
|
|
3170
|
+
}, En = .1, X = Math.PI / 180, Dn = 1.1, On = [600, 2500], kn = 300, An = .5, jn = (e, [t, n]) => Math.min(n, Math.max(t, e)), Mn = (e) => (e % 360 + 360) % 360, Nn = (e, t) => (t - e + 540) % 360 - 180;
|
|
3171
|
+
function Pn({ leaf: e, roots: t, extent: n }) {
|
|
3118
3172
|
let r = {
|
|
3119
3173
|
e: (n.e[0] + n.e[1]) / 2,
|
|
3120
3174
|
n: (n.n[0] + n.n[1]) / 2,
|
|
@@ -3131,7 +3185,7 @@ function kn({ leaf: e, roots: t, extent: n }) {
|
|
|
3131
3185
|
}
|
|
3132
3186
|
return i;
|
|
3133
3187
|
}
|
|
3134
|
-
function
|
|
3188
|
+
function Fn(e) {
|
|
3135
3189
|
let t = e.split(",");
|
|
3136
3190
|
if (t.length !== 6 || t.some((e) => e.trim() === "")) return null;
|
|
3137
3191
|
let [n, r, i, a, o, s] = t.map(Number);
|
|
@@ -3151,7 +3205,7 @@ function An(e) {
|
|
|
3151
3205
|
dist: s
|
|
3152
3206
|
};
|
|
3153
3207
|
}
|
|
3154
|
-
function
|
|
3208
|
+
function In(e) {
|
|
3155
3209
|
let t = (e, t) => +e.toFixed(t);
|
|
3156
3210
|
return [
|
|
3157
3211
|
t(e.e, 2),
|
|
@@ -3162,19 +3216,19 @@ function jn(e) {
|
|
|
3162
3216
|
t(e.dist, 1)
|
|
3163
3217
|
].join(",");
|
|
3164
3218
|
}
|
|
3165
|
-
function
|
|
3219
|
+
function Z(e, t, n = Y) {
|
|
3166
3220
|
let r = {
|
|
3167
3221
|
e: e.e,
|
|
3168
3222
|
n: e.n,
|
|
3169
3223
|
h: e.h,
|
|
3170
|
-
yaw:
|
|
3171
|
-
pitch:
|
|
3172
|
-
dist:
|
|
3224
|
+
yaw: Mn(e.yaw),
|
|
3225
|
+
pitch: jn(e.pitch, n.pitch),
|
|
3226
|
+
dist: jn(e.dist, n.dist)
|
|
3173
3227
|
};
|
|
3174
3228
|
if (t) {
|
|
3175
|
-
let e =
|
|
3229
|
+
let e = Q(r), i = Math.max(n.floor, t(e.e, e.n) + n.clearance);
|
|
3176
3230
|
if (e.h < i) return {
|
|
3177
|
-
...
|
|
3231
|
+
...Bn({
|
|
3178
3232
|
...e,
|
|
3179
3233
|
h: i
|
|
3180
3234
|
}, r),
|
|
@@ -3183,42 +3237,42 @@ function X(e, t, n = J) {
|
|
|
3183
3237
|
}
|
|
3184
3238
|
return r;
|
|
3185
3239
|
}
|
|
3186
|
-
function
|
|
3187
|
-
let n = Math.cos(t *
|
|
3240
|
+
function Ln(e, t) {
|
|
3241
|
+
let n = Math.cos(t * X);
|
|
3188
3242
|
return {
|
|
3189
|
-
e: Math.sin(e *
|
|
3190
|
-
n: Math.cos(e *
|
|
3191
|
-
h: Math.sin(t *
|
|
3243
|
+
e: Math.sin(e * X) * n,
|
|
3244
|
+
n: Math.cos(e * X) * n,
|
|
3245
|
+
h: Math.sin(t * X)
|
|
3192
3246
|
};
|
|
3193
3247
|
}
|
|
3194
|
-
function
|
|
3195
|
-
let t =
|
|
3248
|
+
function Q(e) {
|
|
3249
|
+
let t = Ln(e.yaw, e.pitch);
|
|
3196
3250
|
return {
|
|
3197
3251
|
e: e.e - t.e * e.dist,
|
|
3198
3252
|
n: e.n - t.n * e.dist,
|
|
3199
3253
|
h: e.h - t.h * e.dist
|
|
3200
3254
|
};
|
|
3201
3255
|
}
|
|
3202
|
-
function
|
|
3256
|
+
function Rn(e) {
|
|
3203
3257
|
return {
|
|
3204
|
-
...
|
|
3258
|
+
...Q(e),
|
|
3205
3259
|
yaw: e.yaw,
|
|
3206
3260
|
pitch: e.pitch,
|
|
3207
3261
|
fov: 45
|
|
3208
3262
|
};
|
|
3209
3263
|
}
|
|
3210
|
-
function
|
|
3211
|
-
let r =
|
|
3264
|
+
function zn(e, t, n) {
|
|
3265
|
+
let r = Q(e), [i, a, o] = [
|
|
3212
3266
|
n.e - r.e,
|
|
3213
3267
|
n.n - r.n,
|
|
3214
3268
|
n.h - r.h
|
|
3215
|
-
], [s, c] = [Math.sin(e.yaw *
|
|
3269
|
+
], [s, c] = [Math.sin(e.yaw * X), Math.cos(e.yaw * X)], [l, u] = [Math.sin(e.pitch * X), Math.cos(e.pitch * X)], d = i * s + a * c, f = 2 * Math.tan(t * X / 2) * (d * u + o * l);
|
|
3216
3270
|
return {
|
|
3217
3271
|
x: (i * c - a * s) / f,
|
|
3218
3272
|
y: (d * l - o * u) / f
|
|
3219
3273
|
};
|
|
3220
3274
|
}
|
|
3221
|
-
function
|
|
3275
|
+
function Bn(e, t) {
|
|
3222
3276
|
let [n, r, i] = [
|
|
3223
3277
|
t.e - e.e,
|
|
3224
3278
|
t.n - e.n,
|
|
@@ -3228,17 +3282,17 @@ function Fn(e, t) {
|
|
|
3228
3282
|
e: t.e,
|
|
3229
3283
|
n: t.n,
|
|
3230
3284
|
h: t.h,
|
|
3231
|
-
yaw:
|
|
3232
|
-
pitch: Math.asin(i / a) /
|
|
3285
|
+
yaw: Mn(Math.atan2(n, r) / X),
|
|
3286
|
+
pitch: Math.asin(i / a) / X,
|
|
3233
3287
|
dist: a
|
|
3234
3288
|
};
|
|
3235
3289
|
}
|
|
3236
|
-
function
|
|
3237
|
-
let i =
|
|
3290
|
+
function Vn(e, t, n, r = Y) {
|
|
3291
|
+
let i = Q(e), a = Z({
|
|
3238
3292
|
...e,
|
|
3239
3293
|
yaw: t,
|
|
3240
3294
|
pitch: n
|
|
3241
|
-
}, void 0, r), o =
|
|
3295
|
+
}, void 0, r), o = Ln(a.yaw, a.pitch);
|
|
3242
3296
|
return {
|
|
3243
3297
|
...a,
|
|
3244
3298
|
e: i.e + o.e * a.dist,
|
|
@@ -3246,11 +3300,11 @@ function In(e, t, n, r = J) {
|
|
|
3246
3300
|
h: i.h + o.h * a.dist
|
|
3247
3301
|
};
|
|
3248
3302
|
}
|
|
3249
|
-
function
|
|
3250
|
-
return e.dist * Math.max(Math.sin(-e.pitch *
|
|
3303
|
+
function Hn(e) {
|
|
3304
|
+
return e.dist * Math.max(Math.sin(-e.pitch * X), En);
|
|
3251
3305
|
}
|
|
3252
|
-
function
|
|
3253
|
-
let [i, a] = [Math.sin(e.yaw *
|
|
3306
|
+
function Un(e, t, n, r) {
|
|
3307
|
+
let [i, a] = [Math.sin(e.yaw * X), Math.cos(e.yaw * X)];
|
|
3254
3308
|
return {
|
|
3255
3309
|
...e,
|
|
3256
3310
|
e: e.e + t * a + n * i,
|
|
@@ -3258,20 +3312,20 @@ function Rn(e, t, n, r) {
|
|
|
3258
3312
|
h: e.h + r
|
|
3259
3313
|
};
|
|
3260
3314
|
}
|
|
3261
|
-
function
|
|
3262
|
-
return
|
|
3315
|
+
function Wn(e, t, n) {
|
|
3316
|
+
return Un(e, t, n * e.dist / Hn(e), 0);
|
|
3263
3317
|
}
|
|
3264
|
-
function
|
|
3318
|
+
function Gn(e, t, n) {
|
|
3265
3319
|
return {
|
|
3266
3320
|
e: e.e + (t.e - e.e) * n,
|
|
3267
3321
|
n: e.n + (t.n - e.n) * n,
|
|
3268
3322
|
h: e.h + (t.h - e.h) * n,
|
|
3269
|
-
yaw:
|
|
3323
|
+
yaw: Mn(e.yaw + Nn(e.yaw, t.yaw) * n),
|
|
3270
3324
|
pitch: e.pitch + (t.pitch - e.pitch) * n,
|
|
3271
3325
|
dist: e.dist * (t.dist / e.dist) ** n
|
|
3272
3326
|
};
|
|
3273
3327
|
}
|
|
3274
|
-
function
|
|
3328
|
+
function Kn(e, t) {
|
|
3275
3329
|
let n = ([e, t]) => (e + t) / 2, r = Math.hypot(e.e[1] - e.e[0], e.n[1] - e.n[0], e.h[1] - e.h[0]) / 2;
|
|
3276
3330
|
return {
|
|
3277
3331
|
e: n(e.e),
|
|
@@ -3279,17 +3333,17 @@ function Bn(e, t) {
|
|
|
3279
3333
|
h: n(e.h),
|
|
3280
3334
|
yaw: t.yaw,
|
|
3281
3335
|
pitch: t.pitch,
|
|
3282
|
-
dist:
|
|
3336
|
+
dist: Dn * r / Math.sin(45 * X / 2)
|
|
3283
3337
|
};
|
|
3284
3338
|
}
|
|
3285
|
-
function
|
|
3286
|
-
let n = Math.hypot(t.e - e.e, t.n - e.n), r = Math.log1p(n / Math.min(e.dist, t.dist)) + Math.abs(Math.log(t.dist / e.dist)), i = Math.log1p(
|
|
3339
|
+
function qn(e, t) {
|
|
3340
|
+
let n = Math.hypot(t.e - e.e, t.n - e.n), r = Math.log1p(n / Math.min(e.dist, t.dist)) + Math.abs(Math.log(t.dist / e.dist)), i = Math.log1p(An * n / Math.max(e.dist, t.dist));
|
|
3287
3341
|
return {
|
|
3288
|
-
ms:
|
|
3342
|
+
ms: jn(On[0] + kn * r, On),
|
|
3289
3343
|
at(n) {
|
|
3290
3344
|
if (n <= 0) return e;
|
|
3291
3345
|
if (n >= 1) return t;
|
|
3292
|
-
let r = n * n * (3 - 2 * n), a =
|
|
3346
|
+
let r = n * n * (3 - 2 * n), a = Gn(e, t, r);
|
|
3293
3347
|
return {
|
|
3294
3348
|
...a,
|
|
3295
3349
|
dist: a.dist * Math.exp(4 * i * r * (1 - r))
|
|
@@ -3297,17 +3351,17 @@ function Vn(e, t) {
|
|
|
3297
3351
|
}
|
|
3298
3352
|
};
|
|
3299
3353
|
}
|
|
3300
|
-
function
|
|
3354
|
+
function Jn(e, t) {
|
|
3301
3355
|
let n = e.dist * 1e-5;
|
|
3302
|
-
return Math.abs(e.e - t.e) < n && Math.abs(e.n - t.n) < n && Math.abs(e.h - t.h) < n && Math.abs(e.dist - t.dist) < n && Math.abs(
|
|
3356
|
+
return Math.abs(e.e - t.e) < n && Math.abs(e.n - t.n) < n && Math.abs(e.h - t.h) < n && Math.abs(e.dist - t.dist) < n && Math.abs(Nn(e.yaw, t.yaw)) < .001 && Math.abs(e.pitch - t.pitch) < .001;
|
|
3303
3357
|
}
|
|
3304
3358
|
//#endregion
|
|
3305
3359
|
//#region src/controls/controls.ts
|
|
3306
|
-
var
|
|
3307
|
-
function
|
|
3360
|
+
var Yn = .2, Xn = .002, Zn = .005, Qn = .5, $n = .05;
|
|
3361
|
+
function er(e, t) {
|
|
3308
3362
|
return 2 * e * Math.tan(45 * Math.PI / 360) / Math.max(1, t);
|
|
3309
3363
|
}
|
|
3310
|
-
function
|
|
3364
|
+
function tr(e) {
|
|
3311
3365
|
let t = (t) => +!!e.has(t);
|
|
3312
3366
|
return [
|
|
3313
3367
|
t("KeyD") - t("KeyA") + t("ArrowRight") - t("ArrowLeft"),
|
|
@@ -3315,10 +3369,10 @@ function Yn(e) {
|
|
|
3315
3369
|
t("KeyE") - t("KeyQ")
|
|
3316
3370
|
];
|
|
3317
3371
|
}
|
|
3318
|
-
function
|
|
3319
|
-
return
|
|
3372
|
+
function nr(e, t, n, r, i = Y) {
|
|
3373
|
+
return Jn(e, t) ? t : Z(Gn(e, t, 1 - Math.exp(-n / $n)), r, i);
|
|
3320
3374
|
}
|
|
3321
|
-
var
|
|
3375
|
+
var rr = class {
|
|
3322
3376
|
enabled = !0;
|
|
3323
3377
|
#e;
|
|
3324
3378
|
#t;
|
|
@@ -3337,7 +3391,7 @@ var Zn = class {
|
|
|
3337
3391
|
#m = /* @__PURE__ */ new Set();
|
|
3338
3392
|
#h;
|
|
3339
3393
|
#g = null;
|
|
3340
|
-
constructor(e, t, n, r, i =
|
|
3394
|
+
constructor(e, t, n, r, i = Y) {
|
|
3341
3395
|
this.#e = e, this.#t = t, this.#n = n, this.#r = i, this.#d = this.#j(r), this.#f = this.#d, this.#h = t.onFrame(this.#D);
|
|
3342
3396
|
let a = this.#i.signal;
|
|
3343
3397
|
e.addEventListener("pointerdown", this.#_, { signal: a }), e.addEventListener("pointermove", this.#v, { signal: a });
|
|
@@ -3358,7 +3412,7 @@ var Zn = class {
|
|
|
3358
3412
|
return this.#m.add(e), () => this.#m.delete(e);
|
|
3359
3413
|
}
|
|
3360
3414
|
moveTo(e, t) {
|
|
3361
|
-
let n = this.#d, r = Math.min(n.dist,
|
|
3415
|
+
let n = this.#d, r = Math.min(n.dist, Tn.dist);
|
|
3362
3416
|
this.#O(this.#j({
|
|
3363
3417
|
...n,
|
|
3364
3418
|
e,
|
|
@@ -3382,7 +3436,7 @@ var Zn = class {
|
|
|
3382
3436
|
let i = () => this.#k(!1);
|
|
3383
3437
|
return new Promise((t) => {
|
|
3384
3438
|
this.#p = {
|
|
3385
|
-
path:
|
|
3439
|
+
path: qn(r, this.#j({
|
|
3386
3440
|
...r,
|
|
3387
3441
|
...e
|
|
3388
3442
|
})),
|
|
@@ -3412,7 +3466,7 @@ var Zn = class {
|
|
|
3412
3466
|
e.buttons & 6 || t && e.shiftKey ? $(this.#c, r, i) : t && $(this.#s, r, i);
|
|
3413
3467
|
} else if (n) {
|
|
3414
3468
|
let e = this.#T();
|
|
3415
|
-
$(this.#c, e.x - n.x, e.y - n.y), this.#l += (n.d - e.d) *
|
|
3469
|
+
$(this.#c, e.x - n.x, e.y - n.y), this.#l += (n.d - e.d) * Zn;
|
|
3416
3470
|
} else $(this.#s, r, i);
|
|
3417
3471
|
this.#E();
|
|
3418
3472
|
};
|
|
@@ -3420,7 +3474,7 @@ var Zn = class {
|
|
|
3420
3474
|
this.#a.delete(e.pointerId);
|
|
3421
3475
|
};
|
|
3422
3476
|
#b = (e) => {
|
|
3423
|
-
this.#w(e) && (e.preventDefault(), this.#l += e.deltaY *
|
|
3477
|
+
this.#w(e) && (e.preventDefault(), this.#l += e.deltaY * Xn, this.#E());
|
|
3424
3478
|
};
|
|
3425
3479
|
#x = (e) => {
|
|
3426
3480
|
this.#w(e) && (e.code === "KeyF" && !e.repeat && (this.#u = !this.#u), this.#o.add(e.code), this.#u && this.#E());
|
|
@@ -3432,12 +3486,12 @@ var Zn = class {
|
|
|
3432
3486
|
if (!this.#w(e)) return;
|
|
3433
3487
|
let t = await this.#t.pick(e.offsetX, e.offsetY);
|
|
3434
3488
|
if (!t || this.#i.signal.aborted) return;
|
|
3435
|
-
let [n, r, i] = t.point, a =
|
|
3489
|
+
let [n, r, i] = t.point, a = Bn(Q(this.#f), {
|
|
3436
3490
|
e: n,
|
|
3437
3491
|
n: r,
|
|
3438
3492
|
h: i
|
|
3439
3493
|
});
|
|
3440
|
-
this.#O(
|
|
3494
|
+
this.#O(Z(a, void 0, this.#r));
|
|
3441
3495
|
};
|
|
3442
3496
|
#w(e) {
|
|
3443
3497
|
return this.enabled && !e.defaultPrevented;
|
|
@@ -3459,26 +3513,26 @@ var Zn = class {
|
|
|
3459
3513
|
this.#g = e;
|
|
3460
3514
|
let n = this.#d, [r, i] = this.#c;
|
|
3461
3515
|
if (r || i) {
|
|
3462
|
-
let e =
|
|
3463
|
-
n =
|
|
3516
|
+
let e = er(n.dist, this.#e.clientHeight);
|
|
3517
|
+
n = Wn(n, -r * e, i * e);
|
|
3464
3518
|
}
|
|
3465
3519
|
let [a, o] = this.#s;
|
|
3466
3520
|
if (a || o) {
|
|
3467
|
-
let [e, t] = [n.yaw + a *
|
|
3468
|
-
n = this.#u ?
|
|
3521
|
+
let [e, t] = [n.yaw + a * Yn, n.pitch - o * Yn];
|
|
3522
|
+
n = this.#u ? Vn(n, e, t, this.#r) : Z({
|
|
3469
3523
|
...n,
|
|
3470
3524
|
yaw: e,
|
|
3471
3525
|
pitch: t
|
|
3472
3526
|
}, void 0, this.#r);
|
|
3473
3527
|
}
|
|
3474
|
-
this.#l && (n =
|
|
3528
|
+
this.#l && (n = Z({
|
|
3475
3529
|
...n,
|
|
3476
3530
|
dist: n.dist * Math.exp(this.#l)
|
|
3477
3531
|
}, void 0, this.#r)), this.#c = [0, 0], this.#s = [0, 0], this.#l = 0;
|
|
3478
|
-
let [s, c, l] =
|
|
3532
|
+
let [s, c, l] = tr(this.#o), u = this.enabled && this.#u && (s !== 0 || l !== 0 || c !== 0);
|
|
3479
3533
|
if (u) {
|
|
3480
|
-
let e =
|
|
3481
|
-
n =
|
|
3534
|
+
let e = Qn * Hn(n) * t;
|
|
3535
|
+
n = Un(n, s * e, c * e, l * e);
|
|
3482
3536
|
}
|
|
3483
3537
|
let d = this.#f;
|
|
3484
3538
|
n !== this.#d && this.#k(!1);
|
|
@@ -3487,7 +3541,7 @@ var Zn = class {
|
|
|
3487
3541
|
f.start ??= e;
|
|
3488
3542
|
let t = Math.min(1, (e - f.start) / f.path.ms);
|
|
3489
3543
|
this.#d = this.#f = this.#j(f.path.at(t)), t === 1 && this.#k(!0);
|
|
3490
|
-
} else d !== n && (this.#d = n = this.#j(n), this.#f =
|
|
3544
|
+
} else d !== n && (this.#d = n = this.#j(n), this.#f = nr(d, n, t, this.#n, this.#r));
|
|
3491
3545
|
this.#f !== d && this.#A(), u || this.#p || this.#f !== this.#d ? this.#E() : this.#g = null;
|
|
3492
3546
|
};
|
|
3493
3547
|
#O(e) {
|
|
@@ -3503,14 +3557,14 @@ var Zn = class {
|
|
|
3503
3557
|
for (let t of this.#m) t(e);
|
|
3504
3558
|
}
|
|
3505
3559
|
#j(e) {
|
|
3506
|
-
return
|
|
3560
|
+
return Z(e, this.#n, this.#r);
|
|
3507
3561
|
}
|
|
3508
3562
|
#M() {
|
|
3509
|
-
this.#t.setCamera(
|
|
3563
|
+
this.#t.setCamera(Rn(this.#f));
|
|
3510
3564
|
}
|
|
3511
3565
|
};
|
|
3512
3566
|
function $(e, t, n) {
|
|
3513
3567
|
e[0] += t, e[1] += n;
|
|
3514
3568
|
}
|
|
3515
3569
|
//#endregion
|
|
3516
|
-
export {
|
|
3570
|
+
export { wt as C, Zt as S, Fn as _, Q as a, Rn as b, Kn as c, In as d, Hn as f, Wn as g, Pn as h, Gn as i, qn as l, Bn as m, wn as n, Z as o, Vn as p, Y as r, Tn as s, rr as t, Un as u, zn as v, be as w, Xt as x, Jn as y };
|