mirror of
https://github.com/storytold/spark.git
synced 2026-10-09 00:09:53 +00:00
10966 lines
510 KiB
JavaScript
10966 lines
510 KiB
JavaScript
import * as u from "three";
|
|
import { Mesh as Qo, OrthographicCamera as po, BufferGeometry as fo, Float32BufferAttribute as us, Loader as yo, FileLoader as wo, Quaternion as hs, Vector3 as _A, Color as Cs, Matrix4 as De } from "three";
|
|
const mo = new po(-1, 1, 1, -1, 0, 1);
|
|
class xo extends fo {
|
|
constructor() {
|
|
super(), this.setAttribute("position", new us([-1, 3, 0, -1, -1, 0, 3, -1, 0], 3)), this.setAttribute("uv", new us([0, 2, 0, 0, 2, 0], 2));
|
|
}
|
|
}
|
|
const So = new xo();
|
|
class xs {
|
|
/**
|
|
* Constructs a new full screen quad.
|
|
*
|
|
* @param {?Material} material - The material to render te full screen quad with.
|
|
*/
|
|
constructor(A) {
|
|
this._mesh = new Qo(So, A);
|
|
}
|
|
/**
|
|
* Frees the GPU-related resources allocated by this instance. Call this
|
|
* method whenever the instance is no longer used in your app.
|
|
*/
|
|
dispose() {
|
|
this._mesh.geometry.dispose();
|
|
}
|
|
/**
|
|
* Renders the full screen quad.
|
|
*
|
|
* @param {WebGLRenderer} renderer - The renderer.
|
|
*/
|
|
render(A) {
|
|
A.render(this._mesh, mo);
|
|
}
|
|
/**
|
|
* The quad's material.
|
|
*
|
|
* @type {?Material}
|
|
*/
|
|
get material() {
|
|
return this._mesh.material;
|
|
}
|
|
set material(A) {
|
|
this._mesh.material = A;
|
|
}
|
|
}
|
|
var uA = Uint8Array, mt = Uint16Array, Do = Int32Array, Ss = new uA([
|
|
0,
|
|
0,
|
|
0,
|
|
0,
|
|
0,
|
|
0,
|
|
0,
|
|
0,
|
|
1,
|
|
1,
|
|
1,
|
|
1,
|
|
2,
|
|
2,
|
|
2,
|
|
2,
|
|
3,
|
|
3,
|
|
3,
|
|
3,
|
|
4,
|
|
4,
|
|
4,
|
|
4,
|
|
5,
|
|
5,
|
|
5,
|
|
5,
|
|
0,
|
|
/* unused */
|
|
0,
|
|
0,
|
|
/* impossible */
|
|
0
|
|
]), Ds = new uA([
|
|
0,
|
|
0,
|
|
0,
|
|
0,
|
|
1,
|
|
1,
|
|
2,
|
|
2,
|
|
3,
|
|
3,
|
|
4,
|
|
4,
|
|
5,
|
|
5,
|
|
6,
|
|
6,
|
|
7,
|
|
7,
|
|
8,
|
|
8,
|
|
9,
|
|
9,
|
|
10,
|
|
10,
|
|
11,
|
|
11,
|
|
12,
|
|
12,
|
|
13,
|
|
13,
|
|
/* unused */
|
|
0,
|
|
0
|
|
]), Mo = new uA([16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15]), Ms = function(t, A) {
|
|
for (var e = new mt(31), s = 0; s < 31; ++s)
|
|
e[s] = A += 1 << t[s - 1];
|
|
for (var n = new Do(e[30]), s = 1; s < 30; ++s)
|
|
for (var i = e[s]; i < e[s + 1]; ++i)
|
|
n[i] = i - e[s] << 5 | s;
|
|
return { b: e, r: n };
|
|
}, vs = Ms(Ss, 2), bs = vs.b, vo = vs.r;
|
|
bs[28] = 258, vo[258] = 28;
|
|
var bo = Ms(Ds, 0), Fo = bo.b, Ue = new mt(32768);
|
|
for (var sA = 0; sA < 32768; ++sA) {
|
|
var At = (sA & 43690) >> 1 | (sA & 21845) << 1;
|
|
At = (At & 52428) >> 2 | (At & 13107) << 2, At = (At & 61680) >> 4 | (At & 3855) << 4, Ue[sA] = ((At & 65280) >> 8 | (At & 255) << 8) >> 1;
|
|
}
|
|
var Lt = function(t, A, e) {
|
|
for (var s = t.length, n = 0, i = new mt(A); n < s; ++n)
|
|
t[n] && ++i[t[n] - 1];
|
|
var r = new mt(A);
|
|
for (n = 1; n < A; ++n)
|
|
r[n] = r[n - 1] + i[n - 1] << 1;
|
|
var a;
|
|
if (e) {
|
|
a = new mt(1 << A);
|
|
var o = 15 - A;
|
|
for (n = 0; n < s; ++n)
|
|
if (t[n])
|
|
for (var g = n << 4 | t[n], l = A - t[n], c = r[t[n] - 1]++ << l, I = c | (1 << l) - 1; c <= I; ++c)
|
|
a[Ue[c] >> o] = g;
|
|
} else
|
|
for (a = new mt(s), n = 0; n < s; ++n)
|
|
t[n] && (a[n] = Ue[r[t[n] - 1]++] >> 15 - t[n]);
|
|
return a;
|
|
}, Pt = new uA(288);
|
|
for (var sA = 0; sA < 144; ++sA)
|
|
Pt[sA] = 8;
|
|
for (var sA = 144; sA < 256; ++sA)
|
|
Pt[sA] = 9;
|
|
for (var sA = 256; sA < 280; ++sA)
|
|
Pt[sA] = 7;
|
|
for (var sA = 280; sA < 288; ++sA)
|
|
Pt[sA] = 8;
|
|
var Fs = new uA(32);
|
|
for (var sA = 0; sA < 32; ++sA)
|
|
Fs[sA] = 5;
|
|
var No = /* @__PURE__ */ Lt(Pt, 9, 1), ko = /* @__PURE__ */ Lt(Fs, 5, 1), Me = function(t) {
|
|
for (var A = t[0], e = 1; e < t.length; ++e)
|
|
t[e] > A && (A = t[e]);
|
|
return A;
|
|
}, JA = function(t, A, e) {
|
|
var s = A / 8 | 0;
|
|
return (t[s] | t[s + 1] << 8) >> (A & 7) & e;
|
|
}, ve = function(t, A) {
|
|
var e = A / 8 | 0;
|
|
return (t[e] | t[e + 1] << 8 | t[e + 2] << 16) >> (A & 7);
|
|
}, Ns = function(t) {
|
|
return (t + 7) / 8 | 0;
|
|
}, Mt = function(t, A, e) {
|
|
return (A == null || A < 0) && (A = 0), (e == null || e > t.length) && (e = t.length), new uA(t.subarray(A, e));
|
|
}, To = [
|
|
"unexpected EOF",
|
|
"invalid block type",
|
|
"invalid length/literal",
|
|
"invalid distance",
|
|
"stream finished",
|
|
"no stream handler",
|
|
,
|
|
"no callback",
|
|
"invalid UTF-8 data",
|
|
"extra field too long",
|
|
"date not in range 1980-2099",
|
|
"filename too long",
|
|
"stream finishing",
|
|
"invalid zip data"
|
|
// determined by unknown compression method
|
|
], yA = function(t, A, e) {
|
|
var s = new Error(A || To[t]);
|
|
if (s.code = t, Error.captureStackTrace && Error.captureStackTrace(s, yA), !e)
|
|
throw s;
|
|
return s;
|
|
}, ks = function(t, A, e, s) {
|
|
var n = t.length, i = s ? s.length : 0;
|
|
if (!n || A.f && !A.l)
|
|
return e || new uA(0);
|
|
var r = !e, a = r || A.i != 2, o = A.i;
|
|
r && (e = new uA(n * 3));
|
|
var g = function(dA) {
|
|
var xA = e.length;
|
|
if (dA > xA) {
|
|
var CA = new uA(Math.max(xA * 2, dA));
|
|
CA.set(e), e = CA;
|
|
}
|
|
}, l = A.f || 0, c = A.p || 0, I = A.b || 0, h = A.l, E = A.d, C = A.m, B = A.n, Q = n * 8;
|
|
do {
|
|
if (!h) {
|
|
l = JA(t, c, 1);
|
|
var f = JA(t, c + 1, 3);
|
|
if (c += 3, f)
|
|
if (f == 1)
|
|
h = No, E = ko, C = 9, B = 5;
|
|
else if (f == 2) {
|
|
var D = JA(t, c, 31) + 257, x = JA(t, c + 10, 15) + 4, w = D + JA(t, c + 5, 31) + 1;
|
|
c += 14;
|
|
for (var m = new uA(w), k = new uA(19), M = 0; M < x; ++M)
|
|
k[Mo[M]] = JA(t, c + M * 3, 7);
|
|
c += x * 3;
|
|
for (var S = Me(k), U = (1 << S) - 1, F = Lt(k, S, 1), M = 0; M < w; ) {
|
|
var b = F[JA(t, c, U)];
|
|
c += b & 15;
|
|
var p = b >> 4;
|
|
if (p < 16)
|
|
m[M++] = p;
|
|
else {
|
|
var T = 0, R = 0;
|
|
for (p == 16 ? (R = 3 + JA(t, c, 3), c += 2, T = m[M - 1]) : p == 17 ? (R = 3 + JA(t, c, 7), c += 3) : p == 18 && (R = 11 + JA(t, c, 127), c += 7); R--; )
|
|
m[M++] = T;
|
|
}
|
|
}
|
|
var X = m.subarray(0, D), _ = m.subarray(D);
|
|
C = Me(X), B = Me(_), h = Lt(X, C, 1), E = Lt(_, B, 1);
|
|
} else
|
|
yA(1);
|
|
else {
|
|
var p = Ns(c) + 4, d = t[p - 4] | t[p - 3] << 8, y = p + d;
|
|
if (y > n) {
|
|
o && yA(0);
|
|
break;
|
|
}
|
|
a && g(I + d), e.set(t.subarray(p, y), I), A.b = I += d, A.p = c = y * 8, A.f = l;
|
|
continue;
|
|
}
|
|
if (c > Q) {
|
|
o && yA(0);
|
|
break;
|
|
}
|
|
}
|
|
a && g(I + 131072);
|
|
for (var eA = (1 << C) - 1, q = (1 << B) - 1, O = c; ; O = c) {
|
|
var T = h[ve(t, c) & eA], L = T >> 4;
|
|
if (c += T & 15, c > Q) {
|
|
o && yA(0);
|
|
break;
|
|
}
|
|
if (T || yA(2), L < 256)
|
|
e[I++] = L;
|
|
else if (L == 256) {
|
|
O = c, h = null;
|
|
break;
|
|
} else {
|
|
var j = L - 254;
|
|
if (L > 264) {
|
|
var M = L - 257, P = Ss[M];
|
|
j = JA(t, c, (1 << P) - 1) + bs[M], c += P;
|
|
}
|
|
var W = E[ve(t, c) & q], G = W >> 4;
|
|
W || yA(3), c += W & 15;
|
|
var _ = Fo[G];
|
|
if (G > 3) {
|
|
var P = Ds[G];
|
|
_ += ve(t, c) & (1 << P) - 1, c += P;
|
|
}
|
|
if (c > Q) {
|
|
o && yA(0);
|
|
break;
|
|
}
|
|
a && g(I + 131072);
|
|
var pA = I + j;
|
|
if (I < _) {
|
|
var gA = i - _, fA = Math.min(_, pA);
|
|
for (gA + I < 0 && yA(3); I < fA; ++I)
|
|
e[I] = s[gA + I];
|
|
}
|
|
for (; I < pA; ++I)
|
|
e[I] = e[I - _];
|
|
}
|
|
}
|
|
A.l = h, A.p = O, A.b = I, A.f = l, h && (l = 1, A.m = C, A.d = E, A.n = B);
|
|
} while (!l);
|
|
return I != e.length && r ? Mt(e, 0, I) : e.subarray(0, I);
|
|
}, Uo = /* @__PURE__ */ new uA(0), qA = function(t, A) {
|
|
return t[A] | t[A + 1] << 8;
|
|
}, LA = function(t, A) {
|
|
return (t[A] | t[A + 1] << 8 | t[A + 2] << 16 | t[A + 3] << 24) >>> 0;
|
|
}, be = function(t, A) {
|
|
return LA(t, A) + LA(t, A + 4) * 4294967296;
|
|
}, Go = function(t) {
|
|
(t[0] != 31 || t[1] != 139 || t[2] != 8) && yA(6, "invalid gzip data");
|
|
var A = t[3], e = 10;
|
|
A & 4 && (e += (t[10] | t[11] << 8) + 2);
|
|
for (var s = (A >> 3 & 1) + (A >> 4 & 1); s > 0; s -= !t[e++])
|
|
;
|
|
return e + (A & 2);
|
|
}, Fe = /* @__PURE__ */ function() {
|
|
function t(A, e) {
|
|
typeof A == "function" && (e = A, A = {}), this.ondata = e;
|
|
var s = A && A.dictionary && A.dictionary.subarray(-32768);
|
|
this.s = { i: 0, b: s ? s.length : 0 }, this.o = new uA(32768), this.p = new uA(0), s && this.o.set(s);
|
|
}
|
|
return t.prototype.e = function(A) {
|
|
if (this.ondata || yA(5), this.d && yA(4), !this.p.length)
|
|
this.p = A;
|
|
else if (A.length) {
|
|
var e = new uA(this.p.length + A.length);
|
|
e.set(this.p), e.set(A, this.p.length), this.p = e;
|
|
}
|
|
}, t.prototype.c = function(A) {
|
|
this.s.i = +(this.d = A || !1);
|
|
var e = this.s.b, s = ks(this.p, this.s, this.o);
|
|
this.ondata(Mt(s, e, this.s.b), this.d), this.o = Mt(s, this.s.b - 32768), this.s.b = this.o.length, this.p = Mt(this.p, this.s.p / 8 | 0), this.s.p &= 7;
|
|
}, t.prototype.push = function(A, e) {
|
|
this.e(A), this.c(e);
|
|
}, t;
|
|
}();
|
|
function Ro(t, A) {
|
|
return ks(t, { i: 2 }, A && A.out, A && A.dictionary);
|
|
}
|
|
var Yo = /* @__PURE__ */ function() {
|
|
function t(A, e) {
|
|
this.v = 1, this.r = 0, Fe.call(this, A, e);
|
|
}
|
|
return t.prototype.push = function(A, e) {
|
|
if (Fe.prototype.e.call(this, A), this.r += A.length, this.v) {
|
|
var s = this.p.subarray(this.v - 1), n = s.length > 3 ? Go(s) : 4;
|
|
if (n > s.length) {
|
|
if (!e)
|
|
return;
|
|
} else this.v > 1 && this.onmember && this.onmember(this.r - s.length);
|
|
this.p = s.subarray(n), this.v = 0;
|
|
}
|
|
Fe.prototype.c.call(this, e), this.s.f && !this.s.l && !e && (this.v = Ns(this.s.p) + 9, this.s = { i: 0 }, this.o = new uA(0), this.push(new uA(0), e));
|
|
}, t;
|
|
}(), Ge = typeof TextDecoder < "u" && /* @__PURE__ */ new TextDecoder(), Jo = 0;
|
|
try {
|
|
Ge.decode(Uo, { stream: !0 }), Jo = 1;
|
|
} catch {
|
|
}
|
|
var _o = function(t) {
|
|
for (var A = "", e = 0; ; ) {
|
|
var s = t[e++], n = (s > 127) + (s > 223) + (s > 239);
|
|
if (e + n > t.length)
|
|
return { s: A, r: Mt(t, e - 1) };
|
|
n ? n == 3 ? (s = ((s & 15) << 18 | (t[e++] & 63) << 12 | (t[e++] & 63) << 6 | t[e++] & 63) - 65536, A += String.fromCharCode(55296 | s >> 10, 56320 | s & 1023)) : n & 1 ? A += String.fromCharCode((s & 31) << 6 | t[e++] & 63) : A += String.fromCharCode((s & 15) << 12 | (t[e++] & 63) << 6 | t[e++] & 63) : A += String.fromCharCode(s);
|
|
}
|
|
};
|
|
function Lo(t, A) {
|
|
if (A) {
|
|
for (var e = "", s = 0; s < t.length; s += 16384)
|
|
e += String.fromCharCode.apply(null, t.subarray(s, s + 16384));
|
|
return e;
|
|
} else {
|
|
if (Ge)
|
|
return Ge.decode(t);
|
|
var n = _o(t), i = n.s, e = n.r;
|
|
return e.length && yA(8), i;
|
|
}
|
|
}
|
|
var zo = function(t, A) {
|
|
return A + 30 + qA(t, A + 26) + qA(t, A + 28);
|
|
}, Ho = function(t, A, e) {
|
|
var s = qA(t, A + 28), n = Lo(t.subarray(A + 46, A + 46 + s), !(qA(t, A + 8) & 2048)), i = A + 46 + s, r = LA(t, A + 20), a = e && r == 4294967295 ? qo(t, i) : [r, LA(t, A + 24), LA(t, A + 42)], o = a[0], g = a[1], l = a[2];
|
|
return [qA(t, A + 10), o, g, n, i + qA(t, A + 30) + qA(t, A + 32), l];
|
|
}, qo = function(t, A) {
|
|
for (; qA(t, A) != 1; A += 4 + qA(t, A + 2))
|
|
;
|
|
return [be(t, A + 12), be(t, A + 4), be(t, A + 20)];
|
|
};
|
|
function Ko(t, A) {
|
|
for (var e = {}, s = t.length - 22; LA(t, s) != 101010256; --s)
|
|
(!s || t.length - s > 65558) && yA(13);
|
|
var n = qA(t, s + 8);
|
|
if (!n)
|
|
return {};
|
|
var i = LA(t, s + 16), r = i == 4294967295 || n == 65535;
|
|
if (r) {
|
|
var a = LA(t, s - 12);
|
|
r = LA(t, a) == 101075792, r && (n = LA(t, a + 32), i = LA(t, a + 48));
|
|
}
|
|
for (var o = A && A.filter, g = 0; g < n; ++g) {
|
|
var l = Ho(t, i, r), c = l[0], I = l[1], h = l[2], E = l[3], C = l[4], B = l[5], Q = zo(t, B);
|
|
i = C, (!o || o({
|
|
name: E,
|
|
size: I,
|
|
originalSize: h,
|
|
compression: c
|
|
})) && (c ? c == 8 ? e[E] = Ro(t.subarray(Q, Q + I), { out: new uA(h) }) : yA(14, "unknown compression type " + c) : e[E] = Mt(t, Q, Q + I));
|
|
}
|
|
return e;
|
|
}
|
|
let XA;
|
|
const Ts = typeof TextDecoder < "u" ? new TextDecoder("utf-8", { ignoreBOM: !0, fatal: !0 }) : { decode: () => {
|
|
throw Error("TextDecoder not available");
|
|
} };
|
|
typeof TextDecoder < "u" && Ts.decode();
|
|
let Yt = null;
|
|
function $o() {
|
|
return (Yt === null || Yt.byteLength === 0) && (Yt = new Uint8Array(XA.memory.buffer)), Yt;
|
|
}
|
|
function Vo(t, A) {
|
|
return t = t >>> 0, Ts.decode($o().subarray(t, t + A));
|
|
}
|
|
function Po(t, A, e, s, n, i, r, a, o, g, l, c, I) {
|
|
return XA.raycast_splats(t, A, e, s, n, i, r, a, o, g, l, c, I);
|
|
}
|
|
async function Zo(t, A) {
|
|
if (typeof Response == "function" && t instanceof Response) {
|
|
if (typeof WebAssembly.instantiateStreaming == "function")
|
|
try {
|
|
return await WebAssembly.instantiateStreaming(t, A);
|
|
} catch (s) {
|
|
if (t.headers.get("Content-Type") != "application/wasm")
|
|
console.warn("`WebAssembly.instantiateStreaming` failed because your server does not serve Wasm with `application/wasm` MIME type. Falling back to `WebAssembly.instantiate` which is slower. Original error:\n", s);
|
|
else
|
|
throw s;
|
|
}
|
|
const e = await t.arrayBuffer();
|
|
return await WebAssembly.instantiate(e, A);
|
|
} else {
|
|
const e = await WebAssembly.instantiate(t, A);
|
|
return e instanceof WebAssembly.Instance ? { instance: e, module: t } : e;
|
|
}
|
|
}
|
|
function Xo() {
|
|
const t = {};
|
|
return t.wbg = {}, t.wbg.__wbg_buffer_609cc3eee51ed158 = function(A) {
|
|
return A.buffer;
|
|
}, t.wbg.__wbg_length_3b4f022188ae8db6 = function(A) {
|
|
return A.length;
|
|
}, t.wbg.__wbg_length_6ca527665d89694d = function(A) {
|
|
return A.length;
|
|
}, t.wbg.__wbg_length_8cfd2c6409af88ad = function(A) {
|
|
return A.length;
|
|
}, t.wbg.__wbg_new_9fee97a409b32b68 = function(A) {
|
|
return new Uint16Array(A);
|
|
}, t.wbg.__wbg_new_e3b321dcfef89fc7 = function(A) {
|
|
return new Uint32Array(A);
|
|
}, t.wbg.__wbg_newwithbyteoffsetandlength_e6b7e69acd4c7354 = function(A, e, s) {
|
|
return new Float32Array(A, e >>> 0, s >>> 0);
|
|
}, t.wbg.__wbg_newwithbyteoffsetandlength_f1dead44d1fc7212 = function(A, e, s) {
|
|
return new Uint32Array(A, e >>> 0, s >>> 0);
|
|
}, t.wbg.__wbg_newwithlength_5a5efe313cfd59f1 = function(A) {
|
|
return new Float32Array(A >>> 0);
|
|
}, t.wbg.__wbg_set_10bad9bee0e9c58b = function(A, e, s) {
|
|
A.set(e, s >>> 0);
|
|
}, t.wbg.__wbg_set_d23661d19148b229 = function(A, e, s) {
|
|
A.set(e, s >>> 0);
|
|
}, t.wbg.__wbg_set_f4f1f0daa30696fc = function(A, e, s) {
|
|
A.set(e, s >>> 0);
|
|
}, t.wbg.__wbg_subarray_3aaeec89bb2544f0 = function(A, e, s) {
|
|
return A.subarray(e >>> 0, s >>> 0);
|
|
}, t.wbg.__wbg_subarray_769e1e0f81bb259b = function(A, e, s) {
|
|
return A.subarray(e >>> 0, s >>> 0);
|
|
}, t.wbg.__wbindgen_init_externref_table = function() {
|
|
const A = XA.__wbindgen_export_0, e = A.grow(4);
|
|
A.set(0, void 0), A.set(e + 0, void 0), A.set(e + 1, null), A.set(e + 2, !0), A.set(e + 3, !1);
|
|
}, t.wbg.__wbindgen_memory = function() {
|
|
return XA.memory;
|
|
}, t.wbg.__wbindgen_throw = function(A, e) {
|
|
throw new Error(Vo(A, e));
|
|
}, t;
|
|
}
|
|
function Oo(t, A) {
|
|
return XA = t.exports, Us.__wbindgen_wasm_module = A, Yt = null, XA.__wbindgen_start(), XA;
|
|
}
|
|
async function Us(t) {
|
|
if (XA !== void 0) return XA;
|
|
typeof t < "u" && (Object.getPrototypeOf(t) === Object.prototype ? { module_or_path: t } = t : console.warn("using deprecated parameters for the initialization function; pass a single object instead")), typeof t > "u" && (t = new URL("data:application/wasm;base64,AGFzbQEAAAABzAEeYAJ/fwF/YAJ/fwBgA39/fwF/YAN/f38AYAF/AX9gAX8AYANvf38Bb2AFf39/f38Bf2AFf39/f38AYAFvAW9gA29vfwBgAW8Bf2AAAGAAAX9gBH9/f38AYAR/f39/AX9gA39vbwF/YAF/AW9gAAFvYAF9AX1gBn9/f39/fwBgDX19fX19fX19f29/fX0Bb2AGf39/f39/AX9gBX9/fX9/AGAEf31/fwBgBX9/fH9/AGAEf3x/fwBgBX9/fn9/AGAEf35/fwBgAn19AX0C8gQRA3diZx1fX3diZ19idWZmZXJfNjA5Y2MzZWVlNTFlZDE1OAAJA3diZxpfX3diZ19uZXdfOWZlZTk3YTQwOWIzMmI2OAAJA3diZxpfX3diZ19zZXRfZjRmMWYwZGFhMzA2OTZmYwAKA3diZx1fX3diZ19sZW5ndGhfOGNmZDJjNjQwOWFmODhhZAALA3diZzFfX3diZ19uZXd3aXRoYnl0ZW9mZnNldGFuZGxlbmd0aF9mMWRlYWQ0NGQxZmM3MjEyAAYDd2JnGl9fd2JnX25ld19lM2IzMjFkY2ZlZjg5ZmM3AAkDd2JnGl9fd2JnX3NldF9kMjM2NjFkMTkxNDhiMjI5AAoDd2JnHV9fd2JnX2xlbmd0aF82Y2E1Mjc2NjVkODk2OTRkAAsDd2JnMV9fd2JnX25ld3dpdGhieXRlb2Zmc2V0YW5kbGVuZ3RoX2U2YjdlNjlhY2Q0YzczNTQABgN3YmcaX193Ymdfc2V0XzEwYmFkOWJlZTBlOWM1OGIACgN3YmcdX193YmdfbGVuZ3RoXzNiNGYwMjIxODhhZThkYjYACwN3YmcfX193Ymdfc3ViYXJyYXlfNzY5ZTFlMGY4MWJiMjU5YgAGA3diZx9fX3diZ19zdWJhcnJheV8zYWFlZWM4OWJiMjU0NGYwAAYDd2JnJF9fd2JnX25ld3dpdGhsZW5ndGhfNWE1ZWZlMzEzY2ZkNTlmMQARA3diZxBfX3diaW5kZ2VuX3Rocm93AAEDd2JnEV9fd2JpbmRnZW5fbWVtb3J5ABIDd2JnH19fd2JpbmRnZW5faW5pdF9leHRlcm5yZWZfdGFibGUADANeXQQAAQcFAgMCEwEBAA0BAwEAAA0BAwgIAwEBBRQBAw4AAwEDAgwMAgABAQcDABUBFhcIGRsH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QYGABGxBEHYgBGohBCAHRQ0ACwJ/IAMgBkH8AXFBAnRqIgAoAgAiAUF/c0EHdiABQQZ2ckGBgoQIcSIBIAdBAUYNABogASAAKAIEIgFBf3NBB3YgAUEGdnJBgYKECHFqIgEgB0ECRg0AGiAAKAIIIgBBf3NBB3YgAEEGdnJBgYKECHEgAWoLIgFBCHZB/4EccSABQf+B/AdxakGBgARsQRB2IARqDwsgAUUEQEEADwsgAUEDcSEDAkAgAUEESQRADAELIAFBfHEhBQNAIAQgACACaiIBLAAAQb9/SmogAUEBaiwAAEG/f0pqIAFBAmosAABBv39KaiABQQNqLAAAQb9/SmohBCAFIAJBBGoiAkcNAAsLIANFDQAgACACaiEBA0AgBCABLAAAQb9/SmohBCABQQFqIQEgA0EBayIDDQALCyAEC4oGAQZ/IAAoAggiAyABSQRAIAEgAyICayIEIAAoAgAgAmtLBEAgACACIARBBEEEECYgACgCCCECCyAAKAIEIgYgAkECdGohBSAEQQJPBEAgASADQX9zakECdCIHBEAgBUEAIAf8CwALIAEgAmpBAnQgA0ECdGsgBmpBBGshBSACIARqQQFrIQILIAVBADYCACAAIAJBAWo2AggLIAAoAhQiAyABSQRAIAEgAyICayIEIAAoAgwgAmtLBEAgAEEMaiACIARBBEEEECYgACgCFCECCyAAKAIQIgYgAkECdGohBSAEQQJPBEAgASADQX9zakECdCIHBEAgBUEAIAf8CwALIAEgAmpBAnQgA0ECdGsgBmpBBGshBSACIARqQQFrIQILIAVBADYCACAAIAJBAWo2AhQLIAAoAjgiAyABSQRAIAEgAyICayIEIAAoAjAgAmtLBEAgAEEwaiACIARBBEEEECYgACgCOCECCyAAKAI0IgYgAkECdGohBSAEQQJPBEAgASADQX9zakECdCIHBEAgBUEAIAf8CwALIAEgAmpBAnQgA0ECdGsgBmpBBGshBSACIARqQQFrIQILIAVBADYCACAAIAJBAWo2AjgLIAAoAiAiA0H//wNNBEAgAyEBQYCABCADayICIAAoAhggA2tLBEAgAEEYaiADIAJBBEEEECYgACgCICEBCyAAKAIcIgUgAUECdCIEaiECIANB//8DRwRAQfz/DyADQQJ0IgZrIgcEQCACQQAgB/wLAAsg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IAQgA0EUahAvIAMoAghBAUcNASADKAIQIQAgAygCDAsgAEGEj8AAEEwACyADKAIMIQEgACAENgIAIAAgATYCBCADQSBqJAALuQEBBX8jAEEgayICJAAgACgCACIEQf////8BSwRAQQBBACABEEwACwJAQQQgBEEBdCIFIAVBBE0bIgVBAnQiBkH8////B00EfyACIAQEfyACIARBAnQ2AhwgAiAAKAIENgIUQQQFIAMLNgIYIAJBCGpBBCAGIAJBFGoQLyACKAIIQQFHDQEgAigCECEDIAIoAgwFIAMLIAMgARBMAAsgAigCDCEBIAAgBTYCACAAIAE2AgQgAkEgaiQAC8EBAgN/AX4jAEEwayICJAAgASgCAEGAgICAeEYEQCABKAIMIQMgAkEUaiIEQQA2AgAgAkKAgICAEDcCDCACQSBqIAMoAgAiA0EIaikCADcDACACQShqIANBEGopAgA3AwAgAiADKQIANwMYIAJBDGpBuIvAACACQRhqEBgaIAJBCGogBCgCACIDNgIAIAIgAikCDCIFNwMAIAFBCGogAzYCACABIAU3AgALIABB8I3AADYCBCAAIAE2AgAgAkEwaiQAC68BAQZ/AkACQCAAQYQBSQ0AIADQbyYBECMiASgCDCEFIAEoAhAhAiABQgA3AgwgASgCCCEDIAEoAgQhBCABQgQ3AgQgASgCACEGIAFBADYCACAAIAJJDQEgACACayIAIANPDQEgBCAAQQJ0aiAFNgIAIAEgAjYCECABIAA2AgwgASADNgIIIAEoAgQgASAENgIEIAEoAgAhACABIAY2AgAgAEUNACAAQQJ0EGALDwsAC6gBAQF/IwBBEGsiBiQAAkAgAQRAIAZBBGogASADIAQgBSACKAIQEQgAAkAgBigCBCICIAYoAgwiAU0EQCAGKAIIIQUMAQsgAkECdCECIAYoAgghAyABRQRAQQQhBSADIAIQYAwBCyADIAJBBCABQQJ0IgIQUCIFRQ0CCyAAIAE2AgQgACAFNgIAIAZBEGokAA8LQYyKwABBMhBjAAtBBCACQfyJwAAQTAALrQEBA38gASgCDCECAkACQAJAAkACQAJAIAEoAgQOAgABAgsgAg0BQQEhA0EAIQFBASECDAMLIAJFDQELIAAgARAbDwsgASgCACICKAIEIgFBAEgNASACKAIAIQMgAUUEQEEB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A0EAIAD8CwALIAsoAighFAJAIAsoAiwiEEUNACAQQQJ0IgBFDQAgFEEAIAD8CwALIBNBAnQhCSATBEAgCSEEIAohAANAAkAgACgCACIGQYCAgPwHTw0AIAwgBkF/cyIFQf//A3EiBksEQCADIAZBAnRqIgYgBigCAEEBajYCACAQIAVBEHYiBksEQCAUIAZBAnRqIgYgBigCAEEBajYCAAwCCyAGIBBB3InAABAxAAsgBiAMQcyJwAAQMQALIABBBGohACAEQQRrIgQNAAsLAkAgDEUEQEEAIQQMAQsgDEEBa0H/////A3EiAEEBaiIEQQdxIQUCQCAAQQdJBEBBACEEIAMhAAwBCyAEQfj///8HcSEGQQAhBCADIQADQCAAKAIAIQcgACAENgIAIABBBGoiESgCACESIBEgBCAHaiIENgIAIABBCGoiBygCACERIAcgBCASaiIENgIAIABBDGoiBygCACESIAcgBCARaiIENgIAIABBEGoiBygCACERIAcgBCASaiIENgIAIABBFGoiBygCACESIAcgBCARaiIENgIAIABBGGoiBygCACERIAcgBCASaiIENgIAIABBHGoiBygCACESIAcgBCARaiIENgIAIAQgEmohBCAAQSBqIQAgBkEIayIGDQALCyAFRQ0AA0AgACgCACEGIAAgBDYCACAAQQRqIQAgBCAGaiEEIAVBAWsiBQ0ACwsgDiAENgIEIBMEQCAJIApqIREgCkEEaiEGIBNBAWtB/////wNxQQFqIRIgCygCNCEXIAsoAjghB0EAIQUgCiEJA0AgBiEAAkAgCSgCACIJQYCAgPwHTw0AAkAgDCAJQX9zQf//A3EiCUsEQCADIAlBAnRqIgkoAgAiBiAHTw0BIBcgBkECdGogBTYCACAJIAkoAgBBAWo2AgAMAgsgCSAMQayJwAAQMQALIAYgB0G8icAAEDEACyAAIAAgEUdBAnRqIQYgACEJIBIgBUEBaiIFRw0ACwsCQCAQRQ0AIBBBAWtB/////wNxIgNBAWoiCUEHcSEGQQAhBSAUIQAgA0EHTwRAIAlB+P///wdxIQkDQCAAKAIAIQMgACAFNgIAIABBBGoiDCgCACEHIAwgAyAFaiIDNgIAIABBCGoiBSgCACEMIAUgAyAHaiIDNgIAIABBDGoiBSgCACEHIAUgAyAMaiIDNgIAIABB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uIvAACABEBgLDAAgACABKQIANwMACw0AIABB0I7AACABEBgLDQAgAUHIjsAAQQUQUQsZACAAIAFBkJbAACgCACIAQRQgABsRAQAACw0AIAFBpJDAAEEYEBYLoAIBA38gACgCACEAIwBBkAFrIgMkAAJ/AkAgASgCCCICQYCAgBBxRQRAIAJBgICAIHENASADQQhqIAAoAgAgA0EQahAfIAFBAUEAIAMoAgggAygCDBAUDAILIAAoAgAhAkEAIQADQCAAIANqQY8BaiACQQ9xIgRBMHIgBEHXAGogBEEKSRs6AAAgAEEBayEAIAJBD0sgAkEEdiECDQALIAFBt5LAAEECIAAgA2pBkAFqQQAgAGsQFAwBCyAAKAIAIQJBACEAA0AgACADakGPAWogAkEPcSIEQTByIARBN2ogBEEKSRs6AAAgAEEBayEAIAJBD0sgAkEEdiECDQALIAFBt5LAAEECIAAgA2pBkAFqQQAgAGsQFAsgA0GQAWokAAsJACAAQQA2AgALCAAgACUBEAMLCAAgACUBEAcLC/UUAwBBgIDAAAuhD3NwYXJrLWludGVybmFsLXJzL3NyYy9yYXljYXN0LnJzAHNwYXJrLWludGVybmFsLXJzL3NyYy9zb3J0LnJzAGxpYnJhcnkvYWxsb2Mvc3JjL2ZtdC5ycwAvaG9tZS9ydW5uZXIvLmNhcmdvL3JlZ2lzdHJ5L3NyYy9pbmRleC5jcmF0ZXMuaW8tMTk0OWNmOGM2YjViNTU3Zi93YXNtLWJpbmRnZW4tMC4yLjEwMC9zcmMvY29udmVydC9zbGljZXMucnMAL3J1c3RjLzI5NDgzODgzZWVkNjlkNWZiNGRiMDE5NjRjZGYyYWY0ZDg2ZTljYjIvbGlicmFyeS9zdGQvc3JjL3RocmVhZC9sb2NhbC5ycwBsaWJyYXJ5L2FsbG9jL3NyYy9zdHJpbmcucnMAL3J1c3RjLzI5NDgzODgzZWVkNjlkNWZiNGRiMDE5NjRjZGYyYWY0ZDg2ZTljYjIvbGlicmFyeS9hbGxvYy9zcmMvc2xpY2UucnMAL3J1c3RjLzI5NDgzODgzZWVkNjlkNWZiNGRiMDE5NjRjZGYyYWY0ZDg2ZTljYjIvbGlicmFyeS9hbGxvYy9zcmMvcmF3X3ZlYy9tb2QucnMAL3J1c3QvZGVwcy9kbG1hbGxv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dGAgZmFpbGVkOiAKICBsZWZ0OiAAAACbCBAAEAAAAOQIEAAQAAAA9AgQAAkAAADCCBAACQAAADogAAABAAAAAAAAACAJEAACAAAAfSB9MHgwMDAxMDIwMzA0MDUwNjA3MDgwOTEwMTExMjEzMTQxNTE2MTcxODE5MjAyMTIyMjMyNDI1MjYyNzI4MjkzMDMxMzIzMzM0MzUzNjM3MzgzOTQwNDE0MjQzNDQ0NTQ2NDc0ODQ5NTA1MTUyNTM1NDU1NTY1NzU4NTk2MDYxNjI2MzY0NjU2NjY3Njg2OTcwNzE3MjczNzQ3NTc2Nzc3ODc5ODA4MTgyODM4NDg1ODY4Nzg4ODk5MDkxOTI5Mzk0OTU5Njk3OTg5OSBvdXQgb2YgcmFuZ2UgZm9yIHNsaWNlIG9mIGxlbmd0aCByYW5nZSBlbmQgaW5kZXggACMKEAAQAAAAAQoQACIAAACQCBAAkggQAJQIEAACAAAAAgAAAAcAAAAAAAA/AAAAvwBB/JTAAAsBEgB8CXByb2R1Y2VycwIIbGFuZ3VhZ2UBBFJ1c3QADHByb2Nlc3NlZC1ieQMFcnVzdGMdMS44OS4wICgyOTQ4Mzg4M2UgMjAyNS0wOC0wNCkGd2FscnVzBjAuMjMuMwx3YXNtLWJpbmRnZW4TMC4yLjEwMCAoMjQwNWVjMmI0KQBrD3RhcmdldF9mZWF0dXJlcwYrD211dGFibGUtZ2xvYmFscysTbm9udHJhcHBpbmctZnB0b2ludCsLYnVsay1tZW1vcnkrCHNpZ24tZXh0Kw9yZWZlcmVuY2UtdHlwZXMrCm11bHRpdmFsdWU=", import.meta.url));
|
|
const A = Xo();
|
|
(typeof t == "string" || typeof Request == "function" && t instanceof Request || typeof URL == "function" && t instanceof URL) && (t = fetch(t));
|
|
const { instance: e, module: s } = await Zo(await t, A);
|
|
return Oo(e, s);
|
|
}
|
|
const UA = -12, GA = 9, jo = Math.exp(UA), Wo = Math.exp(GA), Gs = -30, It = Math.exp(Gs), Xe = 11, Oe = 11, Rs = 11, Ac = Xe + Oe, Z = 1 << Xe, KA = 1 << Oe, Ys = 1 << Rs, je = 1, tc = Z - 1, ec = KA - 1, sc = Ys - 1, nc = !0, ic = !0, $h = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
__proto__: null,
|
|
LN_SCALE_MAX: GA,
|
|
LN_SCALE_MIN: UA,
|
|
LN_SCALE_ZERO: Gs,
|
|
SCALE_MAX: Wo,
|
|
SCALE_MIN: jo,
|
|
SCALE_ZERO: It,
|
|
SPLAT_TEX_DEPTH: Ys,
|
|
SPLAT_TEX_DEPTH_BITS: Rs,
|
|
SPLAT_TEX_DEPTH_MASK: sc,
|
|
SPLAT_TEX_HEIGHT: KA,
|
|
SPLAT_TEX_HEIGHT_BITS: Oe,
|
|
SPLAT_TEX_HEIGHT_MASK: ec,
|
|
SPLAT_TEX_LAYER_BITS: Ac,
|
|
SPLAT_TEX_MIN_HEIGHT: je,
|
|
SPLAT_TEX_WIDTH: Z,
|
|
SPLAT_TEX_WIDTH_BITS: Xe,
|
|
SPLAT_TEX_WIDTH_MASK: tc,
|
|
USE_COMPILED_PARSER_FUNCTION: ic,
|
|
WASM_SPLAT_SORT: nc
|
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
function ft(t) {
|
|
return t === "bool" || t === "bvec2" || t === "bvec3" || t === "bvec4";
|
|
}
|
|
function dt(t) {
|
|
return t === "int" || t === "uint" || t === "float";
|
|
}
|
|
function EA(t) {
|
|
return t === "int" || t === "ivec2" || t === "ivec3" || t === "ivec4";
|
|
}
|
|
function QA(t) {
|
|
return t === "uint" || t === "uvec2" || t === "uvec3" || t === "uvec4";
|
|
}
|
|
function Zt(t) {
|
|
return t === "float" || t === "vec2" || t === "vec3" || t === "vec4";
|
|
}
|
|
function Js(t) {
|
|
return t === "mat2" || t === "mat2x2" || t === "mat2x3" || t === "mat2x4" || t === "mat3" || t === "mat3x2" || t === "mat3x3" || t === "mat3x4" || t === "mat4" || t === "mat4x2" || t === "mat4x3" || t === "mat4x4";
|
|
}
|
|
function at(t) {
|
|
return Zt(t) || Js(t);
|
|
}
|
|
function Nt(t) {
|
|
return t === "vec2" || t === "ivec2" || t === "uvec2";
|
|
}
|
|
function kt(t) {
|
|
return t === "vec3" || t === "ivec3" || t === "uvec3";
|
|
}
|
|
function Xt(t) {
|
|
return t === "vec4" || t === "ivec4" || t === "uvec4";
|
|
}
|
|
function rc(t) {
|
|
return Nt(t) || kt(t) || Xt(t);
|
|
}
|
|
function ot(t) {
|
|
return t === "mat2" || t === "mat2x2";
|
|
}
|
|
function ct(t) {
|
|
return t === "mat3" || t === "mat3x3";
|
|
}
|
|
function gt(t) {
|
|
return t === "mat4" || t === "mat4x4";
|
|
}
|
|
function _s(t) {
|
|
switch (t) {
|
|
case "vec2":
|
|
return "float";
|
|
case "vec3":
|
|
return "float";
|
|
case "vec4":
|
|
return "float";
|
|
case "ivec2":
|
|
return "int";
|
|
case "ivec3":
|
|
return "int";
|
|
case "ivec4":
|
|
return "int";
|
|
case "uvec2":
|
|
return "uint";
|
|
case "uvec3":
|
|
return "uint";
|
|
case "uvec4":
|
|
return "uint";
|
|
default:
|
|
throw new Error(`Invalid vector type: ${t}`);
|
|
}
|
|
}
|
|
function Ls(t) {
|
|
switch (t) {
|
|
case "vec2":
|
|
case "ivec2":
|
|
case "uvec2":
|
|
return 2;
|
|
case "vec3":
|
|
case "ivec3":
|
|
case "uvec3":
|
|
return 3;
|
|
case "vec4":
|
|
case "ivec4":
|
|
case "uvec4":
|
|
return 4;
|
|
default:
|
|
throw new Error(`Invalid vector type: ${t}`);
|
|
}
|
|
}
|
|
function ac(t) {
|
|
if (dt(t))
|
|
return "float";
|
|
if (Nt(t))
|
|
return "vec2";
|
|
if (kt(t))
|
|
return "vec3";
|
|
if (Xt(t))
|
|
return "vec4";
|
|
throw new Error(`Invalid vector type: ${t}`);
|
|
}
|
|
function zs(t) {
|
|
if (dt(t))
|
|
return "uint";
|
|
if (Nt(t))
|
|
return "uvec2";
|
|
if (kt(t))
|
|
return "uvec3";
|
|
if (Xt(t))
|
|
return "uvec4";
|
|
throw new Error(`Invalid vector type: ${t}`);
|
|
}
|
|
function oc(t) {
|
|
if (dt(t))
|
|
return "int";
|
|
if (Nt(t))
|
|
return "ivec2";
|
|
if (kt(t))
|
|
return "ivec3";
|
|
if (Xt(t))
|
|
return "ivec4";
|
|
throw new Error(`Invalid vector type: ${t}`);
|
|
}
|
|
function Hs(t) {
|
|
if (typeof t == "string")
|
|
return t;
|
|
if (typeof t == "object" && t.type)
|
|
return t.type;
|
|
throw new Error(`Invalid DynoType: ${String(t)}`);
|
|
}
|
|
function rA(t) {
|
|
return Math.trunc(t).toString();
|
|
}
|
|
function aA(t) {
|
|
return `${Math.max(0, Math.trunc(t)).toString()}u`;
|
|
}
|
|
function H(t) {
|
|
return t === Number.POSITIVE_INFINITY ? "INFINITY" : t === Number.NEGATIVE_INFINITY ? "-INFINITY" : Number.isInteger(t) ? t.toFixed(1) : t.toString();
|
|
}
|
|
function $(t) {
|
|
return t instanceof it ? t.type : t.dynoOut().type;
|
|
}
|
|
class it {
|
|
constructor(A) {
|
|
this.__isDynoValue = !0, this.type = A;
|
|
}
|
|
}
|
|
class K extends it {
|
|
constructor(A, e) {
|
|
super(A.outTypes[e]), this.dyno = A, this.key = e;
|
|
}
|
|
}
|
|
class vt extends it {
|
|
constructor(A, e) {
|
|
super(A), this.literal = e;
|
|
}
|
|
getLiteral() {
|
|
return this.literal;
|
|
}
|
|
}
|
|
function oe(t, A) {
|
|
return new vt(t, A);
|
|
}
|
|
class qs extends vt {
|
|
constructor(A, e) {
|
|
super(A, ""), this.value = e;
|
|
}
|
|
getLiteral() {
|
|
const { type: A, value: e } = this;
|
|
switch (A) {
|
|
case "bool":
|
|
return e ? "true" : "false";
|
|
case "uint":
|
|
return aA(e);
|
|
case "int":
|
|
return rA(e);
|
|
case "float":
|
|
return H(e);
|
|
case "bvec2": {
|
|
const s = e;
|
|
return `bvec2(${s[0]}, ${s[1]})`;
|
|
}
|
|
case "uvec2": {
|
|
if (e instanceof u.Vector2)
|
|
return `uvec2(${aA(e.x)}, ${aA(e.y)})`;
|
|
const s = e;
|
|
return `uvec2(${aA(s[0])}, ${aA(s[1])})`;
|
|
}
|
|
case "ivec2": {
|
|
if (e instanceof u.Vector2)
|
|
return `ivec2(${rA(e.x)}, ${rA(e.y)})`;
|
|
const s = e;
|
|
return `ivec2(${rA(s[0])}, ${rA(s[1])})`;
|
|
}
|
|
case "vec2": {
|
|
if (e instanceof u.Vector2)
|
|
return `vec2(${H(e.x)}, ${H(e.y)})`;
|
|
const s = e;
|
|
return `vec2(${H(s[0])}, ${H(s[1])})`;
|
|
}
|
|
case "bvec3": {
|
|
const s = e;
|
|
return `bvec3(${s[0]}, ${s[1]}, ${s[2]})`;
|
|
}
|
|
case "uvec3": {
|
|
if (e instanceof u.Vector3)
|
|
return `uvec3(${aA(e.x)}, ${aA(e.y)}, ${aA(e.z)})`;
|
|
const s = e;
|
|
return `uvec3(${aA(s[0])}, ${aA(s[1])}, ${aA(s[2])})`;
|
|
}
|
|
case "ivec3": {
|
|
if (e instanceof u.Vector3)
|
|
return `ivec3(${rA(e.x)}, ${rA(e.y)}, ${rA(e.z)})`;
|
|
const s = e;
|
|
return `ivec3(${rA(s[0])}, ${rA(s[1])}, ${rA(s[2])})`;
|
|
}
|
|
case "vec3": {
|
|
if (e instanceof u.Vector3)
|
|
return `vec3(${H(e.x)}, ${H(e.y)}, ${H(e.z)})`;
|
|
const s = e;
|
|
return `vec3(${H(s[0])}, ${H(s[1])}, ${H(s[2])})`;
|
|
}
|
|
case "bvec4": {
|
|
const s = e;
|
|
return `bvec4(${s[0]}, ${s[1]}, ${s[2]}, ${s[3]})`;
|
|
}
|
|
case "uvec4": {
|
|
if (e instanceof u.Vector4)
|
|
return `uvec4(${aA(e.x)}, ${aA(e.y)}, ${aA(e.z)}, ${aA(e.w)})`;
|
|
const s = e;
|
|
return `uvec4(${aA(s[0])}, ${aA(s[1])}, ${aA(s[2])}, ${aA(s[3])})`;
|
|
}
|
|
case "ivec4": {
|
|
if (e instanceof u.Vector4)
|
|
return `ivec4(${rA(e.x)}, ${rA(e.y)}, ${rA(e.z)}, ${rA(e.w)})`;
|
|
const s = e;
|
|
return `ivec4(${rA(s[0])}, ${rA(s[1])}, ${rA(s[2])}, ${rA(s[3])})`;
|
|
}
|
|
case "vec4": {
|
|
if (e instanceof u.Vector4)
|
|
return `vec4(${H(e.x)}, ${H(e.y)}, ${H(e.z)}, ${H(e.w)})`;
|
|
if (e instanceof u.Quaternion)
|
|
return `vec4(${H(e.x)}, ${H(e.y)}, ${H(e.z)}, ${H(e.w)})`;
|
|
const s = e;
|
|
return `vec4(${H(s[0])}, ${H(s[1])}, ${H(s[2])}, ${H(s[3])})`;
|
|
}
|
|
case "mat2":
|
|
case "mat2x2": {
|
|
const s = e, n = s instanceof u.Matrix2 ? s.elements : e, i = new Array(4).fill(0).map((r, a) => H(n[a]));
|
|
return `${A}(${i.join(", ")})`;
|
|
}
|
|
case "mat2x3": {
|
|
const s = e, n = new Array(6).fill(0).map((i, r) => H(s[r]));
|
|
return `${A}(${n.join(", ")})`;
|
|
}
|
|
case "mat2x4": {
|
|
const s = e, n = new Array(8).fill(0).map((i, r) => H(s[r]));
|
|
return `${A}(${n.join(", ")})`;
|
|
}
|
|
case "mat3":
|
|
case "mat3x3": {
|
|
const s = e, n = s instanceof u.Matrix3 ? s.elements : e, i = new Array(9).fill(0).map((r, a) => H(n[a]));
|
|
return `${A}(${i.join(", ")})`;
|
|
}
|
|
case "mat3x2": {
|
|
const s = e, n = new Array(6).fill(0).map((i, r) => H(s[r]));
|
|
return `${A}(${n.join(", ")})`;
|
|
}
|
|
case "mat3x4": {
|
|
const s = e, n = new Array(12).fill(0).map((i, r) => H(s[r]));
|
|
return `${A}(${n.join(", ")})`;
|
|
}
|
|
case "mat4":
|
|
case "mat4x4": {
|
|
const s = e, n = s instanceof u.Matrix4 ? s.elements : e, i = new Array(16).fill(0).map((r, a) => H(n[a]));
|
|
return `${A}(${i.join(", ")})`;
|
|
}
|
|
case "mat4x2": {
|
|
const s = e, n = new Array(8).fill(0).map((i, r) => H(s[r]));
|
|
return `${A}(${n.join(", ")})`;
|
|
}
|
|
case "mat4x3": {
|
|
const s = e, n = new Array(12).fill(0).map((i, r) => H(s[r]));
|
|
return `${A}(${n.join(", ")})`;
|
|
}
|
|
default:
|
|
throw new Error(`Type not implemented: ${String(A)}`);
|
|
}
|
|
}
|
|
}
|
|
function J(t, A) {
|
|
return new qs(t, A);
|
|
}
|
|
function Jt(t) {
|
|
const A = String(t);
|
|
if (ft(t))
|
|
return `${A}(false)`;
|
|
if (at(t))
|
|
return `${A}(0.0)`;
|
|
if (EA(t))
|
|
return `${A}(0)`;
|
|
if (QA(t))
|
|
return `${A}(0u)`;
|
|
throw new Error(`Type not implemented: ${A}`);
|
|
}
|
|
function cc(t) {
|
|
const A = String(t);
|
|
if (ft(t))
|
|
return `${A}(true)`;
|
|
if (at(t))
|
|
return `${A}(1.0)`;
|
|
if (EA(t))
|
|
return `${A}(1)`;
|
|
if (QA(t))
|
|
return `${A}(1u)`;
|
|
throw new Error(`Type not implemented: ${A}`);
|
|
}
|
|
function gc(t) {
|
|
const A = String(t);
|
|
if (ft(t))
|
|
return `${A}(true)`;
|
|
if (at(t))
|
|
return `${A}(-1.0)`;
|
|
if (EA(t))
|
|
return `${A}(-1)`;
|
|
if (QA(t))
|
|
return `${A}(0xFFFFFFFFu)`;
|
|
throw new Error(`Type not implemented: ${A}`);
|
|
}
|
|
const Bs = " ";
|
|
class Ks {
|
|
constructor({ indent: A } = {}) {
|
|
this.globals = /* @__PURE__ */ new Set(), this.statements = [], this.uniforms = {}, this.declares = /* @__PURE__ */ new Set(), this.updaters = [], this.sequence = 0, this.indent = Bs, this.indent = A ?? Bs;
|
|
}
|
|
nextSequence() {
|
|
return this.sequence++;
|
|
}
|
|
}
|
|
class V {
|
|
constructor({
|
|
inTypes: A,
|
|
outTypes: e,
|
|
inputs: s,
|
|
update: n,
|
|
globals: i,
|
|
statements: r,
|
|
generate: a
|
|
}) {
|
|
this.inTypes = A ?? {}, this.outTypes = e ?? {}, this.inputs = s ?? {}, this.update = n, this.globals = i, this.statements = r, this.generate = a ?? (({ inputs: o, outputs: g, compile: l }) => {
|
|
var c, I;
|
|
return {
|
|
globals: (c = this.globals) == null ? void 0 : c.call(this, { inputs: o, outputs: g, compile: l }),
|
|
statements: (I = this.statements) == null ? void 0 : I.call(this, { inputs: o, outputs: g, compile: l })
|
|
};
|
|
});
|
|
}
|
|
get outputs() {
|
|
const A = {};
|
|
for (const e in this.outTypes)
|
|
A[e] = new K(this, e);
|
|
return A;
|
|
}
|
|
apply(A) {
|
|
return Object.assign(this.inputs, A), this.outputs;
|
|
}
|
|
compile({
|
|
inputs: A,
|
|
outputs: e,
|
|
compile: s
|
|
}) {
|
|
const n = [
|
|
`// ${this.constructor.name}(${Object.values(A).join(", ")}) => (${Object.values(e).join(", ")})`
|
|
], i = [];
|
|
for (const g in e) {
|
|
const l = e[g];
|
|
l && !s.declares.has(l) && (s.declares.add(l), i.push(g));
|
|
}
|
|
const { globals: r, statements: a, uniforms: o } = this.generate({
|
|
inputs: A,
|
|
outputs: e,
|
|
compile: s
|
|
});
|
|
for (const g of r ?? [])
|
|
s.globals.add(g);
|
|
for (const g in o)
|
|
s.uniforms[g] = o[g];
|
|
this.update && s.updaters.push(this.update);
|
|
for (const g of i) {
|
|
const l = e[g];
|
|
l && (s.uniforms[l] || n.push(`${We(l, this.outTypes[g])};`));
|
|
}
|
|
return a != null && a.length && (n.push("{"), n.push(...a.map((g) => s.indent + g)), n.push("}")), n;
|
|
}
|
|
}
|
|
class PA extends V {
|
|
constructor({
|
|
inTypes: A,
|
|
outTypes: e,
|
|
inputs: s,
|
|
update: n,
|
|
globals: i,
|
|
construct: r
|
|
}) {
|
|
super({
|
|
inTypes: A,
|
|
outTypes: e,
|
|
inputs: s,
|
|
update: n,
|
|
globals: i,
|
|
generate: (a) => this.generateBlock(a)
|
|
}), this.construct = r;
|
|
}
|
|
generateBlock({
|
|
inputs: A,
|
|
outputs: e,
|
|
compile: s
|
|
}) {
|
|
var E, C;
|
|
const n = {}, i = {};
|
|
for (const B in A)
|
|
A[B] != null && (n[B] = new vt(this.inTypes[B], A[B]));
|
|
for (const B in e)
|
|
e[B] != null && (i[B] = new it(this.outTypes[B]));
|
|
const r = { roots: [] }, a = this.construct(n, i, r);
|
|
for (const B of ((E = this.globals) == null ? void 0 : E.call(this, { inputs: A, outputs: e, compile: s })) ?? [])
|
|
s.globals.add(B);
|
|
const o = [], g = /* @__PURE__ */ new Map();
|
|
function l(B, Q, f) {
|
|
let p = g.get(B);
|
|
if (!p) {
|
|
p = {
|
|
sequence: s.nextSequence(),
|
|
outNames: /* @__PURE__ */ new Map(),
|
|
newOuts: /* @__PURE__ */ new Set()
|
|
}, g.set(B, p);
|
|
for (const d in B.inputs) {
|
|
let y = B.inputs[d];
|
|
for (; y; ) {
|
|
if (y instanceof it) {
|
|
y instanceof K && l(y.dyno, y.key);
|
|
break;
|
|
}
|
|
y = y.dynoOut();
|
|
}
|
|
}
|
|
o.push(B);
|
|
}
|
|
Q && (f || p.newOuts.add(Q), p.outNames.set(Q, f ?? `${Q}_${p.sequence}`));
|
|
}
|
|
for (const B of r.roots)
|
|
l(B);
|
|
for (const B in i) {
|
|
let Q = (a == null ? void 0 : a[B]) ?? i[B];
|
|
for (; Q; ) {
|
|
if (Q instanceof it) {
|
|
Q instanceof K && l(Q.dyno, Q.key, e[B]);
|
|
break;
|
|
}
|
|
Q = Q.dynoOut();
|
|
}
|
|
i[B] = Q;
|
|
}
|
|
const c = [];
|
|
for (const B of o) {
|
|
const Q = {}, f = {};
|
|
for (const y in B.inputs) {
|
|
let D = B.inputs[y];
|
|
for (; D; ) {
|
|
if (D instanceof it) {
|
|
if (D instanceof vt)
|
|
Q[y] = D.getLiteral();
|
|
else if (D instanceof K) {
|
|
const x = (C = g.get(D.dyno)) == null ? void 0 : C.outNames.get(D.key);
|
|
if (!x)
|
|
throw new Error(
|
|
`Source not found for ${D.dyno.constructor.name}.${D.key}`
|
|
);
|
|
Q[y] = x;
|
|
}
|
|
break;
|
|
}
|
|
D = D.dynoOut();
|
|
}
|
|
}
|
|
const p = g.get(B) ?? { outNames: /* @__PURE__ */ new Map() };
|
|
for (const [y, D] of p.outNames.entries())
|
|
f[y] = D;
|
|
const d = B.compile({ inputs: Q, outputs: f, compile: s });
|
|
c.push(d);
|
|
}
|
|
const I = [];
|
|
for (const B in e)
|
|
i[B] instanceof vt && I.push(
|
|
`${e[B]} = ${i[B].getLiteral()};`
|
|
);
|
|
return I.length > 0 && c.push(I), { statements: c.flatMap((B, Q) => Q === 0 ? B : ["", ...B]) };
|
|
}
|
|
}
|
|
function vA(t, A, e, { update: s, globals: n } = {}) {
|
|
return new PA({ inTypes: t, outTypes: A, construct: e, update: s, globals: n });
|
|
}
|
|
function Ot({
|
|
inTypes: t,
|
|
outTypes: A,
|
|
inputs: e,
|
|
update: s,
|
|
globals: n,
|
|
statements: i,
|
|
generate: r
|
|
}) {
|
|
return new V({
|
|
inTypes: t,
|
|
outTypes: A,
|
|
inputs: e,
|
|
update: s,
|
|
globals: n,
|
|
statements: i,
|
|
generate: r
|
|
});
|
|
}
|
|
function We(t, A, e) {
|
|
const s = typeof A == "string" ? A : A.type;
|
|
if (!s)
|
|
throw new Error(`Invalid DynoType: ${String(A)}`);
|
|
return `${s} ${t}${e != null ? `[${e}]` : ""}`;
|
|
}
|
|
function RA(t) {
|
|
var i;
|
|
let A = !1;
|
|
const e = t.split(`
|
|
`).map((r) => {
|
|
const a = r.trimEnd();
|
|
return A ? a : a.length > 0 ? (A = !0, a) : null;
|
|
}).filter((r) => r != null);
|
|
for (; e.length > 0 && e[e.length - 1].length === 0; )
|
|
e.pop();
|
|
if (e.length === 0)
|
|
return [];
|
|
const s = (i = e[0].match(/^\s*/)) == null ? void 0 : i[0];
|
|
if (!s)
|
|
return e;
|
|
const n = new RegExp(`^${s}`);
|
|
return e.map((r) => r.replace(n, ""));
|
|
}
|
|
function hA(t) {
|
|
return RA(t).join(`
|
|
`);
|
|
}
|
|
class v extends V {
|
|
constructor({
|
|
a: A,
|
|
outKey: e,
|
|
outTypeFunc: s
|
|
}) {
|
|
const n = { a: $(A) }, i = s($(A)), r = { [e]: i };
|
|
super({ inTypes: n, outTypes: r, inputs: { a: A } }), this.outKey = e;
|
|
}
|
|
dynoOut() {
|
|
return new K(this, this.outKey);
|
|
}
|
|
}
|
|
class tA extends V {
|
|
constructor({
|
|
a: A,
|
|
b: e,
|
|
outKey: s,
|
|
outTypeFunc: n
|
|
}) {
|
|
const i = { a: $(A), b: $(e) }, r = n($(A), $(e)), a = { [s]: r };
|
|
super({ inTypes: i, outTypes: a, inputs: { a: A, b: e } }), this.outKey = s;
|
|
}
|
|
dynoOut() {
|
|
return new K(this, this.outKey);
|
|
}
|
|
}
|
|
class yt extends V {
|
|
constructor({
|
|
a: A,
|
|
b: e,
|
|
c: s,
|
|
outKey: n,
|
|
outTypeFunc: i
|
|
}) {
|
|
const r = { a: $(A), b: $(e), c: $(s) }, a = i($(A), $(e), $(s)), o = { [n]: a };
|
|
super({ inTypes: r, outTypes: o, inputs: { a: A, b: e, c: s } }), this.outKey = n;
|
|
}
|
|
dynoOut() {
|
|
return new K(this, this.outKey);
|
|
}
|
|
}
|
|
const AA = { type: "Gsplat" }, jt = { type: "PackedSplats" }, lc = (t) => new Vs({ packedSplats: t }), bt = (t, A) => new Zs({ packedSplats: t, index: A }), $s = (t, A, e, s) => new Xs({ packedSplats: t, index: A, base: e, count: s }), ut = (t) => new Os({ gsplat: t }), rt = ({
|
|
gsplat: t,
|
|
flags: A,
|
|
index: e,
|
|
center: s,
|
|
scales: n,
|
|
quaternion: i,
|
|
rgba: r,
|
|
rgb: a,
|
|
opacity: o,
|
|
x: g,
|
|
y: l,
|
|
z: c,
|
|
r: I,
|
|
g: h,
|
|
b: E
|
|
}) => new js({
|
|
gsplat: t,
|
|
flags: A,
|
|
index: e,
|
|
center: s,
|
|
scales: n,
|
|
quaternion: i,
|
|
rgba: r,
|
|
rgb: a,
|
|
opacity: o,
|
|
x: g,
|
|
y: l,
|
|
z: c,
|
|
r: I,
|
|
g: h,
|
|
b: E
|
|
}), Re = (t) => new An({ gsplat: t }), As = (t, {
|
|
scale: A,
|
|
rotate: e,
|
|
translate: s,
|
|
recolor: n
|
|
}) => new tn({ gsplat: t, scale: A, rotate: e, translate: s, recolor: n }), bA = hA(`
|
|
struct Gsplat {
|
|
vec3 center;
|
|
uint flags;
|
|
vec3 scales;
|
|
int index;
|
|
vec4 quaternion;
|
|
vec4 rgba;
|
|
};
|
|
const uint GSPLAT_FLAG_ACTIVE = 1u << 0u;
|
|
|
|
bool isGsplatActive(uint flags) {
|
|
return (flags & GSPLAT_FLAG_ACTIVE) != 0u;
|
|
}
|
|
`), Qe = hA(`
|
|
struct PackedSplats {
|
|
usampler2DArray texture;
|
|
int numSplats;
|
|
vec4 rgbMinMaxLnScaleMinMax;
|
|
};
|
|
`);
|
|
class Vs extends v {
|
|
constructor({
|
|
packedSplats: A
|
|
}) {
|
|
super({ a: A, outKey: "numSplats", outTypeFunc: () => "int" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.numSplats} = ${e.a}.numSplats;`
|
|
];
|
|
}
|
|
}
|
|
const Ps = hA(`
|
|
bool readPackedSplat(usampler2DArray texture, int numSplats, vec4 rgbMinMaxLnScaleMinMax, int index, out Gsplat gsplat) {
|
|
if ((index >= 0) && (index < numSplats)) {
|
|
uvec4 packed = texelFetch(texture, splatTexCoord(index), 0);
|
|
unpackSplatEncoding(packed, gsplat.center, gsplat.scales, gsplat.quaternion, gsplat.rgba, rgbMinMaxLnScaleMinMax);
|
|
return true;
|
|
} else {
|
|
return false;
|
|
}
|
|
}
|
|
`);
|
|
class Zs extends V {
|
|
constructor({
|
|
packedSplats: A,
|
|
index: e
|
|
}) {
|
|
super({
|
|
inTypes: { packedSplats: jt, index: "int" },
|
|
outTypes: { gsplat: AA },
|
|
inputs: { packedSplats: A, index: e },
|
|
globals: () => [bA, Qe, Ps],
|
|
statements: ({ inputs: s, outputs: n }) => {
|
|
const { gsplat: i } = n;
|
|
if (!i)
|
|
return [];
|
|
const { packedSplats: r, index: a } = s;
|
|
let o;
|
|
return r && a ? o = RA(`
|
|
if (readPackedSplat(${r}.texture, ${r}.numSplats, ${r}.rgbMinMaxLnScaleMinMax, ${a}, ${i})) {
|
|
bool zeroSize = all(equal(${i}.scales, vec3(0.0, 0.0, 0.0)));
|
|
${i}.flags = zeroSize ? 0u : GSPLAT_FLAG_ACTIVE;
|
|
} else {
|
|
${i}.flags = 0u;
|
|
}
|
|
`) : o = [`${i}.flags = 0u;`], o.push(`${i}.index = ${a ?? "0"};`), o;
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "gsplat");
|
|
}
|
|
}
|
|
class Xs extends V {
|
|
constructor({
|
|
packedSplats: A,
|
|
index: e,
|
|
base: s,
|
|
count: n
|
|
}) {
|
|
super({
|
|
inTypes: {
|
|
packedSplats: jt,
|
|
index: "int",
|
|
base: "int",
|
|
count: "int"
|
|
},
|
|
outTypes: { gsplat: AA },
|
|
inputs: { packedSplats: A, index: e, base: s, count: n },
|
|
globals: () => [bA, Qe, Ps],
|
|
statements: ({ inputs: i, outputs: r }) => {
|
|
const { gsplat: a } = r;
|
|
if (!a)
|
|
return [];
|
|
const { packedSplats: o, index: g, base: l, count: c } = i;
|
|
let I;
|
|
return o && g && l && c ? I = RA(`
|
|
${a}.flags = 0u;
|
|
if ((${g} >= ${l}) && (${g} < (${l} + ${c}))) {
|
|
if (readPackedSplat(${o}.texture, ${o}.numSplats, ${o}.rgbMinMaxLnScaleMinMax, ${g}, ${a})) {
|
|
bool zeroSize = all(equal(${a}.scales, vec3(0.0, 0.0, 0.0)));
|
|
${a}.flags = zeroSize ? 0u : GSPLAT_FLAG_ACTIVE;
|
|
}
|
|
}
|
|
`) : I = [`${a}.flags = 0u;`], I.push(`${a}.index = ${g ?? "0"};`), I;
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "gsplat");
|
|
}
|
|
}
|
|
class Os extends V {
|
|
constructor({ gsplat: A }) {
|
|
super({
|
|
inTypes: { gsplat: AA },
|
|
outTypes: {
|
|
flags: "uint",
|
|
active: "bool",
|
|
index: "int",
|
|
center: "vec3",
|
|
scales: "vec3",
|
|
quaternion: "vec4",
|
|
rgba: "vec4",
|
|
rgb: "vec3",
|
|
opacity: "float",
|
|
x: "float",
|
|
y: "float",
|
|
z: "float",
|
|
r: "float",
|
|
g: "float",
|
|
b: "float"
|
|
},
|
|
inputs: { gsplat: A },
|
|
globals: () => [bA],
|
|
statements: ({ inputs: e, outputs: s }) => {
|
|
const { gsplat: n } = e, {
|
|
flags: i,
|
|
active: r,
|
|
index: a,
|
|
center: o,
|
|
scales: g,
|
|
quaternion: l,
|
|
rgba: c,
|
|
rgb: I,
|
|
opacity: h,
|
|
x: E,
|
|
y: C,
|
|
z: B,
|
|
r: Q,
|
|
g: f,
|
|
b: p
|
|
} = s;
|
|
return [
|
|
i ? `${i} = ${n ? `${n}.flags` : "0u"};` : null,
|
|
r ? `${r} = isGsplatActive(${n ? `${n}.flags` : "0u"});` : null,
|
|
a ? `${a} = ${n ? `${n}.index` : "0"};` : null,
|
|
o ? `${o} = ${n ? `${n}.center` : "vec3(0.0, 0.0, 0.0)"};` : null,
|
|
g ? `${g} = ${n ? `${n}.scales` : "vec3(0.0, 0.0, 0.0)"};` : null,
|
|
l ? `${l} = ${n ? `${n}.quaternion` : "vec4(0.0, 0.0, 0.0, 1.0)"};` : null,
|
|
c ? `${c} = ${n ? `${n}.rgba` : "vec4(0.0, 0.0, 0.0, 0.0)"};` : null,
|
|
I ? `${I} = ${n ? `${n}.rgba.rgb` : "vec3(0.0, 0.0, 0.0)"};` : null,
|
|
h ? `${h} = ${n ? `${n}.rgba.a` : "0.0"};` : null,
|
|
E ? `${E} = ${n ? `${n}.center.x` : "0.0"};` : null,
|
|
C ? `${C} = ${n ? `${n}.center.y` : "0.0"};` : null,
|
|
B ? `${B} = ${n ? `${n}.center.z` : "0.0"};` : null,
|
|
Q ? `${Q} = ${n ? `${n}.rgba.r` : "0.0"};` : null,
|
|
f ? `${f} = ${n ? `${n}.rgba.g` : "0.0"};` : null,
|
|
p ? `${p} = ${n ? `${n}.rgba.b` : "0.0"};` : null
|
|
].filter(Boolean);
|
|
}
|
|
});
|
|
}
|
|
}
|
|
class js extends V {
|
|
constructor({
|
|
gsplat: A,
|
|
flags: e,
|
|
index: s,
|
|
center: n,
|
|
scales: i,
|
|
quaternion: r,
|
|
rgba: a,
|
|
rgb: o,
|
|
opacity: g,
|
|
x: l,
|
|
y: c,
|
|
z: I,
|
|
r: h,
|
|
g: E,
|
|
b: C
|
|
}) {
|
|
super({
|
|
inTypes: {
|
|
gsplat: AA,
|
|
flags: "uint",
|
|
index: "int",
|
|
center: "vec3",
|
|
scales: "vec3",
|
|
quaternion: "vec4",
|
|
rgba: "vec4",
|
|
rgb: "vec3",
|
|
opacity: "float",
|
|
x: "float",
|
|
y: "float",
|
|
z: "float",
|
|
r: "float",
|
|
g: "float",
|
|
b: "float"
|
|
},
|
|
outTypes: { gsplat: AA },
|
|
inputs: {
|
|
gsplat: A,
|
|
flags: e,
|
|
index: s,
|
|
center: n,
|
|
scales: i,
|
|
quaternion: r,
|
|
rgba: a,
|
|
rgb: o,
|
|
opacity: g,
|
|
x: l,
|
|
y: c,
|
|
z: I,
|
|
r: h,
|
|
g: E,
|
|
b: C
|
|
},
|
|
globals: () => [bA],
|
|
statements: ({ inputs: B, outputs: Q }) => {
|
|
const { gsplat: f } = Q;
|
|
if (!f)
|
|
return [];
|
|
const {
|
|
gsplat: p,
|
|
flags: d,
|
|
index: y,
|
|
center: D,
|
|
scales: x,
|
|
quaternion: w,
|
|
rgba: m,
|
|
rgb: k,
|
|
opacity: M,
|
|
x: S,
|
|
y: U,
|
|
z: F,
|
|
r: b,
|
|
g: T,
|
|
b: R
|
|
} = B;
|
|
return [
|
|
`${f}.flags = ${d ?? (p ? `${p}.flags` : "0u")};`,
|
|
`${f}.index = ${y ?? (p ? `${p}.index` : "0")};`,
|
|
`${f}.center = ${D ?? (p ? `${p}.center` : "vec3(0.0, 0.0, 0.0)")};`,
|
|
`${f}.scales = ${x ?? (p ? `${p}.scales` : "vec3(0.0, 0.0, 0.0)")};`,
|
|
`${f}.quaternion = ${w ?? (p ? `${p}.quaternion` : "vec4(0.0, 0.0, 0.0, 1.0)")};`,
|
|
`${f}.rgba = ${m ?? (p ? `${p}.rgba` : "vec4(0.0, 0.0, 0.0, 0.0)")};`,
|
|
k ? `${f}.rgba.rgb = ${k};` : null,
|
|
M ? `${f}.rgba.a = ${M};` : null,
|
|
S ? `${f}.center.x = ${S};` : null,
|
|
U ? `${f}.center.y = ${U};` : null,
|
|
F ? `${f}.center.z = ${F};` : null,
|
|
b ? `${f}.rgba.r = ${b};` : null,
|
|
T ? `${f}.rgba.g = ${T};` : null,
|
|
R ? `${f}.rgba.b = ${R};` : null
|
|
].filter(Boolean);
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "gsplat");
|
|
}
|
|
}
|
|
const Ws = hA(`
|
|
vec3 gsplatNormal(vec3 scales, vec4 quaternion) {
|
|
float minScale = min(scales.x, min(scales.y, scales.z));
|
|
vec3 normal;
|
|
if (scales.z == minScale) {
|
|
normal = vec3(0.0, 0.0, 1.0);
|
|
} else if (scales.y == minScale) {
|
|
normal = vec3(0.0, 1.0, 0.0);
|
|
} else {
|
|
normal = vec3(1.0, 0.0, 0.0);
|
|
}
|
|
return quatVec(quaternion, normal);
|
|
}
|
|
`);
|
|
class An extends v {
|
|
constructor({ gsplat: A }) {
|
|
super({ a: A, outKey: "normal", outTypeFunc: () => "vec3" }), this.globals = () => [bA, Ws], this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.normal} = gsplatNormal(${e.a}.scales, ${e.a}.quaternion);`
|
|
];
|
|
}
|
|
}
|
|
class tn extends V {
|
|
constructor({
|
|
gsplat: A,
|
|
scale: e,
|
|
rotate: s,
|
|
translate: n,
|
|
recolor: i
|
|
}) {
|
|
super({
|
|
inTypes: {
|
|
gsplat: AA,
|
|
scale: "float",
|
|
rotate: "vec4",
|
|
translate: "vec3",
|
|
recolor: "vec4"
|
|
},
|
|
outTypes: { gsplat: AA },
|
|
inputs: { gsplat: A, scale: e, rotate: s, translate: n, recolor: i },
|
|
globals: () => [bA],
|
|
statements: ({ inputs: r, outputs: a, compile: o }) => {
|
|
const { gsplat: g } = a;
|
|
if (!g || !r.gsplat)
|
|
return [];
|
|
const { scale: l, rotate: c, translate: I, recolor: h } = r, E = o.indent;
|
|
return [
|
|
`${g} = ${r.gsplat};`,
|
|
`if (isGsplatActive(${g}.flags)) {`,
|
|
l ? `${E}${g}.center *= ${l};` : null,
|
|
c ? `${E}${g}.center = quatVec(${c}, ${g}.center);` : null,
|
|
I ? `${E}${g}.center += ${I};` : null,
|
|
l ? `${E}${g}.scales *= ${l};` : null,
|
|
c ? `${E}${g}.quaternion = quatQuat(${c}, ${g}.quaternion);` : null,
|
|
h ? `${E}${g}.rgba *= ${h};` : null,
|
|
"}"
|
|
].filter(Boolean);
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "gsplat");
|
|
}
|
|
}
|
|
const en = (t, A) => new sn({ gsplat: t, rgbMinMaxLnScaleMinMax: A }), Ic = (t) => new ts({ rgba8: t });
|
|
class sn extends V {
|
|
constructor({
|
|
gsplat: A,
|
|
rgbMinMaxLnScaleMinMax: e
|
|
}) {
|
|
super({
|
|
inTypes: { gsplat: AA, rgbMinMaxLnScaleMinMax: "vec4" },
|
|
inputs: { gsplat: A, rgbMinMaxLnScaleMinMax: e },
|
|
globals: () => [bA],
|
|
statements: ({ inputs: s, outputs: n }) => {
|
|
const { output: i } = n;
|
|
if (!i)
|
|
return [];
|
|
const { gsplat: r, rgbMinMaxLnScaleMinMax: a } = s;
|
|
return r ? RA(`
|
|
if (isGsplatActive(${r}.flags)) {
|
|
${i} = packSplatEncoding(${r}.center, ${r}.scales, ${r}.quaternion, ${r}.rgba, ${a});
|
|
} else {
|
|
${i} = uvec4(0u, 0u, 0u, 0u);
|
|
}
|
|
`) : [`${i} = uvec4(0u, 0u, 0u, 0u);`];
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "output");
|
|
}
|
|
}
|
|
class ts extends V {
|
|
constructor({ rgba8: A }) {
|
|
super({
|
|
inTypes: { rgba8: "vec4" },
|
|
inputs: { rgba8: A },
|
|
statements: ({ inputs: e, outputs: s }) => [
|
|
`target = ${e.rgba8 ?? "vec4(0.0, 0.0, 0.0, 0.0)"};`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "rgba8");
|
|
}
|
|
}
|
|
const uc = (t, A, e) => new N({ key: t, type: A, value: e }), hc = (t = !1, A) => new ce({ key: A, value: t }), Cc = (t = 0, A) => new nn({ key: A, value: t }), Bc = (t = 0, A) => new $t({ key: A, value: t }), HA = (t = 0, A) => new ht({ key: A, value: t }), Ec = (t, A) => new rn({ key: A, value: t }), Qc = (t, A) => new an({ key: A, value: t }), pc = (t, A) => new on({ key: A, value: t }), fc = (t, A) => new zt({ key: A, value: t }), dc = (t, A) => new cn({ key: A, value: t }), yc = (t, A) => new gn({ key: A, value: t }), wc = (t, A) => new ln({ key: A, value: t }), tt = (t, A) => new Ft({ key: A, value: t }), mc = (t, A) => new In({ key: A, value: t }), xc = (t, A) => new un({ key: A, value: t }), Sc = (t, A) => new hn({ key: A, value: t }), Dc = (t, A) => new Tt({ key: A, value: t }), Mc = (t, A) => new Cn({ key: A, value: t }), vc = (t, A) => new Bn({ key: A, value: t }), bc = (t, A) => new En({ key: A, value: t }), Fc = (t, A) => new Qn({ key: A, value: t }), Nc = (t, A) => new pn({ key: A, value: t }), kc = (t, A) => new fn({ key: A, value: t }), Tc = (t, A) => new dn({ key: A, value: t }), Uc = (t, A) => new yn({ key: A, value: t }), Gc = (t, A) => new wn({ key: A, value: t }), Rc = (t, A) => new mn({ key: A, value: t }), Yc = (t, A) => new xn({ key: A, value: t }), Jc = (t, A) => new Sn({ key: A, value: t }), _c = (t, A) => new Dn({ key: A, value: t }), Lc = (t, A) => new Mn({ key: A, value: t }), zc = (t, A) => new vn({ key: A, value: t }), Hc = (t, A) => new Ht({ key: A, value: t }), qc = (t, A) => new bn({ key: t, value: A }), Kc = (t, A) => new Fn({ key: A, value: t }), $c = (t, A) => new Nn({ key: A, value: t }), Vc = (t, A) => new kn({ key: A, value: t }), Pc = (t, A) => new Tn({ key: A, value: t }), Zc = (t, A) => new Un({ key: A, value: t }), Xc = (t, A) => new Gn({ key: A, value: t }), Oc = (t, A) => new Rn({ key: A, value: t }), jc = (t, A) => new Yn({ key: A, value: t }), Wc = (t, A) => new Jn({ key: A, value: t }), Ag = (t, A) => new _n({ key: A, value: t });
|
|
class N extends V {
|
|
constructor({
|
|
key: A,
|
|
type: e,
|
|
count: s,
|
|
value: n,
|
|
update: i,
|
|
globals: r
|
|
}) {
|
|
A = A ?? "value", super({
|
|
outTypes: { [A]: e },
|
|
update: () => {
|
|
if (i) {
|
|
const a = i(this.value);
|
|
a !== void 0 && (this.value = a);
|
|
}
|
|
this.uniform.value = this.value;
|
|
},
|
|
generate: ({ inputs: a, outputs: o }) => {
|
|
const g = (r == null ? void 0 : r({ inputs: a, outputs: o })) ?? [], l = {}, c = o[A];
|
|
return c && (g.push(`uniform ${We(c, e, s)};`), l[c] = this.uniform), { globals: g, uniforms: l };
|
|
}
|
|
}), this.type = e, this.count = s, this.value = n, this.uniform = { value: n }, this.outKey = A;
|
|
}
|
|
dynoOut() {
|
|
return new K(this, this.outKey);
|
|
}
|
|
}
|
|
class ce extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "bool", value: e, update: s });
|
|
}
|
|
}
|
|
class nn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "uint", value: e, update: s });
|
|
}
|
|
}
|
|
class $t extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "int", value: e, update: s });
|
|
}
|
|
}
|
|
class ht extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "float", value: e, update: s });
|
|
}
|
|
}
|
|
class rn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "bvec2", value: e, update: s });
|
|
}
|
|
}
|
|
class an extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "uvec2", value: e, update: s });
|
|
}
|
|
}
|
|
class on extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "ivec2", value: e, update: s });
|
|
}
|
|
}
|
|
class zt extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "vec2", value: e, update: s });
|
|
}
|
|
}
|
|
class cn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "bvec3", value: e, update: s });
|
|
}
|
|
}
|
|
class gn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "uvec3", value: e, update: s });
|
|
}
|
|
}
|
|
class ln extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "ivec3", value: e, update: s });
|
|
}
|
|
}
|
|
class Ft extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "vec3", value: e, update: s });
|
|
}
|
|
}
|
|
class In extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "bvec4", value: e, update: s });
|
|
}
|
|
}
|
|
class un extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "uvec4", value: e, update: s });
|
|
}
|
|
}
|
|
class hn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "ivec4", value: e, update: s });
|
|
}
|
|
}
|
|
class Tt extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "vec4", value: e, update: s });
|
|
}
|
|
}
|
|
class Cn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat2", value: e, update: s });
|
|
}
|
|
}
|
|
class Bn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat2x2", value: e, update: s });
|
|
}
|
|
}
|
|
class En extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat2x3", value: e, update: s });
|
|
}
|
|
}
|
|
class Qn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat2x4", value: e, update: s });
|
|
}
|
|
}
|
|
class pn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat3", value: e, update: s });
|
|
}
|
|
}
|
|
class fn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat3x2", value: e, update: s });
|
|
}
|
|
}
|
|
class dn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat3x3", value: e, update: s });
|
|
}
|
|
}
|
|
class yn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat3x4", value: e, update: s });
|
|
}
|
|
}
|
|
class wn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat4", value: e, update: s });
|
|
}
|
|
}
|
|
class mn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat4x2", value: e, update: s });
|
|
}
|
|
}
|
|
class xn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat4x3", value: e, update: s });
|
|
}
|
|
}
|
|
class Sn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "mat4x4", value: e, update: s });
|
|
}
|
|
}
|
|
class Dn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "usampler2D", value: e, update: s });
|
|
}
|
|
}
|
|
class Mn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "isampler2D", value: e, update: s });
|
|
}
|
|
}
|
|
class vn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "sampler2D", value: e, update: s });
|
|
}
|
|
}
|
|
class Ht extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "usampler2DArray", value: e, update: s });
|
|
}
|
|
}
|
|
class bn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "isampler2DArray", value: e, update: s });
|
|
}
|
|
}
|
|
class Fn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "sampler2DArray", value: e, update: s });
|
|
}
|
|
}
|
|
class Nn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "usampler3D", value: e, update: s });
|
|
}
|
|
}
|
|
class kn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "isampler3D", value: e, update: s });
|
|
}
|
|
}
|
|
class Tn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "sampler3D", value: e, update: s });
|
|
}
|
|
}
|
|
class Un extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "usamplerCube", value: e, update: s });
|
|
}
|
|
}
|
|
class Gn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "isamplerCube", value: e, update: s });
|
|
}
|
|
}
|
|
class Rn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "samplerCube", value: e, update: s });
|
|
}
|
|
}
|
|
class Yn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "sampler2DShadow", value: e, update: s });
|
|
}
|
|
}
|
|
class Jn extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "sampler2DArrayShadow", value: e, update: s });
|
|
}
|
|
}
|
|
class _n extends N {
|
|
constructor({
|
|
key: A,
|
|
value: e,
|
|
update: s
|
|
}) {
|
|
super({ key: A, type: "samplerCubeShadow", value: e, update: s });
|
|
}
|
|
}
|
|
const Wt = new Float32Array(1), pe = new Uint32Array(Wt.buffer), es = "Float16Array" in globalThis, qt = es ? new globalThis.Float16Array(1) : null, Ln = new Uint16Array(qt == null ? void 0 : qt.buffer);
|
|
function zn(t) {
|
|
const A = Math.sqrt(t.reduce((e, s) => e + s * s, 0));
|
|
return t.map((e) => e / A);
|
|
}
|
|
function tg(t) {
|
|
return Wt[0] = t, pe[0];
|
|
}
|
|
function eg(t) {
|
|
return pe[0] = t, Wt[0];
|
|
}
|
|
const Ct = es ? sg : ng, wA = es ? ig : rg;
|
|
function sg(t) {
|
|
return qt[0] = t, Ln[0];
|
|
}
|
|
function ng(t) {
|
|
Wt[0] = t;
|
|
const A = pe[0], e = A >> 31 & 1, s = A >> 23 & 255, n = A & 8388607, i = e << 15;
|
|
if (s === 255)
|
|
return n !== 0 ? i | 32767 : i | 31744;
|
|
const r = s - 127 + 15;
|
|
if (r >= 31)
|
|
return i | 31744;
|
|
if (r <= 0) {
|
|
if (r < -10)
|
|
return i;
|
|
const o = (n | 8388608) >> 1 - r + 13;
|
|
return i | o;
|
|
}
|
|
const a = n >> 13;
|
|
return i | r << 10 | a;
|
|
}
|
|
function ig(t) {
|
|
return Ln[0] = t, qt[0];
|
|
}
|
|
function rg(t) {
|
|
const A = t >> 15 & 1, e = t >> 10 & 31, s = t & 1023;
|
|
let n;
|
|
if (e === 0)
|
|
if (s === 0)
|
|
n = A << 31;
|
|
else {
|
|
let i = s, r = -14;
|
|
for (; (i & 1024) === 0; )
|
|
i <<= 1, r--;
|
|
i &= 1023;
|
|
const a = r + 127, o = i << 13;
|
|
n = A << 31 | a << 23 | o;
|
|
}
|
|
else if (e === 31)
|
|
s === 0 ? n = A << 31 | 2139095040 : n = A << 31 | 2143289344;
|
|
else {
|
|
const i = e - 15 + 127, r = s << 13;
|
|
n = A << 31 | i << 23 | r;
|
|
}
|
|
return pe[0] = n, Wt[0];
|
|
}
|
|
function FA(t) {
|
|
return Math.max(0, Math.min(255, Math.round(t * 255)));
|
|
}
|
|
function ie(t) {
|
|
return Math.max(-127, Math.min(127, Math.round(t * 127)));
|
|
}
|
|
function ag(t) {
|
|
return t / 255;
|
|
}
|
|
function og(t) {
|
|
return t / 127;
|
|
}
|
|
class cg {
|
|
// Create a DataCache with a given function that fetches data not in the cache.
|
|
constructor({
|
|
asyncFetch: A,
|
|
maxItems: e = 5
|
|
}) {
|
|
this.asyncFetch = A, this.maxItems = e, this.items = [];
|
|
}
|
|
// Fetch data for the key, returning cached data if available.
|
|
async getFetch(A) {
|
|
const e = this.items.findIndex((n) => n.key === A);
|
|
if (e >= 0) {
|
|
const n = this.items.splice(e, 1)[0];
|
|
return this.items.push(n), n.data;
|
|
}
|
|
const s = await this.asyncFetch(A);
|
|
for (this.items.push({ key: A, data: s }); this.items.length > this.maxItems; )
|
|
this.items.shift();
|
|
return s;
|
|
}
|
|
}
|
|
function gg(t, A) {
|
|
const e = Object.entries(t).map(([s, n]) => [
|
|
s,
|
|
A(n, s)
|
|
]);
|
|
return Object.fromEntries(e);
|
|
}
|
|
function lg(t, A) {
|
|
const e = Object.entries(t).map(([s, n]) => [s, A(n, s)]).filter(([s, n]) => n !== void 0);
|
|
return Object.fromEntries(e);
|
|
}
|
|
function Hn(t) {
|
|
const A = [], e = /* @__PURE__ */ new Set();
|
|
function s(n) {
|
|
n && typeof n == "object" && !e.has(n) && (e.add(n), n instanceof ArrayBuffer ? A.push(n) : ArrayBuffer.isView(n) ? A.push(n.buffer) : Array.isArray(n) ? n.forEach(s) : Object.values(n).forEach(s));
|
|
}
|
|
return s(t), A;
|
|
}
|
|
function Ig(t, A) {
|
|
return new Array(t).fill(null).map((e, s) => A(s));
|
|
}
|
|
class qn {
|
|
constructor({
|
|
// Allocate a new item with the given args
|
|
allocate: A,
|
|
// Dispose of an item (optional, if GC is enough)
|
|
dispose: e,
|
|
// Check if an existing item in the list is valid for the given args,
|
|
// allowing you to store heterogeneous items in the list.
|
|
valid: s
|
|
}) {
|
|
this.items = [], this.allocate = A, this.dispose = e, this.valid = s;
|
|
}
|
|
// Allocate a new item from the free list, first checking if a existing item
|
|
// on the freelist is valid for the given args.
|
|
alloc(A) {
|
|
for (; ; ) {
|
|
const e = this.items.pop();
|
|
if (!e)
|
|
break;
|
|
if (this.valid(e, A))
|
|
return e;
|
|
this.dispose && this.dispose(e);
|
|
}
|
|
return this.allocate(A);
|
|
}
|
|
free(A) {
|
|
this.items.push(A);
|
|
}
|
|
disposeAll() {
|
|
let A;
|
|
for (A = this.items.pop(); A; )
|
|
this.dispose && this.dispose(A), A = this.items.pop();
|
|
}
|
|
}
|
|
function Ye(t, A, e, s, n, i, r, a, o, g, l, c, I, h, E, C, B) {
|
|
const Q = (B == null ? void 0 : B.rgbMin) ?? 0, p = ((B == null ? void 0 : B.rgbMax) ?? 1) - Q, d = FA((h - Q) / p), y = FA((E - Q) / p), D = FA((C - Q) / p), x = FA(I), w = ss(
|
|
Kn.set(o, g, l, c)
|
|
), m = w & 255, k = w >>> 8 & 255, M = w >>> 16 & 255, S = (B == null ? void 0 : B.lnScaleMin) ?? UA, F = 254 / (((B == null ? void 0 : B.lnScaleMax) ?? GA) - S), b = i < It ? 0 : Math.min(
|
|
255,
|
|
Math.max(
|
|
1,
|
|
Math.round((Math.log(i) - S) * F) + 1
|
|
)
|
|
), T = r < It ? 0 : Math.min(
|
|
255,
|
|
Math.max(
|
|
1,
|
|
Math.round((Math.log(r) - S) * F) + 1
|
|
)
|
|
), R = a < It ? 0 : Math.min(
|
|
255,
|
|
Math.max(
|
|
1,
|
|
Math.round((Math.log(a) - S) * F) + 1
|
|
)
|
|
), X = Ct(e), _ = Ct(s), eA = Ct(n), q = A * 4;
|
|
t[q] = d | y << 8 | D << 16 | x << 24, t[q + 1] = X | _ << 16, t[q + 2] = eA | m << 16 | k << 24, t[q + 3] = b | T << 8 | R << 16 | M << 24;
|
|
}
|
|
function ug(t, A, e, s, n) {
|
|
const i = Ct(e), r = Ct(s), a = Ct(n), o = A * 4;
|
|
t[o + 1] = i | r << 16, t[o + 2] = a | t[o + 2] & 4294901760;
|
|
}
|
|
function hg(t, A, e, s, n, i) {
|
|
const r = (i == null ? void 0 : i.lnScaleMin) ?? UA, o = 254 / (((i == null ? void 0 : i.lnScaleMax) ?? GA) - r), g = e < It ? 0 : Math.min(
|
|
255,
|
|
Math.max(
|
|
1,
|
|
Math.round((Math.log(e) - r) * o) + 1
|
|
)
|
|
), l = s < It ? 0 : Math.min(
|
|
255,
|
|
Math.max(
|
|
1,
|
|
Math.round((Math.log(s) - r) * o) + 1
|
|
)
|
|
), c = n < It ? 0 : Math.min(
|
|
255,
|
|
Math.max(
|
|
1,
|
|
Math.round((Math.log(n) - r) * o) + 1
|
|
)
|
|
), I = A * 4;
|
|
t[I + 3] = g | l << 8 | c << 16 | t[I + 3] & 4278190080;
|
|
}
|
|
const Kn = new u.Quaternion();
|
|
function Cg(t, A, e, s, n, i) {
|
|
const r = ss(
|
|
Kn.set(e, s, n, i)
|
|
), a = r & 255, o = r >>> 8 & 255, g = r >>> 16 & 255, l = A * 4;
|
|
t[l + 2] = t[l + 2] & 65535 | a << 16 | o << 24, t[l + 3] = t[l + 3] & 16777215 | g << 24;
|
|
}
|
|
function Bg(t, A, e, s, n, i, r) {
|
|
const a = (r == null ? void 0 : r.rgbMin) ?? 0, g = ((r == null ? void 0 : r.rgbMax) ?? 1) - a, l = FA((e - a) / g), c = FA((s - a) / g), I = FA((n - a) / g), h = FA(i), E = A * 4;
|
|
t[E] = l | c << 8 | I << 16 | h << 24;
|
|
}
|
|
function Eg(t, A, e, s, n, i) {
|
|
const r = (i == null ? void 0 : i.rgbMin) ?? 0, o = ((i == null ? void 0 : i.rgbMax) ?? 1) - r, g = FA((e - r) / o), l = FA((s - r) / o), c = FA((n - r) / o), I = A * 4;
|
|
t[I] = g | l << 8 | c << 16 | t[I] & 4278190080;
|
|
}
|
|
function Qg(t, A, e) {
|
|
const s = FA(e), n = A * 4;
|
|
t[n] = t[n] & 16777215 | s << 24;
|
|
}
|
|
const pg = new u.Vector3(), fg = new u.Vector3(), dg = new u.Quaternion(), yg = new u.Color(), wg = {
|
|
center: pg,
|
|
scales: fg,
|
|
quaternion: dg,
|
|
color: yg,
|
|
opacity: 0
|
|
};
|
|
function Je(t, A, e) {
|
|
const s = wg, n = A * 4, i = t[n], r = t[n + 1], a = t[n + 2], o = t[n + 3], g = (e == null ? void 0 : e.rgbMin) ?? 0, c = ((e == null ? void 0 : e.rgbMax) ?? 1) - g;
|
|
s.color.set(
|
|
g + (i & 255) / 255 * c,
|
|
g + (i >>> 8 & 255) / 255 * c,
|
|
g + (i >>> 16 & 255) / 255 * c
|
|
), s.opacity = (i >>> 24 & 255) / 255, s.center.set(
|
|
wA(r & 65535),
|
|
wA(r >>> 16 & 65535),
|
|
wA(a & 65535)
|
|
);
|
|
const I = (e == null ? void 0 : e.lnScaleMin) ?? UA, E = (((e == null ? void 0 : e.lnScaleMax) ?? GA) - I) / 254, C = o & 255;
|
|
s.scales.x = C === 0 ? 0 : Math.exp(I + (C - 1) * E);
|
|
const B = o >>> 8 & 255;
|
|
s.scales.y = B === 0 ? 0 : Math.exp(I + (B - 1) * E);
|
|
const Q = o >>> 16 & 255;
|
|
s.scales.z = Q === 0 ? 0 : Math.exp(I + (Q - 1) * E);
|
|
const f = a >>> 16 & 65535 | o >>> 8 & 16711680;
|
|
return jn(f, s.quaternion), s;
|
|
}
|
|
function mA(t) {
|
|
const A = Z, e = Math.max(
|
|
je,
|
|
Math.min(KA, Math.ceil(t / A))
|
|
), s = Math.ceil(t / (A * e)), n = A * e * s;
|
|
return { width: A, height: e, depth: s, maxSplats: n };
|
|
}
|
|
function mg(t) {
|
|
const A = Z, e = Math.max(
|
|
je,
|
|
Math.min(KA, Math.ceil(t / A))
|
|
), s = Math.ceil(t / (A * e));
|
|
return A * e * s;
|
|
}
|
|
function xg() {
|
|
return navigator.maxTouchPoints > 0 ? !0 : /Mobi|Android|iPhone|iPad|iPod|Opera Mini|IEMobile/.test(
|
|
navigator.userAgent
|
|
);
|
|
}
|
|
function Sg() {
|
|
return /Android/.test(navigator.userAgent);
|
|
}
|
|
function Dg() {
|
|
return /Oculus/.test(navigator.userAgent);
|
|
}
|
|
function Mg(t, A, e) {
|
|
const s = new Uint8Array(A * 4);
|
|
for (let n = 0; n < e / 2; n++) {
|
|
const i = n * A * 4, r = (e - 1 - n) * A * 4;
|
|
s.set(t.subarray(i, i + A * 4)), t.set(
|
|
t.subarray(r, r + A * 4),
|
|
i
|
|
), t.set(s, r);
|
|
}
|
|
return t;
|
|
}
|
|
function vg(t, A, e) {
|
|
const s = document.createElement("canvas");
|
|
s.width = A, s.height = e;
|
|
const n = s.getContext("2d");
|
|
if (!n)
|
|
throw new Error("Can't get 2d context");
|
|
const i = n.createImageData(A, e);
|
|
return i.data.set(t), n.putImageData(i, 0, 0), s.toDataURL("image/png");
|
|
}
|
|
function $n(t) {
|
|
const A = new u.Clock(t.autoStart);
|
|
return A.startTime = t.startTime, A.oldTime = t.oldTime, A.elapsedTime = t.elapsedTime, A.running = t.running, A;
|
|
}
|
|
function bg(t) {
|
|
return Object.fromEntries(
|
|
Object.entries(t).filter(([A, e]) => e !== void 0)
|
|
);
|
|
}
|
|
const Vn = hA(`
|
|
precision highp float;
|
|
|
|
in vec3 position;
|
|
|
|
void main() {
|
|
gl_Position = vec4(position.xy, 0.0, 1.0);
|
|
}
|
|
`);
|
|
function Pn(t) {
|
|
const A = new u.Vector3();
|
|
for (const e of t)
|
|
A.add(e);
|
|
return A.divideScalar(t.length);
|
|
}
|
|
function Zn(t) {
|
|
if (t.length === 0)
|
|
return new u.Quaternion();
|
|
const A = t[0].clone();
|
|
for (let e = 1; e < t.length; e++)
|
|
t[e].dot(t[0]) < 0 ? (A.x -= t[e].x, A.y -= t[e].y, A.z -= t[e].z, A.w -= t[e].w) : (A.x += t[e].x, A.y += t[e].y, A.z += t[e].z, A.w += t[e].w);
|
|
return A.normalize();
|
|
}
|
|
function Xn(t, A) {
|
|
const e = new u.Vector3(0, 0, 0).applyMatrix4(t), s = new u.Vector3(0, 0, 0).applyMatrix4(A), n = new u.Vector3(0, 0, -1).applyMatrix4(t).sub(e).normalize(), i = new u.Vector3(0, 0, -1).applyMatrix4(A).sub(s).normalize(), r = e.distanceTo(s), a = n.dot(i);
|
|
return { distance: r, coincidence: a };
|
|
}
|
|
function Fg({
|
|
matrix1: t,
|
|
matrix2: A,
|
|
maxDistance: e
|
|
}) {
|
|
const s = new u.Vector3(0, 0, 0).applyMatrix4(t), n = new u.Vector3(0, 0, 0).applyMatrix4(A);
|
|
return s.distanceTo(n) <= e;
|
|
}
|
|
function Ng({
|
|
matrix1: t,
|
|
matrix2: A,
|
|
maxDistance: e,
|
|
minCoincidence: s
|
|
}) {
|
|
const { distance: n, coincidence: i } = Xn(t, A);
|
|
return n <= e && (s == null || i >= s);
|
|
}
|
|
function On(t, A) {
|
|
const [e, s] = [new u.Vector3(), new u.Quaternion()], [n, i] = [new u.Vector3(), new u.Quaternion()];
|
|
t.decompose(e, s, new u.Vector3()), A.decompose(n, i, new u.Vector3());
|
|
const r = e.distanceTo(n), a = Math.abs(s.dot(i));
|
|
return { distance: r, coorient: a };
|
|
}
|
|
function ge({
|
|
matrix1: t,
|
|
matrix2: A,
|
|
maxDistance: e,
|
|
minCoorient: s
|
|
}) {
|
|
const { distance: n, coorient: i } = On(t, A);
|
|
return n <= e && (s == null || i >= s);
|
|
}
|
|
function kg(t, A = 1e-3) {
|
|
return Math.abs(t) < A ? 0 : Math.sign(t);
|
|
}
|
|
function Tg(t) {
|
|
const A = t.w < 0, e = ie(A ? -t.x : t.x), s = ie(A ? -t.y : t.y), n = ie(A ? -t.z : t.z), i = e & 255, r = s & 255, a = n & 255;
|
|
return i | r << 8 | a << 16;
|
|
}
|
|
function Ug(t, A) {
|
|
const e = t << 24 >> 24, s = t << 16 >> 24, n = t << 8 >> 24;
|
|
A.set(e / 127, s / 127, n / 127, 0);
|
|
const i = A.x * A.x + A.y * A.y + A.z * A.z;
|
|
return A.w = Math.sqrt(Math.max(0, 1 - i)), A;
|
|
}
|
|
const Gg = new u.Quaternion(), _e = new u.Vector3();
|
|
function ss(t) {
|
|
const A = Gg.copy(t).normalize();
|
|
A.w < 0 && A.set(-A.x, -A.y, -A.z, -A.w);
|
|
const e = 2 * Math.acos(A.w), s = Math.sqrt(
|
|
A.x * A.x + A.y * A.y + A.z * A.z
|
|
), n = s < 1e-6 ? _e.set(1, 0, 0) : _e.set(A.x, A.y, A.z).divideScalar(s), i = Math.abs(n.x) + Math.abs(n.y) + Math.abs(n.z);
|
|
let r = n.x / i, a = n.y / i;
|
|
if (n.z < 0) {
|
|
const h = r;
|
|
r = (1 - Math.abs(a)) * (r >= 0 ? 1 : -1), a = (1 - Math.abs(h)) * (a >= 0 ? 1 : -1);
|
|
}
|
|
const o = r * 0.5 + 0.5, g = a * 0.5 + 0.5, l = Math.round(o * 255), c = Math.round(g * 255);
|
|
return Math.round(e * (255 / Math.PI)) << 16 | c << 8 | l;
|
|
}
|
|
function jn(t, A) {
|
|
const e = t & 255, s = t >>> 8 & 255, n = t >>> 16 & 255, i = e / 255, r = s / 255;
|
|
let a = (i - 0.5) * 2, o = (r - 0.5) * 2;
|
|
const g = 1 - (Math.abs(a) + Math.abs(o)), l = Math.max(-g, 0);
|
|
a += a >= 0 ? -l : l, o += o >= 0 ? -l : l;
|
|
const c = _e.set(a, o, g).normalize(), h = n / 255 * Math.PI * 0.5, E = Math.sin(h), C = Math.cos(h);
|
|
return A.set(c.x * E, c.y * E, c.z * E, C), A;
|
|
}
|
|
function Rg(t) {
|
|
const A = t.clone().normalize(), e = 2 * (A.w * A.x + A.y * A.z), s = 1 - 2 * (A.x * A.x + A.y * A.y), n = Math.atan2(e, s), i = 2 * (A.w * A.y - A.z * A.x), r = Math.abs(i) >= 1 ? Math.sign(i) * (Math.PI / 2) : Math.asin(i), a = 2 * (A.w * A.z + A.x * A.y), o = 1 - 2 * (A.y * A.y + A.z * A.z), g = Math.atan2(a, o), l = (n + Math.PI) / (2 * Math.PI), c = (r + Math.PI) / (2 * Math.PI), I = (g + Math.PI) / (2 * Math.PI), h = Math.round(l * 255), E = Math.round(c * 255);
|
|
return Math.round(I * 255) << 16 | E << 8 | h;
|
|
}
|
|
function Yg(t, A) {
|
|
const e = t & 255, s = t >>> 8 & 255, n = t >>> 16 & 255, i = e / 255, r = s / 255, a = n / 255, o = i * (2 * Math.PI) - Math.PI, g = r * (2 * Math.PI) - Math.PI, l = a * (2 * Math.PI) - Math.PI, c = Math.cos(o * 0.5), I = Math.sin(o * 0.5), h = Math.cos(g * 0.5), E = Math.sin(g * 0.5), C = Math.cos(l * 0.5), B = Math.sin(l * 0.5);
|
|
return A.w = c * h * C + I * E * B, A.x = I * h * C - c * E * B, A.y = c * E * C + I * h * B, A.z = c * h * B - I * E * C, A.normalize(), A;
|
|
}
|
|
function te(t, A, e, s) {
|
|
const n = Math.max(-127, Math.min(127, t * 127)), i = Math.max(-127, Math.min(127, A * 127)), r = Math.max(-127, Math.min(127, e * 127)), a = Math.max(-127, Math.min(127, s * 127));
|
|
return n & 255 | (i & 255) << 8 | (r & 255) << 16 | (a & 255) << 24;
|
|
}
|
|
function Jg(t, A, e, s) {
|
|
const n = (s == null ? void 0 : s.sh1Min) ?? -1, i = (s == null ? void 0 : s.sh1Max) ?? 1, r = 0.5 * (n + i), a = 126 / (i - n), o = A * 2;
|
|
for (let g = 0; g < 9; ++g) {
|
|
const l = (e[g] - r) * a, c = Math.round(Math.max(-63, Math.min(63, l))) & 127, I = g * 7, h = I + 7, E = Math.floor(I / 32), C = I - E * 32, B = c << C & 4294967295;
|
|
if (t[o + E] |= B, h > E * 32 + 32) {
|
|
const Q = c >>> 32 - C & 4294967295;
|
|
t[o + E + 1] |= Q;
|
|
}
|
|
}
|
|
}
|
|
function _g(t, A, e, s) {
|
|
const n = (s == null ? void 0 : s.sh2Min) ?? -1, i = (s == null ? void 0 : s.sh2Max) ?? 1, r = 0.5 * (n + i), a = 2 / (i - n);
|
|
t[A * 4 + 0] = te(
|
|
(e[0] - r) * a,
|
|
(e[1] - r) * a,
|
|
(e[2] - r) * a,
|
|
(e[3] - r) * a
|
|
), t[A * 4 + 1] = te(
|
|
(e[4] - r) * a,
|
|
(e[5] - r) * a,
|
|
(e[6] - r) * a,
|
|
(e[7] - r) * a
|
|
), t[A * 4 + 2] = te(
|
|
(e[8] - r) * a,
|
|
(e[9] - r) * a,
|
|
(e[10] - r) * a,
|
|
(e[11] - r) * a
|
|
), t[A * 4 + 3] = te(
|
|
(e[12] - r) * a,
|
|
(e[13] - r) * a,
|
|
(e[14] - r) * a,
|
|
0
|
|
);
|
|
}
|
|
function Lg(t, A, e, s) {
|
|
const n = (s == null ? void 0 : s.sh3Min) ?? -1, i = (s == null ? void 0 : s.sh3Max) ?? 1, r = 0.5 * (n + i), a = 62 / (i - n), o = A * 4;
|
|
for (let g = 0; g < 21; ++g) {
|
|
const l = (e[g] - r) * a, c = Math.round(Math.max(-31, Math.min(31, l))) & 63, I = g * 6, h = I + 6, E = Math.floor(I / 32), C = I - E * 32, B = c << C & 4294967295;
|
|
if (t[o + E] |= B, h > E * 32 + 32) {
|
|
const Q = c >>> 32 - C & 4294967295;
|
|
t[o + E + 1] |= Q;
|
|
}
|
|
}
|
|
}
|
|
function Wn(t, A) {
|
|
const e = [];
|
|
let s = 0, n = null;
|
|
const i = new Yo((o, g) => {
|
|
if (e.push(o), s += o.length, g || s >= A) {
|
|
const l = new Uint8Array(s);
|
|
let c = 0;
|
|
for (const I of e)
|
|
l.set(I, c), c += I.length;
|
|
n = l.slice(0, A);
|
|
}
|
|
}), r = 1024;
|
|
let a = 0;
|
|
for (; n == null && a < t.length; ) {
|
|
const o = t.slice(a, a + r);
|
|
i.push(o, !1), a += r;
|
|
}
|
|
if (n == null && (i.push(new Uint8Array(), !0), n == null))
|
|
throw new Error("Failed to decompress partial gzip");
|
|
return n;
|
|
}
|
|
class Ai {
|
|
constructor({
|
|
fileBytes: A,
|
|
chunkBytes: e = 64 * 1024
|
|
}) {
|
|
this.fileBytes = A, this.chunkBytes = e, this.chunks = [], this.totalBytes = 0;
|
|
const s = new DecompressionStream("gzip"), n = new Blob([A]).stream().pipeThrough(s);
|
|
this.reader = n.getReader();
|
|
}
|
|
async read(A) {
|
|
for (; this.totalBytes < A; ) {
|
|
const { value: i, done: r } = await this.reader.read();
|
|
if (r)
|
|
break;
|
|
this.chunks.push(i), this.totalBytes += i.length;
|
|
}
|
|
if (this.totalBytes < A)
|
|
throw new Error(
|
|
`Unexpected EOF: needed ${A}, got ${this.totalBytes}`
|
|
);
|
|
const e = new Uint8Array(this.totalBytes);
|
|
let s = 0;
|
|
for (const i of this.chunks)
|
|
e.set(i, s), s += i.length;
|
|
const n = e.subarray(0, A);
|
|
return this.chunks = [e.subarray(A)], this.totalBytes -= A, n;
|
|
}
|
|
}
|
|
const Vh = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
__proto__: null,
|
|
DataCache: cg,
|
|
FreeList: qn,
|
|
GunzipReader: Ai,
|
|
IDENT_VERTEX_SHADER: Vn,
|
|
Sint8ToFloat: og,
|
|
Uint8ToFloat: ag,
|
|
averagePositions: Pn,
|
|
averageQuaternions: Zn,
|
|
cloneClock: $n,
|
|
coinciDist: Xn,
|
|
computeMaxSplats: mg,
|
|
coorientDist: On,
|
|
decodeQuatEulerXyz888: Yg,
|
|
decodeQuatOctXy88R8: jn,
|
|
decodeQuatXyz888: Ug,
|
|
decompressPartialGzip: Wn,
|
|
encodeQuatEulerXyz888: Rg,
|
|
encodeQuatOctXy88R8: ss,
|
|
encodeQuatXyz888: Tg,
|
|
encodeSh1Rgb: Jg,
|
|
encodeSh2Rgb: _g,
|
|
encodeSh3Rgb: Lg,
|
|
epsilonSign: kg,
|
|
flipPixels: Mg,
|
|
floatBitsToUint: tg,
|
|
floatToSint8: ie,
|
|
floatToUint8: FA,
|
|
fromHalf: wA,
|
|
getArrayBuffers: Hn,
|
|
getTextureSize: mA,
|
|
isAndroid: Sg,
|
|
isMobile: xg,
|
|
isOculus: Dg,
|
|
mapFilterObject: lg,
|
|
mapObject: gg,
|
|
newArray: Ig,
|
|
normalize: zn,
|
|
omitUndefined: bg,
|
|
pixelsToPngUrl: vg,
|
|
setPackedSplat: Ye,
|
|
setPackedSplatCenter: ug,
|
|
setPackedSplatOpacity: Qg,
|
|
setPackedSplatQuat: Cg,
|
|
setPackedSplatRgb: Eg,
|
|
setPackedSplatRgba: Bg,
|
|
setPackedSplatScales: hg,
|
|
toHalf: Ct,
|
|
uintBitsToFloat: eg,
|
|
unpackSplat: Je,
|
|
withinCoinciDist: Ng,
|
|
withinCoorientDist: ge,
|
|
withinDist: Fg
|
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
class ns {
|
|
constructor({
|
|
graph: A,
|
|
inputs: e,
|
|
outputs: s,
|
|
template: n
|
|
}) {
|
|
this.graph = A, this.template = n, this.inputs = e ?? {}, this.outputs = s ?? {};
|
|
const i = new Ks({ indent: this.template.indent });
|
|
for (const a in this.outputs)
|
|
this.outputs[a] && i.declares.add(this.outputs[a]);
|
|
const r = A.compile({
|
|
inputs: this.inputs,
|
|
outputs: this.outputs,
|
|
compile: i
|
|
});
|
|
this.shader = n.generate({ globals: i.globals, statements: r }), this.uniforms = i.uniforms, this.updaters = i.updaters;
|
|
}
|
|
prepareMaterial() {
|
|
return zg(this);
|
|
}
|
|
update() {
|
|
for (const A of this.updaters)
|
|
A();
|
|
}
|
|
}
|
|
class is {
|
|
constructor(A) {
|
|
const e = A.match(/^([ \t]*)\{\{\s*GLOBALS\s*\}\}/m), s = A.match(/^([ \t]*)\{\{\s*STATEMENTS\s*\}\}/m);
|
|
if (!e || !s)
|
|
throw new Error(
|
|
"Template must contain {{ GLOBALS }} and {{ STATEMENTS }}"
|
|
);
|
|
this.before = A.substring(0, e.index), this.between = A.substring(
|
|
e.index + e[0].length,
|
|
s.index
|
|
), this.after = A.substring(
|
|
s.index + s[0].length
|
|
), this.indent = s[1];
|
|
}
|
|
generate({
|
|
globals: A,
|
|
statements: e
|
|
}) {
|
|
return this.before + Array.from(A).join(`
|
|
|
|
`) + this.between + e.map((s) => this.indent + s).join(`
|
|
`) + this.after;
|
|
}
|
|
}
|
|
const Es = /* @__PURE__ */ new Map();
|
|
function zg(t) {
|
|
let A = Es.get(t);
|
|
return A || (A = new u.RawShaderMaterial({
|
|
glslVersion: u.GLSL3,
|
|
vertexShader: Vn,
|
|
fragmentShader: t.shader,
|
|
uniforms: t.uniforms
|
|
}), Es.set(t, A), A);
|
|
}
|
|
function rs(t, A, e = "add") {
|
|
const s = () => {
|
|
throw new Error(`Invalid ${e} types: ${t}, ${A}`);
|
|
};
|
|
if (t === A) return t;
|
|
if (t === "int") {
|
|
if (EA(A)) return A;
|
|
s();
|
|
}
|
|
if (A === "int") {
|
|
if (EA(t)) return t;
|
|
s();
|
|
}
|
|
if (t === "uint") {
|
|
if (QA(A)) return A;
|
|
s();
|
|
}
|
|
if (A === "uint") {
|
|
if (QA(t)) return t;
|
|
s();
|
|
}
|
|
if (t === "float") {
|
|
if (at(A)) return A;
|
|
s();
|
|
}
|
|
if (A === "float") {
|
|
if (at(t)) return t;
|
|
s();
|
|
}
|
|
throw new Error(`Invalid ${e} types: ${t}, ${A}`);
|
|
}
|
|
function Hg(t, A) {
|
|
return rs(t, A, "sub");
|
|
}
|
|
function qg(t, A) {
|
|
const e = () => {
|
|
throw new Error(`Invalid mul types: ${t}, ${A}`);
|
|
}, s = (n) => n;
|
|
if (t === "int") {
|
|
if (EA(A)) return s(A);
|
|
e();
|
|
}
|
|
if (A === "int") {
|
|
if (EA(t)) return s(t);
|
|
e();
|
|
}
|
|
if (t === "uint") {
|
|
if (QA(A)) return s(A);
|
|
e();
|
|
}
|
|
if (A === "uint") {
|
|
if (QA(t)) return s(t);
|
|
e();
|
|
}
|
|
if (t === "float") {
|
|
if (at(A)) return s(A);
|
|
e();
|
|
}
|
|
if (A === "float") {
|
|
if (at(t)) return s(t);
|
|
e();
|
|
}
|
|
if (EA(t) || QA(t) || EA(A) || QA(A)) {
|
|
if (t === A) return s(t);
|
|
e();
|
|
}
|
|
if (t === "vec2") {
|
|
if (A === "vec2" || ot(A)) return s("vec2");
|
|
if (A === "mat3x2") return s("vec3");
|
|
if (A === "mat4x2") return s("vec4");
|
|
e();
|
|
}
|
|
if (t === "vec3") {
|
|
if (A === "mat2x3") return s("vec2");
|
|
if (A === "vec3" || ct(A)) return s("vec3");
|
|
if (A === "mat4x3") return s("vec4");
|
|
e();
|
|
}
|
|
if (t === "vec4") {
|
|
if (A === "mat2x4") return s("vec2");
|
|
if (A === "mat3x4") return s("vec3");
|
|
if (A === "vec4" || gt(A)) return s("vec4");
|
|
e();
|
|
}
|
|
if (A === "vec2") {
|
|
if (ot(t)) return s("vec2");
|
|
if (t === "mat2x3") return s("vec3");
|
|
if (t === "mat2x4") return s("vec4");
|
|
e();
|
|
}
|
|
if (A === "vec3") {
|
|
if (t === "mat3x2") return s("vec2");
|
|
if (ct(t)) return s("vec3");
|
|
if (t === "mat3x4") return s("vec4");
|
|
e();
|
|
}
|
|
if (A === "vec4") {
|
|
if (t === "mat4x2") return s("vec2");
|
|
if (t === "mat4x3") return s("vec3");
|
|
if (gt(t)) return s("vec4");
|
|
e();
|
|
}
|
|
if (ot(t)) {
|
|
if (ot(A)) return s("mat2");
|
|
if (A === "mat3x2") return s("mat3x2");
|
|
if (A === "mat4x2") return s("mat4x2");
|
|
e();
|
|
}
|
|
if (t === "mat2x3") {
|
|
if (ot(A)) return s("mat2x3");
|
|
if (A === "mat3x2") return s("mat3");
|
|
if (A === "mat4x2") return s("mat4x3");
|
|
e();
|
|
}
|
|
if (t === "mat2x4") {
|
|
if (ot(A)) return s("mat2x4");
|
|
if (A === "mat3x2") return s("mat3x4");
|
|
if (A === "mat4x2") return s("mat4");
|
|
e();
|
|
}
|
|
if (t === "mat3x2") {
|
|
if (A === "mat2x3") return s("mat2");
|
|
if (ct(A)) return s("mat3x2");
|
|
if (A === "mat4x3") return s("mat4x2");
|
|
e();
|
|
}
|
|
if (ct(t)) {
|
|
if (A === "mat2x3") return s("mat2x3");
|
|
if (ct(A)) return s("mat3");
|
|
if (A === "mat4x3") return s("mat4x3");
|
|
e();
|
|
}
|
|
if (t === "mat3x4") {
|
|
if (A === "mat2x3") return s("mat2x4");
|
|
if (ct(A)) return s("mat3x4");
|
|
if (A === "mat4x3") return s("mat4");
|
|
e();
|
|
}
|
|
if (t === "mat4x2") {
|
|
if (A === "mat2x4") return s("mat2");
|
|
if (A === "mat3x4") return s("mat3x2");
|
|
if (gt(A)) return s("mat4x2");
|
|
e();
|
|
}
|
|
if (t === "mat4x3") {
|
|
if (A === "mat2x4") return s("mat2x3");
|
|
if (A === "mat3x4") return s("mat3");
|
|
if (gt(A)) return s("mat4x3");
|
|
e();
|
|
}
|
|
if (gt(t)) {
|
|
if (A === "mat2x4") return s("mat2x4");
|
|
if (A === "mat3x4") return s("mat3x4");
|
|
if (gt(A)) return s("mat4");
|
|
e();
|
|
}
|
|
throw new Error(`Invalid mul types: ${t}, ${A}`);
|
|
}
|
|
function Kg(t, A) {
|
|
return rs(t, A, "div");
|
|
}
|
|
function $g(t, A) {
|
|
if (t === A) return t;
|
|
if (t === "int") {
|
|
if (EA(A)) return A;
|
|
} else if (A === "int") {
|
|
if (EA(t)) return t;
|
|
} else if (t === "uint") {
|
|
if (QA(A)) return A;
|
|
} else if (A === "uint" && QA(t))
|
|
return t;
|
|
throw new Error(`Invalid imod types: ${t}, ${A}`);
|
|
}
|
|
function Vg(t, A) {
|
|
if (t === A || A === "float") return t;
|
|
throw new Error(`Invalid mod types: ${t}, ${A}`);
|
|
}
|
|
function Pg(t) {
|
|
return t;
|
|
}
|
|
function Zg(t) {
|
|
return t;
|
|
}
|
|
function Xg(t) {
|
|
return t;
|
|
}
|
|
function Og(t) {
|
|
return t;
|
|
}
|
|
function jg(t) {
|
|
return t;
|
|
}
|
|
function Wg(t) {
|
|
return t;
|
|
}
|
|
function Al(t) {
|
|
return t;
|
|
}
|
|
function tl(t) {
|
|
return t;
|
|
}
|
|
function el(t) {
|
|
return t;
|
|
}
|
|
function sl(t) {
|
|
return t;
|
|
}
|
|
function nl(t) {
|
|
return t;
|
|
}
|
|
function il(t) {
|
|
return t;
|
|
}
|
|
function rl(t) {
|
|
return t;
|
|
}
|
|
function al(t) {
|
|
return t;
|
|
}
|
|
function ol(t) {
|
|
return t;
|
|
}
|
|
function cl(t) {
|
|
return t;
|
|
}
|
|
function ti(t, A, e = "min") {
|
|
if (t === A) return t;
|
|
if (A === "float") {
|
|
if (Zt(t)) return t;
|
|
} else if (A === "int") {
|
|
if (EA(t)) return t;
|
|
} else if (A === "uint" && QA(t))
|
|
return t;
|
|
throw new Error(`Invalid ${e} types: ${t}, ${A}`);
|
|
}
|
|
function gl(t, A) {
|
|
return ti(t, A, "max");
|
|
}
|
|
function ll(t, A, e) {
|
|
if (A === "float") {
|
|
if (Zt(t)) return t;
|
|
} else if (A === "int") {
|
|
if (EA(t)) return t;
|
|
} else if (A === "uint" && QA(t))
|
|
return t;
|
|
throw new Error(`Invalid clamp types: ${t}, ${A}`);
|
|
}
|
|
function Il(t, A, e) {
|
|
if (e === t || e === "float" || e === "bool" && t === "float" || e === "bvec2" && t === "vec2" || e === "bvec3" && t === "vec3" || e === "bvec4" && t === "vec4") return t;
|
|
throw new Error(`Invalid mix types: ${t}, ${A}, ${e}`);
|
|
}
|
|
function ul(t, A) {
|
|
if (t === A || A === "float") return A;
|
|
throw new Error(`Invalid step types: ${t}, ${A}`);
|
|
}
|
|
function hl(t, A, e) {
|
|
if (t === A && (t === e || t === "float"))
|
|
return e;
|
|
throw new Error(`Invalid smoothstep types: ${t}, ${A}, ${e}`);
|
|
}
|
|
function ei(t, A = "isNan") {
|
|
if (t === "float") return "bool";
|
|
if (t === "vec2") return "bvec2";
|
|
if (t === "vec3") return "bvec3";
|
|
if (t === "vec4") return "bvec4";
|
|
throw new Error(`Invalid ${A} types: ${t}`);
|
|
}
|
|
function Cl(t) {
|
|
return ei(t, "isInf");
|
|
}
|
|
const BA = (t, A) => new ri({ a: t, b: A }), Qt = (t, A) => new ai({ a: t, b: A }), iA = (t, A) => new oi({ a: t, b: A }), re = (t, A) => new ci({ a: t, b: A }), Le = (t, A) => new gi({ a: t, b: A }), si = (t, A) => new li({ a: t, b: A }), Bl = (t) => new Ii({ a: t }).outputs, as = (t) => new ui({ a: t }), El = (t) => new hi({ a: t }), Ql = (t) => new Ci({ a: t }), pl = (t) => new Bi({ a: t }), fl = (t) => new Ei({ a: t }), dl = (t) => new Qi({ a: t }), yl = (t) => new pi({ a: t }), ae = (t) => new fi({ a: t }), wl = (t, A) => new di({ a: t, b: A }), ml = (t) => new yi({ a: t }), xl = (t) => new wi({ a: t }), Sl = (t) => new mi({ a: t }), Dl = (t) => new xi({ a: t }), Ml = (t) => new Si({ a: t }), vl = (t) => new Di({ a: t }), bl = (t) => new Mi({ a: t }), Fl = (t, A) => new vi({ a: t, b: A }), ni = (t, A) => new bi({ a: t, b: A }), Nl = (t, A, e) => new Fi({ a: t, min: A, max: e }), ii = (t, A, e) => new Ni({ a: t, b: A, t: e }), kl = (t, A) => new ki({ edge: t, x: A }), Tl = (t, A, e) => new Ti({ edge0: t, edge1: A, x: e }), Ul = (t) => new Ui({ a: t }), Gl = (t) => new Gi({ a: t });
|
|
class ri extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "sum", outTypeFunc: rs }), this.statements = ({ inputs: s, outputs: n }) => [`${n.sum} = ${s.a} + ${s.b};`];
|
|
}
|
|
}
|
|
class ai extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "difference", outTypeFunc: Hg }), this.statements = ({ inputs: s, outputs: n }) => [`${n.difference} = ${s.a} - ${s.b};`];
|
|
}
|
|
}
|
|
class oi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "product", outTypeFunc: qg }), this.statements = ({ inputs: s, outputs: n }) => [`${n.product} = ${s.a} * ${s.b};`];
|
|
}
|
|
}
|
|
class ci extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "quotient", outTypeFunc: Kg }), this.statements = ({ inputs: s, outputs: n }) => [`${n.quotient} = ${s.a} / ${s.b};`];
|
|
}
|
|
}
|
|
class gi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "remainder", outTypeFunc: $g }), this.statements = ({ inputs: s, outputs: n }) => [`${n.remainder} = ${s.a} % ${s.b};`];
|
|
}
|
|
}
|
|
class li extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "remainder", outTypeFunc: Vg }), this.statements = ({ inputs: s, outputs: n }) => [`${n.remainder} = mod(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class Ii extends V {
|
|
constructor({ a: A }) {
|
|
const e = { a: $(A) }, s = e.a, n = {
|
|
fract: s,
|
|
integer: s
|
|
};
|
|
super({ inTypes: e, outTypes: n, inputs: { a: A } }), this.statements = ({ inputs: i, outputs: r }) => [`${r.fract} = modf(${i.a}, ${r.integer});`];
|
|
}
|
|
}
|
|
class ui extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "neg", outTypeFunc: Pg }), this.statements = ({ inputs: e, outputs: s }) => [`${s.neg} = -${e.a};`];
|
|
}
|
|
}
|
|
class hi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "abs", outTypeFunc: Zg }), this.statements = ({ inputs: e, outputs: s }) => [`${s.abs} = abs(${e.a});`];
|
|
}
|
|
}
|
|
class Ci extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "sign", outTypeFunc: Xg }), this.statements = ({ inputs: e, outputs: s }) => [`${s.sign} = sign(${e.a});`];
|
|
}
|
|
}
|
|
class Bi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "floor", outTypeFunc: Og }), this.statements = ({ inputs: e, outputs: s }) => [`${s.floor} = floor(${e.a});`];
|
|
}
|
|
}
|
|
class Ei extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "ceil", outTypeFunc: jg }), this.statements = ({ inputs: e, outputs: s }) => [`${s.ceil} = ceil(${e.a});`];
|
|
}
|
|
}
|
|
class Qi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "trunc", outTypeFunc: Wg }), this.statements = ({ inputs: e, outputs: s }) => [`${s.trunc} = trunc(${e.a});`];
|
|
}
|
|
}
|
|
class pi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "round", outTypeFunc: Al }), this.statements = ({ inputs: e, outputs: s }) => [`${s.round} = round(${e.a});`];
|
|
}
|
|
}
|
|
class fi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "fract", outTypeFunc: tl }), this.statements = ({ inputs: e, outputs: s }) => [`${s.fract} = fract(${e.a});`];
|
|
}
|
|
}
|
|
class di extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "power", outTypeFunc: el }), this.statements = ({ inputs: s, outputs: n }) => [`${n.power} = pow(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class yi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "exp", outTypeFunc: sl }), this.statements = ({ inputs: e, outputs: s }) => [`${s.exp} = exp(${e.a});`];
|
|
}
|
|
}
|
|
class wi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "exp2", outTypeFunc: nl }), this.statements = ({ inputs: e, outputs: s }) => [`${s.exp2} = exp2(${e.a});`];
|
|
}
|
|
}
|
|
class mi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "log", outTypeFunc: il }), this.statements = ({ inputs: e, outputs: s }) => [`${s.log} = log(${e.a});`];
|
|
}
|
|
}
|
|
class xi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "log2", outTypeFunc: rl }), this.statements = ({ inputs: e, outputs: s }) => [`${s.log2} = log2(${e.a});`];
|
|
}
|
|
}
|
|
class Si extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "sqr", outTypeFunc: al }), this.statements = ({ inputs: e, outputs: s }) => [`${s.sqr} = ${e.a} * ${e.a};`];
|
|
}
|
|
}
|
|
class Di extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "sqrt", outTypeFunc: ol }), this.statements = ({ inputs: e, outputs: s }) => [`${s.sqrt} = sqrt(${e.a});`];
|
|
}
|
|
}
|
|
class Mi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "inversesqrt", outTypeFunc: cl }), this.statements = ({ inputs: e, outputs: s }) => [`${s.inversesqrt} = inversesqrt(${e.a});`];
|
|
}
|
|
}
|
|
class vi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "min", outTypeFunc: ti }), this.statements = ({ inputs: s, outputs: n }) => [`${n.min} = min(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class bi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "max", outTypeFunc: gl }), this.statements = ({ inputs: s, outputs: n }) => [`${n.max} = max(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class Fi extends yt {
|
|
constructor({
|
|
a: A,
|
|
min: e,
|
|
max: s
|
|
}) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
c: s,
|
|
outKey: "clamp",
|
|
outTypeFunc: ll
|
|
}), this.statements = ({ inputs: n, outputs: i }) => {
|
|
const { a: r, b: a, c: o } = n;
|
|
return [`${i.clamp} = clamp(${r}, ${a}, ${o});`];
|
|
};
|
|
}
|
|
}
|
|
class Ni extends yt {
|
|
constructor({ a: A, b: e, t: s }) {
|
|
super({ a: A, b: e, c: s, outKey: "mix", outTypeFunc: Il }), this.statements = ({ inputs: n, outputs: i }) => {
|
|
const { a: r, b: a, c: o } = n;
|
|
return [`${i.mix} = mix(${r}, ${a}, ${o});`];
|
|
};
|
|
}
|
|
}
|
|
class ki extends tA {
|
|
constructor({ edge: A, x: e }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outKey: "step",
|
|
outTypeFunc: ul
|
|
}), this.statements = ({ inputs: s, outputs: n }) => {
|
|
const { a: i, b: r } = s;
|
|
return [`${n.step} = step(${i}, ${r});`];
|
|
};
|
|
}
|
|
}
|
|
class Ti extends yt {
|
|
constructor({
|
|
edge0: A,
|
|
edge1: e,
|
|
x: s
|
|
}) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
c: s,
|
|
outKey: "smoothstep",
|
|
outTypeFunc: hl
|
|
}), this.statements = ({ inputs: n, outputs: i }) => {
|
|
const { a: r, b: a, c: o } = n;
|
|
return [`${i.smoothstep} = smoothstep(${r}, ${a}, ${o});`];
|
|
};
|
|
}
|
|
}
|
|
class Ui extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "isNan", outTypeFunc: ei }), this.statements = ({ inputs: e, outputs: s }) => [`${s.isNan} = isNan(${e.a});`];
|
|
}
|
|
}
|
|
class Gi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "isInf", outTypeFunc: Cl }), this.statements = ({ inputs: e, outputs: s }) => [`${s.isInf} = isInf(${e.a});`];
|
|
}
|
|
}
|
|
const Rl = (t, A) => new Yi({ a: t, b: A }), Yl = (t, A) => new Ji({ a: t, b: A }), Jl = (t, A) => new _i({ a: t, b: A }), _l = (t) => new Li({ a: t }), Ll = (t, A) => new zi({ a: t, b: A }), zl = (t, A) => new Hi({ a: t, b: A }), Hl = (t, A) => new qi({ a: t, b: A }), Ri = (t, A) => new Ki({ a: t, b: A }), ql = (t, A) => new $i({ a: t, b: A }), Kl = (t, A) => new Vi({ a: t, b: A }), $l = (t) => new Pi({ a: t }), Vl = (t) => new Zi({ a: t }), os = (t, A, e) => new Xi({ cond: t, t: A, f: e }), Pl = (t) => new ji({ a: t });
|
|
class Yi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outTypeFunc: (s, n) => s, outKey: "and" }), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.and === "bool" ? [`${n.and} = ${s.a} && ${s.b};`] : [`${n.and} = ${s.a} & ${s.b};`];
|
|
}
|
|
}
|
|
class Ji extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outTypeFunc: (s, n) => s, outKey: "or" }), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.or === "bool" ? [`${n.or} = ${s.a} || ${s.b};`] : [`${n.or} = ${s.a} | ${s.b};`];
|
|
}
|
|
}
|
|
class _i extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outTypeFunc: (s, n) => s, outKey: "xor" }), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.xor === "bool" ? [`${n.xor} = ${s.a} ^^ ${s.b};`] : [`${n.xor} = ${s.a} ^ ${s.b};`];
|
|
}
|
|
}
|
|
class Li extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "not" }), this.statements = ({ inputs: e, outputs: s }) => this.outTypes.not === "bool" ? [`${s.not} = !${e.a};`] : [`${s.not} = not(${e.a});`];
|
|
}
|
|
}
|
|
class zi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outTypeFunc: (s, n) => fe(s, "lessThan"),
|
|
outKey: "lessThan"
|
|
}), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.lessThan === "bool" ? [`${n.lessThan} = ${s.a} < ${s.b};`] : [`${n.lessThan} = lessThan(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class Hi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outTypeFunc: (s, n) => fe(s, "lessThanEqual"),
|
|
outKey: "lessThanEqual"
|
|
}), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.lessThanEqual === "bool" ? [`${n.lessThanEqual} = ${s.a} <= ${s.b};`] : [
|
|
`${n.lessThanEqual} = lessThanEqual(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class qi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outTypeFunc: (s, n) => fe(s, "greaterThan"),
|
|
outKey: "greaterThan"
|
|
}), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.greaterThan === "bool" ? [`${n.greaterThan} = ${s.a} > ${s.b};`] : [
|
|
`${n.greaterThan} = greaterThan(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class Ki extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outTypeFunc: (s, n) => fe(s, "greaterThanEqual"),
|
|
outKey: "greaterThanEqual"
|
|
}), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.greaterThanEqual === "bool" ? [`${n.greaterThanEqual} = ${s.a} >= ${s.b};`] : [
|
|
`${n.greaterThanEqual} = greaterThanEqual(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class $i extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outTypeFunc: Oi, outKey: "equal" }), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.equal === "bool" ? [`${n.equal} = ${s.a} == ${s.b};`] : [`${n.equal} = equal(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class Vi extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outTypeFunc: Zl, outKey: "notEqual" }), this.statements = ({ inputs: s, outputs: n }) => this.outTypes.notEqual === "bool" ? [`${n.notEqual} = ${s.a} != ${s.b};`] : [`${n.notEqual} = notEqual(${s.a}, ${s.b});`];
|
|
}
|
|
}
|
|
class Pi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outTypeFunc: (e) => "bool", outKey: "any" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.any} = any(${e.a});`];
|
|
}
|
|
}
|
|
class Zi extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outTypeFunc: (e) => "bool", outKey: "all" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.all} = all(${e.a});`];
|
|
}
|
|
}
|
|
class Xi extends yt {
|
|
constructor({
|
|
cond: A,
|
|
t: e,
|
|
f: s
|
|
}) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
c: s,
|
|
outKey: "select",
|
|
outTypeFunc: (n, i, r) => i
|
|
}), this.statements = ({ inputs: n, outputs: i }) => {
|
|
const { a: r, b: a, c: o } = n;
|
|
return [`${i.select} = (${r}) ? (${a}) : (${o});`];
|
|
};
|
|
}
|
|
}
|
|
function fe(t, A) {
|
|
if (dt(t))
|
|
return "bool";
|
|
if (t === "ivec2" || t === "uvec2" || t === "vec2")
|
|
return "bvec2";
|
|
if (t === "ivec3" || t === "uvec3" || t === "vec3")
|
|
return "bvec3";
|
|
if (t === "ivec4" || t === "uvec4" || t === "vec4")
|
|
return "bvec4";
|
|
throw new Error(`Invalid ${A} type: ${t}`);
|
|
}
|
|
function Oi(t, A = "equal") {
|
|
if (dt(t))
|
|
return "bool";
|
|
if (ft(t))
|
|
return t;
|
|
if (t === "ivec2" || t === "uvec2" || t === "vec2")
|
|
return "bvec2";
|
|
if (t === "ivec3" || t === "uvec3" || t === "vec3")
|
|
return "bvec3";
|
|
if (t === "ivec4" || t === "uvec4" || t === "vec4")
|
|
return "bvec4";
|
|
throw new Error(`Invalid ${A} type: ${t}`);
|
|
}
|
|
function Zl(t) {
|
|
return Oi(t, "notEqual");
|
|
}
|
|
function Xl(t) {
|
|
if (ft(t))
|
|
return "bool";
|
|
if (EA(t))
|
|
return "int";
|
|
if (QA(t))
|
|
return "uint";
|
|
throw new Error(`Invalid compXor type: ${t}`);
|
|
}
|
|
class ji extends v {
|
|
constructor({ a: A }) {
|
|
const e = Xl($(A));
|
|
super({ a: A, outTypeFunc: (s) => e, outKey: "compXor" }), this.statements = ({ inputs: s, outputs: n }) => {
|
|
if (dt(this.outTypes.compXor))
|
|
return [`${n.compXor} = ${s.a};`];
|
|
const r = (Nt(e) ? ["x", "y"] : kt(e) ? ["x", "y", "z"] : ["x", "y", "z", "w"]).map((o) => `${s.a}.${o}`), a = ft(e) ? "^^" : "^";
|
|
return [`${n.compXor} = ${r.join(` ${a} `)};`];
|
|
};
|
|
}
|
|
}
|
|
const Ol = (t) => new ir({ value: t }), jl = (t) => new rr({ value: t }), Wl = (t) => new ar({ value: t }), Wi = (t) => new or({ value: t }), AI = (t) => new cr({ value: t }), tI = (t) => new gr({ value: t }), eI = (t) => new lr({ value: t }), sI = (t) => new Ir({ value: t }), nI = (t) => new ur({ value: t }), iI = (t) => new hr({ value: t }), rI = (t) => new Cr({ value: t }), aI = (t) => new Br({ value: t }), oI = (t) => new Er({ value: t }), Ar = (t) => new Qr({ value: t }), Bt = (t) => new pr({ value: t }), tr = (t) => new fr({ value: t }), cI = (t) => new dr({ value: t }), gI = (t) => new yr({ value: t }), lI = (t) => new wr({ value: t }), er = (t) => new mr({ value: t }), sr = (t) => new xr({ value: t }), II = (t) => new Sr({ value: t }), uI = (t) => new Dr({ value: t }), hI = (t) => new Mr({ value: t }), CI = (t) => new vr({ value: t }), BI = (t) => new br({ value: t }), EI = (t) => new Fr({ value: t }), nr = (t) => new Nr({ value: t }), QI = (t) => new kr({ value: t }), ze = (t) => new Tr({ value: t });
|
|
class cA extends v {
|
|
constructor({
|
|
value: A,
|
|
outType: e,
|
|
outKey: s
|
|
}) {
|
|
super({ a: A, outTypeFunc: () => e, outKey: s }), this.statements = ({ inputs: n, outputs: i }) => [
|
|
`${i[s]} = ${Hs(e)}(${n.a});`
|
|
];
|
|
}
|
|
}
|
|
class ir extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "bool", outKey: "bool" });
|
|
}
|
|
}
|
|
class rr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "int", outKey: "int" });
|
|
}
|
|
}
|
|
class ar extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "uint", outKey: "uint" });
|
|
}
|
|
}
|
|
class or extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "float", outKey: "float" });
|
|
}
|
|
}
|
|
class cr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "bvec2", outKey: "bvec2" });
|
|
}
|
|
}
|
|
class gr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "bvec3", outKey: "bvec3" });
|
|
}
|
|
}
|
|
class lr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "bvec4", outKey: "bvec4" });
|
|
}
|
|
}
|
|
class Ir extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "ivec2", outKey: "ivec2" });
|
|
}
|
|
}
|
|
class ur extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "ivec3", outKey: "ivec3" });
|
|
}
|
|
}
|
|
class hr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "ivec4", outKey: "ivec4" });
|
|
}
|
|
}
|
|
class Cr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "uvec2", outKey: "uvec2" });
|
|
}
|
|
}
|
|
class Br extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "uvec3", outKey: "uvec3" });
|
|
}
|
|
}
|
|
class Er extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "uvec4", outKey: "uvec4" });
|
|
}
|
|
}
|
|
class Qr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "vec2", outKey: "vec2" });
|
|
}
|
|
}
|
|
class pr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "vec3", outKey: "vec3" });
|
|
}
|
|
}
|
|
class fr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "vec4", outKey: "vec4" });
|
|
}
|
|
}
|
|
class dr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "mat2", outKey: "mat2" });
|
|
}
|
|
}
|
|
class yr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "mat3", outKey: "mat3" });
|
|
}
|
|
}
|
|
class wr extends cA {
|
|
constructor({
|
|
value: A
|
|
}) {
|
|
super({ value: A, outType: "mat4", outKey: "mat4" });
|
|
}
|
|
}
|
|
class mr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "int", outTypeFunc: () => "int" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.int} = floatBitsToInt(${e.a});`];
|
|
}
|
|
}
|
|
class xr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "uint", outTypeFunc: () => "uint" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.uint} = floatBitsToUint(${e.a});`];
|
|
}
|
|
}
|
|
class Sr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "float", outTypeFunc: () => "float" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.float} = intBitsToFloat(${e.a});`];
|
|
}
|
|
}
|
|
class Dr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "float", outTypeFunc: () => "float" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.float} = uintBitsToFloat(${e.a});`];
|
|
}
|
|
}
|
|
class Mr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "uint", outTypeFunc: () => "uint" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.uint} = packSnorm2x16(${e.a});`];
|
|
}
|
|
}
|
|
class vr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "vec2", outTypeFunc: () => "vec2" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.vec2} = unpackSnorm2x16(${e.a});`];
|
|
}
|
|
}
|
|
class br extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "uint", outTypeFunc: () => "uint" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.uint} = packUnorm2x16(${e.a});`];
|
|
}
|
|
}
|
|
class Fr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "vec2", outTypeFunc: () => "vec2" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.vec2} = unpackUnorm2x16(${e.a});`];
|
|
}
|
|
}
|
|
class Nr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "uint", outTypeFunc: () => "uint" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.uint} = packHalf2x16(${e.a});`];
|
|
}
|
|
}
|
|
class kr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "vec2", outTypeFunc: () => "vec2" }), this.statements = ({ inputs: e, outputs: s }) => [`${s.vec2} = unpackHalf2x16(${e.a});`];
|
|
}
|
|
}
|
|
class Tr extends v {
|
|
constructor({ value: A }) {
|
|
super({ a: A, outKey: "rgba8", outTypeFunc: () => "vec4" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`uvec4 uRgba = uvec4(${e.a} & 0xffu, (${e.a} >> 8u) & 0xffu, (${e.a} >> 16u) & 0xffu, (${e.a} >> 24u) & 0xffu);`,
|
|
`${s.rgba8} = vec4(uRgba) / 255.0;`
|
|
];
|
|
}
|
|
}
|
|
const pI = (t) => new Yr({ a: t }), fI = (t, A) => new Jr({ a: t, b: A }), Ur = (t, A) => new _r({ a: t, b: A }), dI = (t, A) => new Lr({ a: t, b: A }), Gr = (t) => new zr({ a: t }), yI = (t, A, e) => new Kr({ a: t, b: A, c: e }), wI = (t, A) => new $r({ incident: t, normal: A }), mI = (t, A, e) => new Vr({ incident: t, normal: A, eta: e }), Et = (t) => new Wr({ vector: t }), $A = ({
|
|
vector: t,
|
|
vectorType: A,
|
|
x: e,
|
|
y: s,
|
|
z: n,
|
|
w: i,
|
|
r,
|
|
g: a,
|
|
b: o,
|
|
a: g
|
|
}) => new Aa({ vector: t, vectorType: A, x: e, y: s, z: n, w: i, r, g: a, b: o, a: g }), xI = (t) => new Hr({ a: t }), Rr = (t, A) => new qr({ a: t, b: A }), SI = (t, A) => new ta({ vector: t, select: A }), DI = (t, A) => new Pr({ a: t, b: A }), MI = (t, A) => new Zr({ a: t, b: A }), vI = (t) => new Xr({ a: t }), bI = (t) => new Or({ a: t }), FI = (t) => new jr({ a: t });
|
|
class Yr extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outTypeFunc: (e) => "float", outKey: "length" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.length} = length(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Jr extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "distance", outTypeFunc: (s, n) => "float" }), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.distance} = distance(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class _r extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "dot", outTypeFunc: (s, n) => "float" }), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.dot} = dot(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class Lr extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "cross", outTypeFunc: (s, n) => "vec3" }), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.cross} = cross(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class zr extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "normalize" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.normalize} = normalize(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
function NI(t) {
|
|
if (t === "vec3")
|
|
return "vec2";
|
|
if (t === "vec4")
|
|
return "vec3";
|
|
throw new Error("Invalid type");
|
|
}
|
|
class Hr extends v {
|
|
constructor({ a: A }) {
|
|
super({
|
|
a: A,
|
|
outTypeFunc: (e) => NI(e),
|
|
outKey: "projected"
|
|
}), this.statements = ({ inputs: e, outputs: s }) => {
|
|
if (this.inTypes.a === "vec3")
|
|
return [`${s.projected} = ${e.a}.xy / ${e.a}.z;`];
|
|
if (this.inTypes.a === "vec4")
|
|
return [`${s.projected} = ${e.a}.xyz / ${e.a}.w;`];
|
|
throw new Error("Invalid type");
|
|
};
|
|
}
|
|
}
|
|
function kI(t) {
|
|
if (t === "float") return "vec2";
|
|
if (t === "vec2") return "vec3";
|
|
if (t === "vec3") return "vec4";
|
|
throw new Error("Invalid type");
|
|
}
|
|
class qr extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
const s = $(A), n = kI(s);
|
|
super({ a: A, b: e, outKey: "extend", outTypeFunc: () => n }), this.statements = ({ inputs: i, outputs: r }) => [
|
|
`${r.extend} = ${n}(${i.a}, ${i.b});`
|
|
];
|
|
}
|
|
}
|
|
class Kr extends yt {
|
|
constructor({ a: A, b: e, c: s }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
c: s,
|
|
outKey: "forward",
|
|
outTypeFunc: (n, i, r) => n
|
|
}), this.statements = ({ inputs: n, outputs: i }) => [
|
|
`${i.forward} = faceforward(${n.a}, ${n.b}, ${n.c});`
|
|
];
|
|
}
|
|
}
|
|
class $r extends tA {
|
|
constructor({
|
|
incident: A,
|
|
normal: e
|
|
}) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outKey: "reflection",
|
|
outTypeFunc: (s, n) => s
|
|
}), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.reflection} = reflect(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class Vr extends yt {
|
|
constructor({
|
|
incident: A,
|
|
normal: e,
|
|
eta: s
|
|
}) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
c: s,
|
|
outKey: "refraction",
|
|
outTypeFunc: (n, i, r) => n
|
|
}), this.statements = ({ inputs: n, outputs: i }) => [
|
|
`${i.refraction} = refract(${n.a}, ${n.b}, ${n.c});`
|
|
];
|
|
}
|
|
}
|
|
class Pr extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "product", outTypeFunc: (s, n) => s }), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.product} = matrixCompMult(${A}, ${e});`
|
|
];
|
|
}
|
|
}
|
|
function TI(t, A) {
|
|
if (t === "vec2") {
|
|
if (A === "vec2") return "mat2";
|
|
if (A === "vec3") return "mat3x2";
|
|
if (A === "vec4") return "mat4x2";
|
|
}
|
|
if (t === "vec3") {
|
|
if (A === "vec2") return "mat2x3";
|
|
if (A === "vec3") return "mat3";
|
|
if (A === "vec4") return "mat4x3";
|
|
}
|
|
if (t === "vec4") {
|
|
if (A === "vec2") return "mat2x4";
|
|
if (A === "vec3") return "mat3x4";
|
|
if (A === "vec4") return "mat4";
|
|
}
|
|
throw new Error(`Invalid outer type: ${t}, ${A}`);
|
|
}
|
|
class Zr extends tA {
|
|
constructor({ a: A, b: e }) {
|
|
super({ a: A, b: e, outKey: "outer", outTypeFunc: TI }), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.outer} = outerProduct(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
function UI(t) {
|
|
if (t === "mat2") return "mat2";
|
|
if (t === "mat3") return "mat3";
|
|
if (t === "mat4") return "mat4";
|
|
if (t === "mat2x2") return "mat2x2";
|
|
if (t === "mat2x3") return "mat3x2";
|
|
if (t === "mat2x4") return "mat4x2";
|
|
if (t === "mat3x2") return "mat2x3";
|
|
if (t === "mat3x3") return "mat3x3";
|
|
if (t === "mat3x4") return "mat4x3";
|
|
if (t === "mat4x2") return "mat2x4";
|
|
if (t === "mat4x3") return "mat3x4";
|
|
if (t === "mat4x4") return "mat4x4";
|
|
throw new Error(`Invalid transpose type: ${t}`);
|
|
}
|
|
class Xr extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "transpose", outTypeFunc: UI }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.transpose} = transpose(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Or extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "det", outTypeFunc: (e) => "float" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.det} = determinant(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class jr extends v {
|
|
constructor({ a: A }) {
|
|
super({ a: A, outKey: "inverse", outTypeFunc: (e) => e }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.inverse} = inverse(${A});`
|
|
];
|
|
}
|
|
}
|
|
function GI(t) {
|
|
const A = (e) => e;
|
|
switch (t) {
|
|
case "vec2":
|
|
return A({ x: "float", y: "float", r: "float", g: "float" });
|
|
case "vec3":
|
|
return A({
|
|
x: "float",
|
|
y: "float",
|
|
z: "float",
|
|
r: "float",
|
|
g: "float",
|
|
b: "float"
|
|
});
|
|
case "vec4":
|
|
return A({
|
|
x: "float",
|
|
y: "float",
|
|
z: "float",
|
|
w: "float",
|
|
r: "float",
|
|
g: "float",
|
|
b: "float",
|
|
a: "float"
|
|
});
|
|
case "ivec2":
|
|
return A({ x: "int", y: "int", r: "int", g: "int" });
|
|
case "ivec3":
|
|
return A({
|
|
x: "int",
|
|
y: "int",
|
|
z: "int",
|
|
r: "int",
|
|
g: "int",
|
|
b: "int"
|
|
});
|
|
case "ivec4":
|
|
return A({
|
|
x: "int",
|
|
y: "int",
|
|
z: "int",
|
|
w: "int",
|
|
r: "int",
|
|
g: "int",
|
|
b: "int",
|
|
a: "int"
|
|
});
|
|
case "uvec2":
|
|
return A({ x: "uint", y: "uint", r: "uint", g: "uint" });
|
|
case "uvec3":
|
|
return A({
|
|
x: "uint",
|
|
y: "uint",
|
|
z: "uint",
|
|
r: "uint",
|
|
g: "uint",
|
|
b: "uint"
|
|
});
|
|
case "uvec4":
|
|
return A({
|
|
x: "uint",
|
|
y: "uint",
|
|
z: "uint",
|
|
w: "uint",
|
|
r: "uint",
|
|
g: "uint",
|
|
b: "uint",
|
|
a: "uint"
|
|
});
|
|
default:
|
|
throw new Error(`Invalid vector type: ${t}`);
|
|
}
|
|
}
|
|
class Wr extends V {
|
|
constructor({ vector: A }) {
|
|
const s = { vector: $(A) }, n = GI(s.vector);
|
|
super({ inTypes: s, outTypes: n, inputs: { vector: A } }), this.statements = ({ inputs: i, outputs: r }) => {
|
|
const { x: a, y: o, z: g, w: l, r: c, g: I, b: h, a: E } = r, { vector: C } = i;
|
|
return [
|
|
a ? `${a} = ${C}.x;` : null,
|
|
o ? `${o} = ${C}.y;` : null,
|
|
g ? `${g} = ${C}.z;` : null,
|
|
l ? `${l} = ${C}.w;` : null,
|
|
c ? `${c} = ${C}.r;` : null,
|
|
I ? `${I} = ${C}.g;` : null,
|
|
h ? `${h} = ${C}.b;` : null,
|
|
E ? `${E} = ${C}.a;` : null
|
|
].filter(Boolean);
|
|
};
|
|
}
|
|
}
|
|
class Aa extends V {
|
|
constructor({
|
|
vector: A,
|
|
vectorType: e,
|
|
x: s,
|
|
y: n,
|
|
z: i,
|
|
w: r,
|
|
r: a,
|
|
g: o,
|
|
b: g,
|
|
a: l
|
|
}) {
|
|
if (!A && !e)
|
|
throw new Error("Either vector or vectorType must be provided");
|
|
const c = e ?? $(A), I = _s(c), h = Ls(c), E = {
|
|
vector: c,
|
|
x: I,
|
|
y: I,
|
|
r: I,
|
|
g: I
|
|
}, C = { vector: A, x: s, y: n, r: a, g: o };
|
|
h >= 3 && (Object.assign(E, { z: I, b: I }), Object.assign(C, { z: i, b: g })), h >= 4 && (Object.assign(E, { w: I, a: I }), Object.assign(C, { w: r, a: l })), super({ inTypes: E, outTypes: { vector: c }, inputs: C }), this.statements = ({ inputs: B, outputs: Q }) => {
|
|
const { vector: f } = Q, {
|
|
vector: p,
|
|
x: d,
|
|
y,
|
|
z: D,
|
|
w: x,
|
|
r: w,
|
|
g: m,
|
|
b: k,
|
|
a: M
|
|
} = B, S = [
|
|
`${f}.x = ${d ?? w ?? (p ? `${p}.x` : Jt(I))};`,
|
|
`${f}.y = ${y ?? m ?? (p ? `${p}.y` : Jt(I))};`
|
|
];
|
|
return h >= 3 && S.push(
|
|
`${f}.z = ${D ?? k ?? (p ? `${p}.z` : Jt(I))};`
|
|
), h >= 4 && S.push(
|
|
`${f}.w = ${x ?? M ?? (p ? `${p}.w` : Jt(I))};`
|
|
), S;
|
|
};
|
|
}
|
|
dynoOut() {
|
|
return new K(
|
|
this,
|
|
"vector"
|
|
);
|
|
}
|
|
}
|
|
function RI(t, A) {
|
|
let e = null;
|
|
if (Zt(t) ? e = A.length === 1 ? "float" : A.length === 2 ? "vec2" : A.length === 3 ? "vec3" : A.length === 4 ? "vec4" : null : EA(t) ? e = A.length === 1 ? "int" : A.length === 2 ? "ivec2" : A.length === 3 ? "ivec3" : A.length === 4 ? "ivec4" : null : QA(t) && (e = A.length === 1 ? "uint" : A.length === 2 ? "uvec2" : A.length === 3 ? "uvec3" : A.length === 4 ? "uvec4" : null), e == null)
|
|
throw new Error(`Invalid swizzle: ${A}`);
|
|
return e;
|
|
}
|
|
class ta extends v {
|
|
constructor({ vector: A, select: e }) {
|
|
super({
|
|
a: A,
|
|
outKey: "swizzle",
|
|
outTypeFunc: (s) => RI(s, e)
|
|
}), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.swizzle} = ${s.a}.${e};`
|
|
];
|
|
}
|
|
}
|
|
const YI = (t, A, e) => new oa({ index: t, from: A, to: e }), JI = (t) => new Ut({ value: t }), _I = (t) => new kA({ state: t }), LI = (t) => new TA({ state: t }), ea = (t) => new ca({ value: t }), sa = (t) => new ga({ value: t }), na = (t) => new la({ value: t }), ia = (t) => new Ia({ value: t }), zI = (t) => new ua({ value: t }), HI = (t) => new ha({ value: t }), ra = (t) => new Ca({ value: t }), He = (t) => new Ba({ value: t }), aa = (t, A, e) => new Ea({ z: t, zNear: A, zFar: e }).outputs.depth;
|
|
class oa extends V {
|
|
constructor({
|
|
from: A,
|
|
to: e,
|
|
index: s
|
|
}) {
|
|
super({
|
|
inTypes: { from: "int", to: "int", index: "int" },
|
|
outTypes: { index: "int" },
|
|
inputs: { from: A, to: e, index: s },
|
|
statements: ({ inputs: n, outputs: i }) => [
|
|
`${i.index} = ${n.index} - ${n.from} + ${n.to};`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "index");
|
|
}
|
|
}
|
|
class kA extends V {
|
|
constructor({ state: A }) {
|
|
const e = $(A);
|
|
super({
|
|
inTypes: { state: e },
|
|
outTypes: { state: "uint" },
|
|
inputs: { state: A },
|
|
globals: () => [
|
|
hA(`
|
|
uint pcg_next(uint state) {
|
|
return state * 747796405u + 2891336453u;
|
|
}
|
|
`)
|
|
],
|
|
statements: ({ inputs: s, outputs: n }) => {
|
|
const i = e === "uint" ? `${s.state}` : e === "int" ? `uint(${s.state})` : `floatBitsToUint(${s.state})`;
|
|
return [`${n.state} = pcg_next(${i});`];
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "state");
|
|
}
|
|
}
|
|
class TA extends V {
|
|
constructor({ state: A }) {
|
|
super({
|
|
inTypes: { state: "uint" },
|
|
outTypes: { hash: "uint" },
|
|
inputs: { state: A },
|
|
globals: () => [
|
|
hA(`
|
|
uint pcg_hash(uint state) {
|
|
uint hash = ((state >> ((state >> 28u) + 4u)) ^ state) * 277803737u;
|
|
return (hash >> 22u) ^ hash;
|
|
}
|
|
`)
|
|
],
|
|
statements: ({ inputs: e, outputs: s }) => [
|
|
`${s.hash} = pcg_hash(${e.state});`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class Ut extends V {
|
|
constructor({ value: A }) {
|
|
const e = $(A), s = zs(e);
|
|
super({
|
|
inTypes: { value: e },
|
|
outTypes: { state: "uint" },
|
|
inputs: { value: A },
|
|
globals: () => [
|
|
hA(`
|
|
uint pcg_mix(uint value) {
|
|
return value;
|
|
}
|
|
uint pcg_mix(uvec2 value) {
|
|
return value.x + 0x9e3779b9u * value.y;
|
|
}
|
|
uint pcg_mix(uvec3 value) {
|
|
return value.x + 0x9e3779b9u * value.y + 0x85ebca6bu * value.z;
|
|
}
|
|
uint pcg_mix(uvec4 value) {
|
|
return value.x + 0x9e3779b9u * value.y + 0x85ebca6bu * value.z + 0xc2b2ae35u * value.w;
|
|
}
|
|
`)
|
|
],
|
|
statements: ({ inputs: n, outputs: i }) => {
|
|
const r = QA(e) ? `${n.value}` : EA(e) ? `${s}(${n.value})` : `floatBitsToUint(${n.value})`;
|
|
return [
|
|
`${s} bits = ${r};`,
|
|
`${i.state} = pcg_mix(bits);`
|
|
];
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "state");
|
|
}
|
|
}
|
|
class ca extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "uint" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
let s = new Ut({ value: e }).outputs.state;
|
|
return s = new kA({ state: s }).outputs.state, new TA({ state: s }).outputs;
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class ga extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "uvec2" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
let s = new Ut({ value: e }).outputs.state;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const n = new TA({ state: s }).outputs.hash;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const i = new TA({ state: s }).outputs.hash;
|
|
return { hash: $A({ vectorType: "uvec2", x: n, y: i }) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class la extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "uvec3" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
let s = new Ut({ value: e }).outputs.state;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const n = new TA({ state: s }).outputs.hash;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const i = new TA({ state: s }).outputs.hash;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const r = new TA({ state: s }).outputs.hash;
|
|
return { hash: $A({ vectorType: "uvec3", x: n, y: i, z: r }) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class Ia extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "uvec4" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
let s = new Ut({ value: e }).outputs.state;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const n = new TA({ state: s }).outputs.hash;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const i = new TA({ state: s }).outputs.hash;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const r = new TA({ state: s }).outputs.hash;
|
|
s = new kA({ state: s }).outputs.state;
|
|
const a = new TA({ state: s }).outputs.hash;
|
|
return { hash: $A({ vectorType: "uvec4", x: n, y: i, z: r, w: a }) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class ua extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "float" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
const s = ea(e);
|
|
return { hash: iA(Wi(s), J("float", 1 / 2 ** 32)) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class ha extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "vec2" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
const s = sa(e);
|
|
return { hash: iA(Ar(s), J("float", 1 / 2 ** 32)) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class Ca extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "vec3" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
const s = na(e);
|
|
return { hash: iA(Bt(s), J("float", 1 / 2 ** 32)) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class Ba extends PA {
|
|
constructor({ value: A }) {
|
|
super({
|
|
inTypes: { value: $(A) },
|
|
outTypes: { hash: "vec4" },
|
|
inputs: { value: A },
|
|
construct: ({ value: e }) => {
|
|
if (!e)
|
|
throw new Error("value is required");
|
|
const s = ia(e);
|
|
return { hash: iA(tr(s), J("float", 1 / 2 ** 32)) };
|
|
}
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "hash");
|
|
}
|
|
}
|
|
class Ea extends V {
|
|
constructor({
|
|
z: A,
|
|
zNear: e,
|
|
zFar: s
|
|
}) {
|
|
super({
|
|
inTypes: { z: "float", zNear: "float", zFar: "float" },
|
|
outTypes: { depth: "float" },
|
|
inputs: { z: A, zNear: e, zFar: s },
|
|
statements: ({ inputs: n, outputs: i }) => [
|
|
`float clamped = clamp(${n.z}, ${n.zNear}, ${n.zFar});`,
|
|
`${i.depth} = (log2(clamped + 1.0) - log2(${n.zNear} + 1.0)) / (log2(${n.zFar} + 1.0) - log2(${n.zNear} + 1.0));`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "depth");
|
|
}
|
|
}
|
|
const Qa = (t, {
|
|
scale: A,
|
|
scales: e,
|
|
rotate: s,
|
|
translate: n
|
|
}) => new fa({ position: t, scale: A, scales: e, rotate: s, translate: n }).outputs.position, pa = (t, {
|
|
scale: A,
|
|
scales: e,
|
|
rotate: s
|
|
}) => new da({ dir: t, scale: A, scales: e, rotate: s }).outputs.dir, qI = (t, { rotate: A }) => new ya({ quaternion: t, rotate: A }).outputs.quaternion;
|
|
class fa extends V {
|
|
constructor({
|
|
position: A,
|
|
scale: e,
|
|
scales: s,
|
|
rotate: n,
|
|
translate: i
|
|
}) {
|
|
super({
|
|
inTypes: {
|
|
position: "vec3",
|
|
scale: "float",
|
|
scales: "vec3",
|
|
rotate: "vec4",
|
|
translate: "vec3"
|
|
},
|
|
outTypes: { position: "vec3" },
|
|
inputs: { position: A, scale: e, scales: s, rotate: n, translate: i },
|
|
statements: ({ inputs: r, outputs: a }) => {
|
|
const { position: o } = a;
|
|
if (!o)
|
|
return [];
|
|
const { scale: g, scales: l, rotate: c, translate: I } = r;
|
|
return [
|
|
`${o} = ${r.position ?? "vec3(0.0, 0.0, 0.0)"};`,
|
|
g ? `${o} *= ${g};` : null,
|
|
l ? `${o} *= ${l};` : null,
|
|
c ? `${o} = quatVec(${c}, ${o});` : null,
|
|
I ? `${o} += ${I};` : null
|
|
].filter(Boolean);
|
|
}
|
|
});
|
|
}
|
|
}
|
|
class da extends V {
|
|
constructor({
|
|
dir: A,
|
|
scale: e,
|
|
scales: s,
|
|
rotate: n
|
|
}) {
|
|
super({
|
|
inTypes: { dir: "vec3", scale: "float", scales: "vec3", rotate: "vec4" },
|
|
outTypes: { dir: "vec3" },
|
|
inputs: { dir: A, scale: e, scales: s, rotate: n },
|
|
statements: ({ inputs: i, outputs: r }) => {
|
|
const { dir: a } = r;
|
|
if (!a)
|
|
return [];
|
|
const { scale: o, scales: g, rotate: l } = i;
|
|
return [
|
|
`${a} = ${i.dir ?? "vec3(0.0, 0.0, 0.0)"};`,
|
|
o ? `${a} *= ${o};` : null,
|
|
g ? `${a} *= ${g};` : null,
|
|
l ? `${a} = quatVec(${l}, ${a});` : null
|
|
].filter(Boolean);
|
|
}
|
|
});
|
|
}
|
|
}
|
|
class ya extends V {
|
|
constructor({
|
|
quaternion: A,
|
|
rotate: e
|
|
}) {
|
|
super({
|
|
inTypes: { quaternion: "vec4", rotate: "vec4" },
|
|
outTypes: { quaternion: "vec4" },
|
|
inputs: { quaternion: A, rotate: e },
|
|
statements: ({ inputs: s, outputs: n }) => {
|
|
const { quaternion: i } = n;
|
|
return i ? [
|
|
`${i} = ${s.quaternion ?? "vec4(0.0, 0.0, 0.0, 1.0)"};`,
|
|
e ? `${i} = quatQuat(${s.rotate}, ${i});` : null
|
|
].filter(Boolean) : [];
|
|
}
|
|
});
|
|
}
|
|
}
|
|
const KI = () => {
|
|
throw new Error("Not implemented");
|
|
}, $I = () => {
|
|
throw new Error("Not implemented");
|
|
}, VI = () => {
|
|
throw new Error("Not implemented");
|
|
}, PI = () => {
|
|
throw new Error("Not implemented");
|
|
}, ZI = () => {
|
|
throw new Error("Not implemented");
|
|
}, XI = () => {
|
|
throw new Error("Not implemented");
|
|
}, OI = (t, A) => new wa({ texture: t, lod: A }), jI = (t, A, e) => new ma({ texture: t, coord: A, bias: e }), WI = (t, A, e) => new xa({ texture: t, coord: A, lod: e });
|
|
class wa extends V {
|
|
constructor({ texture: A, lod: e }) {
|
|
const s = $(A);
|
|
super({
|
|
inTypes: { texture: s, lod: "int" },
|
|
outTypes: { size: Sa(s) },
|
|
inputs: { texture: A, lod: e },
|
|
statements: ({ inputs: n, outputs: i }) => [
|
|
`${i.size} = textureSize(${n.texture}, ${n.lod ?? "0"});`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "size");
|
|
}
|
|
}
|
|
class ma extends V {
|
|
constructor({
|
|
texture: A,
|
|
coord: e,
|
|
bias: s
|
|
}) {
|
|
const n = $(A);
|
|
super({
|
|
inTypes: {
|
|
texture: n,
|
|
coord: Au(n),
|
|
bias: "float"
|
|
},
|
|
outTypes: { sample: Da(n) },
|
|
inputs: { texture: A, coord: e, bias: s },
|
|
statements: ({ inputs: i, outputs: r }) => [
|
|
`${r.sample} = texture(${i.texture}, ${i.coord}${i.bias ? `, ${i.bias}` : ""});`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "sample");
|
|
}
|
|
}
|
|
class xa extends V {
|
|
constructor({
|
|
texture: A,
|
|
coord: e,
|
|
lod: s
|
|
}) {
|
|
const n = $(A);
|
|
super({
|
|
inTypes: {
|
|
texture: n,
|
|
coord: Sa(n),
|
|
lod: "int"
|
|
},
|
|
outTypes: { texel: Da(n) },
|
|
inputs: { texture: A, coord: e, lod: s },
|
|
statements: ({ inputs: i, outputs: r }) => [
|
|
`${r.texel} = texelFetch(${i.texture}, ${i.coord}, ${i.lod ?? "0"});`
|
|
]
|
|
});
|
|
}
|
|
dynoOut() {
|
|
return new K(this, "texel");
|
|
}
|
|
}
|
|
function Sa(t) {
|
|
switch (t) {
|
|
case "sampler2D":
|
|
case "usampler2D":
|
|
case "isampler2D":
|
|
case "samplerCube":
|
|
case "usamplerCube":
|
|
case "isamplerCube":
|
|
case "sampler2DShadow":
|
|
case "samplerCubeShadow":
|
|
return "ivec2";
|
|
case "sampler3D":
|
|
case "usampler3D":
|
|
case "isampler3D":
|
|
case "sampler2DArray":
|
|
case "usampler2DArray":
|
|
case "isampler2DArray":
|
|
case "sampler2DArrayShadow":
|
|
return "ivec3";
|
|
default:
|
|
throw new Error(`Invalid texture type: ${t}`);
|
|
}
|
|
}
|
|
function Au(t) {
|
|
switch (t) {
|
|
case "sampler2D":
|
|
case "usampler2D":
|
|
case "isampler2D":
|
|
return "vec2";
|
|
case "sampler3D":
|
|
case "usampler3D":
|
|
case "isampler3D":
|
|
case "samplerCube":
|
|
case "usamplerCube":
|
|
case "isamplerCube":
|
|
case "sampler2DArray":
|
|
case "usampler2DArray":
|
|
case "isampler2DArray":
|
|
case "sampler2DShadow":
|
|
return "vec3";
|
|
case "samplerCubeShadow":
|
|
case "sampler2DArrayShadow":
|
|
return "vec4";
|
|
default:
|
|
throw new Error(`Invalid texture type: ${t}`);
|
|
}
|
|
}
|
|
function Da(t) {
|
|
switch (t) {
|
|
case "sampler2D":
|
|
case "sampler2DArray":
|
|
case "sampler3D":
|
|
case "samplerCube":
|
|
case "sampler2DShadow":
|
|
return "vec4";
|
|
case "usampler2D":
|
|
case "usampler2DArray":
|
|
case "usampler3D":
|
|
case "usamplerCube":
|
|
return "uvec4";
|
|
case "isampler2D":
|
|
case "isampler2DArray":
|
|
case "isampler3D":
|
|
case "isamplerCube":
|
|
return "ivec4";
|
|
case "samplerCubeShadow":
|
|
case "sampler2DArrayShadow":
|
|
return "float";
|
|
default:
|
|
throw new Error(`Invalid texture type: ${t}`);
|
|
}
|
|
}
|
|
const tu = (t) => new Ma({ degrees: t }), eu = (t) => new va({ radians: t }), qe = (t) => new ba({ radians: t }), su = (t) => new Fa({ radians: t }), nu = (t) => new Na({ radians: t }), iu = (t) => new ka({ sin: t }), ru = (t) => new Ta({ cos: t }), au = (t) => new Ua({ tan: t }), ou = (t, A) => new Ga({ y: t, x: A }), cu = (t) => new Ra({ x: t }), gu = (t) => new Ya({ x: t }), lu = (t) => new Ja({ x: t }), Iu = (t) => new _a({ x: t }), uu = (t) => new La({ x: t }), hu = (t) => new za({ x: t });
|
|
class Ma extends v {
|
|
constructor({ degrees: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "radians" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.radians} = radians(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class va extends v {
|
|
constructor({ radians: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "degrees" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.degrees} = degrees(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class ba extends v {
|
|
constructor({ radians: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "sin" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.sin} = sin(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Fa extends v {
|
|
constructor({ radians: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "cos" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.cos} = cos(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Na extends v {
|
|
constructor({ radians: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "tan" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.tan} = tan(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class ka extends v {
|
|
constructor({ sin: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "asin" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.asin} = asin(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Ta extends v {
|
|
constructor({ cos: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "acos" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.acos} = acos(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Ua extends v {
|
|
constructor({ tan: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "atan" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.atan} = atan(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Ga extends tA {
|
|
constructor({ y: A, x: e }) {
|
|
super({
|
|
a: A,
|
|
b: e,
|
|
outTypeFunc: (s, n) => s,
|
|
outKey: "atan2"
|
|
}), this.statements = ({ inputs: s, outputs: n }) => [
|
|
`${n.atan2} = atan2(${s.a}, ${s.b});`
|
|
];
|
|
}
|
|
}
|
|
class Ra extends v {
|
|
constructor({ x: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "sinh" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.sinh} = sinh(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Ya extends v {
|
|
constructor({ x: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "cosh" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.cosh} = cosh(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class Ja extends v {
|
|
constructor({ x: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "tanh" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.tanh} = tanh(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class _a extends v {
|
|
constructor({ x: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "asinh" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.asinh} = asinh(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class La extends v {
|
|
constructor({ x: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "acosh" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.acosh} = acosh(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
class za extends v {
|
|
constructor({ x: A }) {
|
|
super({ a: A, outTypeFunc: (e) => e, outKey: "atanh" }), this.statements = ({ inputs: e, outputs: s }) => [
|
|
`${s.atanh} = atanh(${e.a});`
|
|
];
|
|
}
|
|
}
|
|
const Ph = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
__proto__: null,
|
|
Abs: hi,
|
|
Acos: Ta,
|
|
Acosh: La,
|
|
Add: ri,
|
|
All: Zi,
|
|
And: Yi,
|
|
Any: Pi,
|
|
Asin: ka,
|
|
Asinh: _a,
|
|
Atan: Ua,
|
|
Atan2: Ga,
|
|
Atanh: za,
|
|
BVec2: cr,
|
|
BVec3: gr,
|
|
BVec4: lr,
|
|
BinaryOp: tA,
|
|
Bool: ir,
|
|
Ceil: Ei,
|
|
Clamp: Fi,
|
|
Combine: Aa,
|
|
CombineGsplat: js,
|
|
CompMult: Pr,
|
|
CompXor: ji,
|
|
Compilation: Ks,
|
|
Cos: Fa,
|
|
Cosh: Ya,
|
|
Cross: Lr,
|
|
Degrees: va,
|
|
Determinant: Or,
|
|
Distance: Jr,
|
|
Div: ci,
|
|
Dot: _r,
|
|
Dyno: V,
|
|
DynoBlock: PA,
|
|
DynoBool: ce,
|
|
DynoBvec2: rn,
|
|
DynoBvec3: cn,
|
|
DynoBvec4: In,
|
|
DynoConst: qs,
|
|
DynoFloat: ht,
|
|
DynoInt: $t,
|
|
DynoIsampler2D: Mn,
|
|
DynoIsampler2DArray: bn,
|
|
DynoIsampler3D: kn,
|
|
DynoIsamplerCube: Gn,
|
|
DynoIvec2: on,
|
|
DynoIvec3: ln,
|
|
DynoIvec4: hn,
|
|
DynoLiteral: vt,
|
|
DynoMat2: Cn,
|
|
DynoMat2x2: Bn,
|
|
DynoMat2x3: En,
|
|
DynoMat2x4: Qn,
|
|
DynoMat3: pn,
|
|
DynoMat3x2: fn,
|
|
DynoMat3x3: dn,
|
|
DynoMat3x4: yn,
|
|
DynoMat4: wn,
|
|
DynoMat4x2: mn,
|
|
DynoMat4x3: xn,
|
|
DynoMat4x4: Sn,
|
|
DynoOutput: K,
|
|
DynoProgram: ns,
|
|
DynoProgramTemplate: is,
|
|
DynoRemapIndex: oa,
|
|
DynoSampler2D: vn,
|
|
DynoSampler2DArray: Fn,
|
|
DynoSampler2DArrayShadow: Jn,
|
|
DynoSampler2DShadow: Yn,
|
|
DynoSampler3D: Tn,
|
|
DynoSamplerCube: Rn,
|
|
DynoSamplerCubeShadow: _n,
|
|
DynoUint: nn,
|
|
DynoUniform: N,
|
|
DynoUsampler2D: Dn,
|
|
DynoUsampler2DArray: Ht,
|
|
DynoUsampler3D: Nn,
|
|
DynoUsamplerCube: Un,
|
|
DynoUvec2: an,
|
|
DynoUvec3: gn,
|
|
DynoUvec4: un,
|
|
DynoValue: it,
|
|
DynoVec2: zt,
|
|
DynoVec3: Ft,
|
|
DynoVec4: Tt,
|
|
Equal: $i,
|
|
Exp: yi,
|
|
Exp2: wi,
|
|
ExtendVec: qr,
|
|
FaceForward: Kr,
|
|
Float: or,
|
|
FloatBitsToInt: mr,
|
|
FloatBitsToUint: xr,
|
|
Floor: Bi,
|
|
Fract: fi,
|
|
GreaterThan: qi,
|
|
GreaterThanEqual: Ki,
|
|
Gsplat: AA,
|
|
GsplatNormal: An,
|
|
Hash: ca,
|
|
Hash2: ga,
|
|
Hash3: la,
|
|
Hash4: Ia,
|
|
HashFloat: ua,
|
|
HashVec2: ha,
|
|
HashVec3: Ca,
|
|
HashVec4: Ba,
|
|
IMod: gi,
|
|
IVec2: Ir,
|
|
IVec3: ur,
|
|
IVec4: hr,
|
|
Int: rr,
|
|
IntBitsToFloat: Sr,
|
|
Inverse: jr,
|
|
InverseSqrt: Mi,
|
|
IsInf: Gi,
|
|
IsNan: Ui,
|
|
Length: Yr,
|
|
LessThan: zi,
|
|
LessThanEqual: Hi,
|
|
Log: mi,
|
|
Log2: xi,
|
|
Mat2: dr,
|
|
Mat3: yr,
|
|
Mat4: wr,
|
|
Max: bi,
|
|
Min: vi,
|
|
Mix: Ni,
|
|
Mod: li,
|
|
Modf: Ii,
|
|
Mul: oi,
|
|
Neg: ui,
|
|
Normalize: zr,
|
|
NormalizedDepth: Ea,
|
|
Not: Li,
|
|
NotEqual: Vi,
|
|
NumPackedSplats: Vs,
|
|
Or: Ji,
|
|
Outer: Zr,
|
|
OutputPackedSplat: sn,
|
|
OutputRgba8: ts,
|
|
PackHalf2x16: Nr,
|
|
PackSnorm2x16: Mr,
|
|
PackUnorm2x16: br,
|
|
PcgHash: TA,
|
|
PcgMix: Ut,
|
|
PcgNext: kA,
|
|
Pow: di,
|
|
ProjectH: Hr,
|
|
Radians: Ma,
|
|
ReadPackedSplat: Zs,
|
|
ReadPackedSplatRange: Xs,
|
|
ReflectVec: $r,
|
|
RefractVec: Vr,
|
|
Round: pi,
|
|
Select: Xi,
|
|
Sign: Ci,
|
|
SimpleCast: cA,
|
|
Sin: ba,
|
|
Sinh: Ra,
|
|
Smoothstep: Ti,
|
|
Split: Wr,
|
|
SplitGsplat: Os,
|
|
Sqr: Si,
|
|
Sqrt: Di,
|
|
Step: ki,
|
|
Sub: ai,
|
|
Swizzle: ta,
|
|
TPackedSplats: jt,
|
|
Tan: Na,
|
|
Tanh: Ja,
|
|
TexelFetch: xa,
|
|
Texture: ma,
|
|
TextureSize: wa,
|
|
TransformDir: da,
|
|
TransformGsplat: tn,
|
|
TransformPosition: fa,
|
|
TransformQuaternion: ya,
|
|
Transpose: Xr,
|
|
TrinaryOp: yt,
|
|
Trunc: Qi,
|
|
UVec2: Cr,
|
|
UVec3: Br,
|
|
UVec4: Er,
|
|
Uint: ar,
|
|
UintBitsToFloat: Dr,
|
|
UintToRgba8: Tr,
|
|
UnaryOp: v,
|
|
UnpackHalf2x16: kr,
|
|
UnpackSnorm2x16: vr,
|
|
UnpackUnorm2x16: Fr,
|
|
Vec2: Qr,
|
|
Vec3: pr,
|
|
Vec4: fr,
|
|
Xor: _i,
|
|
abs: El,
|
|
acos: ru,
|
|
acosh: uu,
|
|
add: BA,
|
|
all: Vl,
|
|
and: Rl,
|
|
any: $l,
|
|
arrayIndex: ZI,
|
|
arrayLength: XI,
|
|
asin: iu,
|
|
asinh: Iu,
|
|
atan: au,
|
|
atan2: ou,
|
|
atanh: hu,
|
|
bool: Ol,
|
|
bvec2: AI,
|
|
bvec3: tI,
|
|
bvec4: eI,
|
|
ceil: fl,
|
|
clamp: Nl,
|
|
combine: $A,
|
|
combineGsplat: rt,
|
|
comment: PI,
|
|
compMult: DI,
|
|
compXor: Pl,
|
|
cos: su,
|
|
cosh: gu,
|
|
cross: dI,
|
|
defineGsplat: bA,
|
|
defineGsplatNormal: Ws,
|
|
definePackedSplats: Qe,
|
|
degrees: eu,
|
|
determinant: bI,
|
|
distance: fI,
|
|
div: re,
|
|
dot: Ur,
|
|
dyno: Ot,
|
|
dynoBlock: vA,
|
|
dynoBool: hc,
|
|
dynoBvec2: Ec,
|
|
dynoBvec3: dc,
|
|
dynoBvec4: mc,
|
|
dynoConst: J,
|
|
dynoDeclare: We,
|
|
dynoFloat: HA,
|
|
dynoFor: VI,
|
|
dynoIf: KI,
|
|
dynoInt: Bc,
|
|
dynoIsampler2D: Lc,
|
|
dynoIsampler2DArray: qc,
|
|
dynoIsampler3D: Vc,
|
|
dynoIsamplerCube: Xc,
|
|
dynoIvec2: pc,
|
|
dynoIvec3: wc,
|
|
dynoIvec4: Sc,
|
|
dynoLiteral: oe,
|
|
dynoMat2: Mc,
|
|
dynoMat2x2: vc,
|
|
dynoMat2x3: bc,
|
|
dynoMat2x4: Fc,
|
|
dynoMat3: Nc,
|
|
dynoMat3x2: kc,
|
|
dynoMat3x3: Tc,
|
|
dynoMat3x4: Uc,
|
|
dynoMat4: Gc,
|
|
dynoMat4x2: Rc,
|
|
dynoMat4x3: Yc,
|
|
dynoMat4x4: Jc,
|
|
dynoSampler2D: zc,
|
|
dynoSampler2DArray: Kc,
|
|
dynoSampler2DArrayShadow: Wc,
|
|
dynoSampler2DShadow: jc,
|
|
dynoSampler3D: Pc,
|
|
dynoSamplerCube: Oc,
|
|
dynoSamplerCubeShadow: Ag,
|
|
dynoSwitch: $I,
|
|
dynoUint: Cc,
|
|
dynoUsampler2D: _c,
|
|
dynoUsampler2DArray: Hc,
|
|
dynoUsampler3D: $c,
|
|
dynoUsamplerCube: Zc,
|
|
dynoUvec2: Qc,
|
|
dynoUvec3: yc,
|
|
dynoUvec4: xc,
|
|
dynoVec2: fc,
|
|
dynoVec3: tt,
|
|
dynoVec4: Dc,
|
|
equal: ql,
|
|
exp: ml,
|
|
exp2: xl,
|
|
extendVec: Rr,
|
|
faceforward: yI,
|
|
float: Wi,
|
|
floatBitsToInt: er,
|
|
floatBitsToUint: sr,
|
|
floor: pl,
|
|
fract: ae,
|
|
greaterThan: Hl,
|
|
greaterThanEqual: Ri,
|
|
gsplatNormal: Re,
|
|
hash: ea,
|
|
hash2: sa,
|
|
hash3: na,
|
|
hash4: ia,
|
|
hashFloat: zI,
|
|
hashVec2: HI,
|
|
hashVec3: ra,
|
|
hashVec4: He,
|
|
imod: Le,
|
|
int: jl,
|
|
intBitsToFloat: II,
|
|
inverse: FI,
|
|
inversesqrt: bl,
|
|
isAllFloatType: at,
|
|
isBoolType: ft,
|
|
isFloatType: Zt,
|
|
isInf: Gl,
|
|
isIntType: EA,
|
|
isMat2: ot,
|
|
isMat3: ct,
|
|
isMat4: gt,
|
|
isMatFloatType: Js,
|
|
isNan: Ul,
|
|
isScalarType: dt,
|
|
isUintType: QA,
|
|
isVector2Type: Nt,
|
|
isVector3Type: kt,
|
|
isVector4Type: Xt,
|
|
isVectorType: rc,
|
|
ivec2: sI,
|
|
ivec3: nI,
|
|
ivec4: iI,
|
|
length: pI,
|
|
lessThan: Ll,
|
|
lessThanEqual: zl,
|
|
literalNegOne: gc,
|
|
literalOne: cc,
|
|
literalZero: Jt,
|
|
log: Sl,
|
|
log2: Dl,
|
|
mat2: cI,
|
|
mat3: gI,
|
|
mat4: lI,
|
|
max: ni,
|
|
min: Fl,
|
|
mix: ii,
|
|
mod: si,
|
|
modf: Bl,
|
|
mul: iA,
|
|
neg: as,
|
|
normalize: Gr,
|
|
normalizedDepth: aa,
|
|
not: _l,
|
|
notEqual: Kl,
|
|
numPackedSplats: lc,
|
|
numberAsFloat: H,
|
|
numberAsInt: rA,
|
|
numberAsUint: aA,
|
|
or: Yl,
|
|
outer: MI,
|
|
outputPackedSplat: en,
|
|
outputRgba8: Ic,
|
|
packHalf2x16: nr,
|
|
packSnorm2x16: hI,
|
|
packUnorm2x16: BI,
|
|
pcgHash: LI,
|
|
pcgMix: JI,
|
|
pcgNext: _I,
|
|
pow: wl,
|
|
projectH: xI,
|
|
radians: tu,
|
|
readPackedSplat: bt,
|
|
readPackedSplatRange: $s,
|
|
reflectVec: wI,
|
|
refractVec: mI,
|
|
remapIndex: YI,
|
|
round: yl,
|
|
sameSizeIvec: oc,
|
|
sameSizeUvec: zs,
|
|
sameSizeVec: ac,
|
|
select: os,
|
|
sign: Ql,
|
|
sin: qe,
|
|
sinh: cu,
|
|
smoothstep: Tl,
|
|
split: Et,
|
|
splitGsplat: ut,
|
|
sqr: Ml,
|
|
sqrt: vl,
|
|
step: kl,
|
|
sub: Qt,
|
|
swizzle: SI,
|
|
tan: nu,
|
|
tanh: lu,
|
|
texelFetch: WI,
|
|
texture: jI,
|
|
textureSize: OI,
|
|
transformDir: pa,
|
|
transformGsplat: As,
|
|
transformPos: Qa,
|
|
transformQuat: qI,
|
|
transpose: vI,
|
|
trunc: dl,
|
|
typeLiteral: Hs,
|
|
uint: Wl,
|
|
uintBitsToFloat: uI,
|
|
uintToRgba8: ze,
|
|
uniform: uc,
|
|
unindent: hA,
|
|
unindentLines: RA,
|
|
unpackHalf2x16: QI,
|
|
unpackSnorm2x16: CI,
|
|
unpackUnorm2x16: EI,
|
|
uvec2: rI,
|
|
uvec3: aI,
|
|
uvec4: oI,
|
|
valType: $,
|
|
vec2: Ar,
|
|
vec3: Bt,
|
|
vec4: tr,
|
|
vectorDim: Ls,
|
|
vectorElementType: _s,
|
|
xor: Jl
|
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
var Cu = `precision highp float;
|
|
precision highp int;
|
|
precision highp sampler2D;
|
|
precision highp usampler2D;
|
|
precision highp isampler2D;
|
|
precision highp sampler2DArray;
|
|
precision highp usampler2DArray;
|
|
precision highp isampler2DArray;
|
|
precision highp sampler3D;
|
|
precision highp usampler3D;
|
|
precision highp isampler3D;
|
|
|
|
#include <splatDefines>
|
|
|
|
uniform uint targetLayer;
|
|
uniform int targetBase;
|
|
uniform int targetCount;
|
|
|
|
out vec4 target;
|
|
|
|
{{ GLOBALS }}
|
|
|
|
void computeReadback(int index) {
|
|
{{ STATEMENTS }}
|
|
}
|
|
|
|
void main() {
|
|
int targetIndex = int(targetLayer << SPLAT_TEX_LAYER_BITS) + int(uint(gl_FragCoord.y) << SPLAT_TEX_WIDTH_BITS) + int(gl_FragCoord.x);
|
|
int index = targetIndex - targetBase;
|
|
|
|
if ((index >= 0) && (index < targetCount)) {
|
|
computeReadback(index);
|
|
} else {
|
|
target = vec4(0.0, 0.0, 0.0, 0.0);
|
|
}
|
|
}`;
|
|
const NA = class NA {
|
|
constructor({ renderer: A } = {}) {
|
|
this.renderer = A, this.capacity = 0, this.count = 0;
|
|
}
|
|
dispose() {
|
|
this.target && (this.target.dispose(), this.target = void 0);
|
|
}
|
|
// Ensure we have a buffer large enough for the readback of count indices.
|
|
// Pass in previous bufer of the desired type.
|
|
ensureBuffer(A, e) {
|
|
const n = Math.ceil(Math.max(1, A) / Z) * Z * 4;
|
|
if (e.byteLength >= n)
|
|
return e;
|
|
const i = new ArrayBuffer(n);
|
|
if (e instanceof ArrayBuffer)
|
|
return i;
|
|
const r = e.constructor;
|
|
return new r(i);
|
|
}
|
|
// Ensure our render target is large enough for the readback of capacity indices.
|
|
ensureCapacity(A) {
|
|
const { width: e, height: s, depth: n, maxSplats: i } = mA(A);
|
|
(!this.target || i > this.capacity) && (this.dispose(), this.capacity = i, this.target = new u.WebGLArrayRenderTarget(e, s, n, {
|
|
depthBuffer: !1,
|
|
stencilBuffer: !1,
|
|
generateMipmaps: !1,
|
|
magFilter: u.NearestFilter,
|
|
minFilter: u.NearestFilter
|
|
}), this.target.texture.format = u.RGBAFormat, this.target.texture.type = u.UnsignedByteType, this.target.texture.internalFormat = "RGBA8", this.target.scissorTest = !0);
|
|
}
|
|
// Get a program and THREE.RawShaderMaterial for a given Rgba8Readback,
|
|
// generating it if necessary and caching the result.
|
|
prepareProgramMaterial(A) {
|
|
let e = NA.readbackProgram.get(A);
|
|
if (!e) {
|
|
const n = vA(
|
|
{ index: "int" },
|
|
{ rgba8: "vec4" },
|
|
({ index: i }) => (A.inputs.index = i, { rgba8: new ts({ rgba8: A.outputs.rgba8 }) })
|
|
);
|
|
NA.programTemplate || (NA.programTemplate = new is(Cu)), e = new ns({
|
|
graph: n,
|
|
inputs: { index: "index" },
|
|
outputs: { rgba8: "target" },
|
|
template: NA.programTemplate
|
|
}), Object.assign(e.uniforms, {
|
|
targetLayer: { value: 0 },
|
|
targetBase: { value: 0 },
|
|
targetCount: { value: 0 }
|
|
}), NA.readbackProgram.set(A, e);
|
|
}
|
|
const s = e.prepareMaterial();
|
|
return NA.fullScreenQuad.material = s, { program: e, material: s };
|
|
}
|
|
saveRenderState(A) {
|
|
return {
|
|
xrEnabled: A.xr.enabled,
|
|
autoClear: A.autoClear
|
|
};
|
|
}
|
|
resetRenderState(A, e) {
|
|
A.setRenderTarget(null), A.xr.enabled = e.xrEnabled, A.autoClear = e.autoClear;
|
|
}
|
|
process({
|
|
count: A,
|
|
material: e
|
|
}) {
|
|
const s = this.renderer;
|
|
if (!s)
|
|
throw new Error("No renderer");
|
|
if (!this.target)
|
|
throw new Error("No target");
|
|
const n = Z * KA;
|
|
e.uniforms.targetBase.value = 0, e.uniforms.targetCount.value = A;
|
|
let i = 0;
|
|
for (; i < A; ) {
|
|
const r = Math.floor(i / n), a = r * n, o = Math.min(
|
|
KA,
|
|
Math.ceil((A - a) / Z)
|
|
);
|
|
e.uniforms.targetLayer.value = r, this.target.scissor.set(0, 0, Z, o), s.setRenderTarget(this.target, r), s.xr.enabled = !1, s.autoClear = !1, NA.fullScreenQuad.render(s), i += Z * o;
|
|
}
|
|
this.count = A;
|
|
}
|
|
async read({
|
|
readback: A
|
|
}) {
|
|
const e = this.renderer;
|
|
if (!e)
|
|
throw new Error("No renderer");
|
|
if (!this.target)
|
|
throw new Error("No target");
|
|
const s = Math.ceil(this.count / Z) * Z;
|
|
if (A.byteLength < s * 4)
|
|
throw new Error(
|
|
`Readback buffer too small: ${A.byteLength} < ${s * 4}`
|
|
);
|
|
const n = new Uint8Array(
|
|
A instanceof ArrayBuffer ? A : A.buffer
|
|
), i = Z * KA;
|
|
let r = 0;
|
|
const a = [];
|
|
for (; r < this.count; ) {
|
|
const o = Math.floor(r / i), g = o * i, l = Math.min(
|
|
KA,
|
|
Math.ceil((this.count - g) / Z)
|
|
);
|
|
e.setRenderTarget(this.target, o);
|
|
const c = Z * l * 4, I = n.subarray(
|
|
g * 4,
|
|
g * 4 + c
|
|
), h = e == null ? void 0 : e.readRenderTargetPixelsAsync(
|
|
this.target,
|
|
0,
|
|
0,
|
|
Z,
|
|
l,
|
|
I
|
|
);
|
|
a.push(h), r += Z * l;
|
|
}
|
|
return Promise.all(a).then(() => A);
|
|
}
|
|
// Perform render operation to run the Rgba8Readback program
|
|
// but don't perform the readback yet.
|
|
render({
|
|
reader: A,
|
|
count: e,
|
|
renderer: s
|
|
}) {
|
|
if (this.renderer = s || this.renderer, !this.renderer)
|
|
throw new Error("No renderer");
|
|
this.ensureCapacity(e);
|
|
const { program: n, material: i } = this.prepareProgramMaterial(A);
|
|
n.update();
|
|
const r = this.saveRenderState(this.renderer);
|
|
this.process({ count: e, material: i }), this.resetRenderState(this.renderer, r);
|
|
}
|
|
// Perform a readback of the render target, returning a buffer of the
|
|
// given type.
|
|
async readback({
|
|
readback: A
|
|
}) {
|
|
if (!this.renderer)
|
|
throw new Error("No renderer");
|
|
const e = this.saveRenderState(this.renderer), s = this.read({ readback: A });
|
|
return this.resetRenderState(this.renderer, e), s;
|
|
}
|
|
// Perform a render and readback operation for the given Rgba8Readback,
|
|
// and readback buffer (call ensureBuffer first).
|
|
async renderReadback({
|
|
reader: A,
|
|
count: e,
|
|
renderer: s,
|
|
readback: n
|
|
}) {
|
|
if (this.renderer = s || this.renderer, !this.renderer)
|
|
throw new Error("No renderer");
|
|
this.ensureCapacity(e);
|
|
const { program: i, material: r } = this.prepareProgramMaterial(A);
|
|
i.update();
|
|
const a = this.saveRenderState(this.renderer);
|
|
this.process({ count: e, material: r });
|
|
const o = this.read({ readback: n });
|
|
return this.resetRenderState(this.renderer, a), o;
|
|
}
|
|
getTexture() {
|
|
var A;
|
|
return (A = this.target) == null ? void 0 : A.texture;
|
|
}
|
|
};
|
|
NA.programTemplate = null, NA.readbackProgram = /* @__PURE__ */ new Map(), NA.fullScreenQuad = new xs(
|
|
new u.RawShaderMaterial({ visible: !1 })
|
|
);
|
|
let le = NA;
|
|
const IA = class IA {
|
|
constructor(A = {}) {
|
|
this.capacity = 0, this.count = 0, this.array = null, this.readback = null, this.source = null, this.needsUpdate = !0, this.dyno = new N({
|
|
key: "rgbaArray",
|
|
type: Ha,
|
|
globals: () => [qa],
|
|
value: {
|
|
texture: IA.getEmpty(),
|
|
count: 0
|
|
},
|
|
update: (e) => {
|
|
var s;
|
|
return e.texture = ((s = this.readback) == null ? void 0 : s.getTexture()) ?? this.source ?? IA.getEmpty(), e.count = this.count, e;
|
|
}
|
|
}), A.array ? (this.array = A.array, this.capacity = Math.floor(this.array.length / 4), this.capacity = Math.floor(this.capacity / Z) * Z, this.count = Math.min(
|
|
this.capacity,
|
|
A.count ?? Number.POSITIVE_INFINITY
|
|
)) : (this.capacity = A.capacity ?? 0, this.count = 0);
|
|
}
|
|
// Free up resources
|
|
dispose() {
|
|
this.readback && (this.readback.dispose(), this.readback = null), this.source && (this.source.dispose(), this.source = null);
|
|
}
|
|
// Ensure that our array is large enough to hold capacity RGBA8 values.
|
|
ensureCapacity(A) {
|
|
var e;
|
|
if (!this.array || A > (((e = this.array) == null ? void 0 : e.length) ?? 0) / 4) {
|
|
this.capacity = mA(A).maxSplats;
|
|
const s = new Uint8Array(this.capacity * 4);
|
|
this.array && s.set(this.array), this.array = s;
|
|
}
|
|
return this.array;
|
|
}
|
|
// Get the THREE.DataArrayTexture from either the readback or the source.
|
|
getTexture() {
|
|
var e;
|
|
let A = (e = this.readback) == null ? void 0 : e.getTexture();
|
|
return (this.source || this.array) && (A = this.maybeUpdateSource()), A ?? IA.getEmpty();
|
|
}
|
|
// Create or get a THREE.DataArrayTexture from the data array.
|
|
maybeUpdateSource() {
|
|
if (!this.array)
|
|
throw new Error("No array");
|
|
if (this.needsUpdate || !this.source) {
|
|
if (this.needsUpdate = !1, this.source) {
|
|
const { width: A, height: e, depth: s } = this.source.image;
|
|
this.capacity !== A * e * s && (this.source.dispose(), this.source = null);
|
|
}
|
|
if (this.source)
|
|
this.array.buffer !== this.source.image.data.buffer && (this.source.image.data = new Uint8Array(this.array.buffer));
|
|
else {
|
|
const { width: A, height: e, depth: s } = mA(this.capacity);
|
|
this.source = new u.DataArrayTexture(
|
|
this.array,
|
|
A,
|
|
e,
|
|
s
|
|
), this.source.format = u.RGBAFormat, this.source.type = u.UnsignedByteType, this.source.internalFormat = "RGBA8", this.source.needsUpdate = !0;
|
|
}
|
|
this.source.needsUpdate = !0;
|
|
}
|
|
return this.source;
|
|
}
|
|
// Generate the RGBA8 values from a Rgba8Readback dyno program.
|
|
render({
|
|
reader: A,
|
|
count: e,
|
|
renderer: s
|
|
}) {
|
|
this.readback || (this.readback = new le({ renderer: s })), this.readback.render({ reader: A, count: e, renderer: s }), this.capacity = this.readback.capacity, this.count = this.readback.count;
|
|
}
|
|
// Extract the RGBA8 values from a PackedSplats collection.
|
|
fromPackedSplats({
|
|
packedSplats: A,
|
|
base: e,
|
|
count: s,
|
|
renderer: n
|
|
}) {
|
|
const { dynoSplats: i, dynoBase: r, dynoCount: a, reader: o } = IA.makeDynos();
|
|
return i.packedSplats = A, r.value = e, a.value = s, this.render({ reader: o, count: s, renderer: n }), this;
|
|
}
|
|
// Read back the RGBA8 values from the readback buffer.
|
|
async read() {
|
|
if (!this.readback)
|
|
throw new Error("No readback");
|
|
return (!this.array || this.array.length < this.count * 4) && (this.array = new Uint8Array(this.capacity * 4)), (await this.readback.readback({ readback: this.array })).subarray(0, this.count * 4);
|
|
}
|
|
// Can be used where you need an uninitialized THREE.DataArrayTexture like
|
|
// a uniform you will update with the result of this.getTexture() later.
|
|
static getEmpty() {
|
|
if (!IA.emptySource) {
|
|
const A = new Uint8Array(4);
|
|
IA.emptySource = new u.DataArrayTexture(A, 1, 1, 1), IA.emptySource.format = u.RGBAFormat, IA.emptySource.type = u.UnsignedByteType, IA.emptySource.internalFormat = "RGBA8", IA.emptySource.needsUpdate = !0;
|
|
}
|
|
return IA.emptySource;
|
|
}
|
|
// Create a dyno program that can extract RGBA8 values from a PackedSplats
|
|
static makeDynos() {
|
|
if (!IA.dynos) {
|
|
const A = new ls(), e = new $t({ value: 0 }), s = new $t({ value: 0 }), n = vA(
|
|
{ index: "int" },
|
|
{ rgba8: "vec4" },
|
|
({ index: i }) => {
|
|
if (!i)
|
|
throw new Error("index is undefined");
|
|
i = BA(i, e);
|
|
const r = $s(
|
|
A,
|
|
i,
|
|
e,
|
|
s
|
|
);
|
|
return { rgba8: ut(r).outputs.rgba };
|
|
}
|
|
);
|
|
IA.dynos = { dynoSplats: A, dynoBase: e, dynoCount: s, reader: n };
|
|
}
|
|
return IA.dynos;
|
|
}
|
|
};
|
|
IA.emptySource = null, IA.dynos = null;
|
|
let Ke = IA;
|
|
const Ha = { type: "RgbaArray" }, qa = hA(`
|
|
struct RgbaArray {
|
|
sampler2DArray texture;
|
|
int count;
|
|
};
|
|
`);
|
|
function Bu(t, A) {
|
|
return new V({
|
|
inTypes: { rgba: Ha, index: "int" },
|
|
outTypes: { rgba: "vec4" },
|
|
inputs: { rgba: t, index: A },
|
|
globals: () => [qa],
|
|
statements: ({ inputs: s, outputs: n }) => RA(`
|
|
if ((index >= 0) && (index < ${s.rgba}.count)) {
|
|
${n.rgba} = texelFetch(${s.rgba}.texture, splatTexCoord(index), 0);
|
|
} else {
|
|
${n.rgba} = vec4(0.0, 0.0, 0.0, 0.0);
|
|
}
|
|
`)
|
|
}).outputs.rgba;
|
|
}
|
|
var Eu = /* @__PURE__ */ ((t) => (t.ALL = "all", t.PLANE = "plane", t.SPHERE = "sphere", t.BOX = "box", t.ELLIPSOID = "ellipsoid", t.CYLINDER = "cylinder", t.CAPSULE = "capsule", t.INFINITE_CONE = "infinite_cone", t))(Eu || {});
|
|
function Qu(t) {
|
|
switch (t) {
|
|
case "all":
|
|
return 0;
|
|
case "plane":
|
|
return 1;
|
|
case "sphere":
|
|
return 2;
|
|
case "box":
|
|
return 3;
|
|
case "ellipsoid":
|
|
return 4;
|
|
case "cylinder":
|
|
return 5;
|
|
case "capsule":
|
|
return 6;
|
|
case "infinite_cone":
|
|
return 7;
|
|
default:
|
|
throw new Error(`Unknown SDF type: ${t}`);
|
|
}
|
|
}
|
|
var pu = /* @__PURE__ */ ((t) => (t.MULTIPLY = "multiply", t.SET_RGB = "set_rgb", t.ADD_RGBA = "add_rgba", t))(pu || {});
|
|
function fu(t) {
|
|
switch (t) {
|
|
case "multiply":
|
|
return 0;
|
|
case "set_rgb":
|
|
return 1;
|
|
case "add_rgba":
|
|
return 2;
|
|
default:
|
|
throw new Error(`Unknown blend mode: ${t}`);
|
|
}
|
|
}
|
|
class du extends u.Object3D {
|
|
constructor(A = {}) {
|
|
super();
|
|
const { type: e, invert: s, opacity: n, color: i, displace: r, radius: a } = A;
|
|
this.type = e ?? "sphere", this.invert = s ?? !1, this.opacity = n ?? 1, this.color = i ?? new u.Color(1, 1, 1), this.displace = r ?? new u.Vector3(0, 0, 0), this.radius = a ?? 0;
|
|
}
|
|
}
|
|
const Ee = class Ee extends u.Object3D {
|
|
constructor(A = {}) {
|
|
const {
|
|
name: e,
|
|
rgbaBlendMode: s = "multiply",
|
|
sdfSmooth: n = 0,
|
|
softEdge: i = 0,
|
|
invert: r = !1,
|
|
sdfs: a = null
|
|
} = A;
|
|
super(), this.rgbaBlendMode = s, this.sdfSmooth = n, this.softEdge = i, this.invert = r, this.sdfs = a, this.ordering = Ee.nextOrdering++, this.name = e ?? `Edit ${this.ordering}`;
|
|
}
|
|
addSdf(A) {
|
|
this.sdfs == null && (this.sdfs = []), this.sdfs.includes(A) || this.sdfs.push(A);
|
|
}
|
|
removeSdf(A) {
|
|
this.sdfs != null && (this.sdfs = this.sdfs.filter((e) => e !== A));
|
|
}
|
|
};
|
|
Ee.nextOrdering = 1;
|
|
let Ie = Ee;
|
|
class yu {
|
|
constructor({ maxSdfs: A, maxEdits: e }) {
|
|
this.maxSdfs = Math.max(16, A ?? 0), this.numSdfs = 0, this.sdfData = new Uint32Array(this.maxSdfs * 8 * 4), this.sdfFloatData = new Float32Array(this.sdfData.buffer), this.sdfTexture = this.newSdfTexture(this.sdfData, this.maxSdfs), this.dynoSdfArray = new N({
|
|
key: "sdfArray",
|
|
type: Ka,
|
|
globals: () => [$a],
|
|
value: {
|
|
numSdfs: 0,
|
|
sdfTexture: this.sdfTexture
|
|
},
|
|
update: (s) => (s.numSdfs = this.numSdfs, s.sdfTexture = this.sdfTexture, s)
|
|
}), this.maxEdits = Math.max(16, e ?? 0), this.numEdits = 0, this.editData = new Uint32Array(this.maxEdits * 4), this.editFloatData = new Float32Array(this.editData.buffer), this.dynoNumEdits = new $t({ value: 0 }), this.dynoEdits = this.newEdits(this.editData, this.maxEdits);
|
|
}
|
|
newSdfTexture(A, e) {
|
|
const s = new u.DataTexture(
|
|
A,
|
|
8,
|
|
e,
|
|
u.RGBAIntegerFormat,
|
|
u.UnsignedIntType
|
|
);
|
|
return s.internalFormat = "RGBA32UI", s.needsUpdate = !0, s;
|
|
}
|
|
newEdits(A, e) {
|
|
return new N({
|
|
key: "edits",
|
|
type: "uvec4",
|
|
count: e,
|
|
globals: () => [Va],
|
|
value: A
|
|
});
|
|
}
|
|
// Ensure our SDF texture and edits uniform array have enough capacity.
|
|
// Reallocate if not.
|
|
ensureCapacity({
|
|
maxSdfs: A,
|
|
maxEdits: e
|
|
}) {
|
|
let s = !1;
|
|
return A > this.sdfTexture.image.height && (this.sdfTexture.dispose(), this.maxSdfs = Math.max(this.maxSdfs * 2, A), this.sdfData = new Uint32Array(this.maxSdfs * 8 * 4), this.sdfFloatData = new Float32Array(this.sdfData.buffer), this.sdfTexture = this.newSdfTexture(this.sdfData, this.maxSdfs)), e > (this.dynoEdits.count ?? 0) && (this.maxEdits = Math.max(this.maxEdits * 2, e), this.editData = new Uint32Array(this.maxEdits * 4), this.editFloatData = new Float32Array(this.editData.buffer), this.dynoEdits = this.newEdits(this.editData, this.maxEdits), s = !0), s;
|
|
}
|
|
updateEditData(A, e) {
|
|
const s = this.editData[A] !== e;
|
|
return this.editData[A] = e, s;
|
|
}
|
|
updateEditFloatData(A, e) {
|
|
wt[0] = e;
|
|
const s = this.editFloatData[A] !== wt[0];
|
|
return s && (this.editFloatData[A] = wt[0]), s;
|
|
}
|
|
encodeEdit(A, {
|
|
sdfFirst: e,
|
|
sdfCount: s,
|
|
invert: n,
|
|
rgbaBlendMode: i,
|
|
softEdge: r,
|
|
sdfSmooth: a
|
|
}) {
|
|
const o = A * 4;
|
|
let g = !1;
|
|
return g = this.updateEditData(o + 0, i | (n ? 256 : 0)) || g, g = this.updateEditData(o + 1, e | s << 16) || g, g = this.updateEditFloatData(o + 2, r) || g, g = this.updateEditFloatData(o + 3, a) || g, g;
|
|
}
|
|
updateSdfData(A, e) {
|
|
const s = this.sdfData[A] !== e;
|
|
return this.sdfData[A] = e, s;
|
|
}
|
|
updateSdfFloatData(A, e) {
|
|
wt[0] = e;
|
|
const s = this.sdfFloatData[A] !== wt[0];
|
|
return s && (this.sdfFloatData[A] = wt[0]), s;
|
|
}
|
|
encodeSdf(A, {
|
|
sdfType: e,
|
|
invert: s,
|
|
center: n,
|
|
quaternion: i,
|
|
scale: r,
|
|
sizes: a
|
|
}, o) {
|
|
const g = A * 32, l = e | (s ? 256 : 0);
|
|
let c = !1;
|
|
c = this.updateSdfFloatData(g + 0, (n == null ? void 0 : n.x) ?? 0) || c, c = this.updateSdfFloatData(g + 1, (n == null ? void 0 : n.y) ?? 0) || c, c = this.updateSdfFloatData(g + 2, (n == null ? void 0 : n.z) ?? 0) || c, c = this.updateSdfData(g + 3, l) || c, c = this.updateSdfFloatData(g + 4, (i == null ? void 0 : i.x) ?? 0) || c, c = this.updateSdfFloatData(g + 5, (i == null ? void 0 : i.y) ?? 0) || c, c = this.updateSdfFloatData(g + 6, (i == null ? void 0 : i.z) ?? 0) || c, c = this.updateSdfFloatData(g + 7, (i == null ? void 0 : i.w) ?? 0) || c, c = this.updateSdfFloatData(g + 8, (r == null ? void 0 : r.x) ?? 0) || c, c = this.updateSdfFloatData(g + 9, (r == null ? void 0 : r.y) ?? 0) || c, c = this.updateSdfFloatData(g + 10, (r == null ? void 0 : r.z) ?? 0) || c, c = this.updateSdfData(g + 11, 0) || c, c = this.updateSdfFloatData(g + 12, (a == null ? void 0 : a.x) ?? 0) || c, c = this.updateSdfFloatData(g + 13, (a == null ? void 0 : a.y) ?? 0) || c, c = this.updateSdfFloatData(g + 14, (a == null ? void 0 : a.z) ?? 0) || c, c = this.updateSdfFloatData(g + 15, (a == null ? void 0 : a.w) ?? 0) || c;
|
|
const I = Math.min(4, o.length);
|
|
for (let h = 0; h < I; ++h) {
|
|
const E = g + 16 + h * 4;
|
|
c = this.updateSdfFloatData(E + 0, o[h].x) || c, c = this.updateSdfFloatData(E + 1, o[h].y) || c, c = this.updateSdfFloatData(E + 2, o[h].z) || c, c = this.updateSdfFloatData(E + 3, o[h].w) || c;
|
|
}
|
|
return c;
|
|
}
|
|
// Update the SDFs and edits from an array of SplatEdits and their
|
|
// associated SplatEditSdfs, updating it for the dyno shader program.
|
|
update(A) {
|
|
const e = A.reduce((c, { sdfs: I }) => c + I.length, 0), s = this.ensureCapacity({
|
|
maxEdits: A.length,
|
|
maxSdfs: e
|
|
}), n = [new u.Vector4(), new u.Vector4()], i = new u.Vector3(), r = new u.Quaternion(), a = new u.Vector3(), o = new u.Vector4();
|
|
let g = 0, l = s;
|
|
A.length !== this.dynoNumEdits.value && (this.dynoNumEdits.value = A.length, this.numEdits = A.length, l = !0);
|
|
for (const [c, { edit: I, sdfs: h }] of A.entries()) {
|
|
l = this.encodeEdit(c, {
|
|
sdfFirst: g,
|
|
sdfCount: h.length,
|
|
invert: I.invert,
|
|
rgbaBlendMode: fu(I.rgbaBlendMode),
|
|
softEdge: I.softEdge,
|
|
sdfSmooth: I.sdfSmooth
|
|
}) || l;
|
|
let E = !1;
|
|
for (const C of h)
|
|
o.set(C.scale.x, C.scale.y, C.scale.z, C.radius), C.scale.setScalar(1), C.updateMatrixWorld(), C.matrixWorld.clone().invert().decompose(i, r, a), C.scale.set(o.x, o.y, o.z), C.updateMatrixWorld(), n[0].set(C.color.r, C.color.g, C.color.b, C.opacity), n[1].set(C.displace.x, C.displace.y, C.displace.z, 1), E = this.encodeSdf(
|
|
g,
|
|
{
|
|
sdfType: Qu(C.type),
|
|
invert: C.invert,
|
|
center: i,
|
|
quaternion: r,
|
|
scale: a,
|
|
sizes: o
|
|
},
|
|
n
|
|
) || E, g += 1;
|
|
this.numSdfs = g, E && (this.sdfTexture.needsUpdate = !0), l || (l = E);
|
|
}
|
|
return { updated: l, dynoUpdated: s };
|
|
}
|
|
// Modify a Gsplat in a dyno shader program using the current edits and SDFs.
|
|
modify(A) {
|
|
return wu(
|
|
A,
|
|
this.dynoSdfArray,
|
|
this.dynoNumEdits,
|
|
this.dynoEdits
|
|
);
|
|
}
|
|
}
|
|
const Ka = { type: "SdfArray" }, $a = hA(`
|
|
struct SdfArray {
|
|
int numSdfs;
|
|
usampler2D sdfTexture;
|
|
};
|
|
|
|
void unpackSdfArray(
|
|
usampler2D sdfTexture, int sdfIndex, out uint flags,
|
|
out vec3 center, out vec4 quaternion, out vec3 scale, out vec4 sizes,
|
|
int numValues, out vec4 values[4]
|
|
) {
|
|
uvec4 temp = texelFetch(sdfTexture, ivec2(0, sdfIndex), 0);
|
|
flags = temp.w;
|
|
center = vec3(uintBitsToFloat(temp.x), uintBitsToFloat(temp.y), uintBitsToFloat(temp.z));
|
|
|
|
temp = texelFetch(sdfTexture, ivec2(1, sdfIndex), 0);
|
|
quaternion = vec4(uintBitsToFloat(temp.x), uintBitsToFloat(temp.y), uintBitsToFloat(temp.z), uintBitsToFloat(temp.w));
|
|
|
|
temp = texelFetch(sdfTexture, ivec2(2, sdfIndex), 0);
|
|
scale = vec3(uintBitsToFloat(temp.x), uintBitsToFloat(temp.y), uintBitsToFloat(temp.z));
|
|
|
|
temp = texelFetch(sdfTexture, ivec2(3, sdfIndex), 0);
|
|
sizes = vec4(uintBitsToFloat(temp.x), uintBitsToFloat(temp.y), uintBitsToFloat(temp.z), uintBitsToFloat(temp.w));
|
|
|
|
for (int i = 0; i < numValues; ++i) {
|
|
temp = texelFetch(sdfTexture, ivec2(4 + i, sdfIndex), 0);
|
|
values[i] = vec4(uintBitsToFloat(temp.x), uintBitsToFloat(temp.y), uintBitsToFloat(temp.z), uintBitsToFloat(temp.w));
|
|
}
|
|
}
|
|
|
|
const uint SDF_FLAG_TYPE = 0xFFu;
|
|
const uint SDF_FLAG_INVERT = 1u << 8u;
|
|
|
|
const uint SDF_TYPE_ALL = 0u;
|
|
const uint SDF_TYPE_PLANE = 1u;
|
|
const uint SDF_TYPE_SPHERE = 2u;
|
|
const uint SDF_TYPE_BOX = 3u;
|
|
const uint SDF_TYPE_ELLIPSOID = 4u;
|
|
const uint SDF_TYPE_CYLINDER = 5u;
|
|
const uint SDF_TYPE_CAPSULE = 6u;
|
|
const uint SDF_TYPE_INFINITE_CONE = 7u;
|
|
|
|
float evaluateSdfArray(
|
|
usampler2D sdfTexture, int numSdfs, int sdfFirst, int sdfCount, vec3 pos,
|
|
float smoothK, int numValues, out vec4 outValues[4]
|
|
) {
|
|
float distanceAccum = (smoothK == 0.0) ? 1.0 / 0.0 : 0.0;
|
|
float maxExp = -1.0 / 0.0;
|
|
for (int i = 0; i < numValues; ++i) {
|
|
outValues[i] = vec4(0.0);
|
|
}
|
|
|
|
uint flags;
|
|
vec3 center, scale;
|
|
vec4 quaternion, sizes;
|
|
vec4 values[4];
|
|
|
|
int sdfLast = min(sdfFirst + sdfCount, numSdfs);
|
|
for (int index = sdfFirst; index < sdfLast; ++index) {
|
|
unpackSdfArray(sdfTexture, index, flags, center, quaternion, scale, sizes, numValues, values);
|
|
uint sdfType = flags & SDF_FLAG_TYPE;
|
|
vec3 sdfPos = quatVec(quaternion, pos * scale) + center;
|
|
|
|
float distance;
|
|
switch (sdfType) {
|
|
case SDF_TYPE_ALL:
|
|
distance = -1.0 / 0.0;
|
|
break;
|
|
case SDF_TYPE_PLANE: {
|
|
distance = sdfPos.z;
|
|
break;
|
|
}
|
|
case SDF_TYPE_SPHERE: {
|
|
distance = length(sdfPos) - sizes.w;
|
|
break;
|
|
}
|
|
case SDF_TYPE_BOX: {
|
|
vec3 q = abs(sdfPos) - sizes.xyz + sizes.w;
|
|
distance = length(max(q, 0.0)) + min(max(q.x, max(q.y, q.z)), 0.0) - sizes.w;
|
|
break;
|
|
}
|
|
case SDF_TYPE_ELLIPSOID: {
|
|
vec3 sizes = sizes.xyz;
|
|
float k0 = length(sdfPos / sizes);
|
|
float k1 = length(sdfPos / dot(sizes, sizes));
|
|
distance = k0 * (k0 - 1.0) / k1;
|
|
break;
|
|
}
|
|
case SDF_TYPE_CYLINDER: {
|
|
vec2 d = abs(vec2(length(sdfPos.xz), sdfPos.y)) - sizes.wy;
|
|
distance = min(max(d.x, d.y), 0.0) + length(max(d, 0.0));
|
|
break;
|
|
}
|
|
case SDF_TYPE_CAPSULE: {
|
|
sdfPos.y -= clamp(sdfPos.y, -0.5 * sizes.y, 0.5 * sizes.y);
|
|
distance = length(sdfPos) - sizes.w;
|
|
break;
|
|
}
|
|
case SDF_TYPE_INFINITE_CONE: {
|
|
float angle = 0.25 * PI * sizes.w;
|
|
vec2 c = vec2(sin(angle), cos(angle));
|
|
vec2 q = vec2(length(sdfPos.xy), -sdfPos.z);
|
|
float d = length(q - c * max(dot(q, c), 0.0));
|
|
distance = d * (((q.x * c.y - q.y * c.x) < 0.0) ? -1.0 : 1.0);
|
|
break;
|
|
}
|
|
}
|
|
|
|
if ((flags & SDF_FLAG_INVERT) != 0u) {
|
|
distance = -distance;
|
|
}
|
|
|
|
if (smoothK == 0.0) {
|
|
if (distance < distanceAccum) {
|
|
distanceAccum = distance;
|
|
for (int i = 0; i < numValues; ++i) {
|
|
outValues[i] = values[i];
|
|
}
|
|
}
|
|
} else {
|
|
float scaledDistance = -distance / smoothK;
|
|
if (scaledDistance > maxExp) {
|
|
float scale = exp(maxExp - scaledDistance);
|
|
distanceAccum *= scale;
|
|
for (int i = 0; i < numValues; ++i) {
|
|
outValues[i] *= scale;
|
|
}
|
|
maxExp = scaledDistance;
|
|
}
|
|
|
|
float weight = exp(scaledDistance - maxExp);
|
|
distanceAccum += weight;
|
|
for (int i = 0; i < numValues; ++i) {
|
|
outValues[i] += weight * values[i];
|
|
}
|
|
}
|
|
}
|
|
|
|
if (smoothK == 0.0) {
|
|
return distanceAccum;
|
|
} else {
|
|
// Very distant SDFs may result in 0 accumulation
|
|
if (distanceAccum == 0.0) {
|
|
return 1.0 / 0.0;
|
|
}
|
|
for (int i = 0; i < numValues; ++i) {
|
|
outValues[i] /= distanceAccum;
|
|
}
|
|
return (-log(distanceAccum) - maxExp) * smoothK;
|
|
}
|
|
}
|
|
|
|
float modulateSdfArray(
|
|
usampler2D sdfTexture, int numSdfs, int sdfFirst, int sdfCount, vec3 pos,
|
|
float smoothK, int numValues, out vec4 values[4],
|
|
float softEdge, bool invert
|
|
) {
|
|
float distance = evaluateSdfArray(sdfTexture, numSdfs, sdfFirst, sdfCount, pos, smoothK, numValues, values);
|
|
if (invert) {
|
|
distance = -distance;
|
|
}
|
|
|
|
return (softEdge == 0.0) ? ((distance < 0.0) ? 1.0 : 0.0)
|
|
: clamp(-distance / softEdge + 0.5, 0.0, 1.0);
|
|
}
|
|
`), Va = hA(`
|
|
const uint EDIT_FLAG_BLEND = 0xFFu;
|
|
const uint EDIT_BLEND_MULTIPLY = 0u;
|
|
const uint EDIT_BLEND_SET_RGB = 1u;
|
|
const uint EDIT_BLEND_ADD_RGBA = 2u;
|
|
const uint EDIT_FLAG_INVERT = 0x100u;
|
|
|
|
void decodeEdit(
|
|
uvec4 packedEdit, out int sdfFirst, out int sdfCount,
|
|
out bool invert, out uint rgbaBlendMode, out float softEdge, out float sdfSmooth
|
|
) {
|
|
rgbaBlendMode = packedEdit.x & EDIT_FLAG_BLEND;
|
|
invert = (packedEdit.x & EDIT_FLAG_INVERT) != 0u;
|
|
|
|
sdfFirst = int(packedEdit.y & 0xFFFFu);
|
|
sdfCount = int(packedEdit.y >> 16u);
|
|
|
|
softEdge = uintBitsToFloat(packedEdit.z);
|
|
sdfSmooth = uintBitsToFloat(packedEdit.w);
|
|
}
|
|
|
|
void applyRgbaDisplaceEdit(
|
|
usampler2D sdfTexture, int numSdfs, int sdfFirst, int sdfCount, inout vec3 pos,
|
|
float smoothK, float softEdge, bool invert, uint rgbaBlendMode, inout vec4 rgba
|
|
) {
|
|
vec4 values[4];
|
|
float modulate = modulateSdfArray(sdfTexture, numSdfs, sdfFirst, sdfCount, pos, smoothK, 2, values, softEdge, invert);
|
|
// On Android, moving values[0] is necessary to work around a compiler bug.
|
|
vec4 sdfRgba = values[0];
|
|
vec4 sdfDisplaceScale = values[1];
|
|
|
|
vec4 target;
|
|
switch (rgbaBlendMode) {
|
|
case EDIT_BLEND_MULTIPLY:
|
|
target = rgba * sdfRgba;
|
|
break;
|
|
case EDIT_BLEND_SET_RGB:
|
|
target = vec4(sdfRgba.rgb, rgba.a * sdfRgba.a);
|
|
break;
|
|
case EDIT_BLEND_ADD_RGBA:
|
|
target = rgba + sdfRgba;
|
|
break;
|
|
default:
|
|
// Debug output if blend mode not set
|
|
target = vec4(fract(pos), 1.0);
|
|
}
|
|
rgba = mix(rgba, target, modulate);
|
|
pos += sdfDisplaceScale.xyz * modulate;
|
|
}
|
|
|
|
void applyPackedRgbaDisplaceEdit(uvec4 packedEdit, usampler2D sdfTexture, int numSdfs, inout vec3 pos, inout vec4 rgba) {
|
|
int sdfFirst, sdfCount;
|
|
bool invert;
|
|
uint rgbaBlendMode;
|
|
float softEdge, sdfSmooth;
|
|
decodeEdit(packedEdit, sdfFirst, sdfCount, invert, rgbaBlendMode, softEdge, sdfSmooth);
|
|
applyRgbaDisplaceEdit(sdfTexture, numSdfs, sdfFirst, sdfCount, pos, sdfSmooth, softEdge, invert, rgbaBlendMode, rgba);
|
|
}
|
|
`);
|
|
function wu(t, A, e, s) {
|
|
return new V({
|
|
inTypes: {
|
|
gsplat: AA,
|
|
sdfArray: Ka,
|
|
numEdits: "int",
|
|
rgbaDisplaceEdits: "uvec4"
|
|
},
|
|
outTypes: { gsplat: AA },
|
|
globals: () => [$a, Va],
|
|
inputs: { gsplat: t, sdfArray: A, numEdits: e, rgbaDisplaceEdits: s },
|
|
statements: ({ inputs: i, outputs: r }) => {
|
|
const { sdfArray: a, numEdits: o, rgbaDisplaceEdits: g } = i, { gsplat: l } = r;
|
|
return RA(`
|
|
${l} = ${i.gsplat};
|
|
if (isGsplatActive(${l}.flags)) {
|
|
for (int editIndex = 0; editIndex < ${o}; ++editIndex) {
|
|
applyPackedRgbaDisplaceEdit(
|
|
${g}[editIndex], ${a}.sdfTexture, ${a}.numSdfs,
|
|
${l}.center, ${l}.rgba
|
|
);
|
|
}
|
|
}
|
|
`);
|
|
}
|
|
}).outputs.gsplat;
|
|
}
|
|
const wt = new Float32Array(1);
|
|
class mu {
|
|
constructor(A) {
|
|
this.modifier = A, this.cache = /* @__PURE__ */ new Map();
|
|
}
|
|
apply(A) {
|
|
let e = this.cache.get(A);
|
|
return e || (e = vA(
|
|
{ index: "int" },
|
|
{ gsplat: AA },
|
|
({ index: s }) => {
|
|
const { gsplat: n } = A.apply({ index: s });
|
|
return this.modifier.apply({ gsplat: n });
|
|
}
|
|
), this.cache.set(A, e)), e;
|
|
}
|
|
}
|
|
class xt {
|
|
// Create the dyno uniforms that parameterize the transform, setting them
|
|
// to initial values that are different from any valid transform.
|
|
constructor() {
|
|
this.scale = new ht({ value: Number.NEGATIVE_INFINITY }), this.rotate = new Tt({
|
|
value: new u.Quaternion(
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY
|
|
)
|
|
}), this.translate = new Ft({
|
|
value: new u.Vector3(
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY
|
|
)
|
|
});
|
|
}
|
|
// Apply the transform to a Vec3 position in a dyno program.
|
|
apply(A) {
|
|
return Qa(A, {
|
|
scale: this.scale,
|
|
rotate: this.rotate,
|
|
translate: this.translate
|
|
});
|
|
}
|
|
applyDir(A) {
|
|
return pa(A, {
|
|
rotate: this.rotate
|
|
});
|
|
}
|
|
// Apply the transform to a Gsplat in a dyno program.
|
|
applyGsplat(A) {
|
|
return As(A, {
|
|
scale: this.scale,
|
|
rotate: this.rotate,
|
|
translate: this.translate
|
|
});
|
|
}
|
|
// Update the uniforms to match the given transform matrix.
|
|
updateFromMatrix(A) {
|
|
const e = new u.Vector3(), s = new u.Quaternion(), n = new u.Vector3();
|
|
A.decompose(n, s, e);
|
|
const i = (e.x + e.y + e.z) / 3;
|
|
let r = !1;
|
|
return i !== this.scale.value && (this.scale.value = i, r = !0), n.equals(this.translate.value) || (this.translate.value.copy(n), r = !0), s.equals(this.rotate.value) || (this.rotate.value.copy(s), r = !0), r;
|
|
}
|
|
// Update this transform to match the object's to-world transform.
|
|
update(A) {
|
|
return A.updateMatrixWorld(), this.updateFromMatrix(A.matrixWorld);
|
|
}
|
|
}
|
|
class Vt extends u.Object3D {
|
|
constructor({
|
|
numSplats: A,
|
|
generator: e,
|
|
construct: s,
|
|
update: n
|
|
}) {
|
|
if (super(), this.numSplats = A ?? 0, this.generator = e, this.frameUpdate = n, this.version = 0, s) {
|
|
const i = s(this);
|
|
Object.assign(this, i);
|
|
}
|
|
}
|
|
updateVersion() {
|
|
this.version += 1;
|
|
}
|
|
set needsUpdate(A) {
|
|
A && this.updateVersion();
|
|
}
|
|
}
|
|
const st = class st extends Vt {
|
|
constructor(A = {}) {
|
|
const e = new xt(), s = new xt(), n = new xt(), i = new xt(), r = new Tt({
|
|
value: new u.Vector4(
|
|
Number.NEGATIVE_INFINITY,
|
|
Number.NEGATIVE_INFINITY,
|
|
Number.NEGATIVE_INFINITY,
|
|
Number.NEGATIVE_INFINITY
|
|
)
|
|
}), a = new ht({ value: 0 }), o = new ht({ value: 0 }), g = {
|
|
transform: e,
|
|
viewToWorld: s,
|
|
worldToView: n,
|
|
viewToObject: i,
|
|
recolor: r,
|
|
time: a,
|
|
deltaTime: o
|
|
};
|
|
if (super({
|
|
update: ({ time: l, deltaTime: c, viewToWorld: I, globalEdits: h }) => this.update({ time: l, deltaTime: c, viewToWorld: I, globalEdits: h })
|
|
}), this.isInitialized = !1, this.recolor = new u.Color(1, 1, 1), this.opacity = 1, this.enableViewToObject = !1, this.enableViewToWorld = !1, this.enableWorldToView = !1, this.skinning = null, this.edits = null, this.rgbaDisplaceEdits = null, this.splatRgba = null, this.maxSh = 3, this.packedSplats = A.packedSplats ?? new VA(), this.packedSplats.splatEncoding = A.splatEncoding ?? {
|
|
...de
|
|
}, this.numSplats = this.packedSplats.numSplats, this.editable = A.editable ?? !0, this.onFrame = A.onFrame, this.context = g, this.objectModifier = A.objectModifier, this.worldModifier = A.worldModifier, this.updateGenerator(), A.url || A.fileBytes || A.constructSplats || A.packedSplats && !A.packedSplats.isInitialized)
|
|
this.initialized = this.asyncInitialize(A).then(async () => {
|
|
if (this.updateGenerator(), this.isInitialized = !0, A.onLoad) {
|
|
const l = A.onLoad(this);
|
|
l instanceof Promise && await l;
|
|
}
|
|
return this;
|
|
});
|
|
else if (this.isInitialized = !0, this.initialized = Promise.resolve(this), A.onLoad) {
|
|
const l = A.onLoad(this);
|
|
l instanceof Promise && (this.initialized = l.then(() => this));
|
|
}
|
|
this.add(ku());
|
|
}
|
|
async asyncInitialize(A) {
|
|
const {
|
|
url: e,
|
|
fileBytes: s,
|
|
fileType: n,
|
|
fileName: i,
|
|
maxSplats: r,
|
|
constructSplats: a,
|
|
splatEncoding: o
|
|
} = A;
|
|
if (e || s || a) {
|
|
const g = {
|
|
url: e,
|
|
fileBytes: s,
|
|
fileType: n,
|
|
fileName: i,
|
|
maxSplats: r,
|
|
construct: a,
|
|
splatEncoding: o
|
|
};
|
|
this.packedSplats.reinitialize(g);
|
|
}
|
|
this.packedSplats && (await this.packedSplats.initialized, this.numSplats = this.packedSplats.numSplats, this.updateGenerator());
|
|
}
|
|
static async staticInitialize() {
|
|
await Us(), st.isStaticInitialized = !0;
|
|
}
|
|
// Creates a new Gsplat with the provided parameters (all values in "float" space,
|
|
// i.e. 0-1 for opacity and color) and adds it to the end of the packedSplats,
|
|
// increasing numSplats by 1. If necessary, reallocates the buffer with an exponential
|
|
// doubling strategy to fit the new data, so it's fairly efficient to just
|
|
// pushSplat(...) each Gsplat you want to create in a loop.
|
|
pushSplat(A, e, s, n, i) {
|
|
this.packedSplats.pushSplat(A, e, s, n, i);
|
|
}
|
|
// This method iterates over all Gsplats in this instance's packedSplats,
|
|
// invoking the provided callback with index: number in 0..=(this.numSplats-1) and
|
|
// center: THREE.Vector3, scales: THREE.Vector3, quaternion: THREE.Quaternion,
|
|
// opacity: number (0..1), and color: THREE.Color (rgb values in 0..1).
|
|
// Note that the objects passed in as center etc. are the same for every callback
|
|
// invocation: these objects are reused for efficiency. Changing these values has
|
|
// no effect as they are decoded/unpacked copies of the underlying data. To update
|
|
// the packedSplats, call .packedSplats.setSplat(index, center, scales,
|
|
// quaternion, opacity, color).
|
|
forEachSplat(A) {
|
|
this.packedSplats.forEachSplat(A);
|
|
}
|
|
// Call this when you are finished with the SplatMesh and want to free
|
|
// any buffers it holds (via packedSplats).
|
|
dispose() {
|
|
this.packedSplats.dispose();
|
|
}
|
|
// Returns axis-aligned bounding box of the SplatMesh. If centers_only is true,
|
|
// only the centers of the splats are used to compute the bounding box.
|
|
// IMPORTANT: This should only be called after the SplatMesh is initialized.
|
|
getBoundingBox(A = !0) {
|
|
if (!this.initialized)
|
|
throw new Error(
|
|
"Cannot get bounding box before SplatMesh is initialized"
|
|
);
|
|
const e = new u.Vector3(
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY,
|
|
Number.POSITIVE_INFINITY
|
|
), s = new u.Vector3(
|
|
Number.NEGATIVE_INFINITY,
|
|
Number.NEGATIVE_INFINITY,
|
|
Number.NEGATIVE_INFINITY
|
|
), n = new u.Vector3(), i = [-1, 1];
|
|
return this.packedSplats.forEachSplat(
|
|
(a, o, g, l, c, I) => {
|
|
if (A)
|
|
e.min(o), s.max(o);
|
|
else
|
|
for (const h of i)
|
|
for (const E of i)
|
|
for (const C of i)
|
|
n.set(h * g.x, E * g.y, C * g.z), n.applyQuaternion(l), n.add(o), e.min(n), s.max(n);
|
|
}
|
|
), new u.Box3(e, s);
|
|
}
|
|
constructGenerator(A) {
|
|
const { transform: e, viewToObject: s, recolor: n } = A, i = vA(
|
|
{ index: "int" },
|
|
{ gsplat: AA },
|
|
({ index: r }) => {
|
|
if (!r)
|
|
throw new Error("index is undefined");
|
|
let a = bt(this.packedSplats.dyno, r);
|
|
if (this.maxSh >= 1) {
|
|
const { sh1Texture: g, sh2Texture: l, sh3Texture: c } = this.ensureShTextures();
|
|
if (g) {
|
|
let I = function(p, d) {
|
|
const { x: y, y: D } = Et(d).outputs, x = iA(BA(y, D), J("float", 0.5)), w = iA(Qt(D, y), J("float", 0.5));
|
|
return BA(x, iA(p, w));
|
|
};
|
|
const h = s.translate, { center: E } = ut(a).outputs, C = Gr(Qt(E, h)), B = Mu(a, g, C);
|
|
let Q = I(B, this.packedSplats.dynoSh1MinMax);
|
|
if (this.maxSh >= 2 && l) {
|
|
const p = vu(a, l, C);
|
|
Q = BA(
|
|
Q,
|
|
I(p, this.packedSplats.dynoSh2MinMax)
|
|
);
|
|
}
|
|
if (this.maxSh >= 3 && c) {
|
|
const p = bu(a, c, C);
|
|
Q = BA(
|
|
Q,
|
|
I(p, this.packedSplats.dynoSh3MinMax)
|
|
);
|
|
}
|
|
let { rgba: f } = ut(a).outputs;
|
|
f = BA(f, Rr(Q, J("float", 0))), a = rt({ gsplat: a, rgba: f });
|
|
}
|
|
}
|
|
if (this.splatRgba) {
|
|
const g = Bu(this.splatRgba.dyno, r);
|
|
a = rt({ gsplat: a, rgba: g });
|
|
}
|
|
this.skinning && (a = this.skinning.modify(a)), this.objectModifier && (a = this.objectModifier.apply({ gsplat: a }).gsplat), a = e.applyGsplat(a);
|
|
const o = iA(n, ut(a).outputs.rgba);
|
|
return a = rt({ gsplat: a, rgba: o }), this.rgbaDisplaceEdits && (a = this.rgbaDisplaceEdits.modify(a)), this.worldModifier && (a = this.worldModifier.apply({ gsplat: a }).gsplat), { gsplat: a };
|
|
}
|
|
);
|
|
this.generator = i;
|
|
}
|
|
// Call this whenever something changes in the Gsplat processing pipeline,
|
|
// for example changing maxSh or updating objectModifier or worldModifier.
|
|
// Compiled generators are cached for efficiency and re-use when the same
|
|
// pipeline structure emerges after successive changes.
|
|
updateGenerator() {
|
|
this.constructGenerator(this.context);
|
|
}
|
|
// This is called automatically by SparkRenderer and you should not have to
|
|
// call it. It updates parameters for the generated pipeline and calls
|
|
// updateGenerator() if the pipeline needs to change.
|
|
update({
|
|
time: A,
|
|
viewToWorld: e,
|
|
deltaTime: s,
|
|
globalEdits: n
|
|
}) {
|
|
var B;
|
|
this.numSplats = this.packedSplats.numSplats, this.context.time.value = A, this.context.deltaTime.value = s, st.dynoTime.value = A;
|
|
const { transform: i, viewToObject: r, recolor: a } = this.context;
|
|
let o = i.update(this);
|
|
this.context.viewToWorld.updateFromMatrix(e) && this.enableViewToWorld && (o = !0);
|
|
const g = e.clone().invert();
|
|
this.context.worldToView.updateFromMatrix(g) && this.enableWorldToView && (o = !0);
|
|
const I = new u.Matrix4().compose(
|
|
i.translate.value,
|
|
i.rotate.value,
|
|
new u.Vector3().setScalar(i.scale.value)
|
|
).invert().multiply(e);
|
|
r.updateFromMatrix(I) && (this.enableViewToObject || this.packedSplats.extra.sh1) && (o = !0);
|
|
const h = new u.Vector4(
|
|
this.recolor.r,
|
|
this.recolor.g,
|
|
this.recolor.b,
|
|
this.opacity
|
|
);
|
|
h.equals(a.value) || (a.value.copy(h), o = !0);
|
|
const E = this.editable ? (this.edits ?? []).concat(n) : [];
|
|
this.editable && !this.edits && this.traverseVisible((Q) => {
|
|
Q instanceof Ie && E.push(Q);
|
|
}), E.sort((Q, f) => Q.ordering - f.ordering);
|
|
const C = E.map((Q) => {
|
|
if (Q.sdfs != null)
|
|
return { edit: Q, sdfs: Q.sdfs };
|
|
const f = [];
|
|
return Q.traverseVisible((p) => {
|
|
p instanceof du && f.push(p);
|
|
}), { edit: Q, sdfs: f };
|
|
});
|
|
if (C.length > 0 && !this.rgbaDisplaceEdits) {
|
|
const Q = C.length, f = C.reduce(
|
|
(p, d) => p + d.sdfs.length,
|
|
0
|
|
);
|
|
this.rgbaDisplaceEdits = new yu({
|
|
maxEdits: Q,
|
|
maxSdfs: f
|
|
}), this.updateGenerator();
|
|
}
|
|
if (this.rgbaDisplaceEdits) {
|
|
const Q = this.rgbaDisplaceEdits.update(C);
|
|
o || (o = Q.updated), Q.dynoUpdated && this.updateGenerator();
|
|
}
|
|
o && this.updateVersion(), (B = this.onFrame) == null || B.call(this, { mesh: this, time: A, deltaTime: s });
|
|
}
|
|
// This method conforms to the standard THREE.Raycaster API, performing object-ray
|
|
// intersections using this method to populate the provided intersects[] array
|
|
// with each intersection point.
|
|
raycast(A, e) {
|
|
var h, E;
|
|
if (!this.packedSplats.packedArray || !this.packedSplats.numSplats)
|
|
return;
|
|
const { near: s, far: n, ray: i } = A, r = this.matrixWorld.clone().invert(), a = new u.Matrix3().setFromMatrix4(r), o = i.origin.clone().applyMatrix4(r), g = i.direction.clone().applyMatrix3(a), l = new u.Vector3();
|
|
r.decompose(new u.Vector3(), new u.Quaternion(), l), (l.x * l.y * l.z) ** (1 / 3);
|
|
const I = Po(
|
|
o.x,
|
|
o.y,
|
|
o.z,
|
|
g.x,
|
|
g.y,
|
|
g.z,
|
|
s,
|
|
n,
|
|
this.packedSplats.numSplats,
|
|
this.packedSplats.packedArray,
|
|
!0,
|
|
((h = this.packedSplats.splatEncoding) == null ? void 0 : h.lnScaleMin) ?? UA,
|
|
((E = this.packedSplats.splatEncoding) == null ? void 0 : E.lnScaleMax) ?? GA
|
|
);
|
|
for (const C of I) {
|
|
const B = i.direction.clone().multiplyScalar(C).add(i.origin);
|
|
e.push({
|
|
distance: C,
|
|
point: B,
|
|
object: this
|
|
});
|
|
}
|
|
}
|
|
ensureShTextures() {
|
|
if (!this.packedSplats.extra.sh1)
|
|
return {};
|
|
let A = this.packedSplats.extra.sh1Texture;
|
|
if (!A) {
|
|
let n = this.packedSplats.extra.sh1;
|
|
const { width: i, height: r, depth: a, maxSplats: o } = mA(
|
|
n.length / 2
|
|
);
|
|
if (n.length < o * 2) {
|
|
const l = new Uint32Array(o * 2);
|
|
l.set(n), this.packedSplats.extra.sh1 = l, n = l;
|
|
}
|
|
const g = new u.DataArrayTexture(n, i, r, a);
|
|
g.format = u.RGIntegerFormat, g.type = u.UnsignedIntType, g.internalFormat = "RG32UI", g.needsUpdate = !0, A = new Ht({
|
|
value: g,
|
|
key: "sh1"
|
|
}), this.packedSplats.extra.sh1Texture = A;
|
|
}
|
|
if (!this.packedSplats.extra.sh2)
|
|
return { sh1Texture: A };
|
|
let e = this.packedSplats.extra.sh2Texture;
|
|
if (!e) {
|
|
let n = this.packedSplats.extra.sh2;
|
|
const { width: i, height: r, depth: a, maxSplats: o } = mA(
|
|
n.length / 4
|
|
);
|
|
if (n.length < o * 4) {
|
|
const l = new Uint32Array(o * 4);
|
|
l.set(n), this.packedSplats.extra.sh2 = l, n = l;
|
|
}
|
|
const g = new u.DataArrayTexture(n, i, r, a);
|
|
g.format = u.RGBAIntegerFormat, g.type = u.UnsignedIntType, g.internalFormat = "RGBA32UI", g.needsUpdate = !0, e = new Ht({
|
|
value: g,
|
|
key: "sh2"
|
|
}), this.packedSplats.extra.sh2Texture = e;
|
|
}
|
|
if (!this.packedSplats.extra.sh3)
|
|
return { sh1Texture: A, sh2Texture: e };
|
|
let s = this.packedSplats.extra.sh3Texture;
|
|
if (!s) {
|
|
let n = this.packedSplats.extra.sh3;
|
|
const { width: i, height: r, depth: a, maxSplats: o } = mA(
|
|
n.length / 4
|
|
);
|
|
if (n.length < o * 4) {
|
|
const l = new Uint32Array(o * 4);
|
|
l.set(n), this.packedSplats.extra.sh3 = l, n = l;
|
|
}
|
|
const g = new u.DataArrayTexture(n, i, r, a);
|
|
g.format = u.RGBAIntegerFormat, g.type = u.UnsignedIntType, g.internalFormat = "RGBA32UI", g.needsUpdate = !0, s = new Ht({
|
|
value: g,
|
|
key: "sh3"
|
|
}), this.packedSplats.extra.sh3Texture = s;
|
|
}
|
|
return { sh1Texture: A, sh2Texture: e, sh3Texture: s };
|
|
}
|
|
};
|
|
st.staticInitialized = st.staticInitialize(), st.isStaticInitialized = !1, st.dynoTime = new ht({ value: 0 });
|
|
let pt = st;
|
|
const xu = hA(`
|
|
vec3 evaluateSH1(Gsplat gsplat, usampler2DArray sh1, vec3 viewDir) {
|
|
// Extract sint7 values packed into 2 x uint32
|
|
uvec2 packed = texelFetch(sh1, splatTexCoord(gsplat.index), 0).rg;
|
|
vec3 sh1_0 = vec3(ivec3(
|
|
int(packed.x << 25u) >> 25,
|
|
int(packed.x << 18u) >> 25,
|
|
int(packed.x << 11u) >> 25
|
|
)) / 63.0;
|
|
vec3 sh1_1 = vec3(ivec3(
|
|
int(packed.x << 4u) >> 25,
|
|
int((packed.x >> 3u) | (packed.y << 29u)) >> 25,
|
|
int(packed.y << 22u) >> 25
|
|
)) / 63.0;
|
|
vec3 sh1_2 = vec3(ivec3(
|
|
int(packed.y << 15u) >> 25,
|
|
int(packed.y << 8u) >> 25,
|
|
int(packed.y << 1u) >> 25
|
|
)) / 63.0;
|
|
|
|
return sh1_0 * (-0.4886025 * viewDir.y)
|
|
+ sh1_1 * (0.4886025 * viewDir.z)
|
|
+ sh1_2 * (-0.4886025 * viewDir.x);
|
|
}
|
|
`), Su = hA(`
|
|
vec3 evaluateSH2(Gsplat gsplat, usampler2DArray sh2, vec3 viewDir) {
|
|
// Extract sint8 values packed into 4 x uint32
|
|
uvec4 packed = texelFetch(sh2, splatTexCoord(gsplat.index), 0);
|
|
vec3 sh2_0 = vec3(ivec3(
|
|
int(packed.x << 24u) >> 24,
|
|
int(packed.x << 16u) >> 24,
|
|
int(packed.x << 8u) >> 24
|
|
)) / 127.0;
|
|
vec3 sh2_1 = vec3(ivec3(
|
|
int(packed.x) >> 24,
|
|
int(packed.y << 24u) >> 24,
|
|
int(packed.y << 16u) >> 24
|
|
)) / 127.0;
|
|
vec3 sh2_2 = vec3(ivec3(
|
|
int(packed.y << 8u) >> 24,
|
|
int(packed.y) >> 24,
|
|
int(packed.z << 24u) >> 24
|
|
)) / 127.0;
|
|
vec3 sh2_3 = vec3(ivec3(
|
|
int(packed.z << 16u) >> 24,
|
|
int(packed.z << 8u) >> 24,
|
|
int(packed.z) >> 24
|
|
)) / 127.0;
|
|
vec3 sh2_4 = vec3(ivec3(
|
|
int(packed.w << 24u) >> 24,
|
|
int(packed.w << 16u) >> 24,
|
|
int(packed.w << 8u) >> 24
|
|
)) / 127.0;
|
|
|
|
return sh2_0 * (1.0925484 * viewDir.x * viewDir.y)
|
|
+ sh2_1 * (-1.0925484 * viewDir.y * viewDir.z)
|
|
+ sh2_2 * (0.3153915 * (2.0 * viewDir.z * viewDir.z - viewDir.x * viewDir.x - viewDir.y * viewDir.y))
|
|
+ sh2_3 * (-1.0925484 * viewDir.x * viewDir.z)
|
|
+ sh2_4 * (0.5462742 * (viewDir.x * viewDir.x - viewDir.y * viewDir.y));
|
|
}
|
|
`), Du = hA(`
|
|
vec3 evaluateSH3(Gsplat gsplat, usampler2DArray sh3, vec3 viewDir) {
|
|
// Extract sint6 values packed into 4 x uint32
|
|
uvec4 packed = texelFetch(sh3, splatTexCoord(gsplat.index), 0);
|
|
vec3 sh3_0 = vec3(ivec3(
|
|
int(packed.x << 26u) >> 26,
|
|
int(packed.x << 20u) >> 26,
|
|
int(packed.x << 14u) >> 26
|
|
)) / 31.0;
|
|
vec3 sh3_1 = vec3(ivec3(
|
|
int(packed.x << 8u) >> 26,
|
|
int(packed.x << 2u) >> 26,
|
|
int((packed.x >> 4u) | (packed.y << 28u)) >> 26
|
|
)) / 31.0;
|
|
vec3 sh3_2 = vec3(ivec3(
|
|
int(packed.y << 22u) >> 26,
|
|
int(packed.y << 16u) >> 26,
|
|
int(packed.y << 10u) >> 26
|
|
)) / 31.0;
|
|
vec3 sh3_3 = vec3(ivec3(
|
|
int(packed.y << 4u) >> 26,
|
|
int((packed.y >> 2u) | (packed.z << 30u)) >> 26,
|
|
int(packed.z << 24u) >> 26
|
|
)) / 31.0;
|
|
vec3 sh3_4 = vec3(ivec3(
|
|
int(packed.z << 18u) >> 26,
|
|
int(packed.z << 12u) >> 26,
|
|
int(packed.z << 6u) >> 26
|
|
)) / 31.0;
|
|
vec3 sh3_5 = vec3(ivec3(
|
|
int(packed.z) >> 26,
|
|
int(packed.w << 26u) >> 26,
|
|
int(packed.w << 20u) >> 26
|
|
)) / 31.0;
|
|
vec3 sh3_6 = vec3(ivec3(
|
|
int(packed.w << 14u) >> 26,
|
|
int(packed.w << 8u) >> 26,
|
|
int(packed.w << 2u) >> 26
|
|
)) / 31.0;
|
|
|
|
float xx = viewDir.x * viewDir.x;
|
|
float yy = viewDir.y * viewDir.y;
|
|
float zz = viewDir.z * viewDir.z;
|
|
float xy = viewDir.x * viewDir.y;
|
|
float yz = viewDir.y * viewDir.z;
|
|
float zx = viewDir.z * viewDir.x;
|
|
|
|
return sh3_0 * (-0.5900436 * viewDir.y * (3.0 * xx - yy))
|
|
+ sh3_1 * (2.8906114 * xy * viewDir.z) +
|
|
+ sh3_2 * (-0.4570458 * viewDir.y * (4.0 * zz - xx - yy))
|
|
+ sh3_3 * (0.3731763 * viewDir.z * (2.0 * zz - 3.0 * xx - 3.0 * yy))
|
|
+ sh3_4 * (-0.4570458 * viewDir.x * (4.0 * zz - xx - yy))
|
|
+ sh3_5 * (1.4453057 * viewDir.z * (xx - yy))
|
|
+ sh3_6 * (-0.5900436 * viewDir.x * (xx - 3.0 * yy));
|
|
}
|
|
`);
|
|
function Mu(t, A, e) {
|
|
return Ot({
|
|
inTypes: { gsplat: AA, sh1: "usampler2DArray", viewDir: "vec3" },
|
|
outTypes: { rgb: "vec3" },
|
|
inputs: { gsplat: t, sh1: A, viewDir: e },
|
|
globals: () => [bA, xu],
|
|
statements: ({ inputs: s, outputs: n }) => RA(`
|
|
if (isGsplatActive(${s.gsplat}.flags)) {
|
|
${n.rgb} = evaluateSH1(${s.gsplat}, ${s.sh1}, ${s.viewDir});
|
|
} else {
|
|
${n.rgb} = vec3(0.0);
|
|
}
|
|
`)
|
|
}).outputs.rgb;
|
|
}
|
|
function vu(t, A, e) {
|
|
return Ot({
|
|
inTypes: { gsplat: AA, sh2: "usampler2DArray", viewDir: "vec3" },
|
|
outTypes: { rgb: "vec3" },
|
|
inputs: { gsplat: t, sh2: A, viewDir: e },
|
|
globals: () => [bA, Su],
|
|
statements: ({ inputs: s, outputs: n }) => RA(`
|
|
if (isGsplatActive(${s.gsplat}.flags)) {
|
|
${n.rgb} = evaluateSH2(${s.gsplat}, ${s.sh2}, ${s.viewDir});
|
|
} else {
|
|
${n.rgb} = vec3(0.0);
|
|
}
|
|
`)
|
|
}).outputs.rgb;
|
|
}
|
|
function bu(t, A, e) {
|
|
return Ot({
|
|
inTypes: { gsplat: AA, sh3: "usampler2DArray", viewDir: "vec3" },
|
|
outTypes: { rgb: "vec3" },
|
|
inputs: { gsplat: t, sh3: A, viewDir: e },
|
|
globals: () => [bA, Du],
|
|
statements: ({ inputs: s, outputs: n }) => RA(`
|
|
if (isGsplatActive(${s.gsplat}.flags)) {
|
|
${n.rgb} = evaluateSH3(${s.gsplat}, ${s.sh3}, ${s.viewDir});
|
|
} else {
|
|
${n.rgb} = vec3(0.0);
|
|
}
|
|
`)
|
|
}).outputs.rgb;
|
|
}
|
|
const Fu = new u.BufferGeometry(), Nu = new u.ShaderMaterial();
|
|
function ku() {
|
|
const t = new u.Mesh(Fu, Nu);
|
|
return t.frustumCulled = !1, t.onBeforeRender = function(A, e) {
|
|
if (!e.isScene) {
|
|
this.removeFromParent();
|
|
return;
|
|
}
|
|
let s = !1;
|
|
e.traverse((n) => {
|
|
n instanceof Be && (s = !0);
|
|
}), s || e.add(new Be({ renderer: A })), this.removeFromParent();
|
|
}, t;
|
|
}
|
|
const Qs = [
|
|
"char",
|
|
"uchar",
|
|
"short",
|
|
"ushort",
|
|
"int",
|
|
"uint",
|
|
"float",
|
|
"double"
|
|
], Dt = class Dt {
|
|
// Create a PlyReader from a Uint8Array/ArrayBuffer, no parsing done yet
|
|
constructor({ fileBytes: A }) {
|
|
this.header = "", this.littleEndian = !0, this.elements = {}, this.comments = [], this.data = null, this.numSplats = 0, this.fileBytes = A instanceof ArrayBuffer ? new Uint8Array(A) : A;
|
|
}
|
|
// Identify and parse the PLY text header (assumed to be <64KB in size).
|
|
// this.elements will contain all the elements in the file, typically
|
|
// "vertex" contains the Gsplat data.
|
|
async parseHeader() {
|
|
const e = new ReadableStream({
|
|
start: (r) => {
|
|
r.enqueue(this.fileBytes.slice(0, 65536)), r.close();
|
|
}
|
|
}).pipeThrough(new TextDecoderStream()).getReader();
|
|
this.header = "";
|
|
const s = `end_header
|
|
`;
|
|
for (; ; ) {
|
|
const { value: r, done: a } = await e.read();
|
|
if (a)
|
|
throw new Error("Failed to read header");
|
|
this.header += r;
|
|
const o = this.header.indexOf(s);
|
|
if (o >= 0) {
|
|
this.header = this.header.slice(0, o + s.length);
|
|
break;
|
|
}
|
|
}
|
|
const n = new TextEncoder().encode(this.header).length;
|
|
this.data = new DataView(this.fileBytes.buffer, n), this.elements = {};
|
|
let i = null;
|
|
this.comments = [], this.header.trim().split(`
|
|
`).forEach((r, a) => {
|
|
const o = r.trim();
|
|
if (a === 0) {
|
|
if (o !== "ply")
|
|
throw new Error("Invalid PLY header");
|
|
return;
|
|
}
|
|
if (o.length === 0)
|
|
return;
|
|
const g = o.split(" ");
|
|
switch (g[0]) {
|
|
case "format":
|
|
if (g[1] === "binary_little_endian")
|
|
this.littleEndian = !0;
|
|
else if (g[1] === "binary_big_endian")
|
|
this.littleEndian = !1;
|
|
else
|
|
throw new Error(`Unsupported PLY format: ${g[1]}`);
|
|
if (g[2] !== "1.0")
|
|
throw new Error(`Unsupported PLY version: ${g[2]}`);
|
|
break;
|
|
case "end_header":
|
|
break;
|
|
case "comment":
|
|
this.comments.push(o.slice(8));
|
|
break;
|
|
case "element": {
|
|
const l = g[1];
|
|
i = {
|
|
name: l,
|
|
count: Number.parseInt(g[2]),
|
|
properties: {}
|
|
}, this.elements[l] = i;
|
|
break;
|
|
}
|
|
case "property":
|
|
if (i == null)
|
|
throw new Error("Property must be inside an element");
|
|
g[1] === "list" ? i.properties[g[4]] = {
|
|
isList: !0,
|
|
type: g[3],
|
|
countType: g[2]
|
|
} : i.properties[g[2]] = {
|
|
isList: !1,
|
|
type: g[1]
|
|
};
|
|
break;
|
|
}
|
|
}), this.elements.vertex && (this.numSplats = this.elements.vertex.count);
|
|
}
|
|
parseData(A) {
|
|
let e = 0;
|
|
const s = this.data;
|
|
if (s == null)
|
|
throw new Error("No data to parse");
|
|
for (const n in this.elements) {
|
|
const i = this.elements[n], { count: r, properties: a } = i, o = Gu(a), g = Ru(a, this.littleEndian), l = A(i) ?? (() => {
|
|
});
|
|
for (let c = 0; c < r; c++)
|
|
e = g(s, e, o), l(c, o);
|
|
}
|
|
}
|
|
// Parse all the Gsplat data in the PLY file in go, invoking the given
|
|
// callbacks for each Gsplat.
|
|
parseSplats(A, e) {
|
|
if (this.elements.vertex == null)
|
|
throw new Error("No vertex element found");
|
|
let s = !1;
|
|
const n = [];
|
|
let i = 0, r = [], a = [], o = [], g, l, c;
|
|
function I() {
|
|
const Q = Uu[i];
|
|
r = new Array(3).fill(null).flatMap((f, p) => [0, 1, 2].map((d, y) => p + y * Q / 3)), a = new Array(5).fill(null).flatMap(
|
|
(f, p) => [0, 1, 2].map((d, y) => 3 + p + y * Q / 3)
|
|
), o = new Array(7).fill(null).flatMap(
|
|
(f, p) => [0, 1, 2].map((d, y) => 8 + p + y * Q / 3)
|
|
), g = i >= 1 ? new Float32Array(3 * 3) : void 0, l = i >= 2 ? new Float32Array(5 * 3) : void 0, c = i >= 3 ? new Float32Array(7 * 3) : void 0;
|
|
}
|
|
function h(Q, f) {
|
|
if (!g)
|
|
throw new Error("Missing sh1");
|
|
const p = f.f_rest;
|
|
for (let d = 0; d < r.length; d++)
|
|
g[d] = p[r[d]] * 8 / 255 - 4;
|
|
if (l)
|
|
for (let d = 0; d < a.length; d++)
|
|
l[d] = p[a[d]] * 8 / 255 - 4;
|
|
if (c)
|
|
for (let d = 0; d < o.length; d++)
|
|
c[d] = p[o[d]] * 8 / 255 - 4;
|
|
e == null || e(Q, g, l, c);
|
|
}
|
|
function E(Q) {
|
|
const {
|
|
min_x: f,
|
|
min_y: p,
|
|
min_z: d,
|
|
max_x: y,
|
|
max_y: D,
|
|
max_z: x,
|
|
min_scale_x: w,
|
|
min_scale_y: m,
|
|
min_scale_z: k,
|
|
max_scale_x: M,
|
|
max_scale_y: S,
|
|
max_scale_z: U
|
|
} = Q.properties;
|
|
if (!f || !p || !d || !y || !D || !x || !w || !m || !k || !M || !S || !U)
|
|
throw new Error("Missing PLY chunk properties");
|
|
return s = !0, (F, b) => {
|
|
const {
|
|
min_x: T,
|
|
min_y: R,
|
|
min_z: X,
|
|
max_x: _,
|
|
max_y: eA,
|
|
max_z: q,
|
|
min_scale_x: O,
|
|
min_scale_y: L,
|
|
min_scale_z: j,
|
|
max_scale_x: P,
|
|
max_scale_y: W,
|
|
max_scale_z: G,
|
|
min_r: pA,
|
|
min_g: gA,
|
|
min_b: fA,
|
|
max_r: dA,
|
|
max_g: xA,
|
|
max_b: CA
|
|
} = b;
|
|
n.push({
|
|
min_x: T,
|
|
min_y: R,
|
|
min_z: X,
|
|
max_x: _,
|
|
max_y: eA,
|
|
max_z: q,
|
|
min_scale_x: O,
|
|
min_scale_y: L,
|
|
min_scale_z: j,
|
|
max_scale_x: P,
|
|
max_scale_y: W,
|
|
max_scale_z: G,
|
|
min_r: pA,
|
|
min_g: gA,
|
|
min_b: fA,
|
|
max_r: dA,
|
|
max_g: xA,
|
|
max_b: CA
|
|
});
|
|
};
|
|
}
|
|
function C(Q) {
|
|
if (e && Q.name === "sh")
|
|
return i = $e(Q.properties), I(), h;
|
|
if (Q.name !== "vertex")
|
|
return null;
|
|
const { packed_position: f, packed_rotation: p, packed_scale: d, packed_color: y } = Q.properties;
|
|
if (!f || !p || !d || !y)
|
|
throw new Error(
|
|
"Missing PLY properties: packed_position, packed_rotation, packed_scale, packed_color"
|
|
);
|
|
const D = Math.sqrt(2);
|
|
return (x, w) => {
|
|
const m = n[x >>> 8];
|
|
if (m == null)
|
|
throw new Error("Missing PLY chunk");
|
|
const {
|
|
min_x: k,
|
|
min_y: M,
|
|
min_z: S,
|
|
max_x: U,
|
|
max_y: F,
|
|
max_z: b,
|
|
min_scale_x: T,
|
|
min_scale_y: R,
|
|
min_scale_z: X,
|
|
max_scale_x: _,
|
|
max_scale_y: eA,
|
|
max_scale_z: q,
|
|
min_r: O,
|
|
min_g: L,
|
|
min_b: j,
|
|
max_r: P,
|
|
max_g: W,
|
|
max_b: G
|
|
} = m, { packed_position: pA, packed_rotation: gA, packed_scale: fA, packed_color: dA } = w, xA = (pA >>> 21 & 2047) / 2047 * (U - k) + k, CA = (pA >>> 11 & 1023) / 1023 * (F - M) + M, YA = (pA & 2047) / 2047 * (b - S) + S, SA = ((gA >>> 20 & 1023) / 1023 - 0.5) * D, OA = ((gA >>> 10 & 1023) / 1023 - 0.5) * D, jA = ((gA & 1023) / 1023 - 0.5) * D, Y = Math.sqrt(Math.max(0, 1 - SA * SA - OA * OA - jA * jA)), DA = gA >>> 30, lA = DA === 0 ? SA : DA === 1 ? Y : OA, Gt = DA <= 1 ? OA : DA === 2 ? Y : jA, Ae = DA <= 2 ? jA : Y, MA = DA === 0 ? Y : SA, z = Math.exp(
|
|
(fA >>> 21 & 2047) / 2047 * (_ - T) + T
|
|
), ZA = Math.exp(
|
|
(fA >>> 11 & 1023) / 1023 * (eA - R) + R
|
|
), ye = Math.exp(
|
|
(fA & 2047) / 2047 * (q - X) + X
|
|
), we = (dA >>> 24 & 255) / 255 * ((P ?? 1) - (O ?? 0)) + (O ?? 0), me = (dA >>> 16 & 255) / 255 * ((W ?? 1) - (L ?? 0)) + (L ?? 0), xe = (dA >>> 8 & 255) / 255 * ((G ?? 1) - (j ?? 0)) + (j ?? 0), Se = (dA & 255) / 255;
|
|
A(
|
|
x,
|
|
xA,
|
|
CA,
|
|
YA,
|
|
z,
|
|
ZA,
|
|
ye,
|
|
lA,
|
|
Gt,
|
|
Ae,
|
|
MA,
|
|
Se,
|
|
we,
|
|
me,
|
|
xe
|
|
);
|
|
};
|
|
}
|
|
const B = (Q) => {
|
|
if (Q.name === "chunk")
|
|
return E(Q);
|
|
if (s)
|
|
return C(Q);
|
|
if (Q.name !== "vertex")
|
|
return null;
|
|
const {
|
|
x: f,
|
|
y: p,
|
|
z: d,
|
|
scale_0: y,
|
|
scale_1: D,
|
|
scale_2: x,
|
|
rot_0: w,
|
|
rot_1: m,
|
|
rot_2: k,
|
|
rot_3: M,
|
|
opacity: S,
|
|
f_dc_0: U,
|
|
f_dc_1: F,
|
|
f_dc_2: b,
|
|
red: T,
|
|
green: R,
|
|
blue: X,
|
|
alpha: _
|
|
} = Q.properties;
|
|
if (!f || !p || !d)
|
|
throw new Error("Missing PLY properties: x, y, z");
|
|
const eA = y && D && x, q = w && m && k && M, O = _ != null ? se[_.type] : 1, L = T != null ? se[T.type] : 1, j = R != null ? se[R.type] : 1, P = X != null ? se[X.type] : 1;
|
|
return i = $e(Q.properties), I(), (W, G) => {
|
|
const pA = eA ? Math.exp(G.scale_0) : Dt.defaultPointScale, gA = eA ? Math.exp(G.scale_1) : Dt.defaultPointScale, fA = eA ? Math.exp(G.scale_2) : Dt.defaultPointScale, dA = q ? G.rot_1 : 0, xA = q ? G.rot_2 : 0, CA = q ? G.rot_3 : 0, YA = q ? G.rot_0 : 1, SA = S != null ? 1 / (1 + Math.exp(-G.opacity)) : _ != null ? G.alpha / O : 1, OA = U != null ? G.f_dc_0 * ee + 0.5 : T != null ? G.red / L : 1, jA = F != null ? G.f_dc_1 * ee + 0.5 : R != null ? G.green / j : 1, Y = b != null ? G.f_dc_2 * ee + 0.5 : X != null ? G.blue / P : 1;
|
|
if (A(
|
|
W,
|
|
G.x,
|
|
G.y,
|
|
G.z,
|
|
pA,
|
|
gA,
|
|
fA,
|
|
dA,
|
|
xA,
|
|
CA,
|
|
YA,
|
|
SA,
|
|
OA,
|
|
jA,
|
|
Y
|
|
), e && g) {
|
|
const DA = G.f_rest;
|
|
if (g)
|
|
for (let lA = 0; lA < r.length; lA++)
|
|
g[lA] = DA[r[lA]];
|
|
if (l)
|
|
for (let lA = 0; lA < a.length; lA++)
|
|
l[lA] = DA[a[lA]];
|
|
if (c)
|
|
for (let lA = 0; lA < o.length; lA++)
|
|
c[lA] = DA[o[lA]];
|
|
e(W, g, l, c);
|
|
}
|
|
};
|
|
};
|
|
this.parseData(B);
|
|
}
|
|
// Inject RGBA values into original PLY file, which can be used to modify
|
|
// the color/opacity of the Gsplats and write out the modified PLY file.
|
|
injectRgba(A) {
|
|
let e = 0;
|
|
const s = this.data;
|
|
if (s == null)
|
|
throw new Error("No parsed data");
|
|
if (A.length !== this.numSplats * 4)
|
|
throw new Error("Invalid RGBA array length");
|
|
for (const n in this.elements) {
|
|
const i = this.elements[n], { count: r, properties: a } = i, o = [];
|
|
let g = 0;
|
|
const l = n === "vertex";
|
|
if (l) {
|
|
for (const c of ["opacity", "f_dc_0", "f_dc_1", "f_dc_2"])
|
|
if (!a[c] || a[c].type !== "float")
|
|
throw new Error(`Can't injectRgba due to property: ${c}`);
|
|
}
|
|
for (const [c, I] of Object.entries(a))
|
|
if (I.isList)
|
|
o.push(() => {
|
|
const h = St[I.countType](
|
|
s,
|
|
e,
|
|
this.littleEndian
|
|
);
|
|
e += zA[I.countType], e += h * zA[I.type];
|
|
});
|
|
else {
|
|
if (l)
|
|
if (c === "f_dc_0" || c === "f_dc_1" || c === "f_dc_2") {
|
|
const h = Number.parseInt(
|
|
c.slice(5)
|
|
);
|
|
o.push(() => {
|
|
const E = (A[g + h] / 255 - 0.5) / ee;
|
|
ps[I.type](
|
|
s,
|
|
e,
|
|
this.littleEndian,
|
|
E
|
|
);
|
|
});
|
|
} else c === "opacity" && o.push(() => {
|
|
const h = Math.max(
|
|
-100,
|
|
Math.min(
|
|
100,
|
|
-Math.log(1 / (A[g + 3] / 255) - 1)
|
|
)
|
|
);
|
|
ps[I.type](
|
|
s,
|
|
e,
|
|
this.littleEndian,
|
|
h
|
|
);
|
|
});
|
|
o.push(() => {
|
|
e += zA[I.type];
|
|
});
|
|
}
|
|
for (let c = 0; c < r; c++) {
|
|
for (const I of o)
|
|
I();
|
|
l && (g += 4);
|
|
}
|
|
}
|
|
}
|
|
};
|
|
Dt.defaultPointScale = 1e-3;
|
|
let ue = Dt;
|
|
const ee = 0.28209479177387814, St = {
|
|
char: (t, A, e) => t.getInt8(A),
|
|
uchar: (t, A, e) => t.getUint8(A),
|
|
short: (t, A, e) => t.getInt16(A, e),
|
|
ushort: (t, A, e) => t.getUint16(A, e),
|
|
int: (t, A, e) => t.getInt32(A, e),
|
|
uint: (t, A, e) => t.getUint32(A, e),
|
|
float: (t, A, e) => t.getFloat32(A, e),
|
|
double: (t, A, e) => t.getFloat64(A, e)
|
|
}, ps = {
|
|
char: (t, A, e, s) => {
|
|
t.setInt8(A, s);
|
|
},
|
|
uchar: (t, A, e, s) => {
|
|
t.setUint8(A, s);
|
|
},
|
|
short: (t, A, e, s) => {
|
|
t.setInt16(A, s, e);
|
|
},
|
|
ushort: (t, A, e, s) => {
|
|
t.setUint16(A, s, e);
|
|
},
|
|
int: (t, A, e, s) => {
|
|
t.setInt32(A, s, e);
|
|
},
|
|
uint: (t, A, e, s) => {
|
|
t.setUint32(A, s, e);
|
|
},
|
|
float: (t, A, e, s) => {
|
|
t.setFloat32(A, s, e);
|
|
},
|
|
double: (t, A, e, s) => {
|
|
t.setFloat64(A, s, e);
|
|
}
|
|
}, zA = {
|
|
char: 1,
|
|
uchar: 1,
|
|
short: 2,
|
|
ushort: 2,
|
|
int: 4,
|
|
uint: 4,
|
|
float: 4,
|
|
double: 8
|
|
}, se = {
|
|
char: 127,
|
|
uchar: 255,
|
|
short: 32767,
|
|
ushort: 65535,
|
|
int: 2147483647,
|
|
uint: 4294967295,
|
|
float: 1,
|
|
double: 1
|
|
}, Tu = {
|
|
0: 0,
|
|
9: 1,
|
|
24: 2,
|
|
45: 3
|
|
}, Uu = {
|
|
0: 0,
|
|
1: 9,
|
|
2: 24,
|
|
3: 45
|
|
}, cs = /^f_rest_([0-9]{1,2})$/;
|
|
function Gu(t) {
|
|
const A = {};
|
|
for (const [e, s] of Object.entries(t))
|
|
cs.test(e) ? A.f_rest = new Array($e(t)) : A[e] = s.isList ? [] : 0;
|
|
return A;
|
|
}
|
|
function Ru(t, A) {
|
|
return _u(t) ? Lu(t, A) : zu(t, A);
|
|
}
|
|
const Yu = (() => {
|
|
try {
|
|
new Function("return 42;");
|
|
} catch {
|
|
return !1;
|
|
}
|
|
return !0;
|
|
})(), Ju = /^[a-zA-Z0-9_]+$/;
|
|
function _u(t) {
|
|
if (!Yu)
|
|
return !1;
|
|
for (const [A, e] of Object.entries(t))
|
|
if (!Ju.test(A) || e.isList && !Qs.includes(e.countType) || !Qs.includes(e.type))
|
|
return !1;
|
|
return !0;
|
|
}
|
|
function Lu(t, A) {
|
|
const e = ["let list;"];
|
|
for (const [n, i] of Object.entries(t)) {
|
|
const r = n.match(cs);
|
|
if (r) {
|
|
const a = +r[1];
|
|
e.push(
|
|
/*js*/
|
|
`
|
|
item.f_rest[${a}] = PARSE_FIELD['${i.type}'](data, offset, ${A});
|
|
offset += ${zA[i.type]};
|
|
`
|
|
);
|
|
} else i.isList ? e.push(
|
|
/*js*/
|
|
`
|
|
list = item['${n}'];
|
|
list.length = PARSE_FIELD['${i.countType}'](data, offset, ${A});
|
|
offset += ${zA[i.countType]};
|
|
for (let i = 0; i < list.length; i++) {
|
|
list[i] = PARSE_FIELD['${i.type}'](data, offset, ${A});
|
|
offset += ${zA[i.type]};
|
|
}
|
|
`
|
|
) : e.push(
|
|
/*js*/
|
|
`
|
|
item['${n}'] = PARSE_FIELD['${i.type}'](data, offset, ${A});
|
|
offset += ${zA[i.type]};
|
|
`
|
|
);
|
|
}
|
|
e.push("return offset;");
|
|
const s = new Function(
|
|
"data",
|
|
"offset",
|
|
"item",
|
|
"PARSE_FIELD",
|
|
e.join(`
|
|
`)
|
|
);
|
|
return (n, i, r) => s(n, i, r, St);
|
|
}
|
|
function zu(t, A) {
|
|
const e = [];
|
|
for (const [s, n] of Object.entries(t)) {
|
|
const i = s.match(cs);
|
|
if (i) {
|
|
const r = +i[1];
|
|
e.push(
|
|
(a, o, g) => (g.f_rest[r] = St[n.type](
|
|
a,
|
|
o,
|
|
A
|
|
), o + zA[n.type])
|
|
);
|
|
} else n.isList ? e.push(
|
|
(r, a, o) => {
|
|
const g = o[s];
|
|
g.length = St[n.countType](
|
|
r,
|
|
a,
|
|
A
|
|
);
|
|
let l = a + zA[n.countType];
|
|
for (let c = 0; c < g.length; c++)
|
|
g[c] = St[n.type](
|
|
r,
|
|
l,
|
|
A
|
|
), l += zA[n.type];
|
|
return l;
|
|
}
|
|
) : e.push(
|
|
(r, a, o) => (o[s] = St[n.type](
|
|
r,
|
|
a,
|
|
A
|
|
), a + zA[n.type])
|
|
);
|
|
}
|
|
return (s, n, i) => {
|
|
let r = n;
|
|
for (let a = 0; a < e.length; a++)
|
|
r = e[a](s, r, i);
|
|
return r;
|
|
};
|
|
}
|
|
function $e(t) {
|
|
let A = 0;
|
|
for (; t[`f_rest_${A}`]; )
|
|
A += 1;
|
|
const e = Tu[A];
|
|
if (e == null)
|
|
throw new Error(`Unsupported number of SH coefficients: ${A}`);
|
|
return e;
|
|
}
|
|
const Pa = '(function(){"use strict";let DA;const re=typeof TextDecoder<"u"?new TextDecoder("utf-8",{ignoreBOM:!0,fatal:!0}):{decode:()=>{throw Error("TextDecoder not available")}};typeof TextDecoder<"u"&&re.decode();let jA=null;function is(){return(jA===null||jA.byteLength===0)&&(jA=new Uint8Array(DA.memory.buffer)),jA}function ns(s,A){return s=s>>>0,re.decode(is().subarray(s,s+A))}function rs(s,A,t){return DA.sort_splats(s,A,t)>>>0}function gs(s,A,t){return DA.sort32_splats(s,A,t)>>>0}async function Is(s,A){if(typeof Response=="function"&&s instanceof Response){if(typeof WebAssembly.instantiateStreaming=="function")try{return await WebAssembly.instantiateStreaming(s,A)}catch(e){if(s.headers.get("Content-Type")!="application/wasm")console.warn("`WebAssembly.instantiateStreaming` failed because your server does not serve Wasm with `application/wasm` MIME type. Falling back to `WebAssembly.instantiate` which is slower. Original error:\\n",e);else throw e}const t=await s.arrayBuffer();return await WebAssembly.instantiate(t,A)}else{const t=await WebAssembly.instantiate(s,A);return t instanceof WebAssembly.Instance?{instance:t,module:s}:t}}function as(){const s={};return s.wbg={},s.wbg.__wbg_buffer_609cc3eee51ed158=function(A){return A.buffer},s.wbg.__wbg_length_3b4f022188ae8db6=function(A){return A.length},s.wbg.__wbg_length_6ca527665d89694d=function(A){return A.length},s.wbg.__wbg_length_8cfd2c6409af88ad=function(A){return A.length},s.wbg.__wbg_new_9fee97a409b32b68=function(A){return new Uint16Array(A)},s.wbg.__wbg_new_e3b321dcfef89fc7=function(A){return new Uint32Array(A)},s.wbg.__wbg_newwithbyteoffsetandlength_e6b7e69acd4c7354=function(A,t,e){return new Float32Array(A,t>>>0,e>>>0)},s.wbg.__wbg_newwithbyteoffsetandlength_f1dead44d1fc7212=function(A,t,e){return new Uint32Array(A,t>>>0,e>>>0)},s.wbg.__wbg_newwithlength_5a5efe313cfd59f1=function(A){return new Float32Array(A>>>0)},s.wbg.__wbg_set_10bad9bee0e9c58b=function(A,t,e){A.set(t,e>>>0)},s.wbg.__wbg_set_d23661d19148b229=function(A,t,e){A.set(t,e>>>0)},s.wbg.__wbg_set_f4f1f0daa30696fc=function(A,t,e){A.set(t,e>>>0)},s.wbg.__wbg_subarray_3aaeec89bb2544f0=function(A,t,e){return A.subarray(t>>>0,e>>>0)},s.wbg.__wbg_subarray_769e1e0f81bb259b=function(A,t,e){return A.subarray(t>>>0,e>>>0)},s.wbg.__wbindgen_init_externref_table=function(){const A=DA.__wbindgen_export_0,t=A.grow(4);A.set(0,void 0),A.set(t+0,void 0),A.set(t+1,null),A.set(t+2,!0),A.set(t+3,!1)},s.wbg.__wbindgen_memory=function(){return DA.memory},s.wbg.__wbindgen_throw=function(A,t){throw new Error(ns(A,t))},s}function os(s,A){return DA=s.exports,ge.__wbindgen_wasm_module=A,jA=null,DA.__wbindgen_start(),DA}async function ge(s){if(DA!==void 0)return DA;typeof s<"u"&&(Object.getPrototypeOf(s)===Object.prototype?{module_or_path:s}=s:console.warn("using deprecated parameters for the initialization function; pass a single object instead")),typeof s>"u"&&(s=new URL("data:application/wasm;base64,AGFzbQEAAAABzAEeYAJ/fwF/YAJ/fwBgA39/fwF/YAN/f38AYAF/AX9gAX8AYANvf38Bb2AFf39/f38Bf2AFf39/f38AYAFvAW9gA29vfwBgAW8Bf2AAAGAAAX9gBH9/f38AYAR/f39/AX9gA39vbwF/YAF/AW9gAAFvYAF9AX1gBn9/f39/fwBgDX19fX19fX19f29/fX0Bb2AGf39/f39/AX9gBX9/fX9/AGAEf31/fwBgBX9/fH9/AGAEf3x/fwBgBX9/fn9/AGAEf35/fwBgAn19AX0C8gQRA3diZx1fX3diZ19idWZmZXJfNjA5Y2MzZWVlNTFlZDE1OAAJA3diZxpfX3diZ19uZXdfOWZlZTk3YTQwOWIzMmI2OAAJA3diZxpfX3diZ19zZXRfZjRmMWYwZGFhMzA2OTZmYwAKA3diZx1fX3diZ19sZW5ndGhfOGNmZDJjNjQwOWFmODhhZAALA3diZzFfX3diZ19uZXd3aXRoYnl0ZW9mZnNldGFuZGxlbmd0aF9mMWRlYWQ0NGQxZmM3MjEyAAYDd2JnGl9fd2JnX25ld19lM2IzMjFkY2ZlZjg5ZmM3AAkDd2JnGl9fd2JnX3NldF9kMjM2NjFkMTkxNDhiMjI5AAoDd2JnHV9fd2JnX2xlbmd0aF82Y2E1Mjc2NjVkODk2OTRkAAsDd2JnMV9fd2JnX25ld3dpdGhieXRlb2Zmc2V0YW5kbGVuZ3RoX2U2YjdlNjlhY2Q0YzczNTQABgN3YmcaX193Ymdfc2V0XzEwYmFkOWJlZTBlOWM1OGIACgN3YmcdX193YmdfbGVuZ3RoXzNiNGYwMjIxODhhZThkYjYACwN3YmcfX193Ymdfc3ViYXJyYXlfNzY5ZTFlMGY4MWJiMjU5YgAGA3diZx9fX3diZ19zdWJhcnJheV8zYWFlZWM4OWJiMjU0NGYwAAYDd2JnJF9fd2JnX25ld3dpdGhsZW5ndGhfNWE1ZWZlMzEzY2ZkNTlmMQARA3diZxBfX3diaW5kZ2VuX3Rocm93AAEDd2JnEV9fd2JpbmRnZW5fbWVtb3J5ABIDd2JnH19fd2JpbmRnZW5faW5pdF9leHRlcm5yZWZfdGFibGUADANeXQQAAQcFAgMCEwEBAA0BAwEAAA0BAwgIAwEBBRQBAw4AAwEDAgwMAgABAQcDABUBFhcIGRsHBQ4CEBAFAx0FBA8CBAQEAA0AAAEBAQAAAAMBAgMBAAEAAAEAAAEEBAQJAnABLi5vAIABBQMBABEGCQF/AUGAgMAACwdiBgZtZW1vcnkCAAtzb3J0X3NwbGF0cwBJDXNvcnQzMl9zcGxhdHMASg5yYXljYXN0X3NwbGF0cwA+E19fd2JpbmRnZW5fZXhwb3J0XzABARBfX3diaW5kZ2VuX3N0YXJ0ABAJMwEAQQELLVRTUlc4RSxCRUBIR0JCQUNETj0ySzQhZFlaXDlbZUYwJCprSzciZmdpVV1eagwBAwqx2wFdpiQCCX8BfiMAQRBrIggkAAJ/AkACQAJAAkACQAJAIABB9QFPBEBBACAAQcz/e0sNBxogAEELaiIBQXhxIQVBwJnAACgCACIJRQ0EQR8hB0EAIAVrIQQgAEH0//8HTQRAIAVBBiABQQh2ZyIAa3ZBAXEgAEEBdGtBPmohBwsgB0ECdEGklsAAaigCACIBRQRAQQAhAAwCC0EAIQAgBUEZIAdBAXZrQQAgB0EfRxt0IQMDQAJAIAEoAgRBeHEiBiAFSQ0AIAYgBWsiBiAETw0AIAEhAiAGIgQNAEEAIQQgASEADAQLIAEoAhQiBiAAIAYgASADQR12QQRxaigCECIBRxsgACAGGyEAIANBAXQhAyABDQALDAELQbyZwAAoAgAiAkEQIABBC2pB+ANxIABBC0kbIgVBA3YiAHYiAUEDcQRAAkAgAUF/c0EBcSAAaiIGQQN0IgBBtJfAAGoiAyAAQbyXwABqKAIAIgEoAggiBEcEQCAEIAM2AgwgAyAENgIIDAELQbyZwAAgAkF+IAZ3cTYCAAsgASAAQQNyNgIEIAAgAWoiACAAKAIEQQFyNgIEIAFBCGoMBwsgBUHEmcAAKAIATQ0DAkACQCABRQRAQcCZwAAoAgAiAEUNBiAAaEECdEGklsAAaigCACICKAIEQXhxIAVrIQQgAiEBA0ACQCACKAIQIgANACACKAIUIgANACABKAIYIQcCQAJAIAEgASgCDCIARgRAIAFBFEEQIAEoAhQiABtqKAIAIgINAUEAIQAMAgsgASgCCCICIAA2AgwgACACNgIIDAELIAFBFGogAUEQaiAAGyEDA0AgAyEGIAIiAEEUaiAAQRBqIAAoAhQiAhshAyAAQRRBECACG2ooAgAiAg0ACyAGQQA2AgALIAdFDQQCQCABKAIcQQJ0QaSWwABqIgIoAgAgAUcEQCABIAcoAhBHBEAgByAANgIUIAANAgwHCyAHIAA2AhAgAA0BDAYLIAIgADYCACAARQ0ECyAAIAc2AhggASgCECICBEAgACACNgIQIAIgADYCGAsgASgCFCICRQ0EIAAgAjYCFCACIAA2AhgMBAsgACgCBEF4cSAFayICIAQgAiAESSICGyEEIAAgASACGyEBIAAhAgwACwALAkBBAiAAdCIDQQAgA2tyIAEgAHRxaCIGQQN0IgFBtJfAAGoiAyABQbyXwABqKAIAIgAoAggiBEcEQCAEIAM2AgwgAyAENgIIDAELQbyZwAAgAkF+IAZ3cTYCAAsgACAFQQNyNgIEIAAgBWoiBiABIAVrIgNBAXI2AgQgACABaiADNgIAQcSZwAAoAgAiBARAIARBeHFBtJfAAGohAUHMmcAAKAIAIQICf0G8mcAAKAIAIgVBASAEQQN2dCIEcUUEQEG8mcAAIAQgBXI2AgAgAQwBCyABKAIICyEEIAEgAjYCCCAEIAI2AgwgAiABNgIMIAIgBDYCCAtBzJnAACAGNgIAQcSZwAAgAzYCACAAQQhqDAgLQcCZwABBwJnAACgCAEF+IAEoAhx3cTYCAAsCQAJAIARBEE8EQCABIAVBA3I2AgQgASAFaiIDIARBAXI2AgQgAyAEaiAENgIAQcSZwAAoAgAiBkUNASAGQXhxQbSXwABqIQBBzJnAACgCACECAn9BvJnAACgCACIFQQEgBkEDdnQiBnFFBEBBvJnAACAFIAZyNgIAIAAMAQsgACgCCAshBiAAIAI2AgggBiACNgIMIAIgADYCDCACIAY2AggMAQsgASAEIAVqIgBBA3I2AgQgACABaiIAIAAoAgRBAXI2AgQMAQtBzJnAACADNgIAQcSZwAAgBDYCAAsgAUEIagwGCyAAIAJyRQRAQQAhAkECIAd0IgBBACAAa3IgCXEiAEUNAyAAaEECdEGklsAAaigCACEACyAARQ0BCwNAIAAgAiAAKAIEQXhxIgMgBWsiBiAESSIHGyEJIAAoAhAiAUUEQCAAKAIUIQELIAIgCSADIAVJIgAbIQIgBCAGIAQgBxsgABshBCABIgANAAsLIAJFDQAgBUHEmcAAKAIAIgBNIAQgACAFa09xDQAgAigCGCEHAkACQCACIAIoAgwiAEYEQCACQRRBECACKAIUIgAbaigCACIBDQFBACEADAILIAIoAggiASAANgIMIAAgATYCCAwBCyACQRRqIAJBEGogABshAwNAIAMhBiABIgBBFGogAEEQaiAAKAIUIgEbIQMgAEEUQRAgARtqKAIAIgENAAsgBkEANgIACyAHRQ0CAkAgAigCHEECdEGklsAAaiIBKAIAIAJHBEAgAiAHKAIQRwRAIAcgADYCFCAADQIMBQsgByAANgIQIAANAQwECyABIAA2AgAgAEUNAgsgACAHNgIYIAIoAhAiAQRAIAAgATYCECABIAA2AhgLIAIoAhQiAUUNAiAAIAE2AhQgASAANgIYDAILAkACQAJAAkACQCAFQcSZwAAoAgAiAUsEQCAFQciZwAAoAgAiAE8EQCAFQa+ABGpBgIB8cSIAQRB2IABB//8DcUEAR2oiAkAAIQAgCEEEaiIBQQA2AgggAUEAIAJBEHQgAEF/RiICGzYCBCABQQAgAEEQdCACGzYCAEEAIAgoAgQiAUUNCRogCCgCDCEGQdSZwAAgCCgCCCIEQdSZwAAoAgBqIgA2AgBB2JnAACAAQdiZwAAoAgAiAiAAIAJLGzYCAAJAAkBB0JnAACgCACICBEBBpJfAACEAA0AgASAAKAIAIgMgACgCBCIHakYNAiAAKAIIIgANAAsMAgtB4JnAACgCACIAQQAgACABTRtFBEBB4JnAACABNgIAC0HkmcAAQf8fNgIAQbCXwAAgBjYCAEGol8AAIAQ2AgBBpJfAACABNgIAQcCXwABBtJfAADYCAEHIl8AAQbyXwAA2AgBBvJfAAEG0l8AANgIAQdCXwABBxJfAADYCAEHEl8AAQbyXwAA2AgBB2JfAAEHMl8AANgIAQcyXwABBxJfAADYCAEHgl8AAQdSXwAA2AgBB1JfAAEHMl8AANgIAQeiXwABB3JfAADYCAEHcl8AAQdSXwAA2AgBB8JfAAEHkl8AANgIAQeSXwABB3JfAADYCAEH4l8AAQeyXwAA2AgBB7JfAAEHkl8AANgIAQYCYwABB9JfAADYCAEH0l8AAQeyXwAA2AgBB/JfAAEH0l8AANgIAQYiYwABB/JfAADYCAEGEmMAAQfyXwAA2AgBBkJjAAEGEmMAANgIAQYyYwABBhJjAADYCAEGYmMAAQYyYwAA2AgBBlJjAAEGMmMAANgIAQaCYwABBlJjAADYCAEGcmMAAQZSYwAA2AgBBqJjAAEGcmMAANgIAQaSYwABBnJjAADYCAEGwmMAAQaSYwAA2AgBBrJjAAEGkmMAANgIAQbiYwABBrJjAADYCAEG0mMAAQayYwAA2AgBBwJjAAEG0mMAANgIAQciYwABBvJjAADYCAEG8mMAAQbSYwAA2AgBB0JjAAEHEmMAANgIAQcSYwABBvJjAADYCAEHYmMAAQcyYwAA2AgBBzJjAAEHEmMAANgIAQeCYwABB1JjAADYCAEHUmMAAQcyYwAA2AgBB6JjAAEHcmMAANgIAQdyYwABB1JjAADYCAEHwmMAAQeSYwAA2AgBB5JjAAEHcmMAANgIAQfiYwABB7JjAADYCAEHsmMAAQeSYwAA2AgBBgJnAAEH0mMAANgIAQfSYwABB7JjAADYCAEGImcAAQfyYwAA2AgBB/JjAAEH0mMAANgIAQZCZwABBhJnAADYCAEGEmcAAQfyYwAA2AgBBmJnAAEGMmcAANgIAQYyZwABBhJnAADYCAEGgmcAAQZSZwAA2AgBBlJnAAEGMmcAANgIAQaiZwABBnJnAADYCAEGcmcAAQZSZwAA2AgBBsJnAAEGkmcAANgIAQaSZwABBnJnAADYCAEG4mcAAQayZwAA2AgBBrJnAAEGkmcAANgIAQdCZwAAgAUEPakF4cSIAQQhrIgI2AgBBtJnAAEGsmcAANgIAQciZwAAgBEEoayIDIAEgAGtqQQhqIgA2AgAgAiAAQQFyNgIEIAEgA2pBKDYCBEHcmcAAQYCAgAE2AgAMCAsgAiADSSABIAJNcg0AIAAoAgwiA0EBcQ0AIANBAXYgBkYNAwtB4JnAAEHgmcAAKAIAIgAgASAAIAFJGzYCACABIARqIQNBpJfAACEAAkACQANAIAMgACgCACIHRwRAIAAoAggiAA0BDAILCyAAKAIMIgNBAXENACADQQF2IAZGDQELQaSXwAAhAANAAkAgAiAAKAIAIgNPBEAgAiADIAAoAgRqIgdJDQELIAAoAgghAAwBCwtB0JnAACABQQ9qQXhxIgBBCGsiAzYCAEHImcAAIARBKGsiCSABIABrakEIaiIANgIAIAMgAEEBcjYCBCABIAlqQSg2AgRB3JnAAEGAgIABNgIAIAIgB0Ega0F4cUEIayIAIAAgAkEQakkbIgNBGzYCBEGkl8AAKQIAIQogA0EQakGsl8AAKQIANwIAIAMgCjcCCEGwl8AAIAY2AgBBqJfAACAENgIAQaSXwAAgATYCAEGsl8AAIANBCGo2AgAgA0EcaiEAA0AgAEEHNgIAIABBBGoiACAHSQ0ACyACIANGDQcgAyADKAIEQX5xNgIEIAIgAyACayIAQQFyNgIEIAMgADYCACAAQYACTwRAIAIgABAgDAgLIABB+AFxQbSXwABqIQECf0G8mcAAKAIAIgNBASAAQQN2dCIAcUUEQEG8mcAAIAAgA3I2AgAgAQwBCyABKAIICyEAIAEgAjYCCCAAIAI2AgwgAiABNgIMIAIgADYCCAwHCyAAIAE2AgAgACAAKAIEIARqNgIEIAFBD2pBeHFBCGsiAiAFQQNyNgIEIAdBD2pBeHFBCGsiBCACIAVqIgBrIQUgBEHQmcAAKAIARg0DIARBzJnAACgCAEYNBCAEKAIEIgFBA3FBAUYEQCAEIAFBeHEiARAeIAEgBWohBSABIARqIgQoAgQhAQsgBCABQX5xNgIEIAAgBUEBcjYCBCAAIAVqIAU2AgAgBUGAAk8EQCAAIAUQIAwGCyAFQfgBcUG0l8AAaiEBAn9BvJnAACgCACIDQQEgBUEDdnQiBHFFBEBBvJnAACADIARyNgIAIAEMAQsgASgCCAshAyABIAA2AgggAyAANgIMIAAgATYCDCAAIAM2AggMBQtByJnAACAAIAVrIgE2AgBB0JnAAEHQmcAAKAIAIgAgBWoiAjYCACACIAFBAXI2AgQgACAFQQNyNgIEIABBCGoMCAtBzJnAACgCACEAAkAgASAFayICQQ9NBEBBzJnAAEEANgIAQcSZwABBADYCACAAIAFBA3I2AgQgACABaiIBIAEoAgRBAXI2AgQMAQtBxJnAACACNgIAQcyZwAAgACAFaiIDNgIAIAMgAkEBcjYCBCAAIAFqIAI2AgAgACAFQQNyNgIECyAAQQhqDAcLIAAgBCAHajYCBEHQmcAAQdCZwAAoAgAiAEEPakF4cSIBQQhrIgI2AgBByJnAAEHImcAAKAIAIARqIgMgACABa2pBCGoiATYCACACIAFBAXI2AgQgACADakEoNgIEQdyZwABBgICAATYCAAwDC0HQmcAAIAA2AgBByJnAAEHImcAAKAIAIAVqIgE2AgAgACABQQFyNgIEDAELQcyZwAAgADYCAEHEmcAAQcSZwAAoAgAgBWoiATYCACAAIAFBAXI2AgQgACABaiABNgIACyACQQhqDAMLQQBByJnAACgCACIAIAVNDQIaQciZwAAgACAFayIBNgIAQdCZwABB0JnAACgCACIAIAVqIgI2AgAgAiABQQFyNgIEIAAgBUEDcjYCBCAAQQhqDAILQcCZwABBwJnAACgCAEF+IAIoAhx3cTYCAAsCQCAEQRBPBEAgAiAFQQNyNgIEIAIgBWoiACAEQQFyNgIEIAAgBGogBDYCACAEQYACTwRAIAAgBBAgDAILIARB+AFxQbSXwABqIQECf0G8mcAAKAIAIgNBASAEQQN2dCIEcUUEQEG8mcAAIAMgBHI2AgAgAQwBCyABKAIICyEDIAEgADYCCCADIAA2AgwgACABNgIMIAAgAzYCCAwBCyACIAQgBWoiAEEDcjYCBCAAIAJqIgAgACgCBEEBcjYCBAsgAkEIagsgCEEQaiQAC88GAQh/AkACQCABIABBA2pBfHEiAyAAayIISQ0AIAEgCGsiBkEESQ0AIAZBA3EhB0EAIQECQCAAIANGIgkNAAJAIAAgA2siBUF8SwRAQQAhAwwBC0EAIQMDQCABIAAgA2oiAiwAAEG/f0pqIAJBAWosAABBv39KaiACQQJqLAAAQb9/SmogAkEDaiwAAEG/f0pqIQEgA0EEaiIDDQALCyAJDQAgACADaiECA0AgASACLAAAQb9/SmohASACQQFqIQIgBUEBaiIFDQALCyAAIAhqIQACQCAHRQ0AIAAgBkF8cWoiAywAAEG/f0ohBCAHQQFGDQAgBCADLAABQb9/SmohBCAHQQJGDQAgBCADLAACQb9/SmohBAsgBkECdiEFIAEgBGohBANAIAAhAyAFRQ0CQcABIAUgBUHAAU8bIgZBA3EhByAGQQJ0IQhBACECIAVBBE8EQCAAIAhB8AdxaiEJIAAhAQNAIAEoAgAiAEF/c0EHdiAAQQZ2ckGBgoQIcSACaiABQQRqKAIAIgBBf3NBB3YgAEEGdnJBgYKECHFqIAFBCGooAgAiAEF/c0EHdiAAQQZ2ckGBgoQIcWogAUEMaigCACIAQX9zQQd2IABBBnZyQYGChAhxaiECIAFBEGoiASAJRw0ACwsgBSAGayEFIAMgCGohACACQQh2Qf+B/AdxIAJB/4H8B3FqQYGABGxBEHYgBGohBCAHRQ0ACwJ/IAMgBkH8AXFBAnRqIgAoAgAiAUF/c0EHdiABQQZ2ckGBgoQIcSIBIAdBAUYNABogASAAKAIEIgFBf3NBB3YgAUEGdnJBgYKECHFqIgEgB0ECRg0AGiAAKAIIIgBBf3NBB3YgAEEGdnJBgYKECHEgAWoLIgFBCHZB/4EccSABQf+B/AdxakGBgARsQRB2IARqDwsgAUUEQEEADwsgAUEDcSEDAkAgAUEESQRADAELIAFBfHEhBQNAIAQgACACaiIBLAAAQb9/SmogAUEBaiwAAEG/f0pqIAFBAmosAABBv39KaiABQQNqLAAAQb9/SmohBCAFIAJBBGoiAkcNAAsLIANFDQAgACACaiEBA0AgBCABLAAAQb9/SmohBCABQQFqIQEgA0EBayIDDQALCyAEC4oGAQZ/IAAoAggiAyABSQRAIAEgAyICayIEIAAoAgAgAmtLBEAgACACIARBBEEEECYgACgCCCECCyAAKAIEIgYgAkECdGohBSAEQQJPBEAgASADQX9zakECdCIHBEAgBUEAIAf8CwALIAEgAmpBAnQgA0ECdGsgBmpBBGshBSACIARqQQFrIQILIAVBADYCACAAIAJBAWo2AggLIAAoAhQiAyABSQRAIAEgAyICayIEIAAoAgwgAmtLBEAgAEEMaiACIARBBEEEECYgACgCFCECCyAAKAIQIgYgAkECdGohBSAEQQJPBEAgASADQX9zakECdCIHBEAgBUEAIAf8CwALIAEgAmpBAnQgA0ECdGsgBmpBBGshBSACIARqQQFrIQILIAVBADYCACAAIAJBAWo2AhQLIAAoAjgiAyABSQRAIAEgAyICayIEIAAoAjAgAmtLBEAgAEEwaiACIARBBEEEECYgACgCOCECCyAAKAI0IgYgAkECdGohBSAEQQJPBEAgASADQX9zakECdCIHBEAgBUEAIAf8CwALIAEgAmpBAnQgA0ECdGsgBmpBBGshBSACIARqQQFrIQILIAVBADYCACAAIAJBAWo2AjgLIAAoAiAiA0H//wNNBEAgAyEBQYCABCADayICIAAoAhggA2tLBEAgAEEYaiADIAJBBEEEECYgACgCICEBCyAAKAIcIgUgAUECdCIEaiECIANB//8DRwRAQfz/DyADQQJ0IgZrIgcEQCACQQAgB/wLAAsg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IAQgA0EUahAvIAMoAghBAUcNASADKAIQIQAgAygCDAsgAEGEj8AAEEwACyADKAIMIQEgACAENgIAIAAgATYCBCADQSBqJAALuQEBBX8jAEEgayICJAAgACgCACIEQf////8BSwRAQQBBACABEEwACwJAQQQgBEEBdCIFIAVBBE0bIgVBAnQiBkH8////B00EfyACIAQEfyACIARBAnQ2AhwgAiAAKAIENgIUQQQFIAMLNgIYIAJBCGpBBCAGIAJBFGoQLyACKAIIQQFHDQEgAigCECEDIAIoAgwFIAMLIAMgARBMAAsgAigCDCEBIAAgBTYCACAAIAE2AgQgAkEgaiQAC8EBAgN/AX4jAEEwayICJAAgASgCAEGAgICAeEYEQCABKAIMIQMgAkEUaiIEQQA2AgAgAkKAgICAEDcCDCACQSBqIAMoAgAiA0EIaikCADcDACACQShqIANBEGopAgA3AwAgAiADKQIANwMYIAJBDGpBuIvAACACQRhqEBgaIAJBCGogBCgCACIDNgIAIAIgAikCDCIFNwMAIAFBCGogAzYCACABIAU3AgALIABB8I3AADYCBCAAIAE2AgAgAkEwaiQAC68BAQZ/AkACQCAAQYQBSQ0AIADQbyYBECMiASgCDCEFIAEoAhAhAiABQgA3AgwgASgCCCEDIAEoAgQhBCABQgQ3AgQgASgCACEGIAFBADYCACAAIAJJDQEgACACayIAIANPDQEgBCAAQQJ0aiAFNgIAIAEgAjYCECABIAA2AgwgASADNgIIIAEoAgQgASAENgIEIAEoAgAhACABIAY2AgAgAEUNACAAQQJ0EGALDwsAC6gBAQF/IwBBEGsiBiQAAkAgAQRAIAZBBGogASADIAQgBSACKAIQEQgAAkAgBigCBCICIAYoAgwiAU0EQCAGKAIIIQUMAQsgAkECdCECIAYoAgghAyABRQRAQQQhBSADIAIQYAwBCyADIAJBBCABQQJ0IgIQUCIFRQ0CCyAAIAE2AgQgACAFNgIAIAZBEGokAA8LQYyKwABBMhBjAAtBBCACQfyJwAAQTAALrQEBA38gASgCDCECAkACQAJAAkACQAJAIAEoAgQOAgABAgsgAg0BQQEhA0EAIQFBASECDAMLIAJFDQELIAAgARAbDwsgASgCACICKAIEIgFBAEgNASACKAIAIQMgAUUEQEEB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A0EAIAD8CwALIAsoAighFAJAIAsoAiwiEEUNACAQQQJ0IgBFDQAgFEEAIAD8CwALIBNBAnQhCSATBEAgCSEEIAohAANAAkAgACgCACIGQYCAgPwHTw0AIAwgBkF/cyIFQf//A3EiBksEQCADIAZBAnRqIgYgBigCAEEBajYCACAQIAVBEHYiBksEQCAUIAZBAnRqIgYgBigCAEEBajYCAAwCCyAGIBBB3InAABAxAAsgBiAMQcyJwAAQMQALIABBBGohACAEQQRrIgQNAAsLAkAgDEUEQEEAIQQMAQsgDEEBa0H/////A3EiAEEBaiIEQQdxIQUCQCAAQQdJBEBBACEEIAMhAAwBCyAEQfj///8HcSEGQQAhBCADIQADQCAAKAIAIQcgACAENgIAIABBBGoiESgCACESIBEgBCAHaiIENgIAIABBCGoiBygCACERIAcgBCASaiIENgIAIABBDGoiBygCACESIAcgBCARaiIENgIAIABBEGoiBygCACERIAcgBCASaiIENgIAIABBFGoiBygCACESIAcgBCARaiIENgIAIABBGGoiBygCACERIAcgBCASaiIENgIAIABBHGoiBygCACESIAcgBCARaiIENgIAIAQgEmohBCAAQSBqIQAgBkEIayIGDQALCyAFRQ0AA0AgACgCACEGIAAgBDYCACAAQQRqIQAgBCAGaiEEIAVBAWsiBQ0ACwsgDiAENgIEIBMEQCAJIApqIREgCkEEaiEGIBNBAWtB/////wNxQQFqIRIgCygCNCEXIAsoAjghB0EAIQUgCiEJA0AgBiEAAkAgCSgCACIJQYCAgPwHTw0AAkAgDCAJQX9zQf//A3EiCUsEQCADIAlBAnRqIgkoAgAiBiAHTw0BIBcgBkECdGogBTYCACAJIAkoAgBBAWo2AgAMAgsgCSAMQayJwAAQMQALIAYgB0G8icAAEDEACyAAIAAgEUdBAnRqIQYgACEJIBIgBUEBaiIFRw0ACwsCQCAQRQ0AIBBBAWtB/////wNxIgNBAWoiCUEHcSEGQQAhBSAUIQAgA0EHTwRAIAlB+P///wdxIQkDQCAAKAIAIQMgACAFNgIAIABBBGoiDCgCACEHIAwgAyAFaiIDNgIAIABBCGoiBSgCACEMIAUgAyAHaiIDNgIAIABBDGoiBSgCACEHIAUgAyAMaiIDNgIAIABBEGoiBSgCACEMIAUgAyAHaiIDNgIAIABBFGoiBSgCACEHIAUgAyAMaiIDNgIAIABBGGoiBSgCACEMIAUgAyAHaiIDNgIAIABBHGoiBSgCACEHIAUgAyAMaiIDNgIAIAMgB2ohBSAAQSBqIQAgCUEIayIJDQALCyAGRQ0AA0AgACgCACAAIAU2AgAgAEEEaiEAIAVqIQUgBkEBayIGDQALCyAERQ0BIAsoAjgiAEUNASALKAI0IQUgBEEBayEGIABBAnRBBGshACALKAIQIQcgCygCFCEJA0ACQAJAIBMgBSgCACIDSwRAIAogA0ECdGooAgBBf3NBEHYiCyAQTw0BIBQgC0ECdGoiCygCACIMIAlJDQIgDCAJQZyJwAAQMQALIAMgE0H8iMAAEDEACyALIBBBjInAABAxAAsgByAMQQJ0aiADNgIAIAsgCygCAEEBajYCACAGRQ0CIAZBAWshBiAFQQRqIQUgACAAQQRrIQANAAsMAQsgEyAAQdyIwAAQYgALAkAgEEGAgARPBEAgBCAUKAL8/w9GBEAgFUGAgICAeDYCACAVIAQ2AgQMAgsgDkECNgIMIA5BnIjAADYCCCAOQgI3AhQgDiAUQfz/D2qtQoCAgIDQAIQ3AyggDiAOQQRqrUKAgICA0ACENwMgIA4gDkEgajYCECAVIA5BCGoQGwwBC0H//wMgEEHsiMAAEDEACyAOQTBqJAAgCCgCDEGAgICAeEcNAyAIKAIQIgBFDQUgACAPKAIYIgpLDQQgDygCFCEDIAggFkEAIAAQYSIKNgIwIAhBMGogAyAAEC4gCkGEAUkNBSAKECsMBQsQNQALEDYACyAAIAlBvIfAABBiAAsgCEEgaiAIQRRqKAIANgIAIAggCCkCDDcDGCAIQQE2AjQgCEG0h8AANgIwIAhCATcCPCAIIAhBGGqtQoCAgIDAAIQ3A0ggCCAIQcgAajYCOCAIQSRqIAhBMGoQLSAIKAIoIAgoAiwQYwALIAAgCkHMh8AAEGIACyAIKAIIIgpBhAFPBEAgChArCyAPIA8oAgBBAWo2AgAgCEHQAGokACANKAIIIgpBhAFPBEAgChArCyANKAIEIgpBhAFPBEAgChArCyANQSBqJAAgAAsXAQF/IAAoAgAiAQRAIAAoAgQgARBgCwtAACAABEAgACABEGgACyMAQSBrIgAkACAAQQA2AhggAEEBNgIMIABB/I7AADYCCCAAQgQ3AhAgAEEIaiACED8ACxQAIAEgASAAIAAgAV0bIAAgAFwbCxwAIABBADYCECAAQgA3AgggAEKAgICAwAA3AgALFgEBbyAAJQEQACEBEB0iACABJgEgAAvhBgEGfwJ/AkACQAJAAkACQCAAQQRrIgUoAgAiBkF4cSIEQQRBCCAGQQNxIgcbIAFqTwRAIAdBACABQSdqIgkgBEkbDQECQAJAIAJBCU8EQCACIAMQHCIIDQFBAAwJCyADQcz/e0sNAUEQIANBC2pBeHEgA0ELSRshAQJAIAdFBEAgAUGAAkkgBCABQQRySXIgBCABa0GBgAhPcg0BDAkLIABBCGsiAiAEaiEHAkACQAJAAkAgASAESwRAIAdB0JnAACgCAEYNBCAHQcyZwAAoAgBGDQIgBygCBCIGQQJxDQUgBkF4cSIGIARqIgQgAUkNBSAHIAYQHiAEIAFrIgNBEEkNASAFIAEgBSgCAEEBcXJBAnI2AgAgASACaiIBIANBA3I2AgQgAiAEaiICIAIoAgRBAXI2AgQgASADEBoMDQsgBCABayIDQQ9LDQIMDAsgBSAEIAUoAgBBAXFyQQJyNgIAIAIgBGoiASABKAIEQQFyNgIEDAsLQcSZwAAoAgAgBGoiBCABSQ0CAkAgBCABayIDQQ9NBEAgBSAGQQFxIARyQQJyNgIAIAIgBGoiASABKAIEQQFyNgIEQQAhA0EAIQEMAQsgBSABIAZBAXFyQQJyNgIAIAEgAmoiASADQQFyNgIEIAIgBGoiAiADNgIAIAIgAigCBEF+cTYCBAtBzJnAACABNgIAQcSZwAAgAzYCAAwKCyAFIAEgBkEBcXJBAnI2AgAgASACaiIBIANBA3I2AgQgByAHKAIEQQFyNgIEIAEgAxAaDAkLQciZwAAoAgAgBGoiBCABSw0HCyADEBEiAUUNASADQXxBeCAFKAIAIgJBA3EbIAJBeHFqIgIgAiADSxsiAgRAIAEgACAC/AoAAAsgABAVIAEMCAsgAyABIAEgA0sbIgIEQCAIIAAgAvwKAAALIAUoAgAiAkF4cSIDIAFBBEEIIAJBA3EiAhtqSQ0DIAJBACADIAlLGw0EIAAQFQsgCAwGC0HQi8AAQYCMwAAQOgALQZCMwABBwIzAABA6AAtB0IvAAEGAjMAAEDoAC0GQjMAAQcCMwAAQOgALIAUgASAGQQFxckECcjYCACABIAJqIgIgBCABayIBQQFyNgIEQciZwAAgATYCAEHQmcAAIAI2AgAgAAwBCyAACwsWACAAKAIAIAEgAiAAKAIEKAIMEQIAC4UCAQN/QfCVwAAoAgBFBEACQAJAAn8CQCAARQ0AIAAoAgAgAEEANgIAQQFxRQ0AIAAoAhAhAiAAKAIMIQEgACgCCCEDIAAoAgQMAQsCQEGAgMAAEBEiAEUNACAAQQRrLQAAQQNxRQ0AIABBAEGAgMAA/AsACyAAIgFFDQFBgIAQIQJBgIAQIQNBAAshAEGAlsAAIAI2AgBB9JXAACAANgIAQfyVwAAoAgAhAkH8lcAAIAE2AgBB+JXAACgCACEAQfiVwAAgAzYCAEHwlcAAKAIAQfCVwABBATYCAEUgAEVyRQRAIAIgAEECdBBgCwwBC0EEQYCAwABB+IXAABBMAAsLQfSVwAALxAQBEX9BrJXAACgCAEUEQAJAIAAEQCAAKAJAIQEgACgCPCECIAAoAjghAyAAKAI0IQQgACgCMCEFIAAoAiwhBiAAKAIoIQcgACgCJCEIIAAoAiAhCSAAKAIcIQogACgCGCELIAAoAhQhDCAAKAIQIQ0gACgCDCEOIAAoAgghDyAAKAIEIRAgACgCACAAQQA2AgBBAXENAQtBBCECQQAhAUEAIQNBACEEQQQhBUEAIQZBACEHQQQhCEEAIQlBACEKQQQhC0EAIQxBACENQQQhDkEAIQ9BACEQC0HslcAAIAE2AgBB4JXAACAENgIAQdSVwAAgBzYCAEHIlcAAIAo2AgBBvJXAACANNgIAQbCVwAAgEDYCAEHolcAAKAIAIQdB6JXAACACNgIAQeSVwAAoAgAhAEHklcAAIAM2AgBB3JXAACgCACEKQdyVwAAgBTYCAEHYlcAAKAIAIQFB2JXAACAGNgIAQdCVwAAoAgAhBUHQlcAAIAg2AgBBzJXAACgCACECQcyVwAAgCTYCAEHElcAAKAIAIQZBxJXAACALNgIAQcCVwAAoAgAhA0HAlcAAIAw2AgBBuJXAACgCACEIQbiVwAAgDjYCAEG0lcAAKAIAIQRBtJXAACAPNgIAQayVwAAoAgAhCUGslcAAQQE2AgACQCAJRQ0AIAQEQCAIIARBAnQQYAsgAwRAIAYgA0ECdBBgCyACBEAgBSACQQJ0EGALIAEEQCAKIAFBAnQQYAsgAEUNACAHIABBAnQQYAsLQbCVwAAL8gIBCX9BgJXAACgCAEUEQAJ/AkAgAEUNACAAKAIAIABBADYCAEEBcUUNACAAKAIoIQEgACgCJCEHIAAoAiAhAiAAKAIcIQMgACgCGCEIIAAoAhQhBCAAKAIQIQUgACgCDCEJIAAoAgghBiAAKAIEDAELQQIhCUEEIQdBACEBQQQhCEEACyEAQaiVwAAgATYCAEGclcAAIAM2AgBBkJXAACAFNgIAQYSVwAAgADYCAEGklcAAKAIAIQVBpJXAACAHNgIAQaCVwAAoAgAhAEGglcAAIAI2AgBBmJXAACgCACEBQZiVwAAgCDYCAEGUlcAAKAIAIQJBlJXAACAENgIAQYyVwAAoAgAhBEGMlcAAIAk2AgBBiJXAACgCACEDQYiVwAAgBjYCAEGAlcAAKAIAIQZBgJXAAEEBNgIAAkAgBkUNACADBEAgBCADQQF0EGALIAIEQCABIAJBAnQQYAsgAEUNACAFIABBAnQQYAsLQYSVwAALFAAgACgCACABIAAoAgQoAgwRAAALFAIBbwF/EA8hABAdIgEgACYBIAELEAAgASAAKAIEIAAoAggQFgsZAAJ/IAFBCU8EQCABIAAQHAwBCyAAEBELCyAAIABC356dmJy3lrgCNwMIIABCoe2sjPn0nLgHNwMACyIAIABC7bqtts2F1PXjADcDCCAAQviCmb2V7sbFuX83AwALEwAgAEGAjsAANgIEIAAgATYCAAsQACABIAAoAgAgACgCBBBRCxAAIAEgACgCACAAKAIEEBYLEAAgASgCACABKAIEIAAQGAsOACAAJQEgASUBIAIQBgtbAQJ/AkACQCAAQQRrKAIAIgJBeHEiA0EEQQggAkEDcSICGyABak8EQCACQQAgAyABQSdqSxsNASAAEBUMAgtB0IvAAEGAjMAAEDoAC0GQjMAAQcCMwAAQOgALCx0BAW8gACgCACUBIAEgAhAMIQMQHSIAIAMmASAAC2oBAX8jAEEwayIDJAAgAyABNgIEIAMgADYCACADQQI2AgwgA0G0lMAANgIIIANCAjcCFCADIANBBGqtQoCAgIDQAIQ3AyggAyADrUKAgICA0ACENwMgIAMgA0EgajYCECADQQhqIAIQPwALCQAgACABEA4ACw0AIABBuIvAACABEBgLDAAgACABKQIANwMACw0AIABB0I7AACABEBgLDQAgAUHIjsAAQQUQUQsZACAAIAFBkJbAACgCACIAQRQgABsRAQAACw0AIAFBpJDAAEEYEBYLoAIBA38gACgCACEAIwBBkAFrIgMkAAJ/AkAgASgCCCICQYCAgBBxRQRAIAJBgICAIHENASADQQhqIAAoAgAgA0EQahAfIAFBAUEAIAMoAgggAygCDBAUDAILIAAoAgAhAkEAIQADQCAAIANqQY8BaiACQQ9xIgRBMHIgBEHXAGogBEEKSRs6AAAgAEEBayEAIAJBD0sgAkEEdiECDQALIAFBt5LAAEECIAAgA2pBkAFqQQAgAGsQFAwBCyAAKAIAIQJBACEAA0AgACADakGPAWogAkEPcSIEQTByIARBN2ogBEEKSRs6AAAgAEEBayEAIAJBD0sgAkEEdiECDQALIAFBt5LAAEECIAAgA2pBkAFqQQAgAGsQFAsgA0GQAWokAAsJACAAQQA2AgALCAAgACUBEAMLCAAgACUBEAcLC/UUAwBBgIDAAAuhD3NwYXJrLWludGVybmFsLXJzL3NyYy9yYXljYXN0LnJzAHNwYXJrLWludGVybmFsLXJzL3NyYy9zb3J0LnJzAGxpYnJhcnkvYWxsb2Mvc3JjL2ZtdC5ycwAvaG9tZS9ydW5uZXIvLmNhcmdvL3JlZ2lzdHJ5L3NyYy9pbmRleC5jcmF0ZXMuaW8tMTk0OWNmOGM2YjViNTU3Zi93YXNtLWJpbmRnZW4tMC4yLjEwMC9zcmMvY29udmVydC9zbGljZXMucnMAL3J1c3RjLzI5NDgzODgzZWVkNjlkNWZiNGRiMDE5NjRjZGYyYWY0ZDg2ZTljYjIvbGlicmFyeS9zdGQvc3JjL3RocmVhZC9sb2NhbC5ycwBsaWJyYXJ5L2FsbG9jL3NyYy9zdHJpbmcucnMAL3J1c3RjLzI5NDgzODgzZWVkNjlkNWZiNGRiMDE5NjRjZGYyYWY0ZDg2ZTljYjIvbGlicmFyeS9hbGxvYy9zcmMvc2xpY2UucnMAL3J1c3RjLzI5NDgzODgzZWVkNjlkNWZiNGRiMDE5NjRjZGYyYWY0ZDg2ZTljYjIvbGlicmFyeS9hbGxvYy9zcmMvcmF3X3ZlYy9tb2QucnMAL3J1c3QvZGVwcy9kbG1hbGxv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dGAgZmFpbGVkOiAKICBsZWZ0OiAAAACbCBAAEAAAAOQIEAAQAAAA9AgQAAkAAADCCBAACQAAADogAAABAAAAAAAAACAJEAACAAAAfSB9MHgwMDAxMDIwMzA0MDUwNjA3MDgwOTEwMTExMjEzMTQxNTE2MTcxODE5MjAyMTIyMjMyNDI1MjYyNzI4MjkzMDMxMzIzMzM0MzUzNjM3MzgzOTQwNDE0MjQzNDQ0NTQ2NDc0ODQ5NTA1MTUyNTM1NDU1NTY1NzU4NTk2MDYxNjI2MzY0NjU2NjY3Njg2OTcwNzE3MjczNzQ3NTc2Nzc3ODc5ODA4MTgyODM4NDg1ODY4Nzg4ODk5MDkxOTI5Mzk0OTU5Njk3OTg5OSBvdXQgb2YgcmFuZ2UgZm9yIHNsaWNlIG9mIGxlbmd0aCByYW5nZSBlbmQgaW5kZXggACMKEAAQAAAAAQoQACIAAACQCBAAkggQAJQIEAACAAAAAgAAAAcAAAAAAAA/AAAAvwBB/JTAAAsBEgB8CXByb2R1Y2VycwIIbGFuZ3VhZ2UBBFJ1c3QADHByb2Nlc3NlZC1ieQMFcnVzdGMdMS44OS4wICgyOTQ4Mzg4M2UgMjAyNS0wOC0wNCkGd2FscnVzBjAuMjMuMwx3YXNtLWJpbmRnZW4TMC4yLjEwMCAoMjQwNWVjMmI0KQBrD3RhcmdldF9mZWF0dXJlcwYrD211dGFibGUtZ2xvYmFscysTbm9udHJhcHBpbmctZnB0b2ludCsLYnVsay1tZW1vcnkrCHNpZ24tZXh0Kw9yZWZlcmVuY2UtdHlwZXMrCm11bHRpdmFsdWU=",self.location.href));const A=as();(typeof s=="string"||typeof Request=="function"&&s instanceof Request||typeof URL=="function"&&s instanceof URL)&&(s=fetch(s));const{instance:t,module:e}=await Is(await s,A);return os(t,e)}var Ie={},Cs=function(s,A,t,e,i){var n=new Worker(Ie[A]||(Ie[A]=URL.createObjectURL(new Blob([s+\';addEventListener("error",function(e){e=e.error;postMessage({$e$:[e.message,e.code,e.stack]})})\'],{type:"text/javascript"}))));return n.onmessage=function(r){var g=r.data,I=g.$e$;if(I){var a=new Error(I[0]);a.code=I[1],a.stack=I[2],i(a,null)}else i(null,g)},n.postMessage(t,e),n},V=Uint8Array,JA=Uint16Array,ae=Int32Array,Ft=new V([0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0,0,0,0]),dt=new V([0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13,0,0]),oe=new V([16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15]),Ce=function(s,A){for(var t=new JA(31),e=0;e<31;++e)t[e]=A+=1<<s[e-1];for(var i=new ae(t[30]),e=1;e<30;++e)for(var n=t[e];n<t[e+1];++n)i[n]=n-t[e]<<5|e;return{b:t,r:i}},Be=Ce(Ft,2),Nt=Be.b,Bs=Be.r;Nt[28]=258,Bs[258]=28;for(var hs=Ce(dt,0),he=hs.b,It=new JA(32768),X=0;X<32768;++X){var dA=(X&43690)>>1|(X&21845)<<1;dA=(dA&52428)>>2|(dA&13107)<<2,dA=(dA&61680)>>4|(dA&3855)<<4,It[X]=((dA&65280)>>8|(dA&255)<<8)>>1}for(var vA=function(s,A,t){for(var e=s.length,i=0,n=new JA(A);i<e;++i)s[i]&&++n[s[i]-1];var r=new JA(A);for(i=1;i<A;++i)r[i]=r[i-1]+n[i-1]<<1;var g;if(t){g=new JA(1<<A);var I=15-A;for(i=0;i<e;++i)if(s[i])for(var a=i<<4|s[i],o=A-s[i],C=r[s[i]-1]++<<o,h=C|(1<<o)-1;C<=h;++C)g[It[C]>>I]=a}else for(g=new JA(e),i=0;i<e;++i)s[i]&&(g[i]=It[r[s[i]-1]++]>>15-s[i]);return g},$A=new V(288),X=0;X<144;++X)$A[X]=8;for(var X=144;X<256;++X)$A[X]=9;for(var X=256;X<280;++X)$A[X]=7;for(var X=280;X<288;++X)$A[X]=8;for(var Qe=new V(32),X=0;X<32;++X)Qe[X]=5;var Ee=vA($A,9,1),ce=vA(Qe,5,1),at=function(s){for(var A=s[0],t=1;t<s.length;++t)s[t]>A&&(A=s[t]);return A},hA=function(s,A,t){var e=A/8|0;return(s[e]|s[e+1]<<8)>>(A&7)&t},ot=function(s,A){var t=A/8|0;return(s[t]|s[t+1]<<8|s[t+2]<<16)>>(A&7)},kt=function(s){return(s+7)/8|0},NA=function(s,A,t){return(A==null||A<0)&&(A=0),(t==null||t>s.length)&&(t=s.length),new V(s.subarray(A,t))},le=["unexpected EOF","invalid block type","invalid length/literal","invalid distance","stream finished","no stream handler",,"no callback","invalid UTF-8 data","extra field too long","date not in range 1980-2099","filename too long","stream finishing","invalid zip data"],O=function(s,A,t){var e=new Error(A||le[s]);if(e.code=s,Error.captureStackTrace&&Error.captureStackTrace(e,O),!t)throw e;return e},Gt=function(s,A,t,e){var i=s.length,n=e?e.length:0;if(!i||A.f&&!A.l)return t||new V(0);var r=!t,g=r||A.i!=2,I=A.i;r&&(t=new V(i*3));var a=function(gA){var oA=t.length;if(gA>oA){var CA=new V(Math.max(oA*2,gA));CA.set(t),t=CA}},o=A.f||0,C=A.p||0,h=A.b||0,B=A.l,Q=A.d,u=A.m,l=A.n,E=i*8;do{if(!B){o=hA(s,C,1);var f=hA(s,C+1,3);if(C+=3,f)if(f==1)B=Ee,Q=ce,u=9,l=5;else if(f==2){var d=hA(s,C,31)+257,z=hA(s,C+10,15)+4,m=d+hA(s,C+5,31)+1;C+=14;for(var w=new V(m),G=new V(19),S=0;S<z;++S)G[oe[S]]=hA(s,C+S*3,7);C+=z*3;for(var D=at(G),F=(1<<D)-1,M=vA(G,D,1),S=0;S<m;){var x=M[hA(s,C,F)];C+=x&15;var c=x>>4;if(c<16)w[S++]=c;else{var U=0,v=0;for(c==16?(v=3+hA(s,C,3),C+=2,U=w[S-1]):c==17?(v=3+hA(s,C,7),C+=3):c==18&&(v=11+hA(s,C,127),C+=7);v--;)w[S++]=U}}var q=w.subarray(0,d),Z=w.subarray(d);u=at(q),l=at(Z),B=vA(q,u,1),Q=vA(Z,l,1)}else O(1);else{var c=kt(C)+4,y=s[c-4]|s[c-3]<<8,p=c+y;if(p>i){I&&O(0);break}g&&a(h+y),t.set(s.subarray(c,p),h),A.b=h+=y,A.p=C=p*8,A.f=o;continue}if(C>E){I&&O(0);break}}g&&a(h+131072);for(var W=(1<<u)-1,K=(1<<l)-1,P=C;;P=C){var U=B[ot(s,C)&W],L=U>>4;if(C+=U&15,C>E){I&&O(0);break}if(U||O(2),L<256)t[h++]=L;else if(L==256){P=C,B=null;break}else{var T=L-254;if(L>264){var S=L-257,_=Ft[S];T=hA(s,C,(1<<_)-1)+Nt[S],C+=_}var R=Q[ot(s,C)&K],N=R>>4;R||O(3),C+=R&15;var Z=he[N];if(N>3){var _=dt[N];Z+=ot(s,C)&(1<<_)-1,C+=_}if(C>E){I&&O(0);break}g&&a(h+131072);var sA=h+T;if(h<Z){var iA=n-Z,aA=Math.min(Z,sA);for(iA+h<0&&O(3);h<aA;++h)t[h]=e[iA+h]}for(;h<sA;++h)t[h]=t[h-Z]}}A.l=B,A.p=P,A.b=h,A.f=o,B&&(o=1,A.m=u,A.d=Q,A.n=l)}while(!o);return h!=t.length&&r?NA(t,0,h):t.subarray(0,h)},Qs=new V(0),Es=function(s,A){var t={};for(var e in s)t[e]=s[e];for(var e in A)t[e]=A[e];return t},ue=function(s,A,t){for(var e=s(),i=s.toString(),n=i.slice(i.indexOf("[")+1,i.lastIndexOf("]")).replace(/\\s+/g,"").split(","),r=0;r<e.length;++r){var g=e[r],I=n[r];if(typeof g=="function"){A+=";"+I+"=";var a=g.toString();if(g.prototype)if(a.indexOf("[native code]")!=-1){var o=a.indexOf(" ",8)+1;A+=a.slice(o,a.indexOf("(",o))}else{A+=a;for(var C in g.prototype)A+=";"+I+".prototype."+C+"="+g.prototype[C].toString()}else A+=a}else t[I]=g}return A},Ct=[],cs=function(s){var A=[];for(var t in s)s[t].buffer&&A.push((s[t]=new s[t].constructor(s[t])).buffer);return A},ls=function(s,A,t,e){if(!Ct[t]){for(var i="",n={},r=s.length-1,g=0;g<r;++g)i=ue(s[g],i,n);Ct[t]={c:ue(s[r],i,n),e:n}}var I=Es({},Ct[t].e);return Cs(Ct[t].c+";onmessage=function(e){for(var k in e.data)self[k]=e.data[k];onmessage="+A.toString()+"}",t,I,cs(I),e)},us=function(){return[V,JA,ae,Ft,dt,oe,Nt,he,Ee,ce,It,le,vA,at,hA,ot,kt,NA,O,Gt,Bt,ye,fe]},ye=function(s){return postMessage(s,[s.buffer])},fe=function(s){return s&&{out:s.size&&new V(s.size),dictionary:s.dictionary}},ys=function(s,A,t,e,i,n){var r=ls(t,e,i,function(g,I){r.terminate(),n(g,I)});return r.postMessage([s,A],A.consume?[s.buffer]:[]),function(){r.terminate()}},uA=function(s,A){return s[A]|s[A+1]<<8},tA=function(s,A){return(s[A]|s[A+1]<<8|s[A+2]<<16|s[A+3]<<24)>>>0},Ut=function(s,A){return tA(s,A)+tA(s,A+4)*4294967296},fs=function(s){(s[0]!=31||s[1]!=139||s[2]!=8)&&O(6,"invalid gzip data");var A=s[3],t=10;A&4&&(t+=(s[10]|s[11]<<8)+2);for(var e=(A>>3&1)+(A>>4&1);e>0;e-=!s[t++]);return t+(A&2)},Yt=function(){function s(A,t){typeof A=="function"&&(t=A,A={}),this.ondata=t;var e=A&&A.dictionary&&A.dictionary.subarray(-32768);this.s={i:0,b:e?e.length:0},this.o=new V(32768),this.p=new V(0),e&&this.o.set(e)}return s.prototype.e=function(A){if(this.ondata||O(5),this.d&&O(4),!this.p.length)this.p=A;else if(A.length){var t=new V(this.p.length+A.length);t.set(this.p),t.set(A,this.p.length),this.p=t}},s.prototype.c=function(A){this.s.i=+(this.d=A||!1);var t=this.s.b,e=Gt(this.p,this.s,this.o);this.ondata(NA(e,t,this.s.b),this.d),this.o=NA(e,this.s.b-32768),this.s.b=this.o.length,this.p=NA(this.p,this.s.p/8|0),this.s.p&=7},s.prototype.push=function(A,t){this.e(A),this.c(t)},s}();function ws(s,A,t){return t||(t=A,A={}),typeof t!="function"&&O(7),ys(s,A,[us],function(e){return ye(Bt(e.data[0],fe(e.data[1])))},1,t)}function Bt(s,A){return Gt(s,{i:2},A&&A.out,A&&A.dictionary)}var ms=function(){function s(A,t){this.v=1,this.r=0,Yt.call(this,A,t)}return s.prototype.push=function(A,t){if(Yt.prototype.e.call(this,A),this.r+=A.length,this.v){var e=this.p.subarray(this.v-1),i=e.length>3?fs(e):4;if(i>e.length){if(!t)return}else this.v>1&&this.onmember&&this.onmember(this.r-e.length);this.p=e.subarray(i),this.v=0}Yt.prototype.c.call(this,t),this.s.f&&!this.s.l&&!t&&(this.v=kt(this.s.p)+9,this.s={i:0},this.o=new V(0),this.push(new V(0),t))},s}(),bt=typeof TextDecoder<"u"&&new TextDecoder;try{bt.decode(Qs,{stream:!0})}catch{}var ps=function(s){for(var A="",t=0;;){var e=s[t++],i=(e>127)+(e>223)+(e>239);if(t+i>s.length)return{s:A,r:NA(s,t-1)};i?i==3?(e=((e&15)<<18|(s[t++]&63)<<12|(s[t++]&63)<<6|s[t++]&63)-65536,A+=String.fromCharCode(55296|e>>10,56320|e&1023)):i&1?A+=String.fromCharCode((e&31)<<6|s[t++]&63):A+=String.fromCharCode((e&15)<<12|(s[t++]&63)<<6|s[t++]&63):A+=String.fromCharCode(e)}};function Ds(s,A){if(A){for(var t="",e=0;e<s.length;e+=16384)t+=String.fromCharCode.apply(null,s.subarray(e,e+16384));return t}else{if(bt)return bt.decode(s);var i=ps(s),n=i.s,t=i.r;return t.length&&O(8),n}}var we=function(s,A){return A+30+uA(s,A+26)+uA(s,A+28)},me=function(s,A,t){var e=uA(s,A+28),i=Ds(s.subarray(A+46,A+46+e),!(uA(s,A+8)&2048)),n=A+46+e,r=tA(s,A+20),g=t&&r==4294967295?Ss(s,n):[r,tA(s,A+24),tA(s,A+42)],I=g[0],a=g[1],o=g[2];return[uA(s,A+10),I,a,i,n+uA(s,A+30)+uA(s,A+32),o]},Ss=function(s,A){for(;uA(s,A)!=1;A+=4+uA(s,A+2));return[Ut(s,A+12),Ut(s,A+4),Ut(s,A+20)]},pe=typeof queueMicrotask=="function"?queueMicrotask:typeof setTimeout=="function"?setTimeout:function(s){s()};function xs(s,A,t){t||(t=A,A={}),typeof t!="function"&&O(7);var e=[],i=function(){for(var l=0;l<e.length;++l)e[l]()},n={},r=function(l,E){pe(function(){t(l,E)})};pe(function(){r=t});for(var g=s.length-22;tA(s,g)!=101010256;--g)if(!g||s.length-g>65558)return r(O(13,0,1),null),i;var I=uA(s,g+8);if(I){var a=I,o=tA(s,g+16),C=o==4294967295||a==65535;if(C){var h=tA(s,g-12);C=tA(s,h)==101075792,C&&(a=I=tA(s,h+32),o=tA(s,h+48))}for(var B=A&&A.filter,Q=function(l){var E=me(s,o,C),f=E[0],c=E[1],y=E[2],p=E[3],d=E[4],z=E[5],m=we(s,z);o=d;var w=function(S,D){S?(i(),r(S,null)):(D&&(n[p]=D),--I||r(null,n))};if(!B||B({name:p,size:c,originalSize:y,compression:f}))if(!f)w(null,NA(s,m,m+c));else if(f==8){var G=s.subarray(m,m+c);if(y<524288||c>.8*y)try{w(null,Bt(G,{out:new V(y)}))}catch(S){w(S,null)}else e.push(ws(G,{size:y},w))}else w(O(14,"unknown compression type "+f,1),null);else w(null,null)},u=0;u<a;++u)Q(u)}else r(null,{});return i}function Ms(s,A){for(var t={},e=s.length-22;tA(s,e)!=101010256;--e)(!e||s.length-e>65558)&&O(13);var i=uA(s,e+8);if(!i)return{};var n=tA(s,e+16),r=n==4294967295||i==65535;if(r){var g=tA(s,e-12);r=tA(s,g)==101075792,r&&(i=tA(s,g+32),n=tA(s,g+48))}for(var I=A&&A.filter,a=0;a<i;++a){var o=me(s,n,r),C=o[0],h=o[1],B=o[2],Q=o[3],u=o[4],l=o[5],E=we(s,l);n=u,(!I||I({name:Q,size:h,originalSize:B,compression:C}))&&(C?C==8?t[Q]=Bt(s.subarray(E,E+h),{out:new V(B)}):O(14,"unknown compression type "+C):t[Q]=NA(s,E,E+h))}return t}/**\n * @license\n * Copyright 2010-2025 Three.js Authors\n * SPDX-License-Identifier: MIT\n */const De="178",Fs="",yA="srgb",Se="srgb-linear",xe="linear",Rt="srgb";function IA(s,A,t){return Math.max(A,Math.min(t,s))}function ds(s,A){return(s%A+A)%A}function _t(s,A,t){return(1-t)*s+t*A}class kA{constructor(A=0,t=0,e=0,i=1){this.isQuaternion=!0,this._x=A,this._y=t,this._z=e,this._w=i}static slerpFlat(A,t,e,i,n,r,g){let I=e[i+0],a=e[i+1],o=e[i+2],C=e[i+3];const h=n[r+0],B=n[r+1],Q=n[r+2],u=n[r+3];if(g===0){A[t+0]=I,A[t+1]=a,A[t+2]=o,A[t+3]=C;return}if(g===1){A[t+0]=h,A[t+1]=B,A[t+2]=Q,A[t+3]=u;return}if(C!==u||I!==h||a!==B||o!==Q){let l=1-g;const E=I*h+a*B+o*Q+C*u,f=E>=0?1:-1,c=1-E*E;if(c>Number.EPSILON){const p=Math.sqrt(c),d=Math.atan2(p,E*f);l=Math.sin(l*d)/p,g=Math.sin(g*d)/p}const y=g*f;if(I=I*l+h*y,a=a*l+B*y,o=o*l+Q*y,C=C*l+u*y,l===1-g){const p=1/Math.sqrt(I*I+a*a+o*o+C*C);I*=p,a*=p,o*=p,C*=p}}A[t]=I,A[t+1]=a,A[t+2]=o,A[t+3]=C}static multiplyQuaternionsFlat(A,t,e,i,n,r){const g=e[i],I=e[i+1],a=e[i+2],o=e[i+3],C=n[r],h=n[r+1],B=n[r+2],Q=n[r+3];return A[t]=g*Q+o*C+I*B-a*h,A[t+1]=I*Q+o*h+a*C-g*B,A[t+2]=a*Q+o*B+g*h-I*C,A[t+3]=o*Q-g*C-I*h-a*B,A}get x(){return this._x}set x(A){this._x=A,this._onChangeCallback()}get y(){return this._y}set y(A){this._y=A,this._onChangeCallback()}get z(){return this._z}set z(A){this._z=A,this._onChangeCallback()}get w(){return this._w}set w(A){this._w=A,this._onChangeCallback()}set(A,t,e,i){return this._x=A,this._y=t,this._z=e,this._w=i,this._onChangeCallback(),this}clone(){return new this.constructor(this._x,this._y,this._z,this._w)}copy(A){return this._x=A.x,this._y=A.y,this._z=A.z,this._w=A.w,this._onChangeCallback(),this}setFromEuler(A,t=!0){const e=A._x,i=A._y,n=A._z,r=A._order,g=Math.cos,I=Math.sin,a=g(e/2),o=g(i/2),C=g(n/2),h=I(e/2),B=I(i/2),Q=I(n/2);switch(r){case"XYZ":this._x=h*o*C+a*B*Q,this._y=a*B*C-h*o*Q,this._z=a*o*Q+h*B*C,this._w=a*o*C-h*B*Q;break;case"YXZ":this._x=h*o*C+a*B*Q,this._y=a*B*C-h*o*Q,this._z=a*o*Q-h*B*C,this._w=a*o*C+h*B*Q;break;case"ZXY":this._x=h*o*C-a*B*Q,this._y=a*B*C+h*o*Q,this._z=a*o*Q+h*B*C,this._w=a*o*C-h*B*Q;break;case"ZYX":this._x=h*o*C-a*B*Q,this._y=a*B*C+h*o*Q,this._z=a*o*Q-h*B*C,this._w=a*o*C+h*B*Q;break;case"YZX":this._x=h*o*C+a*B*Q,this._y=a*B*C+h*o*Q,this._z=a*o*Q-h*B*C,this._w=a*o*C-h*B*Q;break;case"XZY":this._x=h*o*C-a*B*Q,this._y=a*B*C-h*o*Q,this._z=a*o*Q+h*B*C,this._w=a*o*C+h*B*Q;break;default:console.warn("THREE.Quaternion: .setFromEuler() encountered an unknown order: "+r)}return t===!0&&this._onChangeCallback(),this}setFromAxisAngle(A,t){const e=t/2,i=Math.sin(e);return this._x=A.x*i,this._y=A.y*i,this._z=A.z*i,this._w=Math.cos(e),this._onChangeCallback(),this}setFromRotationMatrix(A){const t=A.elements,e=t[0],i=t[4],n=t[8],r=t[1],g=t[5],I=t[9],a=t[2],o=t[6],C=t[10],h=e+g+C;if(h>0){const B=.5/Math.sqrt(h+1);this._w=.25/B,this._x=(o-I)*B,this._y=(n-a)*B,this._z=(r-i)*B}else if(e>g&&e>C){const B=2*Math.sqrt(1+e-g-C);this._w=(o-I)/B,this._x=.25*B,this._y=(i+r)/B,this._z=(n+a)/B}else if(g>C){const B=2*Math.sqrt(1+g-e-C);this._w=(n-a)/B,this._x=(i+r)/B,this._y=.25*B,this._z=(I+o)/B}else{const B=2*Math.sqrt(1+C-e-g);this._w=(r-i)/B,this._x=(n+a)/B,this._y=(I+o)/B,this._z=.25*B}return this._onChangeCallback(),this}setFromUnitVectors(A,t){let e=A.dot(t)+1;return e<1e-8?(e=0,Math.abs(A.x)>Math.abs(A.z)?(this._x=-A.y,this._y=A.x,this._z=0,this._w=e):(this._x=0,this._y=-A.z,this._z=A.y,this._w=e)):(this._x=A.y*t.z-A.z*t.y,this._y=A.z*t.x-A.x*t.z,this._z=A.x*t.y-A.y*t.x,this._w=e),this.normalize()}angleTo(A){return 2*Math.acos(Math.abs(IA(this.dot(A),-1,1)))}rotateTowards(A,t){const e=this.angleTo(A);if(e===0)return this;const i=Math.min(1,t/e);return this.slerp(A,i),this}identity(){return this.set(0,0,0,1)}invert(){return this.conjugate()}conjugate(){return this._x*=-1,this._y*=-1,this._z*=-1,this._onChangeCallback(),this}dot(A){return this._x*A._x+this._y*A._y+this._z*A._z+this._w*A._w}lengthSq(){return this._x*this._x+this._y*this._y+this._z*this._z+this._w*this._w}length(){return Math.sqrt(this._x*this._x+this._y*this._y+this._z*this._z+this._w*this._w)}normalize(){let A=this.length();return A===0?(this._x=0,this._y=0,this._z=0,this._w=1):(A=1/A,this._x=this._x*A,this._y=this._y*A,this._z=this._z*A,this._w=this._w*A),this._onChangeCallback(),this}multiply(A){return this.multiplyQuaternions(this,A)}premultiply(A){return this.multiplyQuaternions(A,this)}multiplyQuaternions(A,t){const e=A._x,i=A._y,n=A._z,r=A._w,g=t._x,I=t._y,a=t._z,o=t._w;return this._x=e*o+r*g+i*a-n*I,this._y=i*o+r*I+n*g-e*a,this._z=n*o+r*a+e*I-i*g,this._w=r*o-e*g-i*I-n*a,this._onChangeCallback(),this}slerp(A,t){if(t===0)return this;if(t===1)return this.copy(A);const e=this._x,i=this._y,n=this._z,r=this._w;let g=r*A._w+e*A._x+i*A._y+n*A._z;if(g<0?(this._w=-A._w,this._x=-A._x,this._y=-A._y,this._z=-A._z,g=-g):this.copy(A),g>=1)return this._w=r,this._x=e,this._y=i,this._z=n,this;const I=1-g*g;if(I<=Number.EPSILON){const B=1-t;return this._w=B*r+t*this._w,this._x=B*e+t*this._x,this._y=B*i+t*this._y,this._z=B*n+t*this._z,this.normalize(),this}const a=Math.sqrt(I),o=Math.atan2(a,g),C=Math.sin((1-t)*o)/a,h=Math.sin(t*o)/a;return this._w=r*C+this._w*h,this._x=e*C+this._x*h,this._y=i*C+this._y*h,this._z=n*C+this._z*h,this._onChangeCallback(),this}slerpQuaternions(A,t,e){return this.copy(A).slerp(t,e)}random(){const A=2*Math.PI*Math.random(),t=2*Math.PI*Math.random(),e=Math.random(),i=Math.sqrt(1-e),n=Math.sqrt(e);return this.set(i*Math.sin(A),i*Math.cos(A),n*Math.sin(t),n*Math.cos(t))}equals(A){return A._x===this._x&&A._y===this._y&&A._z===this._z&&A._w===this._w}fromArray(A,t=0){return this._x=A[t],this._y=A[t+1],this._z=A[t+2],this._w=A[t+3],this._onChangeCallback(),this}toArray(A=[],t=0){return A[t]=this._x,A[t+1]=this._y,A[t+2]=this._z,A[t+3]=this._w,A}fromBufferAttribute(A,t){return this._x=A.getX(t),this._y=A.getY(t),this._z=A.getZ(t),this._w=A.getW(t),this._onChangeCallback(),this}toJSON(){return this.toArray()}_onChange(A){return this._onChangeCallback=A,this}_onChangeCallback(){}*[Symbol.iterator](){yield this._x,yield this._y,yield this._z,yield this._w}}class k{constructor(A=0,t=0,e=0){k.prototype.isVector3=!0,this.x=A,this.y=t,this.z=e}set(A,t,e){return e===void 0&&(e=this.z),this.x=A,this.y=t,this.z=e,this}setScalar(A){return this.x=A,this.y=A,this.z=A,this}setX(A){return this.x=A,this}setY(A){return this.y=A,this}setZ(A){return this.z=A,this}setComponent(A,t){switch(A){case 0:this.x=t;break;case 1:this.y=t;break;case 2:this.z=t;break;default:throw new Error("index is out of range: "+A)}return this}getComponent(A){switch(A){case 0:return this.x;case 1:return this.y;case 2:return this.z;default:throw new Error("index is out of range: "+A)}}clone(){return new this.constructor(this.x,this.y,this.z)}copy(A){return this.x=A.x,this.y=A.y,this.z=A.z,this}add(A){return this.x+=A.x,this.y+=A.y,this.z+=A.z,this}addScalar(A){return this.x+=A,this.y+=A,this.z+=A,this}addVectors(A,t){return this.x=A.x+t.x,this.y=A.y+t.y,this.z=A.z+t.z,this}addScaledVector(A,t){return this.x+=A.x*t,this.y+=A.y*t,this.z+=A.z*t,this}sub(A){return this.x-=A.x,this.y-=A.y,this.z-=A.z,this}subScalar(A){return this.x-=A,this.y-=A,this.z-=A,this}subVectors(A,t){return this.x=A.x-t.x,this.y=A.y-t.y,this.z=A.z-t.z,this}multiply(A){return this.x*=A.x,this.y*=A.y,this.z*=A.z,this}multiplyScalar(A){return this.x*=A,this.y*=A,this.z*=A,this}multiplyVectors(A,t){return this.x=A.x*t.x,this.y=A.y*t.y,this.z=A.z*t.z,this}applyEuler(A){return this.applyQuaternion(Me.setFromEuler(A))}applyAxisAngle(A,t){return this.applyQuaternion(Me.setFromAxisAngle(A,t))}applyMatrix3(A){const t=this.x,e=this.y,i=this.z,n=A.elements;return this.x=n[0]*t+n[3]*e+n[6]*i,this.y=n[1]*t+n[4]*e+n[7]*i,this.z=n[2]*t+n[5]*e+n[8]*i,this}applyNormalMatrix(A){return this.applyMatrix3(A).normalize()}applyMatrix4(A){const t=this.x,e=this.y,i=this.z,n=A.elements,r=1/(n[3]*t+n[7]*e+n[11]*i+n[15]);return this.x=(n[0]*t+n[4]*e+n[8]*i+n[12])*r,this.y=(n[1]*t+n[5]*e+n[9]*i+n[13])*r,this.z=(n[2]*t+n[6]*e+n[10]*i+n[14])*r,this}applyQuaternion(A){const t=this.x,e=this.y,i=this.z,n=A.x,r=A.y,g=A.z,I=A.w,a=2*(r*i-g*e),o=2*(g*t-n*i),C=2*(n*e-r*t);return this.x=t+I*a+r*C-g*o,this.y=e+I*o+g*a-n*C,this.z=i+I*C+n*o-r*a,this}project(A){return this.applyMatrix4(A.matrixWorldInverse).applyMatrix4(A.projectionMatrix)}unproject(A){return this.applyMatrix4(A.projectionMatrixInverse).applyMatrix4(A.matrixWorld)}transformDirection(A){const t=this.x,e=this.y,i=this.z,n=A.elements;return this.x=n[0]*t+n[4]*e+n[8]*i,this.y=n[1]*t+n[5]*e+n[9]*i,this.z=n[2]*t+n[6]*e+n[10]*i,this.normalize()}divide(A){return this.x/=A.x,this.y/=A.y,this.z/=A.z,this}divideScalar(A){return this.multiplyScalar(1/A)}min(A){return this.x=Math.min(this.x,A.x),this.y=Math.min(this.y,A.y),this.z=Math.min(this.z,A.z),this}max(A){return this.x=Math.max(this.x,A.x),this.y=Math.max(this.y,A.y),this.z=Math.max(this.z,A.z),this}clamp(A,t){return this.x=IA(this.x,A.x,t.x),this.y=IA(this.y,A.y,t.y),this.z=IA(this.z,A.z,t.z),this}clampScalar(A,t){return this.x=IA(this.x,A,t),this.y=IA(this.y,A,t),this.z=IA(this.z,A,t),this}clampLength(A,t){const e=this.length();return this.divideScalar(e||1).multiplyScalar(IA(e,A,t))}floor(){return this.x=Math.floor(this.x),this.y=Math.floor(this.y),this.z=Math.floor(this.z),this}ceil(){return this.x=Math.ceil(this.x),this.y=Math.ceil(this.y),this.z=Math.ceil(this.z),this}round(){return this.x=Math.round(this.x),this.y=Math.round(this.y),this.z=Math.round(this.z),this}roundToZero(){return this.x=Math.trunc(this.x),this.y=Math.trunc(this.y),this.z=Math.trunc(this.z),this}negate(){return this.x=-this.x,this.y=-this.y,this.z=-this.z,this}dot(A){return this.x*A.x+this.y*A.y+this.z*A.z}lengthSq(){return this.x*this.x+this.y*this.y+this.z*this.z}length(){return Math.sqrt(this.x*this.x+this.y*this.y+this.z*this.z)}manhattanLength(){return Math.abs(this.x)+Math.abs(this.y)+Math.abs(this.z)}normalize(){return this.divideScalar(this.length()||1)}setLength(A){return this.normalize().multiplyScalar(A)}lerp(A,t){return this.x+=(A.x-this.x)*t,this.y+=(A.y-this.y)*t,this.z+=(A.z-this.z)*t,this}lerpVectors(A,t,e){return this.x=A.x+(t.x-A.x)*e,this.y=A.y+(t.y-A.y)*e,this.z=A.z+(t.z-A.z)*e,this}cross(A){return this.crossVectors(this,A)}crossVectors(A,t){const e=A.x,i=A.y,n=A.z,r=t.x,g=t.y,I=t.z;return this.x=i*I-n*g,this.y=n*r-e*I,this.z=e*g-i*r,this}projectOnVector(A){const t=A.lengthSq();if(t===0)return this.set(0,0,0);const e=A.dot(this)/t;return this.copy(A).multiplyScalar(e)}projectOnPlane(A){return Jt.copy(this).projectOnVector(A),this.sub(Jt)}reflect(A){return this.sub(Jt.copy(A).multiplyScalar(2*this.dot(A)))}angleTo(A){const t=Math.sqrt(this.lengthSq()*A.lengthSq());if(t===0)return Math.PI/2;const e=this.dot(A)/t;return Math.acos(IA(e,-1,1))}distanceTo(A){return Math.sqrt(this.distanceToSquared(A))}distanceToSquared(A){const t=this.x-A.x,e=this.y-A.y,i=this.z-A.z;return t*t+e*e+i*i}manhattanDistanceTo(A){return Math.abs(this.x-A.x)+Math.abs(this.y-A.y)+Math.abs(this.z-A.z)}setFromSpherical(A){return this.setFromSphericalCoords(A.radius,A.phi,A.theta)}setFromSphericalCoords(A,t,e){const i=Math.sin(t)*A;return this.x=i*Math.sin(e),this.y=Math.cos(t)*A,this.z=i*Math.cos(e),this}setFromCylindrical(A){return this.setFromCylindricalCoords(A.radius,A.theta,A.y)}setFromCylindricalCoords(A,t,e){return this.x=A*Math.sin(t),this.y=e,this.z=A*Math.cos(t),this}setFromMatrixPosition(A){const t=A.elements;return this.x=t[12],this.y=t[13],this.z=t[14],this}setFromMatrixScale(A){const t=this.setFromMatrixColumn(A,0).length(),e=this.setFromMatrixColumn(A,1).length(),i=this.setFromMatrixColumn(A,2).length();return this.x=t,this.y=e,this.z=i,this}setFromMatrixColumn(A,t){return this.fromArray(A.elements,t*4)}setFromMatrix3Column(A,t){return this.fromArray(A.elements,t*3)}setFromEuler(A){return this.x=A._x,this.y=A._y,this.z=A._z,this}setFromColor(A){return this.x=A.r,this.y=A.g,this.z=A.b,this}equals(A){return A.x===this.x&&A.y===this.y&&A.z===this.z}fromArray(A,t=0){return this.x=A[t],this.y=A[t+1],this.z=A[t+2],this}toArray(A=[],t=0){return A[t]=this.x,A[t+1]=this.y,A[t+2]=this.z,A}fromBufferAttribute(A,t){return this.x=A.getX(t),this.y=A.getY(t),this.z=A.getZ(t),this}random(){return this.x=Math.random(),this.y=Math.random(),this.z=Math.random(),this}randomDirection(){const A=Math.random()*Math.PI*2,t=Math.random()*2-1,e=Math.sqrt(1-t*t);return this.x=e*Math.cos(A),this.y=t,this.z=e*Math.sin(A),this}*[Symbol.iterator](){yield this.x,yield this.y,yield this.z}}const Jt=new k,Me=new kA;class At{constructor(A,t,e,i,n,r,g,I,a){At.prototype.isMatrix3=!0,this.elements=[1,0,0,0,1,0,0,0,1],A!==void 0&&this.set(A,t,e,i,n,r,g,I,a)}set(A,t,e,i,n,r,g,I,a){const o=this.elements;return o[0]=A,o[1]=i,o[2]=g,o[3]=t,o[4]=n,o[5]=I,o[6]=e,o[7]=r,o[8]=a,this}identity(){return this.set(1,0,0,0,1,0,0,0,1),this}copy(A){const t=this.elements,e=A.elements;return t[0]=e[0],t[1]=e[1],t[2]=e[2],t[3]=e[3],t[4]=e[4],t[5]=e[5],t[6]=e[6],t[7]=e[7],t[8]=e[8],this}extractBasis(A,t,e){return A.setFromMatrix3Column(this,0),t.setFromMatrix3Column(this,1),e.setFromMatrix3Column(this,2),this}setFromMatrix4(A){const t=A.elements;return this.set(t[0],t[4],t[8],t[1],t[5],t[9],t[2],t[6],t[10]),this}multiply(A){return this.multiplyMatrices(this,A)}premultiply(A){return this.multiplyMatrices(A,this)}multiplyMatrices(A,t){const e=A.elements,i=t.elements,n=this.elements,r=e[0],g=e[3],I=e[6],a=e[1],o=e[4],C=e[7],h=e[2],B=e[5],Q=e[8],u=i[0],l=i[3],E=i[6],f=i[1],c=i[4],y=i[7],p=i[2],d=i[5],z=i[8];return n[0]=r*u+g*f+I*p,n[3]=r*l+g*c+I*d,n[6]=r*E+g*y+I*z,n[1]=a*u+o*f+C*p,n[4]=a*l+o*c+C*d,n[7]=a*E+o*y+C*z,n[2]=h*u+B*f+Q*p,n[5]=h*l+B*c+Q*d,n[8]=h*E+B*y+Q*z,this}multiplyScalar(A){const t=this.elements;return t[0]*=A,t[3]*=A,t[6]*=A,t[1]*=A,t[4]*=A,t[7]*=A,t[2]*=A,t[5]*=A,t[8]*=A,this}determinant(){const A=this.elements,t=A[0],e=A[1],i=A[2],n=A[3],r=A[4],g=A[5],I=A[6],a=A[7],o=A[8];return t*r*o-t*g*a-e*n*o+e*g*I+i*n*a-i*r*I}invert(){const A=this.elements,t=A[0],e=A[1],i=A[2],n=A[3],r=A[4],g=A[5],I=A[6],a=A[7],o=A[8],C=o*r-g*a,h=g*I-o*n,B=a*n-r*I,Q=t*C+e*h+i*B;if(Q===0)return this.set(0,0,0,0,0,0,0,0,0);const u=1/Q;return A[0]=C*u,A[1]=(i*a-o*e)*u,A[2]=(g*e-i*r)*u,A[3]=h*u,A[4]=(o*t-i*I)*u,A[5]=(i*n-g*t)*u,A[6]=B*u,A[7]=(e*I-a*t)*u,A[8]=(r*t-e*n)*u,this}transpose(){let A;const t=this.elements;return A=t[1],t[1]=t[3],t[3]=A,A=t[2],t[2]=t[6],t[6]=A,A=t[5],t[5]=t[7],t[7]=A,this}getNormalMatrix(A){return this.setFromMatrix4(A).invert().transpose()}transposeIntoArray(A){const t=this.elements;return A[0]=t[0],A[1]=t[3],A[2]=t[6],A[3]=t[1],A[4]=t[4],A[5]=t[7],A[6]=t[2],A[7]=t[5],A[8]=t[8],this}setUvTransform(A,t,e,i,n,r,g){const I=Math.cos(n),a=Math.sin(n);return this.set(e*I,e*a,-e*(I*r+a*g)+r+A,-i*a,i*I,-i*(-a*r+I*g)+g+t,0,0,1),this}scale(A,t){return this.premultiply(zt.makeScale(A,t)),this}rotate(A){return this.premultiply(zt.makeRotation(-A)),this}translate(A,t){return this.premultiply(zt.makeTranslation(A,t)),this}makeTranslation(A,t){return A.isVector2?this.set(1,0,A.x,0,1,A.y,0,0,1):this.set(1,0,A,0,1,t,0,0,1),this}makeRotation(A){const t=Math.cos(A),e=Math.sin(A);return this.set(t,-e,0,e,t,0,0,0,1),this}makeScale(A,t){return this.set(A,0,0,0,t,0,0,0,1),this}equals(A){const t=this.elements,e=A.elements;for(let i=0;i<9;i++)if(t[i]!==e[i])return!1;return!0}fromArray(A,t=0){for(let e=0;e<9;e++)this.elements[e]=A[e+t];return this}toArray(A=[],t=0){const e=this.elements;return A[t]=e[0],A[t+1]=e[1],A[t+2]=e[2],A[t+3]=e[3],A[t+4]=e[4],A[t+5]=e[5],A[t+6]=e[6],A[t+7]=e[7],A[t+8]=e[8],A}clone(){return new this.constructor().fromArray(this.elements)}}const zt=new At,Fe={};function de(s){s in Fe||(Fe[s]=!0,console.warn(s))}const Ne=new At().set(.4123908,.3575843,.1804808,.212639,.7151687,.0721923,.0193308,.1191948,.9505322),ke=new At().set(3.2409699,-1.5373832,-.4986108,-.9692436,1.8759675,.0415551,.0556301,-.203977,1.0569715);function Ns(){const s={enabled:!0,workingColorSpace:Se,spaces:{},convert:function(i,n,r){return this.enabled===!1||n===r||!n||!r||(this.spaces[n].transfer===Rt&&(i.r=ZA(i.r),i.g=ZA(i.g),i.b=ZA(i.b)),this.spaces[n].primaries!==this.spaces[r].primaries&&(i.applyMatrix3(this.spaces[n].toXYZ),i.applyMatrix3(this.spaces[r].fromXYZ)),this.spaces[r].transfer===Rt&&(i.r=TA(i.r),i.g=TA(i.g),i.b=TA(i.b))),i},workingToColorSpace:function(i,n){return this.convert(i,this.workingColorSpace,n)},colorSpaceToWorking:function(i,n){return this.convert(i,n,this.workingColorSpace)},getPrimaries:function(i){return this.spaces[i].primaries},getTransfer:function(i){return i===Fs?xe:this.spaces[i].transfer},getLuminanceCoefficients:function(i,n=this.workingColorSpace){return i.fromArray(this.spaces[n].luminanceCoefficients)},define:function(i){Object.assign(this.spaces,i)},_getMatrix:function(i,n,r){return i.copy(this.spaces[n].toXYZ).multiply(this.spaces[r].fromXYZ)},_getDrawingBufferColorSpace:function(i){return this.spaces[i].outputColorSpaceConfig.drawingBufferColorSpace},_getUnpackColorSpace:function(i=this.workingColorSpace){return this.spaces[i].workingColorSpaceConfig.unpackColorSpace},fromWorkingColorSpace:function(i,n){return de("THREE.ColorManagement: .fromWorkingColorSpace() has been renamed to .workingToColorSpace()."),s.workingToColorSpace(i,n)},toWorkingColorSpace:function(i,n){return de("THREE.ColorManagement: .toWorkingColorSpace() has been renamed to .colorSpaceToWorking()."),s.colorSpaceToWorking(i,n)}},A=[.64,.33,.3,.6,.15,.06],t=[.2126,.7152,.0722],e=[.3127,.329];return s.define({[Se]:{primaries:A,whitePoint:e,transfer:xe,toXYZ:Ne,fromXYZ:ke,luminanceCoefficients:t,workingColorSpaceConfig:{unpackColorSpace:yA},outputColorSpaceConfig:{drawingBufferColorSpace:yA}},[yA]:{primaries:A,whitePoint:e,transfer:Rt,toXYZ:Ne,fromXYZ:ke,luminanceCoefficients:t,outputColorSpaceConfig:{drawingBufferColorSpace:yA}}}),s}const fA=Ns();function ZA(s){return s<.04045?s*.0773993808:Math.pow(s*.9478672986+.0521327014,2.4)}function TA(s){return s<.0031308?s*12.92:1.055*Math.pow(s,.41666)-.055}class Ge{constructor(A=new k(1/0,1/0,1/0),t=new k(-1/0,-1/0,-1/0)){this.isBox3=!0,this.min=A,this.max=t}set(A,t){return this.min.copy(A),this.max.copy(t),this}setFromArray(A){this.makeEmpty();for(let t=0,e=A.length;t<e;t+=3)this.expandByPoint(wA.fromArray(A,t));return this}setFromBufferAttribute(A){this.makeEmpty();for(let t=0,e=A.count;t<e;t++)this.expandByPoint(wA.fromBufferAttribute(A,t));return this}setFromPoints(A){this.makeEmpty();for(let t=0,e=A.length;t<e;t++)this.expandByPoint(A[t]);return this}setFromCenterAndSize(A,t){const e=wA.copy(t).multiplyScalar(.5);return this.min.copy(A).sub(e),this.max.copy(A).add(e),this}setFromObject(A,t=!1){return this.makeEmpty(),this.expandByObject(A,t)}clone(){return new this.constructor().copy(this)}copy(A){return this.min.copy(A.min),this.max.copy(A.max),this}makeEmpty(){return this.min.x=this.min.y=this.min.z=1/0,this.max.x=this.max.y=this.max.z=-1/0,this}isEmpty(){return this.max.x<this.min.x||this.max.y<this.min.y||this.max.z<this.min.z}getCenter(A){return this.isEmpty()?A.set(0,0,0):A.addVectors(this.min,this.max).multiplyScalar(.5)}getSize(A){return this.isEmpty()?A.set(0,0,0):A.subVectors(this.max,this.min)}expandByPoint(A){return this.min.min(A),this.max.max(A),this}expandByVector(A){return this.min.sub(A),this.max.add(A),this}expandByScalar(A){return this.min.addScalar(-A),this.max.addScalar(A),this}expandByObject(A,t=!1){A.updateWorldMatrix(!1,!1);const e=A.geometry;if(e!==void 0){const n=e.getAttribute("position");if(t===!0&&n!==void 0&&A.isInstancedMesh!==!0)for(let r=0,g=n.count;r<g;r++)A.isMesh===!0?A.getVertexPosition(r,wA):wA.fromBufferAttribute(n,r),wA.applyMatrix4(A.matrixWorld),this.expandByPoint(wA);else A.boundingBox!==void 0?(A.boundingBox===null&&A.computeBoundingBox(),ht.copy(A.boundingBox)):(e.boundingBox===null&&e.computeBoundingBox(),ht.copy(e.boundingBox)),ht.applyMatrix4(A.matrixWorld),this.union(ht)}const i=A.children;for(let n=0,r=i.length;n<r;n++)this.expandByObject(i[n],t);return this}containsPoint(A){return A.x>=this.min.x&&A.x<=this.max.x&&A.y>=this.min.y&&A.y<=this.max.y&&A.z>=this.min.z&&A.z<=this.max.z}containsBox(A){return this.min.x<=A.min.x&&A.max.x<=this.max.x&&this.min.y<=A.min.y&&A.max.y<=this.max.y&&this.min.z<=A.min.z&&A.max.z<=this.max.z}getParameter(A,t){return t.set((A.x-this.min.x)/(this.max.x-this.min.x),(A.y-this.min.y)/(this.max.y-this.min.y),(A.z-this.min.z)/(this.max.z-this.min.z))}intersectsBox(A){return A.max.x>=this.min.x&&A.min.x<=this.max.x&&A.max.y>=this.min.y&&A.min.y<=this.max.y&&A.max.z>=this.min.z&&A.min.z<=this.max.z}intersectsSphere(A){return this.clampPoint(A.center,wA),wA.distanceToSquared(A.center)<=A.radius*A.radius}intersectsPlane(A){let t,e;return A.normal.x>0?(t=A.normal.x*this.min.x,e=A.normal.x*this.max.x):(t=A.normal.x*this.max.x,e=A.normal.x*this.min.x),A.normal.y>0?(t+=A.normal.y*this.min.y,e+=A.normal.y*this.max.y):(t+=A.normal.y*this.max.y,e+=A.normal.y*this.min.y),A.normal.z>0?(t+=A.normal.z*this.min.z,e+=A.normal.z*this.max.z):(t+=A.normal.z*this.max.z,e+=A.normal.z*this.min.z),t<=-A.constant&&e>=-A.constant}intersectsTriangle(A){if(this.isEmpty())return!1;this.getCenter(tt),Qt.subVectors(this.max,tt),qA.subVectors(A.a,tt),KA.subVectors(A.b,tt),XA.subVectors(A.c,tt),GA.subVectors(KA,qA),UA.subVectors(XA,KA),zA.subVectors(qA,XA);let t=[0,-GA.z,GA.y,0,-UA.z,UA.y,0,-zA.z,zA.y,GA.z,0,-GA.x,UA.z,0,-UA.x,zA.z,0,-zA.x,-GA.y,GA.x,0,-UA.y,UA.x,0,-zA.y,zA.x,0];return!Lt(t,qA,KA,XA,Qt)||(t=[1,0,0,0,1,0,0,0,1],!Lt(t,qA,KA,XA,Qt))?!1:(Et.crossVectors(GA,UA),t=[Et.x,Et.y,Et.z],Lt(t,qA,KA,XA,Qt))}clampPoint(A,t){return t.copy(A).clamp(this.min,this.max)}distanceToPoint(A){return this.clampPoint(A,wA).distanceTo(A)}getBoundingSphere(A){return this.isEmpty()?A.makeEmpty():(this.getCenter(A.center),A.radius=this.getSize(wA).length()*.5),A}intersect(A){return this.min.max(A.min),this.max.min(A.max),this.isEmpty()&&this.makeEmpty(),this}union(A){return this.min.min(A.min),this.max.max(A.max),this}applyMatrix4(A){return this.isEmpty()?this:(MA[0].set(this.min.x,this.min.y,this.min.z).applyMatrix4(A),MA[1].set(this.min.x,this.min.y,this.max.z).applyMatrix4(A),MA[2].set(this.min.x,this.max.y,this.min.z).applyMatrix4(A),MA[3].set(this.min.x,this.max.y,this.max.z).applyMatrix4(A),MA[4].set(this.max.x,this.min.y,this.min.z).applyMatrix4(A),MA[5].set(this.max.x,this.min.y,this.max.z).applyMatrix4(A),MA[6].set(this.max.x,this.max.y,this.min.z).applyMatrix4(A),MA[7].set(this.max.x,this.max.y,this.max.z).applyMatrix4(A),this.setFromPoints(MA),this)}translate(A){return this.min.add(A),this.max.add(A),this}equals(A){return A.min.equals(this.min)&&A.max.equals(this.max)}toJSON(){return{min:this.min.toArray(),max:this.max.toArray()}}fromJSON(A){return this.min.fromArray(A.min),this.max.fromArray(A.max),this}}const MA=[new k,new k,new k,new k,new k,new k,new k,new k],wA=new k,ht=new Ge,qA=new k,KA=new k,XA=new k,GA=new k,UA=new k,zA=new k,tt=new k,Qt=new k,Et=new k,LA=new k;function Lt(s,A,t,e,i){for(let n=0,r=s.length-3;n<=r;n+=3){LA.fromArray(s,n);const g=i.x*Math.abs(LA.x)+i.y*Math.abs(LA.y)+i.z*Math.abs(LA.z),I=A.dot(LA),a=t.dot(LA),o=e.dot(LA);if(Math.max(-Math.max(I,a,o),Math.min(I,a,o))>g)return!1}return!0}const Ue={aliceblue:15792383,antiquewhite:16444375,aqua:65535,aquamarine:8388564,azure:15794175,beige:16119260,bisque:16770244,black:0,blanchedalmond:16772045,blue:255,blueviolet:9055202,brown:10824234,burlywood:14596231,cadetblue:6266528,chartreuse:8388352,chocolate:13789470,coral:16744272,cornflowerblue:6591981,cornsilk:16775388,crimson:14423100,cyan:65535,darkblue:139,darkcyan:35723,darkgoldenrod:12092939,darkgray:11119017,darkgreen:25600,darkgrey:11119017,darkkhaki:12433259,darkmagenta:9109643,darkolivegreen:5597999,darkorange:16747520,darkorchid:10040012,darkred:9109504,darksalmon:15308410,darkseagreen:9419919,darkslateblue:4734347,darkslategray:3100495,darkslategrey:3100495,darkturquoise:52945,darkviolet:9699539,deeppink:16716947,deepskyblue:49151,dimgray:6908265,dimgrey:6908265,dodgerblue:2003199,firebrick:11674146,floralwhite:16775920,forestgreen:2263842,fuchsia:16711935,gainsboro:14474460,ghostwhite:16316671,gold:16766720,goldenrod:14329120,gray:8421504,green:32768,greenyellow:11403055,grey:8421504,honeydew:15794160,hotpink:16738740,indianred:13458524,indigo:4915330,ivory:16777200,khaki:15787660,lavender:15132410,lavenderblush:16773365,lawngreen:8190976,lemonchiffon:16775885,lightblue:11393254,lightcoral:15761536,lightcyan:14745599,lightgoldenrodyellow:16448210,lightgray:13882323,lightgreen:9498256,lightgrey:13882323,lightpink:16758465,lightsalmon:16752762,lightseagreen:2142890,lightskyblue:8900346,lightslategray:7833753,lightslategrey:7833753,lightsteelblue:11584734,lightyellow:16777184,lime:65280,limegreen:3329330,linen:16445670,magenta:16711935,maroon:8388608,mediumaquamarine:6737322,mediumblue:205,mediumorchid:12211667,mediumpurple:9662683,mediumseagreen:3978097,mediumslateblue:8087790,mediumspringgreen:64154,mediumturquoise:4772300,mediumvioletred:13047173,midnightblue:1644912,mintcream:16121850,mistyrose:16770273,moccasin:16770229,navajowhite:16768685,navy:128,oldlace:16643558,olive:8421376,olivedrab:7048739,orange:16753920,orangered:16729344,orchid:14315734,palegoldenrod:15657130,palegreen:10025880,paleturquoise:11529966,palevioletred:14381203,papayawhip:16773077,peachpuff:16767673,peru:13468991,pink:16761035,plum:14524637,powderblue:11591910,purple:8388736,rebeccapurple:6697881,red:16711680,rosybrown:12357519,royalblue:4286945,saddlebrown:9127187,salmon:16416882,sandybrown:16032864,seagreen:3050327,seashell:16774638,sienna:10506797,silver:12632256,skyblue:8900331,slateblue:6970061,slategray:7372944,slategrey:7372944,snow:16775930,springgreen:65407,steelblue:4620980,tan:13808780,teal:32896,thistle:14204888,tomato:16737095,turquoise:4251856,violet:15631086,wheat:16113331,white:16777215,whitesmoke:16119285,yellow:16776960,yellowgreen:10145074},YA={h:0,s:0,l:0},ct={h:0,s:0,l:0};function Ht(s,A,t){return t<0&&(t+=1),t>1&&(t-=1),t<1/6?s+(A-s)*6*t:t<1/2?A:t<2/3?s+(A-s)*6*(2/3-t):s}class vt{constructor(A,t,e){return this.isColor=!0,this.r=1,this.g=1,this.b=1,this.set(A,t,e)}set(A,t,e){if(t===void 0&&e===void 0){const i=A;i&&i.isColor?this.copy(i):typeof i=="number"?this.setHex(i):typeof i=="string"&&this.setStyle(i)}else this.setRGB(A,t,e);return this}setScalar(A){return this.r=A,this.g=A,this.b=A,this}setHex(A,t=yA){return A=Math.floor(A),this.r=(A>>16&255)/255,this.g=(A>>8&255)/255,this.b=(A&255)/255,fA.colorSpaceToWorking(this,t),this}setRGB(A,t,e,i=fA.workingColorSpace){return this.r=A,this.g=t,this.b=e,fA.colorSpaceToWorking(this,i),this}setHSL(A,t,e,i=fA.workingColorSpace){if(A=ds(A,1),t=IA(t,0,1),e=IA(e,0,1),t===0)this.r=this.g=this.b=e;else{const n=e<=.5?e*(1+t):e+t-e*t,r=2*e-n;this.r=Ht(r,n,A+1/3),this.g=Ht(r,n,A),this.b=Ht(r,n,A-1/3)}return fA.colorSpaceToWorking(this,i),this}setStyle(A,t=yA){function e(n){n!==void 0&&parseFloat(n)<1&&console.warn("THREE.Color: Alpha component of "+A+" will be ignored.")}let i;if(i=/^(\\w+)\\(([^\\)]*)\\)/.exec(A)){let n;const r=i[1],g=i[2];switch(r){case"rgb":case"rgba":if(n=/^\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*(\\d+)\\s*(?:,\\s*(\\d*\\.?\\d+)\\s*)?$/.exec(g))return e(n[4]),this.setRGB(Math.min(255,parseInt(n[1],10))/255,Math.min(255,parseInt(n[2],10))/255,Math.min(255,parseInt(n[3],10))/255,t);if(n=/^\\s*(\\d+)\\%\\s*,\\s*(\\d+)\\%\\s*,\\s*(\\d+)\\%\\s*(?:,\\s*(\\d*\\.?\\d+)\\s*)?$/.exec(g))return e(n[4]),this.setRGB(Math.min(100,parseInt(n[1],10))/100,Math.min(100,parseInt(n[2],10))/100,Math.min(100,parseInt(n[3],10))/100,t);break;case"hsl":case"hsla":if(n=/^\\s*(\\d*\\.?\\d+)\\s*,\\s*(\\d*\\.?\\d+)\\%\\s*,\\s*(\\d*\\.?\\d+)\\%\\s*(?:,\\s*(\\d*\\.?\\d+)\\s*)?$/.exec(g))return e(n[4]),this.setHSL(parseFloat(n[1])/360,parseFloat(n[2])/100,parseFloat(n[3])/100,t);break;default:console.warn("THREE.Color: Unknown color model "+A)}}else if(i=/^\\#([A-Fa-f\\d]+)$/.exec(A)){const n=i[1],r=n.length;if(r===3)return this.setRGB(parseInt(n.charAt(0),16)/15,parseInt(n.charAt(1),16)/15,parseInt(n.charAt(2),16)/15,t);if(r===6)return this.setHex(parseInt(n,16),t);console.warn("THREE.Color: Invalid hex color "+A)}else if(A&&A.length>0)return this.setColorName(A,t);return this}setColorName(A,t=yA){const e=Ue[A.toLowerCase()];return e!==void 0?this.setHex(e,t):console.warn("THREE.Color: Unknown color "+A),this}clone(){return new this.constructor(this.r,this.g,this.b)}copy(A){return this.r=A.r,this.g=A.g,this.b=A.b,this}copySRGBToLinear(A){return this.r=ZA(A.r),this.g=ZA(A.g),this.b=ZA(A.b),this}copyLinearToSRGB(A){return this.r=TA(A.r),this.g=TA(A.g),this.b=TA(A.b),this}convertSRGBToLinear(){return this.copySRGBToLinear(this),this}convertLinearToSRGB(){return this.copyLinearToSRGB(this),this}getHex(A=yA){return fA.workingToColorSpace(eA.copy(this),A),Math.round(IA(eA.r*255,0,255))*65536+Math.round(IA(eA.g*255,0,255))*256+Math.round(IA(eA.b*255,0,255))}getHexString(A=yA){return("000000"+this.getHex(A).toString(16)).slice(-6)}getHSL(A,t=fA.workingColorSpace){fA.workingToColorSpace(eA.copy(this),t);const e=eA.r,i=eA.g,n=eA.b,r=Math.max(e,i,n),g=Math.min(e,i,n);let I,a;const o=(g+r)/2;if(g===r)I=0,a=0;else{const C=r-g;switch(a=o<=.5?C/(r+g):C/(2-r-g),r){case e:I=(i-n)/C+(i<n?6:0);break;case i:I=(n-e)/C+2;break;case n:I=(e-i)/C+4;break}I/=6}return A.h=I,A.s=a,A.l=o,A}getRGB(A,t=fA.workingColorSpace){return fA.workingToColorSpace(eA.copy(this),t),A.r=eA.r,A.g=eA.g,A.b=eA.b,A}getStyle(A=yA){fA.workingToColorSpace(eA.copy(this),A);const t=eA.r,e=eA.g,i=eA.b;return A!==yA?`color(${A} ${t.toFixed(3)} ${e.toFixed(3)} ${i.toFixed(3)})`:`rgb(${Math.round(t*255)},${Math.round(e*255)},${Math.round(i*255)})`}offsetHSL(A,t,e){return this.getHSL(YA),this.setHSL(YA.h+A,YA.s+t,YA.l+e)}add(A){return this.r+=A.r,this.g+=A.g,this.b+=A.b,this}addColors(A,t){return this.r=A.r+t.r,this.g=A.g+t.g,this.b=A.b+t.b,this}addScalar(A){return this.r+=A,this.g+=A,this.b+=A,this}sub(A){return this.r=Math.max(0,this.r-A.r),this.g=Math.max(0,this.g-A.g),this.b=Math.max(0,this.b-A.b),this}multiply(A){return this.r*=A.r,this.g*=A.g,this.b*=A.b,this}multiplyScalar(A){return this.r*=A,this.g*=A,this.b*=A,this}lerp(A,t){return this.r+=(A.r-this.r)*t,this.g+=(A.g-this.g)*t,this.b+=(A.b-this.b)*t,this}lerpColors(A,t,e){return this.r=A.r+(t.r-A.r)*e,this.g=A.g+(t.g-A.g)*e,this.b=A.b+(t.b-A.b)*e,this}lerpHSL(A,t){this.getHSL(YA),A.getHSL(ct);const e=_t(YA.h,ct.h,t),i=_t(YA.s,ct.s,t),n=_t(YA.l,ct.l,t);return this.setHSL(e,i,n),this}setFromVector3(A){return this.r=A.x,this.g=A.y,this.b=A.z,this}applyMatrix3(A){const t=this.r,e=this.g,i=this.b,n=A.elements;return this.r=n[0]*t+n[3]*e+n[6]*i,this.g=n[1]*t+n[4]*e+n[7]*i,this.b=n[2]*t+n[5]*e+n[8]*i,this}equals(A){return A.r===this.r&&A.g===this.g&&A.b===this.b}fromArray(A,t=0){return this.r=A[t],this.g=A[t+1],this.b=A[t+2],this}toArray(A=[],t=0){return A[t]=this.r,A[t+1]=this.g,A[t+2]=this.b,A}fromBufferAttribute(A,t){return this.r=A.getX(t),this.g=A.getY(t),this.b=A.getZ(t),this}toJSON(){return this.getHex()}*[Symbol.iterator](){yield this.r,yield this.g,yield this.b}}const eA=new vt;vt.NAMES=Ue,typeof __THREE_DEVTOOLS__<"u"&&__THREE_DEVTOOLS__.dispatchEvent(new CustomEvent("register",{detail:{revision:De}})),typeof window<"u"&&(window.__THREE__?console.warn("WARNING: Multiple instances of Three.js being imported."):window.__THREE__=De);const Ye=-12,be=9,PA=Math.exp(-30),ks=11,Gs=11,Re=1<<ks,_e=1<<Gs,Je=1;function Us(s){var n;let A=!1;const t=s.split(`\n`).map(r=>{const g=r.trimEnd();return A?g:g.length>0?(A=!0,g):null}).filter(r=>r!=null);for(;t.length>0&&t[t.length-1].length===0;)t.pop();if(t.length===0)return[];const e=(n=t[0].match(/^\\s*/))==null?void 0:n[0];if(!e)return t;const i=new RegExp(`^${e}`);return t.map(r=>r.replace(i,""))}function Ys(s){return Us(s).join(`\n`)}const Zt=new Float32Array(1),ze=new Uint32Array(Zt.buffer),Tt="Float16Array"in globalThis,et=Tt?new globalThis.Float16Array(1):null,Le=new Uint16Array(et==null?void 0:et.buffer);function bs(s){const A=Math.sqrt(s.reduce((t,e)=>t+e*e,0));return s.map(t=>t/A)}const WA=Tt?Rs:_s,$=Tt?Js:zs;function Rs(s){return et[0]=s,Le[0]}function _s(s){Zt[0]=s;const A=ze[0],t=A>>31&1,e=A>>23&255,i=A&8388607,n=t<<15;if(e===255)return i!==0?n|32767:n|31744;const r=e-127+15;if(r>=31)return n|31744;if(r<=0){if(r<-10)return n;const I=(i|8388608)>>1-r+13;return n|I}const g=i>>13;return n|r<<10|g}function Js(s){return Le[0]=s,et[0]}function zs(s){const A=s>>15&1,t=s>>10&31,e=s&1023;let i;if(t===0)if(e===0)i=A<<31;else{let n=e,r=-14;for(;(n&1024)===0;)n<<=1,r--;n&=1023;const g=r+127,I=n<<13;i=A<<31|g<<23|I}else if(t===31)e===0?i=A<<31|2139095040:i=A<<31|2143289344;else{const n=t-15+127,r=e<<13;i=A<<31|n<<23|r}return ze[0]=i,Zt[0]}function QA(s){return Math.max(0,Math.min(255,Math.round(s*255)))}function Ls(s){const A=[],t=new Set;function e(i){i&&typeof i=="object"&&!t.has(i)&&(t.add(i),i instanceof ArrayBuffer?A.push(i):ArrayBuffer.isView(i)?A.push(i.buffer):Array.isArray(i)?i.forEach(e):Object.values(i).forEach(e))}return e(s),A}function qt(s,A,t,e,i,n,r,g,I,a,o,C,h,B,Q,u,l){const E=(l==null?void 0:l.rgbMin)??0,c=((l==null?void 0:l.rgbMax)??1)-E,y=QA((B-E)/c),p=QA((Q-E)/c),d=QA((u-E)/c),z=QA(h),m=Ke(Ze.set(I,a,o,C)),w=m&255,G=m>>>8&255,S=m>>>16&255,D=(l==null?void 0:l.lnScaleMin)??Ye,M=254/(((l==null?void 0:l.lnScaleMax)??be)-D),x=n<PA?0:Math.min(255,Math.max(1,Math.round((Math.log(n)-D)*M)+1)),U=r<PA?0:Math.min(255,Math.max(1,Math.round((Math.log(r)-D)*M)+1)),v=g<PA?0:Math.min(255,Math.max(1,Math.round((Math.log(g)-D)*M)+1)),q=WA(t),Z=WA(e),W=WA(i),K=A*4;s[K]=y|p<<8|d<<16|z<<24,s[K+1]=q|Z<<16,s[K+2]=W|w<<16|G<<24,s[K+3]=x|U<<8|v<<16|S<<24}function He(s,A,t,e,i){const n=WA(t),r=WA(e),g=WA(i),I=A*4;s[I+1]=n|r<<16,s[I+2]=g|s[I+2]&4294901760}function ve(s,A,t,e,i,n){const r=(n==null?void 0:n.lnScaleMin)??Ye,I=254/(((n==null?void 0:n.lnScaleMax)??be)-r),a=t<PA?0:Math.min(255,Math.max(1,Math.round((Math.log(t)-r)*I)+1)),o=e<PA?0:Math.min(255,Math.max(1,Math.round((Math.log(e)-r)*I)+1)),C=i<PA?0:Math.min(255,Math.max(1,Math.round((Math.log(i)-r)*I)+1)),h=A*4;s[h+3]=a|o<<8|C<<16|s[h+3]&4278190080}const Ze=new kA;function Te(s,A,t,e,i,n){const r=Ke(Ze.set(t,e,i,n)),g=r&255,I=r>>>8&255,a=r>>>16&255,o=A*4;s[o+2]=s[o+2]&65535|g<<16|I<<24,s[o+3]=s[o+3]&16777215|a<<24}function Hs(s,A,t,e,i,n,r){const g=(r==null?void 0:r.rgbMin)??0,a=((r==null?void 0:r.rgbMax)??1)-g,o=QA((t-g)/a),C=QA((e-g)/a),h=QA((i-g)/a),B=QA(n),Q=A*4;s[Q]=o|C<<8|h<<16|B<<24}function vs(s,A,t,e,i,n){const r=(n==null?void 0:n.rgbMin)??0,I=((n==null?void 0:n.rgbMax)??1)-r,a=QA((t-r)/I),o=QA((e-r)/I),C=QA((i-r)/I),h=A*4;s[h]=a|o<<8|C<<16|s[h]&4278190080}function Zs(s,A,t){const e=QA(t),i=A*4;s[i]=s[i]&16777215|e<<24}new k,new k,new vt;function Ts(s){const A=Re,t=Math.max(Je,Math.min(_e,Math.ceil(s/A))),e=Math.ceil(s/(A*t)),i=A*t*e;return{width:A,height:t,depth:e,maxSplats:i}}function lt(s){const A=Re,t=Math.max(Je,Math.min(_e,Math.ceil(s/A))),e=Math.ceil(s/(A*t));return A*t*e}Ys(`\n precision highp float;\n\n in vec3 position;\n\n void main() {\n gl_Position = vec4(position.xy, 0.0, 1.0);\n }\n`);const qs=new kA,qe=new k;function Ke(s){const A=qs.copy(s).normalize();A.w<0&&A.set(-A.x,-A.y,-A.z,-A.w);const t=2*Math.acos(A.w),e=Math.sqrt(A.x*A.x+A.y*A.y+A.z*A.z),i=e<1e-6?qe.set(1,0,0):qe.set(A.x,A.y,A.z).divideScalar(e),n=Math.abs(i.x)+Math.abs(i.y)+Math.abs(i.z);let r=i.x/n,g=i.y/n;if(i.z<0){const B=r;r=(1-Math.abs(g))*(r>=0?1:-1),g=(1-Math.abs(B))*(g>=0?1:-1)}const I=r*.5+.5,a=g*.5+.5,o=Math.round(I*255),C=Math.round(a*255);return Math.round(t*(255/Math.PI))<<16|C<<8|o}function ut(s,A,t,e){const i=Math.max(-127,Math.min(127,s*127)),n=Math.max(-127,Math.min(127,A*127)),r=Math.max(-127,Math.min(127,t*127)),g=Math.max(-127,Math.min(127,e*127));return i&255|(n&255)<<8|(r&255)<<16|(g&255)<<24}function yt(s,A,t,e){const i=(e==null?void 0:e.sh1Min)??-1,n=(e==null?void 0:e.sh1Max)??1,r=.5*(i+n),g=126/(n-i),I=A*2;for(let a=0;a<9;++a){const o=(t[a]-r)*g,C=Math.round(Math.max(-63,Math.min(63,o)))&127,h=a*7,B=h+7,Q=Math.floor(h/32),u=h-Q*32,l=C<<u&4294967295;if(s[I+Q]|=l,B>Q*32+32){const E=C>>>32-u&4294967295;s[I+Q+1]|=E}}}function ft(s,A,t,e){const i=(e==null?void 0:e.sh2Min)??-1,n=(e==null?void 0:e.sh2Max)??1,r=.5*(i+n),g=2/(n-i);s[A*4+0]=ut((t[0]-r)*g,(t[1]-r)*g,(t[2]-r)*g,(t[3]-r)*g),s[A*4+1]=ut((t[4]-r)*g,(t[5]-r)*g,(t[6]-r)*g,(t[7]-r)*g),s[A*4+2]=ut((t[8]-r)*g,(t[9]-r)*g,(t[10]-r)*g,(t[11]-r)*g),s[A*4+3]=ut((t[12]-r)*g,(t[13]-r)*g,(t[14]-r)*g,0)}function wt(s,A,t,e){const i=(e==null?void 0:e.sh3Min)??-1,n=(e==null?void 0:e.sh3Max)??1,r=.5*(i+n),g=62/(n-i),I=A*4;for(let a=0;a<21;++a){const o=(t[a]-r)*g,C=Math.round(Math.max(-31,Math.min(31,o)))&63,h=a*6,B=h+6,Q=Math.floor(h/32),u=h-Q*32,l=C<<u&4294967295;if(s[I+Q]|=l,B>Q*32+32){const E=C>>>32-u&4294967295;s[I+Q+1]|=E}}}function Ks(s,A){const t=[];let e=0,i=null;const n=new ms((I,a)=>{if(t.push(I),e+=I.length,a||e>=A){const o=new Uint8Array(e);let C=0;for(const h of t)o.set(h,C),C+=h.length;i=o.slice(0,A)}}),r=1024;let g=0;for(;i==null&&g<s.length;){const I=s.slice(g,g+r);n.push(I,!1),g+=r}if(i==null&&(n.push(new Uint8Array,!0),i==null))throw new Error("Failed to decompress partial gzip");return i}class Xs{constructor({fileBytes:A,chunkBytes:t=64*1024}){this.fileBytes=A,this.chunkBytes=t,this.chunks=[],this.totalBytes=0;const e=new DecompressionStream("gzip"),i=new Blob([A]).stream().pipeThrough(e);this.reader=i.getReader()}async read(A){for(;this.totalBytes<A;){const{value:n,done:r}=await this.reader.read();if(r)break;this.chunks.push(n),this.totalBytes+=n.length}if(this.totalBytes<A)throw new Error(`Unexpected EOF: needed ${A}, got ${this.totalBytes}`);const t=new Uint8Array(this.totalBytes);let e=0;for(const n of this.chunks)t.set(n,e),e+=n.length;const i=t.subarray(0,A);return this.chunks=[t.subarray(A)],this.totalBytes-=A,i}}function Xe(s,A,t){const e=Math.floor(s.length/32);if(e*32!==s.length)throw new Error("Invalid .splat file size");A(e);const i=new Float32Array(s.buffer);for(let n=0;n<e;++n){const r=n*32,g=n*8,I=i[g+0],a=i[g+1],o=i[g+2],C=i[g+3],h=i[g+4],B=i[g+5],Q=s[r+24]/255,u=s[r+25]/255,l=s[r+26]/255,E=s[r+27]/255,f=(s[r+28]-128)/128,c=(s[r+29]-128)/128,y=(s[r+30]-128)/128,p=(s[r+31]-128)/128;t(n,I,a,o,C,h,B,c,y,p,f,E,Q,u,l)}}function Ps(s,A){let t=0,e=0,i=new Uint32Array(0);return Xe(s,n=>{t=n,e=lt(t),i=new Uint32Array(e*4)},(n,r,g,I,a,o,C,h,B,Q,u,l,E,f,c)=>{qt(i,n,r,g,I,a,o,C,h,B,Q,u,l,E,f,c,A)}),{packedArray:i,numSplats:t}}const mt={0:{bytesPerCenter:12,bytesPerScale:12,bytesPerRotation:16,bytesPerColor:4,bytesPerSphericalHarmonicsComponent:4,scaleOffsetBytes:12,rotationOffsetBytes:24,colorOffsetBytes:40,sphericalHarmonicsOffsetBytes:44,scaleRange:1},1:{bytesPerCenter:6,bytesPerScale:6,bytesPerRotation:8,bytesPerColor:4,bytesPerSphericalHarmonicsComponent:2,scaleOffsetBytes:6,rotationOffsetBytes:12,colorOffsetBytes:20,sphericalHarmonicsOffsetBytes:24,scaleRange:32767},2:{bytesPerCenter:6,bytesPerScale:6,bytesPerRotation:8,bytesPerColor:4,bytesPerSphericalHarmonicsComponent:1,scaleOffsetBytes:6,rotationOffsetBytes:12,colorOffsetBytes:20,sphericalHarmonicsOffsetBytes:24,scaleRange:32767}},Pe={0:0,1:9,2:24,3:45};function Ws(s,A,t,e){var u;let r=0;const g=new DataView(s.buffer,r,4096);r+=4096;const I=g.getUint8(0),a=g.getUint8(1);if(I!==0||a<1)throw new Error(`Unsupported .ksplat version: ${I}.${a}`);const o=g.getUint32(4,!0);g.getUint32(16,!0);const C=g.getUint16(20,!0);if(C<0||C>2)throw new Error(`Invalid .ksplat compression level: ${C}`);const h=g.getFloat32(36,!0)||-1.5,B=g.getFloat32(40,!0)||1.5;let Q=4096+o*1024;for(let l=0;l<o;++l){let E=function(rA,b){if(C===0)return Y.getFloat32(rA+_+b*4,!0);if(C===1)return $(Y.getUint16(rA+_+b*2,!0));const lA=Y.getUint8(rA+_+b)/255;return h+lA*(B-h)};const f=new DataView(s.buffer,r,1024);r+=1024;const c=f.getUint32(0,!0),y=f.getUint32(4,!0),p=f.getUint32(8,!0),d=f.getUint32(12,!0),z=f.getFloat32(16,!0),m=f.getUint16(20,!0),w=(f.getUint32(24,!0)||((u=mt[C])==null?void 0:u.scaleRange))??1,G=f.getUint32(32,!0),S=G*p,D=f.getUint32(36,!0),F=D*4,M=m*d+F,x=f.getUint16(40,!0),U=Pe[x],{bytesPerCenter:v,bytesPerScale:q,bytesPerRotation:Z,bytesPerColor:W,bytesPerSphericalHarmonicsComponent:K,scaleOffsetBytes:P,rotationOffsetBytes:L,colorOffsetBytes:T,sphericalHarmonicsOffsetBytes:_}=mt[C],R=v+q+Z+W+U*K,N=R*y,sA=N+M,iA=[0,3,6,1,4,7,2,5,8],aA=[9,14,19,10,15,20,11,16,21,12,17,22,13,18,23],gA=[24,31,38,25,32,39,26,33,40,27,34,41,28,35,42,29,36,43,30,37,44],oA=x>=1?new Float32Array(3*3):void 0,CA=x>=2?new Float32Array(5*3):void 0,FA=x>=3?new Float32Array(7*3):void 0,BA=z/2/w,EA=Q+F,cA=Q+M,Y=new DataView(s.buffer,cA,N),nA=new Float32Array(s.buffer,EA,d*3),j=new Uint32Array(s.buffer,Q,D);let H=G,RA=S;for(let rA=0;rA<c;++rA){const b=rA*R;let lA;if(rA<S)lA=Math.floor(rA/p);else{const xA=j[H-G];rA>=RA+xA&&(H+=1,RA+=xA),lA=H}const AA=C===0?Y.getFloat32(b+0,!0):(Y.getUint16(b+0,!0)-w)*BA+nA[3*lA+0],J=C===0?Y.getFloat32(b+4,!0):(Y.getUint16(b+2,!0)-w)*BA+nA[3*lA+1],pA=C===0?Y.getFloat32(b+8,!0):(Y.getUint16(b+4,!0)-w)*BA+nA[3*lA+2],nt=C===0?Y.getFloat32(b+P+0,!0):$(Y.getUint16(b+P+0,!0)),rt=C===0?Y.getFloat32(b+P+4,!0):$(Y.getUint16(b+P+2,!0)),Ot=C===0?Y.getFloat32(b+P+8,!0):$(Y.getUint16(b+P+4,!0)),jt=C===0?Y.getFloat32(b+L+0,!0):$(Y.getUint16(b+L+0,!0)),$t=C===0?Y.getFloat32(b+L+4,!0):$(Y.getUint16(b+L+2,!0)),Ae=C===0?Y.getFloat32(b+L+8,!0):$(Y.getUint16(b+L+4,!0)),te=C===0?Y.getFloat32(b+L+12,!0):$(Y.getUint16(b+L+6,!0)),ee=Y.getUint8(b+T+0)/255,se=Y.getUint8(b+T+1)/255,ie=Y.getUint8(b+T+2)/255,ne=Y.getUint8(b+T+3)/255;if(t(rA,AA,J,pA,nt,rt,Ot,$t,Ae,te,jt,ne,ee,se,ie),x>=1&&oA){for(const[xA,HA]of iA.entries())oA[xA]=E(b,HA);if(CA)for(const[xA,HA]of aA.entries())CA[xA]=E(b,HA);if(FA)for(const[xA,HA]of gA.entries())FA[xA]=E(b,HA);e==null||e(rA,oA,CA,FA)}}Q+=sA}}function Vs(s,A){var f;let i=0;const n=new DataView(s.buffer,i,4096);i+=4096;const r=n.getUint8(0),g=n.getUint8(1);if(r!==0||g<1)throw new Error(`Unsupported .ksplat version: ${r}.${g}`);const I=n.getUint32(4,!0),a=n.getUint32(16,!0),o=n.getUint16(20,!0);if(o<0||o>2)throw new Error(`Invalid .ksplat compression level: ${o}`);const C=n.getFloat32(36,!0)||-1.5,h=n.getFloat32(40,!0)||1.5,B=a,Q=lt(B),u=new Uint32Array(Q*4),l={};let E=4096+I*1024;for(let c=0;c<I;++c){let y=function(AA,J){if(o===0)return H.getFloat32(AA+sA+J*4,!0);if(o===1)return $(H.getUint16(AA+sA+J*2,!0));const pA=H.getUint8(AA+sA+J)/255;return C+pA*(h-C)};const p=new DataView(s.buffer,i,1024);i+=1024;const d=p.getUint32(0,!0),z=p.getUint32(4,!0),m=p.getUint32(8,!0),w=p.getUint32(12,!0),G=p.getFloat32(16,!0),S=p.getUint16(20,!0),D=(p.getUint32(24,!0)||((f=mt[o])==null?void 0:f.scaleRange))??1,F=p.getUint32(32,!0),M=F*m,x=p.getUint32(36,!0),U=x*4,v=S*w+U,q=p.getUint16(40,!0),Z=Pe[q],{bytesPerCenter:W,bytesPerScale:K,bytesPerRotation:P,bytesPerColor:L,bytesPerSphericalHarmonicsComponent:T,scaleOffsetBytes:_,rotationOffsetBytes:R,colorOffsetBytes:N,sphericalHarmonicsOffsetBytes:sA}=mt[o],iA=W+K+P+L+Z*T,aA=iA*z,gA=aA+v,oA=[0,3,6,1,4,7,2,5,8],CA=[9,14,19,10,15,20,11,16,21,12,17,22,13,18,23],FA=[24,31,38,25,32,39,26,33,40,27,34,41,28,35,42,29,36,43,30,37,44],BA=q>=1?new Float32Array(3*3):void 0,EA=q>=2?new Float32Array(5*3):void 0,cA=q>=3?new Float32Array(7*3):void 0,Y=G/2/D,nA=E+U,j=E+v,H=new DataView(s.buffer,j,aA),RA=new Float32Array(s.buffer,nA,w*3),rA=new Uint32Array(s.buffer,E,x);let b=F,lA=M;for(let AA=0;AA<d;++AA){const J=AA*iA;let pA;if(AA<M)pA=Math.floor(AA/m);else{const _A=rA[b-F];AA>=lA+_A&&(b+=1,lA+=_A),pA=b}const nt=o===0?H.getFloat32(J+0,!0):(H.getUint16(J+0,!0)-D)*Y+RA[3*pA+0],rt=o===0?H.getFloat32(J+4,!0):(H.getUint16(J+2,!0)-D)*Y+RA[3*pA+1],Ot=o===0?H.getFloat32(J+8,!0):(H.getUint16(J+4,!0)-D)*Y+RA[3*pA+2],jt=o===0?H.getFloat32(J+_+0,!0):$(H.getUint16(J+_+0,!0)),$t=o===0?H.getFloat32(J+_+4,!0):$(H.getUint16(J+_+2,!0)),Ae=o===0?H.getFloat32(J+_+8,!0):$(H.getUint16(J+_+4,!0)),te=o===0?H.getFloat32(J+R+0,!0):$(H.getUint16(J+R+0,!0)),ee=o===0?H.getFloat32(J+R+4,!0):$(H.getUint16(J+R+2,!0)),se=o===0?H.getFloat32(J+R+8,!0):$(H.getUint16(J+R+4,!0)),ie=o===0?H.getFloat32(J+R+12,!0):$(H.getUint16(J+R+6,!0)),ne=H.getUint8(J+N+0)/255,xA=H.getUint8(J+N+1)/255,HA=H.getUint8(J+N+2)/255,fi=H.getUint8(J+N+3)/255;if(qt(u,AA,nt,rt,Ot,jt,$t,Ae,ee,se,ie,te,fi,ne,xA,HA,A),q>=1){if(BA){l.sh1||(l.sh1=new Uint32Array(B*2));for(const[_A,gt]of oA.entries())BA[_A]=y(J,gt);yt(l.sh1,AA,BA,A)}if(EA){l.sh2||(l.sh2=new Uint32Array(B*4));for(const[_A,gt]of CA.entries())EA[_A]=y(J,gt);ft(l.sh2,AA,EA,A)}if(cA){l.sh3||(l.sh3=new Uint32Array(B*4));for(const[_A,gt]of FA.entries())cA[_A]=y(J,gt);wt(l.sh3,AA,cA,A)}}}E+=gA}return{packedArray:u,numSplats:B,extra:l}}const We=["char","uchar","short","ushort","int","uint","float","double"],OA=class OA{constructor({fileBytes:A}){this.header="",this.littleEndian=!0,this.elements={},this.comments=[],this.data=null,this.numSplats=0,this.fileBytes=A instanceof ArrayBuffer?new Uint8Array(A):A}async parseHeader(){const t=new ReadableStream({start:r=>{r.enqueue(this.fileBytes.slice(0,65536)),r.close()}}).pipeThrough(new TextDecoderStream).getReader();this.header="";const e=`end_header\n`;for(;;){const{value:r,done:g}=await t.read();if(g)throw new Error("Failed to read header");this.header+=r;const I=this.header.indexOf(e);if(I>=0){this.header=this.header.slice(0,I+e.length);break}}const i=new TextEncoder().encode(this.header).length;this.data=new DataView(this.fileBytes.buffer,i),this.elements={};let n=null;this.comments=[],this.header.trim().split(`\n`).forEach((r,g)=>{const I=r.trim();if(g===0){if(I!=="ply")throw new Error("Invalid PLY header");return}if(I.length===0)return;const a=I.split(" ");switch(a[0]){case"format":if(a[1]==="binary_little_endian")this.littleEndian=!0;else if(a[1]==="binary_big_endian")this.littleEndian=!1;else throw new Error(`Unsupported PLY format: ${a[1]}`);if(a[2]!=="1.0")throw new Error(`Unsupported PLY version: ${a[2]}`);break;case"end_header":break;case"comment":this.comments.push(I.slice(8));break;case"element":{const o=a[1];n={name:o,count:Number.parseInt(a[2]),properties:{}},this.elements[o]=n;break}case"property":if(n==null)throw new Error("Property must be inside an element");a[1]==="list"?n.properties[a[4]]={isList:!0,type:a[3],countType:a[2]}:n.properties[a[2]]={isList:!1,type:a[1]};break}}),this.elements.vertex&&(this.numSplats=this.elements.vertex.count)}parseData(A){let t=0;const e=this.data;if(e==null)throw new Error("No data to parse");for(const i in this.elements){const n=this.elements[i],{count:r,properties:g}=n,I=$s(g),a=Ai(g,this.littleEndian),o=A(n)??(()=>{});for(let C=0;C<r;C++)t=a(e,t,I),o(C,I)}}parseSplats(A,t){if(this.elements.vertex==null)throw new Error("No vertex element found");let e=!1;const i=[];let n=0,r=[],g=[],I=[],a,o,C;function h(){const E=js[n];r=new Array(3).fill(null).flatMap((f,c)=>[0,1,2].map((y,p)=>c+p*E/3)),g=new Array(5).fill(null).flatMap((f,c)=>[0,1,2].map((y,p)=>3+c+p*E/3)),I=new Array(7).fill(null).flatMap((f,c)=>[0,1,2].map((y,p)=>8+c+p*E/3)),a=n>=1?new Float32Array(3*3):void 0,o=n>=2?new Float32Array(5*3):void 0,C=n>=3?new Float32Array(7*3):void 0}function B(E,f){if(!a)throw new Error("Missing sh1");const c=f.f_rest;for(let y=0;y<r.length;y++)a[y]=c[r[y]]*8/255-4;if(o)for(let y=0;y<g.length;y++)o[y]=c[g[y]]*8/255-4;if(C)for(let y=0;y<I.length;y++)C[y]=c[I[y]]*8/255-4;t==null||t(E,a,o,C)}function Q(E){const{min_x:f,min_y:c,min_z:y,max_x:p,max_y:d,max_z:z,min_scale_x:m,min_scale_y:w,min_scale_z:G,max_scale_x:S,max_scale_y:D,max_scale_z:F}=E.properties;if(!f||!c||!y||!p||!d||!z||!m||!w||!G||!S||!D||!F)throw new Error("Missing PLY chunk properties");return e=!0,(M,x)=>{const{min_x:U,min_y:v,min_z:q,max_x:Z,max_y:W,max_z:K,min_scale_x:P,min_scale_y:L,min_scale_z:T,max_scale_x:_,max_scale_y:R,max_scale_z:N,min_r:sA,min_g:iA,min_b:aA,max_r:gA,max_g:oA,max_b:CA}=x;i.push({min_x:U,min_y:v,min_z:q,max_x:Z,max_y:W,max_z:K,min_scale_x:P,min_scale_y:L,min_scale_z:T,max_scale_x:_,max_scale_y:R,max_scale_z:N,min_r:sA,min_g:iA,min_b:aA,max_r:gA,max_g:oA,max_b:CA})}}function u(E){if(t&&E.name==="sh")return n=Xt(E.properties),h(),B;if(E.name!=="vertex")return null;const{packed_position:f,packed_rotation:c,packed_scale:y,packed_color:p}=E.properties;if(!f||!c||!y||!p)throw new Error("Missing PLY properties: packed_position, packed_rotation, packed_scale, packed_color");const d=Math.sqrt(2);return(z,m)=>{const w=i[z>>>8];if(w==null)throw new Error("Missing PLY chunk");const{min_x:G,min_y:S,min_z:D,max_x:F,max_y:M,max_z:x,min_scale_x:U,min_scale_y:v,min_scale_z:q,max_scale_x:Z,max_scale_y:W,max_scale_z:K,min_r:P,min_g:L,min_b:T,max_r:_,max_g:R,max_b:N}=w,{packed_position:sA,packed_rotation:iA,packed_scale:aA,packed_color:gA}=m,oA=(sA>>>21&2047)/2047*(F-G)+G,CA=(sA>>>11&1023)/1023*(M-S)+S,FA=(sA&2047)/2047*(x-D)+D,BA=((iA>>>20&1023)/1023-.5)*d,EA=((iA>>>10&1023)/1023-.5)*d,cA=((iA&1023)/1023-.5)*d,Y=Math.sqrt(Math.max(0,1-BA*BA-EA*EA-cA*cA)),nA=iA>>>30,j=nA===0?BA:nA===1?Y:EA,H=nA<=1?EA:nA===2?Y:cA,RA=nA<=2?cA:Y,rA=nA===0?Y:BA,b=Math.exp((aA>>>21&2047)/2047*(Z-U)+U),lA=Math.exp((aA>>>11&1023)/1023*(W-v)+v),AA=Math.exp((aA&2047)/2047*(K-q)+q),J=(gA>>>24&255)/255*((_??1)-(P??0))+(P??0),pA=(gA>>>16&255)/255*((R??1)-(L??0))+(L??0),nt=(gA>>>8&255)/255*((N??1)-(T??0))+(T??0),rt=(gA&255)/255;A(z,oA,CA,FA,b,lA,AA,j,H,RA,rA,rt,J,pA,nt)}}const l=E=>{if(E.name==="chunk")return Q(E);if(e)return u(E);if(E.name!=="vertex")return null;const{x:f,y:c,z:y,scale_0:p,scale_1:d,scale_2:z,rot_0:m,rot_1:w,rot_2:G,rot_3:S,opacity:D,f_dc_0:F,f_dc_1:M,f_dc_2:x,red:U,green:v,blue:q,alpha:Z}=E.properties;if(!f||!c||!y)throw new Error("Missing PLY properties: x, y, z");const W=p&&d&&z,K=m&&w&&G&&S,P=Z!=null?St[Z.type]:1,L=U!=null?St[U.type]:1,T=v!=null?St[v.type]:1,_=q!=null?St[q.type]:1;return n=Xt(E.properties),h(),(R,N)=>{const sA=W?Math.exp(N.scale_0):OA.defaultPointScale,iA=W?Math.exp(N.scale_1):OA.defaultPointScale,aA=W?Math.exp(N.scale_2):OA.defaultPointScale,gA=K?N.rot_1:0,oA=K?N.rot_2:0,CA=K?N.rot_3:0,FA=K?N.rot_0:1,BA=D!=null?1/(1+Math.exp(-N.opacity)):Z!=null?N.alpha/P:1,EA=F!=null?N.f_dc_0*Dt+.5:U!=null?N.red/L:1,cA=M!=null?N.f_dc_1*Dt+.5:v!=null?N.green/T:1,Y=x!=null?N.f_dc_2*Dt+.5:q!=null?N.blue/_:1;if(A(R,N.x,N.y,N.z,sA,iA,aA,gA,oA,CA,FA,BA,EA,cA,Y),t&&a){const nA=N.f_rest;if(a)for(let j=0;j<r.length;j++)a[j]=nA[r[j]];if(o)for(let j=0;j<g.length;j++)o[j]=nA[g[j]];if(C)for(let j=0;j<I.length;j++)C[j]=nA[I[j]];t(R,a,o,C)}}};this.parseData(l)}injectRgba(A){let t=0;const e=this.data;if(e==null)throw new Error("No parsed data");if(A.length!==this.numSplats*4)throw new Error("Invalid RGBA array length");for(const i in this.elements){const n=this.elements[i],{count:r,properties:g}=n,I=[];let a=0;const o=i==="vertex";if(o){for(const C of["opacity","f_dc_0","f_dc_1","f_dc_2"])if(!g[C]||g[C].type!=="float")throw new Error(`Can\'t injectRgba due to property: ${C}`)}for(const[C,h]of Object.entries(g))if(h.isList)I.push(()=>{const B=VA[h.countType](e,t,this.littleEndian);t+=mA[h.countType],t+=B*mA[h.type]});else{if(o)if(C==="f_dc_0"||C==="f_dc_1"||C==="f_dc_2"){const B=Number.parseInt(C.slice(5));I.push(()=>{const Q=(A[a+B]/255-.5)/Dt;Ve[h.type](e,t,this.littleEndian,Q)})}else C==="opacity"&&I.push(()=>{const B=Math.max(-100,Math.min(100,-Math.log(1/(A[a+3]/255)-1)));Ve[h.type](e,t,this.littleEndian,B)});I.push(()=>{t+=mA[h.type]})}for(let C=0;C<r;C++){for(const h of I)h();o&&(a+=4)}}}};OA.defaultPointScale=.001;let pt=OA;const Dt=.28209479177387814,VA={char:(s,A,t)=>s.getInt8(A),uchar:(s,A,t)=>s.getUint8(A),short:(s,A,t)=>s.getInt16(A,t),ushort:(s,A,t)=>s.getUint16(A,t),int:(s,A,t)=>s.getInt32(A,t),uint:(s,A,t)=>s.getUint32(A,t),float:(s,A,t)=>s.getFloat32(A,t),double:(s,A,t)=>s.getFloat64(A,t)},Ve={char:(s,A,t,e)=>{s.setInt8(A,e)},uchar:(s,A,t,e)=>{s.setUint8(A,e)},short:(s,A,t,e)=>{s.setInt16(A,e,t)},ushort:(s,A,t,e)=>{s.setUint16(A,e,t)},int:(s,A,t,e)=>{s.setInt32(A,e,t)},uint:(s,A,t,e)=>{s.setUint32(A,e,t)},float:(s,A,t,e)=>{s.setFloat32(A,e,t)},double:(s,A,t,e)=>{s.setFloat64(A,e,t)}},mA={char:1,uchar:1,short:2,ushort:2,int:4,uint:4,float:4,double:8},St={char:127,uchar:255,short:32767,ushort:65535,int:2147483647,uint:4294967295,float:1,double:1},Os={0:0,9:1,24:2,45:3},js={0:0,1:9,2:24,3:45},Kt=/^f_rest_([0-9]{1,2})$/;function $s(s){const A={};for(const[t,e]of Object.entries(s))Kt.test(t)?A.f_rest=new Array(Xt(s)):A[t]=e.isList?[]:0;return A}function Ai(s,A){return si(s)?ii(s,A):ni(s,A)}const ti=(()=>{try{new Function("return 42;")}catch{return!1}return!0})(),ei=/^[a-zA-Z0-9_]+$/;function si(s){if(!ti)return!1;for(const[A,t]of Object.entries(s))if(!ei.test(A)||t.isList&&!We.includes(t.countType)||!We.includes(t.type))return!1;return!0}function ii(s,A){const t=["let list;"];for(const[i,n]of Object.entries(s)){const r=i.match(Kt);if(r){const g=+r[1];t.push(`\n item.f_rest[${g}] = PARSE_FIELD[\'${n.type}\'](data, offset, ${A});\n offset += ${mA[n.type]};\n `)}else n.isList?t.push(`\n list = item[\'${i}\'];\n list.length = PARSE_FIELD[\'${n.countType}\'](data, offset, ${A});\n offset += ${mA[n.countType]};\n for (let i = 0; i < list.length; i++) {\n list[i] = PARSE_FIELD[\'${n.type}\'](data, offset, ${A});\n offset += ${mA[n.type]};\n }\n `):t.push(`\n item[\'${i}\'] = PARSE_FIELD[\'${n.type}\'](data, offset, ${A});\n offset += ${mA[n.type]};\n `)}t.push("return offset;");const e=new Function("data","offset","item","PARSE_FIELD",t.join(`\n`));return(i,n,r)=>e(i,n,r,VA)}function ni(s,A){const t=[];for(const[e,i]of Object.entries(s)){const n=e.match(Kt);if(n){const r=+n[1];t.push((g,I,a)=>(a.f_rest[r]=VA[i.type](g,I,A),I+mA[i.type]))}else i.isList?t.push((r,g,I)=>{const a=I[e];a.length=VA[i.countType](r,g,A);let o=g+mA[i.countType];for(let C=0;C<a.length;C++)a[C]=VA[i.type](r,o,A),o+=mA[i.type];return o}):t.push((r,g,I)=>(I[e]=VA[i.type](r,g,A),g+mA[i.type]))}return(e,i,n)=>{let r=i;for(let g=0;g<t.length;g++)r=t[g](e,r,n);return r}}function Xt(s){let A=0;for(;s[`f_rest_${A}`];)A+=1;const t=Os[A];if(t==null)throw new Error(`Unsupported number of SH coefficients: ${A}`);return t}var st=(s=>(s.PLY="ply",s.SPZ="spz",s.SPLAT="splat",s.KSPLAT="ksplat",s.PCSOGS="pcsogs",s.PCSOGSZIP="pcsogszip",s))(st||{});function ri(s){const A=new DataView(s.buffer);if((A.getUint32(0,!0)&16777215)===7957616)return"ply";if((A.getUint32(0,!0)&16777215)===559903){const t=Ks(s,4);return new DataView(t.buffer).getUint32(0,!0)===1347635022?"spz":void 0}if(A.getUint32(0,!0)===67324752)return Oe(s)?"pcsogszip":void 0}function gi(s){const A=s.split(/[?#]/,1)[0],t=Math.max(A.lastIndexOf("/"),A.lastIndexOf("\\\\")),e=A.slice(t+1),i=e.lastIndexOf(".");return i<=0||i===e.length-1?"":e.slice(i+1).toLowerCase()}function Ii(s){const A=gi(s);if(A==="ply")return"ply";if(A==="spz")return"spz";if(A==="splat")return"splat";if(A==="ksplat")return"ksplat";if(A==="sog")return"pcsogszip"}function ai(s){try{let A;if(typeof s=="string")A=s;else{const i=s instanceof ArrayBuffer?new Uint8Array(s):s;if(i.length>65536)return;A=new TextDecoder().decode(i)}const t=JSON.parse(A);if(!t||typeof t!="object"||Array.isArray(t))return;const e=t.version===2;for(const i of["means","scales","quats","sh0"]){if(!t[i]||typeof t[i]!="object"||Array.isArray(t[i]))return;if(e){if(!t[i].files||(i==="scales"||i==="sh0")&&!t[i].codebook||i==="means"&&(!t[i].mins||!t[i].maxs))return}else if(!t[i].shape||!t[i].files||i!=="quats"&&(!t[i].mins||!t[i].maxs))return}return t}catch{return}}function Oe(s){try{const A=s instanceof ArrayBuffer?new Uint8Array(s):s;let t=null;const e=Ms(A,{filter:({name:n})=>n.split(/[\\\\/]/).pop()==="meta.json"?(t=n,!0):!1});if(!t)return;const i=ai(e[t]);return i?{name:t,json:i}:void 0}catch{return}}class oi{constructor({maxSplats:A=1}={}){this.numSplats=0,this.maxSplats=Ts(A).maxSplats,this.centers=new Float32Array(this.maxSplats*3),this.scales=new Float32Array(this.maxSplats*3),this.quaternions=new Float32Array(this.maxSplats*4),this.opacities=new Float32Array(this.maxSplats),this.colors=new Float32Array(this.maxSplats*3)}pushSplat(){const A=this.numSplats;return this.ensureIndex(A),this.numSplats+=1,A}unpushSplat(A){if(A===this.numSplats-1)this.numSplats-=1;else throw new Error("Cannot unpush splat from non-last position")}ensureCapacity(A){if(A>this.maxSplats){const t=Math.max(A,this.maxSplats*2),e=new Float32Array(t*3),i=new Float32Array(t*3),n=new Float32Array(t*4),r=new Float32Array(t),g=new Float32Array(t*3);if(e.set(this.centers),i.set(this.scales),n.set(this.quaternions),r.set(this.opacities),g.set(this.colors),this.centers=e,this.scales=i,this.quaternions=n,this.opacities=r,this.colors=g,this.sh1){const I=new Float32Array(t*9);I.set(this.sh1),this.sh1=I}if(this.sh2){const I=new Float32Array(t*15);I.set(this.sh2),this.sh2=I}if(this.sh3){const I=new Float32Array(t*21);I.set(this.sh3),this.sh3=I}this.maxSplats=t}}ensureIndex(A){this.ensureCapacity(A+1)}setCenter(A,t,e,i){this.centers[A*3]=t,this.centers[A*3+1]=e,this.centers[A*3+2]=i}setScale(A,t,e,i){this.scales[A*3]=t,this.scales[A*3+1]=e,this.scales[A*3+2]=i}setQuaternion(A,t,e,i,n){this.quaternions[A*4]=t,this.quaternions[A*4+1]=e,this.quaternions[A*4+2]=i,this.quaternions[A*4+3]=n}setOpacity(A,t){this.opacities[A]=t}setColor(A,t,e,i){this.colors[A*3]=t,this.colors[A*3+1]=e,this.colors[A*3+2]=i}setSh1(A,t){this.sh1||(this.sh1=new Float32Array(this.maxSplats*9));for(let e=0;e<9;++e)this.sh1[A*9+e]=t[e]}setSh2(A,t){this.sh2||(this.sh2=new Float32Array(this.maxSplats*15));for(let e=0;e<15;++e)this.sh2[A*15+e]=t[e]}setSh3(A,t){this.sh3||(this.sh3=new Float32Array(this.maxSplats*21));for(let e=0;e<21;++e)this.sh3[A*21+e]=t[e]}}async function je(s,A,t){const e="version"in s;if(!e&&s.quats.encoding!=="quaternion_packed")throw new Error("Unsupported quaternion encoding");const i=e?s.count:s.means.shape[0],n=lt(i),r=new Uint32Array(n*4),g={},I=Promise.all([it(A[s.means.files[0]]),it(A[s.means.files[1]])]).then(B=>{for(let Q=0;Q<i;++Q){const u=Q*4,l=(B[0][u+0]+(B[1][u+0]<<8))/65535,E=(B[0][u+1]+(B[1][u+1]<<8))/65535,f=(B[0][u+2]+(B[1][u+2]<<8))/65535;let c=s.means.mins[0]+(s.means.maxs[0]-s.means.mins[0])*l,y=s.means.mins[1]+(s.means.maxs[1]-s.means.mins[1])*E,p=s.means.mins[2]+(s.means.maxs[2]-s.means.mins[2])*f;c=Math.sign(c)*(Math.exp(Math.abs(c))-1),y=Math.sign(y)*(Math.exp(Math.abs(y))-1),p=Math.sign(p)*(Math.exp(Math.abs(p))-1),He(r,Q,c,y,p)}}),a=it(A[s.scales.files[0]]).then(B=>{let Q,u,l;e?Q=u=l=s.scales.codebook.map(E=>Math.exp(E)):(Q=new Array(256).fill(0).map((E,f)=>s.scales.mins[0]+(s.scales.maxs[0]-s.scales.mins[0])*(f/255)).map(E=>Math.exp(E)),u=new Array(256).fill(0).map((E,f)=>s.scales.mins[1]+(s.scales.maxs[1]-s.scales.mins[1])*(f/255)).map(E=>Math.exp(E)),l=new Array(256).fill(0).map((E,f)=>s.scales.mins[2]+(s.scales.maxs[2]-s.scales.mins[2])*(f/255)).map(E=>Math.exp(E)));for(let E=0;E<i;++E){const f=E*4;ve(r,E,Q[B[f+0]],u[B[f+1]],l[B[f+2]],t)}}),o=it(A[s.quats.files[0]]).then(B=>{const Q=Math.sqrt(2),u=new Array(256).fill(0).map((l,E)=>(E/255-.5)*Q);for(let l=0;l<i;++l){const E=l*4,f=u[B[E+0]],c=u[B[E+1]],y=u[B[E+2]],p=Math.sqrt(Math.max(0,1-f*f-c*c-y*y)),d=B[E+3]-252,z=d===0?f:d===1?p:c,m=d<=1?c:d===2?p:y,w=d<=2?y:p;Te(r,l,z,m,w,d===0?p:f)}}),C=it(A[s.sh0.files[0]]).then(B=>{const Q=.28209479177387814;let u,l,E,f;e?(u=l=E=s.sh0.codebook.map(c=>Q*c+.5),f=new Array(256).fill(0).map((c,y)=>y/255)):(u=new Array(256).fill(0).map((c,y)=>s.sh0.mins[0]+(s.sh0.maxs[0]-s.sh0.mins[0])*(y/255)).map(c=>Q*c+.5),l=new Array(256).fill(0).map((c,y)=>s.sh0.mins[1]+(s.sh0.maxs[1]-s.sh0.mins[1])*(y/255)).map(c=>Q*c+.5),E=new Array(256).fill(0).map((c,y)=>s.sh0.mins[2]+(s.sh0.maxs[2]-s.sh0.mins[2])*(y/255)).map(c=>Q*c+.5),f=new Array(256).fill(0).map((c,y)=>s.sh0.mins[3]+(s.sh0.maxs[3]-s.sh0.mins[3])*(y/255)).map(c=>1/(1+Math.exp(-c))));for(let c=0;c<i;++c){const y=c*4;Hs(r,c,u[B[y+0]],l[B[y+1]],E[B[y+2]],f[B[y+3]],t)}}),h=[I,a,o,C];if(s.shN){const B=e?s.shN.bands>=3:s.shN.shape[1]>=45,Q=e?s.shN.bands>=2:s.shN.shape[1]>=24,u=e?s.shN.bands>=1:s.shN.shape[1]>=9;u&&(g.sh1=new Uint32Array(i*2)),Q&&(g.sh2=new Uint32Array(i*4)),B&&(g.sh3=new Uint32Array(i*4));const l=new Float32Array(9),E=new Float32Array(15),f=new Float32Array(21),c=s.shN,y=Promise.all([Pt(A[s.shN.files[0]]),Pt(A[s.shN.files[1]])]).then(([p,d])=>{const z="codebook"in c?c.codebook:new Array(256).fill(0).map((m,w)=>c.mins+(c.maxs-c.mins)*(w/255));for(let m=0;m<i;++m){const w=m*4,G=d.rgba[w+0]+(d.rgba[w+1]<<8),S=(G&63)*15,F=(G>>>6)*p.width+S;for(let M=0;M<3;++M){if(u)for(let x=0;x<3;++x)l[x*3+M]=z[p.rgba[(F+x)*4+M]];if(Q)for(let x=0;x<5;++x)E[x*3+M]=z[p.rgba[(F+3+x)*4+M]];if(B)for(let x=0;x<7;++x)f[x*3+M]=z[p.rgba[(F+8+x)*4+M]]}u&&yt(g.sh1,m,l,t),Q&&ft(g.sh2,m,E,t),B&&wt(g.sh3,m,f,t)}});h.push(y)}return await Promise.all(h),{packedArray:r,numSplats:i,extra:g}}let xt=null;async function Pt(s){if(!xt&&(xt=new OffscreenCanvas(1,1).getContext("webgl2"),!xt))throw new Error("Failed to create WebGL2 context");const A=new Blob([s]),t=await createImageBitmap(A,{premultiplyAlpha:"none"}),e=xt,i=e.createTexture();e.bindTexture(e.TEXTURE_2D,i),e.pixelStorei(e.UNPACK_FLIP_Y_WEBGL,!0),e.texImage2D(e.TEXTURE_2D,0,e.RGBA,e.RGBA,e.UNSIGNED_BYTE,t),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_MAG_FILTER,e.NEAREST),e.texParameteri(e.TEXTURE_2D,e.TEXTURE_MIN_FILTER,e.NEAREST);const n=e.createFramebuffer();e.bindFramebuffer(e.FRAMEBUFFER,n),e.framebufferTexture2D(e.FRAMEBUFFER,e.COLOR_ATTACHMENT0,e.TEXTURE_2D,i,0);const r=new Uint8Array(t.width*t.height*4);return e.readPixels(0,0,t.width,t.height,e.RGBA,e.UNSIGNED_BYTE,r),e.deleteTexture(i),e.deleteFramebuffer(n),{rgba:r,width:t.width,height:t.height}}async function it(s){const{rgba:A}=await Pt(s);return A}async function Ci(s,A){var h;const t=Oe(s);if(!t)throw new Error("Invalid PC SOGS zip file");const{name:e,json:i}=t,n=e.lastIndexOf("/"),r=e.lastIndexOf("\\\\"),g=e.slice(0,Math.max(n,r)+1),I=new Map,a=[...i.means.files,...i.scales.files,...i.quats.files,...i.sh0.files,...((h=i.shN)==null?void 0:h.files)??[]];for(const B of a)I.set(g+B,B);const o=await new Promise((B,Q)=>{xs(s,{filter:({name:u})=>I.has(u)},(u,l)=>{u?Q(u):B(l)})}),C={};for(const[B,Q]of I.entries())C[Q]=o[B];return await je(i,C,A)}class $e{constructor({fileBytes:A}){this.version=-1,this.numSplats=0,this.shDegree=0,this.fractionalBits=0,this.flags=0,this.flagAntiAlias=!1,this.reserved=0,this.headerParsed=!1,this.parsed=!1,this.fileBytes=A instanceof ArrayBuffer?new Uint8Array(A):A,this.reader=new Xs({fileBytes:this.fileBytes})}async parseHeader(){if(this.headerParsed)throw new Error("SPZ file header already parsed");const A=new DataView((await this.reader.read(16)).buffer);if(A.getUint32(0,!0)!==1347635022)throw new Error("Invalid SPZ file");if(this.version=A.getUint32(4,!0),this.version<1||this.version>3)throw new Error(`Unsupported SPZ version: ${this.version}`);this.numSplats=A.getUint32(8,!0),this.shDegree=A.getUint8(12),this.fractionalBits=A.getUint8(13),this.flags=A.getUint8(14),this.flagAntiAlias=(this.flags&1)!==0,this.reserved=A.getUint8(15),this.headerParsed=!0,this.parsed=!1}async parseSplats(A,t,e,i,n,r){if(!this.headerParsed)throw new Error("SPZ file header must be parsed first");if(this.parsed)throw new Error("SPZ file already parsed");if(this.parsed=!0,this.version===1){const g=await this.reader.read(this.numSplats*3*2),I=new Uint16Array(g.buffer);for(let a=0;a<this.numSplats;a++){const o=a*3,C=$(I[o]),h=$(I[o+1]),B=$(I[o+2]);A==null||A(a,C,h,B)}}else if(this.version===2||this.version===3){const g=1<<this.fractionalBits,I=await this.reader.read(this.numSplats*3*3);for(let a=0;a<this.numSplats;a++){const o=a*9,C=((I[o+2]<<24|I[o+1]<<16|I[o]<<8)>>8)/g,h=((I[o+5]<<24|I[o+4]<<16|I[o+3]<<8)>>8)/g,B=((I[o+8]<<24|I[o+7]<<16|I[o+6]<<8)>>8)/g;A==null||A(a,C,h,B)}}else throw new Error("Unreachable");{const g=await this.reader.read(this.numSplats);for(let I=0;I<this.numSplats;I++)t==null||t(I,g[I]/255)}{const g=await this.reader.read(this.numSplats*3),I=ts/.15;for(let a=0;a<this.numSplats;a++){const o=a*3,C=(g[o]/255-.5)*I+.5,h=(g[o+1]/255-.5)*I+.5,B=(g[o+2]/255-.5)*I+.5;e==null||e(a,C,h,B)}}{const g=await this.reader.read(this.numSplats*3);for(let I=0;I<this.numSplats;I++){const a=I*3,o=Math.exp(g[a]/16-10),C=Math.exp(g[a+1]/16-10),h=Math.exp(g[a+2]/16-10);i==null||i(I,o,C,h)}}if(this.version===3){const g=1/Math.sqrt(2),I=await this.reader.read(this.numSplats*4);for(let a=0;a<this.numSplats;a++){const o=a*4,C=[0,0,0,0],h=[I[o],I[o+1],I[o+2],I[o+3]],B=h[0]+(h[1]<<8)+(h[2]<<16)+(h[3]<<24),Q=511,u=B>>>30;let l=B,E=0;for(let c=3;c>=0;--c)if(c!==u){const y=l&Q,p=l>>>9&1;l=l>>>10,C[c]=g*(y/Q),C[c]=p===0?C[c]:-C[c],E+=C[c]*C[c]}const f=1-E;C[u]=Math.sqrt(Math.max(f,0)),n==null||n(a,C[0],C[1],C[2],C[3])}}else{const g=await this.reader.read(this.numSplats*3);for(let I=0;I<this.numSplats;I++){const a=I*3,o=g[a]/127.5-1,C=g[a+1]/127.5-1,h=g[a+2]/127.5-1,B=Math.sqrt(Math.max(0,1-o*o-C*C-h*h));n==null||n(I,o,C,h,B)}}if(r&&this.shDegree>=1){const g=new Float32Array(9),I=this.shDegree>=2?new Float32Array(5*3):void 0,a=this.shDegree>=3?new Float32Array(7*3):void 0,o=await this.reader.read(this.numSplats*As[this.shDegree]*3);let C=0;for(let h=0;h<this.numSplats;h++){for(let B=0;B<9;++B)g[B]=(o[C+B]-128)/128;if(C+=9,I){for(let B=0;B<15;++B)I[B]=(o[C+B]-128)/128;C+=15}if(a){for(let B=0;B<21;++B)a[B]=(o[C+B]-128)/128;C+=21}r==null||r(h,g,I,a)}}}}const As={1:3,2:8,3:15},ts=.28209479177387814,Bi=1347635022,hi=3,Qi=1;class bA{constructor({numSplats:A,shDegree:t,fractionalBits:e=12,flagAntiAlias:i=!0}){this.clippedCount=0;const n=20+(t>=1?9:0)+(t>=2?15:0)+(t>=3?21:0),r=16+A*n;this.buffer=new ArrayBuffer(r),this.view=new DataView(this.buffer),this.view.setUint32(0,Bi,!0),this.view.setUint32(4,hi,!0),this.view.setUint32(8,A,!0),this.view.setUint8(12,t),this.view.setUint8(13,e),this.view.setUint8(14,i?Qi:0),this.view.setUint8(15,0),this.numSplats=A,this.shDegree=t,this.fractionalBits=e,this.fraction=1<<e,this.flagAntiAlias=i}setCenter(A,t,e,i){const n=Math.round(t*this.fraction),r=Math.max(-8388607,Math.min(8388607,n)),g=Math.round(e*this.fraction),I=Math.max(-8388607,Math.min(8388607,g)),a=Math.round(i*this.fraction),o=Math.max(-8388607,Math.min(8388607,a));(n!==r||g!==I||a!==o)&&(this.clippedCount+=1);const B=16+A*9;this.view.setUint8(B,r&255),this.view.setUint8(B+1,r>>8&255),this.view.setUint8(B+2,r>>16&255),this.view.setUint8(B+3,I&255),this.view.setUint8(B+4,I>>8&255),this.view.setUint8(B+5,I>>16&255),this.view.setUint8(B+6,o&255),this.view.setUint8(B+7,o>>8&255),this.view.setUint8(B+8,o>>16&255)}setAlpha(A,t){const e=16+this.numSplats*9+A;this.view.setUint8(e,Math.max(0,Math.min(255,Math.round(t*255))))}static scaleRgb(A){const t=((A-.5)/(ts/.15)+.5)*255;return Math.max(0,Math.min(255,Math.round(t)))}setRgb(A,t,e,i){const n=16+this.numSplats*10+A*3;this.view.setUint8(n,bA.scaleRgb(t)),this.view.setUint8(n+1,bA.scaleRgb(e)),this.view.setUint8(n+2,bA.scaleRgb(i))}setScale(A,t,e,i){const n=16+this.numSplats*13+A*3;this.view.setUint8(n,Math.max(0,Math.min(255,Math.round((Math.log(t)+10)*16)))),this.view.setUint8(n+1,Math.max(0,Math.min(255,Math.round((Math.log(e)+10)*16)))),this.view.setUint8(n+2,Math.max(0,Math.min(255,Math.round((Math.log(i)+10)*16))))}setQuat(A,...t){const e=16+this.numSplats*16+A*4,i=bs(t);let n=0;for(let I=1;I<4;++I)Math.abs(i[I])>Math.abs(i[n])&&(n=I);const r=i[n]<0?1:0;let g=n;for(let I=0;I<4;++I)if(I!==n){const a=(i[I]<0?1:0)^r,o=Math.floor(511*(Math.abs(i[I])/Math.SQRT1_2)+.5);g=g<<10|a<<9|o}this.view.setUint8(e,g&255),this.view.setUint8(e+1,g>>8&255),this.view.setUint8(e+2,g>>16&255),this.view.setUint8(e+3,g>>>24&255)}static quantizeSh(A,t){const e=Math.round(A*128)+128,i=1<<8-t,n=Math.floor((e+i/2)/i)*i;return Math.max(0,Math.min(255,n))}setSh(A,t,e,i){const n=As[this.shDegree]||0,r=16+this.numSplats*20+A*n*3;for(let g=0;g<9;++g)this.view.setUint8(r+g,bA.quantizeSh(t[g],5));if(e){const g=r+9;for(let I=0;I<15;++I)this.view.setUint8(g+I,bA.quantizeSh(e[I],4));if(i){const I=g+15;for(let a=0;a<21;++a)this.view.setUint8(I+a,bA.quantizeSh(i[a],4))}}}async finalize(){const A=new Uint8Array(this.buffer),e=new ReadableStream({async start(r){r.enqueue(A),r.close()}}).pipeThrough(new CompressionStream("gzip")),n=await new Response(e).arrayBuffer();return console.log("Compressed",A.length,"bytes to",n.byteLength,"bytes"),new Uint8Array(n)}}async function Ei(s){var o,C,h;const A=new oi,{inputs:t,clipXyz:e,maxSh:i,fractionalBits:n=12,opacityThreshold:r}=s;for(const B of t){let Q=function(m){return m.multiplyScalar(c),m.applyQuaternion(y),m.add(p),m},u=function(m){return m.multiplyScalar(c),m},l=function(m){return m.premultiply(y),m},E=function(m){return!d||d.containsPoint(m)},f=function(m){return r!==void 0?m>=r:!0};const c=((o=B.transform)==null?void 0:o.scale)??1,y=new kA().fromArray(((C=B.transform)==null?void 0:C.quaternion)??[0,0,0,1]),p=new k().fromArray(((h=B.transform)==null?void 0:h.translate)??[0,0,0]),d=e?new Ge(new k().fromArray(e.min),new k().fromArray(e.max)):void 0;let z=B.fileType;switch(z||(z=ri(B.fileBytes),!z&&B.pathOrUrl&&(z=Ii(B.pathOrUrl))),z){case st.PLY:{const m=new pt({fileBytes:B.fileBytes});await m.parseHeader();let w=null;m.parseSplats((G,S,D,F,M,x,U,v,q,Z,W,K,P,L,T)=>{const _=Q(new k(S,D,F));if(E(_)&&f(K)){w=A.pushSplat(),A.setCenter(w,_.x,_.y,_.z);const R=u(new k(M,x,U));A.setScale(w,R.x,R.y,R.z);const N=l(new kA(v,q,Z,W));A.setQuaternion(w,N.x,N.y,N.z,N.w),A.setOpacity(w,K),A.setColor(w,P,L,T)}else w=null},(G,S,D,F)=>{S&&w!==null&&A.setSh1(w,S),D&&w!==null&&A.setSh2(w,D),F&&w!==null&&A.setSh3(w,F)});break}case st.SPZ:{const m=new $e({fileBytes:B.fileBytes});await m.parseHeader();const w=new Int32Array(m.numSplats);w.fill(-1);const G=new Float32Array(m.numSplats*3),S=new k;m.parseSplats((D,F,M,x)=>{const U=Q(new k(F,M,x));G[D*3]=U.x,G[D*3+1]=U.y,G[D*3+2]=U.z},(D,F)=>{S.fromArray(G,D*3),E(S)&&f(F)&&(w[D]=A.pushSplat(),A.setCenter(w[D],S.x,S.y,S.z),A.setOpacity(w[D],F))},(D,F,M,x)=>{w[D]>=0&&A.setColor(w[D],F,M,x)},(D,F,M,x)=>{if(w[D]>=0){const U=u(new k(F,M,x));A.setScale(w[D],U.x,U.y,U.z)}},(D,F,M,x,U)=>{if(w[D]>=0){const v=l(new kA(F,M,x,U));A.setQuaternion(w[D],v.x,v.y,v.z,v.w)}},(D,F,M,x)=>{w[D]>=0&&(A.setSh1(w[D],F),M&&A.setSh2(w[D],M),x&&A.setSh3(w[D],x))});break}case st.SPLAT:Xe(B.fileBytes,m=>{},(m,w,G,S,D,F,M,x,U,v,q,Z,W,K,P)=>{const L=Q(new k(w,G,S));if(E(L)&&f(Z)){const T=A.pushSplat();A.setCenter(T,L.x,L.y,L.z);const _=u(new k(D,F,M));A.setScale(T,_.x,_.y,_.z);const R=l(new kA(x,U,v,q));A.setQuaternion(T,R.x,R.y,R.z,R.w),A.setOpacity(T,Z),A.setColor(T,W,K,P)}});break;case st.KSPLAT:{let m=null;Ws(B.fileBytes,w=>{},(w,G,S,D,F,M,x,U,v,q,Z,W,K,P,L)=>{const T=Q(new k(G,S,D));if(E(T)&&f(W)){m=A.pushSplat(),A.setCenter(m,T.x,T.y,T.z);const _=u(new k(F,M,x));A.setScale(m,_.x,_.y,_.z);const R=l(new kA(U,v,q,Z));A.setQuaternion(m,R.x,R.y,R.z,R.w),A.setOpacity(m,W),A.setColor(m,K,P,L)}else m=null},(w,G,S,D)=>{m!==null&&(A.setSh1(m,G),S&&A.setSh2(m,S),D&&A.setSh3(m,D))});break}default:throw new Error(`transcodeSpz not implemented for ${z}`)}}const g=Math.min(i??3,A.sh3?3:A.sh2?2:A.sh1?1:0),I=new bA({numSplats:A.numSplats,shDegree:g,fractionalBits:n,flagAntiAlias:!0});for(let B=0;B<A.numSplats;++B){const Q=B*3,u=B*4;I.setCenter(B,A.centers[Q],A.centers[Q+1],A.centers[Q+2]),I.setScale(B,A.scales[Q],A.scales[Q+1],A.scales[Q+2]),I.setQuat(B,A.quaternions[u],A.quaternions[u+1],A.quaternions[u+2],A.quaternions[u+3]),I.setAlpha(B,A.opacities[B]),I.setRgb(B,A.colors[Q],A.colors[Q+1],A.colors[Q+2]),A.sh1&&g>=1&&I.setSh(B,A.sh1.slice(B*9,(B+1)*9),g>=2&&A.sh2?A.sh2.slice(B*15,(B+1)*15):void 0,g>=3&&A.sh3?A.sh3.slice(B*21,(B+1)*21):void 0)}return{fileBytes:await I.finalize(),clippedCount:I.clippedCount}}async function es(s){const{name:A,args:t,id:e}=s.data;let i,n;try{switch(A){case"unpackPly":{const{packedArray:r,fileBytes:g,splatEncoding:I}=t,a=await ci({packedArray:r,fileBytes:g,splatEncoding:I});i={id:e,numSplats:a.numSplats,packedArray:a.packedArray,extra:a.extra};break}case"decodeSpz":{const{fileBytes:r,splatEncoding:g}=t,I=await li(r,g);i={id:e,numSplats:I.numSplats,packedArray:I.packedArray,extra:I.extra};break}case"decodeAntiSplat":{const{fileBytes:r,splatEncoding:g}=t,I=Ps(r,g);i={id:e,numSplats:I.numSplats,packedArray:I.packedArray};break}case"decodeKsplat":{const{fileBytes:r,splatEncoding:g}=t,I=Vs(r,g);i={id:e,numSplats:I.numSplats,packedArray:I.packedArray,extra:I.extra};break}case"decodePcSogs":{const{fileBytes:r,extraFiles:g,splatEncoding:I}=t,a=JSON.parse(new TextDecoder().decode(r)),o=await je(a,g,I);i={id:e,numSplats:o.numSplats,packedArray:o.packedArray,extra:o.extra};break}case"decodePcSogsZip":{const{fileBytes:r,splatEncoding:g}=t,I=await Ci(r,g);i={id:e,numSplats:I.numSplats,packedArray:I.packedArray,extra:I.extra};break}case"sortSplats":{const{totalSplats:r,readback:g,ordering:I}=t;i={id:e,readback:g,...ui({totalSplats:r,readback:g,ordering:I})};break}case"sortDoubleSplats":{const{numSplats:r,readback:g,ordering:I}=t;i={id:e,readback:g,ordering:I,activeSplats:rs(r,g,I)};break}case"sort32Splats":{const{numSplats:r,readback:g,ordering:I}=t;i={id:e,readback:g,ordering:I,activeSplats:gs(r,g,I)};break}case"transcodeSpz":{const r=t,g=await Ei(r);i={id:e,fileBytes:g,input:r};break}default:throw new Error(`Unknown name: ${A}`)}}catch(r){n=r,console.error(n)}self.postMessage({id:e,result:i,error:n},{transfer:Ls(i)})}async function ci({packedArray:s,fileBytes:A,splatEncoding:t}){const e=new pt({fileBytes:A});await e.parseHeader();const i=e.numSplats,n={};return e.parseSplats((r,g,I,a,o,C,h,B,Q,u,l,E,f,c,y)=>{qt(s,r,g,I,a,o,C,h,B,Q,u,l,E,f,c,y,t)},(r,g,I,a)=>{g&&(n.sh1||(n.sh1=new Uint32Array(i*2)),yt(n.sh1,r,g,t)),I&&(n.sh2||(n.sh2=new Uint32Array(i*4)),ft(n.sh2,r,I,t)),a&&(n.sh3||(n.sh3=new Uint32Array(i*4)),wt(n.sh3,r,a,t))}),{packedArray:s,numSplats:i,extra:n}}async function li(s,A){const t=new $e({fileBytes:s});await t.parseHeader();const e=t.numSplats,i=lt(e),n=new Uint32Array(i*4),r={};return await t.parseSplats((g,I,a,o)=>{He(n,g,I,a,o)},(g,I)=>{Zs(n,g,I)},(g,I,a,o)=>{vs(n,g,I,a,o,A)},(g,I,a,o)=>{ve(n,g,I,a,o,A)},(g,I,a,o,C)=>{Te(n,g,I,a,o,C)},(g,I,a,o)=>{I&&(r.sh1||(r.sh1=new Uint32Array(e*2)),yt(r.sh1,g,I,A)),a&&(r.sh2||(r.sh2=new Uint32Array(e*4)),ft(r.sh2,g,a,A)),o&&(r.sh3||(r.sh3=new Uint32Array(e*4)),wt(r.sh3,g,o,A))}),{packedArray:n,numSplats:e,extra:r}}const Wt=31744,Mt=Wt+1;let SA=null;function ui({totalSplats:s,readback:A,ordering:t}){SA||(SA=new Uint32Array(Mt)),SA.fill(0);const e=A.map(I=>new Uint32Array(I.buffer)),i=e[0].length,n=Math.ceil(s/i);let r=0;for(let I=0;I<n;++I){const a=e[I],o=Math.min(a.length,s-r);for(let C=0;C<o;++C){const h=a[C]&32767;h<Wt&&(SA[h]+=1)}r+=o}let g=0;for(let I=0;I<Mt;++I){const a=g+SA[I];SA[I]=g,g=a}r=0;for(let I=0;I<n;++I){const a=e[I],o=Math.min(a.length,s-r);for(let C=0;C<o;++C){const h=a[C]&32767;h<Wt&&(t[SA[h]]=r+C,SA[h]+=1)}r+=o}if(SA[Mt-1]!==g)throw new Error(`Expected ${g} active splats but got ${SA[Mt-1]}`);return{activeSplats:g,ordering:t}}const Vt=[];function ss(s){Vt.push(s)}async function yi(){self.addEventListener("message",ss),await ge(),self.removeEventListener("message",ss),self.addEventListener("message",es);for(const s of Vt)es(s);Vt.length=0}yi().catch(console.error)})();\n//# sourceMappingURL=worker-CBtTDhW6.js.map\n', fs = typeof self < "u" && self.Blob && new Blob([Pa], { type: "text/javascript;charset=utf-8" });
|
|
function Hu(t) {
|
|
let A;
|
|
try {
|
|
if (A = fs && (self.URL || self.webkitURL).createObjectURL(fs), !A) throw "";
|
|
const e = new Worker(A, {
|
|
name: t == null ? void 0 : t.name
|
|
});
|
|
return e.addEventListener("error", () => {
|
|
(self.URL || self.webkitURL).revokeObjectURL(A);
|
|
}), e;
|
|
} catch {
|
|
return new Worker(
|
|
"data:text/javascript;charset=utf-8," + encodeURIComponent(Pa),
|
|
{
|
|
name: t == null ? void 0 : t.name
|
|
}
|
|
);
|
|
} finally {
|
|
A && (self.URL || self.webkitURL).revokeObjectURL(A);
|
|
}
|
|
}
|
|
class qu {
|
|
constructor() {
|
|
this.messages = {}, this.messageIdNext = 0, this.worker = new Hu(), this.worker.onmessage = (A) => this.onMessage(A);
|
|
}
|
|
makeMessageId() {
|
|
return ++this.messageIdNext;
|
|
}
|
|
makeMessagePromiseId() {
|
|
const A = this.makeMessageId(), e = new Promise((s, n) => {
|
|
this.messages[A] = { resolve: s, reject: n };
|
|
});
|
|
return { id: A, promise: e };
|
|
}
|
|
onMessage(A) {
|
|
const { id: e, result: s, error: n } = A.data, i = this.messages[e];
|
|
i && (delete this.messages[e], n ? i.reject(n) : i.resolve(s));
|
|
}
|
|
// Invoke an RPC on the worker with the given name and arguments.
|
|
// The normal usage of a worker is to run one activity at a time,
|
|
// but this function allows for concurrent calls, tagging each request
|
|
// with a unique message Id and awaiting a response to that same Id.
|
|
// The method will automatically transfer any ArrayBuffers in the
|
|
// arguments to the worker. If you'd like to transfer a copy of a
|
|
// buffer then you must clone it before passing to this function.
|
|
async call(A, e) {
|
|
const { id: s, promise: n } = this.makeMessagePromiseId();
|
|
return this.worker.postMessage(
|
|
{ name: A, args: e, id: s },
|
|
{ transfer: Hn(e) }
|
|
), n;
|
|
}
|
|
}
|
|
let Za = 4, he = 0;
|
|
const Xa = [], Oa = [];
|
|
async function Ku() {
|
|
const t = Xa.shift();
|
|
if (t)
|
|
return t;
|
|
if (he < Za) {
|
|
const A = new qu();
|
|
return he += 1, A;
|
|
}
|
|
return new Promise((A) => {
|
|
Oa.push(A);
|
|
});
|
|
}
|
|
function $u(t) {
|
|
if (he > Za) {
|
|
he -= 1;
|
|
return;
|
|
}
|
|
const A = Oa.shift();
|
|
if (A) {
|
|
A(t);
|
|
return;
|
|
}
|
|
Xa.push(t);
|
|
}
|
|
async function lt(t) {
|
|
const A = await Ku();
|
|
try {
|
|
return await t(A);
|
|
} finally {
|
|
$u(A);
|
|
}
|
|
}
|
|
class Vu extends yo {
|
|
constructor(A) {
|
|
super(A), this.fileLoader = new wo(A);
|
|
}
|
|
load(A, e, s, n) {
|
|
const i = this.manager.resolveURL(
|
|
(this.path ?? "") + (A ?? "")
|
|
), r = new Headers(this.requestHeader), a = this.withCredentials ? "include" : "same-origin", o = new Request(i, { headers: r, credentials: a });
|
|
let g = this.fileType;
|
|
this.manager.itemStart(i), ds(o, s).then(async (l) => {
|
|
var B;
|
|
const c = [
|
|
new ProgressEvent("progress", {
|
|
lengthComputable: !0,
|
|
loaded: l.byteLength,
|
|
total: l.byteLength
|
|
})
|
|
];
|
|
function I() {
|
|
if (s) {
|
|
const Q = c.every((d) => d.lengthComputable || d.loaded === 0 && d.total === 0), f = c.reduce((d, y) => d + y.loaded, 0), p = c.reduce((d, y) => d + y.total, 0);
|
|
s(
|
|
new ProgressEvent("progress", {
|
|
lengthComputable: Q,
|
|
loaded: f,
|
|
total: p
|
|
})
|
|
);
|
|
}
|
|
}
|
|
const h = {}, E = [], C = gs(l);
|
|
if (g === "pcsogs" && C === void 0)
|
|
throw new Error("Invalid PC SOGS file");
|
|
if (C !== void 0) {
|
|
g = "pcsogs";
|
|
for (const Q of ["means", "scales", "quats", "sh0", "shN"]) {
|
|
const f = C[Q];
|
|
if (f)
|
|
for (const p of f.files) {
|
|
const d = new URL(p, i).toString(), y = c.length;
|
|
c.push(new ProgressEvent("progress")), this.manager.itemStart(d);
|
|
const D = new Request(d, { headers: r, credentials: a }), x = ds(D, (w) => {
|
|
c[y] = w, I();
|
|
}).then((w) => {
|
|
h[p] = w;
|
|
}).catch((w) => {
|
|
throw this.manager.itemError(d), w;
|
|
}).finally(() => {
|
|
this.manager.itemEnd(d);
|
|
});
|
|
E.push(x);
|
|
}
|
|
}
|
|
}
|
|
if (await Promise.all(E), e) {
|
|
const Q = ((B = this.packedSplats) == null ? void 0 : B.splatEncoding) ?? de, f = await Ao({
|
|
input: l,
|
|
extraFiles: h,
|
|
fileType: g,
|
|
pathOrUrl: i,
|
|
splatEncoding: Q
|
|
});
|
|
this.packedSplats ? (this.packedSplats.initialize(f), e(this.packedSplats)) : e(new VA(f));
|
|
}
|
|
}).catch((l) => {
|
|
this.manager.itemError(i), n == null || n(l);
|
|
}).finally(() => {
|
|
this.manager.itemEnd(i);
|
|
});
|
|
}
|
|
async loadAsync(A, e) {
|
|
return new Promise((s, n) => {
|
|
this.load(
|
|
A,
|
|
(i) => {
|
|
s(i);
|
|
},
|
|
e,
|
|
n
|
|
);
|
|
});
|
|
}
|
|
parse(A) {
|
|
return new pt({ packedSplats: A });
|
|
}
|
|
}
|
|
async function ds(t, A) {
|
|
const e = await fetch(t);
|
|
if (!e.ok)
|
|
throw new Error(
|
|
`${e.status} "${e.statusText}" fetching URL: ${t.url}`
|
|
);
|
|
if (!e.body)
|
|
throw new Error(`Response body is null for URL: ${t.url}`);
|
|
const s = e.body.getReader(), n = Number.parseInt(
|
|
e.headers.get("Content-Length") || "0"
|
|
), i = Number.isNaN(n) ? 0 : n;
|
|
let r = 0;
|
|
const a = [];
|
|
for (; ; ) {
|
|
const { done: l, value: c } = await s.read();
|
|
if (l)
|
|
break;
|
|
a.push(c), r += c.length, A && A(
|
|
new ProgressEvent("progress", {
|
|
lengthComputable: i !== 0,
|
|
loaded: r,
|
|
total: i
|
|
})
|
|
);
|
|
}
|
|
const o = new Uint8Array(r);
|
|
let g = 0;
|
|
for (const l of a)
|
|
o.set(l, g), g += l.length;
|
|
return o.buffer;
|
|
}
|
|
var _t = /* @__PURE__ */ ((t) => (t.PLY = "ply", t.SPZ = "spz", t.SPLAT = "splat", t.KSPLAT = "ksplat", t.PCSOGS = "pcsogs", t.PCSOGSZIP = "pcsogszip", t))(_t || {});
|
|
function ja(t) {
|
|
const A = new DataView(t.buffer);
|
|
if ((A.getUint32(0, !0) & 16777215) === 7957616)
|
|
return "ply";
|
|
if ((A.getUint32(0, !0) & 16777215) === 559903) {
|
|
const e = Wn(t, 4);
|
|
return new DataView(e.buffer).getUint32(0, !0) === 1347635022 ? "spz" : void 0;
|
|
}
|
|
if (A.getUint32(0, !0) === 67324752)
|
|
return Zu(t) ? "pcsogszip" : void 0;
|
|
}
|
|
function Pu(t) {
|
|
const A = t.split(/[?#]/, 1)[0], e = Math.max(
|
|
A.lastIndexOf("/"),
|
|
A.lastIndexOf("\\")
|
|
), s = A.slice(e + 1), n = s.lastIndexOf(".");
|
|
return n <= 0 || n === s.length - 1 ? "" : s.slice(n + 1).toLowerCase();
|
|
}
|
|
function Wa(t) {
|
|
const A = Pu(t);
|
|
if (A === "ply")
|
|
return "ply";
|
|
if (A === "spz")
|
|
return "spz";
|
|
if (A === "splat")
|
|
return "splat";
|
|
if (A === "ksplat")
|
|
return "ksplat";
|
|
if (A === "sog")
|
|
return "pcsogszip";
|
|
}
|
|
function Zh(t) {
|
|
return gs(t) !== void 0;
|
|
}
|
|
function gs(t) {
|
|
try {
|
|
let A;
|
|
if (typeof t == "string")
|
|
A = t;
|
|
else {
|
|
const n = t instanceof ArrayBuffer ? new Uint8Array(t) : t;
|
|
if (n.length > 65536)
|
|
return;
|
|
A = new TextDecoder().decode(n);
|
|
}
|
|
const e = JSON.parse(A);
|
|
if (!e || typeof e != "object" || Array.isArray(e))
|
|
return;
|
|
const s = e.version === 2;
|
|
for (const n of ["means", "scales", "quats", "sh0"]) {
|
|
if (!e[n] || typeof e[n] != "object" || Array.isArray(e[n]))
|
|
return;
|
|
if (s) {
|
|
if (!e[n].files || (n === "scales" || n === "sh0") && !e[n].codebook || n === "means" && (!e[n].mins || !e[n].maxs))
|
|
return;
|
|
} else if (!e[n].shape || !e[n].files || n !== "quats" && (!e[n].mins || !e[n].maxs))
|
|
return;
|
|
}
|
|
return e;
|
|
} catch {
|
|
return;
|
|
}
|
|
}
|
|
function Zu(t) {
|
|
try {
|
|
const A = t instanceof ArrayBuffer ? new Uint8Array(t) : t;
|
|
let e = null;
|
|
const s = Ko(A, {
|
|
filter: ({ name: i }) => i.split(/[\\/]/).pop() === "meta.json" ? (e = i, !0) : !1
|
|
});
|
|
if (!e)
|
|
return;
|
|
const n = gs(s[e]);
|
|
return n ? { name: e, json: n } : void 0;
|
|
} catch {
|
|
return;
|
|
}
|
|
}
|
|
async function Ao({
|
|
input: t,
|
|
extraFiles: A,
|
|
fileType: e,
|
|
pathOrUrl: s,
|
|
splatEncoding: n
|
|
}) {
|
|
const i = t instanceof ArrayBuffer ? new Uint8Array(t) : t;
|
|
let r = e;
|
|
switch (e || (r = ja(i), !r && s && (r = Wa(s))), r) {
|
|
case "ply": {
|
|
const a = new ue({ fileBytes: i });
|
|
await a.parseHeader();
|
|
const o = a.numSplats, g = mA(o).maxSplats, l = {
|
|
fileBytes: i,
|
|
packedArray: new Uint32Array(g * 4),
|
|
splatEncoding: n
|
|
};
|
|
return await lt(async (c) => {
|
|
const { packedArray: I, numSplats: h, extra: E } = await c.call(
|
|
"unpackPly",
|
|
l
|
|
);
|
|
return { packedArray: I, numSplats: h, extra: E };
|
|
});
|
|
}
|
|
case "spz":
|
|
return await lt(async (a) => {
|
|
const { packedArray: o, numSplats: g, extra: l } = await a.call(
|
|
"decodeSpz",
|
|
{
|
|
fileBytes: i,
|
|
splatEncoding: n
|
|
}
|
|
);
|
|
return { packedArray: o, numSplats: g, extra: l };
|
|
});
|
|
case "splat":
|
|
return await lt(async (a) => {
|
|
const { packedArray: o, numSplats: g } = await a.call(
|
|
"decodeAntiSplat",
|
|
{
|
|
fileBytes: i,
|
|
splatEncoding: n
|
|
}
|
|
);
|
|
return { packedArray: o, numSplats: g };
|
|
});
|
|
case "ksplat":
|
|
return await lt(async (a) => {
|
|
const { packedArray: o, numSplats: g, extra: l } = await a.call(
|
|
"decodeKsplat",
|
|
{ fileBytes: i, splatEncoding: n }
|
|
);
|
|
return { packedArray: o, numSplats: g, extra: l };
|
|
});
|
|
case "pcsogs":
|
|
return await lt(async (a) => {
|
|
const { packedArray: o, numSplats: g, extra: l } = await a.call(
|
|
"decodePcSogs",
|
|
{ fileBytes: i, extraFiles: A, splatEncoding: n }
|
|
);
|
|
return { packedArray: o, numSplats: g, extra: l };
|
|
});
|
|
case "pcsogszip":
|
|
return await lt(async (a) => {
|
|
const { packedArray: o, numSplats: g, extra: l } = await a.call(
|
|
"decodePcSogsZip",
|
|
{ fileBytes: i, splatEncoding: n }
|
|
);
|
|
return { packedArray: o, numSplats: g, extra: l };
|
|
});
|
|
default:
|
|
throw new Error(`Unknown splat file type: ${r}`);
|
|
}
|
|
}
|
|
class Xu {
|
|
constructor({ maxSplats: A = 1 } = {}) {
|
|
this.numSplats = 0, this.maxSplats = mA(A).maxSplats, this.centers = new Float32Array(this.maxSplats * 3), this.scales = new Float32Array(this.maxSplats * 3), this.quaternions = new Float32Array(this.maxSplats * 4), this.opacities = new Float32Array(this.maxSplats), this.colors = new Float32Array(this.maxSplats * 3);
|
|
}
|
|
pushSplat() {
|
|
const A = this.numSplats;
|
|
return this.ensureIndex(A), this.numSplats += 1, A;
|
|
}
|
|
unpushSplat(A) {
|
|
if (A === this.numSplats - 1)
|
|
this.numSplats -= 1;
|
|
else
|
|
throw new Error("Cannot unpush splat from non-last position");
|
|
}
|
|
ensureCapacity(A) {
|
|
if (A > this.maxSplats) {
|
|
const e = Math.max(A, this.maxSplats * 2), s = new Float32Array(e * 3), n = new Float32Array(e * 3), i = new Float32Array(e * 4), r = new Float32Array(e), a = new Float32Array(e * 3);
|
|
if (s.set(this.centers), n.set(this.scales), i.set(this.quaternions), r.set(this.opacities), a.set(this.colors), this.centers = s, this.scales = n, this.quaternions = i, this.opacities = r, this.colors = a, this.sh1) {
|
|
const o = new Float32Array(e * 9);
|
|
o.set(this.sh1), this.sh1 = o;
|
|
}
|
|
if (this.sh2) {
|
|
const o = new Float32Array(e * 15);
|
|
o.set(this.sh2), this.sh2 = o;
|
|
}
|
|
if (this.sh3) {
|
|
const o = new Float32Array(e * 21);
|
|
o.set(this.sh3), this.sh3 = o;
|
|
}
|
|
this.maxSplats = e;
|
|
}
|
|
}
|
|
ensureIndex(A) {
|
|
this.ensureCapacity(A + 1);
|
|
}
|
|
setCenter(A, e, s, n) {
|
|
this.centers[A * 3] = e, this.centers[A * 3 + 1] = s, this.centers[A * 3 + 2] = n;
|
|
}
|
|
setScale(A, e, s, n) {
|
|
this.scales[A * 3] = e, this.scales[A * 3 + 1] = s, this.scales[A * 3 + 2] = n;
|
|
}
|
|
setQuaternion(A, e, s, n, i) {
|
|
this.quaternions[A * 4] = e, this.quaternions[A * 4 + 1] = s, this.quaternions[A * 4 + 2] = n, this.quaternions[A * 4 + 3] = i;
|
|
}
|
|
setOpacity(A, e) {
|
|
this.opacities[A] = e;
|
|
}
|
|
setColor(A, e, s, n) {
|
|
this.colors[A * 3] = e, this.colors[A * 3 + 1] = s, this.colors[A * 3 + 2] = n;
|
|
}
|
|
setSh1(A, e) {
|
|
this.sh1 || (this.sh1 = new Float32Array(this.maxSplats * 9));
|
|
for (let s = 0; s < 9; ++s)
|
|
this.sh1[A * 9 + s] = e[s];
|
|
}
|
|
setSh2(A, e) {
|
|
this.sh2 || (this.sh2 = new Float32Array(this.maxSplats * 15));
|
|
for (let s = 0; s < 15; ++s)
|
|
this.sh2[A * 15 + s] = e[s];
|
|
}
|
|
setSh3(A, e) {
|
|
this.sh3 || (this.sh3 = new Float32Array(this.maxSplats * 21));
|
|
for (let s = 0; s < 21; ++s)
|
|
this.sh3[A * 21 + s] = e[s];
|
|
}
|
|
}
|
|
var Ou = `precision highp float;
|
|
precision highp int;
|
|
precision highp sampler2D;
|
|
precision highp usampler2D;
|
|
precision highp isampler2D;
|
|
precision highp sampler2DArray;
|
|
precision highp usampler2DArray;
|
|
precision highp isampler2DArray;
|
|
precision highp sampler3D;
|
|
precision highp usampler3D;
|
|
precision highp isampler3D;
|
|
|
|
#include <splatDefines>
|
|
|
|
uniform uint targetLayer;
|
|
uniform int targetBase;
|
|
uniform int targetCount;
|
|
|
|
out uvec4 target;
|
|
|
|
{{ GLOBALS }}
|
|
|
|
void produceSplat(int index) {
|
|
{{ STATEMENTS }}
|
|
}
|
|
|
|
void main() {
|
|
int targetIndex = int(targetLayer << SPLAT_TEX_LAYER_BITS) + int(uint(gl_FragCoord.y) << SPLAT_TEX_WIDTH_BITS) + int(gl_FragCoord.x);
|
|
int index = targetIndex - targetBase;
|
|
|
|
if ((index >= 0) && (index < targetCount)) {
|
|
produceSplat(index);
|
|
} else {
|
|
target = uvec4(0u, 0u, 0u, 0u);
|
|
}
|
|
}`;
|
|
const de = {
|
|
rgbMin: 0,
|
|
rgbMax: 1,
|
|
lnScaleMin: UA,
|
|
lnScaleMax: GA,
|
|
sh1Min: -1,
|
|
sh1Max: 1,
|
|
sh2Min: -1,
|
|
sh2Max: 1,
|
|
sh3Min: -1,
|
|
sh3Max: 1
|
|
}, nA = class nA {
|
|
constructor(A = {}) {
|
|
this.maxSplats = 0, this.numSplats = 0, this.packedArray = null, this.isInitialized = !1, this.target = null, this.source = null, this.needsUpdate = !0, this.extra = {}, this.dyno = new ls({ packedSplats: this }), this.dynoRgbMinMaxLnScaleMinMax = new Tt({
|
|
key: "rgbMinMaxLnScaleMinMax",
|
|
value: new u.Vector4(0, 1, UA, GA),
|
|
update: (e) => {
|
|
var s, n, i, r;
|
|
return e.set(
|
|
((s = this.splatEncoding) == null ? void 0 : s.rgbMin) ?? 0,
|
|
((n = this.splatEncoding) == null ? void 0 : n.rgbMax) ?? 1,
|
|
((i = this.splatEncoding) == null ? void 0 : i.lnScaleMin) ?? UA,
|
|
((r = this.splatEncoding) == null ? void 0 : r.lnScaleMax) ?? GA
|
|
), e;
|
|
}
|
|
}), this.dynoSh1MinMax = new zt({
|
|
key: "sh1MinMax",
|
|
value: new u.Vector2(-1, 1),
|
|
update: (e) => {
|
|
var s, n;
|
|
return e.set(
|
|
((s = this.splatEncoding) == null ? void 0 : s.sh1Min) ?? -1,
|
|
((n = this.splatEncoding) == null ? void 0 : n.sh1Max) ?? 1
|
|
), e;
|
|
}
|
|
}), this.dynoSh2MinMax = new zt({
|
|
key: "sh2MinMax",
|
|
value: new u.Vector2(-1, 1),
|
|
update: (e) => {
|
|
var s, n;
|
|
return e.set(
|
|
((s = this.splatEncoding) == null ? void 0 : s.sh2Min) ?? -1,
|
|
((n = this.splatEncoding) == null ? void 0 : n.sh2Max) ?? 1
|
|
), e;
|
|
}
|
|
}), this.dynoSh3MinMax = new zt({
|
|
key: "sh3MinMax",
|
|
value: new u.Vector2(-1, 1),
|
|
update: (e) => {
|
|
var s, n;
|
|
return e.set(
|
|
((s = this.splatEncoding) == null ? void 0 : s.sh3Min) ?? -1,
|
|
((n = this.splatEncoding) == null ? void 0 : n.sh3Max) ?? 1
|
|
), e;
|
|
}
|
|
}), this.initialized = Promise.resolve(this), this.reinitialize(A);
|
|
}
|
|
reinitialize(A) {
|
|
this.isInitialized = !1, this.extra = {}, this.splatEncoding = A.splatEncoding, A.url || A.fileBytes || A.construct ? this.initialized = this.asyncInitialize(A).then(() => (this.isInitialized = !0, this)) : (this.initialize(A), this.isInitialized = !0, this.initialized = Promise.resolve(this));
|
|
}
|
|
initialize(A) {
|
|
A.packedArray ? (this.packedArray = A.packedArray, this.maxSplats = Math.floor(this.packedArray.length / 4), this.maxSplats = Math.floor(this.maxSplats / Z) * Z, this.numSplats = Math.min(
|
|
this.maxSplats,
|
|
A.numSplats ?? Number.POSITIVE_INFINITY
|
|
)) : (this.maxSplats = A.maxSplats ?? 0, this.numSplats = 0), this.extra = A.extra ?? {};
|
|
}
|
|
async asyncInitialize(A) {
|
|
const { url: e, fileBytes: s, construct: n } = A;
|
|
if (e) {
|
|
const i = new Vu();
|
|
i.packedSplats = this, await i.loadAsync(e);
|
|
} else if (s) {
|
|
const i = await Ao({
|
|
input: s,
|
|
fileType: A.fileType,
|
|
pathOrUrl: A.fileName ?? e,
|
|
splatEncoding: A.splatEncoding ?? de
|
|
});
|
|
this.initialize(i);
|
|
}
|
|
if (n) {
|
|
const i = n(this);
|
|
i instanceof Promise && await i;
|
|
}
|
|
}
|
|
// Call this when you are finished with the PackedSplats and want to free
|
|
// any buffers it holds.
|
|
dispose() {
|
|
this.target && (this.target.dispose(), this.target = null), this.source && (this.source.dispose(), this.source = null);
|
|
}
|
|
// Ensures that this.packedArray can fit numSplats Gsplats. If it's too small,
|
|
// resize exponentially and copy over the original data.
|
|
//
|
|
// Typically you don't need to call this, because calling this.setSplat(index, ...)
|
|
// and this.pushSplat(...) will automatically call ensureSplats() so we have
|
|
// enough splats.
|
|
ensureSplats(A) {
|
|
const e = A <= this.maxSplats ? this.maxSplats : (
|
|
// Grow exponentially to avoid frequent reallocations
|
|
Math.max(A, 2 * this.maxSplats)
|
|
), s = this.packedArray ? this.packedArray.length / 4 : 0;
|
|
if (!this.packedArray || e > s) {
|
|
this.maxSplats = mA(e).maxSplats;
|
|
const n = new Uint32Array(this.maxSplats * 4);
|
|
this.packedArray && n.set(this.packedArray), this.packedArray = n;
|
|
}
|
|
return this.packedArray;
|
|
}
|
|
// Ensure the extra array for the given level is large enough to hold numSplats
|
|
ensureSplatsSh(A, e) {
|
|
let s, n;
|
|
if (A === 0)
|
|
return this.ensureSplats(e);
|
|
if (A === 1)
|
|
s = 2, n = "sh1";
|
|
else if (A === 2)
|
|
s = 4, n = "sh2";
|
|
else if (A === 3)
|
|
s = 4, n = "sh3";
|
|
else
|
|
throw new Error(`Invalid level: ${A}`);
|
|
let i = this.extra[n] ? this.extra[n].length / s : 0;
|
|
const r = e <= i ? i : Math.max(e, 2 * i);
|
|
if (!this.extra[n] || r > i) {
|
|
i = mA(r).maxSplats;
|
|
const a = new Uint32Array(i * s);
|
|
this.extra[n] && a.set(this.extra[n]), this.extra[n] = a;
|
|
}
|
|
return this.extra[n];
|
|
}
|
|
// Unpack the 16-byte Gsplat data at index into the Three.js components
|
|
// center: THREE.Vector3, scales: THREE.Vector3, quaternion: THREE.Quaternion,
|
|
// opacity: number 0..1, color: THREE.Color 0..1.
|
|
getSplat(A) {
|
|
if (!this.packedArray || A >= this.numSplats)
|
|
throw new Error("Invalid index");
|
|
return Je(this.packedArray, A, this.splatEncoding);
|
|
}
|
|
// Set all PackedSplat components at index with the provided Gsplat attributes
|
|
// (can be the same objects returned by getSplat). Ensures there is capacity
|
|
// for at least index+1 Gsplats.
|
|
setSplat(A, e, s, n, i, r) {
|
|
const a = this.ensureSplats(A + 1);
|
|
Ye(
|
|
a,
|
|
A,
|
|
e.x,
|
|
e.y,
|
|
e.z,
|
|
s.x,
|
|
s.y,
|
|
s.z,
|
|
n.x,
|
|
n.y,
|
|
n.z,
|
|
n.w,
|
|
i,
|
|
r.r,
|
|
r.g,
|
|
r.b
|
|
), this.numSplats = Math.max(this.numSplats, A + 1);
|
|
}
|
|
// Effectively calls this.setSplat(this.numSplats++, center, ...), useful on
|
|
// construction where you just want to iterate and create a collection of Gsplats.
|
|
pushSplat(A, e, s, n, i) {
|
|
const r = this.ensureSplats(this.numSplats + 1);
|
|
Ye(
|
|
r,
|
|
this.numSplats,
|
|
A.x,
|
|
A.y,
|
|
A.z,
|
|
e.x,
|
|
e.y,
|
|
e.z,
|
|
s.x,
|
|
s.y,
|
|
s.z,
|
|
s.w,
|
|
n,
|
|
i.r,
|
|
i.g,
|
|
i.b
|
|
), ++this.numSplats;
|
|
}
|
|
// Iterate over Gsplats index 0..=(this.numSplats-1), unpack each Gsplat
|
|
// and invoke the callback function with the Gsplat attributes.
|
|
forEachSplat(A) {
|
|
if (!(!this.packedArray || !this.numSplats))
|
|
for (let e = 0; e < this.numSplats; ++e) {
|
|
const s = Je(this.packedArray, e, this.splatEncoding);
|
|
A(
|
|
e,
|
|
s.center,
|
|
s.scales,
|
|
s.quaternion,
|
|
s.opacity,
|
|
s.color
|
|
);
|
|
}
|
|
}
|
|
// Ensures our PackedSplats.target render target has enough space to generate
|
|
// maxSplats total Gsplats, and reallocate if not large enough.
|
|
ensureGenerate(A) {
|
|
if (this.target && (A ?? 1) <= this.maxSplats)
|
|
return !1;
|
|
this.dispose();
|
|
const e = mA(A ?? 1), { width: s, height: n, depth: i } = e;
|
|
return this.maxSplats = e.maxSplats, this.target = new u.WebGLArrayRenderTarget(s, n, i, {
|
|
depthBuffer: !1,
|
|
stencilBuffer: !1,
|
|
generateMipmaps: !1,
|
|
magFilter: u.NearestFilter,
|
|
minFilter: u.NearestFilter
|
|
}), this.target.texture.format = u.RGBAIntegerFormat, this.target.texture.type = u.UnsignedIntType, this.target.texture.internalFormat = "RGBA32UI", this.target.scissorTest = !0, !0;
|
|
}
|
|
// Given an array of splatCounts (.numSplats for each
|
|
// SplatGenerator/SplatMesh in the scene), compute a
|
|
// "mapping layout" in the composite array of generated outputs.
|
|
generateMapping(A) {
|
|
let e = 0;
|
|
const s = A.map((n) => {
|
|
const i = e, r = Math.ceil(n / Z) * Z;
|
|
return e += r, { base: i, count: n };
|
|
});
|
|
return { maxSplats: e, mapping: s };
|
|
}
|
|
// Returns a THREE.DataArrayTexture representing the PackedSplats content as
|
|
// a Uint32x4 data array texture (2048 x 2048 x depth in size)
|
|
getTexture() {
|
|
return this.target ? this.target.texture : this.source || this.packedArray ? this.maybeUpdateSource() : nA.getEmpty();
|
|
}
|
|
// Check if source texture needs to be created/updated
|
|
maybeUpdateSource() {
|
|
if (!this.packedArray)
|
|
throw new Error("No packed splats");
|
|
if (this.needsUpdate || !this.source) {
|
|
if (this.needsUpdate = !1, this.source) {
|
|
const { width: A, height: e, depth: s } = this.source.image;
|
|
this.maxSplats !== A * e * s && (this.source.dispose(), this.source = null);
|
|
}
|
|
if (this.source)
|
|
this.packedArray.buffer !== this.source.image.data.buffer && (this.source.image.data = new Uint8Array(this.packedArray.buffer));
|
|
else {
|
|
const { width: A, height: e, depth: s } = mA(this.maxSplats);
|
|
this.source = new u.DataArrayTexture(
|
|
this.packedArray,
|
|
A,
|
|
e,
|
|
s
|
|
), this.source.format = u.RGBAIntegerFormat, this.source.type = u.UnsignedIntType, this.source.internalFormat = "RGBA32UI", this.source.needsUpdate = !0;
|
|
}
|
|
this.source.needsUpdate = !0;
|
|
}
|
|
return this.source;
|
|
}
|
|
// Can be used where you need an uninitialized THREE.DataArrayTexture like
|
|
// a uniform you will update with the result of this.getTexture() later.
|
|
static getEmpty() {
|
|
if (!nA.emptySource) {
|
|
const { width: A, height: e, depth: s, maxSplats: n } = mA(1), i = new Uint32Array(n * 4);
|
|
nA.emptySource = new u.DataArrayTexture(
|
|
i,
|
|
A,
|
|
e,
|
|
s
|
|
), nA.emptySource.format = u.RGBAIntegerFormat, nA.emptySource.type = u.UnsignedIntType, nA.emptySource.internalFormat = "RGBA32UI", nA.emptySource.needsUpdate = !0;
|
|
}
|
|
return nA.emptySource;
|
|
}
|
|
// Get a program and THREE.RawShaderMaterial for a given GsplatGenerator,
|
|
// generating it if necessary and caching the result.
|
|
prepareProgramMaterial(A) {
|
|
let e = nA.generatorProgram.get(A);
|
|
if (!e) {
|
|
const n = vA(
|
|
{ index: "int" },
|
|
{ output: "uvec4" },
|
|
({ index: i }) => {
|
|
A.inputs.index = i;
|
|
const r = A.outputs.gsplat;
|
|
return { output: en(
|
|
r,
|
|
this.dynoRgbMinMaxLnScaleMinMax
|
|
) };
|
|
}
|
|
);
|
|
nA.programTemplate || (nA.programTemplate = new is(
|
|
Ou
|
|
)), e = new ns({
|
|
graph: n,
|
|
inputs: { index: "index" },
|
|
outputs: { output: "target" },
|
|
template: nA.programTemplate
|
|
}), Object.assign(e.uniforms, {
|
|
targetLayer: { value: 0 },
|
|
targetBase: { value: 0 },
|
|
targetCount: { value: 0 }
|
|
}), nA.generatorProgram.set(A, e);
|
|
}
|
|
const s = e.prepareMaterial();
|
|
return nA.fullScreenQuad.material = s, { program: e, material: s };
|
|
}
|
|
saveRenderState(A) {
|
|
return {
|
|
xrEnabled: A.xr.enabled,
|
|
autoClear: A.autoClear
|
|
};
|
|
}
|
|
resetRenderState(A, e) {
|
|
A.setRenderTarget(null), A.xr.enabled = e.xrEnabled, A.autoClear = e.autoClear;
|
|
}
|
|
// Executes a dyno program specified by generator which is any DynoBlock that
|
|
// maps { index: "int" } to { gsplat: Gsplat }. This is called in
|
|
// SparkRenderer.updateInternal() to re-generate Gsplats in the scene for
|
|
// SplatGenerator instances whose version is newer than what was generated
|
|
// for it last time.
|
|
generate({
|
|
generator: A,
|
|
base: e,
|
|
count: s,
|
|
renderer: n
|
|
}) {
|
|
if (!this.target)
|
|
throw new Error("Target must be initialized with ensureSplats");
|
|
if (e + s > this.maxSplats)
|
|
throw new Error("Base + count exceeds maxSplats");
|
|
const { program: i, material: r } = this.prepareProgramMaterial(A);
|
|
i.update();
|
|
const a = this.saveRenderState(n), o = Math.ceil((e + s) / Z) * Z, g = Z * KA;
|
|
for (r.uniforms.targetBase.value = e, r.uniforms.targetCount.value = s; e < o; ) {
|
|
const l = Math.floor(e / g);
|
|
r.uniforms.targetLayer.value = l;
|
|
const c = l * g, I = Math.floor((e - c) / Z), h = Math.min(
|
|
KA,
|
|
Math.ceil((o - c) / Z)
|
|
);
|
|
this.target.scissor.set(
|
|
0,
|
|
I,
|
|
Z,
|
|
h - I
|
|
), n.setRenderTarget(this.target, l), n.xr.enabled = !1, n.autoClear = !1, nA.fullScreenQuad.render(n), e += Z * (h - I);
|
|
}
|
|
return this.resetRenderState(n, a), { nextBase: o };
|
|
}
|
|
};
|
|
nA.emptySource = null, nA.programTemplate = null, nA.generatorProgram = /* @__PURE__ */ new Map(), nA.fullScreenQuad = new xs(
|
|
new u.RawShaderMaterial({ visible: !1 })
|
|
);
|
|
let VA = nA;
|
|
class ls extends N {
|
|
constructor({ packedSplats: A } = {}) {
|
|
super({
|
|
key: "packedSplats",
|
|
type: jt,
|
|
globals: () => [Qe],
|
|
value: {
|
|
texture: VA.getEmpty(),
|
|
numSplats: 0,
|
|
rgbMinMaxLnScaleMinMax: new u.Vector4(
|
|
0,
|
|
1,
|
|
UA,
|
|
GA
|
|
)
|
|
},
|
|
update: (e) => {
|
|
var s, n, i, r, a, o, g, l, c, I;
|
|
return e.texture = ((s = this.packedSplats) == null ? void 0 : s.getTexture()) ?? VA.getEmpty(), e.numSplats = ((n = this.packedSplats) == null ? void 0 : n.numSplats) ?? 0, e.rgbMinMaxLnScaleMinMax.set(
|
|
((r = (i = this.packedSplats) == null ? void 0 : i.splatEncoding) == null ? void 0 : r.rgbMin) ?? 0,
|
|
((o = (a = this.packedSplats) == null ? void 0 : a.splatEncoding) == null ? void 0 : o.rgbMax) ?? 1,
|
|
((l = (g = this.packedSplats) == null ? void 0 : g.splatEncoding) == null ? void 0 : l.lnScaleMin) ?? UA,
|
|
((I = (c = this.packedSplats) == null ? void 0 : c.splatEncoding) == null ? void 0 : I.lnScaleMax) ?? GA
|
|
), e;
|
|
}
|
|
}), this.packedSplats = A;
|
|
}
|
|
}
|
|
class Ve extends u.InstancedBufferGeometry {
|
|
constructor(A, e) {
|
|
super(), this.ordering = A, this.setAttribute("position", new u.BufferAttribute(ju, 3)), this.setIndex(new u.BufferAttribute(Wu, 1)), this._maxInstanceCount = A.length, this.instanceCount = e, this.attribute = new u.InstancedBufferAttribute(A, 1, !1, 1), this.attribute.setUsage(u.DynamicDrawUsage), this.setAttribute("splatIndex", this.attribute);
|
|
}
|
|
update(A, e) {
|
|
this.ordering = A, this.attribute.array = A, this.instanceCount = e, this.attribute.addUpdateRange(0, e), this.attribute.needsUpdate = !0;
|
|
}
|
|
}
|
|
const ju = new Float32Array([
|
|
-1,
|
|
-1,
|
|
0,
|
|
1,
|
|
-1,
|
|
0,
|
|
1,
|
|
1,
|
|
0,
|
|
-1,
|
|
1,
|
|
0
|
|
]), Wu = new Uint16Array([0, 1, 2, 0, 2, 3]), nt = class nt {
|
|
constructor(A) {
|
|
if (this.lastTime = null, this.encodeLinear = !1, this.superXY = 1, this.display = null, this.sorting = null, this.pending = null, this.sortingCheck = !1, this.readback16 = new Uint16Array(0), this.readback32 = new Uint32Array(0), this.spark = A.spark, this.camera = A.camera, this.viewToWorld = A.viewToWorld ?? new u.Matrix4(), A.target) {
|
|
const { width: e, height: s, doubleBuffer: n } = A.target, i = Math.max(1, Math.min(4, A.target.superXY ?? 1));
|
|
if (this.superXY = i, e * i > 8192 || s * i > 8192)
|
|
throw new Error("Target size too large");
|
|
this.target = new u.WebGLRenderTarget(
|
|
e * i,
|
|
s * i,
|
|
{
|
|
format: u.RGBAFormat,
|
|
type: u.UnsignedByteType,
|
|
colorSpace: u.SRGBColorSpace
|
|
}
|
|
), n && (this.back = new u.WebGLRenderTarget(
|
|
e * i,
|
|
s * i,
|
|
{
|
|
format: u.RGBAFormat,
|
|
type: u.UnsignedByteType,
|
|
colorSpace: u.SRGBColorSpace
|
|
}
|
|
)), this.encodeLinear = !0;
|
|
}
|
|
this.onTextureUpdated = A.onTextureUpdated, this.sortRadial = A.sortRadial ?? !0, this.sortDistance = A.sortDistance, this.sortCoorient = A.sortCoorient, this.depthBias = A.depthBias, this.sort360 = A.sort360, this.sort32 = A.sort32, this.stochastic = A.stochastic ?? !1, this.orderingFreelist = new qn({
|
|
allocate: (e) => new Uint32Array(e),
|
|
valid: (e, s) => e.length === s
|
|
}), this.autoUpdate = !1, this.setAutoUpdate(A.autoUpdate ?? !1);
|
|
}
|
|
// Call this when you are done with the SparkViewpoint and want to
|
|
// free up its resources (GPU targets, pixel buffers, etc.)
|
|
dispose() {
|
|
var A;
|
|
this.setAutoUpdate(!1), this.target && (this.target.dispose(), this.target = void 0), this.back && (this.back.dispose(), this.back = void 0), this.display && (this.spark.releaseAccumulator(this.display.accumulator), this.display.geometry.dispose(), this.display = null), (A = this.pending) != null && A.accumulator && (this.spark.releaseAccumulator(this.pending.accumulator), this.pending = null);
|
|
}
|
|
// Use this function to change whether this viewpoint will auto-update
|
|
// its sort order whenever the attached SparkRenderer updates the Gsplats.
|
|
// Turn this on or off depending on whether you expect to do renders from
|
|
// this viewpoint most frames.
|
|
setAutoUpdate(A) {
|
|
!this.autoUpdate && A ? this.spark.autoViewpoints.push(this) : this.autoUpdate && !A && (this.spark.autoViewpoints = this.spark.autoViewpoints.filter(
|
|
(e) => e !== this
|
|
)), this.autoUpdate = A;
|
|
}
|
|
// See below async prepareRenderPixels() for explanation of parameters.
|
|
// Awaiting this method updates the Gsplats in the scene and performs a sort of the
|
|
// Gsplats from this viewpoint, preparing it for a subsequent this.renderTarget()
|
|
// call in the same tick.
|
|
async prepare({
|
|
scene: A,
|
|
camera: e,
|
|
viewToWorld: s,
|
|
update: n,
|
|
forceOrigin: i
|
|
}) {
|
|
var a;
|
|
for (s ? this.viewToWorld = s : (this.camera = e ?? this.camera, this.camera && (this.camera.updateMatrixWorld(), this.viewToWorld = this.camera.matrixWorld.clone())); n ?? !0; ) {
|
|
const o = i ? this.viewToWorld : void 0;
|
|
if (this.spark.updateInternal({ scene: A, originToWorld: o }))
|
|
break;
|
|
await new Promise((l) => setTimeout(l, 10));
|
|
}
|
|
const r = this.spark.active;
|
|
r !== ((a = this.display) == null ? void 0 : a.accumulator) && (this.spark.active.refCount += 1), await this.sortUpdate({ accumulator: r, viewToWorld: this.viewToWorld });
|
|
}
|
|
// Render out the viewpoint to the view target RGBA buffer.
|
|
// Swaps buffers if doubleBuffer: true was set.
|
|
// Calls onTextureUpdated(texture) with the resulting texture.
|
|
renderTarget({
|
|
scene: A,
|
|
camera: e
|
|
}) {
|
|
var n;
|
|
const s = this.back ?? this.target;
|
|
if (!s)
|
|
throw new Error("Must initialize SparkViewpoint with target");
|
|
if (e = e ?? this.camera, !e)
|
|
throw new Error("Must provide camera");
|
|
if (e instanceof u.PerspectiveCamera) {
|
|
const i = new u.PerspectiveCamera().copy(e, !1);
|
|
i.aspect = s.width / s.height, i.updateProjectionMatrix(), e = i;
|
|
}
|
|
this.viewToWorld = e.matrixWorld.clone();
|
|
try {
|
|
this.spark.renderer.setRenderTarget(s), this.spark.prepareViewpoint(this), this.spark.renderer.render(A, e);
|
|
} finally {
|
|
this.spark.prepareViewpoint(this.spark.defaultView), this.spark.renderer.setRenderTarget(null);
|
|
}
|
|
s !== this.target && ([this.target, this.back] = [this.back, this.target]), (n = this.onTextureUpdated) == null || n.call(this, s.texture);
|
|
}
|
|
// Read back the previously rendered target image as a Uint8Array of packed
|
|
// RGBA values (in that order). If superXY was set greater than 1 then
|
|
// downsampling is performed in the target pixel array with simple averaging
|
|
// to derive the returned pixel values. Subsequent calls to this.readTarget()
|
|
// will reuse the same buffers to minimize memory allocations.
|
|
async readTarget() {
|
|
if (!this.target)
|
|
throw new Error("Must initialize SparkViewpoint with target");
|
|
const { width: A, height: e } = this.target, s = A * e * 4;
|
|
(!this.superPixels || this.superPixels.length < s) && (this.superPixels = new Uint8Array(s)), await this.spark.renderer.readRenderTargetPixelsAsync(
|
|
this.target,
|
|
0,
|
|
0,
|
|
A,
|
|
e,
|
|
this.superPixels
|
|
);
|
|
const { superXY: n } = this;
|
|
if (n === 1)
|
|
return this.superPixels;
|
|
const i = A / n, r = e / n, a = i * r * 4;
|
|
(!this.pixels || this.pixels.length < a) && (this.pixels = new Uint8Array(a));
|
|
const { superPixels: o, pixels: g } = this, l = n * n;
|
|
for (let c = 0; c < r; c++) {
|
|
const I = c * i;
|
|
for (let h = 0; h < i; h++) {
|
|
const E = h * n;
|
|
let C = 0, B = 0, Q = 0, f = 0;
|
|
for (let d = 0; d < n; d++) {
|
|
const y = (c * n + d) * this.target.width;
|
|
for (let D = 0; D < n; D++) {
|
|
const x = (y + E + D) * 4;
|
|
C += o[x], B += o[x + 1], Q += o[x + 2], f += o[x + 3];
|
|
}
|
|
}
|
|
const p = (I + h) * 4;
|
|
g[p] = C / l, g[p + 1] = B / l, g[p + 2] = Q / l, g[p + 3] = f / l;
|
|
}
|
|
}
|
|
return g;
|
|
}
|
|
// Render out a viewpoint as a Uint8Array of RGBA values for the provided scene
|
|
// and any camera/viewToWorld viewpoint overrides. By default update is true,
|
|
// which triggers its SparkRenderer to check and potentially update the Gsplats.
|
|
// Setting update to false disables this and sorts the Gsplats as they are.
|
|
// Setting forceOrigin (default: false) to true forces the view update to
|
|
// recalculate the splats with this view origin, potentially altering any
|
|
// view-dependent effects. If you expect view-dependent effects to play a role
|
|
// in the rendering quality, enable this.
|
|
//
|
|
// Underneath, prepareRenderPixels() simply calls await this.prepare(...),
|
|
// this.renderTarget(...), and finally returns the result this.readTarget(),
|
|
// a Promise to a Uint8Array with RGBA values for all the pixels (potentially
|
|
// downsampled if the superXY parameter was used). These steps can also be called
|
|
// manually, for example if you need to alter the scene before and after
|
|
// this.renderTarget(...) to hide UI elements from being rendered.
|
|
async prepareRenderPixels({
|
|
scene: A,
|
|
camera: e,
|
|
viewToWorld: s,
|
|
update: n,
|
|
forceOrigin: i
|
|
}) {
|
|
return await this.prepare({ scene: A, camera: e, viewToWorld: s, update: n, forceOrigin: i }), this.renderTarget({ scene: A, camera: e }), this.readTarget();
|
|
}
|
|
// This is called automatically by SparkRenderer, there is no need to call it!
|
|
// The method cannot be private because then SparkRenderer would
|
|
// not be able to call it.
|
|
autoPoll({ accumulator: A }) {
|
|
var i, r, a, o;
|
|
this.camera && (this.camera.updateMatrixWorld(), this.viewToWorld = this.camera.matrixWorld.clone());
|
|
let e = !1, s = !1;
|
|
if (!this.display)
|
|
e = !0;
|
|
else if (A) {
|
|
e = !0;
|
|
const { mappingVersion: g } = this.display.accumulator;
|
|
A.mappingVersion === g && (this.spark.releaseAccumulator(this.display.accumulator), this.display.accumulator = A, s = !0);
|
|
}
|
|
const n = ((i = this.sorting) == null ? void 0 : i.viewToWorld) ?? ((r = this.display) == null ? void 0 : r.viewToWorld);
|
|
n && !ge({
|
|
matrix1: this.viewToWorld,
|
|
matrix2: n,
|
|
// By default update sort each 1 cm
|
|
maxDistance: this.sortDistance ?? 0.01,
|
|
// By default for radial sort, update for intermittent movement so that
|
|
// we bring back splats culled by being behind the camera.
|
|
// For depth sort, small rotations can change sort order a lot, so
|
|
// update sort for even small rotations.
|
|
minCoorient: this.sortCoorient ?? this.sortRadial ? 0.99 : 0.999
|
|
}) && (e = !0), e && (A && (A.refCount += 1), A && ((a = this.pending) != null && a.accumulator) && this.pending.accumulator !== ((o = this.display) == null ? void 0 : o.accumulator) && this.spark.releaseAccumulator(this.pending.accumulator), this.pending = { accumulator: A, viewToWorld: this.viewToWorld, displayed: s }, this.driveSort());
|
|
}
|
|
async driveSort() {
|
|
var A;
|
|
for (; ; ) {
|
|
if (this.sorting || !this.pending)
|
|
return;
|
|
const { viewToWorld: e, displayed: s } = this.pending;
|
|
let n = this.pending.accumulator ?? ((A = this.display) == null ? void 0 : A.accumulator);
|
|
if (n || (n = this.spark.active, n.refCount += 1), this.pending = null, !n)
|
|
throw new Error("No accumulator to sort");
|
|
this.sorting = { viewToWorld: e }, await this.sortUpdate({ accumulator: n, viewToWorld: e, displayed: s }), this.sorting = null;
|
|
}
|
|
}
|
|
async sortUpdate({
|
|
accumulator: A,
|
|
viewToWorld: e,
|
|
displayed: s = !1
|
|
}) {
|
|
if (this.sortingCheck)
|
|
throw new Error("Only one sort at a time");
|
|
this.sortingCheck = !0, A = A ?? this.spark.active;
|
|
const { numSplats: n, maxSplats: i } = A.splats;
|
|
let r = 0, a = this.orderingFreelist.alloc(i);
|
|
if (this.stochastic) {
|
|
r = n;
|
|
for (let o = 0; o < n; ++o)
|
|
a[o] = o;
|
|
} else if (n > 0) {
|
|
const {
|
|
reader: o,
|
|
doubleSortReader: g,
|
|
sort32Reader: l,
|
|
dynoSortRadial: c,
|
|
dynoOrigin: I,
|
|
dynoDirection: h,
|
|
dynoDepthBias: E,
|
|
dynoSort360: C,
|
|
dynoSplats: B
|
|
} = nt.makeSorter(), Q = this.sort32 ?? !1;
|
|
let f;
|
|
if (Q)
|
|
this.readback32 = o.ensureBuffer(i, this.readback32), f = this.readback32;
|
|
else {
|
|
const w = Math.ceil(i / 2);
|
|
this.readback16 = o.ensureBuffer(w, this.readback16), f = this.readback16;
|
|
}
|
|
const p = A.toWorld.clone().invert(), d = e.clone().premultiply(p);
|
|
c.value = this.sort360 ? !0 : this.sortRadial, I.value.set(0, 0, 0).applyMatrix4(d), h.value.set(0, 0, -1).applyMatrix4(d).sub(I.value).normalize(), E.value = this.depthBias ?? 1, C.value = this.sort360 ?? !1, B.packedSplats = A.splats;
|
|
const y = Q ? l : g, D = Q ? n : Math.ceil(n / 2);
|
|
await o.renderReadback({
|
|
renderer: this.spark.renderer,
|
|
reader: y,
|
|
count: D,
|
|
readback: f
|
|
});
|
|
const x = await lt(async (w) => {
|
|
const m = Q ? "sort32Splats" : "sortDoubleSplats";
|
|
return w.call(m, {
|
|
maxSplats: i,
|
|
numSplats: n,
|
|
readback: f,
|
|
ordering: a
|
|
});
|
|
});
|
|
Q ? this.readback32 = x.readback : this.readback16 = x.readback, a = x.ordering, r = x.activeSplats;
|
|
}
|
|
this.updateDisplay({
|
|
accumulator: A,
|
|
viewToWorld: e,
|
|
ordering: a,
|
|
activeSplats: r,
|
|
displayed: s
|
|
}), this.sortingCheck = !1;
|
|
}
|
|
updateDisplay({
|
|
accumulator: A,
|
|
viewToWorld: e,
|
|
ordering: s,
|
|
activeSplats: n,
|
|
displayed: i = !1
|
|
}) {
|
|
if (!this.display)
|
|
this.display = {
|
|
accumulator: A,
|
|
viewToWorld: e,
|
|
geometry: new Ve(s, n)
|
|
};
|
|
else {
|
|
!i && A !== this.display.accumulator && (this.spark.releaseAccumulator(this.display.accumulator), this.display.accumulator = A), this.display.viewToWorld = e;
|
|
const r = this.display.geometry.ordering;
|
|
r.length === s.length ? this.display.geometry.update(s, n) : (this.display.geometry.dispose(), this.display.geometry = new Ve(s, n)), this.orderingFreelist.free(r);
|
|
}
|
|
this.spark.viewpoint === this && this.spark.prepareViewpoint(this);
|
|
}
|
|
static makeSorter() {
|
|
if (!nt.dynos) {
|
|
const A = new ce({ value: !0 }), e = new Ft({ value: new u.Vector3() }), s = new Ft({ value: new u.Vector3() }), n = new ht({ value: 1 }), i = new ce({ value: !1 }), r = new ls(), a = new le(), o = vA(
|
|
{ index: "int" },
|
|
{ rgba8: "vec4" },
|
|
({ index: l }) => {
|
|
if (!l)
|
|
throw new Error("No index");
|
|
const c = {
|
|
sortRadial: A,
|
|
sortOrigin: e,
|
|
sortDirection: s,
|
|
sortDepthBias: n,
|
|
sort360: i
|
|
}, I = iA(l, J("int", 2)), h = bt(r, I), E = Ne({ gsplat: h, ...c }), C = bt(
|
|
r,
|
|
BA(I, J("int", 1))
|
|
), B = Ne({ gsplat: C, ...c }), Q = $A({
|
|
vectorType: "vec2",
|
|
x: E,
|
|
y: B
|
|
});
|
|
return { rgba8: ze(nr(Q)) };
|
|
}
|
|
), g = vA(
|
|
{ index: "int" },
|
|
{ rgba8: "vec4" },
|
|
({ index: l }) => {
|
|
if (!l)
|
|
throw new Error("No index");
|
|
const c = {
|
|
sortRadial: A,
|
|
sortOrigin: e,
|
|
sortDirection: s,
|
|
sortDepthBias: n,
|
|
sort360: i
|
|
}, I = bt(r, l), h = Ne({ gsplat: I, ...c });
|
|
return { rgba8: ze(sr(h)) };
|
|
}
|
|
);
|
|
nt.dynos = {
|
|
dynoSortRadial: A,
|
|
dynoOrigin: e,
|
|
dynoDirection: s,
|
|
dynoDepthBias: n,
|
|
dynoSort360: i,
|
|
dynoSplats: r,
|
|
reader: a,
|
|
doubleSortReader: o,
|
|
sort32Reader: g
|
|
};
|
|
}
|
|
return nt.dynos;
|
|
}
|
|
};
|
|
nt.EMPTY_TEXTURE = new u.Texture(), nt.dynos = null;
|
|
let Ce = nt;
|
|
const Ah = hA(`
|
|
float computeSort(Gsplat gsplat, bool sortRadial, vec3 sortOrigin, vec3 sortDirection, float sortDepthBias, bool sort360) {
|
|
if (!isGsplatActive(gsplat.flags)) {
|
|
return INFINITY;
|
|
}
|
|
|
|
vec3 center = gsplat.center - sortOrigin;
|
|
float biasedDepth = dot(center, sortDirection) + sortDepthBias;
|
|
if (!sort360 && (biasedDepth <= 0.0)) {
|
|
return INFINITY;
|
|
}
|
|
|
|
return sortRadial ? length(center) : biasedDepth;
|
|
}
|
|
`);
|
|
function Ne({
|
|
gsplat: t,
|
|
sortRadial: A,
|
|
sortOrigin: e,
|
|
sortDirection: s,
|
|
sortDepthBias: n,
|
|
sort360: i
|
|
}) {
|
|
return Ot({
|
|
inTypes: {
|
|
gsplat: AA,
|
|
sortRadial: "bool",
|
|
sortOrigin: "vec3",
|
|
sortDirection: "vec3",
|
|
sortDepthBias: "float",
|
|
sort360: "bool"
|
|
},
|
|
outTypes: { metric: "float" },
|
|
globals: () => [bA, Ah],
|
|
inputs: {
|
|
gsplat: t,
|
|
sortRadial: A,
|
|
sortOrigin: e,
|
|
sortDirection: s,
|
|
sortDepthBias: n,
|
|
sort360: i
|
|
},
|
|
statements: ({ inputs: r, outputs: a }) => {
|
|
const {
|
|
gsplat: o,
|
|
sortRadial: g,
|
|
sortOrigin: l,
|
|
sortDirection: c,
|
|
sortDepthBias: I,
|
|
sort360: h
|
|
} = r;
|
|
return RA(`
|
|
${a.metric} = computeSort(${o}, ${g}, ${l}, ${c}, ${I}, ${h});
|
|
`);
|
|
}
|
|
}).outputs.metric;
|
|
}
|
|
class ke {
|
|
constructor() {
|
|
this.splats = new VA(), this.toWorld = new u.Matrix4(), this.mapping = [], this.refCount = 0, this.splatsVersion = -1, this.mappingVersion = -1;
|
|
}
|
|
ensureGenerate(A) {
|
|
this.splats.ensureGenerate(A) && (this.mapping = []);
|
|
}
|
|
// Generate all Gsplats from an array of generators
|
|
generateSplats({
|
|
renderer: A,
|
|
modifier: e,
|
|
generators: s,
|
|
forceUpdate: n,
|
|
originToWorld: i
|
|
}) {
|
|
const r = this.mapping.reduce((g, l) => (g.set(l.node, l), g), /* @__PURE__ */ new Map());
|
|
let a = 0, o = 0;
|
|
for (const { node: g, generator: l, version: c, base: I, count: h } of s) {
|
|
const E = r.get(g);
|
|
if ((n || l !== (E == null ? void 0 : E.generator) || c !== (E == null ? void 0 : E.version) || I !== (E == null ? void 0 : E.base) || h !== (E == null ? void 0 : E.count)) && l && h > 0) {
|
|
const C = e.apply(l);
|
|
try {
|
|
this.splats.generate({
|
|
generator: C,
|
|
base: I,
|
|
count: h,
|
|
renderer: A
|
|
});
|
|
} catch (B) {
|
|
g.generator = void 0, g.generatorError = B;
|
|
}
|
|
a += 1;
|
|
}
|
|
o = Math.max(o, I + h);
|
|
}
|
|
return this.splats.numSplats = o, this.toWorld = i, this.mapping = s, a !== 0;
|
|
}
|
|
// Check if this accumulator has exactly the same generator mapping as
|
|
// the previous one. If so, we can reuse the Gsplat sort order.
|
|
hasCorrespondence(A) {
|
|
return this.mapping.length !== A.mapping.length ? !1 : this.mapping.every(({ node: e, base: s, count: n }, i) => {
|
|
const {
|
|
node: r,
|
|
base: a,
|
|
count: o
|
|
} = A.mapping[i];
|
|
return e === r && s === a && n === o;
|
|
});
|
|
}
|
|
}
|
|
var th = `const float LN_SCALE_MIN = -12.0;
|
|
const float LN_SCALE_MAX = 9.0;
|
|
|
|
const uint SPLAT_TEX_WIDTH_BITS = 11u;
|
|
const uint SPLAT_TEX_HEIGHT_BITS = 11u;
|
|
const uint SPLAT_TEX_DEPTH_BITS = 11u;
|
|
const uint SPLAT_TEX_LAYER_BITS = SPLAT_TEX_WIDTH_BITS + SPLAT_TEX_HEIGHT_BITS;
|
|
|
|
const uint SPLAT_TEX_WIDTH = 1u << SPLAT_TEX_WIDTH_BITS;
|
|
const uint SPLAT_TEX_HEIGHT = 1u << SPLAT_TEX_HEIGHT_BITS;
|
|
const uint SPLAT_TEX_DEPTH = 1u << SPLAT_TEX_DEPTH_BITS;
|
|
|
|
const uint SPLAT_TEX_WIDTH_MASK = SPLAT_TEX_WIDTH - 1u;
|
|
const uint SPLAT_TEX_HEIGHT_MASK = SPLAT_TEX_HEIGHT - 1u;
|
|
const uint SPLAT_TEX_DEPTH_MASK = SPLAT_TEX_DEPTH - 1u;
|
|
|
|
const uint F16_INF = 0x7c00u;
|
|
const float PI = 3.1415926535897932384626433832795;
|
|
|
|
const float INFINITY = 1.0 / 0.0;
|
|
const float NEG_INFINITY = -INFINITY;
|
|
|
|
float sqr(float x) {
|
|
return x * x;
|
|
}
|
|
|
|
float pow4(float x) {
|
|
float x2 = x * x;
|
|
return x2 * x2;
|
|
}
|
|
|
|
float pow8(float x) {
|
|
float x4 = pow4(x);
|
|
return x4 * x4;
|
|
}
|
|
|
|
vec3 srgbToLinear(vec3 rgb) {
|
|
return pow(rgb, vec3(2.2));
|
|
}
|
|
|
|
vec3 linearToSrgb(vec3 rgb) {
|
|
return pow(rgb, vec3(1.0 / 2.2));
|
|
}
|
|
|
|
uint encodeQuatOctXy88R8(vec4 q) {
|
|
|
|
if (q.w < 0.0) {
|
|
q = -q;
|
|
}
|
|
|
|
float theta = 2.0 * acos(q.w);
|
|
float halfTheta = theta * 0.5;
|
|
float s = sin(halfTheta);
|
|
|
|
vec3 axis = (abs(s) < 1e-6) ? vec3(1.0, 0.0, 0.0) : q.xyz / s;
|
|
|
|
|
|
|
|
float sum = abs(axis.x) + abs(axis.y) + abs(axis.z);
|
|
vec2 p = vec2(axis.x, axis.y) / sum;
|
|
|
|
if (axis.z < 0.0) {
|
|
float oldPx = p.x;
|
|
p.x = (1.0 - abs(p.y)) * (p.x >= 0.0 ? 1.0 : -1.0);
|
|
p.y = (1.0 - abs(oldPx)) * (p.y >= 0.0 ? 1.0 : -1.0);
|
|
}
|
|
|
|
float u_f = p.x * 0.5 + 0.5;
|
|
float v_f = p.y * 0.5 + 0.5;
|
|
|
|
uint quantU = uint(clamp(round(u_f * 255.0), 0.0, 255.0));
|
|
uint quantV = uint(clamp(round(v_f * 255.0), 0.0, 255.0));
|
|
|
|
|
|
|
|
uint angleInt = uint(clamp(round((theta / 3.14159265359) * 255.0), 0.0, 255.0));
|
|
|
|
|
|
return (angleInt << 16u) | (quantV << 8u) | quantU;
|
|
}
|
|
|
|
vec4 decodeQuatOctXy88R8(uint encoded) {
|
|
|
|
uint quantU = encoded & uint(0xFFu);
|
|
uint quantV = (encoded >> 8u) & uint(0xFFu);
|
|
uint angleInt = encoded >> 16u;
|
|
|
|
|
|
float u_f = float(quantU) / 255.0;
|
|
float v_f = float(quantV) / 255.0;
|
|
vec2 f = vec2(u_f * 2.0 - 1.0, v_f * 2.0 - 1.0);
|
|
|
|
vec3 axis = vec3(f.xy, 1.0 - abs(f.x) - abs(f.y));
|
|
float t = max(-axis.z, 0.0);
|
|
axis.x += (axis.x >= 0.0) ? -t : t;
|
|
axis.y += (axis.y >= 0.0) ? -t : t;
|
|
axis = normalize(axis);
|
|
|
|
|
|
float theta = (float(angleInt) / 255.0) * 3.14159265359;
|
|
float halfTheta = theta * 0.5;
|
|
float s = sin(halfTheta);
|
|
float w = cos(halfTheta);
|
|
|
|
return vec4(axis * s, w);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
uvec4 packSplatEncoding(
|
|
vec3 center, vec3 scales, vec4 quaternion, vec4 rgba, vec4 rgbMinMaxLnScaleMinMax
|
|
) {
|
|
float rgbMin = rgbMinMaxLnScaleMinMax.x;
|
|
float rgbMax = rgbMinMaxLnScaleMinMax.y;
|
|
vec3 encRgb = (rgba.rgb - vec3(rgbMin)) / (rgbMax - rgbMin);
|
|
uvec4 uRgba = uvec4(round(clamp(vec4(encRgb, rgba.a) * 255.0, 0.0, 255.0)));
|
|
|
|
uint uQuat = encodeQuatOctXy88R8(quaternion);
|
|
|
|
|
|
uvec3 uQuat3 = uvec3(uQuat & 0xffu, (uQuat >> 8u) & 0xffu, (uQuat >> 16u) & 0xffu);
|
|
|
|
|
|
float lnScaleMin = rgbMinMaxLnScaleMinMax.z;
|
|
float lnScaleMax = rgbMinMaxLnScaleMinMax.w;
|
|
float lnScaleScale = 254.0 / (lnScaleMax - lnScaleMin);
|
|
uvec3 uScales = uvec3(
|
|
(scales.x == 0.0) ? 0u : uint(round(clamp((log(scales.x) - lnScaleMin) * lnScaleScale, 0.0, 254.0))) + 1u,
|
|
(scales.y == 0.0) ? 0u : uint(round(clamp((log(scales.y) - lnScaleMin) * lnScaleScale, 0.0, 254.0))) + 1u,
|
|
(scales.z == 0.0) ? 0u : uint(round(clamp((log(scales.z) - lnScaleMin) * lnScaleScale, 0.0, 254.0))) + 1u
|
|
);
|
|
|
|
|
|
uint word0 = uRgba.r | (uRgba.g << 8u) | (uRgba.b << 16u) | (uRgba.a << 24u);
|
|
uint word1 = packHalf2x16(center.xy);
|
|
uint word2 = packHalf2x16(vec2(center.z, 0.0)) | (uQuat3.x << 16u) | (uQuat3.y << 24u);
|
|
uint word3 = uScales.x | (uScales.y << 8u) | (uScales.z << 16u) | (uQuat3.z << 24u);
|
|
return uvec4(word0, word1, word2, word3);
|
|
}
|
|
|
|
uvec4 packSplat(vec3 center, vec3 scales, vec4 quaternion, vec4 rgba) {
|
|
return packSplatEncoding(center, scales, quaternion, rgba, vec4(0.0, 1.0, LN_SCALE_MIN, LN_SCALE_MAX));
|
|
}
|
|
|
|
void unpackSplatEncoding(uvec4 packed, out vec3 center, out vec3 scales, out vec4 quaternion, out vec4 rgba, vec4 rgbMinMaxLnScaleMinMax) {
|
|
uint word0 = packed.x, word1 = packed.y, word2 = packed.z, word3 = packed.w;
|
|
|
|
uvec4 uRgba = uvec4(word0 & 0xffu, (word0 >> 8u) & 0xffu, (word0 >> 16u) & 0xffu, (word0 >> 24u) & 0xffu);
|
|
float rgbMin = rgbMinMaxLnScaleMinMax.x;
|
|
float rgbMax = rgbMinMaxLnScaleMinMax.y;
|
|
rgba = (vec4(uRgba) / 255.0);
|
|
rgba.rgb = rgba.rgb * (rgbMax - rgbMin) + rgbMin;
|
|
|
|
center = vec4(
|
|
unpackHalf2x16(word1),
|
|
unpackHalf2x16(word2 & 0xffffu)
|
|
).xyz;
|
|
|
|
uvec3 uScales = uvec3(word3 & 0xffu, (word3 >> 8u) & 0xffu, (word3 >> 16u) & 0xffu);
|
|
float lnScaleMin = rgbMinMaxLnScaleMinMax.z;
|
|
float lnScaleMax = rgbMinMaxLnScaleMinMax.w;
|
|
float lnScaleScale = (lnScaleMax - lnScaleMin) / 254.0;
|
|
scales = vec3(
|
|
(uScales.x == 0u) ? 0.0 : exp(lnScaleMin + float(uScales.x - 1u) * lnScaleScale),
|
|
(uScales.y == 0u) ? 0.0 : exp(lnScaleMin + float(uScales.y - 1u) * lnScaleScale),
|
|
(uScales.z == 0u) ? 0.0 : exp(lnScaleMin + float(uScales.z - 1u) * lnScaleScale)
|
|
);
|
|
|
|
uint uQuat = ((word2 >> 16u) & 0xFFFFu) | ((word3 >> 8u) & 0xFF0000u);
|
|
quaternion = decodeQuatOctXy88R8(uQuat);
|
|
|
|
|
|
}
|
|
|
|
void unpackSplat(uvec4 packed, out vec3 center, out vec3 scales, out vec4 quaternion, out vec4 rgba) {
|
|
unpackSplatEncoding(packed, center, scales, quaternion, rgba, vec4(0.0, 1.0, LN_SCALE_MIN, LN_SCALE_MAX));
|
|
}
|
|
|
|
vec3 quatVec(vec4 q, vec3 v) {
|
|
|
|
vec3 t = 2.0 * cross(q.xyz, v);
|
|
return v + q.w * t + cross(q.xyz, t);
|
|
}
|
|
|
|
vec4 quatQuat(vec4 q1, vec4 q2) {
|
|
return vec4(
|
|
q1.w * q2.x + q1.x * q2.w + q1.y * q2.z - q1.z * q2.y,
|
|
q1.w * q2.y - q1.x * q2.z + q1.y * q2.w + q1.z * q2.x,
|
|
q1.w * q2.z + q1.x * q2.y - q1.y * q2.x + q1.z * q2.w,
|
|
q1.w * q2.w - q1.x * q2.x - q1.y * q2.y - q1.z * q2.z
|
|
);
|
|
}
|
|
|
|
mat3 scaleQuaternionToMatrix(vec3 s, vec4 q) {
|
|
|
|
return mat3(
|
|
s.x * (1.0 - 2.0 * (q.y * q.y + q.z * q.z)),
|
|
s.x * (2.0 * (q.x * q.y + q.w * q.z)),
|
|
s.x * (2.0 * (q.x * q.z - q.w * q.y)),
|
|
s.y * (2.0 * (q.x * q.y - q.w * q.z)),
|
|
s.y * (1.0 - 2.0 * (q.x * q.x + q.z * q.z)),
|
|
s.y * (2.0 * (q.y * q.z + q.w * q.x)),
|
|
s.z * (2.0 * (q.x * q.z + q.w * q.y)),
|
|
s.z * (2.0 * (q.y * q.z - q.w * q.x)),
|
|
s.z * (1.0 - 2.0 * (q.x * q.x + q.y * q.y))
|
|
);
|
|
}
|
|
|
|
vec4 slerp(vec4 q1, vec4 q2, float t) {
|
|
|
|
float cosHalfTheta = dot(q1, q2);
|
|
|
|
|
|
if (abs(cosHalfTheta) >= 0.999) {
|
|
return q1;
|
|
}
|
|
|
|
|
|
|
|
if (cosHalfTheta < 0.0) {
|
|
q2 = -q2;
|
|
cosHalfTheta = -cosHalfTheta;
|
|
}
|
|
|
|
|
|
float halfTheta = acos(cosHalfTheta);
|
|
float sinHalfTheta = sqrt(1.0 - cosHalfTheta * cosHalfTheta);
|
|
|
|
|
|
float ratioA = sin((1.0 - t) * halfTheta) / sinHalfTheta;
|
|
float ratioB = sin(t * halfTheta) / sinHalfTheta;
|
|
|
|
|
|
return q1 * ratioA + q2 * ratioB;
|
|
}
|
|
|
|
ivec3 splatTexCoord(int index) {
|
|
uint x = uint(index) & SPLAT_TEX_WIDTH_MASK;
|
|
uint y = (uint(index) >> SPLAT_TEX_WIDTH_BITS) & SPLAT_TEX_HEIGHT_MASK;
|
|
uint z = uint(index) >> SPLAT_TEX_LAYER_BITS;
|
|
return ivec3(x, y, z);
|
|
}`, eh = `precision highp float;
|
|
precision highp int;
|
|
|
|
#include <splatDefines>
|
|
|
|
uniform float near;
|
|
uniform float far;
|
|
uniform bool encodeLinear;
|
|
uniform float time;
|
|
uniform bool debugFlag;
|
|
uniform float maxStdDev;
|
|
uniform float minAlpha;
|
|
uniform bool stochastic;
|
|
uniform bool disableFalloff;
|
|
uniform float falloff;
|
|
|
|
uniform bool splatTexEnable;
|
|
uniform sampler3D splatTexture;
|
|
uniform mat2 splatTexMul;
|
|
uniform vec2 splatTexAdd;
|
|
uniform float splatTexNear;
|
|
uniform float splatTexFar;
|
|
uniform float splatTexMid;
|
|
|
|
out vec4 fragColor;
|
|
|
|
in vec4 vRgba;
|
|
in vec2 vSplatUv;
|
|
in vec3 vNdc;
|
|
flat in uint vSplatIndex;
|
|
|
|
void main() {
|
|
vec4 rgba = vRgba;
|
|
|
|
float z = dot(vSplatUv, vSplatUv);
|
|
if (!splatTexEnable) {
|
|
if (z > (maxStdDev * maxStdDev)) {
|
|
discard;
|
|
}
|
|
} else {
|
|
vec2 uv = splatTexMul * vSplatUv + splatTexAdd;
|
|
float ndcZ = vNdc.z;
|
|
float depth = (2.0 * near * far) / (far + near - ndcZ * (far - near));
|
|
float clampedFar = max(splatTexFar, splatTexNear);
|
|
float clampedDepth = clamp(depth, splatTexNear, clampedFar);
|
|
float logDepth = log2(clampedDepth + 1.0);
|
|
float logNear = log2(splatTexNear + 1.0);
|
|
float logFar = log2(clampedFar + 1.0);
|
|
|
|
float texZ;
|
|
if (splatTexMid > 0.0) {
|
|
float clampedMid = clamp(splatTexMid, splatTexNear, clampedFar);
|
|
float logMid = log2(clampedMid + 1.0);
|
|
texZ = (clampedDepth <= clampedMid) ?
|
|
(0.5 * ((logDepth - logNear) / (logMid - logNear))) :
|
|
(0.5 * ((logDepth - logMid) / (logFar - logMid)) + 0.5);
|
|
} else {
|
|
texZ = (logDepth - logNear) / (logFar - logNear);
|
|
}
|
|
|
|
vec4 modulate = texture(splatTexture, vec3(uv, 1.0 - texZ));
|
|
rgba *= modulate;
|
|
}
|
|
|
|
rgba.a *= mix(1.0, exp(-0.5 * z), falloff);
|
|
|
|
if (rgba.a < minAlpha) {
|
|
discard;
|
|
}
|
|
if (encodeLinear) {
|
|
rgba.rgb = srgbToLinear(rgba.rgb);
|
|
}
|
|
|
|
if (stochastic) {
|
|
const bool STEADY = false;
|
|
uint uTime = STEADY ? 0u : floatBitsToUint(time);
|
|
uvec2 coord = uvec2(gl_FragCoord.xy);
|
|
uint state = uTime + 0x9e3779b9u * coord.x + 0x85ebca6bu * coord.y + 0xc2b2ae35u * uint(vSplatIndex);
|
|
state = state * 747796405u + 2891336453u;
|
|
uint hash = ((state >> ((state >> 28u) + 4u)) ^ state) * 277803737u;
|
|
hash = (hash >> 22u) ^ hash;
|
|
float rand = float(hash) / 4294967296.0;
|
|
if (rand < rgba.a) {
|
|
fragColor = vec4(rgba.rgb, 1.0);
|
|
} else {
|
|
discard;
|
|
}
|
|
} else {
|
|
#ifdef PREMULTIPLIED_ALPHA
|
|
fragColor = vec4(rgba.rgb * rgba.a, rgba.a);
|
|
#else
|
|
fragColor = rgba;
|
|
#endif
|
|
}
|
|
}`, sh = `precision highp float;
|
|
precision highp int;
|
|
precision highp usampler2DArray;
|
|
|
|
#include <splatDefines>
|
|
|
|
attribute uint splatIndex;
|
|
|
|
out vec4 vRgba;
|
|
out vec2 vSplatUv;
|
|
out vec3 vNdc;
|
|
flat out uint vSplatIndex;
|
|
|
|
uniform vec2 renderSize;
|
|
uniform uint numSplats;
|
|
uniform vec4 renderToViewQuat;
|
|
uniform vec3 renderToViewPos;
|
|
uniform float maxStdDev;
|
|
uniform float minPixelRadius;
|
|
uniform float maxPixelRadius;
|
|
uniform float time;
|
|
uniform float deltaTime;
|
|
uniform bool debugFlag;
|
|
uniform float minAlpha;
|
|
uniform bool stochastic;
|
|
uniform bool enable2DGS;
|
|
uniform float blurAmount;
|
|
uniform float preBlurAmount;
|
|
uniform float focalDistance;
|
|
uniform float apertureAngle;
|
|
uniform float clipXY;
|
|
uniform float focalAdjustment;
|
|
|
|
uniform usampler2DArray packedSplats;
|
|
uniform vec4 rgbMinMaxLnScaleMinMax;
|
|
|
|
void main() {
|
|
|
|
gl_Position = vec4(0.0, 0.0, 2.0, 1.0);
|
|
|
|
if (uint(gl_InstanceID) >= numSplats) {
|
|
return;
|
|
}
|
|
|
|
ivec3 texCoord;
|
|
if (stochastic) {
|
|
texCoord = ivec3(
|
|
uint(gl_InstanceID) & SPLAT_TEX_WIDTH_MASK,
|
|
(uint(gl_InstanceID) >> SPLAT_TEX_WIDTH_BITS) & SPLAT_TEX_HEIGHT_MASK,
|
|
(uint(gl_InstanceID) >> SPLAT_TEX_LAYER_BITS)
|
|
);
|
|
} else {
|
|
if (splatIndex == 0xffffffffu) {
|
|
|
|
return;
|
|
}
|
|
texCoord = ivec3(
|
|
splatIndex & SPLAT_TEX_WIDTH_MASK,
|
|
(splatIndex >> SPLAT_TEX_WIDTH_BITS) & SPLAT_TEX_HEIGHT_MASK,
|
|
splatIndex >> SPLAT_TEX_LAYER_BITS
|
|
);
|
|
}
|
|
uvec4 packed = texelFetch(packedSplats, texCoord, 0);
|
|
|
|
vec3 center, scales;
|
|
vec4 quaternion, rgba;
|
|
unpackSplatEncoding(packed, center, scales, quaternion, rgba, rgbMinMaxLnScaleMinMax);
|
|
|
|
if (rgba.a < minAlpha) {
|
|
return;
|
|
}
|
|
bvec3 zeroScales = equal(scales, vec3(0.0));
|
|
if (all(zeroScales)) {
|
|
return;
|
|
}
|
|
|
|
|
|
vec3 viewCenter = quatVec(renderToViewQuat, center) + renderToViewPos;
|
|
|
|
|
|
if (viewCenter.z >= 0.0) {
|
|
return;
|
|
}
|
|
|
|
|
|
vec4 clipCenter = projectionMatrix * vec4(viewCenter, 1.0);
|
|
|
|
|
|
if (abs(clipCenter.z) >= clipCenter.w) {
|
|
return;
|
|
}
|
|
|
|
|
|
float clip = clipXY * clipCenter.w;
|
|
if (abs(clipCenter.x) > clip || abs(clipCenter.y) > clip) {
|
|
return;
|
|
}
|
|
|
|
|
|
vSplatIndex = splatIndex;
|
|
|
|
|
|
vec4 viewQuaternion = quatQuat(renderToViewQuat, quaternion);
|
|
|
|
if (enable2DGS && any(zeroScales)) {
|
|
vRgba = rgba;
|
|
vSplatUv = position.xy * maxStdDev;
|
|
|
|
vec3 offset;
|
|
if (zeroScales.z) {
|
|
offset = vec3(vSplatUv.xy * scales.xy, 0.0);
|
|
} else if (zeroScales.y) {
|
|
offset = vec3(vSplatUv.x * scales.x, 0.0, vSplatUv.y * scales.z);
|
|
} else {
|
|
offset = vec3(0.0, vSplatUv.xy * scales.yz);
|
|
}
|
|
|
|
vec3 viewPos = viewCenter + quatVec(viewQuaternion, offset);
|
|
gl_Position = projectionMatrix * vec4(viewPos, 1.0);
|
|
vNdc = gl_Position.xyz / gl_Position.w;
|
|
return;
|
|
}
|
|
|
|
|
|
vec3 ndcCenter = clipCenter.xyz / clipCenter.w;
|
|
|
|
|
|
mat3 RS = scaleQuaternionToMatrix(scales, viewQuaternion);
|
|
mat3 cov3D = RS * transpose(RS);
|
|
|
|
|
|
vec2 scaledRenderSize = renderSize * focalAdjustment;
|
|
vec2 focal = 0.5 * scaledRenderSize * vec2(projectionMatrix[0][0], projectionMatrix[1][1]);
|
|
|
|
mat3 J;
|
|
if(isOrthographic) {
|
|
J = mat3(
|
|
focal.x, 0.0, 0.0,
|
|
0.0, focal.y, 0.0,
|
|
0.0, 0.0, 0.0
|
|
);
|
|
} else {
|
|
float invZ = 1.0 / viewCenter.z;
|
|
vec2 J1 = focal * invZ;
|
|
vec2 J2 = -(J1 * viewCenter.xy) * invZ;
|
|
J = mat3(
|
|
J1.x, 0.0, J2.x,
|
|
0.0, J1.y, J2.y,
|
|
0.0, 0.0, 0.0
|
|
);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
mat3 cov2D = transpose(J) * cov3D * J;
|
|
float a = cov2D[0][0];
|
|
float d = cov2D[1][1];
|
|
float b = cov2D[0][1];
|
|
|
|
|
|
a += preBlurAmount;
|
|
d += preBlurAmount;
|
|
|
|
float fullBlurAmount = blurAmount;
|
|
if ((focalDistance > 0.0) && (apertureAngle > 0.0)) {
|
|
float focusRadius = maxPixelRadius;
|
|
if (viewCenter.z < 0.0) {
|
|
float focusBlur = abs((-viewCenter.z - focalDistance) / viewCenter.z);
|
|
float apertureRadius = focal.x * tan(0.5 * apertureAngle);
|
|
focusRadius = focusBlur * apertureRadius;
|
|
}
|
|
fullBlurAmount = clamp(sqr(focusRadius), blurAmount, sqr(maxPixelRadius));
|
|
}
|
|
|
|
|
|
float detOrig = a * d - b * b;
|
|
a += fullBlurAmount;
|
|
d += fullBlurAmount;
|
|
float det = a * d - b * b;
|
|
|
|
|
|
float blurAdjust = sqrt(max(0.0, detOrig / det));
|
|
rgba.a *= blurAdjust;
|
|
if (rgba.a < minAlpha) {
|
|
return;
|
|
}
|
|
|
|
|
|
float eigenAvg = 0.5 * (a + d);
|
|
float eigenDelta = sqrt(max(0.0, eigenAvg * eigenAvg - det));
|
|
float eigen1 = eigenAvg + eigenDelta;
|
|
float eigen2 = eigenAvg - eigenDelta;
|
|
|
|
vec2 eigenVec1 = normalize(vec2((abs(b) < 0.001) ? 1.0 : b, eigen1 - a));
|
|
vec2 eigenVec2 = vec2(eigenVec1.y, -eigenVec1.x);
|
|
|
|
float scale1 = min(maxPixelRadius, maxStdDev * sqrt(eigen1));
|
|
float scale2 = min(maxPixelRadius, maxStdDev * sqrt(eigen2));
|
|
if (scale1 < minPixelRadius && scale2 < minPixelRadius) {
|
|
return;
|
|
}
|
|
|
|
|
|
vec2 pixelOffset = position.x * eigenVec1 * scale1 + position.y * eigenVec2 * scale2;
|
|
vec2 ndcOffset = (2.0 / scaledRenderSize) * pixelOffset;
|
|
vec3 ndc = vec3(ndcCenter.xy + ndcOffset, ndcCenter.z);
|
|
|
|
vRgba = rgba;
|
|
vSplatUv = position.xy * maxStdDev;
|
|
vNdc = ndc;
|
|
gl_Position = vec4(ndc.xy * clipCenter.w, clipCenter.zw);
|
|
}`;
|
|
let Te = null;
|
|
function nh() {
|
|
return Te || (u.ShaderChunk.splatDefines = th, Te = {
|
|
splatVertex: sh,
|
|
splatFragment: eh
|
|
}), Te;
|
|
}
|
|
const ys = 5, oA = class oA extends u.Mesh {
|
|
constructor(A) {
|
|
const e = oA.makeUniforms(), s = nh(), n = A.premultipliedAlpha ?? !0, i = new u.ShaderMaterial({
|
|
glslVersion: u.GLSL3,
|
|
vertexShader: s.splatVertex,
|
|
fragmentShader: s.splatFragment,
|
|
uniforms: e,
|
|
premultipliedAlpha: n,
|
|
transparent: !0,
|
|
depthTest: !0,
|
|
depthWrite: !1,
|
|
side: u.DoubleSide
|
|
});
|
|
super(ws, i), this.splatTexture = null, this.autoViewpoints = [], this.rotateToAccumulator = new Tt({ value: new u.Quaternion() }), this.translateToAccumulator = new Ft({ value: new u.Vector3() }), this.lastFrame = -1, this.lastUpdateTime = null, this.defaultCameras = [], this.lastStochastic = null, this.pendingUpdate = {
|
|
scene: null,
|
|
originToWorld: new u.Matrix4(),
|
|
timeoutId: -1
|
|
}, this.envViewpoint = null, this.frustumCulled = !1, this.renderer = A.renderer, this.material = i, this.uniforms = e;
|
|
const r = vA(
|
|
{ gsplat: AA },
|
|
{ gsplat: AA },
|
|
({ gsplat: a }) => {
|
|
if (!a)
|
|
throw new Error("gsplat not defined");
|
|
return a = As(a, {
|
|
rotate: this.rotateToAccumulator,
|
|
translate: this.translateToAccumulator
|
|
}), { gsplat: a };
|
|
}
|
|
);
|
|
this.modifier = new mu(r), this.premultipliedAlpha = n, this.autoUpdate = A.autoUpdate ?? !0, this.preUpdate = A.preUpdate ?? !1, this.needsUpdate = !1, this.originDistance = A.originDistance ?? 1, this.maxStdDev = A.maxStdDev ?? Math.sqrt(8), this.minPixelRadius = A.minPixelRadius ?? 0, this.maxPixelRadius = A.maxPixelRadius ?? 512, this.minAlpha = A.minAlpha ?? 0.5 * (1 / 255), this.enable2DGS = A.enable2DGS ?? !1, this.preBlurAmount = A.preBlurAmount ?? 0, this.blurAmount = A.blurAmount ?? 0.3, this.focalDistance = A.focalDistance ?? 0, this.apertureAngle = A.apertureAngle ?? 0, this.falloff = A.falloff ?? 1, this.clipXY = A.clipXY ?? 1.4, this.focalAdjustment = A.focalAdjustment ?? 1, this.splatEncoding = A.splatEncoding ?? { ...de }, this.active = new ke(), this.accumulatorCount = 1, this.freeAccumulators = [];
|
|
for (let a = 0; a < 1; ++a)
|
|
this.freeAccumulators.push(new ke()), this.accumulatorCount += 1;
|
|
this.defaultView = new Ce({
|
|
...A.view,
|
|
autoUpdate: !0,
|
|
spark: this
|
|
}), this.viewpoint = this.defaultView, this.prepareViewpoint(this.viewpoint), this.clock = A.clock ? $n(A.clock) : new u.Clock();
|
|
}
|
|
static makeUniforms() {
|
|
return {
|
|
// Size of render viewport in pixels
|
|
renderSize: { value: new u.Vector2() },
|
|
// Near and far plane distances
|
|
near: { value: 0.1 },
|
|
far: { value: 1e3 },
|
|
// Total number of Gsplats in packedSplats to render
|
|
numSplats: { value: 0 },
|
|
// SplatAccumulator to view transformation quaternion
|
|
renderToViewQuat: { value: new u.Quaternion() },
|
|
// SplatAccumulator to view transformation translation
|
|
renderToViewPos: { value: new u.Vector3() },
|
|
// Maximum distance (in stddevs) from Gsplat center to render
|
|
maxStdDev: { value: 1 },
|
|
// Minimum pixel radius for splat rendering
|
|
minPixelRadius: { value: 0 },
|
|
// Maximum pixel radius for splat rendering
|
|
maxPixelRadius: { value: 512 },
|
|
// Minimum alpha value for splat rendering
|
|
minAlpha: { value: 0.00196078431372549 },
|
|
// Enable stochastic splat rendering
|
|
stochastic: { value: !1 },
|
|
// Enable interpreting 0-thickness Gsplats as 2DGS
|
|
enable2DGS: { value: !1 },
|
|
// Add to projected 2D splat covariance diagonal (thickens and brightens)
|
|
preBlurAmount: { value: 0 },
|
|
// Add to 2D splat covariance diagonal and adjust opacity (anti-aliasing)
|
|
blurAmount: { value: 0.3 },
|
|
// Depth-of-field distance to focal plane
|
|
focalDistance: { value: 0 },
|
|
// Full-width angle of aperture opening (in radians)
|
|
apertureAngle: { value: 0 },
|
|
// Modulate Gaussian kernal falloff. 0 means "no falloff, flat shading",
|
|
// 1 is normal e^-x^2 falloff.
|
|
falloff: { value: 1 },
|
|
// Clip Gsplats that are clipXY times beyond the +-1 frustum bounds
|
|
clipXY: { value: 1.4 },
|
|
// Debug renderSize scale factor
|
|
focalAdjustment: { value: 1 },
|
|
// Enable splat texture rendering
|
|
splatTexEnable: { value: !1 },
|
|
// Splat texture to render
|
|
splatTexture: { type: "t", value: oA.EMPTY_SPLAT_TEXTURE },
|
|
// Splat texture UV transform (multiply)
|
|
splatTexMul: { value: new u.Matrix2() },
|
|
// Splat texture UV transform (add)
|
|
splatTexAdd: { value: new u.Vector2() },
|
|
// Splat texture near plane distance
|
|
splatTexNear: { value: 0.1 },
|
|
// Splat texture far plane distance
|
|
splatTexFar: { value: 1e3 },
|
|
// Splat texture mid plane distance, or 0.0 to disable
|
|
splatTexMid: { value: 0 },
|
|
// Gsplat collection to render
|
|
packedSplats: { type: "t", value: VA.getEmpty() },
|
|
// Splat encoding ranges
|
|
rgbMinMaxLnScaleMinMax: { value: new u.Vector4() },
|
|
// Time in seconds for time-based effects
|
|
time: { value: 0 },
|
|
// Delta time in seconds since last frame
|
|
deltaTime: { value: 0 },
|
|
// Whether to encode Gsplat with linear RGB (for environment mapping)
|
|
encodeLinear: { value: !1 },
|
|
// Debug flag that alternates each frame
|
|
debugFlag: { value: !1 }
|
|
};
|
|
}
|
|
canAllocAccumulator() {
|
|
return this.freeAccumulators.length > 0 || this.accumulatorCount < ys;
|
|
}
|
|
maybeAllocAccumulator() {
|
|
let A = this.freeAccumulators.pop();
|
|
if (A === void 0) {
|
|
if (this.accumulatorCount >= ys)
|
|
return null;
|
|
A = new ke(), this.accumulatorCount += 1;
|
|
}
|
|
return A.refCount = 1, A;
|
|
}
|
|
releaseAccumulator(A) {
|
|
A.refCount -= 1, A.refCount === 0 && this.freeAccumulators.push(A);
|
|
}
|
|
newViewpoint(A) {
|
|
return new Ce({ ...A, spark: this });
|
|
}
|
|
onBeforeRender(A, e, s) {
|
|
var h, E;
|
|
const n = this.time ?? this.clock.getElapsedTime(), i = n - (this.viewpoint.lastTime ?? n);
|
|
this.viewpoint.lastTime = n;
|
|
const r = A.info.render.frame, a = r !== this.lastFrame;
|
|
this.lastFrame = r;
|
|
const o = this.viewpoint;
|
|
if (o === this.defaultView) {
|
|
if (a)
|
|
if (!A.xr.isPresenting)
|
|
this.defaultView.viewToWorld = s.matrixWorld.clone(), this.defaultCameras = [this.defaultView.viewToWorld];
|
|
else {
|
|
const C = A.xr.getCamera().cameras;
|
|
this.defaultCameras = C.map((B) => B.matrixWorld), this.defaultView.viewToWorld = ih(this.defaultCameras) ?? new u.Matrix4();
|
|
}
|
|
this.autoUpdate && this.update({ scene: e, viewToWorld: this.defaultView.viewToWorld });
|
|
}
|
|
if (a && (this.material.premultipliedAlpha !== this.premultipliedAlpha && (this.material.premultipliedAlpha = this.premultipliedAlpha, this.material.needsUpdate = !0), this.uniforms.time.value = n, this.uniforms.deltaTime.value = i, this.uniforms.debugFlag.value = performance.now() / 1e3 % 2 < 1, o.display && o.stochastic && (this.geometry.instanceCount = this.uniforms.numSplats.value)), o.target)
|
|
this.uniforms.renderSize.value.set(
|
|
o.target.width,
|
|
o.target.height
|
|
);
|
|
else {
|
|
const C = A.getDrawingBufferSize(
|
|
this.uniforms.renderSize.value
|
|
);
|
|
if (C.x === 1 && C.y === 1) {
|
|
const B = (h = A.xr.getSession()) == null ? void 0 : h.renderState.baseLayer;
|
|
B && (C.x = B.framebufferWidth, C.y = B.framebufferHeight);
|
|
}
|
|
}
|
|
const g = s;
|
|
if (this.uniforms.near.value = g.near, this.uniforms.far.value = g.far, this.uniforms.encodeLinear.value = o.encodeLinear, this.uniforms.maxStdDev.value = this.maxStdDev, this.uniforms.minPixelRadius.value = this.minPixelRadius, this.uniforms.maxPixelRadius.value = this.maxPixelRadius, this.uniforms.minAlpha.value = this.minAlpha, this.uniforms.stochastic.value = o.stochastic, this.uniforms.enable2DGS.value = this.enable2DGS, this.uniforms.preBlurAmount.value = this.preBlurAmount, this.uniforms.blurAmount.value = this.blurAmount, this.uniforms.focalDistance.value = this.focalDistance, this.uniforms.apertureAngle.value = this.apertureAngle, this.uniforms.falloff.value = this.falloff, this.uniforms.clipXY.value = this.clipXY, this.uniforms.focalAdjustment.value = this.focalAdjustment, this.lastStochastic !== !o.stochastic && (this.lastStochastic = !o.stochastic, this.material.transparent = !o.stochastic, this.material.depthWrite = o.stochastic, this.material.needsUpdate = !0), this.splatTexture) {
|
|
const { enable: C, texture: B, multiply: Q, add: f, near: p, far: d, mid: y } = this.splatTexture;
|
|
C && B ? (this.uniforms.splatTexEnable.value = !0, this.uniforms.splatTexture.value = B, Q ? this.uniforms.splatTexMul.value.fromArray(Q.elements) : this.uniforms.splatTexMul.value.set(
|
|
0.5 / this.maxStdDev,
|
|
0,
|
|
0,
|
|
0.5 / this.maxStdDev
|
|
), this.uniforms.splatTexAdd.value.set((f == null ? void 0 : f.x) ?? 0.5, (f == null ? void 0 : f.y) ?? 0.5), this.uniforms.splatTexNear.value = p ?? this.uniforms.near.value, this.uniforms.splatTexFar.value = d ?? this.uniforms.far.value, this.uniforms.splatTexMid.value = y ?? 0) : (this.uniforms.splatTexEnable.value = !1, this.uniforms.splatTexture.value = oA.EMPTY_SPLAT_TEXTURE);
|
|
} else
|
|
this.uniforms.splatTexEnable.value = !1, this.uniforms.splatTexture.value = oA.EMPTY_SPLAT_TEXTURE;
|
|
const l = ((E = o.display) == null ? void 0 : E.accumulator.toWorld) ?? new u.Matrix4(), c = s.matrixWorld.clone().invert();
|
|
l.clone().premultiply(c).decompose(
|
|
this.uniforms.renderToViewPos.value,
|
|
this.uniforms.renderToViewQuat.value,
|
|
new u.Vector3()
|
|
);
|
|
}
|
|
// Update the uniforms for the given viewpoint.
|
|
// Note that the client expects to be able to call render() at any point
|
|
// to update the canvas, so we must switch the viewpoint back to
|
|
// defaultView when we're finished.
|
|
prepareViewpoint(A) {
|
|
var e, s, n, i;
|
|
if (this.viewpoint = A ?? this.viewpoint, this.viewpoint.display) {
|
|
const { accumulator: r, geometry: a } = this.viewpoint.display;
|
|
this.uniforms.numSplats.value = r.splats.numSplats, this.uniforms.packedSplats.value = r.splats.getTexture(), this.uniforms.rgbMinMaxLnScaleMinMax.value.set(
|
|
((e = r.splats.splatEncoding) == null ? void 0 : e.rgbMin) ?? 0,
|
|
((s = r.splats.splatEncoding) == null ? void 0 : s.rgbMax) ?? 1,
|
|
((n = r.splats.splatEncoding) == null ? void 0 : n.lnScaleMin) ?? UA,
|
|
((i = r.splats.splatEncoding) == null ? void 0 : i.lnScaleMax) ?? GA
|
|
), this.geometry = a, this.material.transparent = !this.viewpoint.stochastic, this.material.depthWrite = this.viewpoint.stochastic, this.material.needsUpdate = !0;
|
|
} else
|
|
this.uniforms.numSplats.value = 0, this.uniforms.packedSplats.value = VA.getEmpty(), this.geometry = ws;
|
|
}
|
|
// If spark.autoUpdate is false then you must manually call
|
|
// spark.update({ scene }) to have the scene Gsplats be re-generated.
|
|
update({
|
|
scene: A,
|
|
viewToWorld: e
|
|
}) {
|
|
const s = this.matrixWorld;
|
|
this.preUpdate ? this.updateInternal({
|
|
scene: A,
|
|
originToWorld: s.clone(),
|
|
viewToWorld: e
|
|
}) : (this.pendingUpdate.scene = A, this.pendingUpdate.originToWorld.copy(s), this.pendingUpdate.timeoutId === -1 && (this.pendingUpdate.timeoutId = setTimeout(() => {
|
|
const { scene: n, originToWorld: i } = this.pendingUpdate;
|
|
this.pendingUpdate.scene = null, this.pendingUpdate.timeoutId = -1, this.updateInternal({
|
|
scene: n,
|
|
originToWorld: i,
|
|
viewToWorld: e
|
|
}) && this.renderer.getContext().flush();
|
|
}, 1)));
|
|
}
|
|
updateInternal({
|
|
scene: A,
|
|
originToWorld: e,
|
|
viewToWorld: s
|
|
}) {
|
|
var E;
|
|
if (!this.canAllocAccumulator())
|
|
return !1;
|
|
e || (e = this.active.toWorld), s = s ?? e.clone();
|
|
const n = this.time ?? this.clock.getElapsedTime(), i = n - (this.lastUpdateTime ?? n);
|
|
this.lastUpdateTime = n;
|
|
const r = this.active.mapping.reduce((C, B) => (C.set(B.node, B), C), /* @__PURE__ */ new Map()), { generators: a, visibleGenerators: o, globalEdits: g } = this.compileScene(A);
|
|
for (const C of a)
|
|
(E = C.frameUpdate) == null || E.call(C, {
|
|
object: C,
|
|
time: n,
|
|
deltaTime: i,
|
|
viewToWorld: s,
|
|
globalEdits: g
|
|
});
|
|
const l = new Set(o.map((C) => C.uuid));
|
|
for (const C of a) {
|
|
const B = r.get(C), f = C.generator && l.has(C.uuid) ? C.numSplats : 0;
|
|
(this.needsUpdate || C.generator !== (B == null ? void 0 : B.generator) || f !== (B == null ? void 0 : B.count)) && C.updateVersion();
|
|
}
|
|
const c = !ge({
|
|
matrix1: e,
|
|
matrix2: this.active.toWorld,
|
|
maxDistance: this.originDistance
|
|
}), I = this.needsUpdate || c || a.length !== r.size || a.some((C) => {
|
|
var B;
|
|
return C.version !== ((B = r.get(C)) == null ? void 0 : B.version);
|
|
});
|
|
this.needsUpdate = !1;
|
|
let h = null;
|
|
if (I) {
|
|
if (h = this.maybeAllocAccumulator(), !h)
|
|
throw new Error("Unreachable");
|
|
const C = !ge({
|
|
matrix1: e,
|
|
matrix2: this.active.toWorld,
|
|
maxDistance: 1e-5,
|
|
minCoorient: 0.99999
|
|
}), Q = o.map((x, w) => {
|
|
const m = r.get(x);
|
|
return m ? (
|
|
// Sort by version deltas then by previous ordering in the mapping,
|
|
// attempting to keep unchanging generators near the front
|
|
// to improve our chances of avoiding a re-generation.
|
|
[x.version - m.version, m.base, x]
|
|
) : [Number.POSITIVE_INFINITY, x.version, x];
|
|
}).sort((x, w) => x[0] !== w[0] ? x[0] - w[0] : x[1] - w[1]).map(([x, w, m]) => m), f = Q.map((x) => x.numSplats), { maxSplats: p, mapping: d } = h.splats.generateMapping(f), y = Q.map((x, w) => {
|
|
const { base: m, count: k } = d[w];
|
|
return {
|
|
node: x,
|
|
generator: x.generator,
|
|
version: x.version,
|
|
base: m,
|
|
count: k
|
|
};
|
|
});
|
|
e.clone().invert().decompose(
|
|
this.translateToAccumulator.value,
|
|
this.rotateToAccumulator.value,
|
|
new u.Vector3()
|
|
), h.ensureGenerate(p), h.splats.splatEncoding = { ...this.splatEncoding }, h.generateSplats({
|
|
renderer: this.renderer,
|
|
modifier: this.modifier,
|
|
generators: y,
|
|
forceUpdate: C,
|
|
originToWorld: e
|
|
}), h.splatsVersion = this.active.splatsVersion + 1;
|
|
const D = h.hasCorrespondence(this.active);
|
|
h.mappingVersion = this.active.mappingVersion + (D ? 0 : 1), this.releaseAccumulator(this.active), this.active = h, this.prepareViewpoint();
|
|
}
|
|
return setTimeout(() => {
|
|
for (const C of this.autoViewpoints)
|
|
C.autoPoll({ accumulator: h ?? void 0 });
|
|
}, 1), !0;
|
|
}
|
|
compileScene(A) {
|
|
const e = [];
|
|
A.traverse((i) => {
|
|
i instanceof Vt && e.push(i);
|
|
});
|
|
const s = [];
|
|
A.traverseVisible((i) => {
|
|
i instanceof Vt && s.push(i);
|
|
});
|
|
const n = /* @__PURE__ */ new Set();
|
|
return A.traverseVisible((i) => {
|
|
if (i instanceof Ie) {
|
|
let r = i.parent;
|
|
for (; r != null && !(r instanceof pt); )
|
|
r = r.parent;
|
|
r == null && n.add(i);
|
|
}
|
|
}), {
|
|
generators: e,
|
|
visibleGenerators: s,
|
|
globalEdits: Array.from(n)
|
|
};
|
|
}
|
|
// Renders out the scene to an environment map that can be used for
|
|
// Image-based lighting or similar applications. First optionally updates Gsplats,
|
|
// sorts them with respect to the provided worldCenter, renders 6 cube faces,
|
|
// then pre-filters them using THREE.PMREMGenerator and returns a THREE.Texture
|
|
// that can assigned directly to a THREE.MeshStandardMaterial.envMap property.
|
|
async renderEnvMap({
|
|
renderer: A,
|
|
scene: e,
|
|
worldCenter: s,
|
|
size: n = 256,
|
|
near: i = 0.1,
|
|
far: r = 1e3,
|
|
hideObjects: a = [],
|
|
update: o = !1
|
|
}) {
|
|
var h, E;
|
|
if (this.envViewpoint || (this.envViewpoint = this.newViewpoint({ sort360: !0 })), !oA.cubeRender || oA.cubeRender.target.width !== n || oA.cubeRender.near !== i || oA.cubeRender.far !== r) {
|
|
oA.cubeRender && oA.cubeRender.target.dispose();
|
|
const C = new u.WebGLCubeRenderTarget(n, {
|
|
format: u.RGBAFormat,
|
|
generateMipmaps: !0,
|
|
minFilter: u.LinearMipMapLinearFilter
|
|
}), B = new u.CubeCamera(i, r, C);
|
|
oA.cubeRender = { target: C, camera: B, near: i, far: r };
|
|
}
|
|
oA.pmrem || (oA.pmrem = new u.PMREMGenerator(A ?? this.renderer));
|
|
const g = new u.Matrix4().setPosition(s);
|
|
await ((h = this.envViewpoint) == null ? void 0 : h.prepare({ scene: e, viewToWorld: g, update: o }));
|
|
const { target: l, camera: c } = oA.cubeRender;
|
|
c.position.copy(s);
|
|
const I = /* @__PURE__ */ new Map();
|
|
for (const C of a)
|
|
I.set(C, C.visible), C.visible = !1;
|
|
this.prepareViewpoint(this.envViewpoint), c.update(A ?? this.renderer, e), this.prepareViewpoint(this.defaultView);
|
|
for (const [C, B] of I.entries())
|
|
C.visible = B;
|
|
return (E = oA.pmrem) == null ? void 0 : E.fromCubemap(l.texture).texture;
|
|
}
|
|
// Utility function to recursively set the envMap property for any
|
|
// THREE.MeshStandardMaterial within the subtree of root.
|
|
recurseSetEnvMap(A, e) {
|
|
A.traverse((s) => {
|
|
if (s instanceof u.Mesh)
|
|
if (Array.isArray(s.material))
|
|
for (const n of s.material)
|
|
n instanceof u.MeshStandardMaterial && (n.envMap = e);
|
|
else
|
|
s.material instanceof u.MeshStandardMaterial && (s.material.envMap = e);
|
|
});
|
|
}
|
|
// Utility function that helps extract the Gsplat RGBA values from a
|
|
// SplatGenerator, including the result of any real-time RGBA SDF edits applied
|
|
// to a SplatMesh. This effectively "bakes" any computed RGBA values, which can
|
|
// now be used as a pipeline input via SplatMesh.splatRgba to inject these
|
|
// baked values into the Gsplat data.
|
|
getRgba({
|
|
generator: A,
|
|
rgba: e
|
|
}) {
|
|
const s = this.active.mapping.find(({ node: n }) => n === A);
|
|
if (!s)
|
|
throw new Error("Generator not found");
|
|
return e = e ?? new Ke(), e.fromPackedSplats({
|
|
packedSplats: this.active.splats,
|
|
base: s.base,
|
|
count: s.count,
|
|
renderer: this.renderer
|
|
}), e;
|
|
}
|
|
// Utility function that builds on getRgba({ generator }) and additionally
|
|
// reads back the RGBA values to the CPU in a Uint8Array with packed RGBA
|
|
// in that byte order.
|
|
async readRgba({
|
|
generator: A,
|
|
rgba: e
|
|
}) {
|
|
return e = this.getRgba({ generator: A, rgba: e }), e.read();
|
|
}
|
|
};
|
|
oA.cubeRender = null, oA.pmrem = null, oA.EMPTY_SPLAT_TEXTURE = new u.Data3DTexture();
|
|
let Be = oA;
|
|
const ws = new Ve(new Uint32Array(1), 0);
|
|
vA(
|
|
{ packedSplats: jt, index: "int" },
|
|
{ gsplat: AA },
|
|
({ packedSplats: t, index: A }) => {
|
|
if (!t || !A)
|
|
throw new Error("Invalid input");
|
|
return { gsplat: bt(t, A) };
|
|
}
|
|
);
|
|
function ih(t) {
|
|
if (t.length === 0)
|
|
return null;
|
|
const A = new u.Vector3(), e = new u.Quaternion(), s = new u.Vector3(), n = [], i = [];
|
|
for (const r of t)
|
|
r.decompose(A, e, s), n.push(A), i.push(e);
|
|
return new u.Matrix4().compose(
|
|
Pn(n),
|
|
Zn(i),
|
|
new u.Vector3(1, 1, 1)
|
|
);
|
|
}
|
|
function rh(t, A, e) {
|
|
const s = Math.floor(t.length / 32);
|
|
if (s * 32 !== t.length)
|
|
throw new Error("Invalid .splat file size");
|
|
const n = new Float32Array(t.buffer);
|
|
for (let i = 0; i < s; ++i) {
|
|
const r = i * 32, a = i * 8, o = n[a + 0], g = n[a + 1], l = n[a + 2], c = n[a + 3], I = n[a + 4], h = n[a + 5], E = t[r + 24] / 255, C = t[r + 25] / 255, B = t[r + 26] / 255, Q = t[r + 27] / 255, f = (t[r + 28] - 128) / 128, p = (t[r + 29] - 128) / 128, d = (t[r + 30] - 128) / 128, y = (t[r + 31] - 128) / 128;
|
|
e(
|
|
i,
|
|
o,
|
|
g,
|
|
l,
|
|
c,
|
|
I,
|
|
h,
|
|
p,
|
|
d,
|
|
y,
|
|
f,
|
|
Q,
|
|
E,
|
|
C,
|
|
B
|
|
);
|
|
}
|
|
}
|
|
const ms = {
|
|
0: {
|
|
bytesPerCenter: 12,
|
|
bytesPerScale: 12,
|
|
bytesPerRotation: 16,
|
|
bytesPerColor: 4,
|
|
bytesPerSphericalHarmonicsComponent: 4,
|
|
scaleOffsetBytes: 12,
|
|
rotationOffsetBytes: 24,
|
|
colorOffsetBytes: 40,
|
|
sphericalHarmonicsOffsetBytes: 44,
|
|
scaleRange: 1
|
|
},
|
|
1: {
|
|
bytesPerCenter: 6,
|
|
bytesPerScale: 6,
|
|
bytesPerRotation: 8,
|
|
bytesPerColor: 4,
|
|
bytesPerSphericalHarmonicsComponent: 2,
|
|
scaleOffsetBytes: 6,
|
|
rotationOffsetBytes: 12,
|
|
colorOffsetBytes: 20,
|
|
sphericalHarmonicsOffsetBytes: 24,
|
|
scaleRange: 32767
|
|
},
|
|
2: {
|
|
bytesPerCenter: 6,
|
|
bytesPerScale: 6,
|
|
bytesPerRotation: 8,
|
|
bytesPerColor: 4,
|
|
bytesPerSphericalHarmonicsComponent: 1,
|
|
scaleOffsetBytes: 6,
|
|
rotationOffsetBytes: 12,
|
|
colorOffsetBytes: 20,
|
|
sphericalHarmonicsOffsetBytes: 24,
|
|
scaleRange: 32767
|
|
}
|
|
}, ah = {
|
|
0: 0,
|
|
1: 9,
|
|
2: 24,
|
|
3: 45
|
|
};
|
|
function oh(t, A, e, s) {
|
|
var C;
|
|
let r = 0;
|
|
const a = new DataView(t.buffer, r, 4096);
|
|
r += 4096;
|
|
const o = a.getUint8(0), g = a.getUint8(1);
|
|
if (o !== 0 || g < 1)
|
|
throw new Error(
|
|
`Unsupported .ksplat version: ${o}.${g}`
|
|
);
|
|
const l = a.getUint32(4, !0);
|
|
a.getUint32(16, !0);
|
|
const c = a.getUint16(20, !0);
|
|
if (c < 0 || c > 2)
|
|
throw new Error(`Invalid .ksplat compression level: ${c}`);
|
|
const I = a.getFloat32(36, !0) || -1.5, h = a.getFloat32(40, !0) || 1.5;
|
|
let E = 4096 + l * 1024;
|
|
for (let B = 0; B < l; ++B) {
|
|
let Q = function(MA, z) {
|
|
if (c === 0)
|
|
return Y.getFloat32(
|
|
MA + P + z * 4,
|
|
!0
|
|
);
|
|
if (c === 1)
|
|
return wA(
|
|
Y.getUint16(
|
|
MA + P + z * 2,
|
|
!0
|
|
)
|
|
);
|
|
const ZA = Y.getUint8(MA + P + z) / 255;
|
|
return I + ZA * (h - I);
|
|
};
|
|
const f = new DataView(t.buffer, r, 1024);
|
|
r += 1024;
|
|
const p = f.getUint32(0, !0), d = f.getUint32(4, !0), y = f.getUint32(8, !0), D = f.getUint32(12, !0), x = f.getFloat32(16, !0), w = f.getUint16(20, !0), m = (f.getUint32(24, !0) || ((C = ms[c]) == null ? void 0 : C.scaleRange)) ?? 1, k = f.getUint32(32, !0), M = k * y, S = f.getUint32(36, !0), U = S * 4, F = w * D + U, b = f.getUint16(40, !0), T = ah[b], {
|
|
bytesPerCenter: R,
|
|
bytesPerScale: X,
|
|
bytesPerRotation: _,
|
|
bytesPerColor: eA,
|
|
bytesPerSphericalHarmonicsComponent: q,
|
|
scaleOffsetBytes: O,
|
|
rotationOffsetBytes: L,
|
|
colorOffsetBytes: j,
|
|
sphericalHarmonicsOffsetBytes: P
|
|
} = ms[c], W = R + X + _ + eA + T * q, G = W * d, pA = G + F, gA = [0, 3, 6, 1, 4, 7, 2, 5, 8], fA = [
|
|
9,
|
|
14,
|
|
19,
|
|
10,
|
|
15,
|
|
20,
|
|
11,
|
|
16,
|
|
21,
|
|
12,
|
|
17,
|
|
22,
|
|
13,
|
|
18,
|
|
23
|
|
], dA = [
|
|
24,
|
|
31,
|
|
38,
|
|
25,
|
|
32,
|
|
39,
|
|
26,
|
|
33,
|
|
40,
|
|
27,
|
|
34,
|
|
41,
|
|
28,
|
|
35,
|
|
42,
|
|
29,
|
|
36,
|
|
43,
|
|
30,
|
|
37,
|
|
44
|
|
], xA = b >= 1 ? new Float32Array(3 * 3) : void 0, CA = b >= 2 ? new Float32Array(5 * 3) : void 0, YA = b >= 3 ? new Float32Array(7 * 3) : void 0, SA = x / 2 / m, OA = E + U, jA = E + F, Y = new DataView(
|
|
t.buffer,
|
|
jA,
|
|
G
|
|
), DA = new Float32Array(
|
|
t.buffer,
|
|
OA,
|
|
D * 3
|
|
), lA = new Uint32Array(
|
|
t.buffer,
|
|
E,
|
|
S
|
|
);
|
|
let Gt = k, Ae = M;
|
|
for (let MA = 0; MA < p; ++MA) {
|
|
const z = MA * W;
|
|
let ZA;
|
|
if (MA < M)
|
|
ZA = Math.floor(MA / y);
|
|
else {
|
|
const WA = lA[Gt - k];
|
|
MA >= Ae + WA && (Gt += 1, Ae += WA), ZA = Gt;
|
|
}
|
|
const ye = c === 0 ? Y.getFloat32(z + 0, !0) : (Y.getUint16(z + 0, !0) - m) * SA + DA[3 * ZA + 0], we = c === 0 ? Y.getFloat32(z + 4, !0) : (Y.getUint16(z + 2, !0) - m) * SA + DA[3 * ZA + 1], me = c === 0 ? Y.getFloat32(z + 8, !0) : (Y.getUint16(z + 4, !0) - m) * SA + DA[3 * ZA + 2], xe = c === 0 ? Y.getFloat32(z + O + 0, !0) : wA(Y.getUint16(z + O + 0, !0)), Se = c === 0 ? Y.getFloat32(z + O + 4, !0) : wA(Y.getUint16(z + O + 2, !0)), co = c === 0 ? Y.getFloat32(z + O + 8, !0) : wA(Y.getUint16(z + O + 4, !0)), go = c === 0 ? Y.getFloat32(z + L + 0, !0) : wA(
|
|
Y.getUint16(z + L + 0, !0)
|
|
), lo = c === 0 ? Y.getFloat32(z + L + 4, !0) : wA(
|
|
Y.getUint16(z + L + 2, !0)
|
|
), Io = c === 0 ? Y.getFloat32(z + L + 8, !0) : wA(
|
|
Y.getUint16(z + L + 4, !0)
|
|
), uo = c === 0 ? Y.getFloat32(z + L + 12, !0) : wA(
|
|
Y.getUint16(z + L + 6, !0)
|
|
), ho = Y.getUint8(z + j + 0) / 255, Co = Y.getUint8(z + j + 1) / 255, Bo = Y.getUint8(z + j + 2) / 255, Eo = Y.getUint8(z + j + 3) / 255;
|
|
if (e(
|
|
MA,
|
|
ye,
|
|
we,
|
|
me,
|
|
xe,
|
|
Se,
|
|
co,
|
|
lo,
|
|
Io,
|
|
uo,
|
|
go,
|
|
Eo,
|
|
ho,
|
|
Co,
|
|
Bo
|
|
), b >= 1 && xA) {
|
|
for (const [WA, Rt] of gA.entries())
|
|
xA[WA] = Q(z, Rt);
|
|
if (CA)
|
|
for (const [WA, Rt] of fA.entries())
|
|
CA[WA] = Q(z, Rt);
|
|
if (YA)
|
|
for (const [WA, Rt] of dA.entries())
|
|
YA[WA] = Q(z, Rt);
|
|
s == null || s(MA, xA, CA, YA);
|
|
}
|
|
}
|
|
E += pA;
|
|
}
|
|
}
|
|
class ch {
|
|
constructor({ fileBytes: A }) {
|
|
this.version = -1, this.numSplats = 0, this.shDegree = 0, this.fractionalBits = 0, this.flags = 0, this.flagAntiAlias = !1, this.reserved = 0, this.headerParsed = !1, this.parsed = !1, this.fileBytes = A instanceof ArrayBuffer ? new Uint8Array(A) : A, this.reader = new Ai({ fileBytes: this.fileBytes });
|
|
}
|
|
async parseHeader() {
|
|
if (this.headerParsed)
|
|
throw new Error("SPZ file header already parsed");
|
|
const A = new DataView((await this.reader.read(16)).buffer);
|
|
if (A.getUint32(0, !0) !== 1347635022)
|
|
throw new Error("Invalid SPZ file");
|
|
if (this.version = A.getUint32(4, !0), this.version < 1 || this.version > 3)
|
|
throw new Error(`Unsupported SPZ version: ${this.version}`);
|
|
this.numSplats = A.getUint32(8, !0), this.shDegree = A.getUint8(12), this.fractionalBits = A.getUint8(13), this.flags = A.getUint8(14), this.flagAntiAlias = (this.flags & 1) !== 0, this.reserved = A.getUint8(15), this.headerParsed = !0, this.parsed = !1;
|
|
}
|
|
async parseSplats(A, e, s, n, i, r) {
|
|
if (!this.headerParsed)
|
|
throw new Error("SPZ file header must be parsed first");
|
|
if (this.parsed)
|
|
throw new Error("SPZ file already parsed");
|
|
if (this.parsed = !0, this.version === 1) {
|
|
const a = await this.reader.read(this.numSplats * 3 * 2), o = new Uint16Array(a.buffer);
|
|
for (let g = 0; g < this.numSplats; g++) {
|
|
const l = g * 3, c = wA(o[l]), I = wA(o[l + 1]), h = wA(o[l + 2]);
|
|
A == null || A(g, c, I, h);
|
|
}
|
|
} else if (this.version === 2 || this.version === 3) {
|
|
const a = 1 << this.fractionalBits, o = await this.reader.read(this.numSplats * 3 * 3);
|
|
for (let g = 0; g < this.numSplats; g++) {
|
|
const l = g * 9, c = ((o[l + 2] << 24 | o[l + 1] << 16 | o[l] << 8) >> 8) / a, I = ((o[l + 5] << 24 | o[l + 4] << 16 | o[l + 3] << 8) >> 8) / a, h = ((o[l + 8] << 24 | o[l + 7] << 16 | o[l + 6] << 8) >> 8) / a;
|
|
A == null || A(g, c, I, h);
|
|
}
|
|
} else
|
|
throw new Error("Unreachable");
|
|
{
|
|
const a = await this.reader.read(this.numSplats);
|
|
for (let o = 0; o < this.numSplats; o++)
|
|
e == null || e(o, a[o] / 255);
|
|
}
|
|
{
|
|
const a = await this.reader.read(this.numSplats * 3), o = eo / 0.15;
|
|
for (let g = 0; g < this.numSplats; g++) {
|
|
const l = g * 3, c = (a[l] / 255 - 0.5) * o + 0.5, I = (a[l + 1] / 255 - 0.5) * o + 0.5, h = (a[l + 2] / 255 - 0.5) * o + 0.5;
|
|
s == null || s(g, c, I, h);
|
|
}
|
|
}
|
|
{
|
|
const a = await this.reader.read(this.numSplats * 3);
|
|
for (let o = 0; o < this.numSplats; o++) {
|
|
const g = o * 3, l = Math.exp(a[g] / 16 - 10), c = Math.exp(a[g + 1] / 16 - 10), I = Math.exp(a[g + 2] / 16 - 10);
|
|
n == null || n(o, l, c, I);
|
|
}
|
|
}
|
|
if (this.version === 3) {
|
|
const a = 1 / Math.sqrt(2), o = await this.reader.read(this.numSplats * 4);
|
|
for (let g = 0; g < this.numSplats; g++) {
|
|
const l = g * 4, c = [0, 0, 0, 0], I = [
|
|
o[l],
|
|
o[l + 1],
|
|
o[l + 2],
|
|
o[l + 3]
|
|
], h = I[0] + (I[1] << 8) + (I[2] << 16) + (I[3] << 24), E = 511, C = h >>> 30;
|
|
let B = h, Q = 0;
|
|
for (let p = 3; p >= 0; --p)
|
|
if (p !== C) {
|
|
const d = B & E, y = B >>> 9 & 1;
|
|
B = B >>> 10, c[p] = a * (d / E), c[p] = y === 0 ? c[p] : -c[p], Q += c[p] * c[p];
|
|
}
|
|
const f = 1 - Q;
|
|
c[C] = Math.sqrt(Math.max(f, 0)), i == null || i(
|
|
g,
|
|
c[0],
|
|
c[1],
|
|
c[2],
|
|
c[3]
|
|
);
|
|
}
|
|
} else {
|
|
const a = await this.reader.read(this.numSplats * 3);
|
|
for (let o = 0; o < this.numSplats; o++) {
|
|
const g = o * 3, l = a[g] / 127.5 - 1, c = a[g + 1] / 127.5 - 1, I = a[g + 2] / 127.5 - 1, h = Math.sqrt(
|
|
Math.max(0, 1 - l * l - c * c - I * I)
|
|
);
|
|
i == null || i(o, l, c, I, h);
|
|
}
|
|
}
|
|
if (r && this.shDegree >= 1) {
|
|
const a = new Float32Array(9), o = this.shDegree >= 2 ? new Float32Array(5 * 3) : void 0, g = this.shDegree >= 3 ? new Float32Array(7 * 3) : void 0, l = await this.reader.read(
|
|
this.numSplats * to[this.shDegree] * 3
|
|
);
|
|
let c = 0;
|
|
for (let I = 0; I < this.numSplats; I++) {
|
|
for (let h = 0; h < 9; ++h)
|
|
a[h] = (l[c + h] - 128) / 128;
|
|
if (c += 9, o) {
|
|
for (let h = 0; h < 15; ++h)
|
|
o[h] = (l[c + h] - 128) / 128;
|
|
c += 15;
|
|
}
|
|
if (g) {
|
|
for (let h = 0; h < 21; ++h)
|
|
g[h] = (l[c + h] - 128) / 128;
|
|
c += 21;
|
|
}
|
|
r == null || r(I, a, o, g);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
const to = { 1: 3, 2: 8, 3: 15 }, eo = 0.28209479177387814, gh = 1347635022, lh = 3, Ih = 1;
|
|
class et {
|
|
constructor({
|
|
numSplats: A,
|
|
shDegree: e,
|
|
fractionalBits: s = 12,
|
|
flagAntiAlias: n = !0
|
|
}) {
|
|
this.clippedCount = 0;
|
|
const i = 20 + // Rotation
|
|
(e >= 1 ? 9 : 0) + (e >= 2 ? 15 : 0) + (e >= 3 ? 21 : 0), r = 16 + A * i;
|
|
this.buffer = new ArrayBuffer(r), this.view = new DataView(this.buffer), this.view.setUint32(0, gh, !0), this.view.setUint32(4, lh, !0), this.view.setUint32(8, A, !0), this.view.setUint8(12, e), this.view.setUint8(13, s), this.view.setUint8(14, n ? Ih : 0), this.view.setUint8(15, 0), this.numSplats = A, this.shDegree = e, this.fractionalBits = s, this.fraction = 1 << s, this.flagAntiAlias = n;
|
|
}
|
|
setCenter(A, e, s, n) {
|
|
const i = Math.round(e * this.fraction), r = Math.max(-8388607, Math.min(8388607, i)), a = Math.round(s * this.fraction), o = Math.max(-8388607, Math.min(8388607, a)), g = Math.round(n * this.fraction), l = Math.max(-8388607, Math.min(8388607, g));
|
|
(i !== r || a !== o || g !== l) && (this.clippedCount += 1);
|
|
const h = 16 + A * 9;
|
|
this.view.setUint8(h, r & 255), this.view.setUint8(h + 1, r >> 8 & 255), this.view.setUint8(h + 2, r >> 16 & 255), this.view.setUint8(h + 3, o & 255), this.view.setUint8(h + 4, o >> 8 & 255), this.view.setUint8(h + 5, o >> 16 & 255), this.view.setUint8(h + 6, l & 255), this.view.setUint8(h + 7, l >> 8 & 255), this.view.setUint8(h + 8, l >> 16 & 255);
|
|
}
|
|
setAlpha(A, e) {
|
|
const s = 16 + this.numSplats * 9 + A;
|
|
this.view.setUint8(
|
|
s,
|
|
Math.max(0, Math.min(255, Math.round(e * 255)))
|
|
);
|
|
}
|
|
static scaleRgb(A) {
|
|
const e = ((A - 0.5) / (eo / 0.15) + 0.5) * 255;
|
|
return Math.max(0, Math.min(255, Math.round(e)));
|
|
}
|
|
setRgb(A, e, s, n) {
|
|
const i = 16 + this.numSplats * 10 + A * 3;
|
|
this.view.setUint8(i, et.scaleRgb(e)), this.view.setUint8(i + 1, et.scaleRgb(s)), this.view.setUint8(i + 2, et.scaleRgb(n));
|
|
}
|
|
setScale(A, e, s, n) {
|
|
const i = 16 + this.numSplats * 13 + A * 3;
|
|
this.view.setUint8(
|
|
i,
|
|
Math.max(0, Math.min(255, Math.round((Math.log(e) + 10) * 16)))
|
|
), this.view.setUint8(
|
|
i + 1,
|
|
Math.max(0, Math.min(255, Math.round((Math.log(s) + 10) * 16)))
|
|
), this.view.setUint8(
|
|
i + 2,
|
|
Math.max(0, Math.min(255, Math.round((Math.log(n) + 10) * 16)))
|
|
);
|
|
}
|
|
setQuat(A, ...e) {
|
|
const s = 16 + this.numSplats * 16 + A * 4, n = zn(e);
|
|
let i = 0;
|
|
for (let o = 1; o < 4; ++o)
|
|
Math.abs(n[o]) > Math.abs(n[i]) && (i = o);
|
|
const r = n[i] < 0 ? 1 : 0;
|
|
let a = i;
|
|
for (let o = 0; o < 4; ++o)
|
|
if (o !== i) {
|
|
const g = (n[o] < 0 ? 1 : 0) ^ r, l = Math.floor(
|
|
511 * (Math.abs(n[o]) / Math.SQRT1_2) + 0.5
|
|
);
|
|
a = a << 10 | g << 9 | l;
|
|
}
|
|
this.view.setUint8(s, a & 255), this.view.setUint8(s + 1, a >> 8 & 255), this.view.setUint8(s + 2, a >> 16 & 255), this.view.setUint8(s + 3, a >>> 24 & 255);
|
|
}
|
|
static quantizeSh(A, e) {
|
|
const s = Math.round(A * 128) + 128, n = 1 << 8 - e, i = Math.floor((s + n / 2) / n) * n;
|
|
return Math.max(0, Math.min(255, i));
|
|
}
|
|
setSh(A, e, s, n) {
|
|
const i = to[this.shDegree] || 0, r = 16 + this.numSplats * 20 + A * i * 3;
|
|
for (let a = 0; a < 9; ++a)
|
|
this.view.setUint8(r + a, et.quantizeSh(e[a], 5));
|
|
if (s) {
|
|
const a = r + 9;
|
|
for (let o = 0; o < 15; ++o)
|
|
this.view.setUint8(a + o, et.quantizeSh(s[o], 4));
|
|
if (n) {
|
|
const o = a + 15;
|
|
for (let g = 0; g < 21; ++g)
|
|
this.view.setUint8(o + g, et.quantizeSh(n[g], 4));
|
|
}
|
|
}
|
|
}
|
|
async finalize() {
|
|
const A = new Uint8Array(this.buffer), s = new ReadableStream({
|
|
async start(r) {
|
|
r.enqueue(A), r.close();
|
|
}
|
|
}).pipeThrough(new CompressionStream("gzip")), i = await new Response(s).arrayBuffer();
|
|
return console.log(
|
|
"Compressed",
|
|
A.length,
|
|
"bytes to",
|
|
i.byteLength,
|
|
"bytes"
|
|
), new Uint8Array(i);
|
|
}
|
|
}
|
|
async function Xh(t) {
|
|
var l, c, I;
|
|
const A = new Xu(), {
|
|
inputs: e,
|
|
clipXyz: s,
|
|
maxSh: n,
|
|
fractionalBits: i = 12,
|
|
opacityThreshold: r
|
|
} = t;
|
|
for (const h of e) {
|
|
let E = function(w) {
|
|
return w.multiplyScalar(p), w.applyQuaternion(d), w.add(y), w;
|
|
}, C = function(w) {
|
|
return w.multiplyScalar(p), w;
|
|
}, B = function(w) {
|
|
return w.premultiply(d), w;
|
|
}, Q = function(w) {
|
|
return !D || D.containsPoint(w);
|
|
}, f = function(w) {
|
|
return r !== void 0 ? w >= r : !0;
|
|
};
|
|
const p = ((l = h.transform) == null ? void 0 : l.scale) ?? 1, d = new u.Quaternion().fromArray(
|
|
((c = h.transform) == null ? void 0 : c.quaternion) ?? [0, 0, 0, 1]
|
|
), y = new u.Vector3().fromArray(
|
|
((I = h.transform) == null ? void 0 : I.translate) ?? [0, 0, 0]
|
|
), D = s ? new u.Box3(
|
|
new u.Vector3().fromArray(s.min),
|
|
new u.Vector3().fromArray(s.max)
|
|
) : void 0;
|
|
let x = h.fileType;
|
|
switch (x || (x = ja(h.fileBytes), !x && h.pathOrUrl && (x = Wa(h.pathOrUrl))), x) {
|
|
case _t.PLY: {
|
|
const w = new ue({ fileBytes: h.fileBytes });
|
|
await w.parseHeader();
|
|
let m = null;
|
|
w.parseSplats(
|
|
(k, M, S, U, F, b, T, R, X, _, eA, q, O, L, j) => {
|
|
const P = E(new u.Vector3(M, S, U));
|
|
if (Q(P) && f(q)) {
|
|
m = A.pushSplat(), A.setCenter(m, P.x, P.y, P.z);
|
|
const W = C(
|
|
new u.Vector3(F, b, T)
|
|
);
|
|
A.setScale(m, W.x, W.y, W.z);
|
|
const G = B(
|
|
new u.Quaternion(R, X, _, eA)
|
|
);
|
|
A.setQuaternion(
|
|
m,
|
|
G.x,
|
|
G.y,
|
|
G.z,
|
|
G.w
|
|
), A.setOpacity(m, q), A.setColor(m, O, L, j);
|
|
} else
|
|
m = null;
|
|
},
|
|
(k, M, S, U) => {
|
|
M && m !== null && A.setSh1(m, M), S && m !== null && A.setSh2(m, S), U && m !== null && A.setSh3(m, U);
|
|
}
|
|
);
|
|
break;
|
|
}
|
|
case _t.SPZ: {
|
|
const w = new ch({ fileBytes: h.fileBytes });
|
|
await w.parseHeader();
|
|
const m = new Int32Array(w.numSplats);
|
|
m.fill(-1);
|
|
const k = new Float32Array(w.numSplats * 3), M = new u.Vector3();
|
|
w.parseSplats(
|
|
(S, U, F, b) => {
|
|
const T = E(new u.Vector3(U, F, b));
|
|
k[S * 3] = T.x, k[S * 3 + 1] = T.y, k[S * 3 + 2] = T.z;
|
|
},
|
|
(S, U) => {
|
|
M.fromArray(k, S * 3), Q(M) && f(U) && (m[S] = A.pushSplat(), A.setCenter(m[S], M.x, M.y, M.z), A.setOpacity(m[S], U));
|
|
},
|
|
(S, U, F, b) => {
|
|
m[S] >= 0 && A.setColor(m[S], U, F, b);
|
|
},
|
|
(S, U, F, b) => {
|
|
if (m[S] >= 0) {
|
|
const T = C(
|
|
new u.Vector3(U, F, b)
|
|
);
|
|
A.setScale(m[S], T.x, T.y, T.z);
|
|
}
|
|
},
|
|
(S, U, F, b, T) => {
|
|
if (m[S] >= 0) {
|
|
const R = B(
|
|
new u.Quaternion(U, F, b, T)
|
|
);
|
|
A.setQuaternion(
|
|
m[S],
|
|
R.x,
|
|
R.y,
|
|
R.z,
|
|
R.w
|
|
);
|
|
}
|
|
},
|
|
(S, U, F, b) => {
|
|
m[S] >= 0 && (A.setSh1(m[S], U), F && A.setSh2(m[S], F), b && A.setSh3(m[S], b));
|
|
}
|
|
);
|
|
break;
|
|
}
|
|
case _t.SPLAT:
|
|
rh(
|
|
h.fileBytes,
|
|
(w) => {
|
|
},
|
|
(w, m, k, M, S, U, F, b, T, R, X, _, eA, q, O) => {
|
|
const L = E(new u.Vector3(m, k, M));
|
|
if (Q(L) && f(_)) {
|
|
const j = A.pushSplat();
|
|
A.setCenter(j, L.x, L.y, L.z);
|
|
const P = C(
|
|
new u.Vector3(S, U, F)
|
|
);
|
|
A.setScale(j, P.x, P.y, P.z);
|
|
const W = B(
|
|
new u.Quaternion(b, T, R, X)
|
|
);
|
|
A.setQuaternion(
|
|
j,
|
|
W.x,
|
|
W.y,
|
|
W.z,
|
|
W.w
|
|
), A.setOpacity(j, _), A.setColor(j, eA, q, O);
|
|
}
|
|
}
|
|
);
|
|
break;
|
|
case _t.KSPLAT: {
|
|
let w = null;
|
|
oh(
|
|
h.fileBytes,
|
|
(m) => {
|
|
},
|
|
(m, k, M, S, U, F, b, T, R, X, _, eA, q, O, L) => {
|
|
const j = E(new u.Vector3(k, M, S));
|
|
if (Q(j) && f(eA)) {
|
|
w = A.pushSplat(), A.setCenter(w, j.x, j.y, j.z);
|
|
const P = C(
|
|
new u.Vector3(U, F, b)
|
|
);
|
|
A.setScale(w, P.x, P.y, P.z);
|
|
const W = B(
|
|
new u.Quaternion(T, R, X, _)
|
|
);
|
|
A.setQuaternion(
|
|
w,
|
|
W.x,
|
|
W.y,
|
|
W.z,
|
|
W.w
|
|
), A.setOpacity(w, eA), A.setColor(w, q, O, L);
|
|
} else
|
|
w = null;
|
|
},
|
|
(m, k, M, S) => {
|
|
w !== null && (A.setSh1(w, k), M && A.setSh2(w, M), S && A.setSh3(w, S));
|
|
}
|
|
);
|
|
break;
|
|
}
|
|
default:
|
|
throw new Error(`transcodeSpz not implemented for ${x}`);
|
|
}
|
|
}
|
|
const a = Math.min(
|
|
n ?? 3,
|
|
A.sh3 ? 3 : A.sh2 ? 2 : A.sh1 ? 1 : 0
|
|
), o = new et({
|
|
numSplats: A.numSplats,
|
|
shDegree: a,
|
|
fractionalBits: i,
|
|
flagAntiAlias: !0
|
|
});
|
|
for (let h = 0; h < A.numSplats; ++h) {
|
|
const E = h * 3, C = h * 4;
|
|
o.setCenter(
|
|
h,
|
|
A.centers[E],
|
|
A.centers[E + 1],
|
|
A.centers[E + 2]
|
|
), o.setScale(
|
|
h,
|
|
A.scales[E],
|
|
A.scales[E + 1],
|
|
A.scales[E + 2]
|
|
), o.setQuat(
|
|
h,
|
|
A.quaternions[C],
|
|
A.quaternions[C + 1],
|
|
A.quaternions[C + 2],
|
|
A.quaternions[C + 3]
|
|
), o.setAlpha(h, A.opacities[h]), o.setRgb(
|
|
h,
|
|
A.colors[E],
|
|
A.colors[E + 1],
|
|
A.colors[E + 2]
|
|
), A.sh1 && a >= 1 && o.setSh(
|
|
h,
|
|
A.sh1.slice(h * 9, (h + 1) * 9),
|
|
a >= 2 && A.sh2 ? A.sh2.slice(h * 15, (h + 1) * 15) : void 0,
|
|
a >= 3 && A.sh3 ? A.sh3.slice(h * 21, (h + 1) * 21) : void 0
|
|
);
|
|
}
|
|
return { fileBytes: await o.finalize(), clippedCount: o.clippedCount };
|
|
}
|
|
class Oh {
|
|
constructor(A) {
|
|
this.mesh = A.mesh, this.numSplats = A.numSplats ?? this.mesh.numSplats;
|
|
const { width: e, height: s, depth: n, maxSplats: i } = mA(this.numSplats);
|
|
this.skinData = new Uint16Array(i * 4), this.skinTexture = new u.DataArrayTexture(
|
|
this.skinData,
|
|
e,
|
|
s,
|
|
n
|
|
), this.skinTexture.format = u.RGBAIntegerFormat, this.skinTexture.type = u.UnsignedShortType, this.skinTexture.internalFormat = "RGBA16UI", this.skinTexture.needsUpdate = !0, this.numBones = A.numBones ?? 256, this.boneData = new Float32Array(this.numBones * 16), this.boneTexture = new u.DataTexture(
|
|
this.boneData,
|
|
4,
|
|
this.numBones,
|
|
u.RGBAFormat,
|
|
u.FloatType
|
|
), this.boneTexture.internalFormat = "RGBA32F", this.boneTexture.needsUpdate = !0, this.uniform = new N({
|
|
key: "skinning",
|
|
type: so,
|
|
globals: () => [no],
|
|
value: {
|
|
numSplats: this.numSplats,
|
|
numBones: this.numBones,
|
|
skinTexture: this.skinTexture,
|
|
boneTexture: this.boneTexture
|
|
}
|
|
});
|
|
}
|
|
// Apply the skeletal animation to a Gsplat in a dyno program.
|
|
modify(A) {
|
|
return hh(A, this.uniform);
|
|
}
|
|
// Set the "rest" pose for a bone with position and quaternion orientation.
|
|
setRestQuatPos(A, e, s) {
|
|
const n = A * 16;
|
|
this.boneData[n + 0] = e.x, this.boneData[n + 1] = e.y, this.boneData[n + 2] = e.z, this.boneData[n + 3] = e.w, this.boneData[n + 4] = s.x, this.boneData[n + 5] = s.y, this.boneData[n + 6] = s.z, this.boneData[n + 7] = 0, this.boneData[n + 8] = 0, this.boneData[n + 9] = 0, this.boneData[n + 10] = 0, this.boneData[n + 11] = 1, this.boneData[n + 12] = 0, this.boneData[n + 13] = 0, this.boneData[n + 14] = 0, this.boneData[n + 15] = 0;
|
|
}
|
|
// Set the "current" position and orientation of a bone.
|
|
setBoneQuatPos(A, e, s) {
|
|
const n = A * 16, i = new u.Quaternion(
|
|
this.boneData[n + 0],
|
|
this.boneData[n + 1],
|
|
this.boneData[n + 2],
|
|
this.boneData[n + 3]
|
|
), r = new u.Vector3(
|
|
this.boneData[n + 4],
|
|
this.boneData[n + 5],
|
|
this.boneData[n + 6]
|
|
), a = i.clone().invert(), o = s.clone().sub(r);
|
|
o.applyQuaternion(a), a.multiply(e);
|
|
const g = new u.Quaternion(
|
|
o.x,
|
|
o.y,
|
|
o.z,
|
|
0
|
|
).multiply(i);
|
|
this.boneData[n + 8] = a.x, this.boneData[n + 9] = a.y, this.boneData[n + 10] = a.z, this.boneData[n + 11] = a.w, this.boneData[n + 12] = 0.5 * g.x, this.boneData[n + 13] = 0.5 * g.y, this.boneData[n + 14] = 0.5 * g.z, this.boneData[n + 15] = 0.5 * g.w;
|
|
}
|
|
// Set up to 4 bone indices and weights for a Gsplat. For fewer than 4 bones,
|
|
// you can set the remaining weights to 0 (and index=0).
|
|
setSplatBones(A, e, s) {
|
|
const n = A * 4;
|
|
this.skinData[n + 0] = Math.min(255, Math.max(0, Math.round(s.x * 255))) + (e.x << 8), this.skinData[n + 1] = Math.min(255, Math.max(0, Math.round(s.y * 255))) + (e.y << 8), this.skinData[n + 2] = Math.min(255, Math.max(0, Math.round(s.z * 255))) + (e.z << 8), this.skinData[n + 3] = Math.min(255, Math.max(0, Math.round(s.w * 255))) + (e.w << 8);
|
|
}
|
|
// Call this to indicate that the bones have changed and the Gsplats need to be
|
|
// re-generated with updated skinning.
|
|
updateBones() {
|
|
this.boneTexture.needsUpdate = !0, this.mesh.needsUpdate = !0;
|
|
}
|
|
}
|
|
const so = { type: "GsplatSkinning" }, no = hA(`
|
|
struct GsplatSkinning {
|
|
int numSplats;
|
|
int numBones;
|
|
usampler2DArray skinTexture;
|
|
sampler2D boneTexture;
|
|
};
|
|
`), uh = hA(`
|
|
void applyGsplatSkinning(
|
|
int numSplats, int numBones,
|
|
usampler2DArray skinTexture, sampler2D boneTexture,
|
|
int splatIndex, inout vec3 center, inout vec4 quaternion
|
|
) {
|
|
if ((splatIndex < 0) || (splatIndex >= numSplats)) {
|
|
return;
|
|
}
|
|
|
|
uvec4 skinData = texelFetch(skinTexture, splatTexCoord(splatIndex), 0);
|
|
|
|
float weights[4];
|
|
weights[0] = float(skinData.x & 0xffu) / 255.0;
|
|
weights[1] = float(skinData.y & 0xffu) / 255.0;
|
|
weights[2] = float(skinData.z & 0xffu) / 255.0;
|
|
weights[3] = float(skinData.w & 0xffu) / 255.0;
|
|
|
|
uint boneIndices[4];
|
|
boneIndices[0] = (skinData.x >> 8u) & 0xffu;
|
|
boneIndices[1] = (skinData.y >> 8u) & 0xffu;
|
|
boneIndices[2] = (skinData.z >> 8u) & 0xffu;
|
|
boneIndices[3] = (skinData.w >> 8u) & 0xffu;
|
|
|
|
vec4 quat = vec4(0.0);
|
|
vec4 dual = vec4(0.0);
|
|
for (int i = 0; i < 4; i++) {
|
|
if (weights[i] > 0.0) {
|
|
int boneIndex = int(boneIndices[i]);
|
|
vec4 boneQuat = vec4(0.0, 0.0, 0.0, 1.0);
|
|
vec4 boneDual = vec4(0.0);
|
|
if (boneIndex < numBones) {
|
|
boneQuat = texelFetch(boneTexture, ivec2(2, boneIndex), 0);
|
|
boneDual = texelFetch(boneTexture, ivec2(3, boneIndex), 0);
|
|
}
|
|
|
|
if ((i > 0) && (dot(quat, boneQuat) < 0.0)) {
|
|
// Flip sign if next blend is pointing in the opposite direction
|
|
boneQuat = -boneQuat;
|
|
boneDual = -boneDual;
|
|
}
|
|
quat += weights[i] * boneQuat;
|
|
dual += weights[i] * boneDual;
|
|
}
|
|
}
|
|
|
|
// Normalize dual quaternion
|
|
float norm = length(quat);
|
|
quat /= norm;
|
|
dual /= norm;
|
|
vec3 translate = vec3(
|
|
2.0 * (-dual.w * quat.x + dual.x * quat.w - dual.y * quat.z + dual.z * quat.y),
|
|
2.0 * (-dual.w * quat.y + dual.x * quat.z + dual.y * quat.w - dual.z * quat.x),
|
|
2.0 * (-dual.w * quat.z - dual.x * quat.y + dual.y * quat.x + dual.z * quat.w)
|
|
);
|
|
|
|
center = quatVec(quat, center) + translate;
|
|
quaternion = quatQuat(quat, quaternion);
|
|
}
|
|
`);
|
|
function hh(t, A) {
|
|
return new V({
|
|
inTypes: { gsplat: AA, skinning: so },
|
|
outTypes: { gsplat: AA },
|
|
globals: () => [no, uh],
|
|
inputs: { gsplat: t, skinning: A },
|
|
statements: ({ inputs: s, outputs: n }) => {
|
|
const { skinning: i } = s, { gsplat: r } = n;
|
|
return RA(`
|
|
${r} = ${s.gsplat};
|
|
if (isGsplatActive(${r}.flags)) {
|
|
applyGsplatSkinning(
|
|
${i}.numSplats, ${i}.numBones,
|
|
${i}.skinTexture, ${i}.boneTexture,
|
|
${r}.index, ${r}.center, ${r}.quaternion
|
|
);
|
|
}
|
|
`);
|
|
}
|
|
}).outputs.gsplat;
|
|
}
|
|
function jh({
|
|
// PackedSplats object to add splats to
|
|
splats: t,
|
|
// min and max box extents of the grid
|
|
extents: A,
|
|
// step size along each grid axis
|
|
stepSize: e = 1,
|
|
// spherical radius of each Gsplat
|
|
pointRadius: s = 0.01,
|
|
// relative size of the "shadow copy" of each Gsplat placed behind it
|
|
pointShadowScale: n = 2,
|
|
// Gsplat opacity
|
|
opacity: i = 1,
|
|
// Gsplat color (THREE.Color) or function to set color for position:
|
|
// ((THREE.Color, THREE.Vector3) => void) (default: RGB-modulated grid)
|
|
color: r
|
|
}) {
|
|
const o = new u.Vector3(), g = new u.Vector3(), l = new u.Quaternion(0, 0, 0, 1);
|
|
r == null && (r = (I, h) => I.set(
|
|
0.55 + 0.45 * Math.cos(h.x * 1),
|
|
0.55 + 0.45 * Math.cos(h.y * 1),
|
|
0.55 + 0.45 * Math.cos(h.z * 1)
|
|
));
|
|
const c = new u.Color();
|
|
for (let I = A.min.z; I < A.max.z + 1e-6; I += e)
|
|
for (let h = A.min.y; h < A.max.y + 1e-6; h += e)
|
|
for (let E = A.min.x; E < A.max.x + 1e-6; E += e) {
|
|
o.set(E, h, I);
|
|
for (let C = 0; C < 2; ++C)
|
|
g.setScalar(s * (C ? 1 : n)), C ? typeof r == "function" ? r(c, o) : c.copy(r) : c.setScalar(0), t.pushSplat(o, g, l, i, c);
|
|
}
|
|
}
|
|
function Wh({
|
|
// PackedSplats object to add splats to
|
|
splats: t,
|
|
// scale (Gsplat scale along axis)
|
|
scale: A = 0.25,
|
|
// radius of the axes (Gsplat scale orthogonal to axis)
|
|
axisRadius: e = 75e-4,
|
|
// relative size of the "shadow copy" of each Gsplat placed behind it
|
|
axisShadowScale: s = 2,
|
|
// origins of the axes (default single axis at origin)
|
|
origins: n = [new u.Vector3()]
|
|
}) {
|
|
const i = new u.Vector3(), r = new u.Vector3(), a = new u.Quaternion(0, 0, 0, 1), o = new u.Color(), g = 1;
|
|
for (const l of n)
|
|
for (let c = 0; c < 3; ++c) {
|
|
i.set(
|
|
l.x + (c === 0 ? A : 0),
|
|
l.y + (c === 1 ? A : 0),
|
|
l.z + (c === 2 ? A : 0)
|
|
);
|
|
for (let I = 0; I < 2; ++I)
|
|
r.set(
|
|
(c === 0 ? A : e) * (I ? 1 : s),
|
|
(c === 1 ? A : e) * (I ? 1 : s),
|
|
(c === 2 ? A : e) * (I ? 1 : s)
|
|
), o.setRGB(
|
|
I === 0 ? 0 : c === 0 ? 1 : 0,
|
|
I === 0 ? 0 : c === 1 ? 1 : 0,
|
|
I === 0 ? 0 : c === 2 ? 1 : 0
|
|
), t.pushSplat(i, r, a, g, o);
|
|
}
|
|
}
|
|
function AC({
|
|
// PackedSplats object to add splats to
|
|
splats: t,
|
|
// center of the sphere (default: origin)
|
|
origin: A = new u.Vector3(),
|
|
// radius of the sphere
|
|
radius: e = 1,
|
|
// maximum depth of recursion for subdividing the sphere
|
|
// Warning: Gsplat count grows exponentially with depth
|
|
maxDepth: s = 3,
|
|
// filter function to apply to each point, for example to select
|
|
// points in a certain direction or other function ((THREE.Vector3) => boolean)
|
|
// (default: null)
|
|
filter: n = null,
|
|
// radius of each oriented Gsplat
|
|
pointRadius: i = 0.02,
|
|
// flatness of each oriented Gsplat
|
|
pointThickness: r = 1e-3,
|
|
// color of each Gsplat (THREE.Color) or function to set color for point:
|
|
// ((THREE.Color, THREE.Vector3) => void) (default: white)
|
|
color: a = new u.Color(1, 1, 1)
|
|
}) {
|
|
const o = {};
|
|
function g(C) {
|
|
if (n && !n(C))
|
|
return;
|
|
const B = `${C.x},${C.y},${C.z}`;
|
|
o[B] || (o[B] = C);
|
|
}
|
|
function l(C, B, Q, f) {
|
|
if (g(B), g(Q), g(f), C >= s)
|
|
return;
|
|
const p = new u.Vector3().addVectors(B, Q).normalize(), d = new u.Vector3().addVectors(Q, f).normalize(), y = new u.Vector3().addVectors(f, B).normalize();
|
|
l(C + 1, B, p, y), l(C + 1, p, Q, d), l(C + 1, y, d, f), l(C + 1, p, d, y);
|
|
}
|
|
for (const C of [-1, 1])
|
|
for (const B of [-1, 1])
|
|
for (const Q of [-1, 1]) {
|
|
const f = new u.Vector3(C, 0, 0), p = new u.Vector3(0, B, 0), d = new u.Vector3(0, 0, Q);
|
|
l(0, f, p, d);
|
|
}
|
|
const c = Object.values(o), I = new u.Vector3(i, i, r), h = new u.Quaternion(), E = typeof a == "function" ? new u.Color() : a;
|
|
for (const C of c)
|
|
h.setFromUnitVectors(new u.Vector3(0, 0, -1), C), typeof a == "function" && a(E, C), C.multiplyScalar(e), C.add(A), t.pushSplat(C, I, h, 1, E);
|
|
}
|
|
function tC({
|
|
// text string to display
|
|
text: t,
|
|
// browser font to render text with (default: "Arial")
|
|
font: A,
|
|
// font size in pixels/Gsplats (default: 32)
|
|
fontSize: e,
|
|
// SplatMesh.recolor tint assuming white Gsplats (default: white)
|
|
color: s,
|
|
// Individual Gsplat color (default: white)
|
|
rgb: n,
|
|
// Gsplat radius (default: 0.8 covers 1-unit spacing well)
|
|
dotRadius: i,
|
|
// text alignment: "left", "center", "right", "start", "end" (default: "start")
|
|
textAlign: r,
|
|
// line spacing multiplier, lines delimited by "\n" (default: 1.0)
|
|
lineHeight: a,
|
|
// Coordinate scale in object-space (default: 1.0)
|
|
objectScale: o
|
|
}) {
|
|
A = A ?? "Arial", e = e ?? 32, s = s ?? new u.Color(1, 1, 1), i = i ?? 0.8, r = r ?? "start", a = a ?? 1, o = o ?? 1;
|
|
const g = t.split(`
|
|
`), l = document.createElement("canvas"), c = l.getContext("2d");
|
|
if (!c)
|
|
throw new Error("Failed to create canvas context");
|
|
c.font = `${e}px ${A}`, c.textAlign = r;
|
|
const I = c.measureText(""), h = I.fontBoundingBoxAscent + I.fontBoundingBoxDescent;
|
|
let E = Number.POSITIVE_INFINITY, C = Number.NEGATIVE_INFINITY, B = Number.POSITIVE_INFINITY, Q = Number.NEGATIVE_INFINITY;
|
|
for (let F = 0; F < g.length; ++F) {
|
|
const b = c.measureText(g[F]), T = h * a * F;
|
|
E = Math.min(E, -b.actualBoundingBoxLeft), C = Math.max(C, b.actualBoundingBoxRight), B = Math.min(B, T - b.actualBoundingBoxAscent), Q = Math.max(Q, T + b.actualBoundingBoxDescent);
|
|
}
|
|
const f = Math.floor(E), p = Math.floor(B), d = Math.ceil(C) - f, y = Math.ceil(Q) - p;
|
|
l.width = d, l.height = y, c.font = `${e}px ${A}`, c.textAlign = r, c.textBaseline = "alphabetic", c.fillStyle = "#FFFFFF";
|
|
for (let F = 0; F < g.length; ++F) {
|
|
const b = h * a * F - p;
|
|
c.fillText(g[F], -f, b);
|
|
}
|
|
const D = c.getImageData(0, 0, d, y), x = new Uint8Array(D.data.buffer), w = new VA(), m = new u.Vector3(), k = new u.Vector3().setScalar(i * o), M = new u.Quaternion(0, 0, 0, 1);
|
|
n = n ?? new u.Color(1, 1, 1);
|
|
let S = 0;
|
|
for (let F = 0; F < y; ++F)
|
|
for (let b = 0; b < d; ++b) {
|
|
const T = x[S + 3];
|
|
if (T > 0) {
|
|
const R = T / 255;
|
|
m.set(b - 0.5 * (d - 1), 0.5 * (y - 1) - F, 0), m.multiplyScalar(o), w.pushSplat(m, k, M, R, n);
|
|
}
|
|
S += 4;
|
|
}
|
|
const U = new pt({ packedSplats: w });
|
|
return U.recolor = s, U;
|
|
}
|
|
function eC({
|
|
// URL of the image to convert to splats (example: `url: "./image.png"`)
|
|
url: t,
|
|
// Radius of each Gsplat, default covers 1-unit spacing well (default: 0.8)
|
|
dotRadius: A,
|
|
// Subsampling factor for the image. Higher values reduce resolution,
|
|
// for example 2 will halve the width and height by averaging (default: 1)
|
|
subXY: e,
|
|
// Optional callback function to modify each Gsplat before it's added.
|
|
// Return null to skip adding the Gsplat, or a number to set the opacity
|
|
// and add the Gsplat with parameter values in the objects center, rgba etc. were
|
|
// passed into the forEachSplat callback. Ending the callback in `return opacity;`
|
|
// will retain the original opacity.
|
|
// ((width: number, height: number, index: number, center: THREE.Vector3, scales: THREE.Vector3, quaternion: THREE.Quaternion, opacity: number, color: THREE.Color) => number | null)
|
|
forEachSplat: s
|
|
}) {
|
|
return A = A ?? 0.8, e = Math.max(1, Math.floor(e ?? 1)), new pt({
|
|
constructSplats: async (n) => new Promise((i, r) => {
|
|
const a = new Image();
|
|
a.crossOrigin = "anonymous", a.onerror = r, a.onload = () => {
|
|
const { width: o, height: g } = a, l = document.createElement("canvas");
|
|
l.width = o, l.height = g;
|
|
const c = l.getContext("2d");
|
|
if (!c) {
|
|
r(new Error("Failed to create canvas context"));
|
|
return;
|
|
}
|
|
c.imageSmoothingEnabled = !0, c.imageSmoothingQuality = "high";
|
|
const I = Math.round(o / e), h = Math.round(g / e);
|
|
c.drawImage(a, 0, 0, I, h);
|
|
try {
|
|
const E = c.getImageData(0, 0, I, h), C = new Uint8Array(E.data.buffer), B = new u.Vector3(), Q = new u.Vector3().setScalar(A), f = new u.Quaternion(0, 0, 0, 1), p = new u.Color();
|
|
let d = 0;
|
|
for (let y = 0; y < h; ++y)
|
|
for (let D = 0; D < I; ++D) {
|
|
const x = d * 4, w = C[x + 3];
|
|
if (w > 0) {
|
|
let m = w / 255;
|
|
p.set(
|
|
C[x + 0] / 255,
|
|
C[x + 1] / 255,
|
|
C[x + 2] / 255
|
|
), B.set(
|
|
D - 0.5 * (I - 1),
|
|
0.5 * (h - 1) - y,
|
|
0
|
|
), Q.setScalar(A), f.set(0, 0, 0, 1);
|
|
let k = !0;
|
|
if (s) {
|
|
const M = s(
|
|
I,
|
|
h,
|
|
d,
|
|
B,
|
|
Q,
|
|
f,
|
|
m,
|
|
p
|
|
);
|
|
m = M ?? m, k = M !== null;
|
|
}
|
|
k && n.pushSplat(B, Q, f, m, p);
|
|
}
|
|
d += 1;
|
|
}
|
|
i();
|
|
} catch (E) {
|
|
r(E);
|
|
}
|
|
}, a.src = t;
|
|
})
|
|
});
|
|
}
|
|
function Ch({
|
|
box: t,
|
|
cells: A,
|
|
dotScale: e,
|
|
color: s,
|
|
opacity: n
|
|
}) {
|
|
A.x = Math.max(1, Math.round(A.x)), A.y = Math.max(1, Math.round(A.y)), A.z = Math.max(1, Math.round(A.z)), n = n ?? 1;
|
|
const i = A.x * A.y * A.z, r = J("int", A.x), a = J("int", A.y);
|
|
J("int", A.z);
|
|
const o = HA(0), g = new Vt({
|
|
numSplats: i,
|
|
generator: vA(
|
|
{ index: "int" },
|
|
{ gsplat: AA },
|
|
({ index: c }) => {
|
|
if (!c)
|
|
throw new Error("index is undefined");
|
|
const I = Le(c, r), h = re(c, r), E = Le(h, a), C = re(h, a), B = $A({
|
|
vectorType: "ivec3",
|
|
x: I,
|
|
y: E,
|
|
z: C
|
|
}), Q = er(o), f = $A({ vectorType: "ivec2", x: c, y: Q }), p = ra(f), d = J("vec3", t.min), y = J("vec3", t.max), D = Qt(y, d), x = re(BA(Bt(B), p), J("vec3", A));
|
|
let w, m, k;
|
|
s ? (w = J("float", s.r), m = J("float", s.g), k = J("float", s.b)) : { r: w, g: m, b: k } = Et(x).outputs;
|
|
const M = $A({
|
|
vectorType: "vec4",
|
|
r: w,
|
|
g: m,
|
|
b: k,
|
|
a: J("float", n)
|
|
}), S = BA(d, iA(D, x)), U = Bt(J("float", e)), F = J("vec4", new u.Quaternion(0, 0, 0, 1));
|
|
let b = rt({
|
|
flags: oe("uint", "GSPLAT_FLAG_ACTIVE"),
|
|
index: c,
|
|
center: S,
|
|
scales: U,
|
|
quaternion: F,
|
|
rgba: M
|
|
});
|
|
return b = l.applyGsplat(b), { gsplat: b };
|
|
},
|
|
{
|
|
globals: () => [bA]
|
|
}
|
|
),
|
|
update: ({ time: c }) => {
|
|
o.value = c, l.update(g), g.updateVersion();
|
|
}
|
|
}), l = new xt();
|
|
return g;
|
|
}
|
|
const Bh = {
|
|
box: new u.Box3(
|
|
new u.Vector3(-1, -1, -1),
|
|
new u.Vector3(1, 1, 1)
|
|
),
|
|
density: 100,
|
|
fallDirection: new u.Vector3(-1, -3, 1).normalize(),
|
|
fallVelocity: 0.02,
|
|
wanderScale: 0.04,
|
|
wanderVariance: 2,
|
|
color1: new u.Color(1, 1, 1),
|
|
color2: new u.Color(0.5, 0.5, 1),
|
|
minScale: 1e-3,
|
|
maxScale: 5e-3,
|
|
anisoScale: new u.Vector3(1, 1, 1)
|
|
}, Eh = {
|
|
box: new u.Box3(
|
|
new u.Vector3(-2, -1, -2),
|
|
new u.Vector3(2, 5, 2)
|
|
),
|
|
density: 10,
|
|
fallDirection: new u.Vector3(0, -1, 0),
|
|
fallVelocity: 2,
|
|
wanderScale: 0.1,
|
|
wanderVariance: 1,
|
|
color1: new u.Color(1, 1, 1),
|
|
color2: new u.Color(0.25, 0.25, 0.5),
|
|
minScale: 5e-3,
|
|
maxScale: 0.01,
|
|
anisoScale: new u.Vector3(0.1, 1, 0.1)
|
|
};
|
|
function Qh({
|
|
// min and max box extents of the snowBox
|
|
box: t,
|
|
// minimum y-coordinate to clamp particle position, which can be used to
|
|
// fake hitting a ground plane and lingering there for a bit
|
|
minY: A,
|
|
// number of Gsplats to generate (default: calculated from box and density)
|
|
numSplats: e,
|
|
// density of Gsplats per unit volume (default: 100)
|
|
density: s,
|
|
// The xyz anisotropic scale of the Gsplat, which can be used for example
|
|
// to elongate rain particles (default: (1, 1, 1))
|
|
anisoScale: n,
|
|
// Minimum Gsplat particle scale (default: 0.001)
|
|
minScale: i,
|
|
// Maximum Gsplat particle scale (default: 0.005)
|
|
maxScale: r,
|
|
// The average direction of fall (default: (0, -1, 0))
|
|
fallDirection: a,
|
|
// The average speed of the fall (multiplied with fallDirection) (default: 0.02)
|
|
fallVelocity: o,
|
|
// The world scale of wandering overlay motion (default: 0.01)
|
|
wanderScale: g,
|
|
// Controls how uniformly the particles wander in sync, more variance mean
|
|
// more randomness in the motion (default: 2)
|
|
wanderVariance: l,
|
|
// Color 1 of the two colors interpolated between (default: (1, 1, 1))
|
|
color1: c,
|
|
// Color 2 of the two colors interpolated between (default: (0.5, 0.5, 1))
|
|
color2: I,
|
|
// The base opacity of the Gsplats (default: 1)
|
|
opacity: h,
|
|
// Optional callback function to call each frame.
|
|
onFrame: E
|
|
}) {
|
|
t = t ?? new u.Box3(new u.Vector3(-1, -1, -1), new u.Vector3(1, 1, 1));
|
|
const C = (t.max.x - t.min.x) * (t.max.y - t.min.y) * (t.max.z - t.min.z);
|
|
s = s ?? 100, e = e ?? Math.max(1, Math.min(1e6, Math.round(C * s)));
|
|
const B = HA(i ?? 1e-3), Q = HA(r ?? 5e-3), f = tt(
|
|
((n == null ? void 0 : n.clone()) ?? new u.Vector3(1, 1, 1)).normalize()
|
|
), p = tt(
|
|
(a ?? new u.Vector3(0, -1, 0)).normalize()
|
|
), d = HA(o ?? 0.02), y = HA(g ?? 0.01), D = HA(l ?? 2), x = tt(c ?? new u.Color(1, 1, 1)), w = tt(I ?? new u.Color(0.5, 0.5, 1)), m = HA(h ?? 1), k = HA(0), M = tt(new u.Vector3(0, 0, 0)), S = tt(t.min), U = tt(t.max), F = HA(A ?? Number.NEGATIVE_INFINITY), b = Qt(U, S), T = new Vt({
|
|
numSplats: e,
|
|
generator: vA(
|
|
{ index: "int" },
|
|
{ gsplat: AA },
|
|
({ index: X }) => {
|
|
if (!X)
|
|
throw new Error("index not defined");
|
|
const _ = He(X), eA = Et(_).outputs.w;
|
|
let q = Bt(_), O = ae(iA(eA, J("float", 100)));
|
|
O = qe(iA(oe("float", "PI"), O)), O = BA(B, iA(O, Qt(Q, B)));
|
|
const L = iA(O, f), j = ae(iA(eA, J("float", 10))), P = ae(eA), W = ii(x, w, P), G = iA(W, j), pA = He(
|
|
$A({
|
|
vectorType: "ivec2",
|
|
x: X,
|
|
y: J("int", 6837)
|
|
})
|
|
);
|
|
let gA = Bt(pA), fA = iA(Et(pA).outputs.w, D);
|
|
fA = BA(k, fA), q = BA(q, M);
|
|
const dA = si(
|
|
q,
|
|
J("vec3", new u.Vector3(1, 1, 1))
|
|
);
|
|
q = BA(S, iA(b, dA));
|
|
const xA = J("vec4", new u.Quaternion(0, 0, 0, 1));
|
|
gA = qe(BA(Bt(fA), gA)), gA = iA(gA, y);
|
|
let CA = BA(q, gA), YA = Et(CA).outputs.y;
|
|
YA = ni(F, YA), CA = $A({ vector: CA, y: YA });
|
|
let SA = rt({
|
|
flags: oe("uint", "GSPLAT_FLAG_ACTIVE"),
|
|
index: X,
|
|
center: CA,
|
|
scales: L,
|
|
quaternion: xA,
|
|
rgb: G,
|
|
opacity: m
|
|
});
|
|
return SA = R.applyGsplat(SA), { gsplat: SA };
|
|
},
|
|
{
|
|
globals: () => [bA]
|
|
}
|
|
),
|
|
update: ({ object: X, time: _, deltaTime: eA }) => {
|
|
k.value = _, R.update(T);
|
|
const q = p.value.clone().multiplyScalar(d.value * eA);
|
|
M.value.add(q), X.visible = m.value > 0, E == null || E({ object: X, time: _, deltaTime: eA }), T.updateVersion();
|
|
}
|
|
}), R = new xt();
|
|
return {
|
|
snow: T,
|
|
min: S,
|
|
max: U,
|
|
minY: F,
|
|
color1: x,
|
|
color2: w,
|
|
opacity: m,
|
|
fallVelocity: d,
|
|
wanderVariance: D,
|
|
wanderScale: y,
|
|
fallDirection: p,
|
|
minScale: B,
|
|
maxScale: Q,
|
|
anisoScale: f
|
|
};
|
|
}
|
|
const sC = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
__proto__: null,
|
|
DEFAULT_RAIN: Eh,
|
|
DEFAULT_SNOW: Bh,
|
|
snowBox: Qh,
|
|
staticBox: Ch
|
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
function io(t) {
|
|
return vA({ gsplat: AA }, { gsplat: AA }, ({ gsplat: A }) => {
|
|
if (!A)
|
|
throw new Error("No gsplat input");
|
|
let e = Re(A);
|
|
const s = t.applyGsplat(A), n = ut(s).outputs.center, i = Re(s), r = Ur(n, i), a = Ri(r, J("float", 0));
|
|
e = os(a, as(e), e);
|
|
const o = BA(
|
|
iA(e, J("float", 0.5)),
|
|
J("float", 0.5)
|
|
);
|
|
return A = rt({ gsplat: A, rgb: o }), { gsplat: A };
|
|
});
|
|
}
|
|
function ph(t) {
|
|
t.enableWorldToView = !0, t.worldModifier = io(t.context.worldToView), t.updateGenerator();
|
|
}
|
|
function ro(t, A, e, s) {
|
|
return vA({ gsplat: AA }, { gsplat: AA }, ({ gsplat: n }) => {
|
|
if (!n)
|
|
throw new Error("No gsplat input");
|
|
let { center: i } = ut(n).outputs;
|
|
i = t.apply(i);
|
|
const { z: r } = Et(i).outputs;
|
|
let a = aa(as(r), A, e);
|
|
return a = os(s, Qt(J("float", 1), a), a), n = rt({ gsplat: n, r: a, g: a, b: a }), { gsplat: n };
|
|
});
|
|
}
|
|
function fh(t, A, e, s) {
|
|
t.enableWorldToView = !0;
|
|
const n = J("float", A), i = J("float", e), r = J("bool", s ?? !1);
|
|
return t.worldModifier = ro(
|
|
t.context.worldToView,
|
|
n,
|
|
i,
|
|
r
|
|
), t.updateGenerator(), {
|
|
minDepth: n,
|
|
maxDepth: i,
|
|
reverse: r
|
|
};
|
|
}
|
|
const nC = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
__proto__: null,
|
|
makeDepthColorModifier: ro,
|
|
makeNormalColorModifier: io,
|
|
setDepthColor: fh,
|
|
setWorldNormalColor: ph
|
|
}, Symbol.toStringTag, { value: "Module" })), Kt = class Kt {
|
|
static createButton(A, e = {}) {
|
|
const s = navigator.xr;
|
|
if (!s)
|
|
return null;
|
|
const n = s, i = document.createElement("button");
|
|
A.xr.enabled = !0, A.xr.setReferenceSpaceType("local");
|
|
function r() {
|
|
let c = null;
|
|
async function I(C) {
|
|
console.log("onSessionStarted"), C.addEventListener("end", h), await A.xr.setSession(C), i.textContent = "EXIT VR", c = C;
|
|
}
|
|
function h() {
|
|
console.log("onSessionEnded"), c == null || c.removeEventListener("end", h), i.textContent = "ENTER VR", c = null;
|
|
}
|
|
i.style.display = "", i.style.cursor = "pointer", i.style.left = "calc(50% - 100px)", i.style.width = "200px", i.style.height = "100px", i.textContent = "ENTER VR";
|
|
const E = {
|
|
...e,
|
|
optionalFeatures: [
|
|
// "local-floor",
|
|
// "bounded-floor",
|
|
// "layers",
|
|
...e.optionalFeatures || []
|
|
]
|
|
};
|
|
i.onmouseenter = () => {
|
|
i.style.opacity = "1.0";
|
|
}, i.onmouseleave = () => {
|
|
i.style.opacity = "0.5";
|
|
}, i.onclick = () => {
|
|
c === null ? (console.log("requesting session"), n.requestSession("immersive-vr", E).then(
|
|
I
|
|
)) : (console.log("ending session"), c.end());
|
|
};
|
|
}
|
|
function a() {
|
|
i.style.display = "none", i.style.cursor = "auto", i.style.left = "calc(50% - 75px)", i.style.width = "150px", i.onmouseenter = null, i.onmouseleave = null, i.onclick = null;
|
|
}
|
|
function o() {
|
|
a(), i.textContent = "VR NOT SUPPORTED";
|
|
}
|
|
function g(c) {
|
|
a(), console.warn(
|
|
"Exception when trying to call xr.isSessionSupported",
|
|
c
|
|
), i.textContent = "VR NOT ALLOWED";
|
|
}
|
|
function l(c) {
|
|
c.style.position = "absolute", c.style.bottom = "20px", c.style.padding = "12px 6px", c.style.border = "1px solid #fff", c.style.borderRadius = "4px", c.style.background = "rgba(0,0,0,0.1)", c.style.color = "#fff", c.style.font = "normal 13px sans-serif", c.style.textAlign = "center", c.style.opacity = "0.5", c.style.outline = "none", c.style.zIndex = "999";
|
|
}
|
|
return i.id = "VRButton", i.style.display = "none", l(i), n.isSessionSupported("immersive-vr").then((c) => {
|
|
c ? r() : o(), c && Kt.xrSessionIsGranted && i.click();
|
|
}).catch(g), i;
|
|
}
|
|
static registerSessionGrantedListener() {
|
|
const A = navigator.xr;
|
|
if (!A)
|
|
return null;
|
|
const e = A;
|
|
/WebXRViewer\//i.test(navigator.userAgent) || e.addEventListener("sessiongranted", () => {
|
|
Kt.xrSessionIsGranted = !0;
|
|
});
|
|
}
|
|
};
|
|
Kt.xrSessionIsGranted = !1;
|
|
let Pe = Kt;
|
|
Pe.registerSessionGrantedListener();
|
|
const dh = 0.5, yh = 0.5, wh = 0;
|
|
var Is = /* @__PURE__ */ ((t) => (t.w = "wrist", t.t0 = "thumb-metacarpal", t.t1 = "thumb-phalanx-proximal", t.t2 = "thumb-phalanx-distal", t.t3 = "thumb-tip", t.i0 = "index-finger-metacarpal", t.i1 = "index-finger-phalanx-proximal", t.i2 = "index-finger-phalanx-intermediate", t.i3 = "index-finger-phalanx-distal", t.i4 = "index-finger-tip", t.m0 = "middle-finger-metacarpal", t.m1 = "middle-finger-phalanx-proximal", t.m2 = "middle-finger-phalanx-intermediate", t.m3 = "middle-finger-phalanx-distal", t.m4 = "middle-finger-tip", t.r0 = "ring-finger-metacarpal", t.r1 = "ring-finger-phalanx-proximal", t.r2 = "ring-finger-phalanx-intermediate", t.r3 = "ring-finger-phalanx-distal", t.r4 = "ring-finger-tip", t.p0 = "pinky-finger-metacarpal", t.p1 = "pinky-finger-phalanx-proximal", t.p2 = "pinky-finger-phalanx-intermediate", t.p3 = "pinky-finger-phalanx-distal", t.p4 = "pinky-finger-tip", t))(Is || {});
|
|
const ao = Object.keys(Is), iC = ao.length, rC = {
|
|
w: 0,
|
|
t0: 1,
|
|
t1: 2,
|
|
t2: 3,
|
|
t3: 4,
|
|
i0: 5,
|
|
i1: 6,
|
|
i2: 7,
|
|
i3: 8,
|
|
i4: 9,
|
|
m0: 10,
|
|
m1: 11,
|
|
m2: 12,
|
|
m3: 13,
|
|
m4: 14,
|
|
r0: 15,
|
|
r1: 16,
|
|
r2: 17,
|
|
r3: 18,
|
|
r4: 19,
|
|
p0: 20,
|
|
p1: 21,
|
|
p2: 22,
|
|
p3: 23,
|
|
p4: 24
|
|
}, ne = {
|
|
w: 0.02,
|
|
t0: 0.02,
|
|
t1: 0.014,
|
|
t2: 0.0115,
|
|
t3: 85e-4,
|
|
i0: 0.022,
|
|
i1: 0.012,
|
|
i2: 85e-4,
|
|
i3: 75e-4,
|
|
i4: 65e-4,
|
|
m0: 0.021,
|
|
m1: 0.012,
|
|
m2: 8e-3,
|
|
m3: 75e-4,
|
|
m4: 65e-4,
|
|
r0: 0.019,
|
|
r1: 0.011,
|
|
r2: 75e-4,
|
|
r3: 7e-3,
|
|
r4: 6e-3,
|
|
p0: 0.012,
|
|
p1: 0.01,
|
|
p2: 7e-3,
|
|
p3: 65e-4,
|
|
p4: 55e-4
|
|
}, mh = [
|
|
["w", "t0", "t1", "t2", "t3"],
|
|
["w", "i0", "i1", "i2", "i3", "i4"],
|
|
["w", "m0", "m1", "m2", "m3", "m4"],
|
|
["w", "r0", "r1", "r2", "r3", "r4"],
|
|
["w", "p0", "p1", "p2", "p3", "p4"]
|
|
], xh = [
|
|
[8, 10, 8, 6],
|
|
[8, 19, 14, 8, 6],
|
|
[8, 19, 14, 8, 6],
|
|
[8, 19, 14, 8, 6],
|
|
[8, 19, 14, 8, 6]
|
|
], aC = ["t3", "i4", "m4", "r4", "p4"], oC = ["i4", "m4", "r4", "p4"];
|
|
var oo = /* @__PURE__ */ ((t) => (t.left = "left", t.right = "right", t))(oo || {});
|
|
const Ze = Object.keys(oo);
|
|
class cC {
|
|
constructor() {
|
|
this.hands = {}, this.last = {}, this.values = {}, this.tests = {}, this.lastTests = {}, this.updated = !1;
|
|
}
|
|
update({ xr: A, xrFrame: e }) {
|
|
const s = A.getSession();
|
|
if (!s)
|
|
return;
|
|
const n = A.getReferenceSpace();
|
|
if (n && e.getJointPose) {
|
|
this.last = this.hands, this.lastTests = this.tests, this.hands = {}, this.values = {}, this.tests = {};
|
|
for (const i of s.inputSources) {
|
|
if (!i.hand)
|
|
continue;
|
|
const r = i.handedness;
|
|
this.hands[r] = {};
|
|
for (const a of ao) {
|
|
const o = i.hand.get(Is[a]);
|
|
if (o) {
|
|
const g = e.getJointPose(o, n);
|
|
if (g) {
|
|
const { position: l, orientation: c } = g.transform;
|
|
this.hands[r][a] = {
|
|
position: new _A(l.x, l.y, l.z),
|
|
quaternion: new hs(
|
|
c.x,
|
|
c.y,
|
|
c.z,
|
|
c.w
|
|
),
|
|
radius: g.radius || 1e-3
|
|
};
|
|
}
|
|
}
|
|
}
|
|
}
|
|
for (const i of Ze)
|
|
for (const { key: r, value: a } of [
|
|
{ key: `${i}AllTips`, value: this.allTipsTouching(i) },
|
|
{
|
|
key: `${i}IndexThumb`,
|
|
value: this.touching(i, "i4", i, "t3")
|
|
},
|
|
{
|
|
key: `${i}MiddleThumb`,
|
|
value: this.touching(i, "m4", i, "t3")
|
|
},
|
|
{
|
|
key: `${i}RingThumb`,
|
|
value: this.touching(i, "r4", i, "t3")
|
|
},
|
|
{
|
|
key: `${i}PinkyThumb`,
|
|
value: this.touching(i, "p4", i, "t3")
|
|
},
|
|
{ key: `${i}TriTips`, value: this.triTipsTouching(i) }
|
|
])
|
|
this.values[r] = a, this.tests[r] = a === 1 ? !0 : a === 0 ? !1 : this.lastTests[r] ?? !1;
|
|
}
|
|
}
|
|
makeGhostMesh() {
|
|
const A = new _A(), e = new _A(0.01, 0.01, 0.01), s = new hs(0, 0, 0, 1), n = new Cs(1, 1, 1), i = Math.PI * 3;
|
|
new Cs(1, 1, 1);
|
|
let r = 1;
|
|
const a = new pt({
|
|
onFrame: () => {
|
|
let o = 0;
|
|
for (const g of Ze) {
|
|
const l = this.hands[g];
|
|
for (const [c, I] of mh.entries())
|
|
for (let h = 1; h < I.length; ++h) {
|
|
const E = xh[c][h - 1] * 2, C = h + 1 === I.length, B = l == null ? void 0 : l[I[h - 1]], Q = l == null ? void 0 : l[I[h]];
|
|
for (let f = 0; f < E; ++f) {
|
|
const p = (f + 0.5) / E;
|
|
if (r = 0, B && Q) {
|
|
A.copy(B.position).lerp(Q.position, p), s.copy(B.quaternion).slerp(Q.quaternion, p);
|
|
const d = ne[I[h - 1]], y = ne[I[h]];
|
|
let D = (1 - p) * d + p * y;
|
|
C && p > 0.8 && (D *= Math.sqrt(1 - ((p - 0.8) / 0.2) ** 2)), e.set(0.65 * D, 0.5 * D, 3e-3), n.set(
|
|
0.55 + 0.45 * Math.sin(A.x * i),
|
|
0.55 + 0.45 * Math.sin(A.y * i),
|
|
0.55 + 0.45 * Math.sin(A.z * i)
|
|
), g === "right" && n.set(1 - n.r, 1 - n.g, 1 - n.b), r = 0.75;
|
|
}
|
|
a.packedSplats.setSplat(
|
|
o,
|
|
A,
|
|
e,
|
|
s,
|
|
r,
|
|
n
|
|
), o += 1;
|
|
}
|
|
}
|
|
}
|
|
a.packedSplats.numSplats = o, a.packedSplats.needsUpdate = !0, a.numSplats = o, a.updateVersion();
|
|
}
|
|
});
|
|
return a;
|
|
}
|
|
distance(A, e, s, n, i = !1) {
|
|
const r = i ? this.last[A] : this.hands[A], a = i ? this.last[s] : this.hands[s], o = r == null ? void 0 : r[e], g = a == null ? void 0 : a[n];
|
|
return !o || !g ? Number.POSITIVE_INFINITY : o.position.distanceTo(g.position);
|
|
}
|
|
separation(A, e, s, n, i = !1) {
|
|
const r = this.distance(A, e, s, n, i);
|
|
return r === Number.POSITIVE_INFINITY ? Number.POSITIVE_INFINITY : r - ne[e] - ne[n];
|
|
}
|
|
touching(A, e, s, n, i = !1) {
|
|
const r = this.separation(A, e, s, n, i);
|
|
return r === Number.POSITIVE_INFINITY ? Number.POSITIVE_INFINITY : 1 - Math.max(0, Math.min(1, r / 0.01 - wh));
|
|
}
|
|
allTipsTouching(A, e = !1) {
|
|
return Math.min(
|
|
this.touching(A, "t3", A, "i4", e),
|
|
this.touching(A, "i4", A, "m4", e),
|
|
this.touching(A, "m4", A, "r4", e),
|
|
this.touching(A, "r4", A, "p4", e)
|
|
// this.touching(hand, "p4", hand, "t3", last),
|
|
);
|
|
}
|
|
triTipsTouching(A, e = !1) {
|
|
return Math.min(
|
|
this.touching(A, "t3", A, "i4", e),
|
|
this.touching(A, "i4", A, "m4", e),
|
|
this.touching(A, "m4", A, "t3", e)
|
|
);
|
|
}
|
|
}
|
|
class gC {
|
|
constructor({
|
|
xrHands: A,
|
|
control: e,
|
|
moveInertia: s,
|
|
rotateInertia: n
|
|
}) {
|
|
this.lastGrip = {}, this.lastPivot = new _A(), this.rotateVelocity = 0, this.velocity = new _A(), this.xrHands = A, this.control = e, this.moveInertia = s ?? dh, this.rotateInertia = n ?? yh;
|
|
}
|
|
update(A) {
|
|
var i, r, a, o, g;
|
|
const e = {};
|
|
for (const l of Ze) {
|
|
const c = this.xrHands.hands[l];
|
|
c && this.xrHands.tests[`${l}MiddleThumb`] && (e[l] = new _A().add(((i = c.t3) == null ? void 0 : i.position) ?? new _A()).add(((r = c.i4) == null ? void 0 : r.position) ?? new _A()).add(((a = c.m4) == null ? void 0 : a.position) ?? new _A()).add(((o = c.r4) == null ? void 0 : o.position) ?? new _A()).add(((g = c.p4) == null ? void 0 : g.position) ?? new _A()).multiplyScalar(1 / 5));
|
|
}
|
|
if (e.left && e.right && this.lastGrip.left && this.lastGrip.right) {
|
|
const l = e.left.clone().add(e.right).multiplyScalar(0.5), c = this.lastGrip.left.clone().add(this.lastGrip.right).multiplyScalar(0.5);
|
|
this.lastPivot = l;
|
|
const I = l.clone().applyMatrix4(this.control.matrix);
|
|
I.sub(c.clone().applyMatrix4(this.control.matrix)), I.multiplyScalar(1 / A), this.velocity.lerp(I, 1 - Math.exp(-20 * A));
|
|
const h = Math.atan2(e.left.z - l.z, e.left.x - l.x), E = Math.atan2(
|
|
this.lastGrip.left.z - c.z,
|
|
this.lastGrip.left.x - c.x
|
|
);
|
|
let C = h - E;
|
|
C > Math.PI ? C -= Math.PI * 2 : C < -Math.PI && (C += Math.PI * 2);
|
|
const B = C / A, Q = Math.exp(-20 * A);
|
|
this.rotateVelocity = this.rotateVelocity * Q + B * (1 - Q);
|
|
} else if (this.rotateVelocity *= Math.exp(-A / this.rotateInertia), e.left && this.lastGrip.left) {
|
|
const l = e.left.clone().applyMatrix4(this.control.matrix);
|
|
l.sub(this.lastGrip.left.clone().applyMatrix4(this.control.matrix)), l.multiplyScalar(1 / A), this.velocity.lerp(l, 1 - Math.exp(-20 * A));
|
|
} else if (e.right && this.lastGrip.right) {
|
|
const l = e.right.clone().applyMatrix4(this.control.matrix);
|
|
l.sub(
|
|
this.lastGrip.right.clone().applyMatrix4(this.control.matrix)
|
|
), l.multiplyScalar(1 / A), this.velocity.lerp(l, 1 - Math.exp(-20 * A));
|
|
} else
|
|
this.velocity.multiplyScalar(Math.exp(-A / this.moveInertia));
|
|
const s = this.lastPivot.clone().negate(), n = new De().makeTranslation(s).premultiply(new De().makeRotationY(this.rotateVelocity * A)).premultiply(new De().makeTranslation(this.lastPivot));
|
|
this.control.matrix.multiply(n), this.control.matrix.decompose(
|
|
this.control.position,
|
|
this.control.quaternion,
|
|
this.control.scale
|
|
), this.control.updateMatrixWorld(!0), this.control.position.sub(this.velocity.clone().multiplyScalar(A)), this.lastGrip = e;
|
|
}
|
|
}
|
|
const Sh = 1, Dh = 2, Mh = 2e-3, vh = 6e-3, bh = 15e-4, Fh = 0.15, Nh = 0.15, kh = 0.1, Th = 2, Uh = 1, Gh = 200, Rh = 400, Yh = 50, Jh = {
|
|
KeyW: new u.Vector3(0, 0, -1),
|
|
KeyS: new u.Vector3(0, 0, 1),
|
|
KeyA: new u.Vector3(-1, 0, 0),
|
|
KeyD: new u.Vector3(1, 0, 0),
|
|
KeyR: new u.Vector3(0, 1, 0),
|
|
KeyF: new u.Vector3(0, -1, 0)
|
|
}, _h = {
|
|
ArrowUp: new u.Vector3(0, 0, -1),
|
|
ArrowDown: new u.Vector3(0, 0, 1),
|
|
ArrowLeft: new u.Vector3(-1, 0, 0),
|
|
ArrowRight: new u.Vector3(1, 0, 0),
|
|
PageUp: new u.Vector3(0, 1, 0),
|
|
PageDown: new u.Vector3(0, -1, 0)
|
|
}, Lh = {
|
|
KeyQ: new u.Vector3(0, 0, 1),
|
|
KeyE: new u.Vector3(0, 0, -1)
|
|
}, zh = {
|
|
Home: new u.Vector3(0, -1, 0),
|
|
End: new u.Vector3(0, 1, 0),
|
|
Insert: new u.Vector3(-1, 0, 0),
|
|
Delete: new u.Vector3(1, 0, 0)
|
|
};
|
|
class lC {
|
|
constructor({ canvas: A }) {
|
|
this.lastTime = 0, this.fpsMovement = new Hh({}), this.pointerControls = new qh({ canvas: A });
|
|
}
|
|
update(A) {
|
|
const e = performance.now(), s = (e - (this.lastTime || e)) / 1e3;
|
|
this.lastTime = e, this.fpsMovement.update(s, A), this.pointerControls.update(s, A);
|
|
}
|
|
}
|
|
class Hh {
|
|
constructor({
|
|
moveSpeed: A,
|
|
rollSpeed: e,
|
|
stickThreshold: s,
|
|
rotateSpeed: n,
|
|
keycodeMoveMapping: i,
|
|
keycodeRotateMapping: r,
|
|
gamepadMapping: a,
|
|
capsMultiplier: o,
|
|
shiftMultiplier: g,
|
|
ctrlMultiplier: l,
|
|
xr: c
|
|
} = {}) {
|
|
this.enable = !0, this.moveSpeed = A ?? Sh, this.rollSpeed = e ?? Dh, this.stickThreshold = s ?? kh, this.rotateSpeed = n ?? Th, this.keycodeMoveMapping = i ?? {
|
|
...Jh,
|
|
..._h
|
|
}, this.keycodeRotateMapping = r ?? {
|
|
...Lh,
|
|
...zh
|
|
}, this.gamepadMapping = a ?? {
|
|
4: "rollLeft",
|
|
5: "rollRight",
|
|
6: "ctrl",
|
|
7: "shift"
|
|
}, this.capsMultiplier = o ?? 10, this.shiftMultiplier = g ?? 5, this.ctrlMultiplier = l ?? 1 / 5, this.xr = c, this.keydown = {}, this.keycode = {}, document.addEventListener("keydown", (I) => {
|
|
this.keydown[I.key] = !0, this.keycode[I.code] = !0;
|
|
}), document.addEventListener("keyup", (I) => {
|
|
this.keydown[I.key] = !1, this.keycode[I.code] = !1;
|
|
}), window.addEventListener("blur", () => {
|
|
this.keydown = {}, this.keycode = {};
|
|
});
|
|
}
|
|
// Call this method in your render loop with `control` set to the object to control
|
|
// (`THREE.Camera` or a `THREE.Object3D` that contains it), with `deltaTime`
|
|
// in seconds since the last update.
|
|
update(A, e) {
|
|
var l, c;
|
|
if (!this.enable)
|
|
return;
|
|
const s = [new u.Vector2(), new u.Vector2()], n = navigator.getGamepads()[0];
|
|
n && (s[0].set(n.axes[0], n.axes[1]), s[1].set(n.axes[2], n.axes[3]));
|
|
const i = (n == null ? void 0 : n.buttons.map((I) => I.pressed)) || [], r = Array.from(((c = (l = this.xr) == null ? void 0 : l.getSession()) == null ? void 0 : c.inputSources) ?? []);
|
|
for (const I of r) {
|
|
const h = I.gamepad;
|
|
if (h)
|
|
switch (I.handedness) {
|
|
case "none": {
|
|
s[0].x += h.axes[0], s[0].y += h.axes[1], s[1].x += h.axes[2], s[1].y += h.axes[3];
|
|
break;
|
|
}
|
|
case "left": {
|
|
s[0].x += h.axes[2], s[0].y += h.axes[3];
|
|
break;
|
|
}
|
|
case "right": {
|
|
s[1].x += h.axes[2], s[1].y += h.axes[3];
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
for (const I of s)
|
|
I.x = Math.abs(I.x) >= this.stickThreshold ? I.x : 0, I.y = Math.abs(I.y) >= this.stickThreshold ? I.y : 0;
|
|
const a = new u.Vector3(
|
|
s[1].x,
|
|
s[1].y,
|
|
0
|
|
).multiplyScalar(this.rotateSpeed);
|
|
for (const [I, h] of Object.entries(this.keycodeRotateMapping))
|
|
this.keycode[I] && a.add(h);
|
|
for (const I in this.gamepadMapping)
|
|
if (i[Number.parseInt(I)])
|
|
switch (this.gamepadMapping[I]) {
|
|
case "rollLeft":
|
|
a.z += 1;
|
|
break;
|
|
case "rollRight":
|
|
a.z -= 1;
|
|
break;
|
|
}
|
|
if (a.multiply(
|
|
new u.Vector3(this.rotateSpeed, this.rotateSpeed, this.rollSpeed)
|
|
), a.manhattanLength() > 0) {
|
|
a.multiplyScalar(A);
|
|
const I = new u.Euler().setFromQuaternion(
|
|
e.quaternion,
|
|
"YXZ"
|
|
);
|
|
I.y -= a.x, I.x = Math.max(
|
|
-Math.PI / 2,
|
|
Math.min(Math.PI / 2, I.x - a.y)
|
|
), I.z = Math.max(-Math.PI, Math.min(Math.PI, I.z + a.z)), e.quaternion.setFromEuler(I);
|
|
}
|
|
const o = new u.Vector3(s[0].x, 0, s[0].y);
|
|
for (const [I, h] of Object.entries(this.keycodeMoveMapping))
|
|
this.keycode[I] && o.add(h);
|
|
let g = 1;
|
|
this.keydown.CapsLock && (g *= this.capsMultiplier), (this.keycode.ShiftLeft || this.keycode.ShiftRight) && (g *= this.shiftMultiplier), (this.keycode.ControlLeft || this.keycode.ControlRight) && (g *= this.ctrlMultiplier);
|
|
for (const I in this.gamepadMapping)
|
|
if (i[Number.parseInt(I)])
|
|
switch (this.gamepadMapping[I]) {
|
|
case "shift":
|
|
g *= this.shiftMultiplier;
|
|
break;
|
|
case "ctrl":
|
|
g *= this.ctrlMultiplier;
|
|
break;
|
|
}
|
|
o.applyQuaternion(e.quaternion), e.position.add(
|
|
o.multiplyScalar(this.moveSpeed * g * A)
|
|
);
|
|
}
|
|
}
|
|
class qh {
|
|
constructor({
|
|
// The HTML canvas element to attach pointer events to
|
|
canvas: A,
|
|
// Speed of rotation (default DEFAULT_ROTATE_SPEED)
|
|
rotateSpeed: e,
|
|
// Speed of sliding when dragging with right/middle mouse button or two fingers
|
|
// (default DEFAULT_SLIDE_SPEED)
|
|
slideSpeed: s,
|
|
// Speed of movement when using mouse scroll wheel (default DEFAULT_SCROLL_SPEED)
|
|
scrollSpeed: n,
|
|
// Swap the direction of rotation and sliding (default: false)
|
|
swapRotateSlide: i,
|
|
// Reverse the direction of rotation (default: false)
|
|
reverseRotate: r,
|
|
// Reverse the direction of sliding (default: false)
|
|
reverseSlide: a,
|
|
// Reverse the direction of swipe gestures (default: false)
|
|
reverseSwipe: o,
|
|
// Reverse the direction of scroll wheel movement (default: false)
|
|
reverseScroll: g,
|
|
// Inertia factor for movement (default: DEFAULT_MOVE_INERTIA)
|
|
moveInertia: l,
|
|
// Inertia factor for rotation (default: DEFAULT_ROTATE_INERTIA)
|
|
rotateInertia: c,
|
|
// Pointer rolling scale factor (default: DEFAULT_POINTER_ROLL_SCALE)
|
|
pointerRollScale: I,
|
|
// Callback for double press events (default: () => {})
|
|
doublePress: h
|
|
}) {
|
|
this.enable = !0, this.canvas = A, this.rotateSpeed = e ?? Mh, this.slideSpeed = s ?? vh, this.scrollSpeed = n ?? bh, this.swapRotateSlide = i ?? !1, this.reverseRotate = r ?? !1, this.reverseSlide = a ?? !1, this.reverseSwipe = o ?? !1, this.reverseScroll = g ?? !1, this.moveInertia = l ?? Nh, this.rotateInertia = c ?? Fh, this.pointerRollScale = I ?? Uh, this.doublePress = h ?? (() => {
|
|
}), this.doublePressLimitMs = Rh, this.doublePressDistance = Yh, this.lastUp = null, this.rotating = null, this.sliding = null, this.dualPress = !1, this.scroll = new u.Vector3(), this.rotateVelocity = new u.Vector3(), this.moveVelocity = new u.Vector3(), A.addEventListener("pointerdown", (C) => {
|
|
const B = this.getPointerPosition(C), Q = B.clone(), f = B.clone(), p = !this.swapRotateSlide && !this.rotating && (C.pointerType !== "mouse" || C.button === 0) || this.swapRotateSlide && this.sliding && !this.rotating && (C.pointerType !== "mouse" || C.button === 1), { pointerId: d, timeStamp: y } = C;
|
|
if (p)
|
|
this.rotating = { initial: Q, last: f, position: B, pointerId: d, timeStamp: y }, A.setPointerCapture(C.pointerId), this.dualPress = !1;
|
|
else if (!this.sliding) {
|
|
const D = C.pointerType === "mouse" ? C.button : void 0;
|
|
this.sliding = {
|
|
initial: Q,
|
|
last: f,
|
|
position: B,
|
|
pointerId: d,
|
|
button: D,
|
|
timeStamp: y
|
|
}, A.setPointerCapture(C.pointerId), this.dualPress = this.rotating != null && y - this.rotating.timeStamp < Gh;
|
|
}
|
|
});
|
|
const E = (C) => {
|
|
var f, p;
|
|
((f = this.rotating) == null ? void 0 : f.pointerId) === C.pointerId ? (this.rotating = null, A.releasePointerCapture(C.pointerId), this.dualPress && this.sliding && (A.releasePointerCapture(this.sliding.pointerId), this.sliding = null)) : ((p = this.sliding) == null ? void 0 : p.pointerId) === C.pointerId && (this.sliding = null, A.releasePointerCapture(C.pointerId), this.dualPress && this.rotating && (A.releasePointerCapture(this.rotating.pointerId), this.rotating = null));
|
|
const B = this.getPointerPosition(C), Q = this.lastUp;
|
|
if (this.lastUp = { position: B, time: C.timeStamp }, Q && Q.position.distanceTo(B) < this.doublePressDistance) {
|
|
const y = C.timeStamp - Q.time;
|
|
y < this.doublePressLimitMs && (this.lastUp = null, this.doublePress({ position: B, intervalMs: y }));
|
|
}
|
|
};
|
|
document.addEventListener("pointerup", E), document.addEventListener("pointercancel", E), document.addEventListener("pointermove", (C) => {
|
|
var B, Q;
|
|
((B = this.rotating) == null ? void 0 : B.pointerId) === C.pointerId ? this.rotating.position = this.getPointerPosition(C) : ((Q = this.sliding) == null ? void 0 : Q.pointerId) === C.pointerId && (this.sliding.position = this.getPointerPosition(C));
|
|
}), A.addEventListener("contextmenu", (C) => {
|
|
C.preventDefault();
|
|
}), A.addEventListener("wheel", (C) => {
|
|
this.scroll.add(
|
|
new u.Vector3(C.deltaX, C.deltaY, C.deltaZ)
|
|
), C.preventDefault();
|
|
});
|
|
}
|
|
getPointerPosition(A) {
|
|
const e = this.canvas.getBoundingClientRect();
|
|
return new u.Vector2(
|
|
A.clientX - e.left,
|
|
A.clientY - e.top
|
|
);
|
|
}
|
|
update(A, e) {
|
|
if (!this.enable)
|
|
return;
|
|
if (this.dualPress && this.rotating && this.sliding) {
|
|
const n = [
|
|
this.rotating.position.clone().sub(this.rotating.last),
|
|
this.sliding.position.clone().sub(this.sliding.last)
|
|
], i = n[0].dot(n[1]);
|
|
if (i >= 0.2) {
|
|
const r = n[0].clone().add(n[1]), a = new u.Vector3(r.x, -r.y, 0);
|
|
a.multiplyScalar(this.slideSpeed * (this.reverseSwipe ? 1 : -1)), a.applyQuaternion(e.quaternion), e.position.add(a), this.moveVelocity = a.clone().multiplyScalar(1 / A);
|
|
} else if (i <= -0.2) {
|
|
const r = this.sliding.last.clone().sub(this.rotating.last), a = r.length();
|
|
r.multiplyScalar(1 / a).normalize();
|
|
const o = new u.Vector2(-r.y, r.x), g = [n[0].dot(r), n[1].dot(r)], l = [n[0].dot(o), n[1].dot(o)], c = this.rotating.last.clone().add(this.sliding.last).multiplyScalar(0.5);
|
|
let I = new u.Vector3();
|
|
if (e instanceof u.Camera) {
|
|
const f = new u.Vector2(
|
|
c.x / this.canvas.clientWidth * 2 - 1,
|
|
-(c.y / this.canvas.clientHeight) * 2 + 1
|
|
), p = new u.Raycaster();
|
|
p.setFromCamera(f, e), I = p.ray.direction;
|
|
}
|
|
const h = g[1] - g[0], E = I.multiplyScalar(h * this.slideSpeed);
|
|
e.position.add(E), this.moveVelocity = E.clone().multiplyScalar(1 / A);
|
|
const C = [
|
|
Math.atan(l[0] / (-0.5 * a)),
|
|
Math.atan(l[1] / (0.5 * a))
|
|
], B = 0.5 * (C[0] + C[1]) * this.pointerRollScale, Q = new u.Euler().setFromQuaternion(
|
|
e.quaternion,
|
|
"YXZ"
|
|
);
|
|
Q.z = Math.max(
|
|
-Math.PI,
|
|
Math.min(Math.PI, Q.z + 0.5 * B)
|
|
), e.quaternion.setFromEuler(Q);
|
|
}
|
|
this.rotating.last.copy(this.rotating.position), this.sliding.last.copy(this.sliding.position);
|
|
} else {
|
|
const n = new u.Vector3();
|
|
if (this.rotating && !this.dualPress) {
|
|
const r = this.rotating.position.clone().sub(this.rotating.last);
|
|
this.rotating.last.copy(this.rotating.position), n.set(r.x, r.y, 0), n.multiplyScalar(this.rotateSpeed * (this.reverseRotate ? -1 : 1)), this.rotateVelocity = n.clone().multiplyScalar(1 / A);
|
|
} else
|
|
this.rotateVelocity.multiplyScalar(
|
|
Math.exp(-A / this.rotateInertia)
|
|
), n.addScaledVector(this.rotateVelocity, A);
|
|
const i = new u.Euler().setFromQuaternion(
|
|
e.quaternion,
|
|
"YXZ"
|
|
);
|
|
if (i.y -= n.x, i.x = Math.max(
|
|
-Math.PI / 2,
|
|
Math.min(Math.PI / 2, i.x - n.y)
|
|
), i.z *= Math.exp(-0 * A), e.quaternion.setFromEuler(i), this.sliding && !this.dualPress) {
|
|
const r = this.sliding.position.clone().sub(this.sliding.last);
|
|
this.sliding.last.copy(this.sliding.position);
|
|
const a = this.sliding.button !== 2 ? new u.Vector3(r.x, 0, r.y) : new u.Vector3(r.x, -r.y, 0);
|
|
a.multiplyScalar(this.slideSpeed * (this.reverseSlide ? -1 : 1)), a.applyQuaternion(e.quaternion), e.position.add(a), this.moveVelocity = a.clone().multiplyScalar(1 / A);
|
|
} else
|
|
this.moveVelocity.multiplyScalar(
|
|
Math.exp(-A / this.moveInertia)
|
|
), e.position.addScaledVector(this.moveVelocity, A);
|
|
}
|
|
const s = this.scroll.multiplyScalar(this.scrollSpeed);
|
|
s.set(s.x, s.z, s.y), this.reverseScroll && s.multiplyScalar(-1), s.applyQuaternion(e.quaternion), e.position.add(s), this.scroll.set(0, 0, 0);
|
|
}
|
|
}
|
|
export {
|
|
oC as FINGER_TIPS,
|
|
Hh as FpsMovement,
|
|
Ze as HANDS,
|
|
oo as Hand,
|
|
gC as HandMovement,
|
|
ao as JOINT_IDS,
|
|
rC as JOINT_INDEX,
|
|
ne as JOINT_RADIUS,
|
|
mh as JOINT_SEGMENTS,
|
|
xh as JOINT_SEGMENT_STEPS,
|
|
aC as JOINT_TIPS,
|
|
Is as JointEnum,
|
|
GA as LN_SCALE_MAX,
|
|
UA as LN_SCALE_MIN,
|
|
iC as NUM_JOINTS,
|
|
VA as PackedSplats,
|
|
ue as PlyReader,
|
|
qh as PointerControls,
|
|
le as Readback,
|
|
Ke as RgbaArray,
|
|
og as Sint8ToFloat,
|
|
lC as SparkControls,
|
|
Be as SparkRenderer,
|
|
Ce as SparkViewpoint,
|
|
ke as SplatAccumulator,
|
|
Ie as SplatEdit,
|
|
pu as SplatEditRgbaBlendMode,
|
|
du as SplatEditSdf,
|
|
Eu as SplatEditSdfType,
|
|
yu as SplatEdits,
|
|
_t as SplatFileType,
|
|
Vt as SplatGenerator,
|
|
Vu as SplatLoader,
|
|
pt as SplatMesh,
|
|
mu as SplatModifier,
|
|
Oh as SplatSkinning,
|
|
xt as SplatTransformer,
|
|
ch as SpzReader,
|
|
et as SpzWriter,
|
|
ag as Uint8ToFloat,
|
|
Pe as VRButton,
|
|
cC as XrHands,
|
|
Wh as constructAxes,
|
|
jh as constructGrid,
|
|
AC as constructSpherePoints,
|
|
$h as defines,
|
|
Ph as dyno,
|
|
Mg as flipPixels,
|
|
ie as floatToSint8,
|
|
FA as floatToUint8,
|
|
wA as fromHalf,
|
|
sC as generators,
|
|
ja as getSplatFileType,
|
|
eC as imageSplats,
|
|
Sg as isAndroid,
|
|
xg as isMobile,
|
|
Dg as isOculus,
|
|
Zh as isPcSogs,
|
|
nC as modifiers,
|
|
vg as pixelsToPngUrl,
|
|
Ye as setPackedSplat,
|
|
tC as textSplats,
|
|
Ct as toHalf,
|
|
Xh as transcodeSpz,
|
|
Je as unpackSplat,
|
|
Ao as unpackSplats,
|
|
Vh as utils
|
|
};
|
|
//# sourceMappingURL=spark.module.min.js.map
|