ldr 0.34.10 → 0.34.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -1
- package/dist/cli.js +28 -11
- package/dist/index.d.ts +2 -1
- package/dist/index.js +414 -177
- package/dist/load-worker.gen.d.ts +1 -1
- package/dist/node/index.js +439 -185
- package/dist/parts-cdn.d.ts +2 -2
- package/dist/render.d.ts +12 -1
- package/dist/scene.d.ts +24 -5
- package/dist/stud-decal.d.ts +16 -0
- package/package.json +1 -1
package/dist/node/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// ../../../../../../../tmp/ldr-build-
|
|
1
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/spec.ts
|
|
2
2
|
var norm = (s) => s.trim().toLowerCase().replace(/\\/g, "/").replace(/\/+/g, "/");
|
|
3
3
|
var COLOUR_ID_RE = /^[A-Za-z][A-Za-z0-9_]*$/;
|
|
4
4
|
var namedCodes = new Map;
|
|
@@ -833,7 +833,7 @@ function fileStepViews(f) {
|
|
|
833
833
|
viewMemo.set(f, out);
|
|
834
834
|
return out;
|
|
835
835
|
}
|
|
836
|
-
// ../../../../../../../tmp/ldr-build-
|
|
836
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/model.ts
|
|
837
837
|
class ModelLimitError extends Error {
|
|
838
838
|
limit;
|
|
839
839
|
code = "ldr-model-limit";
|
|
@@ -1274,7 +1274,7 @@ function blendedColourHex(code) {
|
|
|
1274
1274
|
const a = LDRAW_EXE_16[code - 256 >> 4], b = LDRAW_EXE_16[code - 256 & 15];
|
|
1275
1275
|
return "#" + [0, 1, 2].map((k) => (a[k] + b[k] >> 1).toString(16).padStart(2, "0")).join("").toUpperCase();
|
|
1276
1276
|
}
|
|
1277
|
-
// ../../../../../../../tmp/ldr-build-
|
|
1277
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/instructions.ts
|
|
1278
1278
|
var MIN_VIS = 0.5;
|
|
1279
1279
|
var REORIENT = 0.35;
|
|
1280
1280
|
var deg = Math.PI / 180;
|
|
@@ -1642,10 +1642,10 @@ function planStepViews(insts, parts, stepOf, nSteps, o = {}) {
|
|
|
1642
1642
|
}
|
|
1643
1643
|
};
|
|
1644
1644
|
}
|
|
1645
|
-
// ../../../../../../../tmp/ldr-build-
|
|
1646
|
-
import * as
|
|
1645
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/render.ts
|
|
1646
|
+
import * as THREE2 from "three";
|
|
1647
1647
|
|
|
1648
|
-
// ../../../../../../../tmp/ldr-build-
|
|
1648
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/pack-io.ts
|
|
1649
1649
|
import { decompress } from "fzstd";
|
|
1650
1650
|
async function decompressPack(data) {
|
|
1651
1651
|
const u = data instanceof Uint8Array ? data : new Uint8Array(data);
|
|
@@ -1668,7 +1668,106 @@ function decodePack(buf) {
|
|
|
1668
1668
|
return { header, arr, bytes: buf.byteLength, buffer: buf };
|
|
1669
1669
|
}
|
|
1670
1670
|
|
|
1671
|
-
// ../../../../../../../tmp/ldr-build-
|
|
1671
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/stud-decal.ts
|
|
1672
|
+
import * as THREE from "three";
|
|
1673
|
+
function studDecalUniforms(near = 0) {
|
|
1674
|
+
return { center: { value: new THREE.Vector3 }, near: { value: near } };
|
|
1675
|
+
}
|
|
1676
|
+
var _quad = new Map;
|
|
1677
|
+
function studDecalGeom(grid = 1) {
|
|
1678
|
+
const hit = _quad.get(grid);
|
|
1679
|
+
if (hit)
|
|
1680
|
+
return hit;
|
|
1681
|
+
const y = -4 / grid, r = 10;
|
|
1682
|
+
const pos = new Float32Array([-r, y, -r, r, y, -r, r, y, r, -r, y, -r, r, y, r, -r, y, r]);
|
|
1683
|
+
const nrm = new Int8Array(18);
|
|
1684
|
+
for (let i = 0;i < 6; i++)
|
|
1685
|
+
nrm[i * 3 + 1] = -127;
|
|
1686
|
+
const col = new Uint8Array(24);
|
|
1687
|
+
for (let i = 0;i < 6; i++) {
|
|
1688
|
+
col[i * 4] = col[i * 4 + 1] = col[i * 4 + 2] = 255;
|
|
1689
|
+
col[i * 4 + 3] = 0;
|
|
1690
|
+
}
|
|
1691
|
+
const g = new THREE.BufferGeometry;
|
|
1692
|
+
g.setAttribute("position", new THREE.BufferAttribute(pos, 3));
|
|
1693
|
+
g.setAttribute("normal", new THREE.BufferAttribute(nrm, 3, true));
|
|
1694
|
+
g.setAttribute("ldrColor", new THREE.BufferAttribute(col, 4, true));
|
|
1695
|
+
g.computeBoundingSphere();
|
|
1696
|
+
g.computeBoundingBox();
|
|
1697
|
+
_quad.set(grid, g);
|
|
1698
|
+
return g;
|
|
1699
|
+
}
|
|
1700
|
+
var cache = new WeakMap;
|
|
1701
|
+
function studDecalMaterial(base, U, grid) {
|
|
1702
|
+
let m = cache.get(base);
|
|
1703
|
+
if (!m)
|
|
1704
|
+
cache.set(base, m = new Map);
|
|
1705
|
+
const hit = m.get(grid);
|
|
1706
|
+
if (hit)
|
|
1707
|
+
return hit;
|
|
1708
|
+
const d = base.clone();
|
|
1709
|
+
const prev = base.onBeforeCompile;
|
|
1710
|
+
const key = base.customProgramCacheKey?.() ?? "";
|
|
1711
|
+
d.polygonOffset = true;
|
|
1712
|
+
d.polygonOffsetFactor = -2;
|
|
1713
|
+
d.polygonOffsetUnits = -4;
|
|
1714
|
+
d.onBeforeCompile = (s, r) => {
|
|
1715
|
+
prev.call(base, s, r);
|
|
1716
|
+
s.uniforms.uStudC = U.center;
|
|
1717
|
+
s.uniforms.uStudNear = U.near;
|
|
1718
|
+
s.vertexShader = s.vertexShader.replace("#include <common>", `#include <common>
|
|
1719
|
+
varying vec2 vSt;
|
|
1720
|
+
varying vec3 vSW;
|
|
1721
|
+
varying vec3 vTx;
|
|
1722
|
+
varying vec3 vTz;`).replace("#include <begin_vertex>", `#include <begin_vertex>
|
|
1723
|
+
vSt = position.xz;
|
|
1724
|
+
mat4 sdM = modelMatrix;
|
|
1725
|
+
#ifdef USE_INSTANCING
|
|
1726
|
+
sdM = modelMatrix * instanceMatrix;
|
|
1727
|
+
#endif
|
|
1728
|
+
vSW = (sdM * vec4(position, 1.0)).xyz;
|
|
1729
|
+
vTx = normalize((viewMatrix * sdM * vec4(1.0, 0.0, 0.0, 0.0)).xyz);
|
|
1730
|
+
vTz = normalize((viewMatrix * sdM * vec4(0.0, 0.0, 1.0, 0.0)).xyz);`);
|
|
1731
|
+
s.fragmentShader = s.fragmentShader.replace("#include <common>", `#include <common>
|
|
1732
|
+
uniform vec3 uStudC;
|
|
1733
|
+
uniform float uStudNear;
|
|
1734
|
+
varying vec2 vSt;
|
|
1735
|
+
varying vec3 vSW;
|
|
1736
|
+
varying vec3 vTx;
|
|
1737
|
+
varying vec3 vTz;`).replace("#include <roughnessmap_fragment>", `#include <roughnessmap_fragment>
|
|
1738
|
+
if (distance(vSW.xz, uStudC.xz) < uStudNear) discard; // the real studs stand here
|
|
1739
|
+
// parallax: march the view ray on from the studs' tops (the quad) down to the plate (they repeat every 20/SG LDU); the first point
|
|
1740
|
+
// inside a stud is its top (the first sample) or its wall (any later one), else the ray reaches the plate between studs
|
|
1741
|
+
const float SG = ${grid.toFixed(1)}, SC = 20.0 / SG, SR = 6.0 / SG, SH = 4.0 / SG; // cell, radius, height (LDU)
|
|
1742
|
+
vec3 sdUp = normalize(vNormal) * (gl_FrontFacing ? 1.0 : -1.0), sdV = normalize(vViewPosition);
|
|
1743
|
+
vec3 sdVt = vec3(dot(sdV, vTx), max(dot(sdV, sdUp), 0.08), dot(sdV, vTz)); // toward the eye, stud space (y: up)
|
|
1744
|
+
vec2 sdStep = sdVt.xz / sdVt.y * (SH / 8.0); if (length(sdStep) > SC * 0.2) sdStep *= SC * 0.2 / length(sdStep);
|
|
1745
|
+
float sdPxA = length(dFdx(vSt)), sdPxB = length(dFdy(vSt)), sdPx = min(sdPxA, sdPxB), sdPxM = max(sdPxA, sdPxB);
|
|
1746
|
+
float sdK = clamp((SC / sdPx - 2.5) / 3.0, 0.0, 1.0); // a stud cell under ~3 px: shading fades to the plate's average (no shimmer)
|
|
1747
|
+
float sdAa = max(sdPxM * 0.7, 0.05);
|
|
1748
|
+
float sdHit = -1.0; vec2 sdC = vec2(0.0);
|
|
1749
|
+
for (int i = 0; i <= 8; i++) { vec2 q = vSt - sdStep * float(i); vec2 c = (fract(q / SC + 0.5) - 0.5) * SC;
|
|
1750
|
+
if (length(c) < SR) { sdHit = float(i); sdC = c; break; } }
|
|
1751
|
+
vec2 sdG = (fract((vSt - sdStep * 8.0) / SC + 0.5) - 0.5) * SC; float sdRg = length(sdG); // the plate point, from its nearest stud
|
|
1752
|
+
float sdTop = sdHit == 0.0 ? 1.0 : 0.0, sdWall = sdHit > 0.0 ? 1.0 : 0.0;
|
|
1753
|
+
float sdRim = sdTop * smoothstep(SR - 0.9 * SH - sdAa, SR, length(sdC)); // the rounded edge of a top
|
|
1754
|
+
vec2 sdD = (sdHit >= 0.0 ? sdC : sdG) / max(length(sdHit >= 0.0 ? sdC : sdG), 1e-4);
|
|
1755
|
+
float sdAo = sdHit >= 0.0 ? 1.0 - 0.22 * sdWall * (sdHit / 8.0) // a wall darkens toward its foot
|
|
1756
|
+
: 1.0 - 0.45 * exp(-(sdRg - SR) / (0.5 * SH)); // the plate darkens next to a stud (contact shadow)
|
|
1757
|
+
float sdEdgeAvg = 0.9; // a cell's average darkening, what the shading fades to
|
|
1758
|
+
diffuseColor.rgb *= mix(sdEdgeAvg, sdAo, sdK);
|
|
1759
|
+
roughnessFactor = clamp(roughnessFactor * mix(1.0, sdTop > 0.5 ? 0.85 : 1.1, sdK), 0.04, 1.0);
|
|
1760
|
+
`).replace("#include <normal_fragment_maps>", `#include <normal_fragment_maps>
|
|
1761
|
+
{ vec3 sdN = sdUp; vec3 sdR = vTx * sdD.x + vTz * sdD.y;
|
|
1762
|
+
if (sdWall > 0.5) sdN = normalize(sdR + sdUp * 0.12); else if (sdRim > 0.0) sdN = normalize(sdUp + sdR * 1.2 * sdRim);
|
|
1763
|
+
normal = normalize(mix(normal, sdN, sdK)); }`);
|
|
1764
|
+
};
|
|
1765
|
+
d.customProgramCacheKey = () => key + `|stud-decal-${grid}`;
|
|
1766
|
+
m.set(grid, d);
|
|
1767
|
+
return d;
|
|
1768
|
+
}
|
|
1769
|
+
|
|
1770
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/cull.ts
|
|
1672
1771
|
var upright = (m, o = 0) => Math.abs(m[o + 7] - 1) < 0.001 && Math.abs(m[o + 4]) < 0.001 && Math.abs(m[o + 10]) < 0.001;
|
|
1673
1772
|
var prepCache = new WeakMap;
|
|
1674
1773
|
var lastH = null;
|
|
@@ -1954,17 +2053,14 @@ function cullPass(insts, H, steps, eCap) {
|
|
|
1954
2053
|
return v;
|
|
1955
2054
|
};
|
|
1956
2055
|
const nI = insts.length;
|
|
1957
|
-
let cap = 0, nR = 0;
|
|
1958
|
-
|
|
1959
|
-
|
|
1960
|
-
|
|
1961
|
-
|
|
1962
|
-
|
|
1963
|
-
|
|
1964
|
-
|
|
1965
|
-
if (p && p.mask) {
|
|
1966
|
-
cap++;
|
|
1967
|
-
lp = part;
|
|
2056
|
+
let cap = 0, nR = 0, nStuds = 0;
|
|
2057
|
+
const pps = new Array(nI);
|
|
2058
|
+
for (let idx = 0;idx < nI; idx++) {
|
|
2059
|
+
const pp = pps[idx] = prepPart(H, insts[idx].part);
|
|
2060
|
+
if (pp) {
|
|
2061
|
+
nStuds += pp.nStuds;
|
|
2062
|
+
if (pp.mask)
|
|
2063
|
+
cap++;
|
|
1968
2064
|
}
|
|
1969
2065
|
}
|
|
1970
2066
|
const rx0 = new Float64Array(cap), rx1 = new Float64Array(cap), rz0 = new Float64Array(cap), rz1 = new Float64Array(cap);
|
|
@@ -1999,7 +2095,7 @@ function cullPass(insts, H, steps, eCap) {
|
|
|
1999
2095
|
z1 = wz;
|
|
2000
2096
|
}
|
|
2001
2097
|
const lv2 = Math.round((m[1] + b[4]) * 2);
|
|
2002
|
-
const pp =
|
|
2098
|
+
const pp = pps[idx];
|
|
2003
2099
|
const cx0 = Math.floor(x0 / CELL), cx1 = Math.floor(x1 / CELL), cz0 = Math.floor(z0 / CELL), cz1 = Math.floor(z1 / CELL);
|
|
2004
2100
|
if (!((cx1 - cx0 + 1) * (cz1 - cz0 + 1) <= 65536) || !inRange(lv2, cx0, cz0) || !inRange(lv2, cx1, cz1))
|
|
2005
2101
|
continue;
|
|
@@ -2120,12 +2216,6 @@ function cullPass(insts, H, steps, eCap) {
|
|
|
2120
2216
|
}
|
|
2121
2217
|
return best;
|
|
2122
2218
|
};
|
|
2123
|
-
let nStuds = 0;
|
|
2124
|
-
for (const it of insts) {
|
|
2125
|
-
const pp = prepPart(H, it.part);
|
|
2126
|
-
if (pp)
|
|
2127
|
-
nStuds += pp.nStuds;
|
|
2128
|
-
}
|
|
2129
2219
|
const studHidden = new Uint8Array(nStuds), studUp = new Uint8Array(nStuds);
|
|
2130
2220
|
let studsHidden = 0;
|
|
2131
2221
|
const tops = steps ? new Int3Table(nStuds, 4) : null;
|
|
@@ -2134,7 +2224,7 @@ function cullPass(insts, H, steps, eCap) {
|
|
|
2134
2224
|
const studHideStep = steps ? new Int32Array(nStuds).fill(STEP_NEVER) : undefined;
|
|
2135
2225
|
for (let idx = 0, j = 0;idx < insts.length; idx++) {
|
|
2136
2226
|
const it = insts[idx];
|
|
2137
|
-
const pp =
|
|
2227
|
+
const pp = pps[idx];
|
|
2138
2228
|
if (!pp)
|
|
2139
2229
|
continue;
|
|
2140
2230
|
const m = it.m, S = pp.studM;
|
|
@@ -2259,7 +2349,7 @@ function precomputeCull(instances, H, useTex = true) {
|
|
|
2259
2349
|
return cullCore(s.all, H, s.nSteps > 1 ? s.stepOf : undefined);
|
|
2260
2350
|
}
|
|
2261
2351
|
|
|
2262
|
-
// ../../../../../../../tmp/ldr-build-
|
|
2352
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/render.ts
|
|
2263
2353
|
async function loadPack(url) {
|
|
2264
2354
|
const res = await fetch(url);
|
|
2265
2355
|
if (!res.ok)
|
|
@@ -2283,14 +2373,14 @@ var toF16 = (a) => {
|
|
|
2283
2373
|
const o = new Uint16Array(a.length);
|
|
2284
2374
|
for (let i = 0;i < a.length; i++) {
|
|
2285
2375
|
const v = a[i];
|
|
2286
|
-
o[i] =
|
|
2376
|
+
o[i] = THREE2.DataUtils.toHalfFloat(v > F16_MAX ? F16_MAX : v < -F16_MAX ? -F16_MAX : v);
|
|
2287
2377
|
}
|
|
2288
2378
|
return o;
|
|
2289
2379
|
};
|
|
2290
2380
|
function keepHalf(bm) {
|
|
2291
2381
|
const p = bm.geometry.getAttribute("position");
|
|
2292
2382
|
if (p && !p.isFloat16BufferAttribute && p.array instanceof Uint16Array)
|
|
2293
|
-
bm.geometry.setAttribute("position", new
|
|
2383
|
+
bm.geometry.setAttribute("position", new THREE2.Float16BufferAttribute(p.array, p.itemSize));
|
|
2294
2384
|
}
|
|
2295
2385
|
function flatNormals(pos, idx) {
|
|
2296
2386
|
const n = new Float32Array(pos.length);
|
|
@@ -2324,17 +2414,17 @@ function geom(b, arr) {
|
|
|
2324
2414
|
let g = c.get(b);
|
|
2325
2415
|
if (g)
|
|
2326
2416
|
return g;
|
|
2327
|
-
g = new
|
|
2417
|
+
g = new THREE2.BufferGeometry;
|
|
2328
2418
|
const pos = arr(b.pos);
|
|
2329
|
-
g.setAttribute("position", new
|
|
2419
|
+
g.setAttribute("position", new THREE2.Float16BufferAttribute(toF16(pos), 3));
|
|
2330
2420
|
const nrm = b.nrm ? arr(b.nrm) : flatNormals(pos, arr(b.idx));
|
|
2331
2421
|
const col = arr(b.col);
|
|
2332
|
-
g.setAttribute("normal", new
|
|
2333
|
-
g.setAttribute("ldrColor", new
|
|
2422
|
+
g.setAttribute("normal", new THREE2.BufferAttribute(toI8(nrm), 3, true));
|
|
2423
|
+
g.setAttribute("ldrColor", new THREE2.BufferAttribute(col instanceof Uint8Array ? col : toU8(col), 4, true));
|
|
2334
2424
|
if (b.idx)
|
|
2335
|
-
g.setIndex(new
|
|
2425
|
+
g.setIndex(new THREE2.BufferAttribute(arr(b.idx), 1));
|
|
2336
2426
|
if (b.uv)
|
|
2337
|
-
g.setAttribute("ldrUV", new
|
|
2427
|
+
g.setAttribute("ldrUV", new THREE2.BufferAttribute(arr(b.uv), 2));
|
|
2338
2428
|
g.computeBoundingSphere();
|
|
2339
2429
|
g.computeBoundingBox();
|
|
2340
2430
|
c.set(b, g);
|
|
@@ -2359,7 +2449,7 @@ function patchParticleFragment(shader, surface) {
|
|
|
2359
2449
|
const frac = Math.max(0.01, Math.min(0.95, surface.particleFraction ?? 0.3));
|
|
2360
2450
|
const size = Math.max(0.02, surface.particleSize ?? 1);
|
|
2361
2451
|
const sparkle = surface.finish === "glitter" ? 1 : 0;
|
|
2362
|
-
shader.uniforms.ldrParticle = { value: new
|
|
2452
|
+
shader.uniforms.ldrParticle = { value: new THREE2.Vector4(pr, pg, pb, frac) };
|
|
2363
2453
|
shader.uniforms.ldrParticleSize = { value: size };
|
|
2364
2454
|
shader.uniforms.ldrSparkle = { value: sparkle };
|
|
2365
2455
|
shader.vertexShader = `varying vec3 ldrGrainP;
|
|
@@ -2392,16 +2482,16 @@ function makeFinishMaterial(side, surface) {
|
|
|
2392
2482
|
transparent: surface.transparent,
|
|
2393
2483
|
opacity: surface.opacity,
|
|
2394
2484
|
depthWrite: surface.depthWrite,
|
|
2395
|
-
...surface.emissive > 0 ? { emissive: new
|
|
2485
|
+
...surface.emissive > 0 ? { emissive: new THREE2.Color(1, 1, 1), emissiveIntensity: surface.emissive } : {}
|
|
2396
2486
|
};
|
|
2397
|
-
const m = needPhysical ? new
|
|
2487
|
+
const m = needPhysical ? new THREE2.MeshPhysicalMaterial({
|
|
2398
2488
|
...common,
|
|
2399
2489
|
clearcoat: surface.clearcoat,
|
|
2400
2490
|
clearcoatRoughness: surface.clearcoatRoughness,
|
|
2401
2491
|
sheen: surface.sheen,
|
|
2402
2492
|
sheenRoughness: surface.sheenRoughness,
|
|
2403
|
-
sheenColor: new
|
|
2404
|
-
}) : new
|
|
2493
|
+
sheenColor: new THREE2.Color(1, 1, 1)
|
|
2494
|
+
}) : new THREE2.MeshStandardMaterial(common);
|
|
2405
2495
|
const particle = !!surface.particleHex;
|
|
2406
2496
|
m.onBeforeCompile = (s) => {
|
|
2407
2497
|
patchLdrColorVertex(s);
|
|
@@ -2468,21 +2558,29 @@ function pngHasAlpha(b) {
|
|
|
2468
2558
|
return false;
|
|
2469
2559
|
}
|
|
2470
2560
|
function packTexture(pack, i, data = false) {
|
|
2471
|
-
const t = new
|
|
2561
|
+
const t = new THREE2.Texture;
|
|
2472
2562
|
t.flipY = false;
|
|
2473
|
-
t.colorSpace = data ?
|
|
2474
|
-
t.wrapS = t.wrapT =
|
|
2563
|
+
t.colorSpace = data ? THREE2.NoColorSpace : THREE2.SRGBColorSpace;
|
|
2564
|
+
t.wrapS = t.wrapT = THREE2.ClampToEdgeWrapping;
|
|
2475
2565
|
const e = pack.header.textures?.[i];
|
|
2476
2566
|
const bytes = e?.data ? pack.arr(e.data) : null;
|
|
2477
2567
|
if (!bytes || typeof createImageBitmap === "undefined")
|
|
2478
2568
|
return { texture: t, ready: Promise.resolve() };
|
|
2569
|
+
const done = decoded.get(e);
|
|
2570
|
+
if (done) {
|
|
2571
|
+
t.image = done;
|
|
2572
|
+
t.needsUpdate = true;
|
|
2573
|
+
return { texture: t, ready: Promise.resolve() };
|
|
2574
|
+
}
|
|
2479
2575
|
const ready = createImageBitmap(new Blob([bytes], { type: e.mime || "image/png" }), { premultiplyAlpha: "none", colorSpaceConversion: "none" }).then((img) => {
|
|
2576
|
+
decoded.set(e, img);
|
|
2480
2577
|
t.image = img;
|
|
2481
2578
|
t.needsUpdate = true;
|
|
2482
2579
|
}).catch(() => {});
|
|
2483
2580
|
return { texture: t, ready };
|
|
2484
2581
|
}
|
|
2485
|
-
var
|
|
2582
|
+
var decoded = new WeakMap;
|
|
2583
|
+
var sharedLineMat = () => new THREE2.ShaderMaterial({
|
|
2486
2584
|
vertexShader: `attribute mat4 instanceMatrix; void main(){ gl_Position = projectionMatrix * modelViewMatrix * instanceMatrix * vec4(position,1.0); }`,
|
|
2487
2585
|
fragmentShader: `void main(){ gl_FragColor = vec4(0.13,0.13,0.13,1.0); }`
|
|
2488
2586
|
});
|
|
@@ -2556,8 +2654,8 @@ function conditionalLines(pack, entry, which = "all") {
|
|
|
2556
2654
|
}
|
|
2557
2655
|
return out;
|
|
2558
2656
|
}
|
|
2559
|
-
var condLineMat = () => new
|
|
2560
|
-
uniforms: { ldrViewProj: { value: new
|
|
2657
|
+
var condLineMat = () => new THREE2.ShaderMaterial({
|
|
2658
|
+
uniforms: { ldrViewProj: { value: new THREE2.Matrix4 } },
|
|
2561
2659
|
vertexShader: `uniform mat4 ldrViewProj; attribute mat4 instanceMatrix; attribute vec3 ldrP1; attribute vec3 ldrC0; attribute vec3 ldrC1; attribute float ldrSide;
|
|
2562
2660
|
void main(){
|
|
2563
2661
|
mat4 mvp = ldrViewProj * instanceMatrix;
|
|
@@ -2595,18 +2693,18 @@ function condBuffers(cond) {
|
|
|
2595
2693
|
}
|
|
2596
2694
|
side[l * 2 + 1] = 1;
|
|
2597
2695
|
}
|
|
2598
|
-
return { ib: new
|
|
2696
|
+
return { ib: new THREE2.InterleavedBuffer(buf, 12), side: new THREE2.BufferAttribute(side, 1) };
|
|
2599
2697
|
}
|
|
2600
2698
|
function condEdges({ ib, side }, im, material) {
|
|
2601
|
-
const g = new
|
|
2602
|
-
g.setAttribute("position", new
|
|
2603
|
-
g.setAttribute("ldrP1", new
|
|
2604
|
-
g.setAttribute("ldrC0", new
|
|
2605
|
-
g.setAttribute("ldrC1", new
|
|
2699
|
+
const g = new THREE2.InstancedBufferGeometry;
|
|
2700
|
+
g.setAttribute("position", new THREE2.InterleavedBufferAttribute(ib, 3, 0));
|
|
2701
|
+
g.setAttribute("ldrP1", new THREE2.InterleavedBufferAttribute(ib, 3, 3));
|
|
2702
|
+
g.setAttribute("ldrC0", new THREE2.InterleavedBufferAttribute(ib, 3, 6));
|
|
2703
|
+
g.setAttribute("ldrC1", new THREE2.InterleavedBufferAttribute(ib, 3, 9));
|
|
2606
2704
|
g.setAttribute("ldrSide", side);
|
|
2607
2705
|
g.setAttribute("instanceMatrix", im.instanceMatrix);
|
|
2608
2706
|
g.instanceCount = im.count;
|
|
2609
|
-
const l = new
|
|
2707
|
+
const l = new THREE2.LineSegments(g, material);
|
|
2610
2708
|
l.frustumCulled = false;
|
|
2611
2709
|
l.name = "ldrCondLines";
|
|
2612
2710
|
l.onBeforeRender = (_r, _s, cam, _g, mat) => {
|
|
@@ -2621,12 +2719,12 @@ function condEdges({ ib, side }, im, material) {
|
|
|
2621
2719
|
}
|
|
2622
2720
|
function sharedLines(pos, im, material = sharedLineMat()) {
|
|
2623
2721
|
const { P, I } = weldLines(pos);
|
|
2624
|
-
const g = new
|
|
2625
|
-
g.setAttribute("position", new
|
|
2626
|
-
g.setIndex(new
|
|
2722
|
+
const g = new THREE2.InstancedBufferGeometry;
|
|
2723
|
+
g.setAttribute("position", new THREE2.BufferAttribute(P, 3));
|
|
2724
|
+
g.setIndex(new THREE2.BufferAttribute(I, 1));
|
|
2627
2725
|
g.setAttribute("instanceMatrix", im.instanceMatrix);
|
|
2628
2726
|
g.instanceCount = im.count;
|
|
2629
|
-
const l = new
|
|
2727
|
+
const l = new THREE2.LineSegments(g, material);
|
|
2630
2728
|
l.frustumCulled = false;
|
|
2631
2729
|
return l;
|
|
2632
2730
|
}
|
|
@@ -2649,8 +2747,8 @@ function writeM4(t, o, m, mo = 0) {
|
|
|
2649
2747
|
t[o + 15] = 1;
|
|
2650
2748
|
}
|
|
2651
2749
|
function newIM(g, mat, n) {
|
|
2652
|
-
const im = new
|
|
2653
|
-
im.instanceMatrix = new
|
|
2750
|
+
const im = new THREE2.InstancedMesh(g, mat, 0);
|
|
2751
|
+
im.instanceMatrix = new THREE2.InstancedBufferAttribute(new Float32Array(n * 16), 16);
|
|
2654
2752
|
im.count = n;
|
|
2655
2753
|
return im;
|
|
2656
2754
|
}
|
|
@@ -2713,7 +2811,7 @@ function sphereUnion(S, A, n) {
|
|
|
2713
2811
|
S[3] = r;
|
|
2714
2812
|
}
|
|
2715
2813
|
function setSphere(im, S) {
|
|
2716
|
-
const sph = im.boundingSphere ?? new
|
|
2814
|
+
const sph = im.boundingSphere ?? new THREE2.Sphere;
|
|
2717
2815
|
sph.center.set(S[0], S[1], S[2]);
|
|
2718
2816
|
sph.radius = S[3];
|
|
2719
2817
|
if (S[3] < 0)
|
|
@@ -2783,7 +2881,7 @@ function fillInstances(im, ids, insts, color) {
|
|
|
2783
2881
|
writeM4(M, k * 16, it.m);
|
|
2784
2882
|
color(it.color).toArray(C, k * 3);
|
|
2785
2883
|
}
|
|
2786
|
-
im.instanceColor = new
|
|
2884
|
+
im.instanceColor = new THREE2.InstancedBufferAttribute(C, 3);
|
|
2787
2885
|
}
|
|
2788
2886
|
function computeCulling(insts, H) {
|
|
2789
2887
|
const c = cullCore(insts, H);
|
|
@@ -2915,10 +3013,10 @@ function studDiscGeom() {
|
|
|
2915
3013
|
col[i * 4 + 2] = 255;
|
|
2916
3014
|
col[i * 4 + 3] = 0;
|
|
2917
3015
|
}
|
|
2918
|
-
const g = new
|
|
2919
|
-
g.setAttribute("position", new
|
|
2920
|
-
g.setAttribute("normal", new
|
|
2921
|
-
g.setAttribute("ldrColor", new
|
|
3016
|
+
const g = new THREE2.BufferGeometry;
|
|
3017
|
+
g.setAttribute("position", new THREE2.Float16BufferAttribute(toF16(pos), 3));
|
|
3018
|
+
g.setAttribute("normal", new THREE2.BufferAttribute(toI8(nrm), 3, true));
|
|
3019
|
+
g.setAttribute("ldrColor", new THREE2.BufferAttribute(col, 4, true));
|
|
2922
3020
|
g.computeBoundingSphere();
|
|
2923
3021
|
g.computeBoundingBox();
|
|
2924
3022
|
return _studDisc = g;
|
|
@@ -2965,11 +3063,11 @@ function studBoxGeom(w) {
|
|
|
2965
3063
|
col[i * 4 + 2] = 255;
|
|
2966
3064
|
col[i * 4 + 3] = 0;
|
|
2967
3065
|
}
|
|
2968
|
-
g = new
|
|
2969
|
-
g.setAttribute("position", new
|
|
2970
|
-
g.setAttribute("normal", new
|
|
2971
|
-
g.setAttribute("ldrColor", new
|
|
2972
|
-
g.setIndex(new
|
|
3066
|
+
g = new THREE2.BufferGeometry;
|
|
3067
|
+
g.setAttribute("position", new THREE2.Float16BufferAttribute(toF16(new Float32Array(pos)), 3));
|
|
3068
|
+
g.setAttribute("normal", new THREE2.BufferAttribute(toI8(new Float32Array(nrm)), 3, true));
|
|
3069
|
+
g.setAttribute("ldrColor", new THREE2.BufferAttribute(col, 4, true));
|
|
3070
|
+
g.setIndex(new THREE2.BufferAttribute(new Uint16Array(idx), 1));
|
|
2973
3071
|
g.computeBoundingSphere();
|
|
2974
3072
|
g.computeBoundingBox();
|
|
2975
3073
|
_studBox.set(w, g);
|
|
@@ -3036,11 +3134,11 @@ function studTubeGeom(w, wi) {
|
|
|
3036
3134
|
col[i * 4 + 2] = 255;
|
|
3037
3135
|
col[i * 4 + 3] = 0;
|
|
3038
3136
|
}
|
|
3039
|
-
g = new
|
|
3040
|
-
g.setAttribute("position", new
|
|
3041
|
-
g.setAttribute("normal", new
|
|
3042
|
-
g.setAttribute("ldrColor", new
|
|
3043
|
-
g.setIndex(new
|
|
3137
|
+
g = new THREE2.BufferGeometry;
|
|
3138
|
+
g.setAttribute("position", new THREE2.Float16BufferAttribute(toF16(new Float32Array(pos)), 3));
|
|
3139
|
+
g.setAttribute("normal", new THREE2.BufferAttribute(toI8(new Float32Array(nrm)), 3, true));
|
|
3140
|
+
g.setAttribute("ldrColor", new THREE2.BufferAttribute(col, 4, true));
|
|
3141
|
+
g.setIndex(new THREE2.BufferAttribute(new Uint16Array(idx), 1));
|
|
3044
3142
|
g.computeBoundingSphere();
|
|
3045
3143
|
g.computeBoundingBox();
|
|
3046
3144
|
_studTube.set(key, g);
|
|
@@ -3186,7 +3284,7 @@ function studTopClosed(b, arr) {
|
|
|
3186
3284
|
}
|
|
3187
3285
|
var EDGE_CAP_MIN = 4;
|
|
3188
3286
|
|
|
3189
|
-
class LdrLodRoot extends
|
|
3287
|
+
class LdrLodRoot extends THREE2.LOD {
|
|
3190
3288
|
clusters = [];
|
|
3191
3289
|
vpH = 1080;
|
|
3192
3290
|
px = 0.5;
|
|
@@ -3195,8 +3293,8 @@ class LdrLodRoot extends THREE.LOD {
|
|
|
3195
3293
|
edgeCap = 0;
|
|
3196
3294
|
enabled = true;
|
|
3197
3295
|
apply = () => {};
|
|
3198
|
-
inv = new
|
|
3199
|
-
cp = new
|
|
3296
|
+
inv = new THREE2.Matrix4;
|
|
3297
|
+
cp = new THREE2.Vector3;
|
|
3200
3298
|
lastW = new Float32Array(16).fill(NaN);
|
|
3201
3299
|
constructor() {
|
|
3202
3300
|
super();
|
|
@@ -3328,7 +3426,51 @@ function fillBucketIds(bIds, fill, studBucket, j0, j1) {
|
|
|
3328
3426
|
bIds[b][fill[b]++] = j;
|
|
3329
3427
|
}
|
|
3330
3428
|
}
|
|
3331
|
-
|
|
3429
|
+
var _studGrid = new WeakMap;
|
|
3430
|
+
function studGridGeom(g, n) {
|
|
3431
|
+
if (n <= 1)
|
|
3432
|
+
return g;
|
|
3433
|
+
let m = _studGrid.get(g);
|
|
3434
|
+
if (!m)
|
|
3435
|
+
_studGrid.set(g, m = new Map);
|
|
3436
|
+
const hit = m.get(n);
|
|
3437
|
+
if (hit)
|
|
3438
|
+
return hit;
|
|
3439
|
+
const src = g;
|
|
3440
|
+
const P = src.getAttribute("position"), nv = P.count, k = n * n, pos = new Float32Array(nv * 3 * k), out = new THREE2.BufferGeometry;
|
|
3441
|
+
for (let a = 0, c = 0;a < n; a++)
|
|
3442
|
+
for (let b = 0;b < n; b++, c++) {
|
|
3443
|
+
const ox = ((a + 0.5) / n - 0.5) * 20, oz = ((b + 0.5) / n - 0.5) * 20, o = c * nv * 3;
|
|
3444
|
+
for (let v = 0;v < nv; v++) {
|
|
3445
|
+
pos[o + v * 3] = P.getX(v) / n + ox;
|
|
3446
|
+
pos[o + v * 3 + 1] = P.getY(v) / n;
|
|
3447
|
+
pos[o + v * 3 + 2] = P.getZ(v) / n + oz;
|
|
3448
|
+
}
|
|
3449
|
+
}
|
|
3450
|
+
out.setAttribute("position", g.getAttribute("position") instanceof THREE2.Float16BufferAttribute ? new THREE2.Float16BufferAttribute(toF16(pos), 3) : new THREE2.BufferAttribute(pos, 3));
|
|
3451
|
+
for (const name of Object.keys(src.attributes)) {
|
|
3452
|
+
if (name === "position")
|
|
3453
|
+
continue;
|
|
3454
|
+
const A = src.getAttribute(name);
|
|
3455
|
+
const sa = A.array, dst = new sa.constructor(sa.length * k);
|
|
3456
|
+
for (let c = 0;c < k; c++)
|
|
3457
|
+
dst.set(sa, c * sa.length);
|
|
3458
|
+
out.setAttribute(name, new A.constructor(dst, A.itemSize, A.normalized));
|
|
3459
|
+
}
|
|
3460
|
+
const I = src.getIndex();
|
|
3461
|
+
if (I) {
|
|
3462
|
+
const ia = I.array, ni = ia.length, big = nv * k > 65535, dst = big ? new Uint32Array(ni * k) : new Uint16Array(ni * k);
|
|
3463
|
+
for (let c = 0;c < k; c++)
|
|
3464
|
+
for (let i = 0;i < ni; i++)
|
|
3465
|
+
dst[c * ni + i] = ia[i] + c * nv;
|
|
3466
|
+
out.setIndex(new THREE2.BufferAttribute(dst, 1));
|
|
3467
|
+
}
|
|
3468
|
+
out.computeBoundingSphere();
|
|
3469
|
+
out.computeBoundingBox();
|
|
3470
|
+
m.set(n, out);
|
|
3471
|
+
return out;
|
|
3472
|
+
}
|
|
3473
|
+
function* buildStudMeshesGen(insts, H, cull, arr, LOD, color, matOf, steps, colorIndex, trim = false, grid = 1) {
|
|
3332
3474
|
const bKind = [], bMat = [];
|
|
3333
3475
|
const bAll = [];
|
|
3334
3476
|
const studBucket = new Uint16Array(cull.nStuds);
|
|
@@ -3446,7 +3588,7 @@ function* buildStudMeshesGen(insts, H, cull, arr, LOD, color, matOf, steps, colo
|
|
|
3446
3588
|
}
|
|
3447
3589
|
const n = trim ? v : c.length;
|
|
3448
3590
|
const im = newIM(g, bMat[b], n);
|
|
3449
|
-
im.instanceColor = new
|
|
3591
|
+
im.instanceColor = new THREE2.InstancedBufferAttribute(new Float32Array(n * 3), 3);
|
|
3450
3592
|
sMesh.push({ im, kind, vis: v, all: c.length, ...steps ? { slots: { own: new Int32Array(n), hide: new Int32Array(n), inst: new Int32Array(n), stud: new Int16Array(n), col: new Uint16Array(n) } } : {} });
|
|
3451
3593
|
}
|
|
3452
3594
|
};
|
|
@@ -3454,10 +3596,10 @@ function* buildStudMeshesGen(insts, H, cull, arr, LOD, color, matOf, steps, colo
|
|
|
3454
3596
|
if (b)
|
|
3455
3597
|
yield;
|
|
3456
3598
|
const kind = bKind[b];
|
|
3457
|
-
const
|
|
3599
|
+
const g0 = geom(H.studKinds[kind].body, arr), g = g0 && studGridGeom(g0, grid);
|
|
3458
3600
|
const ids = bIds[b];
|
|
3459
3601
|
const studTris = g ? (g.getIndex() ? g.getIndex().count : g.getAttribute("position").count) / 3 : 24;
|
|
3460
|
-
const kStud = LOD ? Math.max(256, Math.min(4096, Math.round(65536 / Math.max(1, studTris)))) : Infinity;
|
|
3602
|
+
const kStud = LOD ? Math.max(256, Math.min(4096, Math.round(65536 * grid / Math.max(1, studTris)))) : Infinity;
|
|
3461
3603
|
const clusters = yield* gridClustersGen(ids.length, (i) => sx[ids[i]], (i) => sz[ids[i]], kStud);
|
|
3462
3604
|
for (let c0 = 0;c0 < clusters.length; c0 += 4) {
|
|
3463
3605
|
if (c0)
|
|
@@ -3605,6 +3747,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3605
3747
|
const { header: H, arr } = pack;
|
|
3606
3748
|
const LOD = P.lod !== false;
|
|
3607
3749
|
const EDGES = !!P.edges;
|
|
3750
|
+
const G = Math.max(1, Math.round(P.studGrid ?? 1));
|
|
3608
3751
|
const root = new LdrLodRoot;
|
|
3609
3752
|
root.enabled = LOD;
|
|
3610
3753
|
root.px = P.lodPx ?? 0.5;
|
|
@@ -3625,8 +3768,8 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3625
3768
|
base.apply(this, a);
|
|
3626
3769
|
};
|
|
3627
3770
|
};
|
|
3628
|
-
const matF = makeMaterial(P.side === "front" ?
|
|
3629
|
-
const matD = makeMaterial(
|
|
3771
|
+
const matF = makeMaterial(P.side === "front" ? THREE2.FrontSide : THREE2.DoubleSide), matB = makeMaterial(P.side === "front" ? THREE2.BackSide : THREE2.DoubleSide);
|
|
3772
|
+
const matD = makeMaterial(THREE2.DoubleSide);
|
|
3630
3773
|
let nUncert = 0;
|
|
3631
3774
|
matF.userData.ldrSideRole = "F";
|
|
3632
3775
|
matB.userData.ldrSideRole = "B";
|
|
@@ -3659,7 +3802,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3659
3802
|
const key = fk + "|" + role;
|
|
3660
3803
|
let m = matCache.get(key);
|
|
3661
3804
|
if (!m) {
|
|
3662
|
-
const side = uncert ?
|
|
3805
|
+
const side = uncert ? THREE2.DoubleSide : P.side === "front" ? mirror ? THREE2.BackSide : THREE2.FrontSide : THREE2.DoubleSide;
|
|
3663
3806
|
if (fk === "default:op" && lc.luminance === 0) {
|
|
3664
3807
|
m = role === "D" ? matD : role === "B" ? matB : matF;
|
|
3665
3808
|
} else {
|
|
@@ -3773,7 +3916,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3773
3916
|
let w = lineCache.get(ref);
|
|
3774
3917
|
if (!w) {
|
|
3775
3918
|
const r = weldLines(src ? src.pos : arr(ref), LOD && !src?.lens);
|
|
3776
|
-
lineCache.set(ref, w = { P: new
|
|
3919
|
+
lineCache.set(ref, w = { P: new THREE2.BufferAttribute(r.P, 3), I: new THREE2.BufferAttribute(r.I, 1), lens: src?.lens ?? r.lens, order: r.order });
|
|
3777
3920
|
}
|
|
3778
3921
|
return lineObj(w, im, cl);
|
|
3779
3922
|
};
|
|
@@ -3793,17 +3936,17 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3793
3936
|
I[n * 2 + 1] = FI[k * 2 + 1];
|
|
3794
3937
|
lens[n++] = full.lens[k];
|
|
3795
3938
|
}
|
|
3796
|
-
lineCache.set(ref, w = { P: full.P, I: new
|
|
3939
|
+
lineCache.set(ref, w = { P: full.P, I: new THREE2.BufferAttribute(I.subarray(0, n * 2), 1), lens: lens.subarray(0, n) });
|
|
3797
3940
|
}
|
|
3798
3941
|
return lineObj(w, im, cl);
|
|
3799
3942
|
};
|
|
3800
3943
|
const lineObj = (w, im, cl) => {
|
|
3801
|
-
const g = new
|
|
3944
|
+
const g = new THREE2.InstancedBufferGeometry;
|
|
3802
3945
|
g.setAttribute("position", w.P);
|
|
3803
3946
|
g.setIndex(w.I);
|
|
3804
3947
|
g.setAttribute("instanceMatrix", im.instanceMatrix);
|
|
3805
3948
|
g.instanceCount = im.count;
|
|
3806
|
-
const l = new
|
|
3949
|
+
const l = new THREE2.LineSegments(g, lmat());
|
|
3807
3950
|
l.frustumCulled = false;
|
|
3808
3951
|
if (LOD)
|
|
3809
3952
|
l.userData.ldrLens = w.lens;
|
|
@@ -3854,7 +3997,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3854
3997
|
return gm ?? undefined;
|
|
3855
3998
|
};
|
|
3856
3999
|
const texMat = (t, base, wrapU, g) => {
|
|
3857
|
-
const role = base.userData?.ldrSideRole ?? (base.side ===
|
|
4000
|
+
const role = base.userData?.ldrSideRole ?? (base.side === THREE2.BackSide ? "B" : base.side === THREE2.DoubleSide ? "D" : "F");
|
|
3858
4001
|
const fin = base.userData?.ldrFinish ?? "default";
|
|
3859
4002
|
const gloss = glossOf(g);
|
|
3860
4003
|
const k = t + ":" + role + ":" + fin + ":" + (wrapU ? 1 : 0) + (gloss ? ":g" + g : "");
|
|
@@ -3880,7 +4023,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
3880
4023
|
return c;
|
|
3881
4024
|
};
|
|
3882
4025
|
const lodLevels = (b, base, mat) => !LOD || !b?.lod ? [] : b.lod.map((l) => {
|
|
3883
|
-
const im = new
|
|
4026
|
+
const im = new THREE2.InstancedMesh(geom(l, arr), mat, 0);
|
|
3884
4027
|
im.userData = { ...base.userData };
|
|
3885
4028
|
im.instanceMatrix = base.instanceMatrix;
|
|
3886
4029
|
im.count = base.count;
|
|
@@ -4072,8 +4215,8 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4072
4215
|
}
|
|
4073
4216
|
}
|
|
4074
4217
|
yield root;
|
|
4075
|
-
const tmpM = new
|
|
4076
|
-
const tmpC = new
|
|
4218
|
+
const tmpM = new THREE2.Matrix4;
|
|
4219
|
+
const tmpC = new THREE2.Color;
|
|
4077
4220
|
for (const [mat, items] of coldByMat) {
|
|
4078
4221
|
yield root;
|
|
4079
4222
|
const entries = [];
|
|
@@ -4113,7 +4256,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4113
4256
|
yield root;
|
|
4114
4257
|
}
|
|
4115
4258
|
}
|
|
4116
|
-
const bm = new
|
|
4259
|
+
const bm = new THREE2.BatchedMesh(members.length, Math.max(1, maxV), Math.max(1, maxI), mat);
|
|
4117
4260
|
bm.perObjectFrustumCulled = true;
|
|
4118
4261
|
bm.sortObjects = false;
|
|
4119
4262
|
bm.frustumCulled = true;
|
|
@@ -4157,7 +4300,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4157
4300
|
members.length = 0;
|
|
4158
4301
|
members.push(...live);
|
|
4159
4302
|
bm.computeBoundingSphere();
|
|
4160
|
-
const cl = newCluster(bm.boundingSphere ?? new
|
|
4303
|
+
const cl = newCluster(bm.boundingSphere ?? new THREE2.Sphere, bm);
|
|
4161
4304
|
const bodyErrs = live.map(({ p }) => [0, ...(p.body?.lod ?? []).map((l) => l.err)]);
|
|
4162
4305
|
bm.userData.ldrMergeGids = instGids;
|
|
4163
4306
|
cl.mergedLod = { bm, gids: instGids, errs: bodyErrs };
|
|
@@ -4178,7 +4321,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4178
4321
|
continue;
|
|
4179
4322
|
if (!pp.edges && !(wantCond && (pp.condl || pp.condlu)))
|
|
4180
4323
|
continue;
|
|
4181
|
-
const ghost = newIM(geom(pp.body, arr) || new
|
|
4324
|
+
const ghost = newIM(geom(pp.body, arr) || new THREE2.BufferGeometry, mat, ids.length);
|
|
4182
4325
|
fillInstances(ghost, ids, insts, color);
|
|
4183
4326
|
const nL = cl.lines.length, nC = cl.cond.length;
|
|
4184
4327
|
if (pp.edges)
|
|
@@ -4228,7 +4371,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4228
4371
|
yield root;
|
|
4229
4372
|
}
|
|
4230
4373
|
}
|
|
4231
|
-
const ubm = new
|
|
4374
|
+
const ubm = new THREE2.BatchedMesh(umembers.length, Math.max(1, uV), Math.max(1, uI), mat);
|
|
4232
4375
|
ubm.perObjectFrustumCulled = true;
|
|
4233
4376
|
ubm.sortObjects = false;
|
|
4234
4377
|
ubm.frustumCulled = true;
|
|
@@ -4278,7 +4421,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4278
4421
|
umembers.length = 0;
|
|
4279
4422
|
umembers.push(...uLive);
|
|
4280
4423
|
ubm.computeBoundingSphere();
|
|
4281
|
-
const ucl = newCluster(ubm.boundingSphere ?? new
|
|
4424
|
+
const ucl = newCluster(ubm.boundingSphere ?? new THREE2.Sphere, ubm);
|
|
4282
4425
|
const uErrs = uLive.map(({ p }) => [0, ...(p.under?.lod ?? []).map((l) => l.err)]);
|
|
4283
4426
|
ubm.userData._stepMode = !!steps;
|
|
4284
4427
|
ubm.userData.ldrMergeGids = uInstGids;
|
|
@@ -4300,7 +4443,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4300
4443
|
continue;
|
|
4301
4444
|
const ord = [...ids.filter((id) => !cull.underHidden[id]), ...ids.filter((id) => cull.underHidden[id])];
|
|
4302
4445
|
const vis = ids.length - ids.reduce((a, id) => a + cull.underHidden[id], 0);
|
|
4303
|
-
const ghost = newIM(geom(pp.under, arr) || new
|
|
4446
|
+
const ghost = newIM(geom(pp.under, arr) || new THREE2.BufferGeometry, mat, ord.length);
|
|
4304
4447
|
fillInstances(ghost, ord, insts, color);
|
|
4305
4448
|
const nC = ucl.cond.length;
|
|
4306
4449
|
addCond(pp, ghost, ucl, "under");
|
|
@@ -4352,7 +4495,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4352
4495
|
}
|
|
4353
4496
|
}
|
|
4354
4497
|
yield root;
|
|
4355
|
-
const _studGen = buildStudMeshesGen(insts, H, cull, arr, LOD, color, (c, mirror) => materialFor(c, mirror, false), steps, steps && colorIndex, !steps && !!P.cullStuds);
|
|
4498
|
+
const _studGen = buildStudMeshesGen(insts, H, cull, arr, LOD, color, (c, mirror) => materialFor(c, mirror, false), steps, steps && colorIndex, !steps && !!P.cullStuds, G);
|
|
4356
4499
|
let _studR = _studGen.next();
|
|
4357
4500
|
while (!_studR.done) {
|
|
4358
4501
|
yield root;
|
|
@@ -4361,10 +4504,10 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4361
4504
|
const sMesh = _studR.value;
|
|
4362
4505
|
const sKind = sMesh.map((x) => x?.kind ?? "");
|
|
4363
4506
|
const sVis = sMesh.map((x) => x?.vis ?? 0);
|
|
4364
|
-
const STUD_ERR = 12;
|
|
4365
|
-
const STUD_BOX_ERR = 2.49;
|
|
4507
|
+
const STUD_ERR = 12 / G;
|
|
4508
|
+
const STUD_BOX_ERR = 2.49 / G;
|
|
4366
4509
|
const STUD_BOX_W_LOW = 5.317;
|
|
4367
|
-
const STUD_DISC_ERR = 8;
|
|
4510
|
+
const STUD_DISC_ERR = 8 / G;
|
|
4368
4511
|
let _coopS = 0;
|
|
4369
4512
|
const sqLineKey = new Map;
|
|
4370
4513
|
for (let ci = 0;ci < sMesh.length; ci++) {
|
|
@@ -4395,7 +4538,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4395
4538
|
const h = studTopClosed(k.body, arr) ? null : studHole(k.body, arr);
|
|
4396
4539
|
const hole = h ? { r: h.r, w: h.r * Math.sqrt(Math.PI) / 2 } : undefined;
|
|
4397
4540
|
if (LOD && (hole || studTopClosed(k.body, arr)) && (im.geometry.getIndex()?.count ?? im.geometry.getAttribute("position").count) > 30) {
|
|
4398
|
-
const box = new
|
|
4541
|
+
const box = new THREE2.InstancedMesh(studGridGeom(hole ? studTubeGeom(sqW, hole.w) : studBoxGeom(sqW), G), im.material, 0);
|
|
4399
4542
|
box.userData = { ldrStud: true, ldrLod: true };
|
|
4400
4543
|
box.instanceMatrix = im.instanceMatrix;
|
|
4401
4544
|
box.count = im.count;
|
|
@@ -4405,11 +4548,11 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4405
4548
|
box.onBeforeRender = trackVp;
|
|
4406
4549
|
root.add(box);
|
|
4407
4550
|
discObjs.push(box);
|
|
4408
|
-
cl.lv.push({ objs: [box], err: h ? Math.max(STUD_BOX_ERR, 6 * Math.SQRT2 - h.out) : STUD_BOX_ERR });
|
|
4551
|
+
cl.lv.push({ objs: [box], err: h ? Math.max(STUD_BOX_ERR, (6 * Math.SQRT2 - h.out) / G) : STUD_BOX_ERR });
|
|
4409
4552
|
cl.studLineLv = 1;
|
|
4410
4553
|
}
|
|
4411
4554
|
if (LOD) {
|
|
4412
|
-
const disc = new
|
|
4555
|
+
const disc = new THREE2.InstancedMesh(studGridGeom(studDiscGeom(), G), im.material, 0);
|
|
4413
4556
|
disc.userData = { ldrStud: true, ldrLod: true };
|
|
4414
4557
|
disc.instanceMatrix = im.instanceMatrix;
|
|
4415
4558
|
disc.count = im.count;
|
|
@@ -4422,7 +4565,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4422
4565
|
cl.lv.push({ objs: [disc], err: STUD_DISC_ERR });
|
|
4423
4566
|
cl.lv.push({ objs: [], err: STUD_ERR });
|
|
4424
4567
|
}
|
|
4425
|
-
if (EDGES && k.edges) {
|
|
4568
|
+
if (EDGES && k.edges && G === 1) {
|
|
4426
4569
|
const round = addLines(k.edges, im, cl);
|
|
4427
4570
|
let sq = cl.studLineLv === 1 && round ? sqLineKey.get(kind) : null;
|
|
4428
4571
|
if (sq === undefined) {
|
|
@@ -4448,6 +4591,18 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4448
4591
|
toggles.push({ mesh: countTo(() => objs), all: trim ? vis : all, visible: vis, flag: "studs" });
|
|
4449
4592
|
if (sm.slots)
|
|
4450
4593
|
stepBatches.push({ im, objs, flag: "studs", ...sm.slots });
|
|
4594
|
+
if (sm.slots && P.studDecal && im.material.opacity === 1 && !im.material.transparent) {
|
|
4595
|
+
const n = im.instanceMatrix.count, decal = new THREE2.InstancedMesh(studDecalGeom(G), studDecalMaterial(im.material, P.studDecal, G), n);
|
|
4596
|
+
decal.instanceMatrix = new THREE2.InstancedBufferAttribute(im.instanceMatrix.array.slice(), 16);
|
|
4597
|
+
decal.instanceColor = new THREE2.InstancedBufferAttribute(im.instanceColor.array.slice(), 3);
|
|
4598
|
+
decal.count = im.count;
|
|
4599
|
+
decal.boundingSphere = im.boundingSphere;
|
|
4600
|
+
decal.visible = false;
|
|
4601
|
+
decal.userData = { ldrStudDecal: true };
|
|
4602
|
+
root.add(decal);
|
|
4603
|
+
stepBatches[stepBatches.length - 1].decal = decal;
|
|
4604
|
+
stats.studDecals = (stats.studDecals ?? 0) + 1;
|
|
4605
|
+
}
|
|
4451
4606
|
}
|
|
4452
4607
|
yield root;
|
|
4453
4608
|
stats.uncertParts = Object.values(H.parts).filter((x) => x.uncert).length;
|
|
@@ -4489,12 +4644,17 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4489
4644
|
const texturesReady = Promise.all(pending).then(() => {});
|
|
4490
4645
|
let stepS = STEP_NEVER - 1, cullS = !!P.cullStuds, cullU = !!P.cullUnder;
|
|
4491
4646
|
let only = null;
|
|
4492
|
-
|
|
4647
|
+
let studMask = null;
|
|
4648
|
+
const applySteps = (studsOnly = false) => {
|
|
4493
4649
|
const st = { studsTotal: 0, studsHidden: 0, undersTotal: 0, undersHidden: 0 };
|
|
4494
|
-
const S = stepS, O = only;
|
|
4650
|
+
const S = stepS, O = only, SM = studMask, SA = SM && !("r" in SM) ? SM : null, SCi = SM && "r" in SM ? SM : null, SR2 = SCi ? Math.sign(SCi.r) * SCi.r * SCi.r : 0;
|
|
4495
4651
|
const wm = new Float64Array(12);
|
|
4496
4652
|
for (const b of stepBatches) {
|
|
4653
|
+
if (studsOnly && b.flag !== "studs")
|
|
4654
|
+
continue;
|
|
4497
4655
|
const MA = b.im.instanceMatrix.array, CA = b.im.instanceColor.array;
|
|
4656
|
+
const D = b.decal, DM = D?.instanceMatrix.array, DC = D?.instanceColor.array, sm = b.flag === "studs" ? SM : null;
|
|
4657
|
+
let w2 = 0;
|
|
4498
4658
|
const useHide = b.flag === "studs" ? cullS : b.flag === "under" ? cullU : false;
|
|
4499
4659
|
const { own, hide, inst, stud, col } = b;
|
|
4500
4660
|
let w = 0;
|
|
@@ -4516,14 +4676,31 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4516
4676
|
const n = inst[i];
|
|
4517
4677
|
if (O && !O[n])
|
|
4518
4678
|
continue;
|
|
4519
|
-
if (stud)
|
|
4679
|
+
if (stud)
|
|
4520
4680
|
mul12To(instM, instPP[n].studM, stud[i] * 12, wm, n * 12);
|
|
4681
|
+
const real = !sm || (SA ? !!SA[n] : (wm[0] - SCi.x) ** 2 + (wm[2] - SCi.z) ** 2 < SR2);
|
|
4682
|
+
if (!real && !D)
|
|
4683
|
+
continue;
|
|
4684
|
+
if (D) {
|
|
4685
|
+
writeM4(DM, w2 * 16, wm);
|
|
4686
|
+
palette[col[i]].toArray(DC, w2 * 3);
|
|
4687
|
+
w2++;
|
|
4688
|
+
}
|
|
4689
|
+
if (!real)
|
|
4690
|
+
continue;
|
|
4691
|
+
if (stud)
|
|
4521
4692
|
writeM4(MA, w * 16, wm);
|
|
4522
|
-
|
|
4693
|
+
else
|
|
4523
4694
|
writeM4(MA, w * 16, instM, n * 12);
|
|
4524
4695
|
palette[col[i]].toArray(CA, w * 3);
|
|
4525
4696
|
w++;
|
|
4526
4697
|
}
|
|
4698
|
+
if (D) {
|
|
4699
|
+
D.instanceMatrix.needsUpdate = true;
|
|
4700
|
+
D.instanceColor.needsUpdate = true;
|
|
4701
|
+
D.count = w2;
|
|
4702
|
+
D.visible = !!SM;
|
|
4703
|
+
}
|
|
4527
4704
|
b.im.instanceMatrix.needsUpdate = true;
|
|
4528
4705
|
b.im.instanceColor.needsUpdate = true;
|
|
4529
4706
|
for (const o of b.objs) {
|
|
@@ -4533,20 +4710,21 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4533
4710
|
o.geometry.instanceCount = w;
|
|
4534
4711
|
}
|
|
4535
4712
|
}
|
|
4536
|
-
|
|
4537
|
-
const
|
|
4538
|
-
|
|
4539
|
-
|
|
4540
|
-
|
|
4541
|
-
|
|
4542
|
-
|
|
4543
|
-
|
|
4544
|
-
|
|
4713
|
+
if (!studsOnly)
|
|
4714
|
+
for (const b of stepBatched) {
|
|
4715
|
+
const useHide = b.flag === "under" ? cullU : false;
|
|
4716
|
+
const { own, hide, inst, bm } = b;
|
|
4717
|
+
for (let i = 0;i < own.length; i++) {
|
|
4718
|
+
const hid = !!hide && hide[i] <= S;
|
|
4719
|
+
if (b.flag === "under") {
|
|
4720
|
+
st.undersTotal++;
|
|
4721
|
+
if (hid)
|
|
4722
|
+
st.undersHidden++;
|
|
4723
|
+
}
|
|
4724
|
+
const on = own[i] <= S && !(useHide && hid) && !(O && !O[inst[i]]);
|
|
4725
|
+
bm.setVisibleAt(i, on);
|
|
4545
4726
|
}
|
|
4546
|
-
const on = own[i] <= S && !(useHide && hid) && !(O && !O[inst[i]]);
|
|
4547
|
-
bm.setVisibleAt(i, on);
|
|
4548
4727
|
}
|
|
4549
|
-
}
|
|
4550
4728
|
return st;
|
|
4551
4729
|
};
|
|
4552
4730
|
const setCull = (studs, under) => {
|
|
@@ -4566,7 +4744,14 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4566
4744
|
only = mask;
|
|
4567
4745
|
return applySteps();
|
|
4568
4746
|
};
|
|
4569
|
-
const
|
|
4747
|
+
const setStudMask = (mask) => {
|
|
4748
|
+
if (!steps)
|
|
4749
|
+
return false;
|
|
4750
|
+
studMask = mask;
|
|
4751
|
+
applySteps(true);
|
|
4752
|
+
return true;
|
|
4753
|
+
};
|
|
4754
|
+
const box = new THREE2.Box3;
|
|
4570
4755
|
for (const it of insts) {
|
|
4571
4756
|
if (!H.parts[it.part])
|
|
4572
4757
|
continue;
|
|
@@ -4588,11 +4773,11 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4588
4773
|
for (const m of new Set([matF, matB, matD, ...matCache.values(), ...texMats.values()])) {
|
|
4589
4774
|
const role = m.userData?.ldrSideRole;
|
|
4590
4775
|
if (role === "D") {
|
|
4591
|
-
m.side =
|
|
4776
|
+
m.side = THREE2.DoubleSide;
|
|
4592
4777
|
} else if (role === "B") {
|
|
4593
|
-
m.side = front ?
|
|
4778
|
+
m.side = front ? THREE2.BackSide : THREE2.DoubleSide;
|
|
4594
4779
|
} else {
|
|
4595
|
-
m.side = front ?
|
|
4780
|
+
m.side = front ? THREE2.FrontSide : THREE2.DoubleSide;
|
|
4596
4781
|
}
|
|
4597
4782
|
m.needsUpdate = true;
|
|
4598
4783
|
}
|
|
@@ -4624,7 +4809,7 @@ function* buildLdrSceneGen(insts, pack, P, color, mark) {
|
|
|
4624
4809
|
o.matrixAutoUpdate = false;
|
|
4625
4810
|
o.matrixWorldNeedsUpdate = true;
|
|
4626
4811
|
}
|
|
4627
|
-
return { root, stats, setCull, setSide, setEdges, setCond, setLod, setStep, box, texturesReady, trimmed };
|
|
4812
|
+
return { root, stats, setCull, setSide, setEdges, setCond, setLod, setStep, setStudMask, box, texturesReady, trimmed };
|
|
4628
4813
|
}
|
|
4629
4814
|
function buildLdrScene(insts, pack, P, color, mark) {
|
|
4630
4815
|
const g = buildLdrSceneGen(insts, pack, P, color, mark);
|
|
@@ -4702,18 +4887,18 @@ async function warmPackGeometry(pack, stop = () => false, sliceMs = 8) {
|
|
|
4702
4887
|
await new Promise((r) => setTimeout(r, 0));
|
|
4703
4888
|
}
|
|
4704
4889
|
}
|
|
4705
|
-
// ../../../../../../../tmp/ldr-build-
|
|
4706
|
-
import * as
|
|
4707
|
-
var _box = new
|
|
4708
|
-
var _m4 = new
|
|
4890
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/scene.ts
|
|
4891
|
+
import * as THREE3 from "three";
|
|
4892
|
+
var _box = new THREE3.Box3;
|
|
4893
|
+
var _m4 = new THREE3.Matrix4;
|
|
4709
4894
|
function ghostMaterial(side, g) {
|
|
4710
|
-
const m = new
|
|
4711
|
-
m.blending =
|
|
4712
|
-
m.blendSrc =
|
|
4713
|
-
m.blendDst =
|
|
4714
|
-
m.blendSrcAlpha =
|
|
4715
|
-
m.blendDstAlpha =
|
|
4716
|
-
const tint = new
|
|
4895
|
+
const m = new THREE3.MeshStandardMaterial({ color: 16777215, roughness: 0.85, metalness: 0, side, transparent: false, depthWrite: true, opacity: g.opacity, polygonOffset: true, polygonOffsetFactor: 1, polygonOffsetUnits: 1 });
|
|
4896
|
+
m.blending = THREE3.CustomBlending;
|
|
4897
|
+
m.blendSrc = THREE3.SrcAlphaFactor;
|
|
4898
|
+
m.blendDst = THREE3.OneMinusSrcAlphaFactor;
|
|
4899
|
+
m.blendSrcAlpha = THREE3.OneFactor;
|
|
4900
|
+
m.blendDstAlpha = THREE3.OneMinusSrcAlphaFactor;
|
|
4901
|
+
const tint = new THREE3.Color(g.color);
|
|
4717
4902
|
const u = { ldrGhostTint: { value: tint }, ldrGhostMix: { value: g.whiten } };
|
|
4718
4903
|
m.onBeforeCompile = (sh) => {
|
|
4719
4904
|
Object.assign(sh.uniforms, u);
|
|
@@ -4727,13 +4912,13 @@ function ghostMaterial(side, g) {
|
|
|
4727
4912
|
}
|
|
4728
4913
|
function colorFn(src, pack, fallback) {
|
|
4729
4914
|
const table = new Map;
|
|
4730
|
-
const put = (k, v) => table.set(String(k), new
|
|
4915
|
+
const put = (k, v) => table.set(String(k), new THREE3.Color(typeof v === "string" ? v : v.hex));
|
|
4731
4916
|
if (typeof src === "function") {
|
|
4732
4917
|
return (c) => {
|
|
4733
4918
|
let col = table.get(c);
|
|
4734
4919
|
if (!col) {
|
|
4735
4920
|
const v = src(+c);
|
|
4736
|
-
col = v === undefined ? direct(c) ?? fallback : new
|
|
4921
|
+
col = v === undefined ? direct(c) ?? fallback : new THREE3.Color(v);
|
|
4737
4922
|
table.set(c, col);
|
|
4738
4923
|
}
|
|
4739
4924
|
return col;
|
|
@@ -4751,14 +4936,14 @@ function colorFn(src, pack, fallback) {
|
|
|
4751
4936
|
var direct = (c) => {
|
|
4752
4937
|
const n = +c;
|
|
4753
4938
|
if (n > 16777215 && n >>> 24 === 2)
|
|
4754
|
-
return new
|
|
4939
|
+
return new THREE3.Color(n & 16777215);
|
|
4755
4940
|
const b = blendedColourHex(n);
|
|
4756
|
-
return b ? new
|
|
4941
|
+
return b ? new THREE3.Color(b) : null;
|
|
4757
4942
|
};
|
|
4758
4943
|
function withLocalColours(base, local) {
|
|
4759
4944
|
if (!local.size)
|
|
4760
4945
|
return base;
|
|
4761
|
-
const own = new Map([...local].map(([k, v]) => [k, new
|
|
4946
|
+
const own = new Map([...local].map(([k, v]) => [k, new THREE3.Color(v.hex)]));
|
|
4762
4947
|
return (c) => own.get(c) ?? base(c);
|
|
4763
4948
|
}
|
|
4764
4949
|
var plasticCache = new WeakMap;
|
|
@@ -4770,7 +4955,7 @@ function toPlastic(old) {
|
|
|
4770
4955
|
return old;
|
|
4771
4956
|
let m = plasticCache.get(old);
|
|
4772
4957
|
if (!m) {
|
|
4773
|
-
const p = new
|
|
4958
|
+
const p = new THREE3.MeshPhysicalMaterial({
|
|
4774
4959
|
vertexColors: true,
|
|
4775
4960
|
roughness: 0.3,
|
|
4776
4961
|
clearcoat: 0.3,
|
|
@@ -4781,8 +4966,11 @@ function toPlastic(old) {
|
|
|
4781
4966
|
opacity: old.opacity,
|
|
4782
4967
|
depthWrite: old.depthWrite,
|
|
4783
4968
|
metalness: old.metalness,
|
|
4784
|
-
emissive: old.emissive?.clone?.() ?? new
|
|
4785
|
-
emissiveIntensity: old.emissiveIntensity ?? 0
|
|
4969
|
+
emissive: old.emissive?.clone?.() ?? new THREE3.Color(0),
|
|
4970
|
+
emissiveIntensity: old.emissiveIntensity ?? 0,
|
|
4971
|
+
polygonOffset: old.polygonOffset,
|
|
4972
|
+
polygonOffsetFactor: old.polygonOffsetFactor,
|
|
4973
|
+
polygonOffsetUnits: old.polygonOffsetUnits
|
|
4786
4974
|
});
|
|
4787
4975
|
p.onBeforeCompile = old.onBeforeCompile;
|
|
4788
4976
|
p.customProgramCacheKey = () => "Phys" + old.customProgramCacheKey() + old.side;
|
|
@@ -4802,14 +4990,24 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4802
4990
|
const useTex = o.textures !== false;
|
|
4803
4991
|
const { all, stepOf, nSteps, localColours } = sceneInstances(instances, pack.header, useTex);
|
|
4804
4992
|
const uniq = { length: nSteps };
|
|
4805
|
-
const color = withLocalColours(colorFn(o.colors, pack, new
|
|
4993
|
+
const color = withLocalColours(colorFn(o.colors, pack, new THREE3.Color(o.fallbackColor ?? 10528169)), localColours);
|
|
4806
4994
|
const stepViews = new Array(uniq.length).fill(null);
|
|
4807
4995
|
instances.forEach((i, k) => {
|
|
4808
4996
|
if (i.view)
|
|
4809
4997
|
stepViews[stepOf[k]] = i.view;
|
|
4810
4998
|
});
|
|
4811
|
-
const
|
|
4812
|
-
const
|
|
4999
|
+
const parts = pack.header.parts;
|
|
5000
|
+
const miss = new Set;
|
|
5001
|
+
let drawnAll = 0;
|
|
5002
|
+
for (let k = 0;k < all.length; k++) {
|
|
5003
|
+
const p = all[k].part;
|
|
5004
|
+
if (parts[p])
|
|
5005
|
+
drawnAll++;
|
|
5006
|
+
else
|
|
5007
|
+
miss.add(p);
|
|
5008
|
+
}
|
|
5009
|
+
const missing = [...miss];
|
|
5010
|
+
const object = new THREE3.Group;
|
|
4813
5011
|
object.name = "ldr";
|
|
4814
5012
|
if (!o.ldrawSpace)
|
|
4815
5013
|
object.rotation.x = Math.PI;
|
|
@@ -4828,7 +5026,7 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4828
5026
|
x.geometry?.dispose?.();
|
|
4829
5027
|
if (x.material)
|
|
4830
5028
|
mats.add(x.material);
|
|
4831
|
-
if (x.dispose && x.isInstancedMesh)
|
|
5029
|
+
if (x.dispose && (x.isInstancedMesh || x.isBatchedMesh))
|
|
4832
5030
|
x.dispose();
|
|
4833
5031
|
});
|
|
4834
5032
|
for (const m of [...mats, ...pairs.values()]) {
|
|
@@ -4839,16 +5037,17 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4839
5037
|
cur = null;
|
|
4840
5038
|
};
|
|
4841
5039
|
let ghostOn = false, ghost = null, ghostBuild = null, ghostGen = 0;
|
|
4842
|
-
let
|
|
5040
|
+
let studMaskShown = null;
|
|
5041
|
+
let shownStep = null, shownMask = null, shownGhost = null;
|
|
4843
5042
|
const ghostOpts = { opacity: 0.2, color: 16777215, whiten: 0.75 };
|
|
4844
5043
|
const ghostMats = new Map;
|
|
4845
5044
|
const syncGhost = () => {
|
|
4846
5045
|
if (!ghost)
|
|
4847
5046
|
return;
|
|
4848
|
-
const show = ghostOn && shownStep != null &&
|
|
5047
|
+
const show = ghostOn && shownStep != null && shownGhost != null && shownGhost < uniq.length - 1;
|
|
4849
5048
|
ghost.root.visible = show;
|
|
4850
5049
|
if (show)
|
|
4851
|
-
ghost.setStep(uniq.length - 2 -
|
|
5050
|
+
ghost.setStep(uniq.length - 2 - shownGhost, shownMask);
|
|
4852
5051
|
};
|
|
4853
5052
|
const disposeGhost = () => {
|
|
4854
5053
|
ghostGen++;
|
|
@@ -4873,7 +5072,7 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4873
5072
|
const rev = new Int32Array(stepOf.length);
|
|
4874
5073
|
for (let k = 0;k < rev.length; k++)
|
|
4875
5074
|
rev[k] = n - 1 - stepOf[k];
|
|
4876
|
-
const so = { ...sceneOpts(), edges: false, cond: false, tex: false, steps: rev, cull: undefined };
|
|
5075
|
+
const so = { ...sceneOpts(), studDecal: undefined, edges: false, cond: false, tex: false, steps: rev, cull: undefined };
|
|
4877
5076
|
so.cull = cullCore(all, pack.header, rev);
|
|
4878
5077
|
const g = await buildLdrSceneAsync(all, pack, so, color, () => {}, { postPaintSliceMs: 12 });
|
|
4879
5078
|
if (my !== ghostGen) {
|
|
@@ -4889,9 +5088,9 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4889
5088
|
return;
|
|
4890
5089
|
if (x.material)
|
|
4891
5090
|
old.add(x.material);
|
|
4892
|
-
let m = ghostMats.get(x.material?.side ??
|
|
5091
|
+
let m = ghostMats.get(x.material?.side ?? THREE3.FrontSide);
|
|
4893
5092
|
if (!m)
|
|
4894
|
-
ghostMats.set(x.material?.side ??
|
|
5093
|
+
ghostMats.set(x.material?.side ?? THREE3.FrontSide, m = ghostMaterial(x.material?.side ?? THREE3.FrontSide, ghostOpts));
|
|
4895
5094
|
x.material = m;
|
|
4896
5095
|
x.castShadow = x.receiveShadow = false;
|
|
4897
5096
|
x.renderOrder = 1;
|
|
@@ -4908,8 +5107,28 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4908
5107
|
syncGhost();
|
|
4909
5108
|
})();
|
|
4910
5109
|
const multiStep = uniq.length > 1;
|
|
4911
|
-
const drawnAt = (step, mask) =>
|
|
4912
|
-
|
|
5110
|
+
const drawnAt = (step, mask) => {
|
|
5111
|
+
if (step == null && !mask)
|
|
5112
|
+
return drawnAll;
|
|
5113
|
+
let n = 0;
|
|
5114
|
+
for (let k = 0;k < all.length; k++)
|
|
5115
|
+
if ((step == null || stepOf[k] <= step) && (!mask || mask[k]) && parts[all[k].part])
|
|
5116
|
+
n++;
|
|
5117
|
+
return n;
|
|
5118
|
+
};
|
|
5119
|
+
let stepMode = multiStep && (o.step != null || !!o.eagerSteps);
|
|
5120
|
+
let flatCull = o.precomputedCull, stepCull = o.precomputedCull?.studHideStep ? o.precomputedCull : undefined;
|
|
5121
|
+
const withCull = (so) => {
|
|
5122
|
+
if (!so.cull) {
|
|
5123
|
+
so.cull = cullCore(all, pack.header, so.steps);
|
|
5124
|
+
if (so.steps)
|
|
5125
|
+
stepCull = so.cull;
|
|
5126
|
+
else
|
|
5127
|
+
flatCull = so.cull;
|
|
5128
|
+
}
|
|
5129
|
+
return so;
|
|
5130
|
+
};
|
|
5131
|
+
const sceneOpts = () => ({ localColours: localColours.size ? localColours : undefined, cullStuds: cs, cullUnder: cu, studGrid: o.studGrid, studDecal: o.studDecal, edges: o.edges, side, cond: o.conditionalLines, condStuds: o.conditionalStudLines !== false, tex: o.textures !== false, lod: o.lod !== false, lodPx: o.lodPx, lodEdgePx: o.lodEdgePx, lodEdgeMinPx: o.lodEdgeMinPx, lodEdgeCap: o.lodEdgeCap, lodUnder: o.lodUnder, steps: stepMode ? stepOf : undefined, cull: stepMode ? stepCull : flatCull });
|
|
4913
5132
|
const applyBuilt = (built, t0) => {
|
|
4914
5133
|
cur = built;
|
|
4915
5134
|
pairs.clear();
|
|
@@ -4932,15 +5151,28 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4932
5151
|
cur.setLod(false);
|
|
4933
5152
|
if (cur.root.parent !== object)
|
|
4934
5153
|
object.add(cur.root);
|
|
5154
|
+
if (studMaskShown && stepMode)
|
|
5155
|
+
cur.setStudMask(studMaskShown);
|
|
4935
5156
|
Object.assign(stats, { drawn: drawnAt(null), studsTotal: cur.stats.studsTotal, studsHidden: cur.stats.studsHidden, undersTotal: cur.stats.undersTotal, undersHidden: cur.stats.undersHidden, condBatches: cur.stats.condBatches ?? 0, texBatches: cur.stats.texBatches ?? 0, textures: cur.stats.textures ?? 0, glossmaps: cur.stats.glossmaps ?? 0, clusters: cur.stats.clusters ?? 0, longestSliceMs: cur.stats.longestSliceMs, buildYields: cur.stats.buildYields, buildMs: performance.now() - t0 });
|
|
4936
5157
|
api.texturesReady = cur.texturesReady;
|
|
4937
5158
|
};
|
|
4938
|
-
const setStep = (step, mask = null) => {
|
|
5159
|
+
const setStep = (step, mask = null, ghostAfter) => {
|
|
4939
5160
|
if (!multiStep)
|
|
4940
5161
|
return;
|
|
4941
5162
|
const t0 = performance.now();
|
|
4942
5163
|
shownStep = step;
|
|
4943
5164
|
shownMask = mask;
|
|
5165
|
+
shownGhost = step == null ? null : Math.max(step, ghostAfter ?? step);
|
|
5166
|
+
if (!stepMode) {
|
|
5167
|
+
if (!mask && (step == null || step >= uniq.length - 1)) {
|
|
5168
|
+
Object.assign(stats, { drawn: drawnAt(null), buildMs: performance.now() - t0 });
|
|
5169
|
+
syncGhost();
|
|
5170
|
+
return;
|
|
5171
|
+
}
|
|
5172
|
+
stepMode = true;
|
|
5173
|
+
disposeCur();
|
|
5174
|
+
applyBuilt(buildLdrScene(all, pack, withCull(sceneOpts()), color, () => {}), t0);
|
|
5175
|
+
}
|
|
4944
5176
|
Object.assign(stats, cur.setStep(step, mask), { drawn: drawnAt(step, mask), buildMs: performance.now() - t0 });
|
|
4945
5177
|
if (ghostOn && step != null && !ghost)
|
|
4946
5178
|
buildGhost();
|
|
@@ -4956,6 +5188,10 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4956
5188
|
stepCount: uniq.length,
|
|
4957
5189
|
stepViews,
|
|
4958
5190
|
setStep,
|
|
5191
|
+
setStudMask: (m) => {
|
|
5192
|
+
studMaskShown = m;
|
|
5193
|
+
return stepMode ? cur.setStudMask(m) : false;
|
|
5194
|
+
},
|
|
4959
5195
|
setEdges: (v) => {
|
|
4960
5196
|
edges = v;
|
|
4961
5197
|
cur.setEdges(v);
|
|
@@ -4970,7 +5206,7 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
4970
5206
|
if (!a && cur.trimmed.studs || !b && cur.trimmed.under) {
|
|
4971
5207
|
disposeCur();
|
|
4972
5208
|
const t0 = performance.now();
|
|
4973
|
-
applyBuilt(buildLdrScene(all, pack, sceneOpts(), color, () => {}), t0);
|
|
5209
|
+
applyBuilt(buildLdrScene(all, pack, withCull(sceneOpts()), color, () => {}), t0);
|
|
4974
5210
|
} else
|
|
4975
5211
|
cur.setCull(a, b);
|
|
4976
5212
|
ghost?.setCull(a, b);
|
|
@@ -5007,7 +5243,7 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
5007
5243
|
p.needsUpdate = true;
|
|
5008
5244
|
}
|
|
5009
5245
|
},
|
|
5010
|
-
getBox: (target = new
|
|
5246
|
+
getBox: (target = new THREE3.Box3) => {
|
|
5011
5247
|
object.updateMatrixWorld(true);
|
|
5012
5248
|
target.makeEmpty();
|
|
5013
5249
|
object.traverse((x) => {
|
|
@@ -5036,14 +5272,12 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
5036
5272
|
};
|
|
5037
5273
|
if (!progressive) {
|
|
5038
5274
|
const t0 = performance.now();
|
|
5039
|
-
applyBuilt(buildLdrScene(all, pack, sceneOpts(), color, () => {}), t0);
|
|
5275
|
+
applyBuilt(buildLdrScene(all, pack, withCull(sceneOpts()), color, () => {}), t0);
|
|
5040
5276
|
return finish();
|
|
5041
5277
|
}
|
|
5042
5278
|
return (async () => {
|
|
5043
5279
|
const t0 = performance.now();
|
|
5044
|
-
const so = sceneOpts();
|
|
5045
|
-
if (!so.cull)
|
|
5046
|
-
so.cull = cullCore(all, pack.header, so.steps);
|
|
5280
|
+
const so = withCull(sceneOpts());
|
|
5047
5281
|
const built = await buildLdrSceneAsync(all, pack, so, color, () => {}, {
|
|
5048
5282
|
sliceMs: o.sliceMs,
|
|
5049
5283
|
postPaintSliceMs: o.postPaintSliceMs,
|
|
@@ -5057,10 +5291,10 @@ function createLdrObjectInner(instances, pack, options, progressive) {
|
|
|
5057
5291
|
return finish();
|
|
5058
5292
|
})();
|
|
5059
5293
|
}
|
|
5060
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5294
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/parts-cdn.ts
|
|
5061
5295
|
import { decompress as decompress2 } from "fzstd";
|
|
5062
5296
|
|
|
5063
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5297
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/embedded.ts
|
|
5064
5298
|
function splitFiles(text, fallback) {
|
|
5065
5299
|
const files = new Map;
|
|
5066
5300
|
let cur = null, saw = false, skip = false;
|
|
@@ -5138,8 +5372,8 @@ function embeddedKeys(text, names, fallback = "main.ldr") {
|
|
|
5138
5372
|
return out;
|
|
5139
5373
|
}
|
|
5140
5374
|
|
|
5141
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5142
|
-
var DEFAULT_PARTS_CDN = "https://ldr-
|
|
5375
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/parts-cdn.ts
|
|
5376
|
+
var DEFAULT_PARTS_CDN = "https://ldr-parts-cdn.baconbrix.workers.dev/v1/";
|
|
5143
5377
|
var indexCache = new Map;
|
|
5144
5378
|
var shardCache = new Map;
|
|
5145
5379
|
function loadPartsIndex(cdn = DEFAULT_PARTS_CDN, f = fetch) {
|
|
@@ -5399,10 +5633,10 @@ async function prepareModel(source, o = {}) {
|
|
|
5399
5633
|
return { insts, pack, tier, missing, requests, bytes, cull, timings: { fetchModel: t1 - t0, parse: t2 - t1, parts: t3 - t2, ...cull ? { cull: performance.now() - t3 } : {} } };
|
|
5400
5634
|
}
|
|
5401
5635
|
|
|
5402
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5403
|
-
var load_worker_gen_default = 'var nn=ArrayBuffer,W=Uint8Array,ze=Uint16Array,rn=Int16Array;var $e=Int32Array,Ye=function(e,t,n){if(W.prototype.slice)return W.prototype.slice.call(e,t,n);if(t==null||t<0)t=0;if(n==null||n>e.length)n=e.length;var r=new W(n-t);return r.set(e.subarray(t,n)),r},Re=function(e,t,n,r){if(W.prototype.fill)return W.prototype.fill.call(e,t,n,r);if(n==null||n<0)n=0;if(r==null||r>e.length)r=e.length;for(;n<r;++n)e[n]=t;return e},sn=function(e,t,n,r){if(W.prototype.copyWithin)return W.prototype.copyWithin.call(e,t,n,r);if(n==null||n<0)n=0;if(r==null||r>e.length)r=e.length;while(n<r)e[t++]=e[n++]};var on=["invalid zstd data","window size too large (>2046MB)","invalid block type","FSE accuracy too high","match distance too far back","unexpected EOF"],Z=function(e,t,n){var r=Error(t||on[e]);if(r.code=e,Error.captureStackTrace)Error.captureStackTrace(r,Z);if(!n)throw r;return r},bt=function(e,t,n){var r=0,s=0;for(;r<n;++r)s|=e[t++]<<(r<<3);return s},an=function(e,t){return(e[t]|e[t+1]<<8|e[t+2]<<16|e[t+3]<<24)>>>0},ln=function(e,t){var n=e[0]|e[1]<<8|e[2]<<16;if(n==3126568&&e[3]==253){var r=e[4],s=r>>5&1,o=r>>2&1,i=r&3,c=r>>6;if(r&8)Z(0);var a=6-s,u=i==3?4:i,l=bt(e,a,u);a+=u;var f=c?1<<c:s,h=bt(e,a,f)+(c==1&&256),g=h;if(!s){var p=1<<10+(e[5]>>3);g=p+(p>>3)*(e[5]&7)}if(g>2145386496)Z(1);var m=new W((t==1?h||g:t?0:g)+12);return m[0]=1,m[4]=4,m[8]=8,{b:a+f,y:0,l:0,d:l,w:t&&t!=1?t:m.subarray(12),e:g,o:new $e(m.buffer,0,3),u:h,c:o,m:Math.min(131072,g)}}else if((n>>4|e[3]<<20)==25481893)return an(e,4)+8;Z(0)},Se=function(e){var t=0;for(;1<<t<=e;++t);return t-1},Be=function(e,t,n){var r=(t<<3)+4,s=(e[t]&15)+5;if(s>n)Z(3);var o=1<<s,i=o,c=-1,a=-1,u=-1,l=o,f=new nn(512+(o<<2)),h=new rn(f,0,256),g=new ze(f,0,256),p=new ze(f,512,o),m=512+(o<<1),A=new W(f,m,o),x=new W(f,m+o);while(c<255&&i>0){var d=Se(i+1),w=r>>3,b=(1<<d+1)-1,M=(e[w]|e[w+1]<<8|e[w+2]<<16)>>(r&7)&b,k=(1<<d)-1,N=b-i-1,P=M&k;if(P<N)r+=d,M=P;else if(r+=d+1,M>k)M-=N;if(h[++c]=--M,M==-1)i+=M,A[--l]=c;else i-=M;if(!M)do{var D=r>>3;a=(e[D]|e[D+1]<<8)>>(r&7)&3,r+=2,c+=a}while(a==3)}if(c>255||i)Z(0);var y=0,B=(o>>1)+(o>>3)+3,C=o-1;for(var I=0;I<=c;++I){var R=h[I];if(R<1){g[I]=-R;continue}for(u=0;u<R;++u){A[y]=I;do y=y+B&C;while(y>=l)}}if(y)Z(0);for(u=0;u<o;++u){var S=g[A[u]]++,V=x[u]=s-Se(S);p[u]=(S<<V)-o}return[r+7>>3,{b:s,s:A,n:x,t:p}]},cn=function(e,t){var n=0,r=-1,s=new W(292),o=e[t],i=s.subarray(0,256),c=s.subarray(256,268),a=new ze(s.buffer,268);if(o<128){var u=Be(e,t+1,6),l=u[0],f=u[1];t+=o;var h=l<<3,g=e[t];if(!g)Z(0);var p=0,m=0,A=f.b,x=A,d=(++t<<3)-8+Se(g);for(;;){if(d-=A,d<h)break;var w=d>>3;if(p+=(e[w]|e[w+1]<<8)>>(d&7)&(1<<A)-1,i[++r]=f.s[p],d-=x,d<h)break;w=d>>3,m+=(e[w]|e[w+1]<<8)>>(d&7)&(1<<x)-1,i[++r]=f.s[m],A=f.n[p],p=f.t[p],x=f.n[m],m=f.t[m]}if(++r>255)Z(0)}else{r=o-127;for(;n<r;n+=2){var b=e[++t];i[n]=b>>4,i[n+1]=b&15}++t}var M=0;for(n=0;n<r;++n){var k=i[n];if(k>11)Z(0);M+=k&&1<<k-1}var N=Se(M)+1,P=1<<N,D=P-M;if(D&D-1)Z(0);i[r++]=Se(D)+1;for(n=0;n<r;++n){var k=i[n];++c[i[n]=k&&N+1-k]}var y=new W(P<<1),B=y.subarray(0,P),C=y.subarray(P);a[N]=0;for(n=N;n>0;--n){var I=a[n];Re(C,n,I,a[n-1]=I+c[n]*(1<<N-n))}if(a[0]!=P)Z(0);for(n=0;n<r;++n){var R=i[n];if(R){var S=a[R];Re(B,n,S,a[R]=S+(1<<N-R))}}return[t,{n:C,b:N,s:B}]},un=Be(new W([81,16,99,140,49,198,24,99,12,33,196,24,99,102,102,134,70,146,4]),0,6)[1],fn=Be(new W([33,20,196,24,99,140,33,132,16,66,8,33,132,16,66,8,33,68,68,68,68,68,68,68,68,36,9]),0,6)[1],pn=Be(new W([32,132,16,66,102,70,68,68,68,68,36,73,2]),0,5)[1],yt=function(e,t){var n=e.length,r=new $e(n);for(var s=0;s<n;++s)r[s]=t,t+=1<<e[s];return r},Je=new W(new $e([0,0,0,0,16843009,50528770,134678020,202050057,269422093]).buffer,0,36),mn=yt(Je,0),Qe=new W(new $e([0,0,0,0,0,0,0,0,16843009,50528770,117769220,185207048,252579084,16]).buffer,0,53),hn=yt(Qe,3),Fe=function(e,t,n){var r=e.length,s=t.length,o=e[r-1],i=(1<<n.b)-1,c=-n.b;if(!o)Z(0);var a=0,u=n.b,l=(r<<3)-8+Se(o)-u,f=-1;for(;l>c&&f<s;){var h=l>>3,g=(e[h]|e[h+1]<<8|e[h+2]<<16)>>(l&7);a=(a<<u|g)&i,t[++f]=n.s[a],l-=u=n.n[a]}if(l!=c||f+1!=s)Z(0)},gn=function(e,t,n){var r=6,s=t.length,o=s+3>>2,i=o<<1,c=o+i;Fe(e.subarray(r,r+=e[0]|e[1]<<8),t.subarray(0,o),n),Fe(e.subarray(r,r+=e[2]|e[3]<<8),t.subarray(o,i),n),Fe(e.subarray(r,r+=e[4]|e[5]<<8),t.subarray(i,c),n),Fe(e.subarray(r),t.subarray(c),n)},dn=function(e,t,n){var r,s=t.b,o=e[s],i=o>>1&3;t.l=o&1;var c=o>>3|e[s+1]<<5|e[s+2]<<13,a=(s+=3)+c;if(i==1){if(s>=e.length)return;if(t.b=s+1,n)return Re(n,e[s],t.y,t.y+=c),n;return Re(new W(c),e[s])}if(a>e.length)return;if(i==0){if(t.b=a,n)return n.set(e.subarray(s,a),t.y),t.y+=c,n;return Ye(e,s,a)}if(i==2){var u=e[s],l=u&3,f=u>>2&3,h=u>>4,g=0,p=0;if(l<2)if(f&1)h|=e[++s]<<4|(f&2&&e[++s]<<12);else h=u>>3;else if(p=f,f<2)h|=(e[++s]&63)<<4,g=e[s]>>6|e[++s]<<2;else if(f==2)h|=e[++s]<<4|(e[++s]&3)<<12,g=e[s]>>2|e[++s]<<6;else h|=e[++s]<<4|(e[++s]&63)<<12,g=e[s]>>6|e[++s]<<2|e[++s]<<10;++s;var m=n?n.subarray(t.y,t.y+t.m):new W(t.m),A=m.length-h;if(l==0)m.set(e.subarray(s,s+=h),A);else if(l==1)Re(m,e[s++],A);else{var x=t.h;if(l==2){var d=cn(e,s);g+=s-(s=d[0]),t.h=x=d[1]}else if(!x)Z(0);(p?gn:Fe)(e.subarray(s,s+=g),m.subarray(A),x)}var w=e[s++];if(w){if(w==255)w=(e[s++]|e[s++]<<8)+32512;else if(w>127)w=w-128<<8|e[s++];var b=e[s++];if(b&3)Z(0);var M=[fn,pn,un];for(var k=2;k>-1;--k){var N=b>>(k<<1)+2&3;if(N==1){var P=new W([0,0,e[s++]]);M[k]={s:P.subarray(2,3),n:P.subarray(0,1),t:new ze(P.buffer,0,1),b:0}}else if(N==2)r=Be(e,s,9-(k&1)),s=r[0],M[k]=r[1];else if(N==3){if(!t.t)Z(0);M[k]=t.t[k]}}var D=t.t=M,y=D[0],B=D[1],C=D[2],I=e[a-1];if(!I)Z(0);var R=(a<<3)-8+Se(I)-C.b,S=R>>3,V=0,he=(e[S]|e[S+1]<<8)>>(R&7)&(1<<C.b)-1;S=(R-=B.b)>>3;var ce=(e[S]|e[S+1]<<8)>>(R&7)&(1<<B.b)-1;S=(R-=y.b)>>3;var Me=(e[S]|e[S+1]<<8)>>(R&7)&(1<<y.b)-1;for(++w;--w;){var re=C.s[he],Te=C.n[he],be=y.s[Me],ve=y.n[Me],fe=B.s[ce],ke=B.n[ce];S=(R-=fe)>>3;var O=1<<fe,T=O+((e[S]|e[S+1]<<8|e[S+2]<<16|e[S+3]<<24)>>>(R&7)&O-1);S=(R-=Qe[be])>>3;var _=hn[be]+((e[S]|e[S+1]<<8|e[S+2]<<16)>>(R&7)&(1<<Qe[be])-1);S=(R-=Je[re])>>3;var X=mn[re]+((e[S]|e[S+1]<<8|e[S+2]<<16)>>(R&7)&(1<<Je[re])-1);if(S=(R-=Te)>>3,he=C.t[he]+((e[S]|e[S+1]<<8)>>(R&7)&(1<<Te)-1),S=(R-=ve)>>3,Me=y.t[Me]+((e[S]|e[S+1]<<8)>>(R&7)&(1<<ve)-1),S=(R-=ke)>>3,ce=B.t[ce]+((e[S]|e[S+1]<<8)>>(R&7)&(1<<ke)-1),T>3)t.o[2]=t.o[1],t.o[1]=t.o[0],t.o[0]=T-=3;else{var q=T-(X!=0);if(q){if(T=q==3?t.o[0]-1:t.o[q],q>1)t.o[2]=t.o[1];t.o[1]=t.o[0],t.o[0]=T}else T=t.o[0]}for(var k=0;k<X;++k)m[V+k]=m[A+k];V+=X,A+=X;var ee=V-T;if(ee<0){var J=-ee,L=t.e+ee;if(J>_)J=_;for(var k=0;k<J;++k)m[V+k]=t.w[L+k];V+=J,_-=J,ee=0}for(var k=0;k<_;++k)m[V+k]=m[ee+k];V+=_}if(V!=A)while(A<m.length)m[V++]=m[A++];else V=m.length;if(n)t.y+=V;else m=Ye(m,0,V)}else if(n){if(t.y+=h,A)for(var k=0;k<h;++k)m[k]=m[A+k]}else if(A)m=Ye(m,A);return t.b=a,m}Z(2)},bn=function(e,t){if(e.length==1)return e[0];var n=new W(t);for(var r=0,s=0;r<e.length;++r){var o=e[r];n.set(o,s),s+=o.length}return n};function je(e,t){var n=[],r=+!t,s=0,o=0;for(;e.length;){var i=ln(e,r||t);if(typeof i=="object"){if(r){if(t=null,i.w.length==i.u)n.push(t=i.w),o+=i.u}else n.push(t),i.e=0;for(;!i.l;){var c=dn(e,i,t);if(!c)Z(5);if(t)i.e=i.y;else n.push(c),o+=c.length,sn(i.w,0,c.length),i.w.set(c,i.w.length-c.length)}s=i.b+i.c*4}else s=i;e=e.subarray(s)}return bn(n,o)}async function yn(e){let t=e instanceof Uint8Array?e:new Uint8Array(e),n=(r)=>r.buffer.slice(r.byteOffset,r.byteOffset+r.byteLength);if(t[0]===40&&t[1]===181&&t[2]===47&&t[3]===253)return n(je(t));if(t[0]===31&&t[1]===139)return new Response(new Blob([t]).stream().pipeThrough(new DecompressionStream("gzip"))).arrayBuffer();return n(t)}async function xt(e){return new TextDecoder().decode(await yn(e))}var wt=(e)=>decodeURIComponent(e.split(/[?#]/)[0].split("/").pop()||"main.ldr").replace(/\\.(zst|gz)$/i,"")||"main.ldr";function Ve(e){let t=new DataView(e).getUint32(0,!0),n=JSON.parse(new TextDecoder().decode(new Uint8Array(e,4,t))),r=4+t;return{header:n,arr:(o)=>o&&(o[2]==="f32"?new Float32Array(e,r+o[0],o[1]):o[2]==="u16"?new Uint16Array(e,r+o[0],o[1]):o[2]==="u8"?new Uint8Array(e,r+o[0],o[1]):new Uint32Array(e,r+o[0],o[1])),bytes:e.byteLength,buffer:e}}var Y=(e)=>e.trim().toLowerCase().replace(/\\\\/g,"/").replace(/\\/+/g,"/"),et=/^[A-Za-z][A-Za-z0-9_]*$/,qe=new Map;function tt(e){let t=e.toLowerCase(),n=2166136261;for(let s=0;s<t.length;s++)n^=t.charCodeAt(s),n=Math.imul(n,16777619);let r=-1-(n>>>0&1073741823);if(!qe.has(r))qe.set(r,t);return r}function nt(e){let t=e.charCodeAt(0)|32;if(t>=97&&t<=122&&et.test(e))return tt(e);if(/^0x/i.test(e))return parseInt(e,16);return+e}var At=/^~?\\s*moved\\s+to\\s+(.+)$/i,xn=new Set(["FILE","NOFILE","!DATA","!:","STEP","BFC","ROTSTEP","BUFEXCHG","!TEXMAP"]),wn=new Set(["FILE","NOFILE","!DATA"]),Et=1000000000000000,Pt=new Set(["part","subpart","primitive","8_primitive","48_primitive","shortcut","helper"]),An=new Set(["model","submodel","configuration"]),Mn=/^(?:!?LDRAW_ORG|Unofficial|Official\\s+LCAD)\\s+(\\S+)/i;function Mt(e){let t=Mn.exec(e);if(!t)return;let n=t[1].toLowerCase().replace(/^unofficial_/,"");return Pt.has(n)||An.has(n)?n:void 0}function vn(e){let t=[],n=0;while(n<e.length){while(e[n]===" "||e[n]==="\\t")n++;if(n>=e.length)break;if(e[n]===\'"\'){let r="";n++;while(n<e.length&&e[n]!==\'"\'){if(e[n]==="\\\\"&&n+1<e.length)n++;r+=e[n++]}n++,t.push(r)}else{let r=n;while(r<e.length&&e[r]!==" "&&e[r]!=="\\t")r++;t.push(e.slice(n,r)),n=r}}return t}function Cn(e,t=!1){let n=/^\\s*(\\S+)\\s+(.*)$/.exec(e);if(!n)return null;let r=n[1].toUpperCase(),s=r==="PLANAR"?9:r==="CYLINDRICAL"?10:r==="SPHERICAL"?11:0;if(!s)return null;let o=n[2].trim().split(/\\s+/);if(o.length<s+1)return null;let i=o.slice(0,s).map(Number);if(!i.every((f)=>Number.isFinite(f)&&Math.abs(f)<=1000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000))return null;if(s>=10&&!(Math.abs(i[9])>=0.000001)||s===11&&!(Math.abs(i[10])>=0.000001))return null;let c=n[2].trim();for(let f=0;f<s;f++)c=c.replace(/^\\S+\\s*/,"");let a=vn(c);if(!a.length)return null;let u={method:r,p1:i.slice(0,3),p2:i.slice(3,6),p3:i.slice(6,9),texture:a[0]};if(s>=10)u.a=i[9];if(s===11)u.b=i[10];let l=a.findIndex((f,h)=>h>0&&f.toUpperCase()==="GLOSSMAP");if(l>0&&a[l+1])u.glossmap=a[l+1];if(t)u.next=!0;return u}var kn=(e)=>{let t=e.replace(/[^A-Za-z0-9+/]/g,"");if(t.length%4===1)t=t.slice(0,-1);let n=t+"=".repeat((4-t.length%4)%4),r=atob(n),s=new Uint8Array(r.length);for(let o=0;o<r.length;o++)s[o]=r.charCodeAt(o);return s};function Tn(e,t){let n=e.length,r=1,s=(p)=>p===32||p===9,o=()=>{while(r<n&&s(e.charCodeAt(r)))r++;let p=r,m=e.charCodeAt(r),A=m===45;if(A)m=e.charCodeAt(++r);let x=0,d=0;while(m>=48&&m<=57)x=x*10+(m-48),d++,m=e.charCodeAt(++r);if(d>0&&d<=15&&(r>=n||s(m)))return A?-x:x;while(r<n&&!s(e.charCodeAt(r)))r++;return p<r?+e.slice(p,r):NaN};while(r<n&&s(e.charCodeAt(r)))r++;let i=r;if(r>=n)return null;let c=e.charCodeAt(r),a=c===45,u=0,l=0;if(a)c=e.charCodeAt(++r);while(c>=48&&c<=57)u=u*10+(c-48),l++,c=e.charCodeAt(++r);if(l>0&&l<=15&&(r>=n||s(c))){if(a)u=-u}else{while(r<n&&!s(e.charCodeAt(r)))r++;u=nt(e.slice(i,r))}let f=Array(12);for(let p=0;p<12;p++){let m=o();if(!Number.isFinite(m))return null;f[p]=m}while(r<n&&s(e.charCodeAt(r)))r++;if(r>=n)return null;let h=e.slice(r),g=t.get(h);if(g===void 0)g=Y(/[ \\t]{2,}|\\t/.test(h)?h.split(/\\s+/).join(" "):h),t.set(h,g);if(!Number.isFinite(u))return null;return{t:1,color:u,m:f,file:g}}var Ln=[0,12,6,9,12,12];function vt(e){let t=+e[0];if(!(t>=1&&t<=5&&Number.isInteger(t))||e.length<2)return null;let n=nt(e[1]),r=Ln[t];if(!Number.isFinite(n)||e.length<2+r+(t===1?1:0))return null;let s=Array(r);for(let o=0;o<r;o++){let i=+e[2+o];if(!Number.isFinite(i))return null;s[o]=i}if(t===1){let o=Y(e.slice(14).join(" "));return o?{t:1,color:n,m:s,file:o}:null}if(t===2)return{t:2,color:n,p:s};if(t===3)return{t:3,color:n,p:s};if(t===4)return{t:4,color:n,p:s};return{t:5,color:n,p:s}}function It(e,t="main.ldr",n={}){let r=!!n.geometryText,s=new Map,o=null,i="",c,a=null,u=[],l=null,f=()=>{if(!a)return;let w=kn(a.chunks.join("")),b=w[0]===137&&w[1]===80&&w[2]===78&&w[3]===71;(c??=new Map).set(Y(a.name),{name:a.name,bytes:w,...b?{mime:"image/png"}:{}}),a=null},h=new Map,g=!0,p=(w)=>{if(f(),o={name:Y(w),cmds:[]},s.set(o.name,o),!i)i=o.name;u=[],l=null,g=!0},m=!1,A=!1,x=()=>{if(A)return;A=!0,s.clear(),o=null,i=""},d=(w,b)=>{if(l){w.tex=l,l=null;return}let M=u[u.length-1];if(!M)return;if(M.fallback){if(!b)w.fallback=!0}else w.tex=M.map};for(let w of e.split(`\n`)){let b=w.trim();if(!b)continue;if(r&&b.charCodeAt(0)>=50&&b.charCodeAt(0)<=53&&(b.charCodeAt(1)===32||b.charCodeAt(1)===9)){if(a||m)continue;if(!o)p(t);let P=b.slice(2).trimStart(),D=P.search(/\\s/),y={t:b.charCodeAt(0)-48,color:nt(D<0?P:P.slice(0,D)),p:[],src:b};d(y,!1),o.cmds.push(y),g=!1;continue}if(b.charCodeAt(0)===48&&(b.charCodeAt(1)===32||b.charCodeAt(1)===9)){let P=2;while(b.charCodeAt(P)===32||b.charCodeAt(P)===9)P++;let D=P;while(D<b.length&&b.charCodeAt(D)!==32&&b.charCodeAt(D)!==9)D++;let y=b.slice(P,D),B=/[^\\x21-\\x7e]/.test(y)?b.slice(P).trim().split(/\\s+/)[0]:y;if(!xn.has(B)&&!(B.length>=4&&B.length<=6&&wn.has(B.toUpperCase()))){if(m||a)continue;if(!o)p(t);let C=b.slice(P),I={t:0,text:C};if(y.charCodeAt(0)===33)I.meta=y;if(l=null,g&&!o.org){let S=Mt(C);if(S)o.org=S}let R=C.match(At);if(R&&!o.movedTo){let S=R[1].trim().replace(/\\\\/g,"/");if(!/\\.(dat|ldr|mpd)$/i.test(S))S+=".dat";o.movedTo=Y(S)}o.cmds.push(I);continue}}if(b.charCodeAt(0)===49&&(b.charCodeAt(1)===32||b.charCodeAt(1)===9)&&!a&&!m){let P=Tn(b,h);if(P){if(!o)p(t);d(P,!1),o.cmds.push(P),g=!1;continue}}let M=b.split(/\\s+/);if(+M[0]===0){let P=b.slice(1).trim(),D=M.length>1&&M[1].length>=4&&M[1].length<=6?M[1].toUpperCase():M[1];if(D==="FILE"){let C=P.slice(5).trimStart().split("\\r")[0].trim();if(C){x(),m=!1,p(C);continue}}if(D==="NOFILE"){f(),o=null,m=!0;continue}if(D==="!DATA"){x(),f(),o=null,m=!1,a={name:P.slice(5).trim(),chunks:[]};continue}if(m)continue;if(a){if(M[1]==="!:")a.chunks.push(M.slice(2).join(""));continue}if(!o)p(t);let y={t:0,text:P};if(M[1]==="STEP")y.step=!0,u=[],l=null;else if(M[1]==="BFC")y.bfc=M.slice(2).join(" ");else if(M[1]==="ROTSTEP")if(y.meta="ROTSTEP",y.step=!0,u=[],l=null,(M[2]??"").toUpperCase()==="END")y.rotstep={x:0,y:0,z:0,mode:"END"};else{let C=(M[5]??"REL").toUpperCase(),I=(R)=>{let S=Number(R);return Number.isFinite(S)?S:0};y.rotstep={x:I(M[2]),y:I(M[3]),z:I(M[4]),mode:["REL","ABS","ADD"].includes(C)?C:"REL"}}else if(M[1]==="BUFEXCHG"){y.meta="BUFEXCHG";let C=(M[2]??"").toUpperCase();y.bufexchg={op:C==="RETRIEVE"?"RETRIEVE":"STORE",buf:M[3]??"A"}}else if(M[1]?.startsWith("!"))y.meta=M[1];if(g&&!o.org){let C=Mt(P);if(C)o.org=C}if(M[1]==="!TEXMAP"){let C=(M[2]??"").toUpperCase();if(l=null,C==="START"||C==="NEXT"){let I=Cn(P.replace(/^!TEXMAP\\s+\\S+/i,""),C==="NEXT");if(y.texmap={op:C,...I?{map:I}:{}},I)if((o.texmaps??=[]).push(I),C==="START")u.push({map:I,fallback:!1});else l=I}else if(C==="FALLBACK"){y.texmap={op:C};let I=u[u.length-1];if(I)I.fallback=!0}else if(C==="END")y.texmap={op:C},u.pop()}else if(M[1]==="!:"){l=null;let C=vt(M.slice(2));if(C)d(C,!0),y.geom=C}else l=null;let B=P.match(At);if(B&&!o.movedTo){let C=B[1].trim().replace(/\\\\/g,"/");if(!/\\.(dat|ldr|mpd)$/i.test(C))C+=".dat";o.movedTo=Y(C)}o.cmds.push(y);continue}if(a||m)continue;if(!o)p(t);let N=vt(M);if(!N){if(/^[2-5][ \\t]/.test(b))g=!1;continue}d(N,!1),o.cmds.push(N),g=!1}return f(),c?{main:i,files:s,data:c}:{main:i,files:s}}var rr=Math.PI/180;function Ft(e,t){let n=(r)=>[t[3]*r[0]+t[4]*r[1]+t[5]*r[2]+t[0],t[6]*r[0]+t[7]*r[1]+t[8]*r[2]+t[1],t[9]*r[0]+t[10]*r[1]+t[11]*r[2]+t[2]];return{...e,p1:n(e.p1),p2:n(e.p2),p3:n(e.p3)}}function Rt(e,t){let[n,r,s,o,i,c,a,u,l,f,h,g]=e,[p,m,A,x,d,w,b,M,k,N,P,D]=t;return[o*p+i*m+c*A+n,a*p+u*m+l*A+r,f*p+h*m+g*A+s,o*x+i*b+c*N,o*d+i*M+c*P,o*w+i*k+c*D,a*x+u*b+l*N,a*d+u*M+l*P,a*w+u*k+l*D,f*x+h*b+g*N,f*d+h*M+g*P,f*w+h*k+g*D]}var rt=[0,0,0,1,0,0,0,1,0,0,0,1];var Ct=new WeakMap,Sn=/^(s|8|48)\\//;function st(e,t){let n=e.files.get(Y(t));if(!n)return"part";let r=Ct.get(n);if(r)return r;if(n.org)r=Pt.has(n.org)?"part":"model";else if(n.name===e.main)r="model";else r=n.cmds.some((s)=>s.t>=2||s.t===0&&!!s.geom||s.t===1&&Sn.test(s.file))?"part":"model";return Ct.set(n,r),r}var kt=new WeakMap;function Bt(e){let t=kt.get(e);if(t)return t;t=[];let n=0;for(let r of e.cmds){if(r.t===0&&r.step){n++;continue}if((r.t>=2||r.t===0&&r.geom&&r.geom.t>=2)&&t[t.length-1]!==n)t.push(n)}return kt.set(e,t),t}var Tt=(e)=>e>16777215?"0x"+e.toString(16).toUpperCase():e<0?qe.get(e)??String(e):String(e),En=(e)=>e.t===0?"0 "+e.text:e.t===1?`1 ${Tt(e.color)} ${e.m.join(" ")} ${e.file}`:e.src?e.src:`${e.t} ${Tt(e.color)} ${e.p.join(" ")}`,ot=(e,t)=>`${Y(e)}#${t}`;function Pn(e,t){let n=[],r=0,s=(o)=>!!o&&o.t===0&&o.texmap?.op==="NEXT";for(let o of e.cmds){if(o.t===0){if(o.step){r++;continue}if(o.bfc!==void 0||o.meta==="!COLOUR"){n.push(o);continue}if(r!==t)continue;if(o.texmap)n.push(o);else if(o.geom){if(o.geom.t>=2)n.push(o);else if(s(n[n.length-1]))n.pop()}continue}if(r!==t)continue;if(o.t===1){if(s(n[n.length-1]))n.pop();continue}n.push(o)}return{name:ot(e.name,t),cmds:n}}function Dt(e,t){return[`0 ldr: own geometry of ${e.name}, step ${t}`,...Pn(e,t).cmds.map(En)].join(`\n`)+`\n`}function it(e){let t=2166136261;for(let n=0;n<e.length;n++)t^=e.charCodeAt(n),t=Math.imul(t,16777619);return(t>>>0).toString(16).padStart(8,"0")}function Ut(e){let[t,n,r,s,o,i,c,a,u,l,f,h]=e,g=a*h-u*f,p=-(c*h-u*l),m=c*f-a*l,A=s*g+o*p+i*m;if(!Number.isFinite(A)||Math.abs(A)<0.000000000001)return null;let x=1/A,d=[g*x,-(o*h-i*f)*x,(o*u-i*a)*x,p*x,(s*h-i*l)*x,-(s*u-i*c)*x,m*x,-(s*f-o*l)*x,(s*a-o*c)*x];return[-(d[0]*t+d[1]*n+d[2]*r),-(d[3]*t+d[4]*n+d[5]*r),-(d[6]*t+d[7]*n+d[8]*r),...d]}var In=(e)=>String(+e.toFixed(6)||0),Lt=(e)=>\'"\'+e.replace(/\\\\/g,"\\\\\\\\").replace(/"/g,"\\\\\\"")+\'"\';function Nt(e,t){let n=[...t.p1,...t.p2,...t.p3,...t.method!=="PLANAR"?[t.a??360]:[],...t.method==="SPHERICAL"?[t.b??180]:[]].map(In).join(" "),r=`0 ldr: ${e} with a model-level !TEXMAP\n0 BFC CERTIFY CCW\n0 !TEXMAP START ${t.method} ${n} ${Lt(t.texture)}${t.glossmap?" GLOSSMAP "+Lt(t.glossmap):""}\n1 16 0 0 0 1 0 0 0 1 0 0 0 1 ${Y(e)}\n0 !TEXMAP END\n`;return{name:`${Y(e)}#tex-${it(r)}`,source:r}}var Fn=(e,t)=>{let n=[,,,,,,,,,];for(let r=0;r<3;r++)for(let s=0;s<3;s++)n[r*3+s]=e[r*3]*t[s]+e[r*3+1]*t[3+s]+e[r*3+2]*t[6+s];return n};function Rn(e,t,n){let r=Math.PI/180,s=Math.sin(e*r),o=Math.cos(e*r),i=Math.sin(t*r),c=Math.cos(t*r),a=Math.sin(n*r),u=Math.cos(n*r);return[c*u,-c*a,i,o*a+s*i*u,o*u-s*i*a,-s*c,s*a-o*i*u,s*u+o*i*a,o*c]}var St=new WeakMap;function Ot(e){let t=St.get(e);if(t)return t;let n=[],r=null;for(let s of e.cmds){if(s.t!==0||!s.step)continue;let o=s.rotstep;if(o)if(o.mode==="END")r=null;else{let i=Rn(o.x,o.y,o.z);r=o.mode==="ABS"?{abs:!0,m:i,rotstep:o}:o.mode==="ADD"&&r?{abs:r.abs,m:Fn(r.m,i),rotstep:o}:{abs:!1,m:i,rotstep:o}}n.push(r)}return n.push(r),St.set(e,n),n}class at extends Error{limit;code="ldr-model-limit";constructor(e,t){super(`ldr: ${e} expands past ${t.toLocaleString("en-US")} (see maxInstances)`);this.limit=t;this.name="ModelLimitError"}}var Bn=(e)=>{for(let t=0;t<12;t++)if(!(Math.abs(e[t])<=Et))return!1;return!0},zt=999999,Vt=(e)=>e.map((t)=>String(t).padStart(6,"0")).join(".")+"~",_t=new WeakMap,$t=new WeakMap;function Dn(e,t){let n=$t.get(t);if(!n)n={head:[...t.values()].map((o)=>{let i=_t.get(o)??"",c=i.indexOf("!COLOUR");return c<0?"":"0 "+i.slice(c).trim().replace(/\\s+/g," ")}).filter(Boolean).join(`\n`),parts:new Map},$t.set(t,n);let r=n.parts.get(e);if(!r){let s=Y(e),o=`0 ldr: ${s} placed in a model\'s !COLOUR scope\n0 BFC CERTIFY CCW\n${n.head}\n1 16 0 0 0 1 0 0 0 1 0 0 0 1 ${s}\n`;r={name:`${s}#col-${it(o)}`,source:o},n.parts.set(e,r)}return r}function Un(e,t={}){let n=[],r=t.maxDepth??64,s=t.looseGeometry!==!1,o=!!t.textures,i=!!t.callouts,c=new Map,a=0,u=new Set,l=t.maxInstances??2000000,f=0,h=(p,m)=>{let A=p.name+"#"+m,x=c.get(A);if(!x){let d;x=Object.assign(()=>d??=Dt(p,m),{file:p,step:m}),c.set(A,x)}return x},g=(p,m,A,x,d,w,b,M,k=null,N=[],P=[],D=void 0,y=null)=>{let B=p.files.get(m);if(!B||b>r||u.has(B))return;if(++f>l)throw new at("model",l);u.add(B);let C=y,I=0,R=b>0?++a:0,S=i&&R?[...N,R]:N,V=i&&R?[...P,A]:P,he=i&&!k?new Map:null,ce=-1,Me=0,re=(O,T,_,X,q,ee,J)=>{if(ce!==I)ce=I,Me=0;let L=he?.get(I+"|"+T);if(L)return L.n++,g(O,O===p?T:O.main,_,X,d+"/"+T,[...q,zt],b+1,ee,[...q,zt],S,V,J,C);let F=[...q,Me++],v=n.length;g(O,O===p?T:O.main,_,X,d+"/"+T,F,b+1,ee,k,S,V,J,C),he?.set(I+"|"+T,{n:1,from:v,to:n.length})},Te=Ot(B),be=s?Bt(B):[],ve=0,fe=(O,T,_,X,q,ee,J,L,F)=>{if(k)X=k;if(++f>l)throw new at("model",l);let v={part:O,color:T,m:_,step:X[0],steps:X,localStep:q,path:d};if(L)v.colour=L;if(R){if(v.sub=R,i)v.subPath=S,v.subMats=V}if(ee)v.embedded=!0;if(J){let E=Nt(O,J);v.texPart=E.name,v.texSource=E.source}else if(F){let E=Dn(O,F);v.colPart=E.name,v.colSource=E.source}let U=Te[q];if(U)v.view=U;return n.push(v),v},ke=(O)=>{while(ve<be.length&&be[ve]<=O){let T=be[ve++];fe(ot(B.name,T),x,A,[...w,T],T,!1,null,D,y).source=h(B,T)}};for(let O of B.cmds){if(O.t===0&&O.step){I++;continue}let T=O;if(T.t>=2||T.t===0&&T.geom&&T.geom.t>=2){ke(I);continue}if(T.t===0){if(T.meta==="!COLOUR"){let U=On(T.text);if(U&&U.code!==16&&U.code!==24)_t.set(U,T.text),(C=new Map(C??[])).set(U.code,U);continue}if(o&&T.geom?.t===1)T=T.geom;else continue}if(T.t!==1)continue;if(o&&T.fallback)continue;let _=Rt(A,T.m);if(!Bn(_))continue;let X=T.color===16?x:T.color,q=T.color===16?D:C?.get(T.color),ee=[...w,I],J=o?T.tex??M:null,L=J?Ut(T.m):null,F=J&&L?Ft(J,L):null;if(p.files.has(T.file)){if(st(p,T.file)==="model"){re(p,T.file,_,X,ee,F,q);continue}fe(T.file,X,_,ee,I,!0,F,q,C);continue}let v=t.resolveModel?.(T.file);if(v){re(v,T.file,_,X,ee,F,q);continue}fe(T.file,X,_,ee,I,!1,F,q,C)}if(ke(1/0),u.delete(B),he){for(let O of he.values())if(O.n>1)for(let T=O.from;T<O.to;T++)n[T].mult??=O.n}};if(st(e,e.main)==="part"){if(e.files.get(e.main))n.push({part:e.main,color:16,m:[...rt],step:0,steps:[0],localStep:0,path:e.main,embedded:!0});return n}return g(e,e.main,rt,16,e.main,[],0,null),n}function Gt(e,t="main.ldr",n){return Un(It(e,t,{geometryText:!0}),n)}var Nn=new Set(["CHROME","PEARLESCENT","RUBBER","MATTE_METALLIC","METAL","MATERIAL"]);function lt(e){if(!e)return null;if(e.startsWith("#")&&/^#[0-9A-Fa-f]{6}$/.test(e))return e.toUpperCase();if(/^0x[0-9A-Fa-f]{6}$/i.test(e))return("#"+e.slice(2)).toUpperCase();return null}function jt(e,t){let n={value:"#FFFFFF",fraction:0.5};while(t<e.length){let r=e[t].toUpperCase(),s=e[t+1];if(r==="VALUE"){let o=lt(s);if(o)n.value=o;t+=2}else if(r==="ALPHA")n.alpha=+s,t+=2;else if(r==="LUMINANCE")n.luminance=+s,t+=2;else if(r==="FRACTION")n.fraction=+s,t+=2;else if(r==="VFRACTION")n.vfraction=+s,t+=2;else if(r==="SIZE")n.size=+s,t+=2;else if(r==="MINSIZE")n.minsize=+s,t+=2;else if(r==="MAXSIZE")n.maxsize=+s,t+=2;else break}return{grain:n,next:t}}function On(e){let t=e.indexOf("!COLOUR");if(t<0)return null;let n=e.slice(t+7).trim().split(/\\s+/).filter(Boolean);if(n.length<2)return null;let r=n[0],s=NaN,o="#FF00FF",i="#333333",c=255,a=0,u={type:"default"},l=1;while(l<n.length){let f=n[l].toUpperCase(),h=n[l+1];if(f==="CODE")s=h!==void 0&&et.test(h)?tt(h):h!==void 0&&/^\\d+$/.test(h)?+h:NaN,l+=2;else if(f==="VALUE"){let g=lt(h);if(g)o=g;l+=2}else if(f==="EDGE")i=lt(h)??h,l+=2;else if(f==="ALPHA")c=+h,l+=2;else if(f==="LUMINANCE")a=+h,l+=2;else if(f==="CHROME")u={type:"chrome"},l+=1;else if(f==="PEARLESCENT")u={type:"pearlescent"},l+=1;else if(f==="RUBBER")u={type:"rubber"},l+=1;else if(f==="MATTE_METALLIC")u={type:"matte_metallic"},l+=1;else if(f==="METAL")u={type:"metal"},l+=1;else if(f==="MATERIAL"){let g=(n[l+1]||"").toUpperCase();if(g==="GLITTER"){let{grain:p,next:m}=jt(n,l+2);u={type:"glitter",material:p},l=m}else if(g==="SPECKLE"){let{grain:p,next:m}=jt(n,l+2);u={type:"speckle",material:p},l=m}else if(g==="FABRIC"){let p=(n[l+2]||"").toUpperCase(),m=["VELVET","CANVAS","STRING","FUR"].includes(p)?p.toLowerCase():void 0;u={type:"fabric",kind:m},l+=m?3:2}else l=n.length}else if(Nn.has(f))l+=1;else l+=1}if(Number.isNaN(s)||!o)return null;return{code:s,name:r,hex:o,edge:i,alpha:Number.isFinite(c)?c:255,luminance:Number.isFinite(a)?a:0,finish:u}}function zn(e){let t=Math.max(0,Math.min(1,(e.alpha??255)/255)),n=t<1,r=Math.max(0,Math.min(1,(e.luminance??0)/255)),s={opacity:t,transparent:n,depthWrite:!n,emissive:r,clearcoat:0,clearcoatRoughness:0,sheen:0,sheenRoughness:0};switch(e.finish?.type??"default"){case"chrome":return{...s,metalness:1,roughness:0,finish:"chrome"};case"pearlescent":return{...s,metalness:0.25,roughness:0.3,clearcoat:0.5,clearcoatRoughness:0.25,sheen:0.4,sheenRoughness:0.35,finish:"pearlescent"};case"rubber":return{...s,metalness:0,roughness:0.9,finish:"rubber"};case"matte_metallic":return{...s,metalness:0.4,roughness:0.8,finish:"matte_metallic"};case"metal":return{...s,metalness:0.85,roughness:0.2,finish:"metal"};case"glitter":{let i=e.finish.material,c=i.size??(i.minsize!=null&&i.maxsize!=null?(i.minsize+i.maxsize)/2:1);return{...s,metalness:0.35,roughness:0.25,clearcoat:1,clearcoatRoughness:0.08,particleHex:i.value,particleFraction:i.fraction,particleSize:c,finish:"glitter"}}case"speckle":{let i=e.finish.material,c=i.size??(i.minsize!=null&&i.maxsize!=null?(i.minsize+i.maxsize)/2:1);return{...s,metalness:0.2,roughness:0.55,particleHex:i.value,particleFraction:i.fraction,particleSize:c,finish:"speckle"}}case"fabric":return{...s,metalness:0,roughness:0.85,sheen:0.65,sheenRoughness:0.75,finish:"fabric"};default:return{...s,metalness:0,roughness:0.45,finish:"default"}}}function ct(e){let t=zn(e),n=!t.transparent?"op":t.opacity>=0.75?"a200":t.opacity>=0.4?"a128":`a${Math.round(t.opacity*255)}`,r=t.emissive>0?`L${Math.round(t.emissive*16)}`:"",s=`${t.finish}:${n}${r}`;if(t.particleHex)s+=`:${t.particleHex}:${(t.particleFraction??0).toFixed(2)}`;return s}function $n(e,t){let n=new Map,r=null,s=!1,o=!1;for(let i of e.split(/\\r?\\n/)){let c=/^\\s*0\\s+FILE\\s+(\\S[^\\r]*)/i.exec(i);if(c){if(!s)n.clear();s=!0,o=!1,r=[],n.set(Y(c[1]),r);continue}if(/^\\s*0\\s+(NOFILE|!DATA)(\\s|$)/i.test(i)){if(!s&&/!DATA/i.test(i))n.clear(),s=!0;r=null,o=!0;continue}if(!r){if(s||o)continue;r=[],n.set(Y(t),r)}let a=i.trim().replace(/\\s+/g," ");if(a)r.push(a)}return n}var jn=(e)=>{if(!e.startsWith("1 "))return null;let t=e.split(" ");return t.length>=15?Y(t.slice(14).join(" ")):null};function Vn(e){let t=2166136261,n=1523705862;for(let r=0;r<e.length;r++){let s=e.charCodeAt(r);t=Math.imul(t^s,16777619),n=Math.imul(n^s,16777629)^n>>>15}return(t>>>0).toString(16).padStart(8,"0")+(n>>>0).toString(16).padStart(8,"0")}function Wt(e,t,n="main.ldr"){let r=[...t],s=new Map;if(!r.length)return s;let o=$n(e,n);for(let i of r){let c=Y(i);if(!o.has(c)||s.has(c))continue;let a=new Set([c]),u=[c];while(u.length)for(let f of o.get(u.pop())){let h=jn(f);if(h&&o.has(h)&&!a.has(h))a.add(h),u.push(h)}let l=[c,...[...a].filter((f)=>f!==c).sort()].map((f)=>"0 FILE "+(f===c?"":f)+`\n`+o.get(f).join(`\n`)).join(`\n`);s.set(c,`emb/${Vn(l)}.dat`)}return s}var Xt=(e,t=0)=>Math.abs(e[t+7]-1)<0.001&&Math.abs(e[t+4])<0.001&&Math.abs(e[t+10])<0.001,Ht=new WeakMap,ut=null,ft="",pt=null;function mt(e,t){if(e===ut&&t===ft)return pt;let n=Ht.get(e);if(!n)Ht.set(e,n=new Map);let r=n.get(t);if(r!==void 0)return ut=e,ft=t,pt=r,r;let s=e.parts[t];if(!s)return n.set(t,null),null;let o=s.studs.length,i=new Float64Array(o*12),c=[],a=[];s.studs.forEach((g,p)=>{c.push(g[0]),a.push(g[1]);for(let m=0;m<12;m++)i[p*12+m]=g[2+m]});let u=null,l=0,f=0;if(s.mask){l=s.mask[0],f=s.mask[1];let g=s.mask[2];u=new Uint8Array(g.length);for(let p=0;p<g.length;p++)u[p]=g.charCodeAt(p)===49?1:0}let h=!!u;if(u){for(let g=0;g<u.length;g++)if(u[g]!==1){h=!1;break}}return n.set(t,r={nStuds:o,studM:i,kind:c,color:a,mask:u,nx:l,nz:f,full:h}),ut=e,ft=t,pt=r,r}var Pe=1073741824;class Ee{t;tag;mask;size=0;shift;constructor(e=1024,t=-1){let n=1024;while(n<e*2)n*=2;this.t=new Int32Array(n*4),this.tag=new Uint8Array(n),this.mask=n-1,this.shift=t}slot(e,t,n){let r=this.shift;if(r<0){let o=Math.imul(e,2654435761)^Math.imul(t,2246822507)^Math.imul(n,3266489909);return o^=o>>>15,o=Math.imul(o,739982445),o^=o>>>12,o&this.mask}let s=Math.imul(e>>r+2,2654435761)^Math.imul(t,2246822507)^Math.imul(n>>r+2,3266489909);return s^=s>>>15,s=Math.imul(s,739982445),s^=s>>>12,(s<<4|(e>>r&3)<<2|n>>r&3)&this.mask}static tagOf(e,t,n){return Math.imul(e^Math.imul(t,374761393)^Math.imul(n,668265261),2654435761)>>>24|1}get(e,t,n){let r=Ee.tagOf(e,t,n),s=this.tag,o=this.t,i=this.mask,c=this.slot(e,t,n);for(;;){let a=s[c];if(a===0)return-1;if(a===r){let u=c<<2;if(o[u]===e&&o[u+1]===t&&o[u+2]===n)return o[u+3]}c=c+1&i}}put(e,t,n,r){if((this.size+1)*2>this.tag.length)this.grow();let s=Ee.tagOf(e,t,n),o=this.tag,i=this.t,c=this.mask,a=this.slot(e,t,n);for(;;){let u=o[a],l=a<<2;if(u===0)return o[a]=s,i[l]=e,i[l+1]=t,i[l+2]=n,i[l+3]=r,this.size++,-1;if(u===s&&i[l]===e&&i[l+1]===t&&i[l+2]===n){let f=i[l+3];return i[l+3]=r,f}a=a+1&c}}grow(){let e=this.t,t=this.tag,n=t.length*2;this.t=new Int32Array(n*4),this.tag=new Uint8Array(n),this.mask=n-1,this.size=0;for(let r=0;r<t.length;r++)if(t[r]){let s=r<<2;this.put(e[s],e[s+1],e[s+2],e[s+3])}}}class Zt{grp=new Ee(64);gBits=[];gX0=[];gZ0=[];gNz=[];gNx=[];bits;rest;lk=NaN;lpx=NaN;lpz=NaN;lg=-1;group(e,t,n){if(e!==this.lk||t!==this.lpx||n!==this.lpz)this.lk=e,this.lpx=t,this.lpz=n,this.lg=this.grp.get(e,t,n);return this.lg}constructor(e,t,n,r){let s=[],o=[],i=[],c=[],a=[];for(let f=0;f<r;f++){let h=e[f],g=t[f],p=n[f],m=(h%20+20)%20,A=(p%20+20)%20,x=this.group(g,m,A);if(x<0)x=s.length,this.grp.put(g,m,A,x),this.lg=x,s.push(0),o.push(h),i.push(h),c.push(p),a.push(p);if(s[x]++,h<o[x])o[x]=h;else if(h>i[x])i[x]=h;if(p<c[x])c[x]=p;else if(p>a[x])a[x]=p}let u=0,l=0;for(let f=0;f<s.length;f++){let h=(i[f]-o[f])/20+1,g=(a[f]-c[f])/20+1,p=h*g;if(this.gX0.push(o[f]),this.gZ0.push(c[f]),this.gNx.push(h),this.gNz.push(g),p<=64*s[f]+1024&&u+p<2147483648)this.gBits.push(u),u+=p;else this.gBits.push(-1),l+=s[f]}this.bits=new Uint8Array(Math.ceil(u/8)),this.rest=new Ee(l);for(let f=0;f<r;f++){let h=e[f],g=t[f],p=n[f],m=this.group(g,(h%20+20)%20,(p%20+20)%20),A=this.gBits[m];if(A<0){this.rest.put(h,g,p,1);continue}let x=A+(h-this.gX0[m])/20*this.gNz[m]+(p-this.gZ0[m])/20;this.bits[x>>>3]|=1<<(x&7)}}has(e,t,n){let r=this.group(t,(e%20+20)%20,(n%20+20)%20);if(r<0)return!1;let s=this.gBits[r];if(s<0)return this.rest.get(e,t,n)>=0;let o=(e-this.gX0[r])/20,i=(n-this.gZ0[r])/20;if(o<0||i<0||o>=this.gNx[r]||i>=this.gNz[r])return!1;let c=s+o*this.gNz[r]+i;return(this.bits[c>>>3]&1<<(c&7))!==0}}var _n=(e,t,n,r)=>e===0&&r===0&&(t===1||t===-1)&&(n===1||n===-1)||t===0&&n===0&&(e===1||e===-1)&&(r===1||r===-1),Ie=(e,t,n)=>e>-Pe&&e<Pe&&t>-Pe&&t<Pe&&n>-Pe&&n<Pe,De=2147483647;function Gn(e,t){let n=e.colorTable?.[t];if(n)return(n.alpha??255)<255;return t.charCodeAt(0)===35&&/\\/[^:/]*:a\\d/.test(t)}function Wn(e,t,n){return Kt(e,t,n,-1)??Kt(e,t,n,Yt)}var Yt=0;function Kt(e,t,n,r){let o=new Map,i=(L)=>{let F=o.get(L);if(F===void 0)o.set(L,F=Gn(t,L));return F},c=e.length,a=0,u=0;for(let L=0,F="";L<c;L++){let v=e[L].part;if(v===F){a++;continue}let U=t.parts[v];if(U&&U.mask)a++,F=v}let l=new Float64Array(a),f=new Float64Array(a),h=new Float64Array(a),g=new Float64Array(a),p=new Int32Array(a),m=new Int32Array(a),A=new Float64Array(a),x=new Float64Array(a),d=[],w=new Int32Array(a),b=new Float64Array(a*9),M=new Uint8Array(a);if(r<0)r=a*4+64;let k=new Ee(e.length*2),N=new Int32Array(r),P=new Int32Array(r),D=0,y=0;for(let L=0;L<e.length;L++){let F=e[L],v=F.m,U=t.parts[F.part];if(!U||!U.mask||!Xt(v)||i(F.color))continue;let E=U.bbox,z=1/0,j=-1/0,te=1/0,H=-1/0;for(let K=0;K<2;K++)for(let le=0;le<2;le++){let ne=K?E[3]:E[0],Le=le?E[5]:E[2],Ae=v[0]+v[3]*ne+v[5]*Le,de=v[2]+v[9]*ne+v[11]*Le;if(Ae<z)z=Ae;if(Ae>j)j=Ae;if(de<te)te=de;if(de>H)H=de}let G=Math.round((v[1]+E[4])*2),Q=mt(t,F.part),ue=Math.floor(z/40),ye=Math.floor(j/40),xe=Math.floor(te/40),we=Math.floor(H/40);if(!((ye-ue+1)*(we-xe+1)<=65536)||!Ie(G,ue,xe)||!Ie(G,ye,we))continue;let ge=Math.floor((z+5)/40),se=Math.floor((j-5)/40),oe=Math.floor((te+5)/40),ie=Math.floor((H-5)/40),Ce=ge<=se&&oe<=ie?(se-ge+1)*(ie-oe+1):0;y+=Ce;let pe=-1;for(let K=ge<=se&&oe<=ie?k.get(G,ge,oe):-1,le=0;K>=0&&le<8;K=N[K],le++){let ne=P[K];if(l[ne]!==z||f[ne]!==j||h[ne]!==te||g[ne]!==H||d[ne]!==Q)continue;let Le=e[p[ne]].m,Ae=!0;for(let de=0;de<12;de++)if(Le[de]!==v[de]){Ae=!1;break}if(Ae){pe=ne;break}}if(pe>=0){let K=n?n[L]:0;if(n&&K<n[p[pe]])m[pe]=p[pe],p[pe]=L;else if(m[pe]<0||n&&K<n[m[pe]])m[pe]=L;continue}let ae=u++;l[ae]=z,f[ae]=j,h[ae]=te,g[ae]=H,p[ae]=L,m[ae]=-1,d.push(Q),A[ae]=E[0],x[ae]=E[2],w[ae]=G;let me=ae*9;if(b[me]=v[0],b[me+1]=v[1],b[me+2]=v[2],b[me+3]=v[3],b[me+4]=v[6],b[me+5]=v[9],b[me+6]=v[5],b[me+7]=v[8],b[me+8]=v[11],M[ae]=Q.full&&E[3]-E[0]<=20*Q.nx&&E[5]-E[2]<=20*Q.nz&&v[4]===0&&v[6]===0&&v[8]===0&&v[10]===0&&_n(v[3],v[5],v[9],v[11])?1:0,D+Ce>r){D=r+1;continue}for(let K=ge;K<=se;K++)for(let le=oe;le<=ie;le++){if(!Ie(G,K,le))continue;let ne=D++;P[ne]=ae,N[ne]=k.put(G,K,le,ne)}}if(D>r)return Yt=y,null;let B=[0,5,-5,5,-5],C=[0,5,5,-5,-5],I=(L,F,v,U)=>{if(!(F-6>=l[L]-0.5&&F+6<=f[L]+0.5&&U-6>=h[L]-0.5&&U+6<=g[L]+0.5))return!1;if(M[L]===1)return!0;let E=L*9,z=d[L],j=A[L],te=x[L],H=F-b[E],G=v-b[E+1],Q=U-b[E+2],ue=b[E+3]*H+b[E+4]*G+b[E+5]*Q,ye=b[E+6]*H+b[E+7]*G+b[E+8]*Q,{nx:xe,nz:we,mask:ge}=z;for(let se=0;se<5;se++){let oe=Math.floor((ue+B[se]-j)/20),ie=Math.floor((ye+C[se]-te)/20);if(oe<0||ie<0||oe>=xe||ie>=we||ge[oe*we+ie]!==1)return!1}return!0},R=NaN,S=NaN,V=NaN,he=-1,ce=-1,Me=(L,F,v,U)=>{let E=Math.round(F*2),z=Math.floor(L/40),j=Math.floor(v/40);if(!Ie(E,z,j))return De;let te=De;if(!n&&ce>=0&&w[ce]===E&&(p[ce]!==U||m[ce]>=0)&&I(ce,L,F,v))return 0;if(E!==R||z!==S||j!==V)R=E,S=z,V=j,he=k.get(E,z,j);for(let H=he;H>=0;H=N[H]){let G=P[H],Q=p[G];if(Q===U&&(Q=m[G])<0)continue;if(!I(G,L,F,v))continue;if(!n)return ce=G,0;let ue=n[Q];if(ue<te)te=ue}return te},re=0;for(let L of e){let F=mt(t,L.part);if(F)re+=F.nStuds}let Te=new Uint8Array(re),be=new Uint8Array(re),ve=0,fe=n?new Ee(re,4):null,ke=n?null:new Int32Array(re),O=n?null:new Int32Array(re),T=n?null:new Int32Array(re),_=0,X=n?new Int32Array(re).fill(De):void 0;for(let L=0,F=0;L<e.length;L++){let v=e[L],U=mt(t,v.part);if(!U)continue;let E=v.m,z=U.studM,j=E[0],te=E[1],H=E[2],G=E[3],Q=E[4],ue=E[5],ye=E[6],xe=E[7],we=E[8],ge=E[9],se=E[10],oe=E[11];for(let ie=0;ie<U.nStuds;ie++,F++){let Ce=ie*12,pe=z[Ce+4],ae=z[Ce+7],me=z[Ce+10];if(!(Math.abs(ye*pe+xe*ae+we*me-1)<0.001&&Math.abs(G*pe+Q*ae+ue*me)<0.001&&Math.abs(ge*pe+se*ae+oe*me)<0.001))continue;be[F]=1;let K=z[Ce],le=z[Ce+1],ne=z[Ce+2],Le=j+G*K+Q*le+ue*ne,Ae=te+ye*K+xe*le+we*ne,de=H+ge*K+se*le+oe*ne,ht=Me(Le,Ae,de,L);if(ht!==De){if(Te[F]=1,ve++,X)X[F]=ht}let Ue=Math.round(Le),Ne=Math.round(Ae),Oe=Math.round(de);if(!Ie(Ue,Ne,Oe))continue;if(!fe){ke[_]=Ue,O[_]=Ne,T[_++]=Oe;continue}let gt=n[L],dt=fe.get(Ue,Ne,Oe);if(dt<0||gt<dt)fe.put(Ue,Ne,Oe,gt)}}let q=fe?null:new Zt(ke,O,T,_),ee=new Uint8Array(e.length),J=n?new Int32Array(e.length).fill(De):void 0;for(let L=0;L<e.length;L++){let F=e[L],v=t.parts[F.part];if(!v||!v.under||!Xt(F.m)||i(F.color))continue;let U=v.bbox,E=Math.round((U[3]-U[0])/20),z=Math.round((U[5]-U[2])/20);if(!E||!z||E*z>4096)continue;let j=F.m,te=Math.round(j[1]+U[4]),H=!0,G=0;for(let Q=0;Q<E&&H;Q++)for(let ue=0;ue<z;ue++){let ye=U[0]+10+20*Q,xe=U[2]+10+20*ue,we=j[0]+j[3]*ye+j[5]*xe,ge=j[2]+j[9]*ye+j[11]*xe,se=Math.round(we),oe=Math.round(ge),ie=!Ie(se,te,oe)?-1:fe?fe.get(se,te,oe):q.has(se,te,oe)?1:-1;if(ie<0){H=!1;break}if(ie>G)G=ie}if(H){if(ee[L]=1,J)J[L]=G}}return{nStuds:re,studHidden:Te,studUp:be,underHidden:ee,studsHidden:ve,studHideStep:X,underHideStep:J}}function Xn(e,t,n){let r=(l)=>l.colPart&&t.parts[l.colPart]?l.colPart:n&&l.texPart&&t.parts[l.texPart]?l.texPart:l.part,s=new Map,o=new Map,i=(l)=>{let f=l.colour;if(!f)return String(l.color);let h=o.get(f);if(h!==void 0)return h;let g=t.colorTable?.[l.color],p=g?.hex??t.colors?.[l.color],m=g?ct({alpha:g.alpha??255,luminance:g.luminance??0,finish:g.finish??{type:"default"}}):"default:op",A=ct(f);if(h=p&&p.toUpperCase()===f.hex.toUpperCase()&&m===A?String(l.color):f.hex.toUpperCase()+"/"+A,h!==String(l.color))s.set(h,f);return o.set(f,h),h},c=e.map((l)=>({part:r(l),color:i(l),m:l.m,steps:l.steps})),{stepOf:a,nSteps:u}=Hn(c);return{all:c,stepOf:a,nSteps:u,localColours:s}}function Hn(e){let t=!0;for(let o=0;o<e.length;o++){let i=e[o].steps;if(i.length!==1){t=!1;break}let c=i[0];if(!(Number.isInteger(c)&&c>=0&&c<1e6)){t=!1;break}}if(t){let o=new Set;for(let a=0;a<e.length;a++)o.add(e[a].steps[0]);let i=[...o].sort((a,u)=>a-u),c=new Map(i.map((a,u)=>[a,u]));return{stepOf:e.map((a)=>c.get(a.steps[0])),nSteps:i.length}}let n=e.map((o)=>Vt(o.steps)),r=[...new Set(n)].sort(),s=new Map(r.map((o,i)=>[o,i]));return{stepOf:n.map((o)=>s.get(o)),nSteps:r.length}}function _e(e,t,n=!0){let r=Xn(e,t,n);return Wn(r.all,t,r.nSteps>1?r.stepOf:void 0)}var Ke="https://ldr-demo.vercel.app/cdn/v1/",We=new Map,Ge=new Map;function Xe(e=Ke,t=fetch){let n=We.get(e);if(!n)n=t(e+"parts.json").then((r)=>{if(!r.ok)throw Error(`ldr: parts CDN index ${r.status} (${e}parts.json)`);return r.json()}),n.catch(()=>We.delete(e)),We.set(e,n);return n}var Kn=(e)=>Array.isArray(e)&&e.length===3&&typeof e[0]==="number"&&typeof e[1]==="number"&&(e[2]==="f32"||e[2]==="u16"||e[2]==="u8"||e[2]==="u32"),He=(e,t)=>Kn(e)?[e[0]+t,e[1],e[2]]:Array.isArray(e)?e.map((n)=>He(n,t)):e&&typeof e==="object"?Object.fromEntries(Object.entries(e).map(([n,r])=>[n,He(r,t)])):e;function Zn(e,t={}){let n=[],r=0,s={},o={};for(let h of e){let g=h.buffer;if(!g)throw Error("ldr: mergePacks needs packs from decodePack/loadPack");let p=new DataView(g).getUint32(0,!0),m=new Uint8Array(g,4+p),A=r;n.push(m),r+=m.byteLength;let x=(4-r%4)%4;if(x)n.push(new Uint8Array(x)),r+=x;for(let[d,w]of Object.entries(h.header.parts??{}))if(!(d in s))s[d]=He(w,A);for(let[d,w]of Object.entries(h.header.studKinds??{}))if(!(d in o))o[d]=He(w,A)}let i=e[0]?.header??{version:1,weld:!0},c=new TextEncoder().encode(JSON.stringify({...i,parts:s,studKinds:o,...t})),a=(4-(4+c.length)%4)%4,u=4+c.length+a,l=new Uint8Array(u+r);new DataView(l.buffer).setUint32(0,c.length+a,!0),l.set(c,4),l.fill(32,4+c.length,u);let f=u;for(let h of n)l.set(h,f),f+=h.byteLength;return Ve(l.buffer)}async function Yn(e,t={}){e=[...e];try{return await Jt(e,t)}catch(n){let r=t.cdn??Ke,s=t.fetch??fetch;We.delete(r);let o=(i,c)=>s(i,{...c,cache:"reload"});try{return await Jt(e,{...t,fetch:o})}catch{throw n}}}async function Jt(e,t){let n=t.cdn??Ke,r=t.fetch??fetch,s=t.gap??16384,o=await Xe(n,r),i=[...new Set([...new Set(e)].map(Y))],c=[],a=[];for(let d of i){if(Ge.has(n+d))continue;let w=o.parts[d];if(w)a.push({name:d,off:w[0],len:w[1],file:w[2]??0});else c.push(d)}a.sort((d,w)=>d.file-w.file||d.off-w.off);let u=[];for(let d of a){let w=u[u.length-1];if(w&&w.file===d.file&&d.off-w.end<=s)w.end=Math.max(w.end,d.off+d.len),w.items.push(d);else u.push({file:d.file,start:d.off,end:d.off+d.len,items:[d]})}let l=0,f=0,h=0,g=new Map,p=async()=>{while(h<u.length){let d=u[h++],w=g.get(d.file);if(w)w=w.subarray(d.start,d.end);else{let b=await r(new URL(o.archives[d.file],n).href,{headers:{Range:`bytes=${d.start}-${d.end-1}`,"Accept-Encoding":"identity"}});if(!b.ok)throw Error(`ldr: parts CDN ${b.status}`);if(f++,w=new Uint8Array(await b.arrayBuffer()),l+=w.byteLength,b.status===200)g.set(d.file,w),w=w.subarray(d.start,d.end)}for(let b of d.items){let M=je(w.subarray(b.off-d.start,b.off-d.start+b.len)),k=M.buffer.slice(M.byteOffset,M.byteOffset+M.byteLength);Ge.set(n+b.name,Ve(k))}}};await Promise.all(Array.from({length:Math.min(t.concurrency??24,u.length)},p));let m=i.filter((d)=>Ge.has(n+d)).map((d)=>Ge.get(n+d)),A={colors:o.colors,...o.colorTable?{colorTable:o.colorTable}:{}};return{pack:m.length?Zn(m,A):Ve(Jn(A)),missing:c,requests:f,bytes:l}}function Jn(e){let t=new TextEncoder().encode(JSON.stringify({version:1,weld:!0,parts:{},studKinds:{},...e})),n=(4-(4+t.length)%4)%4,r=new Uint8Array(4+t.length+n).fill(32);return new DataView(r.buffer).setUint32(0,t.length+n,!0),r.set(t,4),r.buffer}function Qn(e,t){let n=t.header.parts;if(!n)return 0;let r=0;for(let s of e){let o=n[s.part]?.body?.tris;if(o)r+=o}return r}function Qt(e,t,n){let r=0,s=0,o=!1,i=new Set,c=new Map;for(let a of e){let u;if(a.embedded)u=t.get(a.part);else if(u=c.get(a.part),u===void 0)c.set(a.part,u=Y(a.part));let l=u?n.parts[u]:void 0;if(!l)continue;if(l[3]!=null)o=!0,r+=l[3];if(!i.has(u))i.add(u),s+=l[1]}return{bodyTris:r,packBytes:s,known:o}}class Ze extends Error{code="ldr-budget";bodyTris;packBytes;maxBodyTris;maxPackBytes;constructor(e){let t=[e.maxBodyTris!=null&&e.bodyTris>e.maxBodyTris?`${e.bodyTris} triangles (limit ${e.maxBodyTris})`:"",e.maxPackBytes!=null&&e.packBytes>e.maxPackBytes?`${(e.packBytes/1e6).toFixed(1)} MB parts pack (limit ${(e.maxPackBytes/1e6).toFixed(0)} MB)`:""].filter(Boolean).join(", ");super(`ldr: model exceeds device budget: ${t}`);this.name="BudgetError",this.bodyTris=e.bodyTris,this.packBytes=e.packBytes,this.maxBodyTris=e.maxBodyTris,this.maxPackBytes=e.maxPackBytes}}async function qt(e,t={}){let n=performance.now(),r=t.fetch??fetch,s=Xe(t.cdn??Ke,r);s.catch(()=>{});let o=t.text?e:await r(e).then(async(y)=>{if(!y.ok)throw Error(`ldr: ${y.status} fetching ${e}`);return xt(await y.arrayBuffer())}),i=performance.now(),c=t.name??(t.text?"main.ldr":wt(e)),a=Gt(o,c,{looseGeometry:!1,callouts:t.callouts}),u=performance.now();t.onParsed?.(a),await s;let l=Wt(o,new Set(a.filter((y)=>y.embedded).map((y)=>y.part)),c),f=(y,B)=>t.maxBodyTris!=null&&y>t.maxBodyTris||t.maxPackBytes!=null&&B>t.maxPackBytes,h=t.maxBodyTris!=null||t.maxPackBytes!=null,g=(y)=>new Ze({...y,maxBodyTris:t.maxBodyTris,maxPackBytes:t.maxPackBytes}),p="full";if(h){let y=Qt(a,l,await s);if(f(y.known?y.bodyTris:0,y.packBytes)){if(!t.lowCdn)throw g(y);let B=await Xe(t.lowCdn,r).catch(()=>null);if(!B)throw g(y);let C=Qt(a,l,B);if(f(C.known?C.bodyTris:0,C.packBytes))throw g(C);p="low"}}let m=[...a.filter((y)=>!y.embedded).map((y)=>y.part),...l.values()],A=async()=>{let y=await Yn(m,p==="low"?{...t,cdn:t.lowCdn}:t);for(let[B,C]of l){let I=y.pack.header.parts[C];if(I)y.pack.header.parts[B]=I}return{...y,packBytes:y.pack.buffer?.byteLength??y.pack.bytes??0,bodyTris:Qn(a,y.pack)}},x=await A();if(h&&f(x.bodyTris,x.packBytes)&&p==="full"&&t.lowCdn&&await Xe(t.lowCdn,r).then(()=>!0,()=>!1)){p="low";let y=x;x=await A(),x.requests+=y.requests,x.bytes+=y.bytes}if(h&&f(x.bodyTris,x.packBytes))throw g(x);let{pack:d,missing:w,requests:b,bytes:M}=x,k=new Map([...l].map(([y,B])=>[B,y])),N=w.map((y)=>k.get(y)??y),P=performance.now(),D=t.cull?_e(a,d.header,t.textures!==!1):void 0;return{insts:a,pack:d,tier:p,missing:N,requests:b,bytes:M,cull:D,timings:{fetchModel:i-n,parse:u-i,parts:P-u,...D?{cull:performance.now()-P}:{}}}}var qn=new Set(["part","color","m","step","steps","localStep","path"]);function en(e){let t=e.length,n=0;for(let p of e){if(typeof p.part!=="string"||typeof p.path!=="string"||typeof p.color!=="number"||typeof p.step!=="number"||typeof p.localStep!=="number"||!Array.isArray(p.m)||p.m.length!==12||!Array.isArray(p.steps))return null;n+=p.steps.length}let r=[],s=new Map,o=(p)=>{let m=s.get(p);if(m===void 0)s.set(p,m=r.length),r.push(p);return m},i=new Uint32Array(t),c=new Uint32Array(t),a=new Float64Array(t*3),u=new Float64Array(t*12),l=new Uint32Array(t+1),f=new Float64Array(n),h=[],g=0;for(let p=0;p<t;p++){let m=e[p];i[p]=o(m.part),c[p]=o(m.path),a[p*3]=m.color,a[p*3+1]=m.step,a[p*3+2]=m.localStep;let A=m.m,x=p*12;for(let b=0;b<12;b++)u[x+b]=A[b];let d=m.steps;for(let b=0;b<d.length;b++)f[g++]=d[b];l[p+1]=g;let w=null;for(let b in m)if(!qn.has(b))(w??={})[b]=m[b];if(w)h.push([p,w])}return{n:t,strs:r,part:i,path:c,num:a,m:u,so:l,steps:f,extra:h}}var tn=(e)=>[e.part.buffer,e.path.buffer,e.num.buffer,e.m.buffer,e.so.buffer,e.steps.buffer];self.onmessage=async(e)=>{let{id:t,source:n,opts:r}=e.data;try{let s=await qt(n,{...r,cull:!1,onParsed:(l)=>{let f=en(l);if(f)self.postMessage({id:t,packed:f},tn(f));else self.postMessage({id:t,insts:l})}}),o=s.pack.buffer;if(self.postMessage({id:t,buffer:o,tier:s.tier,missing:s.missing,requests:s.requests,bytes:s.bytes,timings:s.timings},[o]),!r.cull)return;let i=performance.now(),c=_e(s.insts,s.pack.header,r.textures!==!1),a=performance.now()-i,u=[];for(let l of[c.studHidden,c.studUp,c.underHidden,c.studHideStep,c.underHideStep])if(l)u.push(l.buffer);self.postMessage({id:t,cull:c,ms:a},u)}catch(s){if(s instanceof Ze||s?.code==="ldr-budget")self.postMessage({id:t,phase:"error",error:String(s?.message??s),budget:{bodyTris:s.bodyTris,packBytes:s.packBytes,maxBodyTris:s.maxBodyTris,maxPackBytes:s.maxPackBytes}});else self.postMessage({id:t,phase:"error",error:String(s?.message??s)})}};\n';
|
|
5636
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/load-worker.gen.ts
|
|
5637
|
+
var load_worker_gen_default = 'var sn=ArrayBuffer,H=Uint8Array,$e=Uint16Array,on=Int16Array;var je=Int32Array,Ye=function(e,t,n){if(H.prototype.slice)return H.prototype.slice.call(e,t,n);if(t==null||t<0)t=0;if(n==null||n>e.length)n=e.length;var r=new H(n-t);return r.set(e.subarray(t,n)),r},Be=function(e,t,n,r){if(H.prototype.fill)return H.prototype.fill.call(e,t,n,r);if(n==null||n<0)n=0;if(r==null||r>e.length)r=e.length;for(;n<r;++n)e[n]=t;return e},an=function(e,t,n,r){if(H.prototype.copyWithin)return H.prototype.copyWithin.call(e,t,n,r);if(n==null||n<0)n=0;if(r==null||r>e.length)r=e.length;while(n<r)e[t++]=e[n++]};var ln=["invalid zstd data","window size too large (>2046MB)","invalid block type","FSE accuracy too high","match distance too far back","unexpected EOF"],Z=function(e,t,n){var r=Error(t||ln[e]);if(r.code=e,Error.captureStackTrace)Error.captureStackTrace(r,Z);if(!n)throw r;return r},yt=function(e,t,n){var r=0,s=0;for(;r<n;++r)s|=e[t++]<<(r<<3);return s},cn=function(e,t){return(e[t]|e[t+1]<<8|e[t+2]<<16|e[t+3]<<24)>>>0},un=function(e,t){var n=e[0]|e[1]<<8|e[2]<<16;if(n==3126568&&e[3]==253){var r=e[4],s=r>>5&1,o=r>>2&1,i=r&3,c=r>>6;if(r&8)Z(0);var a=6-s,u=i==3?4:i,l=yt(e,a,u);a+=u;var f=c?1<<c:s,h=yt(e,a,f)+(c==1&&256),g=h;if(!s){var p=1<<10+(e[5]>>3);g=p+(p>>3)*(e[5]&7)}if(g>2145386496)Z(1);var m=new H((t==1?h||g:t?0:g)+12);return m[0]=1,m[4]=4,m[8]=8,{b:a+f,y:0,l:0,d:l,w:t&&t!=1?t:m.subarray(12),e:g,o:new je(m.buffer,0,3),u:h,c:o,m:Math.min(131072,g)}}else if((n>>4|e[3]<<20)==25481893)return cn(e,4)+8;Z(0)},Se=function(e){var t=0;for(;1<<t<=e;++t);return t-1},De=function(e,t,n){var r=(t<<3)+4,s=(e[t]&15)+5;if(s>n)Z(3);var o=1<<s,i=o,c=-1,a=-1,u=-1,l=o,f=new sn(512+(o<<2)),h=new on(f,0,256),g=new $e(f,0,256),p=new $e(f,512,o),m=512+(o<<1),A=new H(f,m,o),b=new H(f,m+o);while(c<255&&i>0){var d=Se(i+1),x=r>>3,w=(1<<d+1)-1,v=(e[x]|e[x+1]<<8|e[x+2]<<16)>>(r&7)&w,M=(1<<d)-1,U=w-i-1,S=v&M;if(S<U)r+=d,v=S;else if(r+=d+1,v>M)v-=U;if(h[++c]=--v,v==-1)i+=v,A[--l]=c;else i-=v;if(!v)do{var D=r>>3;a=(e[D]|e[D+1]<<8)>>(r&7)&3,r+=2,c+=a}while(a==3)}if(c>255||i)Z(0);var y=0,R=(o>>1)+(o>>3)+3,C=o-1;for(var F=0;F<=c;++F){var B=h[F];if(B<1){g[F]=-B;continue}for(u=0;u<B;++u){A[y]=F;do y=y+R&C;while(y>=l)}}if(y)Z(0);for(u=0;u<o;++u){var L=g[A[u]]++,V=b[u]=s-Se(L);p[u]=(L<<V)-o}return[r+7>>3,{b:s,s:A,n:b,t:p}]},fn=function(e,t){var n=0,r=-1,s=new H(292),o=e[t],i=s.subarray(0,256),c=s.subarray(256,268),a=new $e(s.buffer,268);if(o<128){var u=De(e,t+1,6),l=u[0],f=u[1];t+=o;var h=l<<3,g=e[t];if(!g)Z(0);var p=0,m=0,A=f.b,b=A,d=(++t<<3)-8+Se(g);for(;;){if(d-=A,d<h)break;var x=d>>3;if(p+=(e[x]|e[x+1]<<8)>>(d&7)&(1<<A)-1,i[++r]=f.s[p],d-=b,d<h)break;x=d>>3,m+=(e[x]|e[x+1]<<8)>>(d&7)&(1<<b)-1,i[++r]=f.s[m],A=f.n[p],p=f.t[p],b=f.n[m],m=f.t[m]}if(++r>255)Z(0)}else{r=o-127;for(;n<r;n+=2){var w=e[++t];i[n]=w>>4,i[n+1]=w&15}++t}var v=0;for(n=0;n<r;++n){var M=i[n];if(M>11)Z(0);v+=M&&1<<M-1}var U=Se(v)+1,S=1<<U,D=S-v;if(D&D-1)Z(0);i[r++]=Se(D)+1;for(n=0;n<r;++n){var M=i[n];++c[i[n]=M&&U+1-M]}var y=new H(S<<1),R=y.subarray(0,S),C=y.subarray(S);a[U]=0;for(n=U;n>0;--n){var F=a[n];Be(C,n,F,a[n-1]=F+c[n]*(1<<U-n))}if(a[0]!=S)Z(0);for(n=0;n<r;++n){var B=i[n];if(B){var L=a[B];Be(R,n,L,a[B]=L+(1<<U-B))}}return[t,{n:C,b:U,s:R}]},pn=De(new H([81,16,99,140,49,198,24,99,12,33,196,24,99,102,102,134,70,146,4]),0,6)[1],mn=De(new H([33,20,196,24,99,140,33,132,16,66,8,33,132,16,66,8,33,68,68,68,68,68,68,68,68,36,9]),0,6)[1],hn=De(new H([32,132,16,66,102,70,68,68,68,68,36,73,2]),0,5)[1],xt=function(e,t){var n=e.length,r=new je(n);for(var s=0;s<n;++s)r[s]=t,t+=1<<e[s];return r},Je=new H(new je([0,0,0,0,16843009,50528770,134678020,202050057,269422093]).buffer,0,36),gn=xt(Je,0),Qe=new H(new je([0,0,0,0,0,0,0,0,16843009,50528770,117769220,185207048,252579084,16]).buffer,0,53),dn=xt(Qe,3),Re=function(e,t,n){var r=e.length,s=t.length,o=e[r-1],i=(1<<n.b)-1,c=-n.b;if(!o)Z(0);var a=0,u=n.b,l=(r<<3)-8+Se(o)-u,f=-1;for(;l>c&&f<s;){var h=l>>3,g=(e[h]|e[h+1]<<8|e[h+2]<<16)>>(l&7);a=(a<<u|g)&i,t[++f]=n.s[a],l-=u=n.n[a]}if(l!=c||f+1!=s)Z(0)},bn=function(e,t,n){var r=6,s=t.length,o=s+3>>2,i=o<<1,c=o+i;Re(e.subarray(r,r+=e[0]|e[1]<<8),t.subarray(0,o),n),Re(e.subarray(r,r+=e[2]|e[3]<<8),t.subarray(o,i),n),Re(e.subarray(r,r+=e[4]|e[5]<<8),t.subarray(i,c),n),Re(e.subarray(r),t.subarray(c),n)},yn=function(e,t,n){var r,s=t.b,o=e[s],i=o>>1&3;t.l=o&1;var c=o>>3|e[s+1]<<5|e[s+2]<<13,a=(s+=3)+c;if(i==1){if(s>=e.length)return;if(t.b=s+1,n)return Be(n,e[s],t.y,t.y+=c),n;return Be(new H(c),e[s])}if(a>e.length)return;if(i==0){if(t.b=a,n)return n.set(e.subarray(s,a),t.y),t.y+=c,n;return Ye(e,s,a)}if(i==2){var u=e[s],l=u&3,f=u>>2&3,h=u>>4,g=0,p=0;if(l<2)if(f&1)h|=e[++s]<<4|(f&2&&e[++s]<<12);else h=u>>3;else if(p=f,f<2)h|=(e[++s]&63)<<4,g=e[s]>>6|e[++s]<<2;else if(f==2)h|=e[++s]<<4|(e[++s]&3)<<12,g=e[s]>>2|e[++s]<<6;else h|=e[++s]<<4|(e[++s]&63)<<12,g=e[s]>>6|e[++s]<<2|e[++s]<<10;++s;var m=n?n.subarray(t.y,t.y+t.m):new H(t.m),A=m.length-h;if(l==0)m.set(e.subarray(s,s+=h),A);else if(l==1)Be(m,e[s++],A);else{var b=t.h;if(l==2){var d=fn(e,s);g+=s-(s=d[0]),t.h=b=d[1]}else if(!b)Z(0);(p?bn:Re)(e.subarray(s,s+=g),m.subarray(A),b)}var x=e[s++];if(x){if(x==255)x=(e[s++]|e[s++]<<8)+32512;else if(x>127)x=x-128<<8|e[s++];var w=e[s++];if(w&3)Z(0);var v=[mn,hn,pn];for(var M=2;M>-1;--M){var U=w>>(M<<1)+2&3;if(U==1){var S=new H([0,0,e[s++]]);v[M]={s:S.subarray(2,3),n:S.subarray(0,1),t:new $e(S.buffer,0,1),b:0}}else if(U==2)r=De(e,s,9-(M&1)),s=r[0],v[M]=r[1];else if(U==3){if(!t.t)Z(0);v[M]=t.t[M]}}var D=t.t=v,y=D[0],R=D[1],C=D[2],F=e[a-1];if(!F)Z(0);var B=(a<<3)-8+Se(F)-C.b,L=B>>3,V=0,me=(e[L]|e[L+1]<<8)>>(B&7)&(1<<C.b)-1;L=(B-=R.b)>>3;var be=(e[L]|e[L+1]<<8)>>(B&7)&(1<<R.b)-1;L=(B-=y.b)>>3;var ye=(e[L]|e[L+1]<<8)>>(B&7)&(1<<y.b)-1;for(++x;--x;){var ue=C.s[me],Pe=C.n[me],xe=y.s[ye],Ce=y.n[ye],ke=R.s[be],he=R.n[be];L=(B-=ke)>>3;var O=1<<ke,k=O+((e[L]|e[L+1]<<8|e[L+2]<<16|e[L+3]<<24)>>>(B&7)&O-1);L=(B-=Qe[xe])>>3;var J=dn[xe]+((e[L]|e[L+1]<<8|e[L+2]<<16)>>(B&7)&(1<<Qe[xe])-1);L=(B-=Je[ue])>>3;var _=gn[ue]+((e[L]|e[L+1]<<8|e[L+2]<<16)>>(B&7)&(1<<Je[ue])-1);if(L=(B-=Pe)>>3,me=C.t[me]+((e[L]|e[L+1]<<8)>>(B&7)&(1<<Pe)-1),L=(B-=Ce)>>3,ye=y.t[ye]+((e[L]|e[L+1]<<8)>>(B&7)&(1<<Ce)-1),L=(B-=he)>>3,be=R.t[be]+((e[L]|e[L+1]<<8)>>(B&7)&(1<<he)-1),k>3)t.o[2]=t.o[1],t.o[1]=t.o[0],t.o[0]=k-=3;else{var W=k-(_!=0);if(W){if(k=W==3?t.o[0]-1:t.o[W],W>1)t.o[2]=t.o[1];t.o[1]=t.o[0],t.o[0]=k}else k=t.o[0]}for(var M=0;M<_;++M)m[V+M]=m[A+M];V+=_,A+=_;var ne=V-k;if(ne<0){var q=-ne,le=t.e+ne;if(q>J)q=J;for(var M=0;M<q;++M)m[V+M]=t.w[le+M];V+=q,J-=q,ne=0}for(var M=0;M<J;++M)m[V+M]=m[ne+M];V+=J}if(V!=A)while(A<m.length)m[V++]=m[A++];else V=m.length;if(n)t.y+=V;else m=Ye(m,0,V)}else if(n){if(t.y+=h,A)for(var M=0;M<h;++M)m[M]=m[A+M]}else if(A)m=Ye(m,A);return t.b=a,m}Z(2)},xn=function(e,t){if(e.length==1)return e[0];var n=new H(t);for(var r=0,s=0;r<e.length;++r){var o=e[r];n.set(o,s),s+=o.length}return n};function Ve(e,t){var n=[],r=+!t,s=0,o=0;for(;e.length;){var i=un(e,r||t);if(typeof i=="object"){if(r){if(t=null,i.w.length==i.u)n.push(t=i.w),o+=i.u}else n.push(t),i.e=0;for(;!i.l;){var c=yn(e,i,t);if(!c)Z(5);if(t)i.e=i.y;else n.push(c),o+=c.length,an(i.w,0,c.length),i.w.set(c,i.w.length-c.length)}s=i.b+i.c*4}else s=i;e=e.subarray(s)}return xn(n,o)}async function wn(e){let t=e instanceof Uint8Array?e:new Uint8Array(e),n=(r)=>r.buffer.slice(r.byteOffset,r.byteOffset+r.byteLength);if(t[0]===40&&t[1]===181&&t[2]===47&&t[3]===253)return n(Ve(t));if(t[0]===31&&t[1]===139)return new Response(new Blob([t]).stream().pipeThrough(new DecompressionStream("gzip"))).arrayBuffer();return n(t)}async function wt(e){return new TextDecoder().decode(await wn(e))}var At=(e)=>decodeURIComponent(e.split(/[?#]/)[0].split("/").pop()||"main.ldr").replace(/\\.(zst|gz)$/i,"")||"main.ldr";function _e(e){let t=new DataView(e).getUint32(0,!0),n=JSON.parse(new TextDecoder().decode(new Uint8Array(e,4,t))),r=4+t;return{header:n,arr:(o)=>o&&(o[2]==="f32"?new Float32Array(e,r+o[0],o[1]):o[2]==="u16"?new Uint16Array(e,r+o[0],o[1]):o[2]==="u8"?new Uint8Array(e,r+o[0],o[1]):new Uint32Array(e,r+o[0],o[1])),bytes:e.byteLength,buffer:e}}var Y=(e)=>e.trim().toLowerCase().replace(/\\\\/g,"/").replace(/\\/+/g,"/"),et=/^[A-Za-z][A-Za-z0-9_]*$/,qe=new Map;function tt(e){let t=e.toLowerCase(),n=2166136261;for(let s=0;s<t.length;s++)n^=t.charCodeAt(s),n=Math.imul(n,16777619);let r=-1-(n>>>0&1073741823);if(!qe.has(r))qe.set(r,t);return r}function nt(e){let t=e.charCodeAt(0)|32;if(t>=97&&t<=122&&et.test(e))return tt(e);if(/^0x/i.test(e))return parseInt(e,16);return+e}var Mt=/^~?\\s*moved\\s+to\\s+(.+)$/i,An=new Set(["FILE","NOFILE","!DATA","!:","STEP","BFC","ROTSTEP","BUFEXCHG","!TEXMAP"]),Mn=new Set(["FILE","NOFILE","!DATA"]),Pt=1000000000000000,It=new Set(["part","subpart","primitive","8_primitive","48_primitive","shortcut","helper"]),vn=new Set(["model","submodel","configuration"]),Cn=/^(?:!?LDRAW_ORG|Unofficial|Official\\s+LCAD)\\s+(\\S+)/i;function vt(e){let t=Cn.exec(e);if(!t)return;let n=t[1].toLowerCase().replace(/^unofficial_/,"");return It.has(n)||vn.has(n)?n:void 0}function kn(e){let t=[],n=0;while(n<e.length){while(e[n]===" "||e[n]==="\\t")n++;if(n>=e.length)break;if(e[n]===\'"\'){let r="";n++;while(n<e.length&&e[n]!==\'"\'){if(e[n]==="\\\\"&&n+1<e.length)n++;r+=e[n++]}n++,t.push(r)}else{let r=n;while(r<e.length&&e[r]!==" "&&e[r]!=="\\t")r++;t.push(e.slice(n,r)),n=r}}return t}function Tn(e,t=!1){let n=/^\\s*(\\S+)\\s+(.*)$/.exec(e);if(!n)return null;let r=n[1].toUpperCase(),s=r==="PLANAR"?9:r==="CYLINDRICAL"?10:r==="SPHERICAL"?11:0;if(!s)return null;let o=n[2].trim().split(/\\s+/);if(o.length<s+1)return null;let i=o.slice(0,s).map(Number);if(!i.every((f)=>Number.isFinite(f)&&Math.abs(f)<=1000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000))return null;if(s>=10&&!(Math.abs(i[9])>=0.000001)||s===11&&!(Math.abs(i[10])>=0.000001))return null;let c=n[2].trim();for(let f=0;f<s;f++)c=c.replace(/^\\S+\\s*/,"");let a=kn(c);if(!a.length)return null;let u={method:r,p1:i.slice(0,3),p2:i.slice(3,6),p3:i.slice(6,9),texture:a[0]};if(s>=10)u.a=i[9];if(s===11)u.b=i[10];let l=a.findIndex((f,h)=>h>0&&f.toUpperCase()==="GLOSSMAP");if(l>0&&a[l+1])u.glossmap=a[l+1];if(t)u.next=!0;return u}var Ln=(e)=>{let t=e.replace(/[^A-Za-z0-9+/]/g,"");if(t.length%4===1)t=t.slice(0,-1);let n=t+"=".repeat((4-t.length%4)%4),r=atob(n),s=new Uint8Array(r.length);for(let o=0;o<r.length;o++)s[o]=r.charCodeAt(o);return s};function Sn(e,t){let n=e.length,r=1,s=(p)=>p===32||p===9,o=()=>{while(r<n&&s(e.charCodeAt(r)))r++;let p=r,m=e.charCodeAt(r),A=m===45;if(A)m=e.charCodeAt(++r);let b=0,d=0;while(m>=48&&m<=57)b=b*10+(m-48),d++,m=e.charCodeAt(++r);if(d>0&&d<=15&&(r>=n||s(m)))return A?-b:b;while(r<n&&!s(e.charCodeAt(r)))r++;return p<r?+e.slice(p,r):NaN};while(r<n&&s(e.charCodeAt(r)))r++;let i=r;if(r>=n)return null;let c=e.charCodeAt(r),a=c===45,u=0,l=0;if(a)c=e.charCodeAt(++r);while(c>=48&&c<=57)u=u*10+(c-48),l++,c=e.charCodeAt(++r);if(l>0&&l<=15&&(r>=n||s(c))){if(a)u=-u}else{while(r<n&&!s(e.charCodeAt(r)))r++;u=nt(e.slice(i,r))}let f=Array(12);for(let p=0;p<12;p++){let m=o();if(!Number.isFinite(m))return null;f[p]=m}while(r<n&&s(e.charCodeAt(r)))r++;if(r>=n)return null;let h=e.slice(r),g=t.get(h);if(g===void 0)g=Y(/[ \\t]{2,}|\\t/.test(h)?h.split(/\\s+/).join(" "):h),t.set(h,g);if(!Number.isFinite(u))return null;return{t:1,color:u,m:f,file:g}}var En=[0,12,6,9,12,12];function Ct(e){let t=+e[0];if(!(t>=1&&t<=5&&Number.isInteger(t))||e.length<2)return null;let n=nt(e[1]),r=En[t];if(!Number.isFinite(n)||e.length<2+r+(t===1?1:0))return null;let s=Array(r);for(let o=0;o<r;o++){let i=+e[2+o];if(!Number.isFinite(i))return null;s[o]=i}if(t===1){let o=Y(e.slice(14).join(" "));return o?{t:1,color:n,m:s,file:o}:null}if(t===2)return{t:2,color:n,p:s};if(t===3)return{t:3,color:n,p:s};if(t===4)return{t:4,color:n,p:s};return{t:5,color:n,p:s}}function Ft(e,t="main.ldr",n={}){let r=!!n.geometryText,s=new Map,o=null,i="",c,a=null,u=[],l=null,f=()=>{if(!a)return;let x=Ln(a.chunks.join("")),w=x[0]===137&&x[1]===80&&x[2]===78&&x[3]===71;(c??=new Map).set(Y(a.name),{name:a.name,bytes:x,...w?{mime:"image/png"}:{}}),a=null},h=new Map,g=!0,p=(x)=>{if(f(),o={name:Y(x),cmds:[]},s.set(o.name,o),!i)i=o.name;u=[],l=null,g=!0},m=!1,A=!1,b=()=>{if(A)return;A=!0,s.clear(),o=null,i=""},d=(x,w)=>{if(l){x.tex=l,l=null;return}let v=u[u.length-1];if(!v)return;if(v.fallback){if(!w)x.fallback=!0}else x.tex=v.map};for(let x of e.split(`\n`)){let w=x.trim();if(!w)continue;if(r&&w.charCodeAt(0)>=50&&w.charCodeAt(0)<=53&&(w.charCodeAt(1)===32||w.charCodeAt(1)===9)){if(a||m)continue;if(!o)p(t);let S=w.slice(2).trimStart(),D=S.search(/\\s/),y={t:w.charCodeAt(0)-48,color:nt(D<0?S:S.slice(0,D)),p:[],src:w};d(y,!1),o.cmds.push(y),g=!1;continue}if(w.charCodeAt(0)===48&&(w.charCodeAt(1)===32||w.charCodeAt(1)===9)){let S=2;while(w.charCodeAt(S)===32||w.charCodeAt(S)===9)S++;let D=S;while(D<w.length&&w.charCodeAt(D)!==32&&w.charCodeAt(D)!==9)D++;let y=w.slice(S,D),R=/[^\\x21-\\x7e]/.test(y)?w.slice(S).trim().split(/\\s+/)[0]:y;if(!An.has(R)&&!(R.length>=4&&R.length<=6&&Mn.has(R.toUpperCase()))){if(m||a)continue;if(!o)p(t);let C=w.slice(S),F={t:0,text:C};if(y.charCodeAt(0)===33)F.meta=y;if(l=null,g&&!o.org){let L=vt(C);if(L)o.org=L}let B=C.match(Mt);if(B&&!o.movedTo){let L=B[1].trim().replace(/\\\\/g,"/");if(!/\\.(dat|ldr|mpd)$/i.test(L))L+=".dat";o.movedTo=Y(L)}o.cmds.push(F);continue}}if(w.charCodeAt(0)===49&&(w.charCodeAt(1)===32||w.charCodeAt(1)===9)&&!a&&!m){let S=Sn(w,h);if(S){if(!o)p(t);d(S,!1),o.cmds.push(S),g=!1;continue}}let v=w.split(/\\s+/);if(+v[0]===0){let S=w.slice(1).trim(),D=v.length>1&&v[1].length>=4&&v[1].length<=6?v[1].toUpperCase():v[1];if(D==="FILE"){let C=S.slice(5).trimStart().split("\\r")[0].trim();if(C){b(),m=!1,p(C);continue}}if(D==="NOFILE"){f(),o=null,m=!0;continue}if(D==="!DATA"){b(),f(),o=null,m=!1,a={name:S.slice(5).trim(),chunks:[]};continue}if(m)continue;if(a){if(v[1]==="!:")a.chunks.push(v.slice(2).join(""));continue}if(!o)p(t);let y={t:0,text:S};if(v[1]==="STEP")y.step=!0,u=[],l=null;else if(v[1]==="BFC")y.bfc=v.slice(2).join(" ");else if(v[1]==="ROTSTEP")if(y.meta="ROTSTEP",y.step=!0,u=[],l=null,(v[2]??"").toUpperCase()==="END")y.rotstep={x:0,y:0,z:0,mode:"END"};else{let C=(v[5]??"REL").toUpperCase(),F=(B)=>{let L=Number(B);return Number.isFinite(L)?L:0};y.rotstep={x:F(v[2]),y:F(v[3]),z:F(v[4]),mode:["REL","ABS","ADD"].includes(C)?C:"REL"}}else if(v[1]==="BUFEXCHG"){y.meta="BUFEXCHG";let C=(v[2]??"").toUpperCase();y.bufexchg={op:C==="RETRIEVE"?"RETRIEVE":"STORE",buf:v[3]??"A"}}else if(v[1]?.startsWith("!"))y.meta=v[1];if(g&&!o.org){let C=vt(S);if(C)o.org=C}if(v[1]==="!TEXMAP"){let C=(v[2]??"").toUpperCase();if(l=null,C==="START"||C==="NEXT"){let F=Tn(S.replace(/^!TEXMAP\\s+\\S+/i,""),C==="NEXT");if(y.texmap={op:C,...F?{map:F}:{}},F)if((o.texmaps??=[]).push(F),C==="START")u.push({map:F,fallback:!1});else l=F}else if(C==="FALLBACK"){y.texmap={op:C};let F=u[u.length-1];if(F)F.fallback=!0}else if(C==="END")y.texmap={op:C},u.pop()}else if(v[1]==="!:"){l=null;let C=Ct(v.slice(2));if(C)d(C,!0),y.geom=C}else l=null;let R=S.match(Mt);if(R&&!o.movedTo){let C=R[1].trim().replace(/\\\\/g,"/");if(!/\\.(dat|ldr|mpd)$/i.test(C))C+=".dat";o.movedTo=Y(C)}o.cmds.push(y);continue}if(a||m)continue;if(!o)p(t);let U=Ct(v);if(!U){if(/^[2-5][ \\t]/.test(w))g=!1;continue}d(U,!1),o.cmds.push(U),g=!1}return f(),c?{main:i,files:s,data:c}:{main:i,files:s}}var sr=Math.PI/180;function Rt(e,t){let n=(r)=>[t[3]*r[0]+t[4]*r[1]+t[5]*r[2]+t[0],t[6]*r[0]+t[7]*r[1]+t[8]*r[2]+t[1],t[9]*r[0]+t[10]*r[1]+t[11]*r[2]+t[2]];return{...e,p1:n(e.p1),p2:n(e.p2),p3:n(e.p3)}}function Bt(e,t){let[n,r,s,o,i,c,a,u,l,f,h,g]=e,[p,m,A,b,d,x,w,v,M,U,S,D]=t;return[o*p+i*m+c*A+n,a*p+u*m+l*A+r,f*p+h*m+g*A+s,o*b+i*w+c*U,o*d+i*v+c*S,o*x+i*M+c*D,a*b+u*w+l*U,a*d+u*v+l*S,a*x+u*M+l*D,f*b+h*w+g*U,f*d+h*v+g*S,f*x+h*M+g*D]}var rt=[0,0,0,1,0,0,0,1,0,0,0,1];var kt=new WeakMap,Pn=/^(s|8|48)\\//;function st(e,t){let n=e.files.get(Y(t));if(!n)return"part";let r=kt.get(n);if(r)return r;if(n.org)r=It.has(n.org)?"part":"model";else if(n.name===e.main)r="model";else r=n.cmds.some((s)=>s.t>=2||s.t===0&&!!s.geom||s.t===1&&Pn.test(s.file))?"part":"model";return kt.set(n,r),r}var Tt=new WeakMap;function Dt(e){let t=Tt.get(e);if(t)return t;t=[];let n=0;for(let r of e.cmds){if(r.t===0&&r.step){n++;continue}if((r.t>=2||r.t===0&&r.geom&&r.geom.t>=2)&&t[t.length-1]!==n)t.push(n)}return Tt.set(e,t),t}var Lt=(e)=>e>16777215?"0x"+e.toString(16).toUpperCase():e<0?qe.get(e)??String(e):String(e),In=(e)=>e.t===0?"0 "+e.text:e.t===1?`1 ${Lt(e.color)} ${e.m.join(" ")} ${e.file}`:e.src?e.src:`${e.t} ${Lt(e.color)} ${e.p.join(" ")}`,ot=(e,t)=>`${Y(e)}#${t}`;function Fn(e,t){let n=[],r=0,s=(o)=>!!o&&o.t===0&&o.texmap?.op==="NEXT";for(let o of e.cmds){if(o.t===0){if(o.step){r++;continue}if(o.bfc!==void 0||o.meta==="!COLOUR"){n.push(o);continue}if(r!==t)continue;if(o.texmap)n.push(o);else if(o.geom){if(o.geom.t>=2)n.push(o);else if(s(n[n.length-1]))n.pop()}continue}if(r!==t)continue;if(o.t===1){if(s(n[n.length-1]))n.pop();continue}n.push(o)}return{name:ot(e.name,t),cmds:n}}function Ut(e,t){return[`0 ldr: own geometry of ${e.name}, step ${t}`,...Fn(e,t).cmds.map(In)].join(`\n`)+`\n`}function it(e){let t=2166136261;for(let n=0;n<e.length;n++)t^=e.charCodeAt(n),t=Math.imul(t,16777619);return(t>>>0).toString(16).padStart(8,"0")}function Nt(e){let[t,n,r,s,o,i,c,a,u,l,f,h]=e,g=a*h-u*f,p=-(c*h-u*l),m=c*f-a*l,A=s*g+o*p+i*m;if(!Number.isFinite(A)||Math.abs(A)<0.000000000001)return null;let b=1/A,d=[g*b,-(o*h-i*f)*b,(o*u-i*a)*b,p*b,(s*h-i*l)*b,-(s*u-i*c)*b,m*b,-(s*f-o*l)*b,(s*a-o*c)*b];return[-(d[0]*t+d[1]*n+d[2]*r),-(d[3]*t+d[4]*n+d[5]*r),-(d[6]*t+d[7]*n+d[8]*r),...d]}var Rn=(e)=>String(+e.toFixed(6)||0),St=(e)=>\'"\'+e.replace(/\\\\/g,"\\\\\\\\").replace(/"/g,"\\\\\\"")+\'"\';function Ot(e,t){let n=[...t.p1,...t.p2,...t.p3,...t.method!=="PLANAR"?[t.a??360]:[],...t.method==="SPHERICAL"?[t.b??180]:[]].map(Rn).join(" "),r=`0 ldr: ${e} with a model-level !TEXMAP\n0 BFC CERTIFY CCW\n0 !TEXMAP START ${t.method} ${n} ${St(t.texture)}${t.glossmap?" GLOSSMAP "+St(t.glossmap):""}\n1 16 0 0 0 1 0 0 0 1 0 0 0 1 ${Y(e)}\n0 !TEXMAP END\n`;return{name:`${Y(e)}#tex-${it(r)}`,source:r}}var Bn=(e,t)=>{let n=[,,,,,,,,,];for(let r=0;r<3;r++)for(let s=0;s<3;s++)n[r*3+s]=e[r*3]*t[s]+e[r*3+1]*t[3+s]+e[r*3+2]*t[6+s];return n};function Dn(e,t,n){let r=Math.PI/180,s=Math.sin(e*r),o=Math.cos(e*r),i=Math.sin(t*r),c=Math.cos(t*r),a=Math.sin(n*r),u=Math.cos(n*r);return[c*u,-c*a,i,o*a+s*i*u,o*u-s*i*a,-s*c,s*a-o*i*u,s*u+o*i*a,o*c]}var Et=new WeakMap;function zt(e){let t=Et.get(e);if(t)return t;let n=[],r=null;for(let s of e.cmds){if(s.t!==0||!s.step)continue;let o=s.rotstep;if(o)if(o.mode==="END")r=null;else{let i=Dn(o.x,o.y,o.z);r=o.mode==="ABS"?{abs:!0,m:i,rotstep:o}:o.mode==="ADD"&&r?{abs:r.abs,m:Bn(r.m,i),rotstep:o}:{abs:!1,m:i,rotstep:o}}n.push(r)}return n.push(r),Et.set(e,n),n}class at extends Error{limit;code="ldr-model-limit";constructor(e,t){super(`ldr: ${e} expands past ${t.toLocaleString("en-US")} (see maxInstances)`);this.limit=t;this.name="ModelLimitError"}}var Un=(e)=>{for(let t=0;t<12;t++)if(!(Math.abs(e[t])<=Pt))return!1;return!0},$t=999999,_t=(e)=>e.map((t)=>String(t).padStart(6,"0")).join(".")+"~",Gt=new WeakMap,jt=new WeakMap;function Nn(e,t){let n=jt.get(t);if(!n)n={head:[...t.values()].map((o)=>{let i=Gt.get(o)??"",c=i.indexOf("!COLOUR");return c<0?"":"0 "+i.slice(c).trim().replace(/\\s+/g," ")}).filter(Boolean).join(`\n`),parts:new Map},jt.set(t,n);let r=n.parts.get(e);if(!r){let s=Y(e),o=`0 ldr: ${s} placed in a model\'s !COLOUR scope\n0 BFC CERTIFY CCW\n${n.head}\n1 16 0 0 0 1 0 0 0 1 0 0 0 1 ${s}\n`;r={name:`${s}#col-${it(o)}`,source:o},n.parts.set(e,r)}return r}function On(e,t={}){let n=[],r=t.maxDepth??64,s=t.looseGeometry!==!1,o=!!t.textures,i=!!t.callouts,c=new Map,a=0,u=new Set,l=t.maxInstances??2000000,f=0,h=(p,m)=>{let A=p.name+"#"+m,b=c.get(A);if(!b){let d;b=Object.assign(()=>d??=Ut(p,m),{file:p,step:m}),c.set(A,b)}return b},g=(p,m,A,b,d,x,w,v,M=null,U=[],S=[],D=void 0,y=null)=>{let R=p.files.get(m);if(!R||w>r||u.has(R))return;if(++f>l)throw new at("model",l);u.add(R);let C=y,F=0,B=w>0?++a:0,L=i&&B?[...U,B]:U,V=i&&B?[...S,A]:S,me=i&&!M?new Map:null,be=-1,ye=0,ue=(O,k,J,_,W,ne,q)=>{if(be!==F)be=F,ye=0;let le=me?.get(F+"|"+k);if(le)return le.n++,g(O,O===p?k:O.main,J,_,d+"/"+k,[...W,$t],w+1,ne,[...W,$t],L,V,q,C);let T=[...W,ye++],P=n.length;g(O,O===p?k:O.main,J,_,d+"/"+k,T,w+1,ne,M,L,V,q,C),me?.set(F+"|"+k,{n:1,from:P,to:n.length})},Pe=zt(R),xe=s?Dt(R):[],Ce=0,ke=(O,k,J,_,W,ne,q,le,T)=>{if(M)_=M;if(++f>l)throw new at("model",l);let P={part:O,color:k,m:J,step:_[0],steps:_,localStep:W,path:d};if(le)P.colour=le;if(B){if(P.sub=B,i)P.subPath=L,P.subMats=V}if(ne)P.embedded=!0;if(q){let N=Ot(O,q);P.texPart=N.name,P.texSource=N.source}else if(T){let N=Nn(O,T);P.colPart=N.name,P.colSource=N.source}let E=Pe[W];if(E)P.view=E;return n.push(P),P},he=(O)=>{while(Ce<xe.length&&xe[Ce]<=O){let k=xe[Ce++];ke(ot(R.name,k),b,A,[...x,k],k,!1,null,D,y).source=h(R,k)}};for(let O of R.cmds){if(O.t===0&&O.step){F++;continue}let k=O;if(k.t>=2||k.t===0&&k.geom&&k.geom.t>=2){he(F);continue}if(k.t===0){if(k.meta==="!COLOUR"){let E=$n(k.text);if(E&&E.code!==16&&E.code!==24)Gt.set(E,k.text),(C=new Map(C??[])).set(E.code,E);continue}if(o&&k.geom?.t===1)k=k.geom;else continue}if(k.t!==1)continue;if(o&&k.fallback)continue;let J=Bt(A,k.m);if(!Un(J))continue;let _=k.color===16?b:k.color,W=k.color===16?D:C?.get(k.color),ne=[...x,F],q=o?k.tex??v:null,le=q?Nt(k.m):null,T=q&&le?Rt(q,le):null;if(p.files.has(k.file)){if(st(p,k.file)==="model"){ue(p,k.file,J,_,ne,T,W);continue}ke(k.file,_,J,ne,F,!0,T,W,C);continue}let P=t.resolveModel?.(k.file);if(P){ue(P,k.file,J,_,ne,T,W);continue}ke(k.file,_,J,ne,F,!1,T,W,C)}if(he(1/0),u.delete(R),me){for(let O of me.values())if(O.n>1)for(let k=O.from;k<O.to;k++)n[k].mult??=O.n}};if(st(e,e.main)==="part"){if(e.files.get(e.main))n.push({part:e.main,color:16,m:[...rt],step:0,steps:[0],localStep:0,path:e.main,embedded:!0});return n}return g(e,e.main,rt,16,e.main,[],0,null),n}function Ht(e,t="main.ldr",n){return On(Ft(e,t,{geometryText:!0}),n)}var zn=new Set(["CHROME","PEARLESCENT","RUBBER","MATTE_METALLIC","METAL","MATERIAL"]);function lt(e){if(!e)return null;if(e.startsWith("#")&&/^#[0-9A-Fa-f]{6}$/.test(e))return e.toUpperCase();if(/^0x[0-9A-Fa-f]{6}$/i.test(e))return("#"+e.slice(2)).toUpperCase();return null}function Vt(e,t){let n={value:"#FFFFFF",fraction:0.5};while(t<e.length){let r=e[t].toUpperCase(),s=e[t+1];if(r==="VALUE"){let o=lt(s);if(o)n.value=o;t+=2}else if(r==="ALPHA")n.alpha=+s,t+=2;else if(r==="LUMINANCE")n.luminance=+s,t+=2;else if(r==="FRACTION")n.fraction=+s,t+=2;else if(r==="VFRACTION")n.vfraction=+s,t+=2;else if(r==="SIZE")n.size=+s,t+=2;else if(r==="MINSIZE")n.minsize=+s,t+=2;else if(r==="MAXSIZE")n.maxsize=+s,t+=2;else break}return{grain:n,next:t}}function $n(e){let t=e.indexOf("!COLOUR");if(t<0)return null;let n=e.slice(t+7).trim().split(/\\s+/).filter(Boolean);if(n.length<2)return null;let r=n[0],s=NaN,o="#FF00FF",i="#333333",c=255,a=0,u={type:"default"},l=1;while(l<n.length){let f=n[l].toUpperCase(),h=n[l+1];if(f==="CODE")s=h!==void 0&&et.test(h)?tt(h):h!==void 0&&/^\\d+$/.test(h)?+h:NaN,l+=2;else if(f==="VALUE"){let g=lt(h);if(g)o=g;l+=2}else if(f==="EDGE")i=lt(h)??h,l+=2;else if(f==="ALPHA")c=+h,l+=2;else if(f==="LUMINANCE")a=+h,l+=2;else if(f==="CHROME")u={type:"chrome"},l+=1;else if(f==="PEARLESCENT")u={type:"pearlescent"},l+=1;else if(f==="RUBBER")u={type:"rubber"},l+=1;else if(f==="MATTE_METALLIC")u={type:"matte_metallic"},l+=1;else if(f==="METAL")u={type:"metal"},l+=1;else if(f==="MATERIAL"){let g=(n[l+1]||"").toUpperCase();if(g==="GLITTER"){let{grain:p,next:m}=Vt(n,l+2);u={type:"glitter",material:p},l=m}else if(g==="SPECKLE"){let{grain:p,next:m}=Vt(n,l+2);u={type:"speckle",material:p},l=m}else if(g==="FABRIC"){let p=(n[l+2]||"").toUpperCase(),m=["VELVET","CANVAS","STRING","FUR"].includes(p)?p.toLowerCase():void 0;u={type:"fabric",kind:m},l+=m?3:2}else l=n.length}else if(zn.has(f))l+=1;else l+=1}if(Number.isNaN(s)||!o)return null;return{code:s,name:r,hex:o,edge:i,alpha:Number.isFinite(c)?c:255,luminance:Number.isFinite(a)?a:0,finish:u}}function jn(e){let t=Math.max(0,Math.min(1,(e.alpha??255)/255)),n=t<1,r=Math.max(0,Math.min(1,(e.luminance??0)/255)),s={opacity:t,transparent:n,depthWrite:!n,emissive:r,clearcoat:0,clearcoatRoughness:0,sheen:0,sheenRoughness:0};switch(e.finish?.type??"default"){case"chrome":return{...s,metalness:1,roughness:0,finish:"chrome"};case"pearlescent":return{...s,metalness:0.25,roughness:0.3,clearcoat:0.5,clearcoatRoughness:0.25,sheen:0.4,sheenRoughness:0.35,finish:"pearlescent"};case"rubber":return{...s,metalness:0,roughness:0.9,finish:"rubber"};case"matte_metallic":return{...s,metalness:0.4,roughness:0.8,finish:"matte_metallic"};case"metal":return{...s,metalness:0.85,roughness:0.2,finish:"metal"};case"glitter":{let i=e.finish.material,c=i.size??(i.minsize!=null&&i.maxsize!=null?(i.minsize+i.maxsize)/2:1);return{...s,metalness:0.35,roughness:0.25,clearcoat:1,clearcoatRoughness:0.08,particleHex:i.value,particleFraction:i.fraction,particleSize:c,finish:"glitter"}}case"speckle":{let i=e.finish.material,c=i.size??(i.minsize!=null&&i.maxsize!=null?(i.minsize+i.maxsize)/2:1);return{...s,metalness:0.2,roughness:0.55,particleHex:i.value,particleFraction:i.fraction,particleSize:c,finish:"speckle"}}case"fabric":return{...s,metalness:0,roughness:0.85,sheen:0.65,sheenRoughness:0.75,finish:"fabric"};default:return{...s,metalness:0,roughness:0.45,finish:"default"}}}function ct(e){let t=jn(e),n=!t.transparent?"op":t.opacity>=0.75?"a200":t.opacity>=0.4?"a128":`a${Math.round(t.opacity*255)}`,r=t.emissive>0?`L${Math.round(t.emissive*16)}`:"",s=`${t.finish}:${n}${r}`;if(t.particleHex)s+=`:${t.particleHex}:${(t.particleFraction??0).toFixed(2)}`;return s}function Vn(e,t){let n=new Map,r=null,s=!1,o=!1;for(let i of e.split(/\\r?\\n/)){let c=/^\\s*0\\s+FILE\\s+(\\S[^\\r]*)/i.exec(i);if(c){if(!s)n.clear();s=!0,o=!1,r=[],n.set(Y(c[1]),r);continue}if(/^\\s*0\\s+(NOFILE|!DATA)(\\s|$)/i.test(i)){if(!s&&/!DATA/i.test(i))n.clear(),s=!0;r=null,o=!0;continue}if(!r){if(s||o)continue;r=[],n.set(Y(t),r)}let a=i.trim().replace(/\\s+/g," ");if(a)r.push(a)}return n}var _n=(e)=>{if(!e.startsWith("1 "))return null;let t=e.split(" ");return t.length>=15?Y(t.slice(14).join(" ")):null};function Gn(e){let t=2166136261,n=1523705862;for(let r=0;r<e.length;r++){let s=e.charCodeAt(r);t=Math.imul(t^s,16777619),n=Math.imul(n^s,16777629)^n>>>15}return(t>>>0).toString(16).padStart(8,"0")+(n>>>0).toString(16).padStart(8,"0")}function Wt(e,t,n="main.ldr"){let r=[...t],s=new Map;if(!r.length)return s;let o=Vn(e,n);for(let i of r){let c=Y(i);if(!o.has(c)||s.has(c))continue;let a=new Set([c]),u=[c];while(u.length)for(let f of o.get(u.pop())){let h=_n(f);if(h&&o.has(h)&&!a.has(h))a.add(h),u.push(h)}let l=[c,...[...a].filter((f)=>f!==c).sort()].map((f)=>"0 FILE "+(f===c?"":f)+`\n`+o.get(f).join(`\n`)).join(`\n`);s.set(c,`emb/${Gn(l)}.dat`)}return s}var Xt=(e,t=0)=>Math.abs(e[t+7]-1)<0.001&&Math.abs(e[t+4])<0.001&&Math.abs(e[t+10])<0.001,Kt=new WeakMap,ut=null,ft="",pt=null;function Hn(e,t){if(e===ut&&t===ft)return pt;let n=Kt.get(e);if(!n)Kt.set(e,n=new Map);let r=n.get(t);if(r!==void 0)return ut=e,ft=t,pt=r,r;let s=e.parts[t];if(!s)return n.set(t,null),null;let o=s.studs.length,i=new Float64Array(o*12),c=[],a=[];s.studs.forEach((g,p)=>{c.push(g[0]),a.push(g[1]);for(let m=0;m<12;m++)i[p*12+m]=g[2+m]});let u=null,l=0,f=0;if(s.mask){l=s.mask[0],f=s.mask[1];let g=s.mask[2];u=new Uint8Array(g.length);for(let p=0;p<g.length;p++)u[p]=g.charCodeAt(p)===49?1:0}let h=!!u;if(u){for(let g=0;g<u.length;g++)if(u[g]!==1){h=!1;break}}return n.set(t,r={nStuds:o,studM:i,kind:c,color:a,mask:u,nx:l,nz:f,full:h}),ut=e,ft=t,pt=r,r}var Ie=1073741824;class Ee{t;tag;mask;size=0;shift;constructor(e=1024,t=-1){let n=1024;while(n<e*2)n*=2;this.t=new Int32Array(n*4),this.tag=new Uint8Array(n),this.mask=n-1,this.shift=t}slot(e,t,n){let r=this.shift;if(r<0){let o=Math.imul(e,2654435761)^Math.imul(t,2246822507)^Math.imul(n,3266489909);return o^=o>>>15,o=Math.imul(o,739982445),o^=o>>>12,o&this.mask}let s=Math.imul(e>>r+2,2654435761)^Math.imul(t,2246822507)^Math.imul(n>>r+2,3266489909);return s^=s>>>15,s=Math.imul(s,739982445),s^=s>>>12,(s<<4|(e>>r&3)<<2|n>>r&3)&this.mask}static tagOf(e,t,n){return Math.imul(e^Math.imul(t,374761393)^Math.imul(n,668265261),2654435761)>>>24|1}get(e,t,n){let r=Ee.tagOf(e,t,n),s=this.tag,o=this.t,i=this.mask,c=this.slot(e,t,n);for(;;){let a=s[c];if(a===0)return-1;if(a===r){let u=c<<2;if(o[u]===e&&o[u+1]===t&&o[u+2]===n)return o[u+3]}c=c+1&i}}put(e,t,n,r){if((this.size+1)*2>this.tag.length)this.grow();let s=Ee.tagOf(e,t,n),o=this.tag,i=this.t,c=this.mask,a=this.slot(e,t,n);for(;;){let u=o[a],l=a<<2;if(u===0)return o[a]=s,i[l]=e,i[l+1]=t,i[l+2]=n,i[l+3]=r,this.size++,-1;if(u===s&&i[l]===e&&i[l+1]===t&&i[l+2]===n){let f=i[l+3];return i[l+3]=r,f}a=a+1&c}}grow(){let e=this.t,t=this.tag,n=t.length*2;this.t=new Int32Array(n*4),this.tag=new Uint8Array(n),this.mask=n-1,this.size=0;for(let r=0;r<t.length;r++)if(t[r]){let s=r<<2;this.put(e[s],e[s+1],e[s+2],e[s+3])}}}class Yt{grp=new Ee(64);gBits=[];gX0=[];gZ0=[];gNz=[];gNx=[];bits;rest;lk=NaN;lpx=NaN;lpz=NaN;lg=-1;group(e,t,n){if(e!==this.lk||t!==this.lpx||n!==this.lpz)this.lk=e,this.lpx=t,this.lpz=n,this.lg=this.grp.get(e,t,n);return this.lg}constructor(e,t,n,r){let s=[],o=[],i=[],c=[],a=[];for(let f=0;f<r;f++){let h=e[f],g=t[f],p=n[f],m=(h%20+20)%20,A=(p%20+20)%20,b=this.group(g,m,A);if(b<0)b=s.length,this.grp.put(g,m,A,b),this.lg=b,s.push(0),o.push(h),i.push(h),c.push(p),a.push(p);if(s[b]++,h<o[b])o[b]=h;else if(h>i[b])i[b]=h;if(p<c[b])c[b]=p;else if(p>a[b])a[b]=p}let u=0,l=0;for(let f=0;f<s.length;f++){let h=(i[f]-o[f])/20+1,g=(a[f]-c[f])/20+1,p=h*g;if(this.gX0.push(o[f]),this.gZ0.push(c[f]),this.gNx.push(h),this.gNz.push(g),p<=64*s[f]+1024&&u+p<2147483648)this.gBits.push(u),u+=p;else this.gBits.push(-1),l+=s[f]}this.bits=new Uint8Array(Math.ceil(u/8)),this.rest=new Ee(l);for(let f=0;f<r;f++){let h=e[f],g=t[f],p=n[f],m=this.group(g,(h%20+20)%20,(p%20+20)%20),A=this.gBits[m];if(A<0){this.rest.put(h,g,p,1);continue}let b=A+(h-this.gX0[m])/20*this.gNz[m]+(p-this.gZ0[m])/20;this.bits[b>>>3]|=1<<(b&7)}}has(e,t,n){let r=this.group(t,(e%20+20)%20,(n%20+20)%20);if(r<0)return!1;let s=this.gBits[r];if(s<0)return this.rest.get(e,t,n)>=0;let o=(e-this.gX0[r])/20,i=(n-this.gZ0[r])/20;if(o<0||i<0||o>=this.gNx[r]||i>=this.gNz[r])return!1;let c=s+o*this.gNz[r]+i;return(this.bits[c>>>3]&1<<(c&7))!==0}}var Wn=(e,t,n,r)=>e===0&&r===0&&(t===1||t===-1)&&(n===1||n===-1)||t===0&&n===0&&(e===1||e===-1)&&(r===1||r===-1),Fe=(e,t,n)=>e>-Ie&&e<Ie&&t>-Ie&&t<Ie&&n>-Ie&&n<Ie,Ue=2147483647;function Xn(e,t){let n=e.colorTable?.[t];if(n)return(n.alpha??255)<255;return t.charCodeAt(0)===35&&/\\/[^:/]*:a\\d/.test(t)}function mt(e,t,n){return Zt(e,t,n,-1)??Zt(e,t,n,Jt)}var Jt=0;function Zt(e,t,n,r){let o=new Map,i=(T)=>{let P=o.get(T);if(P===void 0)o.set(T,P=Xn(t,T));return P},c=e.length,a=0,u=0,l=0,f=Array(c);for(let T=0;T<c;T++){let P=f[T]=Hn(t,e[T].part);if(P){if(l+=P.nStuds,P.mask)a++}}let h=new Float64Array(a),g=new Float64Array(a),p=new Float64Array(a),m=new Float64Array(a),A=new Int32Array(a),b=new Int32Array(a),d=new Float64Array(a),x=new Float64Array(a),w=[],v=new Int32Array(a),M=new Float64Array(a*9),U=new Uint8Array(a);if(r<0)r=a*4+64;let S=new Ee(e.length*2),D=new Int32Array(r),y=new Int32Array(r),R=0,C=0;for(let T=0;T<e.length;T++){let P=e[T],E=P.m,N=t.parts[P.part];if(!N||!N.mask||!Xt(E)||i(P.color))continue;let I=N.bbox,z=1/0,j=-1/0,ee=1/0,X=-1/0;for(let K=0;K<2;K++)for(let ae=0;ae<2;ae++){let te=K?I[3]:I[0],Le=ae?I[5]:I[2],ve=E[0]+E[3]*te+E[5]*Le,de=E[2]+E[9]*te+E[11]*Le;if(ve<z)z=ve;if(ve>j)j=ve;if(de<ee)ee=de;if(de>X)X=de}let G=Math.round((E[1]+I[4])*2),Q=f[T],ce=Math.floor(z/40),we=Math.floor(j/40),Ae=Math.floor(ee/40),Me=Math.floor(X/40);if(!((we-ce+1)*(Me-Ae+1)<=65536)||!Fe(G,ce,Ae)||!Fe(G,we,Me))continue;let ge=Math.floor((z+5)/40),re=Math.floor((j-5)/40),se=Math.floor((ee+5)/40),oe=Math.floor((X-5)/40),Te=ge<=re&&se<=oe?(re-ge+1)*(oe-se+1):0;C+=Te;let fe=-1;for(let K=ge<=re&&se<=oe?S.get(G,ge,se):-1,ae=0;K>=0&&ae<8;K=D[K],ae++){let te=y[K];if(h[te]!==z||g[te]!==j||p[te]!==ee||m[te]!==X||w[te]!==Q)continue;let Le=e[A[te]].m,ve=!0;for(let de=0;de<12;de++)if(Le[de]!==E[de]){ve=!1;break}if(ve){fe=te;break}}if(fe>=0){let K=n?n[T]:0;if(n&&K<n[A[fe]])b[fe]=A[fe],A[fe]=T;else if(b[fe]<0||n&&K<n[b[fe]])b[fe]=T;continue}let ie=u++;h[ie]=z,g[ie]=j,p[ie]=ee,m[ie]=X,A[ie]=T,b[ie]=-1,w.push(Q),d[ie]=I[0],x[ie]=I[2],v[ie]=G;let pe=ie*9;if(M[pe]=E[0],M[pe+1]=E[1],M[pe+2]=E[2],M[pe+3]=E[3],M[pe+4]=E[6],M[pe+5]=E[9],M[pe+6]=E[5],M[pe+7]=E[8],M[pe+8]=E[11],U[ie]=Q.full&&I[3]-I[0]<=20*Q.nx&&I[5]-I[2]<=20*Q.nz&&E[4]===0&&E[6]===0&&E[8]===0&&E[10]===0&&Wn(E[3],E[5],E[9],E[11])?1:0,R+Te>r){R=r+1;continue}for(let K=ge;K<=re;K++)for(let ae=se;ae<=oe;ae++){if(!Fe(G,K,ae))continue;let te=R++;y[te]=ie,D[te]=S.put(G,K,ae,te)}}if(R>r)return Jt=C,null;let F=[0,5,-5,5,-5],B=[0,5,5,-5,-5],L=(T,P,E,N)=>{if(!(P-6>=h[T]-0.5&&P+6<=g[T]+0.5&&N-6>=p[T]-0.5&&N+6<=m[T]+0.5))return!1;if(U[T]===1)return!0;let I=T*9,z=w[T],j=d[T],ee=x[T],X=P-M[I],G=E-M[I+1],Q=N-M[I+2],ce=M[I+3]*X+M[I+4]*G+M[I+5]*Q,we=M[I+6]*X+M[I+7]*G+M[I+8]*Q,{nx:Ae,nz:Me,mask:ge}=z;for(let re=0;re<5;re++){let se=Math.floor((ce+F[re]-j)/20),oe=Math.floor((we+B[re]-ee)/20);if(se<0||oe<0||se>=Ae||oe>=Me||ge[se*Me+oe]!==1)return!1}return!0},V=NaN,me=NaN,be=NaN,ye=-1,ue=-1,Pe=(T,P,E,N)=>{let I=Math.round(P*2),z=Math.floor(T/40),j=Math.floor(E/40);if(!Fe(I,z,j))return Ue;let ee=Ue;if(!n&&ue>=0&&v[ue]===I&&(A[ue]!==N||b[ue]>=0)&&L(ue,T,P,E))return 0;if(I!==V||z!==me||j!==be)V=I,me=z,be=j,ye=S.get(I,z,j);for(let X=ye;X>=0;X=D[X]){let G=y[X],Q=A[G];if(Q===N&&(Q=b[G])<0)continue;if(!L(G,T,P,E))continue;if(!n)return ue=G,0;let ce=n[Q];if(ce<ee)ee=ce}return ee},xe=new Uint8Array(l),Ce=new Uint8Array(l),ke=0,he=n?new Ee(l,4):null,O=n?null:new Int32Array(l),k=n?null:new Int32Array(l),J=n?null:new Int32Array(l),_=0,W=n?new Int32Array(l).fill(Ue):void 0;for(let T=0,P=0;T<e.length;T++){let E=e[T],N=f[T];if(!N)continue;let I=E.m,z=N.studM,j=I[0],ee=I[1],X=I[2],G=I[3],Q=I[4],ce=I[5],we=I[6],Ae=I[7],Me=I[8],ge=I[9],re=I[10],se=I[11];for(let oe=0;oe<N.nStuds;oe++,P++){let Te=oe*12,fe=z[Te+4],ie=z[Te+7],pe=z[Te+10];if(!(Math.abs(we*fe+Ae*ie+Me*pe-1)<0.001&&Math.abs(G*fe+Q*ie+ce*pe)<0.001&&Math.abs(ge*fe+re*ie+se*pe)<0.001))continue;Ce[P]=1;let K=z[Te],ae=z[Te+1],te=z[Te+2],Le=j+G*K+Q*ae+ce*te,ve=ee+we*K+Ae*ae+Me*te,de=X+ge*K+re*ae+se*te,gt=Pe(Le,ve,de,T);if(gt!==Ue){if(xe[P]=1,ke++,W)W[P]=gt}let Ne=Math.round(Le),Oe=Math.round(ve),ze=Math.round(de);if(!Fe(Ne,Oe,ze))continue;if(!he){O[_]=Ne,k[_]=Oe,J[_++]=ze;continue}let dt=n[T],bt=he.get(Ne,Oe,ze);if(bt<0||dt<bt)he.put(Ne,Oe,ze,dt)}}let ne=he?null:new Yt(O,k,J,_),q=new Uint8Array(e.length),le=n?new Int32Array(e.length).fill(Ue):void 0;for(let T=0;T<e.length;T++){let P=e[T],E=t.parts[P.part];if(!E||!E.under||!Xt(P.m)||i(P.color))continue;let N=E.bbox,I=Math.round((N[3]-N[0])/20),z=Math.round((N[5]-N[2])/20);if(!I||!z||I*z>4096)continue;let j=P.m,ee=Math.round(j[1]+N[4]),X=!0,G=0;for(let Q=0;Q<I&&X;Q++)for(let ce=0;ce<z;ce++){let we=N[0]+10+20*Q,Ae=N[2]+10+20*ce,Me=j[0]+j[3]*we+j[5]*Ae,ge=j[2]+j[9]*we+j[11]*Ae,re=Math.round(Me),se=Math.round(ge),oe=!Fe(re,ee,se)?-1:he?he.get(re,ee,se):ne.has(re,ee,se)?1:-1;if(oe<0){X=!1;break}if(oe>G)G=oe}if(X){if(q[T]=1,le)le[T]=G}}return{nStuds:l,studHidden:xe,studUp:Ce,underHidden:q,studsHidden:ke,studHideStep:W,underHideStep:le}}function ht(e,t,n){let r=(l)=>l.colPart&&t.parts[l.colPart]?l.colPart:n&&l.texPart&&t.parts[l.texPart]?l.texPart:l.part,s=new Map,o=new Map,i=(l)=>{let f=l.colour;if(!f)return String(l.color);let h=o.get(f);if(h!==void 0)return h;let g=t.colorTable?.[l.color],p=g?.hex??t.colors?.[l.color],m=g?ct({alpha:g.alpha??255,luminance:g.luminance??0,finish:g.finish??{type:"default"}}):"default:op",A=ct(f);if(h=p&&p.toUpperCase()===f.hex.toUpperCase()&&m===A?String(l.color):f.hex.toUpperCase()+"/"+A,h!==String(l.color))s.set(h,f);return o.set(f,h),h},c=e.map((l)=>({part:r(l),color:i(l),m:l.m,steps:l.steps})),{stepOf:a,nSteps:u}=Kn(c);return{all:c,stepOf:a,nSteps:u,localColours:s}}function Kn(e){let t=!0;for(let o=0;o<e.length;o++){let i=e[o].steps;if(i.length!==1){t=!1;break}let c=i[0];if(!(Number.isInteger(c)&&c>=0&&c<1e6)){t=!1;break}}if(t){let o=new Set;for(let a=0;a<e.length;a++)o.add(e[a].steps[0]);let i=[...o].sort((a,u)=>a-u),c=new Map(i.map((a,u)=>[a,u]));return{stepOf:e.map((a)=>c.get(a.steps[0])),nSteps:i.length}}let n=e.map((o)=>_t(o.steps)),r=[...new Set(n)].sort(),s=new Map(r.map((o,i)=>[o,i]));return{stepOf:n.map((o)=>s.get(o)),nSteps:r.length}}function Qt(e,t,n=!0){let r=ht(e,t,n);return mt(r.all,t,r.nSteps>1?r.stepOf:void 0)}var Ke="https://ldr-parts-cdn.baconbrix.workers.dev/v1/",He=new Map,Ge=new Map;function We(e=Ke,t=fetch){let n=He.get(e);if(!n)n=t(e+"parts.json").then((r)=>{if(!r.ok)throw Error(`ldr: parts CDN index ${r.status} (${e}parts.json)`);return r.json()}),n.catch(()=>He.delete(e)),He.set(e,n);return n}var Zn=(e)=>Array.isArray(e)&&e.length===3&&typeof e[0]==="number"&&typeof e[1]==="number"&&(e[2]==="f32"||e[2]==="u16"||e[2]==="u8"||e[2]==="u32"),Xe=(e,t)=>Zn(e)?[e[0]+t,e[1],e[2]]:Array.isArray(e)?e.map((n)=>Xe(n,t)):e&&typeof e==="object"?Object.fromEntries(Object.entries(e).map(([n,r])=>[n,Xe(r,t)])):e;function Yn(e,t={}){let n=[],r=0,s={},o={};for(let h of e){let g=h.buffer;if(!g)throw Error("ldr: mergePacks needs packs from decodePack/loadPack");let p=new DataView(g).getUint32(0,!0),m=new Uint8Array(g,4+p),A=r;n.push(m),r+=m.byteLength;let b=(4-r%4)%4;if(b)n.push(new Uint8Array(b)),r+=b;for(let[d,x]of Object.entries(h.header.parts??{}))if(!(d in s))s[d]=Xe(x,A);for(let[d,x]of Object.entries(h.header.studKinds??{}))if(!(d in o))o[d]=Xe(x,A)}let i=e[0]?.header??{version:1,weld:!0},c=new TextEncoder().encode(JSON.stringify({...i,parts:s,studKinds:o,...t})),a=(4-(4+c.length)%4)%4,u=4+c.length+a,l=new Uint8Array(u+r);new DataView(l.buffer).setUint32(0,c.length+a,!0),l.set(c,4),l.fill(32,4+c.length,u);let f=u;for(let h of n)l.set(h,f),f+=h.byteLength;return _e(l.buffer)}async function Jn(e,t={}){e=[...e];try{return await qt(e,t)}catch(n){let r=t.cdn??Ke,s=t.fetch??fetch;He.delete(r);let o=(i,c)=>s(i,{...c,cache:"reload"});try{return await qt(e,{...t,fetch:o})}catch{throw n}}}async function qt(e,t){let n=t.cdn??Ke,r=t.fetch??fetch,s=t.gap??16384,o=await We(n,r),i=[...new Set([...new Set(e)].map(Y))],c=[],a=[];for(let d of i){if(Ge.has(n+d))continue;let x=o.parts[d];if(x)a.push({name:d,off:x[0],len:x[1],file:x[2]??0});else c.push(d)}a.sort((d,x)=>d.file-x.file||d.off-x.off);let u=[];for(let d of a){let x=u[u.length-1];if(x&&x.file===d.file&&d.off-x.end<=s)x.end=Math.max(x.end,d.off+d.len),x.items.push(d);else u.push({file:d.file,start:d.off,end:d.off+d.len,items:[d]})}let l=0,f=0,h=0,g=new Map,p=async()=>{while(h<u.length){let d=u[h++],x=g.get(d.file);if(x)x=x.subarray(d.start,d.end);else{let w=await r(new URL(o.archives[d.file],n).href,{headers:{Range:`bytes=${d.start}-${d.end-1}`,"Accept-Encoding":"identity"}});if(!w.ok)throw Error(`ldr: parts CDN ${w.status}`);if(f++,x=new Uint8Array(await w.arrayBuffer()),l+=x.byteLength,w.status===200)g.set(d.file,x),x=x.subarray(d.start,d.end)}for(let w of d.items){let v=Ve(x.subarray(w.off-d.start,w.off-d.start+w.len)),M=v.buffer.slice(v.byteOffset,v.byteOffset+v.byteLength);Ge.set(n+w.name,_e(M))}}};await Promise.all(Array.from({length:Math.min(t.concurrency??24,u.length)},p));let m=i.filter((d)=>Ge.has(n+d)).map((d)=>Ge.get(n+d)),A={colors:o.colors,...o.colorTable?{colorTable:o.colorTable}:{}};return{pack:m.length?Yn(m,A):_e(Qn(A)),missing:c,requests:f,bytes:l}}function Qn(e){let t=new TextEncoder().encode(JSON.stringify({version:1,weld:!0,parts:{},studKinds:{},...e})),n=(4-(4+t.length)%4)%4,r=new Uint8Array(4+t.length+n).fill(32);return new DataView(r.buffer).setUint32(0,t.length+n,!0),r.set(t,4),r.buffer}function qn(e,t){let n=t.header.parts;if(!n)return 0;let r=0;for(let s of e){let o=n[s.part]?.body?.tris;if(o)r+=o}return r}function en(e,t,n){let r=0,s=0,o=!1,i=new Set,c=new Map;for(let a of e){let u;if(a.embedded)u=t.get(a.part);else if(u=c.get(a.part),u===void 0)c.set(a.part,u=Y(a.part));let l=u?n.parts[u]:void 0;if(!l)continue;if(l[3]!=null)o=!0,r+=l[3];if(!i.has(u))i.add(u),s+=l[1]}return{bodyTris:r,packBytes:s,known:o}}class Ze extends Error{code="ldr-budget";bodyTris;packBytes;maxBodyTris;maxPackBytes;constructor(e){let t=[e.maxBodyTris!=null&&e.bodyTris>e.maxBodyTris?`${e.bodyTris} triangles (limit ${e.maxBodyTris})`:"",e.maxPackBytes!=null&&e.packBytes>e.maxPackBytes?`${(e.packBytes/1e6).toFixed(1)} MB parts pack (limit ${(e.maxPackBytes/1e6).toFixed(0)} MB)`:""].filter(Boolean).join(", ");super(`ldr: model exceeds device budget: ${t}`);this.name="BudgetError",this.bodyTris=e.bodyTris,this.packBytes=e.packBytes,this.maxBodyTris=e.maxBodyTris,this.maxPackBytes=e.maxPackBytes}}async function tn(e,t={}){let n=performance.now(),r=t.fetch??fetch,s=We(t.cdn??Ke,r);s.catch(()=>{});let o=t.text?e:await r(e).then(async(y)=>{if(!y.ok)throw Error(`ldr: ${y.status} fetching ${e}`);return wt(await y.arrayBuffer())}),i=performance.now(),c=t.name??(t.text?"main.ldr":At(e)),a=Ht(o,c,{looseGeometry:!1,callouts:t.callouts}),u=performance.now();t.onParsed?.(a),await s;let l=Wt(o,new Set(a.filter((y)=>y.embedded).map((y)=>y.part)),c),f=(y,R)=>t.maxBodyTris!=null&&y>t.maxBodyTris||t.maxPackBytes!=null&&R>t.maxPackBytes,h=t.maxBodyTris!=null||t.maxPackBytes!=null,g=(y)=>new Ze({...y,maxBodyTris:t.maxBodyTris,maxPackBytes:t.maxPackBytes}),p="full";if(h){let y=en(a,l,await s);if(f(y.known?y.bodyTris:0,y.packBytes)){if(!t.lowCdn)throw g(y);let R=await We(t.lowCdn,r).catch(()=>null);if(!R)throw g(y);let C=en(a,l,R);if(f(C.known?C.bodyTris:0,C.packBytes))throw g(C);p="low"}}let m=[...a.filter((y)=>!y.embedded).map((y)=>y.part),...l.values()],A=async()=>{let y=await Jn(m,p==="low"?{...t,cdn:t.lowCdn}:t);for(let[R,C]of l){let F=y.pack.header.parts[C];if(F)y.pack.header.parts[R]=F}return{...y,packBytes:y.pack.buffer?.byteLength??y.pack.bytes??0,bodyTris:qn(a,y.pack)}},b=await A();if(h&&f(b.bodyTris,b.packBytes)&&p==="full"&&t.lowCdn&&await We(t.lowCdn,r).then(()=>!0,()=>!1)){p="low";let y=b;b=await A(),b.requests+=y.requests,b.bytes+=y.bytes}if(h&&f(b.bodyTris,b.packBytes))throw g(b);let{pack:d,missing:x,requests:w,bytes:v}=b,M=new Map([...l].map(([y,R])=>[R,y])),U=x.map((y)=>M.get(y)??y),S=performance.now(),D=t.cull?Qt(a,d.header,t.textures!==!1):void 0;return{insts:a,pack:d,tier:p,missing:U,requests:w,bytes:v,cull:D,timings:{fetchModel:i-n,parse:u-i,parts:S-u,...D?{cull:performance.now()-S}:{}}}}var er=new Set(["part","color","m","step","steps","localStep","path"]);function nn(e){let t=e.length,n=0;for(let p of e){if(typeof p.part!=="string"||typeof p.path!=="string"||typeof p.color!=="number"||typeof p.step!=="number"||typeof p.localStep!=="number"||!Array.isArray(p.m)||p.m.length!==12||!Array.isArray(p.steps))return null;n+=p.steps.length}let r=[],s=new Map,o=(p)=>{let m=s.get(p);if(m===void 0)s.set(p,m=r.length),r.push(p);return m},i=new Uint32Array(t),c=new Uint32Array(t),a=new Float64Array(t*3),u=new Float64Array(t*12),l=new Uint32Array(t+1),f=new Float64Array(n),h=[],g=0;for(let p=0;p<t;p++){let m=e[p];i[p]=o(m.part),c[p]=o(m.path),a[p*3]=m.color,a[p*3+1]=m.step,a[p*3+2]=m.localStep;let A=m.m,b=p*12;for(let w=0;w<12;w++)u[b+w]=A[w];let d=m.steps;for(let w=0;w<d.length;w++)f[g++]=d[w];l[p+1]=g;let x=null;for(let w in m)if(!er.has(w))(x??={})[w]=m[w];if(x)h.push([p,x])}return{n:t,strs:r,part:i,path:c,num:a,m:u,so:l,steps:f,extra:h}}var rn=(e)=>[e.part.buffer,e.path.buffer,e.num.buffer,e.m.buffer,e.so.buffer,e.steps.buffer];self.onmessage=async(e)=>{let{id:t,source:n,opts:r}=e.data;try{let s=await tn(n,{...r,cull:!1,onParsed:(f)=>{let h=nn(f);if(h)self.postMessage({id:t,packed:h},rn(h));else self.postMessage({id:t,insts:f})}}),o=s.pack.buffer;if(self.postMessage({id:t,buffer:o,tier:s.tier,missing:s.missing,requests:s.requests,bytes:s.bytes,timings:s.timings},[o]),!r.cull)return;let i=performance.now(),c=ht(s.insts,s.pack.header,r.textures!==!1),a=mt(c.all,s.pack.header,r.stepCull&&c.nSteps>1?c.stepOf:void 0),u=performance.now()-i,l=[];for(let f of[a.studHidden,a.studUp,a.underHidden,a.studHideStep,a.underHideStep])if(f)l.push(f.buffer);self.postMessage({id:t,cull:a,ms:u},l)}catch(s){if(s instanceof Ze||s?.code==="ldr-budget")self.postMessage({id:t,phase:"error",error:String(s?.message??s),budget:{bodyTris:s.bodyTris,packBytes:s.packBytes,maxBodyTris:s.maxBodyTris,maxPackBytes:s.maxPackBytes}});else self.postMessage({id:t,phase:"error",error:String(s?.message??s)})}};\n';
|
|
5404
5638
|
|
|
5405
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5639
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/inst-io.ts
|
|
5406
5640
|
var CORE = new Set(["part", "color", "m", "step", "steps", "localStep", "path"]);
|
|
5407
5641
|
function unpackInstances(p) {
|
|
5408
5642
|
const { n, strs, part, path, num, m, so, steps, extra } = p;
|
|
@@ -5427,7 +5661,7 @@ function unpackInstances(p) {
|
|
|
5427
5661
|
return out;
|
|
5428
5662
|
}
|
|
5429
5663
|
|
|
5430
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5664
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/cdn.ts
|
|
5431
5665
|
var worker;
|
|
5432
5666
|
var seq = 0;
|
|
5433
5667
|
var pending = new Map;
|
|
@@ -5476,6 +5710,7 @@ function getWorker() {
|
|
|
5476
5710
|
return worker = null;
|
|
5477
5711
|
}
|
|
5478
5712
|
}
|
|
5713
|
+
var eagerSteps = (o) => o.step != null || (o.eagerSteps ?? !!o.callouts);
|
|
5479
5714
|
var abs = (u) => {
|
|
5480
5715
|
try {
|
|
5481
5716
|
return new URL(u, globalThis.location?.href).href;
|
|
@@ -5485,7 +5720,7 @@ var abs = (u) => {
|
|
|
5485
5720
|
};
|
|
5486
5721
|
function prepareInWorker(w, source, o) {
|
|
5487
5722
|
const id = ++seq;
|
|
5488
|
-
const opts = { cdn: abs(o.cdn ?? DEFAULT_PARTS_CDN), gap: o.gap, concurrency: o.concurrency, text: o.text, name: o.name, cull: true, textures: o.textures, callouts: o.callouts, maxBodyTris: o.maxBodyTris, maxPackBytes: o.maxPackBytes, lowCdn: o.lowCdn && abs(o.lowCdn) };
|
|
5723
|
+
const opts = { cdn: abs(o.cdn ?? DEFAULT_PARTS_CDN), gap: o.gap, concurrency: o.concurrency, text: o.text, name: o.name, cull: true, stepCull: eagerSteps(o), textures: o.textures, callouts: o.callouts, maxBodyTris: o.maxBodyTris, maxPackBytes: o.maxPackBytes, lowCdn: o.lowCdn && abs(o.lowCdn) };
|
|
5489
5724
|
const name = o.name ?? (o.text ? undefined : modelFileName(source));
|
|
5490
5725
|
let insts;
|
|
5491
5726
|
pendingInsts.set(id, (v) => {
|
|
@@ -5526,7 +5761,8 @@ async function loadModel(source, o = {}) {
|
|
|
5526
5761
|
} else
|
|
5527
5762
|
prep = await prepareModel(source, o);
|
|
5528
5763
|
const t3 = performance.now();
|
|
5529
|
-
const
|
|
5764
|
+
const oo = { ...o, eagerSteps: eagerSteps(o) };
|
|
5765
|
+
const obj = await createLdrObjectAsync(prep.insts, prep.pack, prep.cull ? { ...oo, precomputedCull: prep.cull } : oo);
|
|
5530
5766
|
for (const m of prep.missing)
|
|
5531
5767
|
if (!obj.stats.missing.includes(m))
|
|
5532
5768
|
obj.stats.missing.push(m);
|
|
@@ -5541,7 +5777,7 @@ async function loadModel(source, o = {}) {
|
|
|
5541
5777
|
timings: { ...prep.timings, parts: t3 - t0 - prep.timings.fetchModel - prep.timings.parse, build: t4 - t3, total: t4 - t0 }
|
|
5542
5778
|
});
|
|
5543
5779
|
}
|
|
5544
|
-
// ../../../../../../../tmp/ldr-build-
|
|
5780
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/usdz.ts
|
|
5545
5781
|
var IDENT = [0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1];
|
|
5546
5782
|
var MAX_ERR = 8;
|
|
5547
5783
|
var REL_ERR = 0.1;
|
|
@@ -6173,7 +6409,7 @@ function hiddenInstances(n, items, geo, clear, RES = 512) {
|
|
|
6173
6409
|
hidden[k] = seen[k] ? 0 : 1;
|
|
6174
6410
|
return hidden;
|
|
6175
6411
|
}
|
|
6176
|
-
// ../../../../../../../tmp/ldr-build-
|
|
6412
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/library.ts
|
|
6177
6413
|
import { existsSync, readFileSync, statSync } from "fs";
|
|
6178
6414
|
import { join } from "path";
|
|
6179
6415
|
var xf = (m, x, y, z) => [m[3] * x + m[4] * y + m[5] * z + m[0], m[6] * x + m[7] * y + m[8] * z + m[1], m[9] * x + m[10] * y + m[11] * z + m[2]];
|
|
@@ -6523,11 +6759,11 @@ class Library {
|
|
|
6523
6759
|
return insts;
|
|
6524
6760
|
}
|
|
6525
6761
|
}
|
|
6526
|
-
// ../../../../../../../tmp/ldr-build-
|
|
6762
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/build-pack.ts
|
|
6527
6763
|
import fs3 from "node:fs";
|
|
6528
6764
|
import path3 from "node:path";
|
|
6529
6765
|
|
|
6530
|
-
// ../../../../../../../tmp/ldr-build-
|
|
6766
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/resolver.ts
|
|
6531
6767
|
import fs from "node:fs";
|
|
6532
6768
|
import path from "node:path";
|
|
6533
6769
|
var TOP_STUD_RE = /^(stud|studa|stud2|stud2a|stud6|stud6a|stud10|stud15|stud2s|stud2s2|stud-logo\d*|stud2-logo\d*)\.dat$/i;
|
|
@@ -6856,11 +7092,11 @@ function collectDeps(lib, refs) {
|
|
|
6856
7092
|
return out;
|
|
6857
7093
|
}
|
|
6858
7094
|
|
|
6859
|
-
// ../../../../../../../tmp/ldr-build-
|
|
7095
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/compile.ts
|
|
6860
7096
|
import fs2 from "node:fs";
|
|
6861
7097
|
import path2 from "node:path";
|
|
6862
7098
|
|
|
6863
|
-
// ../../../../../../../tmp/ldr-build-
|
|
7099
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/lod.ts
|
|
6864
7100
|
import { MeshoptSimplifier, MeshoptEncoder } from "meshoptimizer";
|
|
6865
7101
|
await Promise.all([MeshoptSimplifier.ready, MeshoptEncoder.ready]);
|
|
6866
7102
|
function reorderMesh(P, N, C, I) {
|
|
@@ -7166,7 +7402,7 @@ function levelLines(P, I, E, err, always, tol = 0.01) {
|
|
|
7166
7402
|
return out;
|
|
7167
7403
|
}
|
|
7168
7404
|
|
|
7169
|
-
// ../../../../../../../tmp/ldr-build-
|
|
7405
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/compile.ts
|
|
7170
7406
|
class BfcState {
|
|
7171
7407
|
accum;
|
|
7172
7408
|
ccw = true;
|
|
@@ -7469,6 +7705,22 @@ class Compiler {
|
|
|
7469
7705
|
seatStuds(out, fullKind, (k) => this.compile(k, false).bbox);
|
|
7470
7706
|
if (this.opts.tex && this.hasTex(key))
|
|
7471
7707
|
this.texPass(key, out, separateStuds, colorOf);
|
|
7708
|
+
const cap = OPEN_BOTTOM[key.replace(/^.*[\\/]/, "").toLowerCase()];
|
|
7709
|
+
if (cap && isFinite(out.bbox[0])) {
|
|
7710
|
+
const [cx0, cz0, cx1, cz1] = cap, y = out.bbox[4], b = out.body, per = b.col.length / (b.pos.length / 3);
|
|
7711
|
+
let v = -1;
|
|
7712
|
+
for (let i = 1;i < b.pos.length; i += 3)
|
|
7713
|
+
if (Math.abs(b.pos[i] - y) < 0.01) {
|
|
7714
|
+
v = (i - 1) / 3;
|
|
7715
|
+
break;
|
|
7716
|
+
}
|
|
7717
|
+
if (v >= 0) {
|
|
7718
|
+
const rgba = b.col.slice(v * per, v * per + per);
|
|
7719
|
+
b.pos.push(cx0, y, cz0, cx0, y, cz1, cx1, y, cz1, cx0, y, cz0, cx1, y, cz1, cx1, y, cz0);
|
|
7720
|
+
for (let k = 0;k < 6; k++)
|
|
7721
|
+
b.col.push(...rgba);
|
|
7722
|
+
}
|
|
7723
|
+
}
|
|
7472
7724
|
const [x0, y0, z0, x1, y1, z1] = out.bbox;
|
|
7473
7725
|
let ax0 = Infinity, ax1 = -Infinity, az0 = Infinity, az1 = -Infinity;
|
|
7474
7726
|
for (const b of [out.body, out.under])
|
|
@@ -7694,6 +7946,7 @@ class Compiler {
|
|
|
7694
7946
|
}
|
|
7695
7947
|
}
|
|
7696
7948
|
}
|
|
7949
|
+
var OPEN_BOTTOM = { "11477.dat": [-10, -20, 10, 20] };
|
|
7697
7950
|
function underEnclosed(c) {
|
|
7698
7951
|
const u = c.under.pos;
|
|
7699
7952
|
let uy0 = Infinity, uy1 = -Infinity, ux0 = Infinity, ux1 = -Infinity, uz0 = Infinity, uz1 = -Infinity;
|
|
@@ -8110,7 +8363,7 @@ function encodePack(parts, studKinds, weld, extra, options = {}) {
|
|
|
8110
8363
|
return Buffer.concat([head, ...chunks.map((c) => new Uint8Array(c.buffer, c.byteOffset, c.byteLength))]);
|
|
8111
8364
|
}
|
|
8112
8365
|
|
|
8113
|
-
// ../../../../../../../tmp/ldr-build-
|
|
8366
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/build-pack.ts
|
|
8114
8367
|
function packCompilerOpts(o) {
|
|
8115
8368
|
return { studs: o.studs ?? "low", prims: o.primitives ?? "full", weld: o.weld ?? true, separateStuds: true, cond: !!o.cond, tex: !!o.textures, ...o.partWorkLimit ? { workLimit: o.partWorkLimit } : {} };
|
|
8116
8369
|
}
|
|
@@ -8182,7 +8435,7 @@ function buildPack(o) {
|
|
|
8182
8435
|
const warnings = [...lib.conflicts].map((n) => `${n}: defined differently by two models; the first definition is used`);
|
|
8183
8436
|
return { data: encodePack(parts, kinds, comp.opts.weld, extra, { texture, lod: o.lod !== false, reorder: !!o.reorder }), parts: parts.size, studKinds: kinds.size, missing: [...missing], ...warnings.length ? { warnings } : {} };
|
|
8184
8437
|
}
|
|
8185
|
-
// ../../../../../../../tmp/ldr-build-
|
|
8438
|
+
// ../../../../../../../tmp/ldr-build-vpoU1w/src/node/promote.ts
|
|
8186
8439
|
var GEOM = /^\s*[2-5]\s/;
|
|
8187
8440
|
var REF = /^\s*1\s/;
|
|
8188
8441
|
var FILE = /^\s*0\s+FILE\s+(\S.*?)\s*$/i;
|
|
@@ -8511,6 +8764,7 @@ export {
|
|
|
8511
8764
|
splitModel,
|
|
8512
8765
|
stepKey,
|
|
8513
8766
|
stepViewMatrix,
|
|
8767
|
+
studDecalUniforms,
|
|
8514
8768
|
texWrapper,
|
|
8515
8769
|
texmapTriangleUV,
|
|
8516
8770
|
texmapUV,
|