@nebula-spatial/viewer 0.4.4 → 0.4.5
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/CHANGELOG.md +33 -0
- package/README.md +59 -0
- package/USD-VISUAL-MATERIAL-SUPPORT.md +51 -0
- package/dist/assets/types.d.ts +7 -1
- package/dist/{index-D-o1ODOX.js → index-CxbZ--5C.js} +2032 -1790
- package/dist/index.js +1 -1
- package/dist/inspection/types.d.ts +13 -0
- package/dist/mjcf-visual-6_RqDf4z.js +73 -0
- package/dist/{session-c7xBLA4J.js → session-CnlODeFp.js} +2 -2
- package/dist/session-DNyPmQOW.js +795 -0
- package/dist/{stage-D113SHD8.js → stage-BPiGudYP.js} +131 -118
- package/dist/urdf-session-CuIZOiCF.js +3238 -0
- package/dist/usd-session-JDfuDgWv.js +1907 -0
- package/dist/xacro-DrBtv-gK.js +1537 -0
- package/package.json +4 -2
- package/dist/mjcf-visual-M1lmyjvw.js +0 -63
- package/dist/session-Cz6qHYMc.js +0 -676
- package/dist/urdf-session-AP-cMuwd.js +0 -3001
- package/dist/usd-session-CmSdkRw9.js +0 -1192
|
@@ -0,0 +1,1907 @@
|
|
|
1
|
+
import { Mesh as te, FrontSide as _t, DoubleSide as gt, MeshPhysicalMaterial as ie, DataTexture as Xe, UnsignedByteType as He, RGBAFormat as qe, NoColorSpace as K, Float32BufferAttribute as St, SRGBColorSpace as Je, RepeatWrapping as q, Color as st, MeshStandardMaterial as ze, TextureLoader as wt, MirroredRepeatWrapping as rt, ClampToEdgeWrapping as ot, Group as Ie, Vector3 as T, Quaternion as ee, Matrix4 as pe, Box3 as Me, Sphere as Ut, SphereGeometry as bt, BoxGeometry as Et } from "three";
|
|
2
|
+
import { n as xt, c as vt, a as Ae, b as Dt, d as Pt, p as At, S as Qe } from "./session-DNyPmQOW.js";
|
|
3
|
+
import { ConvexGeometry as Rt } from "three/examples/jsm/geometries/ConvexGeometry.js";
|
|
4
|
+
import { buildUSDScene as Ot, USDLoader as It } from "@openusd-wasm/three-loader";
|
|
5
|
+
import { PXR as Mt } from "@openusd-wasm/pxr";
|
|
6
|
+
import { d as at } from "./stage-BPiGudYP.js";
|
|
7
|
+
function Tt(e) {
|
|
8
|
+
var a, h;
|
|
9
|
+
const t = e.stage;
|
|
10
|
+
if (!t || !((h = (a = e.pxr) == null ? void 0 : a.Sdf) != null && h.Path)) return;
|
|
11
|
+
const n = /* @__PURE__ */ new Map(), o = (f) => {
|
|
12
|
+
if (!f || f === "/") return "default";
|
|
13
|
+
const d = n.get(f);
|
|
14
|
+
if (d !== void 0) return d;
|
|
15
|
+
const i = new e.pxr.Sdf.Path(f), r = t.GetPrimAtPath(i), s = r.GetAttribute("purpose"), u = e.pxr.Usd.TimeCode.Default();
|
|
16
|
+
let p;
|
|
17
|
+
try {
|
|
18
|
+
s.IsValid() && s.HasAuthoredValue() && (p = String(s.Get(u)));
|
|
19
|
+
} finally {
|
|
20
|
+
u.delete(), s.delete(), r.delete(), i.delete();
|
|
21
|
+
}
|
|
22
|
+
const y = p ?? o(f.slice(0, f.lastIndexOf("/")));
|
|
23
|
+
return n.set(f, y), y;
|
|
24
|
+
};
|
|
25
|
+
e.scene.traverse((f) => {
|
|
26
|
+
var s, u;
|
|
27
|
+
if (!(f instanceof te)) return;
|
|
28
|
+
let d = f, i;
|
|
29
|
+
for (; d && !i; )
|
|
30
|
+
i = (s = d.userData.usd) == null ? void 0 : s.path, d = d.parent;
|
|
31
|
+
if (!i) return;
|
|
32
|
+
const r = o(i) === "guide";
|
|
33
|
+
f.userData.usdPurposeExcluded = r, r ? ((u = f.userData).usdPurposeLayerMask ?? (u.usdPurposeLayerMask = f.layers.mask), f.layers.disableAll()) : f.userData.usdPurposeLayerMask !== void 0 && (f.layers.mask = f.userData.usdPurposeLayerMask, delete f.userData.usdPurposeLayerMask);
|
|
34
|
+
});
|
|
35
|
+
}
|
|
36
|
+
function Nt(e) {
|
|
37
|
+
if (!e) return;
|
|
38
|
+
if (typeof window > "u") return { baseURL: e };
|
|
39
|
+
const t = new URL(e, document.baseURI).href, n = new URL("openusd_pxr_wasm.js", t.endsWith("/") ? t : `${t}/`);
|
|
40
|
+
if (n.origin === window.location.origin) return { baseURL: t };
|
|
41
|
+
const o = new Blob([`import ${JSON.stringify(n.href)};
|
|
42
|
+
`], { type: "text/javascript" });
|
|
43
|
+
return {
|
|
44
|
+
baseURL: t,
|
|
45
|
+
// pxr 0.0.13 sets mainScriptUrlOrBlob itself; its public preRun hook runs
|
|
46
|
+
// before OpenUSD initializes and lazily spawns its pthread workers.
|
|
47
|
+
preRun: [(a) => {
|
|
48
|
+
a.mainScriptUrlOrBlob = o;
|
|
49
|
+
}]
|
|
50
|
+
};
|
|
51
|
+
}
|
|
52
|
+
function $t(e) {
|
|
53
|
+
var d, i;
|
|
54
|
+
const t = e.stage, n = e.pxr;
|
|
55
|
+
if (!t || !((d = n == null ? void 0 : n.Sdf) != null && d.Path) || !((i = n == null ? void 0 : n.Usd) != null && i.TimeCode)) return;
|
|
56
|
+
const o = n.Usd.TimeCode.Default(), a = /* @__PURE__ */ new Map(), h = /* @__PURE__ */ new Set(), f = (r) => {
|
|
57
|
+
let s, u, p;
|
|
58
|
+
try {
|
|
59
|
+
if (s = new n.Sdf.Path(r), u = t.GetPrimAtPath(s), !u.IsValid() || (p = u.GetAttribute("doubleSided"), !p.IsValid() || typeof p.HasAuthoredValue != "function")) return "unknown";
|
|
60
|
+
if (!p.HasAuthoredValue()) return;
|
|
61
|
+
const y = p.Get(o);
|
|
62
|
+
return typeof y == "boolean" ? y : "unknown";
|
|
63
|
+
} catch {
|
|
64
|
+
return "unknown";
|
|
65
|
+
} finally {
|
|
66
|
+
p == null || p.delete(), u == null || u.delete(), s == null || s.delete();
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
try {
|
|
70
|
+
e.scene.traverse((r) => {
|
|
71
|
+
var l;
|
|
72
|
+
if (!(r instanceof te)) return;
|
|
73
|
+
const s = (l = r.userData.usd) == null ? void 0 : l.path;
|
|
74
|
+
if (typeof s != "string") return;
|
|
75
|
+
const u = f(s);
|
|
76
|
+
if (u === "unknown") return;
|
|
77
|
+
const p = u === !1 ? _t : gt, y = (c) => {
|
|
78
|
+
if (!(c instanceof ie) || c.transmission <= 0 || c.metalness !== 0 || c.side === p) return c;
|
|
79
|
+
let w = a.get(c);
|
|
80
|
+
w || (w = /* @__PURE__ */ new Map(), a.set(c, w));
|
|
81
|
+
let g = w.get(p);
|
|
82
|
+
return g || (g = c.clone(), g.side = p, g.needsUpdate = !0, g.userData.usdGlassSidePolicy = u === !1 ? "authored-false" : u === !0 ? "authored-true" : "viewer-default-double", w.set(p, g)), h.add(c), g;
|
|
83
|
+
};
|
|
84
|
+
if (Array.isArray(r.material)) {
|
|
85
|
+
const c = r.material, w = c.map(y);
|
|
86
|
+
w.some((g, m) => g !== c[m]) && (r.material = w);
|
|
87
|
+
} else {
|
|
88
|
+
const c = y(r.material);
|
|
89
|
+
c !== r.material && (r.material = c);
|
|
90
|
+
}
|
|
91
|
+
}), e.scene.traverse((r) => {
|
|
92
|
+
if (r instanceof te) for (const s of Array.isArray(r.material) ? r.material : [r.material]) h.delete(s);
|
|
93
|
+
});
|
|
94
|
+
for (const r of h) r.dispose();
|
|
95
|
+
} finally {
|
|
96
|
+
o.delete();
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
function Ct(e, t) {
|
|
100
|
+
if (!e.stage || t.shaders.length) return null;
|
|
101
|
+
const n = e.stage, o = e.pxr, a = o.Usd.TimeCode.Default(), h = (i, r) => {
|
|
102
|
+
const s = new o.Sdf.Path(i), u = n.GetPrimAtPath(s);
|
|
103
|
+
try {
|
|
104
|
+
if (!u.IsValid()) throw new Error("Missing prim");
|
|
105
|
+
return r(u);
|
|
106
|
+
} finally {
|
|
107
|
+
u.delete(), s.delete();
|
|
108
|
+
}
|
|
109
|
+
}, f = (i) => {
|
|
110
|
+
const r = i.GetConnections();
|
|
111
|
+
try {
|
|
112
|
+
return r.map((s) => typeof s == "string" ? s : s.GetString());
|
|
113
|
+
} finally {
|
|
114
|
+
for (const s of r) typeof s != "string" && s.delete();
|
|
115
|
+
}
|
|
116
|
+
}, d = (i, r = /* @__PURE__ */ new Set()) => {
|
|
117
|
+
if (r.has(i) || r.size >= 32) throw new Error("Cyclic material input");
|
|
118
|
+
r.add(i);
|
|
119
|
+
const s = i.lastIndexOf(".");
|
|
120
|
+
if (s < 0 || !i.slice(s + 1).startsWith("inputs:")) throw new Error("Not a constant input");
|
|
121
|
+
return h(i.slice(0, s), (u) => {
|
|
122
|
+
const p = u.GetAttribute(i.slice(s + 1));
|
|
123
|
+
try {
|
|
124
|
+
if (!p.IsValid()) throw new Error("Missing material input");
|
|
125
|
+
const y = f(p);
|
|
126
|
+
if (y.length > 1) throw new Error("Ambiguous material input");
|
|
127
|
+
const l = y.length ? d(y[0], r) : p.Get(a);
|
|
128
|
+
if (l == null) throw new Error("Unauthored material input");
|
|
129
|
+
return l;
|
|
130
|
+
} finally {
|
|
131
|
+
p.delete();
|
|
132
|
+
}
|
|
133
|
+
});
|
|
134
|
+
};
|
|
135
|
+
try {
|
|
136
|
+
return h(t.path, (i) => {
|
|
137
|
+
if (!i.IsInstance()) return null;
|
|
138
|
+
const r = i.GetAttribute("outputs:surface");
|
|
139
|
+
let s;
|
|
140
|
+
try {
|
|
141
|
+
if (!r.IsValid()) return null;
|
|
142
|
+
s = f(r);
|
|
143
|
+
} finally {
|
|
144
|
+
r.delete();
|
|
145
|
+
}
|
|
146
|
+
if (s.length !== 1 || !s[0].endsWith(".outputs:surface")) return null;
|
|
147
|
+
const u = s[0].slice(0, -16);
|
|
148
|
+
return h(u, (p) => {
|
|
149
|
+
const y = p.GetAttribute("info:id");
|
|
150
|
+
try {
|
|
151
|
+
if (y.Get(a) !== "UsdPreviewSurface") return null;
|
|
152
|
+
} finally {
|
|
153
|
+
y.delete();
|
|
154
|
+
}
|
|
155
|
+
const l = {}, c = p.GetAttributes();
|
|
156
|
+
try {
|
|
157
|
+
for (const g of c) {
|
|
158
|
+
const m = String(g.GetName());
|
|
159
|
+
m.startsWith("inputs:") && (l[m] = d(`${u}.${m}`));
|
|
160
|
+
}
|
|
161
|
+
} finally {
|
|
162
|
+
for (const g of c) g.delete();
|
|
163
|
+
}
|
|
164
|
+
return { ...t, shaders: [{ path: u, id: "UsdPreviewSurface", inputs: l }] };
|
|
165
|
+
});
|
|
166
|
+
});
|
|
167
|
+
} catch {
|
|
168
|
+
return null;
|
|
169
|
+
} finally {
|
|
170
|
+
a.delete();
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
function de(e, t, n = 1, o = 0) {
|
|
174
|
+
var u;
|
|
175
|
+
const a = e.image, h = (a == null ? void 0 : a.naturalWidth) || (a == null ? void 0 : a.width), f = (a == null ? void 0 : a.naturalHeight) || (a == null ? void 0 : a.height);
|
|
176
|
+
if (!Number.isInteger(h) || !Number.isInteger(f) || h <= 0 || f <= 0) throw new Error("Texture has no decoded pixels");
|
|
177
|
+
let d;
|
|
178
|
+
if (e instanceof Xe) {
|
|
179
|
+
if (e.type !== He || e.format !== qe || ((u = a.data) == null ? void 0 : u.length) !== h * f * 4) throw new Error("Unsupported scalar pixel format");
|
|
180
|
+
d = a.data;
|
|
181
|
+
} else {
|
|
182
|
+
const p = document.createElement("canvas");
|
|
183
|
+
p.width = h, p.height = f;
|
|
184
|
+
const y = p.getContext("2d", { willReadFrequently: !0 });
|
|
185
|
+
if (!y) throw new Error("Scalar conversion requires a 2D canvas");
|
|
186
|
+
y.drawImage(a, 0, 0), d = y.getImageData(0, 0, h, f).data;
|
|
187
|
+
}
|
|
188
|
+
const i = new Uint8Array(h * f * 4), r = "rgba".indexOf(t);
|
|
189
|
+
for (let p = 0; p < i.length; p += 4) {
|
|
190
|
+
const y = d[p], l = d[p + 1], c = d[p + 2];
|
|
191
|
+
if (t === "grayscale" && (y !== l || l !== c)) throw new Error("Non-grayscale scalar image needs an explicit mono convention");
|
|
192
|
+
const w = t === "average" ? (y + l + c) / 3 : t === "maximum" ? Math.max(y, l, c) : t === "grayscale" ? y : d[p + r], g = Math.round(255 * Math.min(1, Math.max(0, w / 255 * n + o)));
|
|
193
|
+
i[p] = i[p + 1] = i[p + 2] = g, i[p + 3] = 255;
|
|
194
|
+
}
|
|
195
|
+
const s = new Xe(i, h, f, qe, He);
|
|
196
|
+
return s.wrapS = e.wrapS, s.wrapT = e.wrapT, s.offset.copy(e.offset), s.repeat.copy(e.repeat), s.center.copy(e.center), s.rotation = e.rotation, s.matrix.copy(e.matrix), s.matrixAutoUpdate = e.matrixAutoUpdate, s.channel = e.channel, s.flipY = e.flipY, s.minFilter = e.minFilter, s.magFilter = e.magFilter, s.anisotropy = e.anisotropy, s.generateMipmaps = e.generateMipmaps, s.colorSpace = K, s.needsUpdate = !0, s;
|
|
197
|
+
}
|
|
198
|
+
function Lt(e, t, n, o = [], a = !1) {
|
|
199
|
+
if (e.some((r) => !Number.isInteger(r) || r < 0) || e.reduce((r, s) => r + s, 0) !== t.length || o.some((r) => !Number.isInteger(r) || r < 0 || r >= e.length))
|
|
200
|
+
throw new Error("Invalid authored face topology");
|
|
201
|
+
const h = [], f = [], d = new Set(o);
|
|
202
|
+
let i = 0;
|
|
203
|
+
if (e.forEach((r, s) => {
|
|
204
|
+
if (!d.has(s)) for (let u = 1; u < r - 1; u++)
|
|
205
|
+
h.push(i, i + (a ? u + 1 : u), i + (a ? u : u + 1)), f.push(s);
|
|
206
|
+
i += r;
|
|
207
|
+
}), h.length !== n.length || h.some((r, s) => t[r] !== n[s]))
|
|
208
|
+
throw new Error("Authored polygon/loader corner correspondence unavailable");
|
|
209
|
+
return { corners: h, faces: f };
|
|
210
|
+
}
|
|
211
|
+
function Gt(e, t, n) {
|
|
212
|
+
if (t.length !== n || t.some((a) => !Number.isInteger(a) || a < 0 || a >= e.length))
|
|
213
|
+
throw new Error("Invalid faceVarying UV indices");
|
|
214
|
+
const o = t.flatMap((a) => e[a]);
|
|
215
|
+
if (o.length !== n * 2 || !o.every(Number.isFinite)) throw new Error("Invalid UV values");
|
|
216
|
+
return o;
|
|
217
|
+
}
|
|
218
|
+
function Ft(e, t) {
|
|
219
|
+
const n = Array(e).fill(0);
|
|
220
|
+
for (const o of t) for (const a of o.faces) {
|
|
221
|
+
if (!Number.isInteger(a) || a < 0 || a >= e || n[a] !== 0)
|
|
222
|
+
throw new Error("Invalid or overlapping material subset faces");
|
|
223
|
+
n[a] = o.slot;
|
|
224
|
+
}
|
|
225
|
+
return n;
|
|
226
|
+
}
|
|
227
|
+
function Bt(e, t, n, o) {
|
|
228
|
+
if (!e.stage) return;
|
|
229
|
+
const a = e.stage, h = e.pxr, f = h.Usd.TimeCode.Default(), d = (r, s) => t.warnings.push({
|
|
230
|
+
code: "USD_VISUAL_TOPOLOGY_UNSUPPORTED",
|
|
231
|
+
source: "usd-visual",
|
|
232
|
+
message: `USD ${r} 的部分视觉拓扑未能安全补齐,未确认部分保留 Loader 输出:${String(s)}`
|
|
233
|
+
}), i = (r, s) => {
|
|
234
|
+
const u = r.GetAttribute(s);
|
|
235
|
+
try {
|
|
236
|
+
return u.IsValid() ? u.Get(f) : null;
|
|
237
|
+
} finally {
|
|
238
|
+
u.delete();
|
|
239
|
+
}
|
|
240
|
+
};
|
|
241
|
+
try {
|
|
242
|
+
for (const r of e.data.elements) {
|
|
243
|
+
const s = e.index.objectsByPath.get(r.path);
|
|
244
|
+
if (!(s instanceof te)) continue;
|
|
245
|
+
const u = new h.Sdf.Path(r.path), p = a.GetPrimAtPath(u);
|
|
246
|
+
let y = [];
|
|
247
|
+
try {
|
|
248
|
+
if (p.GetTypeName() !== "Mesh") continue;
|
|
249
|
+
y = p.GetChildren();
|
|
250
|
+
const l = y.filter((b) => b.GetTypeName() === "GeomSubset" && i(b, "familyName") === "materialBind"), c = p.GetAttribute("primvars:st");
|
|
251
|
+
let w = null, g = null;
|
|
252
|
+
try {
|
|
253
|
+
n(r.material) && c.IsValid() && c.GetMetadata("interpolation") === "faceVarying" && (g = i(p, "primvars:st:indices"), g && (w = c.Get(f)));
|
|
254
|
+
} finally {
|
|
255
|
+
c.delete();
|
|
256
|
+
}
|
|
257
|
+
const m = l.length > 0 && !Array.isArray(s.material) && s.geometry.groups.length === 0;
|
|
258
|
+
if (!w && !m) continue;
|
|
259
|
+
const U = i(p, "faceVertexCounts"), E = i(p, "faceVertexIndices");
|
|
260
|
+
if (!U || !E || s.geometry.index) throw new Error("Authored face topology unavailable");
|
|
261
|
+
const M = Lt(
|
|
262
|
+
U,
|
|
263
|
+
E,
|
|
264
|
+
r.geometry.pointIndices ?? [],
|
|
265
|
+
i(p, "holeIndices") ?? [],
|
|
266
|
+
i(p, "orientation") === "leftHanded"
|
|
267
|
+
);
|
|
268
|
+
if (s.geometry.getAttribute("position").count !== M.corners.length)
|
|
269
|
+
throw new Error("Loader geometry corner count mismatch");
|
|
270
|
+
if (w && g) {
|
|
271
|
+
const b = Gt(w, g, E.length), A = M.corners.flatMap((W) => [b[W * 2], b[W * 2 + 1]]), L = s.geometry.getAttribute("uv");
|
|
272
|
+
(!L || L.array.length !== A.length || A.some((W, v) => Math.abs(W - L.array[v]) > 1e-6)) && (s.geometry.setAttribute("uv", new St(A, 2)), r.geometry.uvs = A);
|
|
273
|
+
}
|
|
274
|
+
if (!m) continue;
|
|
275
|
+
const R = l.map((b) => {
|
|
276
|
+
if (i(b, "elementType") !== "face") throw new Error("Non-face material subset");
|
|
277
|
+
const A = h.UsdShade.ComputeBoundMaterialPath(b), L = (A == null ? void 0 : A.resolvedTargetPath) || (A == null ? void 0 : A.materialPath);
|
|
278
|
+
if (!L || !e.index.materialsByPath.has(L)) throw new Error("Unresolved subset material");
|
|
279
|
+
const W = i(b, "indices");
|
|
280
|
+
if (!Array.isArray(W)) throw new Error("Missing subset face indices");
|
|
281
|
+
return { materialPath: L, faces: W };
|
|
282
|
+
}), D = [...new Set(R.map((b) => b.materialPath))], P = Ft(U.length, R.map((b) => ({ faces: b.faces, slot: D.indexOf(b.materialPath) + 1 }))), C = M.faces.map((b) => P[b]), _ = [s.material];
|
|
283
|
+
try {
|
|
284
|
+
for (const b of D) _.push(o(r, b));
|
|
285
|
+
} catch (b) {
|
|
286
|
+
for (const A of _.slice(1)) A.dispose();
|
|
287
|
+
throw b;
|
|
288
|
+
}
|
|
289
|
+
s.material = _;
|
|
290
|
+
for (let b = 0; b < C.length; ) {
|
|
291
|
+
let A = b + 1;
|
|
292
|
+
for (; A < C.length && C[A] === C[b]; ) A++;
|
|
293
|
+
s.geometry.addGroup(b * 3, (A - b) * 3, C[b]), b = A;
|
|
294
|
+
}
|
|
295
|
+
} catch (l) {
|
|
296
|
+
d(r.path, l);
|
|
297
|
+
} finally {
|
|
298
|
+
for (const l of y) l.delete();
|
|
299
|
+
p.delete(), u.delete();
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
} finally {
|
|
303
|
+
f.delete();
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
const Vt = /* @__PURE__ */ new Set(["png", "jpg", "jpeg", "webp", "avif", "gif", "bmp"]), Te = /^(?:UsdPreviewSurface|ND_UsdPreviewSurface_surfaceshader)$/i, kt = /(?:standard.?surface|principled|openpbr|adobe.?standard.?material)/i;
|
|
307
|
+
async function Wt(e, t) {
|
|
308
|
+
var i;
|
|
309
|
+
const n = /* @__PURE__ */ new Set();
|
|
310
|
+
for (const r of e.data.materials) {
|
|
311
|
+
const s = Ct(e, r);
|
|
312
|
+
s && (r.shaders = s.shaders, e.index.materialsByPath.set(r.path, r), n.add(r.path));
|
|
313
|
+
}
|
|
314
|
+
const o = (r, s) => {
|
|
315
|
+
const u = e.data.view.prims.find((w) => w.path === r.path);
|
|
316
|
+
if (!u) throw new Error(`Missing view prim: ${r.path}`);
|
|
317
|
+
const p = e.index.materialsByPath.get(s), y = Le(p), c = Ot({
|
|
318
|
+
...e.data,
|
|
319
|
+
elements: [{ ...r, material: s }],
|
|
320
|
+
view: { ...e.data.view, prims: [{ ...u, parentPath: null }] },
|
|
321
|
+
animations: [],
|
|
322
|
+
lights: [],
|
|
323
|
+
skels: { ...e.data.skels, bindings: [], skeletons: [], animations: [] }
|
|
324
|
+
}, {
|
|
325
|
+
convertZUp: !1,
|
|
326
|
+
loadLights: !1,
|
|
327
|
+
loadTextures: !y,
|
|
328
|
+
sourcePath: t.sourcePath,
|
|
329
|
+
textureResolver: (w) => {
|
|
330
|
+
for (const g of [w.resolvedPath, w.path, w.url]) {
|
|
331
|
+
if (!g) continue;
|
|
332
|
+
const m = t.files.objectUrlIfPresent(g, t.entryDirectory ?? "");
|
|
333
|
+
if (m) return m;
|
|
334
|
+
}
|
|
335
|
+
return null;
|
|
336
|
+
}
|
|
337
|
+
}).index.objectsByPath.get(r.path);
|
|
338
|
+
if (c.geometry.dispose(), Array.isArray(c.material)) throw new Error("Unexpected scratch material array");
|
|
339
|
+
return c.material;
|
|
340
|
+
}, a = /* @__PURE__ */ new Set();
|
|
341
|
+
for (const r of e.data.elements) {
|
|
342
|
+
const s = e.index.objectsByPath.get(r.path);
|
|
343
|
+
if (!(s instanceof te)) continue;
|
|
344
|
+
const u = (p) => {
|
|
345
|
+
const y = me(p.userData.usdMaterialPath);
|
|
346
|
+
if (!y || !n.has(y) || p.userData.usdSurfaceShaderId) return p;
|
|
347
|
+
const l = o(r, y), c = `Material ${y} has no supported surface shader.`;
|
|
348
|
+
return l.userData.usdInstanceResolvedDiagnostics = [c], l.userData.usdMaterialDiagnostics = we([
|
|
349
|
+
...Re(p.userData.usdMaterialDiagnostics),
|
|
350
|
+
...Re(l.userData.usdMaterialDiagnostics)
|
|
351
|
+
]), a.add(p), l;
|
|
352
|
+
};
|
|
353
|
+
if (Array.isArray(s.material)) {
|
|
354
|
+
const p = s.material.map(u);
|
|
355
|
+
p.some((y, l) => y !== s.material[l]) && (s.material = p);
|
|
356
|
+
} else s.material = u(s.material);
|
|
357
|
+
}
|
|
358
|
+
e.scene.traverse((r) => {
|
|
359
|
+
if (r instanceof te) for (const s of Array.isArray(r.material) ? r.material : [r.material]) a.delete(s);
|
|
360
|
+
});
|
|
361
|
+
for (const r of a) r.dispose();
|
|
362
|
+
Bt(e, t.diagnostics, (r) => {
|
|
363
|
+
if (!r) return !0;
|
|
364
|
+
const s = e.index.materialsByPath.get(r), u = s && Le(s);
|
|
365
|
+
return !!u && xe(u) && ue(u, /* @__PURE__ */ new Set());
|
|
366
|
+
}, o);
|
|
367
|
+
const h = Ht(e), f = [];
|
|
368
|
+
for (const [r, s] of h) {
|
|
369
|
+
const u = e.index.materialsByPath.get(r);
|
|
370
|
+
if (!u) continue;
|
|
371
|
+
const p = s[0], y = we(s.flatMap((_) => Re(_.userData.usdMaterialDiagnostics))), l = me(p.userData.usdSurfaceShaderId);
|
|
372
|
+
if (l && (Te.test(l) || kt.test(l))) {
|
|
373
|
+
const _ = await Xt(u, s, y, t), b = await Yt(u, s, t);
|
|
374
|
+
_.applied.push(...b.applied), _.resources.push(...b.resources);
|
|
375
|
+
const A = b.applied.length ? { applied: [], unsupported: [], bounded: !0 } : Te.test(l) ? zt(e, u, s, t) : jt(u, s, t);
|
|
376
|
+
_.applied.push(...A.applied);
|
|
377
|
+
const L = we(s.flatMap((W) => Re(W.userData.usdInstanceResolvedDiagnostics)));
|
|
378
|
+
_.resolved.push(...L), L.length && _.applied.push("instance.surface.constants"), f.push({
|
|
379
|
+
materialPath: r,
|
|
380
|
+
sourceShaderId: l,
|
|
381
|
+
action: _.applied.length ? "augmented" : "preserved",
|
|
382
|
+
fidelity: A.bounded || y.some((W) => !_.resolved.includes(W)) ? "bounded-approximation" : "native",
|
|
383
|
+
appliedInputs: _.applied,
|
|
384
|
+
unsupportedNodes: A.unsupported,
|
|
385
|
+
resources: _.resources,
|
|
386
|
+
loaderDiagnostics: y,
|
|
387
|
+
resolvedLoaderDiagnostics: _.resolved
|
|
388
|
+
});
|
|
389
|
+
continue;
|
|
390
|
+
}
|
|
391
|
+
const c = Le(u);
|
|
392
|
+
if (!c) {
|
|
393
|
+
const _ = Ze(e, r), b = u.shaders.map((A) => J(A.inputs["info:mdl:sourceAsset"])).filter(ke);
|
|
394
|
+
for (const A of b) t.diagnostics.droppedFeatures.push({ code: "USD_VISUAL_SHADER_NODE_UNSUPPORTED", source: "usd-visual", message: `USD 材质 ${r} 使用尚未支持的 MDL 材质 ${A};保留现有结果,未生成替代内容。` });
|
|
395
|
+
f.push({
|
|
396
|
+
materialPath: r,
|
|
397
|
+
sourceShaderId: b[0] ?? null,
|
|
398
|
+
action: "fallback",
|
|
399
|
+
fidelity: _ ? "authored-fallback" : "default-fallback",
|
|
400
|
+
appliedInputs: [],
|
|
401
|
+
unsupportedNodes: we(u.shaders.map((A) => A.id).filter(ke)),
|
|
402
|
+
resources: [],
|
|
403
|
+
loaderDiagnostics: y
|
|
404
|
+
});
|
|
405
|
+
continue;
|
|
406
|
+
}
|
|
407
|
+
if (je(c)) {
|
|
408
|
+
const _ = qt(e, s, c), b = _.applied.length ? await Qt(s, c, _, t) : [];
|
|
409
|
+
_.applied.length && b.push(...await Jt(s, c, _, t)), Be(t.diagnostics, r, c, _.applied, _.unsupported, b, _.applied.length ? "augmented" : "fallback"), f.push({
|
|
410
|
+
materialPath: r,
|
|
411
|
+
sourceShaderId: "OmniGlass",
|
|
412
|
+
action: _.applied.length ? "augmented" : "fallback",
|
|
413
|
+
fidelity: "bounded-approximation",
|
|
414
|
+
appliedInputs: _.applied,
|
|
415
|
+
unsupportedNodes: [..._.unsupported],
|
|
416
|
+
resources: b,
|
|
417
|
+
loaderDiagnostics: y
|
|
418
|
+
});
|
|
419
|
+
continue;
|
|
420
|
+
}
|
|
421
|
+
const w = [], g = [], m = /* @__PURE__ */ new Set(), U = en(s, c, w);
|
|
422
|
+
let E = !1;
|
|
423
|
+
if (xe(c)) {
|
|
424
|
+
const _ = J(O(c, ["diffuse_texture"]));
|
|
425
|
+
if (_) {
|
|
426
|
+
const S = await re(_, t);
|
|
427
|
+
if (g.push(S.report), S.url && ue(c, m) && s.every((I) => Y(I) && !I.map)) {
|
|
428
|
+
let I = null;
|
|
429
|
+
try {
|
|
430
|
+
I = await (t.createTexture ?? oe)(S.url, Je);
|
|
431
|
+
} catch (x) {
|
|
432
|
+
if (x instanceof Error && x.name === "AbortError") throw x;
|
|
433
|
+
g[g.length - 1] = { path: _, status: "decode-failed" };
|
|
434
|
+
}
|
|
435
|
+
if (I) {
|
|
436
|
+
for (const x of s)
|
|
437
|
+
Y(x) && (x.map = I, x.color.set(16777215), x.needsUpdate = !0, E = !0);
|
|
438
|
+
E ? w.push("diffuse_texture") : I.dispose();
|
|
439
|
+
}
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
const b = ae(c, ["enable_ORM_texture"], !1);
|
|
443
|
+
if (b) {
|
|
444
|
+
const S = J(O(c, ["ORM_texture"])), I = N(c, ["reflection_roughness_texture_influence"]) ?? 0, x = N(c, ["metallic_texture_influence"]) ?? 0;
|
|
445
|
+
N(c, ["ao_to_diffuse"]);
|
|
446
|
+
const Q = O(c, ["ORM_texture_colorspace"]);
|
|
447
|
+
if (Q !== void 0 && Q !== "raw") m.add("OmniPBR.ORM_texture_colorspace");
|
|
448
|
+
else if (I || x)
|
|
449
|
+
if (!S) m.add("OmniPBR.ORM_texture_missing");
|
|
450
|
+
else {
|
|
451
|
+
const k = await re(S, t);
|
|
452
|
+
if (g.push(k.report), k.url && ue(c, m)) {
|
|
453
|
+
let j = null, X = !1;
|
|
454
|
+
try {
|
|
455
|
+
j = await (t.createTexture ?? oe)(k.url, K), j.colorSpace = K, j.wrapS = q, j.wrapT = q;
|
|
456
|
+
const V = [
|
|
457
|
+
{
|
|
458
|
+
slot: "roughnessMap",
|
|
459
|
+
scalar: "roughness",
|
|
460
|
+
channel: "g",
|
|
461
|
+
influence: I,
|
|
462
|
+
constant: N(c, ["reflection_roughness_constant"]) ?? 0.5
|
|
463
|
+
},
|
|
464
|
+
{
|
|
465
|
+
slot: "metalnessMap",
|
|
466
|
+
scalar: "metalness",
|
|
467
|
+
channel: "b",
|
|
468
|
+
influence: x,
|
|
469
|
+
constant: N(c, ["metallic_constant"]) ?? 0
|
|
470
|
+
}
|
|
471
|
+
];
|
|
472
|
+
for (const G of V) {
|
|
473
|
+
if (!Number.isFinite(G.influence) || G.influence < 0 || G.influence > 1 || G.constant < 0 || G.constant > 1) {
|
|
474
|
+
m.add(`OmniPBR.${G.scalar}_ORM_range`);
|
|
475
|
+
continue;
|
|
476
|
+
}
|
|
477
|
+
const ce = s.filter(Y).filter((F) => !F[G.slot]);
|
|
478
|
+
if (ce.length) {
|
|
479
|
+
if (G.influence === 0) {
|
|
480
|
+
for (const F of ce) F[G.scalar] = G.constant;
|
|
481
|
+
continue;
|
|
482
|
+
}
|
|
483
|
+
try {
|
|
484
|
+
const F = G.influence === 1 ? j : de(
|
|
485
|
+
j,
|
|
486
|
+
G.channel,
|
|
487
|
+
G.influence,
|
|
488
|
+
G.constant * (1 - G.influence)
|
|
489
|
+
);
|
|
490
|
+
for (const H of ce)
|
|
491
|
+
H[G.slot] = F, H[G.scalar] = 1, H.needsUpdate = !0;
|
|
492
|
+
F === j && (X = !0), w.push(`${G.scalar}.ORM.${G.channel}`, `ORM.${G.scalar}.influence=${G.influence}`), E = !0;
|
|
493
|
+
} catch {
|
|
494
|
+
m.add(`OmniPBR.${G.scalar}_ORM_conversion`);
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
}
|
|
498
|
+
E && w.push("ORM_texture");
|
|
499
|
+
} catch (V) {
|
|
500
|
+
if (V instanceof Error && V.name === "AbortError") throw V;
|
|
501
|
+
g[g.length - 1] = { path: S, status: "decode-failed" };
|
|
502
|
+
} finally {
|
|
503
|
+
X || j == null || j.dispose();
|
|
504
|
+
}
|
|
505
|
+
}
|
|
506
|
+
}
|
|
507
|
+
}
|
|
508
|
+
if (!b && ue(c, m))
|
|
509
|
+
for (const S of [
|
|
510
|
+
{ file: "reflectionroughness_texture", weight: "reflection_roughness_texture_influence", constant: "reflection_roughness_constant", fallback: 0.5, map: "roughnessMap", scalar: "roughness" },
|
|
511
|
+
{ file: "metallic_texture", weight: "metallic_texture_influence", constant: "metallic_constant", fallback: 0, map: "metalnessMap", scalar: "metalness" }
|
|
512
|
+
]) {
|
|
513
|
+
const I = N(c, [S.weight]) ?? 0;
|
|
514
|
+
if (I === 0) continue;
|
|
515
|
+
if (I < 0 || I > 1) {
|
|
516
|
+
m.add(`OmniPBR.${S.weight}`);
|
|
517
|
+
continue;
|
|
518
|
+
}
|
|
519
|
+
const x = J(O(c, [S.file]));
|
|
520
|
+
if (!x) continue;
|
|
521
|
+
const Q = O(c, [`${S.file}_colorspace`]);
|
|
522
|
+
if (Q !== void 0 && Q !== "raw") {
|
|
523
|
+
m.add(`OmniPBR.${S.file}_colorspace`);
|
|
524
|
+
continue;
|
|
525
|
+
}
|
|
526
|
+
const k = await re(x, t);
|
|
527
|
+
g.push(k.report);
|
|
528
|
+
const j = s.filter(Y).filter((V) => !V[S.map]);
|
|
529
|
+
if (!k.url || !j.length) continue;
|
|
530
|
+
let X = null;
|
|
531
|
+
try {
|
|
532
|
+
X = await (t.createTexture ?? oe)(k.url, K);
|
|
533
|
+
const V = N(c, [S.constant]) ?? S.fallback, G = de(X, "grayscale", I, V * (1 - I));
|
|
534
|
+
G.wrapS = q, G.wrapT = q;
|
|
535
|
+
for (const ce of j)
|
|
536
|
+
ce[S.map] = G, ce[S.scalar] = 1, ce.needsUpdate = !0;
|
|
537
|
+
w.push(S.file), E = !0;
|
|
538
|
+
} catch (V) {
|
|
539
|
+
if (V instanceof Error && V.name === "AbortError") throw V;
|
|
540
|
+
m.add(`OmniPBR.${S.file}_conversion`);
|
|
541
|
+
} finally {
|
|
542
|
+
X == null || X.dispose();
|
|
543
|
+
}
|
|
544
|
+
}
|
|
545
|
+
const A = ae(c, ["enable_opacity"], !1), L = N(c, ["opacity_threshold"]) ?? 0;
|
|
546
|
+
if (A && L >= 0 && ae(c, ["enable_opacity_texture"], !1) && ue(c, m)) {
|
|
547
|
+
const S = J(O(c, ["opacity_texture"])), I = O(c, ["opacity_mode"]) ?? 1, x = I === 0 || I === "mono_alpha" ? "a" : I === 1 || I === "mono_average" ? "average" : I === 3 || I === "mono_maximum" ? "maximum" : null, Q = O(c, ["opacity_texture_colorspace"]);
|
|
548
|
+
if (Q !== void 0 && Q !== "raw") m.add("OmniPBR.opacity_texture_colorspace");
|
|
549
|
+
else if (!x) m.add("OmniPBR.opacity_mode");
|
|
550
|
+
else if (!S) m.add("OmniPBR.opacity_texture_missing");
|
|
551
|
+
else {
|
|
552
|
+
const k = await re(S, t);
|
|
553
|
+
g.push(k.report);
|
|
554
|
+
const j = s.filter(Y).filter((V) => !V.alphaMap);
|
|
555
|
+
let X = null;
|
|
556
|
+
if (k.url && j.length) try {
|
|
557
|
+
X = await (t.createTexture ?? oe)(k.url, K);
|
|
558
|
+
const V = de(X, x);
|
|
559
|
+
V.wrapS = q, V.wrapT = q;
|
|
560
|
+
for (const G of j)
|
|
561
|
+
G.alphaMap = V, G.opacity = 1, G.alphaTest = Math.max(0, L), G.transparent = L === 0, G.depthWrite = L > 0, G.needsUpdate = !0;
|
|
562
|
+
w.push("opacity_texture"), E = !0;
|
|
563
|
+
} catch (V) {
|
|
564
|
+
if (V instanceof Error && V.name === "AbortError") throw V;
|
|
565
|
+
g[g.length - 1] = { path: S, status: "decode-failed" };
|
|
566
|
+
} finally {
|
|
567
|
+
X == null || X.dispose();
|
|
568
|
+
}
|
|
569
|
+
}
|
|
570
|
+
}
|
|
571
|
+
const v = Ne(c, ["diffuse_tint"]);
|
|
572
|
+
if (v) {
|
|
573
|
+
for (const S of s)
|
|
574
|
+
Y(S) && (S.map ? S.color.copy(v) : S.color.copy(Ne(c, ["diffuse_color_constant"]) ?? new st(0.2, 0.2, 0.2)).multiply(v), S.needsUpdate = !0);
|
|
575
|
+
w.push("diffuse_tint"), E = !0;
|
|
576
|
+
}
|
|
577
|
+
const z = J(O(c, ["normalmap_texture"]));
|
|
578
|
+
if (z) {
|
|
579
|
+
const S = await re(z, t);
|
|
580
|
+
g.push(S.report);
|
|
581
|
+
const I = O(c, ["normalmap_texture_colorspace"]), x = N(c, ["bump_factor"]) ?? 1;
|
|
582
|
+
if (I !== void 0 && I !== "raw") m.add("OmniPBR.normalmap_texture_colorspace");
|
|
583
|
+
else if (!Number.isFinite(x) || x < 0) m.add("OmniPBR.bump_factor");
|
|
584
|
+
else if (S.url && ue(c, m)) {
|
|
585
|
+
const Q = s.filter(Y).filter((k) => !k.normalMap);
|
|
586
|
+
if (Q.length)
|
|
587
|
+
try {
|
|
588
|
+
const k = await (t.createTexture ?? oe)(S.url, K);
|
|
589
|
+
k.colorSpace = K, k.wrapS = q, k.wrapT = q;
|
|
590
|
+
for (const j of Q)
|
|
591
|
+
j.normalMap = k, j.normalScale.set(
|
|
592
|
+
x * (ae(c, ["flip_tangent_u"], !1) ? -1 : 1),
|
|
593
|
+
x * (ae(c, ["flip_tangent_v"], !0) ? -1 : 1)
|
|
594
|
+
), j.needsUpdate = !0;
|
|
595
|
+
w.push("normalmap_texture", "normal.tangent_convention"), E = !0;
|
|
596
|
+
} catch (k) {
|
|
597
|
+
if (k instanceof Error && k.name === "AbortError") throw k;
|
|
598
|
+
g[g.length - 1] = { path: z, status: "decode-failed" };
|
|
599
|
+
}
|
|
600
|
+
}
|
|
601
|
+
}
|
|
602
|
+
Zt(c, m), E = await Kt(s, c, w, m, g, t) || E;
|
|
603
|
+
}
|
|
604
|
+
const M = B(c, "diffuseColor") ?? B(c, "baseColor");
|
|
605
|
+
let R = !1;
|
|
606
|
+
if (M) {
|
|
607
|
+
const _ = he(u, M);
|
|
608
|
+
if (_ && ct(_)) {
|
|
609
|
+
const b = nn(_);
|
|
610
|
+
if (b) {
|
|
611
|
+
const A = await re(b.path, t);
|
|
612
|
+
g.push(A.report);
|
|
613
|
+
const L = B(_, "manifold");
|
|
614
|
+
L && m.add(((i = he(u, L)) == null ? void 0 : i.id) ?? L.path);
|
|
615
|
+
const W = Object.keys(_.inputs).filter((S) => !["inputs:filename", "inputs:resultRGB", "inputs:linearize"].includes(S)), v = _.inputs["inputs:linearize"], z = v === 0 || v === 1;
|
|
616
|
+
if (z || m.add("PxrTexture.colorSpace"), W.length > 0 && !L && m.add("PxrTexture.controls"), A.url && !L && W.length === 0 && z && M.outputName === "resultRGB" && s.every((S) => Y(S) && !S.map)) {
|
|
617
|
+
let S = null;
|
|
618
|
+
try {
|
|
619
|
+
S = await (t.createTexture ?? oe)(A.url, v === 1 ? Je : K);
|
|
620
|
+
} catch (I) {
|
|
621
|
+
if (I instanceof Error && I.name === "AbortError") throw I;
|
|
622
|
+
g[g.length - 1] = { path: b.path, status: "decode-failed" };
|
|
623
|
+
}
|
|
624
|
+
if (S) {
|
|
625
|
+
for (const I of s)
|
|
626
|
+
Y(I) && (I.map = S, I.color.set(16777215), I.needsUpdate = !0, R = !0);
|
|
627
|
+
R ? w.push("diffuseColor.texture") : S.dispose();
|
|
628
|
+
}
|
|
629
|
+
}
|
|
630
|
+
} else
|
|
631
|
+
m.add(_.id ?? _.path);
|
|
632
|
+
} else _ ? m.add(_.id ?? _.path) : m.add(M.path);
|
|
633
|
+
}
|
|
634
|
+
tn(u, c, m);
|
|
635
|
+
const D = U || R || E ? "augmented" : "fallback", P = Ze(e, r), C = D === "augmented" ? "bounded-approximation" : P ? "authored-fallback" : "default-fallback";
|
|
636
|
+
Be(t.diagnostics, r, c, w, m, g, D), f.push({
|
|
637
|
+
materialPath: r,
|
|
638
|
+
sourceShaderId: it(c),
|
|
639
|
+
action: D,
|
|
640
|
+
fidelity: C,
|
|
641
|
+
appliedInputs: we(w),
|
|
642
|
+
unsupportedNodes: [...m],
|
|
643
|
+
resources: g,
|
|
644
|
+
loaderDiagnostics: y
|
|
645
|
+
});
|
|
646
|
+
}
|
|
647
|
+
$t(e);
|
|
648
|
+
const d = f.filter((r) => r.loaderDiagnostics.some(
|
|
649
|
+
(s) => {
|
|
650
|
+
var u;
|
|
651
|
+
return !((u = r.resolvedLoaderDiagnostics) != null && u.includes(s)) && !(r.action === "augmented" && s === `Material ${r.materialPath} has no supported surface shader.`);
|
|
652
|
+
}
|
|
653
|
+
));
|
|
654
|
+
return d.length > 0 && t.diagnostics.droppedFeatures.push({
|
|
655
|
+
code: "USD_VISUAL_LOADER_DIAGNOSTIC",
|
|
656
|
+
message: `${d.length} 个 USD 材质仍有尚未被视觉适配层消解的 Loader 限制;具体材质和原始诊断见 visualAdaptation 报告。`,
|
|
657
|
+
source: "usd-visual"
|
|
658
|
+
}), Object.freeze({
|
|
659
|
+
schemaVersion: 1,
|
|
660
|
+
materials: f,
|
|
661
|
+
summary: Object.freeze({
|
|
662
|
+
preserved: f.filter((r) => r.action === "preserved").length,
|
|
663
|
+
augmented: f.filter((r) => r.action === "augmented").length,
|
|
664
|
+
fallback: f.filter((r) => r.action === "fallback").length,
|
|
665
|
+
missingResources: f.flatMap((r) => r.resources).filter((r) => r.status === "missing").length,
|
|
666
|
+
unsupportedResources: f.flatMap((r) => r.resources).filter((r) => r.status === "unsupported-format").length
|
|
667
|
+
})
|
|
668
|
+
});
|
|
669
|
+
}
|
|
670
|
+
function zt(e, t, n, o) {
|
|
671
|
+
var y;
|
|
672
|
+
const a = { applied: [], unsupported: [], bounded: !1 }, h = me((y = n[0]) == null ? void 0 : y.userData.usdSurfaceShaderPath), f = t.shaders.filter((l) => Te.test(l.id ?? "")), d = h ? f.find((l) => l.path === h) : f.length === 1 ? f[0] : void 0;
|
|
673
|
+
if (!d) return a;
|
|
674
|
+
const i = N(d, ["opacity"]), r = O(d, ["opacityMode"]) ?? "transparent", s = N(d, ["opacityThreshold"]) ?? 0, u = (l) => (a.bounded = !0, a.unsupported.push(l), o.diagnostics.droppedFeatures.push({
|
|
675
|
+
code: "USD_VISUAL_PREVIEW_TRANSPARENCY_UNSUPPORTED",
|
|
676
|
+
source: "usd-visual",
|
|
677
|
+
message: `USD 材质 ${t.path} 的 ${l} 未完成透明适配,保留 Loader 输出;未生成替代内容。`
|
|
678
|
+
}), a);
|
|
679
|
+
if (B(d, "opacity") || B(d, "opacityThreshold") || B(d, "opacityMode")) return u("connected opacity/threshold/mode");
|
|
680
|
+
if (s > 0 || r === "presence") {
|
|
681
|
+
if (n.some((c) => !Y(c) || c.alphaMap || c.map)) return u("textured coverage/cutout");
|
|
682
|
+
const l = Ee(i ?? 1);
|
|
683
|
+
for (const c of n)
|
|
684
|
+
c.opacity = s > 0 ? l >= s ? 1 : 0 : l, c.alphaTest = s > 0 ? 0.5 : 0, c.transparent = s === 0 && l < 1, c.depthWrite = !c.transparent, c instanceof ie && (c.transmission = 0), c.needsUpdate = !0;
|
|
685
|
+
return a.applied.push(s > 0 ? "PreviewSurface.cutout.constant" : "PreviewSurface.presence.constant"), a;
|
|
686
|
+
}
|
|
687
|
+
if (r !== "transparent") return u(`opacityMode=${String(r)}`);
|
|
688
|
+
if (i === null || i >= 1) return a;
|
|
689
|
+
if (!B(d, "metallic") && N(d, ["metallic"]) === 1 && !B(d, "useSpecularWorkflow") && [void 0, !1, 0].includes(O(d, ["useSpecularWorkflow"]))) {
|
|
690
|
+
if (n.some((l) => !Y(l) || l.alphaMap || l.map || l.metalnessMap || l.alphaTest > 0)) return u("textured metal transparency");
|
|
691
|
+
for (const l of n)
|
|
692
|
+
Y(l) && (l.opacity = 1, l.transparent = !1, l.depthWrite = !0, l.metalness = 1, l instanceof ie && (l.transmission = 0), l.needsUpdate = !0);
|
|
693
|
+
return a.applied.push("PreviewSurface.transparent.pure-metal"), a;
|
|
694
|
+
}
|
|
695
|
+
if (B(d, "metallic") || B(d, "useSpecularWorkflow") || B(d, "ior") || (N(d, ["metallic"]) ?? 0) !== 0 || ![void 0, !1, 0].includes(O(d, ["useSpecularWorkflow"]))) return u("non-dielectric or connected transparency");
|
|
696
|
+
if (n.some((l) => !Y(l) || l.alphaMap || l.map || l.metalnessMap || l.alphaTest > 0)) return u("textured or non-standard transparency");
|
|
697
|
+
const p = /* @__PURE__ */ new Map();
|
|
698
|
+
for (const l of n) {
|
|
699
|
+
if (!Y(l)) continue;
|
|
700
|
+
const c = l instanceof ie ? l : new ie();
|
|
701
|
+
c !== l && (ze.prototype.copy.call(c, l), c.defines = { STANDARD: "", PHYSICAL: "" }, p.set(l, c)), c.opacity = 1, c.transparent = !1, c.transmission = 1 - Ee(i), c.ior = N(d, ["ior"]) ?? 1.5, c.depthWrite = !0, c.needsUpdate = !0;
|
|
702
|
+
}
|
|
703
|
+
if (p.size) {
|
|
704
|
+
e.scene.traverse((l) => {
|
|
705
|
+
l instanceof te && (l.material = Array.isArray(l.material) ? l.material.map((c) => p.get(c) ?? c) : p.get(l.material) ?? l.material);
|
|
706
|
+
}), n.forEach((l, c) => {
|
|
707
|
+
n[c] = p.get(l) ?? l;
|
|
708
|
+
});
|
|
709
|
+
for (const l of p.keys()) l.dispose();
|
|
710
|
+
}
|
|
711
|
+
return a.applied.push("PreviewSurface.transparent.constant-dielectric"), a.bounded = !0, o.diagnostics.approximations.push({
|
|
712
|
+
code: "USD_VISUAL_PREVIEW_TRANSMISSION_APPROXIMATION",
|
|
713
|
+
source: "usd-visual",
|
|
714
|
+
message: `USD 材质 ${t.path} 的常量介质透明已映射为实时透射;保留表面反射;Three.js 透射与反射共用粗糙度,不等同于 PreviewSurface 的零粗糙度透射。不推断壁厚或体积吸收,不保证多层折射与路径追踪等价。`
|
|
715
|
+
}), a;
|
|
716
|
+
}
|
|
717
|
+
function jt(e, t, n) {
|
|
718
|
+
var s;
|
|
719
|
+
const o = { applied: [], unsupported: [], bounded: !1 }, a = me((s = t[0]) == null ? void 0 : s.userData.usdSurfaceShaderPath), h = e.shaders.filter((u) => u.id === "ND_standard_surface_surfaceshader"), f = a ? h.find((u) => u.path === a) : h.length === 1 ? h[0] : void 0;
|
|
720
|
+
if (!f) return o;
|
|
721
|
+
const d = (u) => {
|
|
722
|
+
o.bounded = !0, o.unsupported.push(u), n.diagnostics.droppedFeatures.push({
|
|
723
|
+
code: "USD_VISUAL_MATERIALX_TRANSPARENCY_UNSUPPORTED",
|
|
724
|
+
source: "usd-visual",
|
|
725
|
+
message: `USD 材质 ${e.path} 的 MaterialX ${u} 尚未完整适配;不猜测厚度或生成替代内容。`
|
|
726
|
+
});
|
|
727
|
+
}, i = O(f, ["opacity"]);
|
|
728
|
+
if (B(f, "opacity")) d("connected opacity");
|
|
729
|
+
else if (Array.isArray(i) && i.length === 3 && i.every((u) => typeof u == "number" && Number.isFinite(u)))
|
|
730
|
+
if (i[0] !== i[1] || i[1] !== i[2]) d("colored opacity");
|
|
731
|
+
else if (t.some((u) => !Y(u) || u.alphaMap || u.map)) d("textured coverage");
|
|
732
|
+
else {
|
|
733
|
+
const u = Ee(i[0]);
|
|
734
|
+
for (const p of t)
|
|
735
|
+
p.opacity = u, p.transparent = u < 1, p.depthWrite = u === 1, p.needsUpdate = !0;
|
|
736
|
+
o.applied.push("MaterialX.opacity.achromatic-constant");
|
|
737
|
+
}
|
|
738
|
+
const r = N(f, ["transmission"]) ?? 0;
|
|
739
|
+
return B(f, "transmission") && d("connected transmission"), r > 0 && (o.bounded = !0, Array.isArray(i) && i.some((u) => typeof u == "number" && u > 0 && u < 1) && d("fractional coverage + transmission compositing"), ae(f, ["thin_walled"], !1) ? n.diagnostics.approximations.push({
|
|
740
|
+
code: "USD_VISUAL_MATERIALX_TRANSMISSION_APPROXIMATION",
|
|
741
|
+
source: "usd-visual",
|
|
742
|
+
message: `USD 材质 ${e.path} 的 MaterialX 薄壁透射使用 Loader 的实时近似;并非完整 MaterialX 着色器执行。`
|
|
743
|
+
}) : d("solid transmission / absorption path length")), o;
|
|
744
|
+
}
|
|
745
|
+
async function Yt(e, t, n) {
|
|
746
|
+
var D;
|
|
747
|
+
const o = { applied: [], resources: [] }, a = me((D = t[0]) == null ? void 0 : D.userData.usdSurfaceShaderPath), h = e.shaders.filter((P) => Te.test(P.id ?? "")), f = a ? h.find((P) => P.path === a) : h.length === 1 ? h[0] : void 0;
|
|
748
|
+
if (!f || B(f, "opacityThreshold") || B(f, "opacityMode")) return o;
|
|
749
|
+
const d = N(f, ["opacityThreshold"]) ?? 0;
|
|
750
|
+
if (d <= 0 && O(f, ["opacityMode"]) !== "presence") return o;
|
|
751
|
+
const i = B(f, "opacity");
|
|
752
|
+
if (!(i != null && i.outputName) || !["r", "g", "b", "a"].includes(i.outputName)) return o;
|
|
753
|
+
const r = he(e, i);
|
|
754
|
+
if (!r || r.id !== "UsdUVTexture" || O(r, ["sourceColorSpace"]) !== "raw") return o;
|
|
755
|
+
const s = B(r, "st"), u = s && he(e, s);
|
|
756
|
+
if (!u || u.id !== "UsdPrimvarReader_float2" || O(u, ["varname"]) !== "st" || t.some((P) => !Y(P) || P.map)) return o;
|
|
757
|
+
const p = "rgba".indexOf(i.outputName), y = (P, C) => {
|
|
758
|
+
if (B(r, P)) return null;
|
|
759
|
+
const _ = r.inputs[`inputs:${P}`];
|
|
760
|
+
return _ === void 0 ? C : Array.isArray(_) && _.length === 4 && _.every(Number.isFinite) ? _[p] : null;
|
|
761
|
+
}, l = y("scale", 1), c = y("bias", 0);
|
|
762
|
+
if (l === null || c === null) return o;
|
|
763
|
+
const w = (P) => {
|
|
764
|
+
const C = O(r, [P]);
|
|
765
|
+
return C === "repeat" ? q : C === "mirror" ? rt : C === "clamp" ? ot : null;
|
|
766
|
+
}, g = w("wrapS"), m = w("wrapT"), U = J(O(r, ["file"]));
|
|
767
|
+
if (!U || g === null || m === null) return o;
|
|
768
|
+
const E = JSON.stringify([r.path, i.outputName, l, c, g, m, d]);
|
|
769
|
+
if (t.every((P) => {
|
|
770
|
+
var C;
|
|
771
|
+
return Y(P) && ((C = P.alphaMap) == null ? void 0 : C.userData.usdCoverageConversionKey) === E;
|
|
772
|
+
}))
|
|
773
|
+
return o.applied.push(`PreviewSurface.opacity.texture.${i.outputName}->g`), o.resources.push({ path: U, status: "available" }), o;
|
|
774
|
+
const M = await re(U, n);
|
|
775
|
+
o.resources.push(M.report);
|
|
776
|
+
let R = null;
|
|
777
|
+
try {
|
|
778
|
+
if (!M.url) return o;
|
|
779
|
+
R = await (n.createTexture ?? oe)(M.url, K);
|
|
780
|
+
const P = de(R, i.outputName, l, c);
|
|
781
|
+
P.wrapS = g, P.wrapT = m, P.userData.usdCoverageConversionKey = E;
|
|
782
|
+
for (const C of t)
|
|
783
|
+
Y(C) && (C.alphaMap = P, C.opacity = 1, C.alphaTest = d > 0 ? d : 0, C.transparent = d <= 0, C.depthWrite = d > 0, C instanceof ie && (C.transmission = 0), C.needsUpdate = !0);
|
|
784
|
+
o.applied.push(`PreviewSurface.opacity.texture.${i.outputName}->g`), n.diagnostics.approximations.push({
|
|
785
|
+
code: "USD_VISUAL_COVERAGE_TEXTURE_APPROXIMATION",
|
|
786
|
+
source: "usd-visual",
|
|
787
|
+
message: `USD 材质 ${e.path} 的透明遮罩已按源通道转换;采用 8 位纹理重排,阈值边缘与过滤结果不保证跨渲染器逐像素一致。`
|
|
788
|
+
});
|
|
789
|
+
} catch (P) {
|
|
790
|
+
if (P instanceof Error && P.name === "AbortError") throw P;
|
|
791
|
+
o.resources[0] = { path: U, status: "decode-failed" };
|
|
792
|
+
} finally {
|
|
793
|
+
R == null || R.dispose();
|
|
794
|
+
}
|
|
795
|
+
return o;
|
|
796
|
+
}
|
|
797
|
+
async function Xt(e, t, n, o) {
|
|
798
|
+
var R;
|
|
799
|
+
const a = { applied: [], resolved: [], resources: [] }, h = me((R = t[0]) == null ? void 0 : R.userData.usdSurfaceShaderPath), f = e.shaders.find((D) => D.path === h) ?? e.shaders.find((D) => D.id === "UsdPreviewSurface");
|
|
800
|
+
if (!f || f.id !== "UsdPreviewSurface") return a;
|
|
801
|
+
const d = B(f, "roughness");
|
|
802
|
+
if (!d || !d.outputName || !["r", "g", "b", "a"].includes(d.outputName)) return a;
|
|
803
|
+
const i = he(e, d);
|
|
804
|
+
if (!i || i.id !== "UsdUVTexture") return a;
|
|
805
|
+
const r = `Texture output ${d.outputName} from ${i.path} cannot be mapped to Three.js roughness without channel repacking.`;
|
|
806
|
+
if (!n.includes(r) || O(i, ["sourceColorSpace"]) !== "raw") return a;
|
|
807
|
+
const s = B(i, "st");
|
|
808
|
+
if (s) {
|
|
809
|
+
const D = he(e, s);
|
|
810
|
+
if ((D == null ? void 0 : D.id) !== "UsdPrimvarReader_float2" || O(D, ["varname"]) !== "st") return a;
|
|
811
|
+
} else if (i.inputs["inputs:st"] !== void 0) return a;
|
|
812
|
+
const u = "rgba".indexOf(d.outputName);
|
|
813
|
+
function p(D, P) {
|
|
814
|
+
if (B(i, D)) return null;
|
|
815
|
+
const C = i.inputs[`inputs:${D}`];
|
|
816
|
+
return C === void 0 ? P : Array.isArray(C) && C.length === 4 && C.every(Number.isFinite) ? C[u] : null;
|
|
817
|
+
}
|
|
818
|
+
const y = p("scale", 1), l = p("bias", 0);
|
|
819
|
+
if (y === null || l === null) return a;
|
|
820
|
+
function c(D) {
|
|
821
|
+
if (B(i, D)) return null;
|
|
822
|
+
const P = i.inputs[`inputs:${D}`];
|
|
823
|
+
return P === "repeat" ? q : P === "mirror" ? rt : P === "clamp" ? ot : null;
|
|
824
|
+
}
|
|
825
|
+
const w = c("wrapS"), g = c("wrapT");
|
|
826
|
+
if (w === null || g === null) return a;
|
|
827
|
+
const m = J(O(i, ["file"]));
|
|
828
|
+
if (!m) return a;
|
|
829
|
+
const U = t.filter(Y);
|
|
830
|
+
if (!U.length) return a;
|
|
831
|
+
if (U.every((D) => {
|
|
832
|
+
var P;
|
|
833
|
+
return ((P = D.roughnessMap) == null ? void 0 : P.userData.usdResolvedChannelDiagnostic) === r;
|
|
834
|
+
}))
|
|
835
|
+
return a.applied.push(`roughness.texture.${d.outputName}->g`), a.resolved.push(r), a;
|
|
836
|
+
if (U.some((D) => D.roughnessMap !== null)) return a;
|
|
837
|
+
const E = await re(m, o);
|
|
838
|
+
a.resources.push(E.report);
|
|
839
|
+
let M = null;
|
|
840
|
+
if (E.url)
|
|
841
|
+
try {
|
|
842
|
+
M = await (o.createTexture ?? oe)(E.url, K);
|
|
843
|
+
const D = de(M, d.outputName, y, l);
|
|
844
|
+
D.wrapS = w, D.wrapT = g, D.userData.usdResolvedChannelDiagnostic = r;
|
|
845
|
+
for (const P of U)
|
|
846
|
+
P.roughnessMap = D, P.roughness = 1, P.needsUpdate = !0;
|
|
847
|
+
a.applied.push(`roughness.texture.${d.outputName}->g`), a.resolved.push(r);
|
|
848
|
+
} catch (D) {
|
|
849
|
+
if (D instanceof Error && D.name === "AbortError") throw D;
|
|
850
|
+
a.resources[0] = { path: m, status: "decode-failed" };
|
|
851
|
+
} finally {
|
|
852
|
+
M == null || M.dispose();
|
|
853
|
+
}
|
|
854
|
+
return Be(o.diagnostics, e.path, f, [], /* @__PURE__ */ new Set(), a.resources, "preserved"), a;
|
|
855
|
+
}
|
|
856
|
+
function Ht(e) {
|
|
857
|
+
const t = /* @__PURE__ */ new Map(), n = /* @__PURE__ */ new Set();
|
|
858
|
+
return e.scene.traverse((o) => {
|
|
859
|
+
if (o instanceof te)
|
|
860
|
+
for (const a of Array.isArray(o.material) ? o.material : [o.material]) {
|
|
861
|
+
if (n.has(a)) continue;
|
|
862
|
+
n.add(a);
|
|
863
|
+
const h = me(a.userData.usdMaterialPath);
|
|
864
|
+
if (!h) continue;
|
|
865
|
+
const f = t.get(h);
|
|
866
|
+
f ? f.push(a) : t.set(h, [a]);
|
|
867
|
+
}
|
|
868
|
+
}), t;
|
|
869
|
+
}
|
|
870
|
+
function Le(e) {
|
|
871
|
+
const t = e.shaders.filter((n) => /^PxrSurface$/i.test(n.id ?? "") || xe(n) || je(n));
|
|
872
|
+
return t.length === 1 ? t[0] : null;
|
|
873
|
+
}
|
|
874
|
+
function je(e) {
|
|
875
|
+
var o;
|
|
876
|
+
const t = J(e.inputs["info:mdl:sourceAsset"]), n = e.inputs["info:mdl:sourceAsset:subIdentifier"];
|
|
877
|
+
return ((o = t == null ? void 0 : t.replaceAll("\\", "/").split("/").at(-1)) == null ? void 0 : o.toLowerCase()) === "omniglass.mdl" && (n === void 0 || n === "OmniGlass");
|
|
878
|
+
}
|
|
879
|
+
function qt(e, t, n) {
|
|
880
|
+
const o = { applied: [], unsupported: /* @__PURE__ */ new Set() }, a = /* @__PURE__ */ new Set(["glass_color", "glass_ior", "frosting_roughness", "thin_walled", "reflection_color", "enable_opacity", "cutout_opacity", "opacity_constant", "opacity_threshold"]);
|
|
881
|
+
for (const [m, U] of Object.entries(n.inputs)) {
|
|
882
|
+
if (!m.startsWith("inputs:")) continue;
|
|
883
|
+
const E = m.slice(7);
|
|
884
|
+
a.has(E) || ["glass_color_texture", "roughness_texture", "normalmap_texture"].includes(E) && !J(U) || o.unsupported.add(`OmniGlass.${E}`);
|
|
885
|
+
}
|
|
886
|
+
const h = (m) => (o.unsupported.add(`OmniGlass.${m}`), o);
|
|
887
|
+
for (const m of a) if (B(n, m)) return h(`${m}.connection`);
|
|
888
|
+
const f = N(n, ["glass_ior"]) ?? 1.491, d = N(n, ["frosting_roughness"]) ?? 0, i = O(n, ["thin_walled"]) ?? !1, r = O(n, ["glass_color"]) ?? [1, 1, 1], s = O(n, ["reflection_color"]) ?? [1, 1, 1];
|
|
889
|
+
if (!Array.isArray(s) || s.length !== 3 || !s.every((m) => typeof m == "number" && Number.isFinite(m) && m >= 0 && m <= 1)) return h("reflection_color.range");
|
|
890
|
+
if (O(n, ["glass_ior"]) !== void 0 && N(n, ["glass_ior"]) === null || f < 1 || f > 2.333) return h("glass_ior.range");
|
|
891
|
+
if (O(n, ["frosting_roughness"]) !== void 0 && N(n, ["frosting_roughness"]) === null || d < 0 || d > 1) return h("frosting_roughness.range");
|
|
892
|
+
if (typeof i != "boolean") return h("thin_walled.type");
|
|
893
|
+
if (!Array.isArray(r) || r.length !== 3 || !r.every((m) => typeof m == "number" && Number.isFinite(m) && m >= 0 && m <= 1)) return h("glass_color.range");
|
|
894
|
+
if (t.some((m) => !Y(m))) return h("non-standard-loader-material");
|
|
895
|
+
if (t.some((m) => Y(m) && (m.map || m.alphaMap || m.roughnessMap || m.metalnessMap))) return h("existing-loader-texture-semantics");
|
|
896
|
+
i || o.unsupported.add("OmniGlass.solid_volume_absorption"), i && r.some((m) => m !== 1) && o.unsupported.add("OmniGlass.tint_reflection_coupling"), !i && r.some((m) => m !== 1) && o.unsupported.add("OmniGlass.glass_color.volume");
|
|
897
|
+
const u = O(n, ["enable_opacity"]) ?? !1;
|
|
898
|
+
if (typeof u != "boolean") return h("enable_opacity.type");
|
|
899
|
+
const p = N(n, ["cutout_opacity"]), y = N(n, ["opacity_constant"]);
|
|
900
|
+
if (u && p !== null && y !== null && Math.abs(p - y) > 1e-6) return h("opacity.alias-conflict");
|
|
901
|
+
for (const m of ["cutout_opacity", "opacity_constant", "opacity_threshold"]) if (u && O(n, [m]) !== void 0 && N(n, [m]) === null) return h(`${m}.type`);
|
|
902
|
+
const l = u ? p ?? y ?? 1 : 1, c = u ? N(n, ["opacity_threshold"]) ?? 0 : 0;
|
|
903
|
+
if (l < 0 || l > 1 || c < 0 || c > 1) return h("opacity.range");
|
|
904
|
+
if (u && (J(O(n, ["opacity_texture"])) || B(n, "opacity_texture"))) return h("opacity_texture");
|
|
905
|
+
const w = c > 0 ? l >= c ? 1 : 0 : l, g = /* @__PURE__ */ new Map();
|
|
906
|
+
for (const m of t) {
|
|
907
|
+
const U = m instanceof ie ? m : new ie();
|
|
908
|
+
U !== m && (ze.prototype.copy.call(U, m), U.defines = { STANDARD: "", PHYSICAL: "" }, g.set(m, U)), U.color.setRGB(...i ? r : [1, 1, 1]), U.specularColor.setRGB(...s), U.metalness = 0, U.roughness = d, U.ior = f, U.opacity = w, U.transparent = c === 0 && w < 1, U.alphaTest = c > 0 ? 0.5 : 0, U.transmission = 1, U.thickness = 0, U.depthWrite = !U.transparent, U.attenuationColor.setRGB(1, 1, 1), U.attenuationDistance = 1 / 0, U.needsUpdate = !0;
|
|
909
|
+
}
|
|
910
|
+
e.scene.traverse((m) => {
|
|
911
|
+
m instanceof te && (m.material = Array.isArray(m.material) ? m.material.map((U) => g.get(U) ?? U) : g.get(m.material) ?? m.material);
|
|
912
|
+
}), t.forEach((m, U) => {
|
|
913
|
+
t[U] = g.get(m) ?? m;
|
|
914
|
+
});
|
|
915
|
+
for (const m of g.keys()) m.dispose();
|
|
916
|
+
return o.applied.push("OmniGlass.reflection_color.specular-approximation", "OmniGlass.glass_ior", "OmniGlass.frosting_roughness", "OmniGlass.surface_transmission"), u && o.applied.push("OmniGlass.opacity.constant-coverage"), w > 0 && w < 1 && o.unsupported.add("OmniGlass.fractional_coverage_transmission_compositing"), i && o.applied.push("OmniGlass.thin_walled", "OmniGlass.glass_color.surface-approximation"), o;
|
|
917
|
+
}
|
|
918
|
+
async function Jt(e, t, n, o) {
|
|
919
|
+
const a = [], h = ["normalmap_texture", "normalmap_texture_colorspace", "bump_factor", "flip_tangent_u", "flip_tangent_v"], f = () => h.forEach((c) => n.unsupported.delete(`OmniGlass.${c}`));
|
|
920
|
+
if (h.some((c) => B(t, c))) return a;
|
|
921
|
+
const d = J(O(t, ["normalmap_texture"]));
|
|
922
|
+
if (!d)
|
|
923
|
+
return f(), a;
|
|
924
|
+
const i = N(t, ["bump_factor"]) ?? 1;
|
|
925
|
+
if (O(t, ["bump_factor"]) !== void 0 && N(t, ["bump_factor"]) === null || i < 0) return a;
|
|
926
|
+
if (i === 0)
|
|
927
|
+
return f(), a;
|
|
928
|
+
const r = O(t, ["flip_tangent_u"]) ?? !1, s = O(t, ["flip_tangent_v"]) ?? !0;
|
|
929
|
+
if (typeof r != "boolean" || typeof s != "boolean" || O(t, ["normalmap_texture_colorspace"]) !== "raw" || ["project_uvw", "world_or_object", "uv_space_index", "texture_scale", "texture_translate", "texture_rotate"].some((c) => B(t, c)) || !ue(t, /* @__PURE__ */ new Set())) return a;
|
|
930
|
+
const p = e.filter((c) => c instanceof ie);
|
|
931
|
+
if (!p.length || p.some((c) => c.normalMap))
|
|
932
|
+
return n.unsupported.add("OmniGlass.existing_normalMap"), a;
|
|
933
|
+
const y = await re(d, o);
|
|
934
|
+
if (a.push(y.report), !y.url) return a;
|
|
935
|
+
let l = null;
|
|
936
|
+
try {
|
|
937
|
+
l = await (o.createTexture ?? oe)(y.url, K), l.colorSpace = K, l.wrapS = q, l.wrapT = q, l.channel = 0;
|
|
938
|
+
for (const c of p)
|
|
939
|
+
c.normalMap = l, c.normalScale.set(i * (r ? -1 : 1), i * (s ? -1 : 1)), c.needsUpdate = !0;
|
|
940
|
+
f(), n.applied.push("OmniGlass.normalmap_texture", "OmniGlass.normal.tangent_convention"), l = null;
|
|
941
|
+
} catch (c) {
|
|
942
|
+
if (c instanceof Error && c.name === "AbortError") throw c;
|
|
943
|
+
a[0] = { path: d, status: "decode-failed" };
|
|
944
|
+
} finally {
|
|
945
|
+
l == null || l.dispose();
|
|
946
|
+
}
|
|
947
|
+
return a;
|
|
948
|
+
}
|
|
949
|
+
async function Qt(e, t, n, o) {
|
|
950
|
+
const a = [], h = J(O(t, ["roughness_texture"]));
|
|
951
|
+
if (!h) return a;
|
|
952
|
+
const f = N(t, ["roughness_texture_influence"]) ?? 1;
|
|
953
|
+
if (B(t, "roughness_texture_influence") || f < 0 || f > 1 || O(t, ["roughness_texture_influence"]) !== void 0 && N(t, ["roughness_texture_influence"]) === null) return a;
|
|
954
|
+
if (f === 0)
|
|
955
|
+
return n.unsupported.delete("OmniGlass.roughness_texture"), n.unsupported.delete("OmniGlass.roughness_texture_influence"), a;
|
|
956
|
+
if (O(t, ["roughness_texture_colorspace"]) !== "raw" || ["project_uvw", "uv_space_index", "texture_scale", "texture_translate", "texture_rotate"].some((u) => B(t, u)) || !ue(t, /* @__PURE__ */ new Set())) return a;
|
|
957
|
+
const r = await re(h, o);
|
|
958
|
+
if (a.push(r.report), !r.url) return a;
|
|
959
|
+
let s = null;
|
|
960
|
+
try {
|
|
961
|
+
s = await (o.createTexture ?? oe)(r.url, K);
|
|
962
|
+
const u = N(t, ["frosting_roughness"]) ?? 0, p = de(s, "grayscale", f, u * (1 - f));
|
|
963
|
+
p.wrapS = q, p.wrapT = q;
|
|
964
|
+
for (const y of e) y instanceof ie && (y.roughnessMap = p, y.roughness = 1, y.needsUpdate = !0);
|
|
965
|
+
n.applied.push("OmniGlass.roughness_texture.grayscale-linear-blend");
|
|
966
|
+
for (const y of ["roughness_texture", "roughness_texture_influence", "roughness_texture_colorspace"]) n.unsupported.delete(`OmniGlass.${y}`);
|
|
967
|
+
} catch (u) {
|
|
968
|
+
if (u instanceof Error && u.name === "AbortError") throw u;
|
|
969
|
+
n.unsupported.add("OmniGlass.roughness_texture.pixel-conversion");
|
|
970
|
+
} finally {
|
|
971
|
+
s == null || s.dispose();
|
|
972
|
+
}
|
|
973
|
+
return a;
|
|
974
|
+
}
|
|
975
|
+
function xe(e) {
|
|
976
|
+
var n;
|
|
977
|
+
const t = J(e.inputs["info:mdl:sourceAsset"]);
|
|
978
|
+
return ((n = t == null ? void 0 : t.replaceAll("\\", "/").split("/").at(-1)) == null ? void 0 : n.toLowerCase()) === "omnipbr.mdl";
|
|
979
|
+
}
|
|
980
|
+
function it(e) {
|
|
981
|
+
return xe(e) ? "OmniPBR" : je(e) ? "OmniGlass" : e.id;
|
|
982
|
+
}
|
|
983
|
+
function ue(e, t) {
|
|
984
|
+
const n = Ke(e, "texture_scale", [1, 1]), o = Ke(e, "texture_translate", [0, 0]), a = N(e, ["texture_rotate"]) ?? 0, h = ae(e, ["project_uvw"], !1), f = N(e, ["uv_space_index"]) ?? 0, d = !h && f === 0 && n[0] === 1 && n[1] === 1 && o[0] === 0 && o[1] === 0 && a === 0;
|
|
985
|
+
return d || t.add("OmniPBR.uvTransform"), d;
|
|
986
|
+
}
|
|
987
|
+
async function Kt(e, t, n, o, a, h) {
|
|
988
|
+
const f = () => {
|
|
989
|
+
for (const y of ["ao_texture", "ao_texture_colorspace", "ao_to_diffuse"]) o.delete(`OmniPBR.${y}`);
|
|
990
|
+
};
|
|
991
|
+
if (B(t, "ao_to_diffuse"))
|
|
992
|
+
return o.add("OmniPBR.ao_to_diffuse.connection"), !1;
|
|
993
|
+
const d = N(t, ["ao_to_diffuse"]) ?? 0;
|
|
994
|
+
if (O(t, ["ao_to_diffuse"]) !== void 0 && N(t, ["ao_to_diffuse"]) === null || d < 0 || d > 1)
|
|
995
|
+
return o.add("OmniPBR.ao_to_diffuse.range"), !1;
|
|
996
|
+
if (d === 0)
|
|
997
|
+
return f(), !1;
|
|
998
|
+
if (B(t, "enable_ORM_texture"))
|
|
999
|
+
return o.add("OmniPBR.enable_ORM_texture.connection"), !1;
|
|
1000
|
+
const i = ae(t, ["enable_ORM_texture"], !1), r = i ? "ORM_texture" : "ao_texture";
|
|
1001
|
+
if (B(t, r))
|
|
1002
|
+
return o.add(`OmniPBR.${r}.connection`), !1;
|
|
1003
|
+
const s = J(O(t, [r]));
|
|
1004
|
+
if (!s)
|
|
1005
|
+
return f(), !1;
|
|
1006
|
+
if (O(t, [`${r}_colorspace`]) !== "raw")
|
|
1007
|
+
return o.add(`OmniPBR.${r}_colorspace`), !1;
|
|
1008
|
+
if (!ue(t, o)) return !1;
|
|
1009
|
+
const u = await re(s, h);
|
|
1010
|
+
if (a.push(u.report), !u.url) return !1;
|
|
1011
|
+
let p = null;
|
|
1012
|
+
try {
|
|
1013
|
+
p = await (h.createTexture ?? oe)(u.url, K);
|
|
1014
|
+
const y = de(p, i ? "r" : "grayscale");
|
|
1015
|
+
y.wrapS = q, y.wrapT = q, y.channel = 0;
|
|
1016
|
+
const l = e.filter(Y).filter((c) => !c.aoMap);
|
|
1017
|
+
if (!l.length)
|
|
1018
|
+
return y.dispose(), o.add("OmniPBR.existing_aoMap"), !1;
|
|
1019
|
+
for (const c of l)
|
|
1020
|
+
c.aoMap = y, c.aoMapIntensity = d, c.needsUpdate = !0;
|
|
1021
|
+
return f(), n.push(i ? "OmniPBR.ORM.r.aoMap" : "OmniPBR.ao_texture.aoMap"), h.diagnostics.approximations.push({ code: "USD_VISUAL_AO_LIGHTING_APPROXIMATION", source: "usd-visual", message: `USD 材质 AO 已映射为 Three.js 间接光遮蔽(${t.path});并非 OmniPBR 对漫反射贴图的等价调制。` }), !0;
|
|
1022
|
+
} catch (y) {
|
|
1023
|
+
if (y instanceof Error && y.name === "AbortError") throw y;
|
|
1024
|
+
return o.add(`OmniPBR.${r}.pixel-conversion`), !1;
|
|
1025
|
+
} finally {
|
|
1026
|
+
p == null || p.dispose();
|
|
1027
|
+
}
|
|
1028
|
+
}
|
|
1029
|
+
function Zt(e, t) {
|
|
1030
|
+
const n = /* @__PURE__ */ new Set([
|
|
1031
|
+
"inputs:diffuse_color_constant",
|
|
1032
|
+
"inputs:diffuse_texture",
|
|
1033
|
+
"inputs:reflection_roughness_constant",
|
|
1034
|
+
"inputs:metallic_constant",
|
|
1035
|
+
"inputs:opacity_constant",
|
|
1036
|
+
"inputs:enable_opacity",
|
|
1037
|
+
"inputs:enable_emission",
|
|
1038
|
+
"inputs:emissive_color",
|
|
1039
|
+
"inputs:emissive_intensity",
|
|
1040
|
+
"inputs:texture_scale",
|
|
1041
|
+
"inputs:texture_translate",
|
|
1042
|
+
"inputs:texture_rotate",
|
|
1043
|
+
"inputs:project_uvw",
|
|
1044
|
+
"inputs:uv_space_index",
|
|
1045
|
+
"info:mdl:sourceAsset",
|
|
1046
|
+
"inputs:enable_ORM_texture",
|
|
1047
|
+
"inputs:ORM_texture",
|
|
1048
|
+
"inputs:metallic_texture_influence",
|
|
1049
|
+
"inputs:reflection_roughness_texture_influence",
|
|
1050
|
+
"inputs:ao_to_diffuse",
|
|
1051
|
+
"inputs:diffuse_tint",
|
|
1052
|
+
"inputs:normalmap_texture",
|
|
1053
|
+
"inputs:bump_factor",
|
|
1054
|
+
"inputs:flip_tangent_u",
|
|
1055
|
+
"inputs:flip_tangent_v",
|
|
1056
|
+
"inputs:reflectionroughness_texture",
|
|
1057
|
+
"inputs:metallic_texture",
|
|
1058
|
+
"inputs:opacity_texture"
|
|
1059
|
+
]);
|
|
1060
|
+
(N(e, ["specular_level"]) ?? 0.5) !== 0.5 && t.add("OmniPBR.specular_level"), n.add("inputs:specular_level");
|
|
1061
|
+
const o = /* @__PURE__ */ new Set(["inputs:opacity_mode", "inputs:opacity_threshold", "inputs:enable_opacity_texture"]);
|
|
1062
|
+
ae(e, ["enable_emission"], !1) && t.add("OmniPBR.emission_radiometric_equivalence");
|
|
1063
|
+
const a = {
|
|
1064
|
+
"inputs:albedo_desaturation": 0,
|
|
1065
|
+
"inputs:albedo_add": 0,
|
|
1066
|
+
"inputs:albedo_brightness": 1,
|
|
1067
|
+
"inputs:world_or_object": !1
|
|
1068
|
+
};
|
|
1069
|
+
for (const h of Object.keys(e.inputs))
|
|
1070
|
+
h in a && e.inputs[h] === a[h] || !n.has(h) && !o.has(h) && t.add(`OmniPBR.${h.replace(/^inputs:/, "")}`);
|
|
1071
|
+
}
|
|
1072
|
+
function en(e, t, n) {
|
|
1073
|
+
let o = !1;
|
|
1074
|
+
const a = xe(t), h = Ne(t, ["diffuseColor", "baseColor", "base_color", "diffuse_color_constant"]), f = N(t, ["roughness", "specularRoughness", "specular_roughness", "reflection_roughness_constant"]) ?? (a ? 0.5 : null), d = N(t, ["metallic", "metalness", "metallicFactor", "metallic_constant"]) ?? (a ? 0 : null), i = N(t, ["opacity_threshold"]) ?? 0, r = ae(t, ["enable_opacity"], !1) && i >= 0, s = N(t, ["opacity", "presence", "opacity_constant"]) ?? (a ? 1 : null), u = a ? r ? i > 0 ? s >= i ? 1 : 0 : s : 1 : s, p = ae(t, ["enable_emission"], !a), y = p ? Ne(t, ["emissiveColor", "emissionColor", "emission_color", "emissive_color"]) : null;
|
|
1075
|
+
for (const l of e)
|
|
1076
|
+
Y(l) && (h && (l.color.copy(h), o = !0), f !== null && (l.roughness = Ee(f), o = !0), d !== null && (l.metalness = Ee(d), o = !0), u !== null && (l.opacity = Ee(u), l.transparent = l.opacity < 1, l.depthWrite = l.opacity >= 1, o = !0), a && !p && (l.emissive.setRGB(0, 0, 0), l.emissiveIntensity = 0), y && (l.emissive.copy(y), a && (l.emissiveIntensity = Math.max(0, N(t, ["emissive_intensity"]) ?? 40)), o = !0), o && (l.needsUpdate = !0));
|
|
1077
|
+
return h && n.push("diffuseColor.constant"), f !== null && n.push("roughness.constant"), d !== null && n.push("metalness.constant"), u !== null && n.push("opacity.constant"), y && n.push("emissiveColor.constant"), o;
|
|
1078
|
+
}
|
|
1079
|
+
function tn(e, t, n) {
|
|
1080
|
+
const o = /* @__PURE__ */ new Set(), a = (h) => {
|
|
1081
|
+
if (o.has(h.path)) return;
|
|
1082
|
+
o.add(h.path);
|
|
1083
|
+
const f = he(e, h);
|
|
1084
|
+
if (!f) {
|
|
1085
|
+
n.add(h.path);
|
|
1086
|
+
return;
|
|
1087
|
+
}
|
|
1088
|
+
if (!ct(f)) {
|
|
1089
|
+
n.add(f.id ?? f.path);
|
|
1090
|
+
for (const [d, i] of Object.entries(f.inputs)) {
|
|
1091
|
+
if (!d.endsWith(".resolvedConnect") && !d.endsWith(".connect")) continue;
|
|
1092
|
+
const r = Ve(i);
|
|
1093
|
+
r && a(r);
|
|
1094
|
+
}
|
|
1095
|
+
}
|
|
1096
|
+
};
|
|
1097
|
+
for (const [h, f] of Object.entries(t.inputs)) {
|
|
1098
|
+
if (!h.endsWith(".resolvedConnect") && !h.endsWith(".connect") || /(?:diffuseColor|baseColor)/i.test(h)) continue;
|
|
1099
|
+
const d = Ve(f);
|
|
1100
|
+
d && a(d);
|
|
1101
|
+
}
|
|
1102
|
+
}
|
|
1103
|
+
async function re(e, t) {
|
|
1104
|
+
const n = xt(t.entryDirectory ? `${t.entryDirectory}/${e}` : e);
|
|
1105
|
+
let o = t.files.find(e, t.entryDirectory ?? "") ?? t.files.find(n);
|
|
1106
|
+
if (!o)
|
|
1107
|
+
try {
|
|
1108
|
+
await t.files.ensure(n), o = t.files.find(n) ?? t.files.find(e, t.entryDirectory ?? "");
|
|
1109
|
+
} catch (a) {
|
|
1110
|
+
const h = a == null ? void 0 : a.code;
|
|
1111
|
+
if (a instanceof Error && a.name === "AbortError" || h === "E_ASSET_AUTH") throw a;
|
|
1112
|
+
const f = h === "E_ASSET_RESOURCE_NOT_FOUND" || /\((404|410)\)/.test(String(a));
|
|
1113
|
+
return { report: { path: e, status: f ? "missing" : "unresolved" }, url: null };
|
|
1114
|
+
}
|
|
1115
|
+
return o ? Vt.has(sn(e)) ? { report: { path: e, status: "available" }, url: t.files.objectUrl(o) } : { report: { path: e, status: "unsupported-format" }, url: null } : { report: { path: e, status: "unresolved" }, url: null };
|
|
1116
|
+
}
|
|
1117
|
+
function Be(e, t, n, o, a, h, f) {
|
|
1118
|
+
f === "augmented" && e.approximations.push({
|
|
1119
|
+
code: "USD_VISUAL_MATERIAL_AUGMENTED",
|
|
1120
|
+
message: `USD 材质 ${t}(${it(n) ?? "renderer-specific shader"})已通过视觉适配层映射资产明确提供的输入:${we(o).join(", ")}。这是有限范围的材质映射,不保证与原渲染器完全等价;原始 Loader 诊断保留在 visualAdaptation 报告中。`,
|
|
1121
|
+
source: "usd-visual"
|
|
1122
|
+
});
|
|
1123
|
+
for (const i of h)
|
|
1124
|
+
i.status === "missing" && e.warnings.push({
|
|
1125
|
+
code: "USD_VISUAL_RESOURCE_MISSING",
|
|
1126
|
+
message: `USD 材质资源缺失:${i.path}(${t})。未生成替代内容。`,
|
|
1127
|
+
source: "usd-visual"
|
|
1128
|
+
}), i.status === "unsupported-format" && e.droppedFeatures.push({
|
|
1129
|
+
code: "USD_VISUAL_TEXTURE_FORMAT_UNSUPPORTED",
|
|
1130
|
+
message: `USD 材质纹理格式无法由浏览器直接消费:${i.path}(${t})。需要离线确定性转码。`,
|
|
1131
|
+
source: "usd-visual"
|
|
1132
|
+
}), i.status === "decode-failed" && e.warnings.push({
|
|
1133
|
+
code: "USD_VISUAL_TEXTURE_DECODE_FAILED",
|
|
1134
|
+
message: `USD 纹理解码失败:${i.path}(${t})。保留原材质。`,
|
|
1135
|
+
source: "usd-visual"
|
|
1136
|
+
}), i.status === "unresolved" && e.warnings.push({
|
|
1137
|
+
code: "USD_VISUAL_RESOURCE_UNRESOLVED",
|
|
1138
|
+
message: `无法确认 USD 材质资源是否可用:${i.path}(${t})。未生成替代内容。`,
|
|
1139
|
+
source: "usd-visual"
|
|
1140
|
+
});
|
|
1141
|
+
const d = {
|
|
1142
|
+
"OmniGlass.solid_volume_absorption": "实体玻璃目前仅渲染表面透射:缺少可靠的内部光程,未实现体积吸收。未推断或生成壁厚",
|
|
1143
|
+
"OmniGlass.glass_color.volume": "源玻璃颜色用于体积吸收,当前未还原该体积颜色;未用表面染色替代",
|
|
1144
|
+
"OmniGlass.depth": "源 depth 是体积吸收缩放,不能直接当作 Three.js 壁厚或衰减距离;此输入尚未映射",
|
|
1145
|
+
"OmniGlass.fractional_coverage_transmission_compositing": "覆盖率与透射参数已映射,但其组合使用实时合成近似,不保证与 MDL 渲染等价",
|
|
1146
|
+
"OmniGlass.tint_reflection_coupling": "薄壁玻璃颜色已作表面近似,其反射与透射颜色响应不保证与 MDL 等价"
|
|
1147
|
+
};
|
|
1148
|
+
for (const i of a) e.droppedFeatures.push({
|
|
1149
|
+
code: "USD_VISUAL_SHADER_NODE_UNSUPPORTED",
|
|
1150
|
+
message: d[i] ? `USD 材质 ${t}:${d[i]}。` : `USD 材质功能或节点 ${i} 尚未完成浏览器适配(${t})。未生成替代内容。`,
|
|
1151
|
+
source: "usd-visual"
|
|
1152
|
+
});
|
|
1153
|
+
}
|
|
1154
|
+
function nn(e) {
|
|
1155
|
+
const t = O(e, ["filename", "file"]), n = J(t);
|
|
1156
|
+
return n ? { shader: e, path: n } : null;
|
|
1157
|
+
}
|
|
1158
|
+
function B(e, t) {
|
|
1159
|
+
return Ve(e.inputs[`inputs:${t}.resolvedConnect`] ?? e.inputs[`inputs:${t}.connect`]);
|
|
1160
|
+
}
|
|
1161
|
+
function Ve(e) {
|
|
1162
|
+
const t = Array.isArray(e) ? e[0] : e;
|
|
1163
|
+
if (typeof t != "string") return null;
|
|
1164
|
+
const n = /^(.*?)(?:\.outputs:([^/]+))?$/.exec(t);
|
|
1165
|
+
return n ? { path: n[1], outputName: n[2] ?? null } : null;
|
|
1166
|
+
}
|
|
1167
|
+
function he(e, t) {
|
|
1168
|
+
return e.shaders.find((n) => n.path === t.path) ?? null;
|
|
1169
|
+
}
|
|
1170
|
+
function ct(e) {
|
|
1171
|
+
return e.id === "PxrTexture";
|
|
1172
|
+
}
|
|
1173
|
+
function Y(e) {
|
|
1174
|
+
return e instanceof ze || e instanceof ie;
|
|
1175
|
+
}
|
|
1176
|
+
async function oe(e, t) {
|
|
1177
|
+
const n = await new wt().loadAsync(e);
|
|
1178
|
+
return n.colorSpace = t, n.flipY = !0, n;
|
|
1179
|
+
}
|
|
1180
|
+
function Ne(e, t) {
|
|
1181
|
+
const n = O(e, t);
|
|
1182
|
+
if (!Array.isArray(n) || n.length < 3) return null;
|
|
1183
|
+
const o = n.slice(0, 3);
|
|
1184
|
+
return o.every((a) => typeof a == "number" && Number.isFinite(a)) ? new st(o[0], o[1], o[2]) : null;
|
|
1185
|
+
}
|
|
1186
|
+
function ae(e, t, n) {
|
|
1187
|
+
const o = O(e, t);
|
|
1188
|
+
return typeof o == "boolean" ? o : n;
|
|
1189
|
+
}
|
|
1190
|
+
function Ke(e, t, n) {
|
|
1191
|
+
const o = O(e, [t]);
|
|
1192
|
+
return Array.isArray(o) && o.length >= 2 && o.slice(0, 2).every((a) => typeof a == "number" && Number.isFinite(a)) ? [o[0], o[1]] : n;
|
|
1193
|
+
}
|
|
1194
|
+
function N(e, t) {
|
|
1195
|
+
const n = O(e, t), o = typeof n == "number" ? n : Number.NaN;
|
|
1196
|
+
return Number.isFinite(o) ? o : null;
|
|
1197
|
+
}
|
|
1198
|
+
function O(e, t) {
|
|
1199
|
+
for (const n of t) {
|
|
1200
|
+
if (B(e, n)) return;
|
|
1201
|
+
const o = e.inputs[`inputs:${n}`];
|
|
1202
|
+
if (o !== void 0) return o;
|
|
1203
|
+
}
|
|
1204
|
+
}
|
|
1205
|
+
function J(e) {
|
|
1206
|
+
if (typeof e == "string") return e;
|
|
1207
|
+
if (!e || typeof e != "object") return null;
|
|
1208
|
+
for (const t of ["path", "resolvedPath", "url"]) {
|
|
1209
|
+
const n = e[t];
|
|
1210
|
+
if (typeof n == "string" && n) return n;
|
|
1211
|
+
}
|
|
1212
|
+
return null;
|
|
1213
|
+
}
|
|
1214
|
+
function Ze(e, t) {
|
|
1215
|
+
return e.data.elements.some((n) => n.material === t && n.geometry.displayColor !== null);
|
|
1216
|
+
}
|
|
1217
|
+
function sn(e) {
|
|
1218
|
+
var t, n;
|
|
1219
|
+
return ((n = (t = e.split(/[?#]/, 1)[0]) == null ? void 0 : t.split(".").pop()) == null ? void 0 : n.toLowerCase()) ?? "";
|
|
1220
|
+
}
|
|
1221
|
+
function Ee(e) {
|
|
1222
|
+
return Math.min(1, Math.max(0, e));
|
|
1223
|
+
}
|
|
1224
|
+
function Re(e) {
|
|
1225
|
+
return Array.isArray(e) ? e.filter(ke) : [];
|
|
1226
|
+
}
|
|
1227
|
+
function me(e) {
|
|
1228
|
+
return typeof e == "string" && e ? e : null;
|
|
1229
|
+
}
|
|
1230
|
+
function ke(e) {
|
|
1231
|
+
return typeof e == "string" && e.length > 0;
|
|
1232
|
+
}
|
|
1233
|
+
function we(e) {
|
|
1234
|
+
return [...new Set(e)];
|
|
1235
|
+
}
|
|
1236
|
+
async function On(e, t, n) {
|
|
1237
|
+
var w;
|
|
1238
|
+
mn();
|
|
1239
|
+
const o = n.hasLocalFiles(), a = e.entryPath ?? e.filename ?? "asset.usd", h = o ? a : await yn(e, a), f = o ? n.getBlob(a) : await _n(e), d = a.split("/").pop() || "asset.usd", i = a.split("/").slice(0, -1).join("/"), r = Nt(t.options.openUsdBaseUrl), s = e.hasResourceResolver && !o ? await new Mt().load(r) : void 0;
|
|
1240
|
+
s && await Un(s, e, f, d, n);
|
|
1241
|
+
const u = new It({
|
|
1242
|
+
convertZUp: !1,
|
|
1243
|
+
loadLights: !1,
|
|
1244
|
+
preserveStage: !0,
|
|
1245
|
+
...s ? { pxr: s } : r ? { pxrOptions: r } : {}
|
|
1246
|
+
});
|
|
1247
|
+
let p = null, y = null, l = null, c = null;
|
|
1248
|
+
try {
|
|
1249
|
+
if (p = await u.parseAsync(f, {
|
|
1250
|
+
sourcePath: h,
|
|
1251
|
+
fileName: d,
|
|
1252
|
+
files: o || e.hasResourceResolver ? n.asSourceRecord(i) : void 0,
|
|
1253
|
+
// A local package is the complete browser-visible file set. Resolving it
|
|
1254
|
+
// through fetch would both hide missing uploads and accept SPA fallback
|
|
1255
|
+
// responses as binary USD layers.
|
|
1256
|
+
autoResolveAssets: !o && !e.hasResourceResolver,
|
|
1257
|
+
// USD layer references are authoritative; disable directory guessing because SPA fallback pages may be returned as HTTP 200.
|
|
1258
|
+
assetSearchRoots: [],
|
|
1259
|
+
textureResolver: o || e.hasResourceResolver ? (v) => {
|
|
1260
|
+
for (const z of [v.resolvedPath, v.path, v.url])
|
|
1261
|
+
if (z) {
|
|
1262
|
+
const S = n.objectUrlIfPresent(z, i);
|
|
1263
|
+
if (S) return S;
|
|
1264
|
+
}
|
|
1265
|
+
return null;
|
|
1266
|
+
} : void 0,
|
|
1267
|
+
preserveStage: !0
|
|
1268
|
+
}), t.signal.aborted) throw Fe();
|
|
1269
|
+
const g = hn(p);
|
|
1270
|
+
p.scene.scale.multiplyScalar(g.metersPerUnit), p.data.stage.upAxis.toUpperCase() === "Y" && p.scene.quaternion.setFromAxisAngle(new T(1, 0, 0), Math.PI / 2), p.scene.updateMatrixWorld(!0);
|
|
1271
|
+
const m = p.data.physics.rigidBodies.filter((v) => v.enabled), U = pt(p, m.map((v) => v.path)), E = Dt(), M = await Wt(p, {
|
|
1272
|
+
files: n,
|
|
1273
|
+
entryDirectory: i,
|
|
1274
|
+
sourcePath: h,
|
|
1275
|
+
isLocalPackage: o,
|
|
1276
|
+
diagnostics: E
|
|
1277
|
+
});
|
|
1278
|
+
if (t.signal.aborted) throw Fe();
|
|
1279
|
+
Tt(p);
|
|
1280
|
+
const R = rn(E);
|
|
1281
|
+
m.some((v) => v.startsAsleep === !0) && E.droppedFeatures.push({ code: "E_USD_STARTS_ASLEEP", message: "USD startsAsleep 无法在 MuJoCo 初始化阶段保证完全等价,已按正常初始状态加载。", source: "usd-physics" });
|
|
1282
|
+
const D = Pt({
|
|
1283
|
+
id: h,
|
|
1284
|
+
name: h.split("/").pop() ?? h,
|
|
1285
|
+
source: { format: "usd", uri: h },
|
|
1286
|
+
links: m.map((v) => ({ id: v.path, name: v.name, visuals: [], collisions: [] })),
|
|
1287
|
+
joints: U.flatMap((v) => v.body0 && v.body1 ? [{
|
|
1288
|
+
id: v.path,
|
|
1289
|
+
type: v.jointType,
|
|
1290
|
+
parent: v.body0,
|
|
1291
|
+
child: v.body1,
|
|
1292
|
+
origin: { position: v.localPos1.map((z) => z * g.metersPerUnit), rotationRpy: [0, 0, 0] },
|
|
1293
|
+
axis: ft(v.axis).applyQuaternion(Ue(v.localRot1 ?? [1, 0, 0, 0])).toArray(),
|
|
1294
|
+
...Number.isFinite(v.lowerLimit) && Number.isFinite(v.upperLimit) ? { limits: {
|
|
1295
|
+
lower: v.lowerLimit * (v.jointType === "revolute" ? Math.PI / 180 : g.metersPerUnit),
|
|
1296
|
+
upper: v.upperLimit * (v.jointType === "revolute" ? Math.PI / 180 : g.metersPerUnit)
|
|
1297
|
+
} } : {}
|
|
1298
|
+
}] : []),
|
|
1299
|
+
diagnostics: E,
|
|
1300
|
+
extension: { rigidBodyCount: m.length, jointCount: U.length, visualAdaptation: M }
|
|
1301
|
+
});
|
|
1302
|
+
if (m.length === 0) {
|
|
1303
|
+
const v = et(p, E), z = p.scene, S = p;
|
|
1304
|
+
return l = { root: z, sync() {
|
|
1305
|
+
}, dispose() {
|
|
1306
|
+
S.dispose();
|
|
1307
|
+
} }, p = null, Ge(D, l, !1, () => {
|
|
1308
|
+
}, void 0, void 0, v, R);
|
|
1309
|
+
}
|
|
1310
|
+
let P;
|
|
1311
|
+
try {
|
|
1312
|
+
P = pn(p, m.map((z) => z.path), g, U), (w = P.massOverrides) != null && w.length && E.approximations.push({ code: "USD_INFERRED_INERTIA", message: "保留显式总质量;惯量按碰撞几何的密度分布推导并同比缩放,重叠体积会重复计入。", source: "usd-physics" });
|
|
1313
|
+
const { MujocoRuntime: v } = await import("./mujoco-runtime-C29PXDOl.js");
|
|
1314
|
+
y = new v(), await y.initialize(P, t.options.mujocoBaseUrl), t.signal.throwIfAborted();
|
|
1315
|
+
} catch (v) {
|
|
1316
|
+
const z = At(v, t.signal, "usd-physics");
|
|
1317
|
+
y == null || y.dispose(), y = null, E.droppedFeatures.push(z);
|
|
1318
|
+
const S = et(p, E), I = p.scene, x = p;
|
|
1319
|
+
return l = { root: I, sync() {
|
|
1320
|
+
}, dispose() {
|
|
1321
|
+
x.dispose();
|
|
1322
|
+
} }, p = null, Ge(D, l, !1, () => {
|
|
1323
|
+
}, void 0, z, S, R);
|
|
1324
|
+
}
|
|
1325
|
+
const C = c = cn(p, m.map((v) => v.path), E);
|
|
1326
|
+
if (t.signal.aborted) throw Fe();
|
|
1327
|
+
l = new Qe(y, C);
|
|
1328
|
+
const _ = ut(p, m.map((v) => v.path), E), b = _ ? new Qe(y, _) : void 0;
|
|
1329
|
+
c = null;
|
|
1330
|
+
const A = p, L = y, W = l;
|
|
1331
|
+
return p = null, y = null, l = null, Ge(D, W, !0, () => {
|
|
1332
|
+
L.dispose(), A.dispose();
|
|
1333
|
+
}, L, void 0, b, R);
|
|
1334
|
+
} catch (g) {
|
|
1335
|
+
throw c && at(c.root), l == null || l.dispose(), y == null || y.dispose(), p == null || p.dispose(), g;
|
|
1336
|
+
}
|
|
1337
|
+
}
|
|
1338
|
+
function rn(e) {
|
|
1339
|
+
const t = [
|
|
1340
|
+
"USD_VISUAL_RESOURCE_MISSING",
|
|
1341
|
+
"USD_VISUAL_TEXTURE_FORMAT_UNSUPPORTED",
|
|
1342
|
+
"USD_VISUAL_RESOURCE_UNRESOLVED",
|
|
1343
|
+
"USD_VISUAL_TEXTURE_DECODE_FAILED",
|
|
1344
|
+
"USD_VISUAL_SHADER_NODE_UNSUPPORTED",
|
|
1345
|
+
"USD_VISUAL_LOADER_DIAGNOSTIC",
|
|
1346
|
+
"USD_VISUAL_TOPOLOGY_UNSUPPORTED"
|
|
1347
|
+
], n = [...e.warnings, ...e.droppedFeatures, ...e.approximations];
|
|
1348
|
+
for (const o of t) {
|
|
1349
|
+
const a = n.find((h) => h.code === o);
|
|
1350
|
+
if (a) return a;
|
|
1351
|
+
}
|
|
1352
|
+
}
|
|
1353
|
+
function Ge(e, t, n, o, a, h, f, d) {
|
|
1354
|
+
let i = !1;
|
|
1355
|
+
return {
|
|
1356
|
+
asset: e,
|
|
1357
|
+
binding: t,
|
|
1358
|
+
hasPhysics: n,
|
|
1359
|
+
runtime: a,
|
|
1360
|
+
fallback: h,
|
|
1361
|
+
visualWarning: d,
|
|
1362
|
+
collision: f,
|
|
1363
|
+
step(r) {
|
|
1364
|
+
if (!a) return !1;
|
|
1365
|
+
const s = a.step(r);
|
|
1366
|
+
return s && t.sync(), s;
|
|
1367
|
+
},
|
|
1368
|
+
reset() {
|
|
1369
|
+
a == null || a.reset(), t.sync();
|
|
1370
|
+
},
|
|
1371
|
+
dispose() {
|
|
1372
|
+
i || (i = !0, f == null || f.dispose(), t.dispose(), o());
|
|
1373
|
+
}
|
|
1374
|
+
};
|
|
1375
|
+
}
|
|
1376
|
+
const on = /* @__PURE__ */ new Set([
|
|
1377
|
+
"E_USD_PHYSICS_UNSUPPORTED",
|
|
1378
|
+
"E_USD_UNBAKED_BODY_SCALE",
|
|
1379
|
+
"E_USD_INVALID_JOINT_REFERENCE",
|
|
1380
|
+
"E_USD_UNSUPPORTED_JOINT",
|
|
1381
|
+
"E_USD_MULTIPLE_PARENTS",
|
|
1382
|
+
"E_USD_JOINT_CYCLE",
|
|
1383
|
+
"E_USD_UNSUPPORTED_DRIVE",
|
|
1384
|
+
"E_USD_INVALID_MASS",
|
|
1385
|
+
"E_USD_PARTIAL_INERTIA",
|
|
1386
|
+
"E_USD_MISSING_COLLISION_GEOMETRY",
|
|
1387
|
+
"E_USD_UNREACHABLE_BODIES",
|
|
1388
|
+
"E_USD_MULTIPLE_PHYSICS_SCENES",
|
|
1389
|
+
"E_USD_NONUNIFORM_RADIAL_SCALE",
|
|
1390
|
+
"E_USD_UNSUPPORTED_GEOMETRY",
|
|
1391
|
+
"E_USD_CONSTRAINED_INITIAL_VELOCITY",
|
|
1392
|
+
"E_USD_UNSUPPORTED_APPROXIMATION"
|
|
1393
|
+
]);
|
|
1394
|
+
function In(e) {
|
|
1395
|
+
const t = an(e);
|
|
1396
|
+
return t !== null && on.has(t);
|
|
1397
|
+
}
|
|
1398
|
+
function an(e) {
|
|
1399
|
+
if (!e || typeof e != "object" || !("code" in e)) return null;
|
|
1400
|
+
const t = e.code;
|
|
1401
|
+
return typeof t == "string" ? t : null;
|
|
1402
|
+
}
|
|
1403
|
+
function cn(e, t, n) {
|
|
1404
|
+
e.scene.updateMatrixWorld(!0);
|
|
1405
|
+
const o = new Ie();
|
|
1406
|
+
o.name = "USD simulation";
|
|
1407
|
+
const a = /* @__PURE__ */ new Map(), h = /* @__PURE__ */ new Map();
|
|
1408
|
+
for (const i of t) {
|
|
1409
|
+
const r = e.index.objectsByPath.get(i);
|
|
1410
|
+
if (!r) throw $(`USD rigid body node is missing: ${i}`, "E_USD_PHYSICS_UNSUPPORTED");
|
|
1411
|
+
const s = new Ie();
|
|
1412
|
+
s.name = i, o.add(s), a.set(i, s);
|
|
1413
|
+
const u = new T(), p = new ee();
|
|
1414
|
+
r.matrixWorld.decompose(u, p, new T()), h.set(i, new pe().compose(u, p, new T(1, 1, 1)));
|
|
1415
|
+
}
|
|
1416
|
+
const f = ln(e, t, n), d = [];
|
|
1417
|
+
e.scene.traverse((i) => {
|
|
1418
|
+
var y;
|
|
1419
|
+
if (!(i instanceof te) || i.userData.usdPurposeExcluded) return;
|
|
1420
|
+
let r = i, s, u, p = !0;
|
|
1421
|
+
for (; r; ) {
|
|
1422
|
+
p && (p = r.visible);
|
|
1423
|
+
const l = (y = r.userData.usd) == null ? void 0 : y.path;
|
|
1424
|
+
!u && l && (u = l), !s && l && a.has(l) && (s = l), r = r.parent;
|
|
1425
|
+
}
|
|
1426
|
+
!s && u && (s = f.get(lt(u))), p && d.push([i, s]);
|
|
1427
|
+
});
|
|
1428
|
+
for (const [i, r] of d) {
|
|
1429
|
+
const s = i.clone(!1);
|
|
1430
|
+
s.geometry = i.geometry.clone(), s.material = Array.isArray(i.material) ? i.material.map((u) => u.clone()) : i.material.clone(), s.matrix.copy(r ? h.get(r) : new pe()).invert().multiply(i.matrixWorld), s.matrix.decompose(s.position, s.quaternion, s.scale), (r ? a.get(r) : o).add(s);
|
|
1431
|
+
}
|
|
1432
|
+
return { root: o, bindings: a, expectedLinkCount: a.size };
|
|
1433
|
+
}
|
|
1434
|
+
function ln(e, t, n) {
|
|
1435
|
+
var i, r;
|
|
1436
|
+
const o = /* @__PURE__ */ new Map(), a = /* @__PURE__ */ new Map(), h = e.stage, f = e.pxr;
|
|
1437
|
+
if (!h || !((i = f == null ? void 0 : f.Sdf) != null && i.Path) || !((r = e.data.view) != null && r.prims)) return o;
|
|
1438
|
+
const d = new Set(e.data.view.prims.map((s) => s.path));
|
|
1439
|
+
for (const s of t) {
|
|
1440
|
+
const u = `${s}/Visual/`;
|
|
1441
|
+
for (const p of d) {
|
|
1442
|
+
if (!p.startsWith(u)) continue;
|
|
1443
|
+
const y = h.GetPrimAtPath(new f.Sdf.Path(p));
|
|
1444
|
+
try {
|
|
1445
|
+
const l = y.GetMetadata("references"), c = typeof l == "string" ? l : l == null ? void 0 : l.string;
|
|
1446
|
+
if (c == null) {
|
|
1447
|
+
n == null || n.warnings.push({ code: "USD_VISUAL_REFERENCE_MISSING", message: `刚体视觉节点缺少 reference:${p}`, source: "usd-visual-binding" });
|
|
1448
|
+
continue;
|
|
1449
|
+
}
|
|
1450
|
+
const w = un(c);
|
|
1451
|
+
if (!w) {
|
|
1452
|
+
n == null || n.warnings.push({ code: "USD_VISUAL_REFERENCE_UNRESOLVED", message: `无法解析视觉引用元数据:${p}`, source: "usd-visual-binding" });
|
|
1453
|
+
continue;
|
|
1454
|
+
}
|
|
1455
|
+
if (!w.primPath) continue;
|
|
1456
|
+
const g = lt(w.primPath), m = a.get(g);
|
|
1457
|
+
if (m && m.owner !== s)
|
|
1458
|
+
throw $(`USD visual reference maps to multiple rigid bodies: ${w.primPath} -> ${m.owner}, ${s}`, "E_USD_VISUAL_REFERENCE_AMBIGUOUS");
|
|
1459
|
+
a.set(g, { owner: s, target: w.primPath }), o.set(g, s);
|
|
1460
|
+
} finally {
|
|
1461
|
+
y.delete();
|
|
1462
|
+
}
|
|
1463
|
+
}
|
|
1464
|
+
}
|
|
1465
|
+
return o;
|
|
1466
|
+
}
|
|
1467
|
+
function un(e) {
|
|
1468
|
+
var n, o;
|
|
1469
|
+
const t = e.match(/SdfReference\(([^,]*),\s*(?:(\/[^,\)]+),\s*)?SdfLayerOffset/);
|
|
1470
|
+
return t ? { identifier: ((n = t[1]) == null ? void 0 : n.trim()) ?? "", primPath: ((o = t[2]) == null ? void 0 : o.trim()) ?? null } : null;
|
|
1471
|
+
}
|
|
1472
|
+
function lt(e) {
|
|
1473
|
+
const t = e.replaceAll("\\", "/");
|
|
1474
|
+
for (const n of ["/Geometry/", "/Visual/"]) {
|
|
1475
|
+
const o = t.indexOf(n);
|
|
1476
|
+
if (o >= 0) return t.slice(o + n.length);
|
|
1477
|
+
}
|
|
1478
|
+
return t;
|
|
1479
|
+
}
|
|
1480
|
+
function ut(e, t, n) {
|
|
1481
|
+
e.scene.updateMatrixWorld(!0);
|
|
1482
|
+
const o = new Ie();
|
|
1483
|
+
o.name = "USD authored collisions";
|
|
1484
|
+
const a = vt(), h = /* @__PURE__ */ new Map(), f = /* @__PURE__ */ new Map();
|
|
1485
|
+
for (const i of t) {
|
|
1486
|
+
const r = e.index.objectsByPath.get(i);
|
|
1487
|
+
if (!r) continue;
|
|
1488
|
+
const s = new T(), u = new ee();
|
|
1489
|
+
r.matrixWorld.decompose(s, u, new T()), f.set(i, new pe().compose(s, u, new T(1, 1, 1)));
|
|
1490
|
+
const p = new Ie();
|
|
1491
|
+
p.name = i, p.position.copy(s), p.quaternion.copy(u), h.set(i, p), o.add(p);
|
|
1492
|
+
}
|
|
1493
|
+
let d = 0;
|
|
1494
|
+
for (const i of e.data.physics.colliders) {
|
|
1495
|
+
if (!i.enabled) continue;
|
|
1496
|
+
const r = e.index.objectsByPath.get(i.path);
|
|
1497
|
+
if (!r) continue;
|
|
1498
|
+
const s = i.bodyPath && h.has(i.bodyPath) ? i.bodyPath : null, u = s ? h.get(s) : o, p = s ? f.get(s) : new pe(), y = [];
|
|
1499
|
+
if (r.traverse((g) => {
|
|
1500
|
+
g instanceof te && y.push(g);
|
|
1501
|
+
}), y.length === 0) continue;
|
|
1502
|
+
const l = String(i.typeName ?? r.type).toLowerCase(), c = l.includes("mesh") ? i.approximation ?? "none" : null;
|
|
1503
|
+
if (c === "convexDecomposition" || c === "meshSimplification") {
|
|
1504
|
+
n == null || n.droppedFeatures.push({
|
|
1505
|
+
code: "E_USD_COLLISION_DEBUG_APPROXIMATION_UNAVAILABLE",
|
|
1506
|
+
message: `USD collider ${i.path} 使用 ${c},但资产未提供可唯一还原的最终代理几何。`,
|
|
1507
|
+
source: "usd-collision-debug"
|
|
1508
|
+
});
|
|
1509
|
+
continue;
|
|
1510
|
+
}
|
|
1511
|
+
if (l.includes("mesh") && c !== "none") {
|
|
1512
|
+
const g = [], m = p.clone().invert();
|
|
1513
|
+
for (const U of y) {
|
|
1514
|
+
const E = m.clone().multiply(U.matrixWorld), M = U.geometry.getAttribute("position");
|
|
1515
|
+
for (let R = 0; R < M.count; R += 1) g.push(new T().fromBufferAttribute(M, R).applyMatrix4(E));
|
|
1516
|
+
}
|
|
1517
|
+
if (g.length >= 4 && c === "convexHull") {
|
|
1518
|
+
const U = new Rt(g), E = Ae(U, a, "mesh");
|
|
1519
|
+
U.dispose(), E.name = `Collision:${i.path}`, E.userData.usdColliderPath = i.path, u.add(E), d += 1;
|
|
1520
|
+
} else if (g.length > 0 && c === "boundingSphere") {
|
|
1521
|
+
const E = new Me().setFromPoints(g).getBoundingSphere(new Ut()), M = new bt(E.radius, 24, 16);
|
|
1522
|
+
M.translate(E.center.x, E.center.y, E.center.z);
|
|
1523
|
+
const R = Ae(M, a, "feature");
|
|
1524
|
+
M.dispose(), R.name = `Collision:${i.path}`, R.userData.usdColliderPath = i.path, u.add(R), d += 1;
|
|
1525
|
+
} else if (g.length > 0 && c === "boundingCube") {
|
|
1526
|
+
const U = new Me().setFromPoints(g), E = U.getSize(new T()), M = U.getCenter(new T()), R = new Et(E.x, E.y, E.z);
|
|
1527
|
+
R.translate(M.x, M.y, M.z);
|
|
1528
|
+
const D = Ae(R, a, "feature");
|
|
1529
|
+
R.dispose(), D.name = `Collision:${i.path}`, D.userData.usdColliderPath = i.path, u.add(D), d += 1;
|
|
1530
|
+
} else ["convexHull", "boundingSphere", "boundingCube"].includes(String(c)) || n == null || n.droppedFeatures.push({
|
|
1531
|
+
code: "E_USD_COLLISION_DEBUG_APPROXIMATION_UNAVAILABLE",
|
|
1532
|
+
message: `USD collider ${i.path} 使用未知 approximation=${c}。`,
|
|
1533
|
+
source: "usd-collision-debug"
|
|
1534
|
+
});
|
|
1535
|
+
continue;
|
|
1536
|
+
}
|
|
1537
|
+
const w = l.includes("mesh") ? "mesh" : "feature";
|
|
1538
|
+
for (const g of y) {
|
|
1539
|
+
const m = Ae(g.geometry, a, w);
|
|
1540
|
+
m.name = `Collision:${i.path}`, m.matrixAutoUpdate = !1, m.matrix.copy(p).invert().multiply(g.matrixWorld), m.userData.usdColliderPath = i.path, u.add(m), d += 1;
|
|
1541
|
+
}
|
|
1542
|
+
}
|
|
1543
|
+
if (d === 0) {
|
|
1544
|
+
a.dispose();
|
|
1545
|
+
return;
|
|
1546
|
+
}
|
|
1547
|
+
return { root: o, bindings: h, expectedLinkCount: h.size };
|
|
1548
|
+
}
|
|
1549
|
+
function et(e, t) {
|
|
1550
|
+
const n = ut(e, [], t);
|
|
1551
|
+
if (n)
|
|
1552
|
+
return n.root.visible = !1, { root: n.root, sync() {
|
|
1553
|
+
}, dispose() {
|
|
1554
|
+
n.root.removeFromParent(), at(n.root);
|
|
1555
|
+
} };
|
|
1556
|
+
}
|
|
1557
|
+
function pt(e, t) {
|
|
1558
|
+
e.scene.updateMatrixWorld(!0);
|
|
1559
|
+
const n = new Set(t);
|
|
1560
|
+
return e.data.joints.filter((o) => o.enabled).map((o) => {
|
|
1561
|
+
const a = { ...o };
|
|
1562
|
+
for (const h of [0, 1]) {
|
|
1563
|
+
const f = h === 0 ? "body0" : "body1", d = h === 0 ? "localPos0" : "localPos1", i = h === 0 ? "localRot0" : "localRot1", r = o[f];
|
|
1564
|
+
if (!r) continue;
|
|
1565
|
+
let s = r;
|
|
1566
|
+
for (; s && !e.index.rigidBodiesByPath.has(s); )
|
|
1567
|
+
s = s.slice(0, s.lastIndexOf("/"));
|
|
1568
|
+
if (s && !n.has(s))
|
|
1569
|
+
throw $(`USD joint references an unknown or disabled rigid body: ${o.path} (${r})`, "E_USD_INVALID_JOINT_REFERENCE");
|
|
1570
|
+
const u = e.index.objectsByPath.get(r), p = s ? e.index.objectsByPath.get(s) : e.scene;
|
|
1571
|
+
if (!u || !p)
|
|
1572
|
+
throw $(`USD joint target node is missing: ${o.path} (${r})`, "E_USD_INVALID_JOINT_REFERENCE");
|
|
1573
|
+
if (s === r) continue;
|
|
1574
|
+
const y = p.matrixWorld.clone().invert().multiply(u.matrixWorld), l = new T(), c = new ee(), w = new T();
|
|
1575
|
+
y.decompose(l, c, w);
|
|
1576
|
+
const g = new pe().compose(l, c, new T(1, 1, 1));
|
|
1577
|
+
if (y.elements.some((U, E) => Math.abs(U - g.elements[E]) > 1e-5))
|
|
1578
|
+
throw $(`USD joint target has unsupported scale or shear: ${o.path} (${r})`, "E_USD_PHYSICS_UNSUPPORTED");
|
|
1579
|
+
a[f] = s || null, a[d] = new T(...o[d]).applyMatrix4(y).toArray();
|
|
1580
|
+
const m = c.multiply(Ue(o[i] ?? [1, 0, 0, 0])).normalize();
|
|
1581
|
+
a[i] = [m.w, m.x, m.y, m.z];
|
|
1582
|
+
}
|
|
1583
|
+
return a;
|
|
1584
|
+
});
|
|
1585
|
+
}
|
|
1586
|
+
function pn(e, t, n, o = pt(e, t)) {
|
|
1587
|
+
e.scene.updateMatrixWorld(!0);
|
|
1588
|
+
const a = [], h = [], f = [], d = [], i = [], r = [], s = [], { metersPerUnit: u, kilogramsPerUnit: p } = n, y = new Map(t.map((_) => {
|
|
1589
|
+
const b = e.index.rigidBodiesByPath.get(_);
|
|
1590
|
+
if (!b) throw $(`USD rigid body metadata is missing: ${_}`, "E_USD_PHYSICS_UNSUPPORTED");
|
|
1591
|
+
return [_, b];
|
|
1592
|
+
})), l = /* @__PURE__ */ new Map();
|
|
1593
|
+
for (const _ of y.keys()) {
|
|
1594
|
+
const b = e.index.objectsByPath.get(_);
|
|
1595
|
+
if (!b) throw $(`USD rigid body node is missing: ${_}`, "E_USD_PHYSICS_UNSUPPORTED");
|
|
1596
|
+
const A = new T(), L = new ee(), W = new T();
|
|
1597
|
+
if (b.matrixWorld.decompose(A, L, W), W.clone().divideScalar(u).toArray().some((z) => Math.abs(Math.abs(z) - 1) > 1e-5))
|
|
1598
|
+
throw $(`USD rigid body has unbaked scale: ${_}`, "E_USD_UNBAKED_BODY_SCALE");
|
|
1599
|
+
l.set(_, new pe().compose(A, L, new T(1, 1, 1)));
|
|
1600
|
+
}
|
|
1601
|
+
const c = /* @__PURE__ */ new Map();
|
|
1602
|
+
for (const _ of o) {
|
|
1603
|
+
if (!_.body1 || !y.has(_.body1) || _.body0 && !y.has(_.body0))
|
|
1604
|
+
throw $(`USD joint references an unknown rigid body: ${_.path}`, "E_USD_INVALID_JOINT_REFERENCE");
|
|
1605
|
+
if (!["fixed", "revolute", "prismatic"].includes(_.jointType))
|
|
1606
|
+
throw $(`Unsupported USD joint type ${_.jointType}: ${_.path}`, "E_USD_UNSUPPORTED_JOINT");
|
|
1607
|
+
if (c.has(_.body1)) throw $(`USD rigid body has multiple parent joints: ${_.body1}`, "E_USD_MULTIPLE_PARENTS");
|
|
1608
|
+
c.set(_.body1, _), _.body0 && _.collisionEnabled !== !0 && f.push(`<exclude body1="${Se(_.body0)}" body2="${Se(_.body1)}"/>`);
|
|
1609
|
+
}
|
|
1610
|
+
let w = 0;
|
|
1611
|
+
const g = /* @__PURE__ */ new Set(), m = (_, b = new pe()) => {
|
|
1612
|
+
var j, X, V, G, ce;
|
|
1613
|
+
if (g.has(_)) throw $(`USD joint graph contains a cycle at ${_}`, "E_USD_JOINT_CYCLE");
|
|
1614
|
+
g.add(_);
|
|
1615
|
+
const A = y.get(_), L = l.get(_), W = b.clone().invert().multiply(L), v = new T(), z = new ee();
|
|
1616
|
+
W.decompose(v, z, new T());
|
|
1617
|
+
const S = c.get(_), I = [`<body name="${Se(_)}" pos="${Z(v.toArray())}" quat="${be(z)}">`];
|
|
1618
|
+
if (!S && !A.kinematicEnabled && I.push("<freejoint/>"), S && [...A.velocity ?? [], ...A.angularVelocity ?? []].some((F) => F !== 0))
|
|
1619
|
+
throw $(`Constrained USD initial velocity cannot be projected reliably: ${_}`, "E_USD_CONSTRAINED_INITIAL_VELOCITY");
|
|
1620
|
+
if (!S && !A.kinematicEnabled) {
|
|
1621
|
+
const F = new T(...A.velocity ?? [0, 0, 0]).multiplyScalar(u).applyQuaternion(e.scene.quaternion), H = new T(...A.angularVelocity ?? [0, 0, 0]).multiplyScalar(Math.PI / 180).applyQuaternion(e.scene.quaternion).applyQuaternion(new ee().setFromRotationMatrix(L).invert());
|
|
1622
|
+
s.push({ body: _, velocity: [...F.toArray(), ...H.toArray()] });
|
|
1623
|
+
}
|
|
1624
|
+
if (S && S.jointType !== "fixed") {
|
|
1625
|
+
const F = S.jointType === "revolute" ? "hinge" : "slide", H = ft(S.axis).applyQuaternion(Ue(S.localRot1 ?? [1, 0, 0, 0])), ne = F === "hinge" ? Math.PI / 180 : u, ye = S.body0 ? b : e.scene.matrixWorld.clone();
|
|
1626
|
+
if (!S.body0) {
|
|
1627
|
+
const se = new T(), ge = new ee();
|
|
1628
|
+
ye.decompose(se, ge, new T()), ye.compose(se, ge, new T(1, 1, 1));
|
|
1629
|
+
}
|
|
1630
|
+
const $e = new ee().setFromRotationMatrix(ye), ve = new ee().setFromRotationMatrix(L), _e = $e.clone().multiply(Ue(S.localRot0 ?? [1, 0, 0, 0])).invert().multiply(ve).multiply(Ue(S.localRot1 ?? [1, 0, 0, 0]));
|
|
1631
|
+
let fe = 0;
|
|
1632
|
+
if (F === "hinge") {
|
|
1633
|
+
const se = S.axis === "Y" ? _e.y : S.axis === "Z" ? _e.z : _e.x;
|
|
1634
|
+
fe = 2 * Math.atan2(se, _e.w), fe = Math.atan2(Math.sin(fe), Math.cos(fe));
|
|
1635
|
+
} else {
|
|
1636
|
+
const se = new T(...S.localPos0).multiplyScalar(u).applyMatrix4(ye);
|
|
1637
|
+
fe = new T(...S.localPos1).multiplyScalar(u).applyMatrix4(L).sub(se).dot(H.clone().applyQuaternion(ve));
|
|
1638
|
+
}
|
|
1639
|
+
const Ye = Number.isFinite(S.lowerLimit) && Number.isFinite(S.upperLimit) && Math.abs(S.lowerLimit) < 1e20 && Math.abs(S.upperLimit) < 1e20, mt = Ye && S.lowerLimit < S.upperLimit, De = p * (F === "slide" ? u : u * u), Ce = Oe(e, S.path, `physxJointAxis:${F === "slide" ? "linear" : "angular"}:dynamicFrictionEffort`), yt = typeof Ce == "number" && Number.isFinite(Ce) ? Ce * De : 0;
|
|
1640
|
+
I.push(`<joint name="${Se(S.path)}" type="${F}" pos="${Z(S.localPos1.map((se) => se * u))}" axis="${Z(H.toArray())}" ref="${fe}" ${mt ? `range="${S.lowerLimit * ne} ${S.upperLimit * ne}"` : 'limited="false"'} frictionloss="${yt}" armature="0.00001"/>`), Ye && S.lowerLimit === S.upperLimit && h.push(`<joint joint1="${Se(S.path)}" polycoef="${S.lowerLimit * ne - fe} 0 0 0 0"/>`);
|
|
1641
|
+
const le = S.drive;
|
|
1642
|
+
if (le && ((le.stiffness ?? 0) !== 0 || (le.damping ?? 0) !== 0)) {
|
|
1643
|
+
if (le.type === "acceleration") throw $(`Unsupported USD acceleration drive: ${S.path}`, "E_USD_UNSUPPORTED_DRIVE");
|
|
1644
|
+
const se = (le.stiffness ?? 0) * De / ne, ge = (le.damping ?? 0) * De / ne, Pe = le.maxForce == null ? null : le.maxForce * De;
|
|
1645
|
+
i.push(`<general joint="${Se(S.path)}" gainprm="1" biastype="affine" biasprm="0 ${-se} ${-ge}" ${Pe != null && Number.isFinite(Pe) ? `forcelimited="true" forcerange="${-Pe} ${Pe}"` : ""}/>`), r.push(se * (le.targetPosition ?? 0) * ne + ge * (le.targetVelocity ?? 0) * ne);
|
|
1646
|
+
}
|
|
1647
|
+
}
|
|
1648
|
+
const x = A.mass;
|
|
1649
|
+
if ((x == null ? void 0 : x.mass) != null && (!Number.isFinite(x.mass) || x.mass < 0)) throw $(`USD rigid body mass must be finite and non-negative: ${_}`, "E_USD_INVALID_MASS");
|
|
1650
|
+
let Q = !1;
|
|
1651
|
+
if ((x == null ? void 0 : x.mass) != null && x.mass > 0 && ((j = x.centerOfMass) == null ? void 0 : j.length) === 3 && x.centerOfMass.every(Number.isFinite) && ((X = x.diagonalInertia) == null ? void 0 : X.length) === 3 && x.diagonalInertia.every((F) => Number.isFinite(F) && F > 0) && ((V = x.principalAxes) == null ? void 0 : V.length) === 4 && x.principalAxes.every(Number.isFinite))
|
|
1652
|
+
Q = !0, I.push(`<inertial mass="${x.mass * p}" pos="${Z(x.centerOfMass.map((F) => F * u))}" quat="${be(Ue(x.principalAxes))}" diaginertia="${Z(x.diagonalInertia.map((F) => F * p * u * u))}"/>`);
|
|
1653
|
+
else {
|
|
1654
|
+
if ((G = x == null ? void 0 : x.diagonalInertia) != null && G.some((F) => F > 0))
|
|
1655
|
+
throw $(`USD rigid body has incomplete explicit inertia: ${_}`, "E_USD_PARTIAL_INERTIA");
|
|
1656
|
+
if ((x == null ? void 0 : x.mass) != null && x.mass > 0) {
|
|
1657
|
+
if ((ce = x.centerOfMass) != null && ce.every(Number.isFinite) && x.centerOfMass.some((F) => F !== 0)) throw $(`Custom center of mass requires explicit inertia: ${_}`, "E_USD_PARTIAL_INERTIA");
|
|
1658
|
+
d.push({ body: _, mass: x.mass * p });
|
|
1659
|
+
}
|
|
1660
|
+
}
|
|
1661
|
+
const k = e.data.physics.colliders.filter((F) => F.enabled && F.bodyPath === _);
|
|
1662
|
+
if (!k.length && !Q) throw $(`USD rigid body has no authored collision geometry: ${_}`, "E_USD_MISSING_COLLISION_GEOMETRY");
|
|
1663
|
+
for (const F of k) {
|
|
1664
|
+
const H = e.data.physics.materials.find((_e) => _e.path === F.material), ne = (x == null ? void 0 : x.density) != null && x.density > 0 ? x.density : H == null ? void 0 : H.density, ye = ne != null && ne > 0 ? ne * p / u ** 3 : 1e3, $e = (H == null ? void 0 : H.dynamicFriction) ?? 0.4, ve = `density="${ye}" group="3" contype="1" conaffinity="1" friction="${$e} 0.01 0.0002"`;
|
|
1665
|
+
I.push(tt(e, F, _, L, w++, a, ve));
|
|
1666
|
+
}
|
|
1667
|
+
for (const [F, H] of c) H.body0 === _ && I.push(m(F, L));
|
|
1668
|
+
return I.push("</body>"), I.join("");
|
|
1669
|
+
}, U = e.data.physics.colliders.filter((_) => _.enabled && !_.bodyPath), E = U.map((_) => {
|
|
1670
|
+
const b = e.data.physics.materials.find((v) => v.path === _.material), A = (b == null ? void 0 : b.density) != null && b.density > 0 ? b.density * p / u ** 3 : 1e3, L = (b == null ? void 0 : b.dynamicFriction) ?? 0.4, W = `density="${A}" group="3" contype="1" conaffinity="1" friction="${L} 0.01 0.0002"`;
|
|
1671
|
+
return tt(e, _, "", new pe(), w++, a, W);
|
|
1672
|
+
}).join(""), M = fn(e, t, U) ? `<geom name="__viewer_default_ground__" type="plane" pos="0 0 ${dn(e, t)}" size="1 1 0.1" group="3" contype="1" conaffinity="1" friction="0.8 0.01 0.0002"/>` : "", D = [...y.keys()].filter((_) => {
|
|
1673
|
+
var b;
|
|
1674
|
+
return !((b = c.get(_)) != null && b.body0);
|
|
1675
|
+
}).map((_) => m(_)).join("");
|
|
1676
|
+
if (g.size !== y.size) throw $("USD joint graph contains unreachable bodies or a cycle.", "E_USD_UNREACHABLE_BODIES");
|
|
1677
|
+
if (e.data.physics.scenes.length > 1) throw $("Multiple USD PhysicsScene prims are not supported.", "E_USD_MULTIPLE_PHYSICS_SCENES");
|
|
1678
|
+
const P = e.data.physics.scenes[0], C = P != null && P.gravityDirection && P.gravityMagnitude != null && P.gravityMagnitude >= 0 ? new T(...P.gravityDirection).normalize().multiplyScalar(P.gravityMagnitude * u).applyQuaternion(e.scene.quaternion) : new T(0, 0, -9.81);
|
|
1679
|
+
return {
|
|
1680
|
+
// Do not inflate contact surfaces across authored clearances. PhysX contactOffset
|
|
1681
|
+
// is not a MuJoCo force-generating margin and must not be copied as one.
|
|
1682
|
+
format: "mjcf",
|
|
1683
|
+
files: /* @__PURE__ */ new Map(),
|
|
1684
|
+
initialControls: r,
|
|
1685
|
+
initialVelocities: s,
|
|
1686
|
+
massOverrides: d,
|
|
1687
|
+
xml: `<mujoco><compiler angle="radian" autolimits="true"/><option integrator="implicitfast" gravity="${Z(C.toArray())}"><flag filterparent="disable"/></option><default><geom margin="0" solref="0.004 1"/></default>${a.length ? `<asset>${a.join("")}</asset>` : ""}<worldbody>${M}${E}${D}</worldbody>${f.length ? `<contact>${f.join("")}</contact>` : ""}${h.length ? `<equality>${h.join("")}</equality>` : ""}${i.length ? `<actuator>${i.join("")}</actuator>` : ""}</mujoco>`
|
|
1688
|
+
};
|
|
1689
|
+
}
|
|
1690
|
+
function fn(e, t, n = e.data.physics.colliders.filter((o) => o.enabled && !o.bodyPath)) {
|
|
1691
|
+
if (!t.length || n.some((d) => d.typeName.toLowerCase().includes("plane"))) return !1;
|
|
1692
|
+
const o = We(e, e.data.physics.colliders.filter(
|
|
1693
|
+
(d) => d.enabled && d.bodyPath && t.includes(d.bodyPath)
|
|
1694
|
+
));
|
|
1695
|
+
if (o.isEmpty()) return n.length === 0;
|
|
1696
|
+
const a = Math.max(o.max.x - o.min.x, 1e-6), h = Math.max(o.max.y - o.min.y, 1e-6), f = Math.max(a, h, o.max.z - o.min.z) * 0.05;
|
|
1697
|
+
return !n.some((d) => {
|
|
1698
|
+
const i = We(e, [d]);
|
|
1699
|
+
if (i.isEmpty()) return !1;
|
|
1700
|
+
const r = i.max.x >= o.min.x && i.min.x <= o.max.x, s = i.max.y >= o.min.y && i.min.y <= o.max.y;
|
|
1701
|
+
return r && s && i.max.z <= o.min.z + f;
|
|
1702
|
+
});
|
|
1703
|
+
}
|
|
1704
|
+
function dn(e, t) {
|
|
1705
|
+
const n = We(e, e.data.physics.colliders.filter(
|
|
1706
|
+
(a) => a.enabled && a.bodyPath && t.includes(a.bodyPath)
|
|
1707
|
+
)), o = n.isEmpty() ? 0 : n.min.z;
|
|
1708
|
+
return Number.isFinite(o) ? String(o) : "0";
|
|
1709
|
+
}
|
|
1710
|
+
function We(e, t) {
|
|
1711
|
+
const n = new Me();
|
|
1712
|
+
for (const o of t) {
|
|
1713
|
+
const a = e.index.objectsByPath.get(o.path);
|
|
1714
|
+
a && n.union(new Me().setFromObject(a));
|
|
1715
|
+
}
|
|
1716
|
+
return n;
|
|
1717
|
+
}
|
|
1718
|
+
function ft(e) {
|
|
1719
|
+
return e === "Y" ? new T(0, 1, 0) : e === "Z" ? new T(0, 0, 1) : new T(1, 0, 0);
|
|
1720
|
+
}
|
|
1721
|
+
function tt(e, t, n, o, a, h, f) {
|
|
1722
|
+
const d = e.index.objectsByPath.get(t.path);
|
|
1723
|
+
if (!d) throw $(`USD collider node is missing: ${t.path}`, "E_USD_MISSING_COLLISION_GEOMETRY");
|
|
1724
|
+
const i = o.clone().invert().multiply(d.matrixWorld), r = new T(), s = new ee(), u = new T();
|
|
1725
|
+
i.decompose(r, s, u);
|
|
1726
|
+
const p = t.typeName.replace(/^UsdGeom/, "").toLowerCase(), y = (l, c) => {
|
|
1727
|
+
const w = Oe(e, t.path, l);
|
|
1728
|
+
return typeof w == "number" ? w : c;
|
|
1729
|
+
};
|
|
1730
|
+
if (p.includes("cube")) {
|
|
1731
|
+
const l = Math.abs(y("size", 2)) / 2;
|
|
1732
|
+
return `<geom type="box" pos="${Z(r.toArray())}" quat="${be(s)}" size="${Z([Math.abs(u.x) * l, Math.abs(u.y) * l, Math.abs(u.z) * l])}" ${f}/>`;
|
|
1733
|
+
}
|
|
1734
|
+
if (p.includes("plane")) {
|
|
1735
|
+
if (n) throw $(`USD plane collider requires a static world owner: ${t.path}`, "E_USD_UNSUPPORTED_GEOMETRY");
|
|
1736
|
+
const l = String(Oe(e, t.path, "axis") ?? "Z").toUpperCase(), w = { X: new T(1, 0, 0), Y: new T(0, 1, 0), Z: new T(0, 0, 1) }[l];
|
|
1737
|
+
if (!w) throw $(`Unsupported USD plane axis: ${l}`, "E_USD_UNSUPPORTED_GEOMETRY");
|
|
1738
|
+
const g = s.clone().multiply(new ee().setFromUnitVectors(new T(0, 0, 1), w));
|
|
1739
|
+
return `<geom type="plane" pos="${Z(r.toArray())}" quat="${be(g)}" size="1 1 0.1" ${f}/>`;
|
|
1740
|
+
}
|
|
1741
|
+
if (p.includes("cone"))
|
|
1742
|
+
throw $(`MuJoCo has no analytic cone geom; a validated mesh conversion is required: ${t.path}`, "E_USD_UNSUPPORTED_GEOMETRY");
|
|
1743
|
+
if (p.includes("sphere")) {
|
|
1744
|
+
const l = [Math.abs(u.x), Math.abs(u.y), Math.abs(u.z)];
|
|
1745
|
+
if (Math.max(...l) - Math.min(...l) > 1e-6) throw $(`USD sphere collider does not support non-uniform scale: ${t.path}`, "E_USD_NONUNIFORM_RADIAL_SCALE");
|
|
1746
|
+
return `<geom type="sphere" pos="${Z(r.toArray())}" quat="${be(s)}" size="${l[0] * y("radius", 1)}" ${f}/>`;
|
|
1747
|
+
}
|
|
1748
|
+
if (p.includes("cylinder") || p.includes("capsule")) {
|
|
1749
|
+
const l = String(Oe(e, t.path, "axis") ?? "Z").toUpperCase(), c = { X: 0, Y: 1, Z: 2 }[l];
|
|
1750
|
+
if (c === void 0) throw $(`Unsupported USD collider axis: ${l}`, "E_USD_UNSUPPORTED_GEOMETRY");
|
|
1751
|
+
const w = [Math.abs(u.x), Math.abs(u.y), Math.abs(u.z)], g = w.filter((R, D) => D !== c);
|
|
1752
|
+
if (Math.abs(g[0] - g[1]) > 1e-6) throw $(`USD ${t.typeName} collider does not support non-uniform radial scale: ${t.path}`, "E_USD_NONUNIFORM_RADIAL_SCALE");
|
|
1753
|
+
const m = new T(...{ X: [1, 0, 0], Y: [0, 1, 0], Z: [0, 0, 1] }[l]), U = s.clone().multiply(new ee().setFromUnitVectors(new T(0, 0, 1), m)), E = y("radius", 1) * g[0], M = y("height", 2) * w[c] / 2;
|
|
1754
|
+
return `<geom type="${p.includes("capsule") ? "capsule" : "cylinder"}" pos="${Z(r.toArray())}" quat="${be(U)}" size="${E} ${M}" ${f}/>`;
|
|
1755
|
+
}
|
|
1756
|
+
if (p.includes("mesh")) {
|
|
1757
|
+
if (t.approximation && !["none", "convexHull"].includes(t.approximation)) throw $(`USD mesh approximation cannot be mapped exactly: ${t.path}`, "E_USD_UNSUPPORTED_APPROXIMATION");
|
|
1758
|
+
const l = [];
|
|
1759
|
+
if (d.traverse((U) => {
|
|
1760
|
+
U instanceof te && l.push(U);
|
|
1761
|
+
}), !l.length) throw $(`USD collider has no mesh geometry: ${t.path}`, "E_USD_MISSING_COLLISION_GEOMETRY");
|
|
1762
|
+
const c = [], w = [];
|
|
1763
|
+
let g = 0;
|
|
1764
|
+
for (const U of l) {
|
|
1765
|
+
const E = U.geometry.getAttribute("position");
|
|
1766
|
+
for (let R = 0; R < E.count; R++) {
|
|
1767
|
+
const D = new T().fromBufferAttribute(E, R).applyMatrix4(o.clone().invert().multiply(U.matrixWorld));
|
|
1768
|
+
c.push(D.x, D.y, D.z);
|
|
1769
|
+
}
|
|
1770
|
+
const M = U.geometry.index;
|
|
1771
|
+
for (let R = 0; R < (M ? M.count : E.count); R += 3) w.push(g + (M ? M.getX(R) : R), g + (M ? M.getX(R + 1) : R + 1), g + (M ? M.getX(R + 2) : R + 2));
|
|
1772
|
+
g += E.count;
|
|
1773
|
+
}
|
|
1774
|
+
const m = `collision_${a}`;
|
|
1775
|
+
return h.push(`<mesh name="${m}" vertex="${Z(c)}" face="${Z(w)}"/>`), `<geom type="mesh" mesh="${m}" ${f}/>`;
|
|
1776
|
+
}
|
|
1777
|
+
throw $(`Unsupported USD collider geometry: ${t.typeName}`, "E_USD_UNSUPPORTED_GEOMETRY");
|
|
1778
|
+
}
|
|
1779
|
+
function hn(e) {
|
|
1780
|
+
const t = e.stage.GetPseudoRoot();
|
|
1781
|
+
try {
|
|
1782
|
+
const n = Number(t.GetMetadata("metersPerUnit") ?? 0.01), o = Number(t.GetMetadata("kilogramsPerUnit") ?? 1);
|
|
1783
|
+
if (!Number.isFinite(n) || n <= 0) throw $("USD metersPerUnit must be finite and positive.", "E_USD_INVALID_UNITS");
|
|
1784
|
+
if (!Number.isFinite(o) || o <= 0) throw $("USD kilogramsPerUnit must be finite and positive.", "E_USD_INVALID_UNITS");
|
|
1785
|
+
return { metersPerUnit: n, kilogramsPerUnit: o };
|
|
1786
|
+
} finally {
|
|
1787
|
+
t.delete();
|
|
1788
|
+
}
|
|
1789
|
+
}
|
|
1790
|
+
function Ue(e) {
|
|
1791
|
+
const [t = 1, n = 0, o = 0, a = 0] = e;
|
|
1792
|
+
return new ee(n, o, a, t).normalize();
|
|
1793
|
+
}
|
|
1794
|
+
function Z(e) {
|
|
1795
|
+
return e.join(" ");
|
|
1796
|
+
}
|
|
1797
|
+
function be(e) {
|
|
1798
|
+
return `${e.w} ${e.x} ${e.y} ${e.z}`;
|
|
1799
|
+
}
|
|
1800
|
+
function Oe(e, t, n) {
|
|
1801
|
+
var i, r;
|
|
1802
|
+
const o = e.stage;
|
|
1803
|
+
if (!o || !((r = (i = e.pxr) == null ? void 0 : i.Sdf) != null && r.Path)) return null;
|
|
1804
|
+
const a = new e.pxr.Sdf.Path(t), h = o.GetPrimAtPath(a), f = h.GetAttribute(n), d = e.pxr.Usd.TimeCode.Default();
|
|
1805
|
+
try {
|
|
1806
|
+
return f.IsValid() ? f.Get(d) : null;
|
|
1807
|
+
} finally {
|
|
1808
|
+
d.delete(), f.delete(), h.delete(), a.delete();
|
|
1809
|
+
}
|
|
1810
|
+
}
|
|
1811
|
+
function mn() {
|
|
1812
|
+
if (!globalThis.isSecureContext) throw $("OpenUSD requires a secure context.", "E_USD_SECURE_CONTEXT_REQUIRED");
|
|
1813
|
+
if (!globalThis.crossOriginIsolated) throw $("OpenUSD requires COOP/COEP cross-origin isolation.", "E_USD_CROSS_ORIGIN_ISOLATION_REQUIRED");
|
|
1814
|
+
}
|
|
1815
|
+
async function yn(e, t) {
|
|
1816
|
+
var n;
|
|
1817
|
+
if (e.url)
|
|
1818
|
+
try {
|
|
1819
|
+
return new URL(e.url, ((n = globalThis.location) == null ? void 0 : n.href) ?? e.baseUrl ?? void 0).href;
|
|
1820
|
+
} catch {
|
|
1821
|
+
return e.url;
|
|
1822
|
+
}
|
|
1823
|
+
return e.resolve(t);
|
|
1824
|
+
}
|
|
1825
|
+
async function _n(e) {
|
|
1826
|
+
const t = e.url ?? await e.resolve(e.entryPath ?? ""), n = await fetch(t, { signal: e.signal });
|
|
1827
|
+
if (!n.ok) throw $(`USD request failed (${n.status}): ${t}`, n.status === 401 || n.status === 403 ? "E_ASSET_AUTH" : "E_ASSET_FETCH");
|
|
1828
|
+
return n.blob();
|
|
1829
|
+
}
|
|
1830
|
+
const gn = /* @__PURE__ */ new Set(["usd", "usda", "usdc"]), nt = 1024, Sn = 8;
|
|
1831
|
+
let wn = 0;
|
|
1832
|
+
async function Un(e, t, n, o, a) {
|
|
1833
|
+
const h = `/tmp/viewer-usd-resolver/${++wn}`;
|
|
1834
|
+
e.FS.createDir(h);
|
|
1835
|
+
const f = [{ path: dt(o), blob: n, depth: 0 }], d = /* @__PURE__ */ new Set();
|
|
1836
|
+
try {
|
|
1837
|
+
for (; f.length > 0; ) {
|
|
1838
|
+
t.signal.throwIfAborted();
|
|
1839
|
+
const i = f.shift();
|
|
1840
|
+
if (d.has(i.path) || i.depth > Sn) continue;
|
|
1841
|
+
if (d.size >= nt) throw $(`USD dependency limit exceeded (${nt}).`, "E_ASSET_RESOURCE_LIMIT");
|
|
1842
|
+
d.add(i.path);
|
|
1843
|
+
const r = `${h}/${i.path}`;
|
|
1844
|
+
e.FS.createDir(r.split("/").slice(0, -1).join("/")), e.FS.writeFile(r, new Uint8Array(await i.blob.arrayBuffer()));
|
|
1845
|
+
const s = e.UsdUtils.ExtractSanitizedExternalReferences(r);
|
|
1846
|
+
for (const u of s) {
|
|
1847
|
+
const p = bn(i.path, u);
|
|
1848
|
+
if (!p || d.has(p)) continue;
|
|
1849
|
+
const y = await t.resolve(p), l = await fetch(y, { signal: t.signal });
|
|
1850
|
+
if (!l.ok) {
|
|
1851
|
+
const w = l.status === 401 || l.status === 403 ? "E_ASSET_AUTH" : "E_ASSET_FETCH";
|
|
1852
|
+
throw $(`USD dependency request failed (${l.status}): ${p}`, w);
|
|
1853
|
+
}
|
|
1854
|
+
const c = await l.blob();
|
|
1855
|
+
a.put(p, c), gn.has(En(p)) && f.push({ path: p, blob: c, depth: i.depth + 1 });
|
|
1856
|
+
}
|
|
1857
|
+
}
|
|
1858
|
+
} finally {
|
|
1859
|
+
ht(e, h);
|
|
1860
|
+
}
|
|
1861
|
+
}
|
|
1862
|
+
function bn(e, t) {
|
|
1863
|
+
if (!t || /^(?:data|blob):/i.test(t)) return null;
|
|
1864
|
+
if (/^[a-z][a-z0-9+.-]*:/i.test(t) || t.startsWith("/")) return t;
|
|
1865
|
+
const n = e.split("/").slice(0, -1).join("/");
|
|
1866
|
+
return dt(n ? `${n}/${t}` : t);
|
|
1867
|
+
}
|
|
1868
|
+
function dt(e) {
|
|
1869
|
+
const t = [];
|
|
1870
|
+
for (const n of e.replaceAll("\\", "/").split("/"))
|
|
1871
|
+
!n || n === "." || (n === ".." ? t.pop() : t.push(n));
|
|
1872
|
+
return t.join("/");
|
|
1873
|
+
}
|
|
1874
|
+
function En(e) {
|
|
1875
|
+
var t, n;
|
|
1876
|
+
return ((n = (t = e.split(/[?#]/, 1)[0]) == null ? void 0 : t.split(".").pop()) == null ? void 0 : n.toLowerCase()) ?? "";
|
|
1877
|
+
}
|
|
1878
|
+
function ht(e, t) {
|
|
1879
|
+
if (e.FS.exists(t)) {
|
|
1880
|
+
for (const n of e.FS.listDir(t))
|
|
1881
|
+
n.isDir ? ht(e, n.path) : e.FS.deleteFile(n.path);
|
|
1882
|
+
e.FS.deleteDir(t);
|
|
1883
|
+
}
|
|
1884
|
+
}
|
|
1885
|
+
function Se(e) {
|
|
1886
|
+
return e.replaceAll("&", "&").replaceAll('"', """).replaceAll("<", "<").replaceAll(">", ">");
|
|
1887
|
+
}
|
|
1888
|
+
function $(e, t) {
|
|
1889
|
+
return Object.assign(new Error(e), { code: t });
|
|
1890
|
+
}
|
|
1891
|
+
function Fe() {
|
|
1892
|
+
return Object.assign(new Error("USD load aborted."), { name: "AbortError", code: "E_ABORTED" });
|
|
1893
|
+
}
|
|
1894
|
+
export {
|
|
1895
|
+
ln as buildUsdVisualReferenceOwners,
|
|
1896
|
+
et as compileUsdCollisionOverlay,
|
|
1897
|
+
ut as compileUsdCollisionVisual,
|
|
1898
|
+
pn as compileUsdPhysics,
|
|
1899
|
+
cn as compileUsdVisual,
|
|
1900
|
+
rn as firstUsdVisualWarning,
|
|
1901
|
+
In as isUsdPhysicsFallbackEligible,
|
|
1902
|
+
On as loadUsdSimulation,
|
|
1903
|
+
un as parseUsdReferenceMetadata,
|
|
1904
|
+
pt as resolveUsdJoints,
|
|
1905
|
+
Un as resolveUsdResourcePackage,
|
|
1906
|
+
fn as shouldInjectUsdDefaultGround
|
|
1907
|
+
};
|