@mml-io/mml-web-threejs 0.24.1 → 0.26.0

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/build/index.js CHANGED
@@ -1552,14 +1552,248 @@ var ThreeJSMElement = class extends MElementGraphics {
1552
1552
  import { Model as Model2, TransformableElement } from "@mml-io/mml-web";
1553
1553
  import { ModelGraphics } from "@mml-io/mml-web";
1554
1554
  import { LoadingInstanceManager as LoadingInstanceManager4 } from "@mml-io/mml-web";
1555
+ import * as THREE13 from "three";
1556
+
1557
+ // src/ThreeJSAutoInstanceScene.ts
1555
1558
  import * as THREE12 from "three";
1559
+ function autoInstanceScene(root, debug) {
1560
+ const eligibleMeshes = [];
1561
+ root.traverse((object) => {
1562
+ if (!object.isMesh) return;
1563
+ const mesh = object;
1564
+ if (mesh.isSkinnedMesh) return;
1565
+ if (mesh.geometry.morphAttributes && Object.keys(mesh.geometry.morphAttributes).length > 0)
1566
+ return;
1567
+ if (Array.isArray(mesh.material)) return;
1568
+ eligibleMeshes.push(mesh);
1569
+ });
1570
+ if (eligibleMeshes.length === 0) return;
1571
+ const buckets = /* @__PURE__ */ new Map();
1572
+ const materialIds = /* @__PURE__ */ new Map();
1573
+ let nextMaterialId = 0;
1574
+ for (const mesh of eligibleMeshes) {
1575
+ const mat = mesh.material;
1576
+ if (!materialIds.has(mat)) {
1577
+ materialIds.set(mat, nextMaterialId++);
1578
+ }
1579
+ const materialId = materialIds.get(mat);
1580
+ const geomFingerprint = computeGeometryFingerprint(mesh.geometry);
1581
+ const key = `${materialId}|${geomFingerprint}`;
1582
+ let bucket = buckets.get(key);
1583
+ if (!bucket) {
1584
+ bucket = [];
1585
+ buckets.set(key, bucket);
1586
+ }
1587
+ bucket.push(mesh);
1588
+ }
1589
+ const verifiedGroups = [];
1590
+ for (const bucket of buckets.values()) {
1591
+ if (bucket.length < 2) continue;
1592
+ const subGroups = verifyGeometryEquality(bucket);
1593
+ for (const subGroup of subGroups) {
1594
+ if (subGroup.length >= 2) {
1595
+ verifiedGroups.push(subGroup);
1596
+ }
1597
+ }
1598
+ }
1599
+ if (verifiedGroups.length === 0) return;
1600
+ root.updateWorldMatrix(true, true);
1601
+ const rootInverse = new THREE12.Matrix4().copy(root.matrixWorld).invert();
1602
+ let totalMeshesInstanced = 0;
1603
+ let totalInstancedMeshes = 0;
1604
+ let totalDuplicatesRemoved = 0;
1605
+ const tempMatrix = new THREE12.Matrix4();
1606
+ const flipMatrix = new THREE12.Matrix4().makeScale(-1, 1, 1);
1607
+ for (const group of verifiedGroups) {
1608
+ const seenMatrixKeys = /* @__PURE__ */ new Set();
1609
+ const uniqueMatrices = [];
1610
+ for (const mesh of group) {
1611
+ tempMatrix.multiplyMatrices(rootInverse, mesh.matrixWorld);
1612
+ const key = matrixKey(tempMatrix);
1613
+ if (!seenMatrixKeys.has(key)) {
1614
+ seenMatrixKeys.add(key);
1615
+ uniqueMatrices.push(tempMatrix.clone());
1616
+ }
1617
+ }
1618
+ const duplicatesInGroup = group.length - uniqueMatrices.length;
1619
+ totalDuplicatesRemoved += duplicatesInGroup;
1620
+ if (uniqueMatrices.length < 2) {
1621
+ for (let i = 1; i < group.length; i++) {
1622
+ group[i].removeFromParent();
1623
+ if (group[i].geometry !== group[0].geometry) {
1624
+ group[i].geometry.dispose();
1625
+ }
1626
+ const mat = group[i].material;
1627
+ if (mat !== group[0].material) {
1628
+ mat.dispose();
1629
+ }
1630
+ }
1631
+ continue;
1632
+ }
1633
+ const normalMatrices = uniqueMatrices.filter((m) => m.determinant() >= 0);
1634
+ const mirroredMatrices = uniqueMatrices.filter((m) => m.determinant() < 0);
1635
+ const referenceMesh = group[0];
1636
+ const keptGeometry = referenceMesh.geometry;
1637
+ const keptMaterial = referenceMesh.material;
1638
+ for (const mesh of group) {
1639
+ mesh.removeFromParent();
1640
+ if (mesh.geometry !== keptGeometry) {
1641
+ mesh.geometry.dispose();
1642
+ }
1643
+ const mat = mesh.material;
1644
+ if (mat !== keptMaterial) {
1645
+ mat.dispose();
1646
+ }
1647
+ }
1648
+ if (normalMatrices.length > 0) {
1649
+ const instancedMesh = new THREE12.InstancedMesh(
1650
+ referenceMesh.geometry,
1651
+ referenceMesh.material,
1652
+ normalMatrices.length
1653
+ );
1654
+ instancedMesh.castShadow = referenceMesh.castShadow;
1655
+ instancedMesh.receiveShadow = referenceMesh.receiveShadow;
1656
+ for (let i = 0; i < normalMatrices.length; i++) {
1657
+ instancedMesh.setMatrixAt(i, normalMatrices[i]);
1658
+ }
1659
+ instancedMesh.instanceMatrix.needsUpdate = true;
1660
+ root.add(instancedMesh);
1661
+ totalMeshesInstanced += normalMatrices.length;
1662
+ totalInstancedMeshes++;
1663
+ }
1664
+ if (mirroredMatrices.length > 0) {
1665
+ const instancedMesh = new THREE12.InstancedMesh(
1666
+ referenceMesh.geometry,
1667
+ referenceMesh.material,
1668
+ mirroredMatrices.length
1669
+ );
1670
+ instancedMesh.castShadow = referenceMesh.castShadow;
1671
+ instancedMesh.receiveShadow = referenceMesh.receiveShadow;
1672
+ instancedMesh.scale.set(-1, 1, 1);
1673
+ for (let i = 0; i < mirroredMatrices.length; i++) {
1674
+ tempMatrix.multiplyMatrices(flipMatrix, mirroredMatrices[i]);
1675
+ instancedMesh.setMatrixAt(i, tempMatrix);
1676
+ }
1677
+ instancedMesh.instanceMatrix.needsUpdate = true;
1678
+ root.add(instancedMesh);
1679
+ totalMeshesInstanced += mirroredMatrices.length;
1680
+ totalInstancedMeshes++;
1681
+ }
1682
+ }
1683
+ const drawCallsSaved = totalMeshesInstanced - totalInstancedMeshes;
1684
+ const duplicates = totalDuplicatesRemoved > 0 ? `, removed ${totalDuplicatesRemoved} duplicate overlapping meshes` : "";
1685
+ if (debug) {
1686
+ console.log(`autoInstanceScene:
1687
+ Instanced ${totalMeshesInstanced} meshes into ${totalInstancedMeshes} InstancedMesh objects
1688
+ Savings: ${drawCallsSaved} draw calls
1689
+ ${duplicates}`);
1690
+ }
1691
+ }
1692
+ function computeGeometryFingerprint(geometry) {
1693
+ const posAttr = geometry.getAttribute("position");
1694
+ const indexAttr = geometry.index;
1695
+ const vertexCount = posAttr ? posAttr.count : 0;
1696
+ const indexCount = indexAttr ? indexAttr.count : 0;
1697
+ let posHash = 0;
1698
+ if (posAttr) {
1699
+ posHash = hashTypedArray(posAttr.array);
1700
+ }
1701
+ let idxHash = 0;
1702
+ if (indexAttr) {
1703
+ idxHash = hashTypedArray(indexAttr.array);
1704
+ }
1705
+ const normalAttr = geometry.getAttribute("normal");
1706
+ let normalHash = 0;
1707
+ if (normalAttr) {
1708
+ normalHash = hashTypedArray(normalAttr.array);
1709
+ }
1710
+ const uvAttr = geometry.getAttribute("uv");
1711
+ let uvHash = 0;
1712
+ if (uvAttr) {
1713
+ uvHash = hashTypedArray(uvAttr.array);
1714
+ }
1715
+ return `${vertexCount}:${indexCount}:${posHash}:${idxHash}:${normalHash}:${uvHash}`;
1716
+ }
1717
+ var _hashFloat32 = new Float32Array(1);
1718
+ var _hashDataView = new DataView(_hashFloat32.buffer);
1719
+ function hashTypedArray(arr) {
1720
+ let hash = 2166136261;
1721
+ const len = arr.length;
1722
+ const step = len > 256 ? Math.floor(len / 256) : 1;
1723
+ for (let i = 0; i < len; i += step) {
1724
+ _hashFloat32[0] = arr[i];
1725
+ const intBits = _hashDataView.getInt32(0, true);
1726
+ hash ^= intBits;
1727
+ hash = Math.imul(hash, 16777619);
1728
+ }
1729
+ return hash >>> 0;
1730
+ }
1731
+ function verifyGeometryEquality(meshes) {
1732
+ const groups = [];
1733
+ for (const mesh of meshes) {
1734
+ let placed = false;
1735
+ for (const group of groups) {
1736
+ if (geometriesAreEqual(group[0].geometry, mesh.geometry)) {
1737
+ group.push(mesh);
1738
+ placed = true;
1739
+ break;
1740
+ }
1741
+ }
1742
+ if (!placed) {
1743
+ groups.push([mesh]);
1744
+ }
1745
+ }
1746
+ return groups;
1747
+ }
1748
+ function geometriesAreEqual(a, b) {
1749
+ if (a === b) return true;
1750
+ const attrNamesA = Object.keys(a.attributes);
1751
+ const attrNamesB = Object.keys(b.attributes);
1752
+ if (attrNamesA.length !== attrNamesB.length) return false;
1753
+ for (const name of attrNamesA) {
1754
+ const attrA = a.getAttribute(name);
1755
+ const attrB = b.getAttribute(name);
1756
+ if (!attrA || !attrB) return false;
1757
+ if (attrA.count !== attrB.count) return false;
1758
+ if (attrA.itemSize !== attrB.itemSize) return false;
1759
+ if (!typedArraysEqual(attrA.array, attrB.array))
1760
+ return false;
1761
+ }
1762
+ const idxA = a.index;
1763
+ const idxB = b.index;
1764
+ if (idxA === null !== (idxB === null)) return false;
1765
+ if (idxA && idxB) {
1766
+ if (idxA.count !== idxB.count) return false;
1767
+ if (!typedArraysEqual(idxA.array, idxB.array))
1768
+ return false;
1769
+ }
1770
+ return true;
1771
+ }
1772
+ function typedArraysEqual(a, b) {
1773
+ if (a.length !== b.length) return false;
1774
+ for (let i = 0; i < a.length; i++) {
1775
+ if (a[i] !== b[i]) return false;
1776
+ }
1777
+ return true;
1778
+ }
1779
+ var MATRIX_QUANTIZE = 1e5;
1780
+ function matrixKey(m) {
1781
+ const e = m.elements;
1782
+ let s = "" + Math.round(e[0] * MATRIX_QUANTIZE);
1783
+ for (let i = 1; i < 16; i++) {
1784
+ s += "," + Math.round(e[i] * MATRIX_QUANTIZE);
1785
+ }
1786
+ return s;
1787
+ }
1788
+
1789
+ // src/elements/ThreeJSModel.ts
1556
1790
  function createFilteredClip(clip, nodeNames) {
1557
1791
  const compatibleTracks = clip.tracks.filter((track) => {
1558
1792
  const trackName = track.name;
1559
1793
  const nodeName = trackName.split(".")[0];
1560
1794
  return nodeNames.has(nodeName);
1561
1795
  });
1562
- const filteredClip = new THREE12.AnimationClip(clip.name, clip.duration, compatibleTracks);
1796
+ const filteredClip = new THREE13.AnimationClip(clip.name, clip.duration, compatibleTracks);
1563
1797
  return filteredClip;
1564
1798
  }
1565
1799
  var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
@@ -1933,16 +2167,17 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
1933
2167
  child.receiveShadow = true;
1934
2168
  }
1935
2169
  });
2170
+ autoInstanceScene(result.group);
1936
2171
  const group = result.group;
1937
2172
  const bones = /* @__PURE__ */ new Map();
1938
2173
  const nodeNames = /* @__PURE__ */ new Set();
1939
2174
  group.traverse((object) => {
1940
2175
  nodeNames.add(object.name);
1941
- if (object instanceof THREE12.Bone) {
2176
+ if (object instanceof THREE13.Bone) {
1942
2177
  bones.set(object.name, object);
1943
2178
  }
1944
2179
  });
1945
- const boundingBox = new THREE12.Box3();
2180
+ const boundingBox = new THREE13.Box3();
1946
2181
  group.updateWorldMatrix(true, true);
1947
2182
  boundingBox.expandByObject(group);
1948
2183
  this.loadedState = {
@@ -1950,12 +2185,12 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
1950
2185
  bones,
1951
2186
  nodeNames,
1952
2187
  boundingBox: {
1953
- size: boundingBox.getSize(new THREE12.Vector3(0, 0, 0)),
1954
- centerOffset: boundingBox.getCenter(new THREE12.Vector3(0, 0, 0))
2188
+ size: boundingBox.getSize(new THREE13.Vector3(0, 0, 0)),
2189
+ centerOffset: boundingBox.getCenter(new THREE13.Vector3(0, 0, 0))
1955
2190
  }
1956
2191
  };
1957
2192
  this.model.getContainer().add(group);
1958
- this.childAnimationMixer = new THREE12.AnimationMixer(group);
2193
+ this.childAnimationMixer = new THREE13.AnimationMixer(group);
1959
2194
  if (!this.documentTimeTickListener) {
1960
2195
  this.documentTimeTickListener = this.model.addDocumentTimeTickListener(
1961
2196
  (documentTime) => {
@@ -1990,8 +2225,8 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
1990
2225
  });
1991
2226
  }
1992
2227
  registerAttachment(attachment) {
1993
- const childAnimationGroup = new THREE12.AnimationObjectGroup();
1994
- const childAnimationMixer = new THREE12.AnimationMixer(childAnimationGroup);
2228
+ const childAnimationGroup = new THREE13.AnimationObjectGroup();
2229
+ const childAnimationMixer = new THREE13.AnimationMixer(childAnimationGroup);
1995
2230
  const animState = {
1996
2231
  directAnimation: null,
1997
2232
  childAnimations: {
@@ -2012,8 +2247,8 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
2012
2247
  if (!attachmentLoadedState) {
2013
2248
  throw new Error("Attachment must be loaded before registering");
2014
2249
  }
2015
- const animationGroup = new THREE12.AnimationObjectGroup();
2016
- const animationMixer = new THREE12.AnimationMixer(animationGroup);
2250
+ const animationGroup = new THREE13.AnimationObjectGroup();
2251
+ const animationMixer = new THREE13.AnimationMixer(animationGroup);
2017
2252
  const action = animationMixer.clipAction(this.animState.currentAnimationClip);
2018
2253
  animState.directAnimation = {
2019
2254
  animationMixer,
@@ -2040,7 +2275,7 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
2040
2275
  this.clearDebugVisualisation();
2041
2276
  } else {
2042
2277
  if (!this.debugBoundingBox) {
2043
- this.debugBoundingBox = new THREE12.Mesh(
2278
+ this.debugBoundingBox = new THREE13.Mesh(
2044
2279
  _ThreeJSModel.DebugBoundingBoxGeometry,
2045
2280
  _ThreeJSModel.DebugBoundingBoxMaterial
2046
2281
  );
@@ -2121,8 +2356,8 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
2121
2356
  currentAnimationClip: anim,
2122
2357
  appliedAnimation: null
2123
2358
  };
2124
- const animationGroup = new THREE12.AnimationObjectGroup();
2125
- const animationMixer = new THREE12.AnimationMixer(animationGroup);
2359
+ const animationGroup = new THREE13.AnimationObjectGroup();
2360
+ const animationMixer = new THREE13.AnimationMixer(animationGroup);
2126
2361
  const action = animationMixer.clipAction(anim);
2127
2362
  this.animState.appliedAnimation = {
2128
2363
  animationGroup,
@@ -2323,8 +2558,8 @@ var _ThreeJSModel = class _ThreeJSModel extends ModelGraphics {
2323
2558
  }
2324
2559
  }
2325
2560
  };
2326
- _ThreeJSModel.DebugBoundingBoxGeometry = new THREE12.BoxGeometry(1, 1, 1, 1, 1, 1);
2327
- _ThreeJSModel.DebugBoundingBoxMaterial = new THREE12.MeshBasicMaterial({
2561
+ _ThreeJSModel.DebugBoundingBoxGeometry = new THREE13.BoxGeometry(1, 1, 1, 1, 1, 1);
2562
+ _ThreeJSModel.DebugBoundingBoxMaterial = new THREE13.MeshBasicMaterial({
2328
2563
  color: 16711680,
2329
2564
  wireframe: true,
2330
2565
  transparent: true,
@@ -2355,15 +2590,15 @@ var ThreeJSOverlay = class extends OverlayGraphics {
2355
2590
 
2356
2591
  // src/elements/ThreeJSPlane.ts
2357
2592
  import { PlaneGraphics } from "@mml-io/mml-web";
2358
- import * as THREE13 from "three";
2593
+ import * as THREE14 from "three";
2359
2594
  var _ThreeJSPlane = class _ThreeJSPlane extends PlaneGraphics {
2360
2595
  constructor(plane) {
2361
2596
  super(plane);
2362
2597
  this.plane = plane;
2363
- this.material = new THREE13.MeshStandardMaterial({
2364
- color: new THREE13.Color(plane.props.color.r, plane.props.color.g, plane.props.color.b)
2598
+ this.material = new THREE14.MeshStandardMaterial({
2599
+ color: new THREE14.Color(plane.props.color.r, plane.props.color.g, plane.props.color.b)
2365
2600
  });
2366
- this.mesh = new THREE13.Mesh(_ThreeJSPlane.planeGeometry, this.material);
2601
+ this.mesh = new THREE14.Mesh(_ThreeJSPlane.planeGeometry, this.material);
2367
2602
  this.mesh.castShadow = plane.props.castShadows;
2368
2603
  this.mesh.receiveShadow = true;
2369
2604
  this.plane.getContainer().add(this.mesh);
@@ -2376,7 +2611,7 @@ var _ThreeJSPlane = class _ThreeJSPlane extends PlaneGraphics {
2376
2611
  return this.mesh;
2377
2612
  }
2378
2613
  setColor(color) {
2379
- this.material.color = new THREE13.Color(color.r, color.g, color.b);
2614
+ this.material.color = new THREE14.Color(color.r, color.g, color.b);
2380
2615
  }
2381
2616
  setWidth(width) {
2382
2617
  this.mesh.scale.x = width;
@@ -2396,12 +2631,12 @@ var _ThreeJSPlane = class _ThreeJSPlane extends PlaneGraphics {
2396
2631
  dispose() {
2397
2632
  }
2398
2633
  };
2399
- _ThreeJSPlane.planeGeometry = new THREE13.PlaneGeometry(1, 1);
2634
+ _ThreeJSPlane.planeGeometry = new THREE14.PlaneGeometry(1, 1);
2400
2635
  var ThreeJSPlane = _ThreeJSPlane;
2401
2636
 
2402
2637
  // src/elements/ThreeJSPositionProbe.ts
2403
2638
  import { PositionProbeGraphics } from "@mml-io/mml-web";
2404
- import * as THREE14 from "three";
2639
+ import * as THREE15 from "three";
2405
2640
  var _ThreeJSPositionProbe = class _ThreeJSPositionProbe extends PositionProbeGraphics {
2406
2641
  constructor(positionProbe) {
2407
2642
  super(positionProbe);
@@ -2429,7 +2664,7 @@ var _ThreeJSPositionProbe = class _ThreeJSPositionProbe extends PositionProbeGra
2429
2664
  this.clearDebugVisualisation();
2430
2665
  } else {
2431
2666
  if (this.positionProbe.isConnected && !this.debugMesh) {
2432
- const mesh = new THREE14.Mesh(
2667
+ const mesh = new THREE15.Mesh(
2433
2668
  _ThreeJSPositionProbe.DebugGeometry,
2434
2669
  _ThreeJSPositionProbe.DebugMaterial
2435
2670
  );
@@ -2451,8 +2686,8 @@ var _ThreeJSPositionProbe = class _ThreeJSPositionProbe extends PositionProbeGra
2451
2686
  this.clearDebugVisualisation();
2452
2687
  }
2453
2688
  };
2454
- _ThreeJSPositionProbe.DebugGeometry = new THREE14.SphereGeometry(1, 16, 16, 1);
2455
- _ThreeJSPositionProbe.DebugMaterial = new THREE14.MeshBasicMaterial({
2689
+ _ThreeJSPositionProbe.DebugGeometry = new THREE15.SphereGeometry(1, 16, 16, 1);
2690
+ _ThreeJSPositionProbe.DebugMaterial = new THREE15.MeshBasicMaterial({
2456
2691
  color: 16711680,
2457
2692
  wireframe: true,
2458
2693
  transparent: true,
@@ -2485,11 +2720,11 @@ var ThreeJSPrompt = class extends PromptGraphics {
2485
2720
 
2486
2721
  // src/elements/ThreeJSRemoteDocument.ts
2487
2722
  import { RemoteDocumentGraphics } from "@mml-io/mml-web";
2488
- import * as THREE16 from "three";
2723
+ import * as THREE17 from "three";
2489
2724
 
2490
2725
  // src/ThreeJSReconnectingStatus.ts
2491
2726
  import { CanvasText } from "@mml-io/mml-web";
2492
- import * as THREE15 from "three";
2727
+ import * as THREE16 from "three";
2493
2728
  function createReconnectingStatus() {
2494
2729
  const canvas = new CanvasText().renderText("Reconnecting", {
2495
2730
  bold: true,
@@ -2509,18 +2744,18 @@ function createReconnectingStatus() {
2509
2744
  },
2510
2745
  alignment: "center"
2511
2746
  });
2512
- const texture = new THREE15.Texture(canvas);
2513
- texture.minFilter = THREE15.LinearFilter;
2514
- texture.magFilter = THREE15.LinearFilter;
2515
- texture.format = THREE15.RGBAFormat;
2747
+ const texture = new THREE16.Texture(canvas);
2748
+ texture.minFilter = THREE16.LinearFilter;
2749
+ texture.magFilter = THREE16.LinearFilter;
2750
+ texture.format = THREE16.RGBAFormat;
2516
2751
  texture.needsUpdate = true;
2517
2752
  const width = canvas.width;
2518
2753
  const height = canvas.height;
2519
- const material = new THREE15.MeshBasicMaterial({
2754
+ const material = new THREE16.MeshBasicMaterial({
2520
2755
  map: texture,
2521
- side: THREE15.DoubleSide
2756
+ side: THREE16.DoubleSide
2522
2757
  });
2523
- const geometry = new THREE15.PlaneGeometry(width / 100, height / 100, 1, 1);
2758
+ const geometry = new THREE16.PlaneGeometry(width / 100, height / 100, 1, 1);
2524
2759
  return { geometry, material, width: width / 100, height: height / 100 };
2525
2760
  }
2526
2761
  var reconnectingStatus = null;
@@ -2547,7 +2782,7 @@ var ThreeJSRemoteDocument = class extends RemoteDocumentGraphics {
2547
2782
  } else {
2548
2783
  if (this.statusUI === null) {
2549
2784
  const { geometry, material, height } = getThreeJSReconnectingStatus();
2550
- const mesh = new THREE16.Mesh(
2785
+ const mesh = new THREE17.Mesh(
2551
2786
  geometry,
2552
2787
  material
2553
2788
  );
@@ -2563,17 +2798,17 @@ var ThreeJSRemoteDocument = class extends RemoteDocumentGraphics {
2563
2798
 
2564
2799
  // src/elements/ThreeJSSphere.ts
2565
2800
  import { SphereGraphics } from "@mml-io/mml-web";
2566
- import * as THREE17 from "three";
2801
+ import * as THREE18 from "three";
2567
2802
  var defaultSphereWidthSegments = 16;
2568
2803
  var defaultSphereHeightSegments = 16;
2569
2804
  var _ThreeJSSphere = class _ThreeJSSphere extends SphereGraphics {
2570
2805
  constructor(sphere) {
2571
2806
  super(sphere);
2572
2807
  this.sphere = sphere;
2573
- this.material = new THREE17.MeshStandardMaterial({
2574
- color: new THREE17.Color(sphere.props.color.r, sphere.props.color.g, sphere.props.color.b)
2808
+ this.material = new THREE18.MeshStandardMaterial({
2809
+ color: new THREE18.Color(sphere.props.color.r, sphere.props.color.g, sphere.props.color.b)
2575
2810
  });
2576
- this.mesh = new THREE17.Mesh(_ThreeJSSphere.sphereGeometry, this.material);
2811
+ this.mesh = new THREE18.Mesh(_ThreeJSSphere.sphereGeometry, this.material);
2577
2812
  this.mesh.castShadow = sphere.props.castShadows;
2578
2813
  this.mesh.receiveShadow = true;
2579
2814
  this.sphere.getContainer().add(this.mesh);
@@ -2586,7 +2821,7 @@ var _ThreeJSSphere = class _ThreeJSSphere extends SphereGraphics {
2586
2821
  return this.mesh;
2587
2822
  }
2588
2823
  setColor(color) {
2589
- this.material.color = new THREE17.Color(color.r, color.g, color.b);
2824
+ this.material.color = new THREE18.Color(color.r, color.g, color.b);
2590
2825
  }
2591
2826
  setRadius(radius) {
2592
2827
  this.mesh.scale.x = radius * 2;
@@ -2605,7 +2840,7 @@ var _ThreeJSSphere = class _ThreeJSSphere extends SphereGraphics {
2605
2840
  dispose() {
2606
2841
  }
2607
2842
  };
2608
- _ThreeJSSphere.sphereGeometry = new THREE17.SphereGeometry(
2843
+ _ThreeJSSphere.sphereGeometry = new THREE18.SphereGeometry(
2609
2844
  0.5,
2610
2845
  defaultSphereWidthSegments,
2611
2846
  defaultSphereHeightSegments
@@ -2617,7 +2852,7 @@ import {
2617
2852
  Matr4,
2618
2853
  TransformableGraphics
2619
2854
  } from "@mml-io/mml-web";
2620
- import * as THREE18 from "three";
2855
+ import * as THREE19 from "three";
2621
2856
  var ThreeJSTransformable = class extends TransformableGraphics {
2622
2857
  constructor(transformableElement) {
2623
2858
  super(transformableElement);
@@ -2631,7 +2866,7 @@ var ThreeJSTransformable = class extends TransformableGraphics {
2631
2866
  return new Matr4(container.matrixWorld.elements);
2632
2867
  }
2633
2868
  getWorldPosition() {
2634
- return this.getContainer().getWorldPosition(new THREE18.Vector3());
2869
+ return this.getContainer().getWorldPosition(new THREE19.Vector3());
2635
2870
  }
2636
2871
  getLocalPosition() {
2637
2872
  return this.getContainer().position;
@@ -2679,13 +2914,13 @@ var ThreeJSTransformable = class extends TransformableGraphics {
2679
2914
  this.getContainer().position.z = z;
2680
2915
  }
2681
2916
  setRotationX(rotationX) {
2682
- this.getContainer().rotation.x = rotationX * THREE18.MathUtils.DEG2RAD;
2917
+ this.getContainer().rotation.x = rotationX * THREE19.MathUtils.DEG2RAD;
2683
2918
  }
2684
2919
  setRotationY(rotationY) {
2685
- this.getContainer().rotation.y = rotationY * THREE18.MathUtils.DEG2RAD;
2920
+ this.getContainer().rotation.y = rotationY * THREE19.MathUtils.DEG2RAD;
2686
2921
  }
2687
2922
  setRotationZ(rotationZ) {
2688
- this.getContainer().rotation.z = rotationZ * THREE18.MathUtils.DEG2RAD;
2923
+ this.getContainer().rotation.z = rotationZ * THREE19.MathUtils.DEG2RAD;
2689
2924
  }
2690
2925
  setScaleX(scaleX) {
2691
2926
  this.getContainer().scale.x = scaleX;
@@ -2714,12 +2949,12 @@ import {
2714
2949
  VideoGraphics,
2715
2950
  WHEPVideoSource
2716
2951
  } from "@mml-io/mml-web";
2717
- import * as THREE19 from "three";
2952
+ import * as THREE20 from "three";
2718
2953
  var audioRefDistance2 = 1;
2719
2954
  var audioRolloffFactor2 = 1;
2720
- var disabledVideoMaterial = new THREE19.MeshStandardMaterial({
2955
+ var disabledVideoMaterial = new THREE20.MeshStandardMaterial({
2721
2956
  color: 0,
2722
- side: THREE19.DoubleSide
2957
+ side: THREE20.DoubleSide
2723
2958
  });
2724
2959
  var ThreeJSVideo = class extends VideoGraphics {
2725
2960
  constructor(video, updateMeshCallback) {
@@ -2728,13 +2963,13 @@ var ThreeJSVideo = class extends VideoGraphics {
2728
2963
  this.updateMeshCallback = updateMeshCallback;
2729
2964
  this.videoSource = null;
2730
2965
  this.loadedVideoState = null;
2731
- const geometry = new THREE19.PlaneGeometry(1, 1, 1, 1);
2732
- this.videoMaterial = new THREE19.MeshStandardMaterial({
2966
+ const geometry = new THREE20.PlaneGeometry(1, 1, 1, 1);
2967
+ this.videoMaterial = new THREE20.MeshStandardMaterial({
2733
2968
  color: 16777215,
2734
2969
  transparent: false,
2735
- side: THREE19.DoubleSide
2970
+ side: THREE20.DoubleSide
2736
2971
  });
2737
- this.mesh = new THREE19.Mesh(geometry, disabledVideoMaterial);
2972
+ this.mesh = new THREE20.Mesh(geometry, disabledVideoMaterial);
2738
2973
  this.mesh.castShadow = true;
2739
2974
  this.mesh.receiveShadow = false;
2740
2975
  this.video.getContainer().add(this.mesh);
@@ -2830,7 +3065,7 @@ var ThreeJSVideo = class extends VideoGraphics {
2830
3065
  video.crossOrigin = "anonymous";
2831
3066
  const audioListener = this.getAudioListener();
2832
3067
  const audioContext = audioListener.context;
2833
- const audio = new THREE19.PositionalAudio(audioListener);
3068
+ const audio = new THREE20.PositionalAudio(audioListener);
2834
3069
  audio.setMediaElementSource(video);
2835
3070
  audio.setVolume(this.video.props.volume);
2836
3071
  audio.setRefDistance(audioRefDistance2);
@@ -2857,7 +3092,7 @@ var ThreeJSVideo = class extends VideoGraphics {
2857
3092
  if (!this.loadedVideoState || this.loadedVideoState.video !== video) {
2858
3093
  return;
2859
3094
  }
2860
- const videoTexture = new THREE19.VideoTexture(video);
3095
+ const videoTexture = new THREE20.VideoTexture(video);
2861
3096
  this.videoMaterial.map = videoTexture;
2862
3097
  this.videoMaterial.needsUpdate = true;
2863
3098
  this.mesh.material = this.videoMaterial;
@@ -2896,12 +3131,12 @@ var ThreeJSVideo = class extends VideoGraphics {
2896
3131
  updateMaterialEmissiveIntensity() {
2897
3132
  if (this.loadedVideoState && this.loadedVideoState.videoTexture) {
2898
3133
  if (this.video.props.emissive > 0) {
2899
- this.videoMaterial.emissive = new THREE19.Color(16777215);
3134
+ this.videoMaterial.emissive = new THREE20.Color(16777215);
2900
3135
  this.videoMaterial.emissiveMap = this.loadedVideoState.videoTexture;
2901
3136
  this.videoMaterial.emissiveIntensity = this.video.props.emissive;
2902
3137
  this.videoMaterial.needsUpdate = true;
2903
3138
  } else {
2904
- this.videoMaterial.emissive = new THREE19.Color(0);
3139
+ this.videoMaterial.emissive = new THREE20.Color(0);
2905
3140
  this.videoMaterial.emissiveMap = null;
2906
3141
  this.videoMaterial.emissiveIntensity = 1;
2907
3142
  this.videoMaterial.needsUpdate = true;
@@ -2968,7 +3203,7 @@ var ThreeJSImageHandleImpl = class {
2968
3203
  };
2969
3204
 
2970
3205
  // src/resources/ThreeJSImageResource.ts
2971
- import * as THREE20 from "three";
3206
+ import * as THREE21 from "three";
2972
3207
 
2973
3208
  // src/resources/ThreeJSImageLoader.ts
2974
3209
  var ThreeJSImageLoader = class {
@@ -3014,7 +3249,7 @@ var ThreeJSImageResource = class {
3014
3249
  (image) => {
3015
3250
  this.imageElement = image;
3016
3251
  this.hasTransparency = hasTransparency2(image);
3017
- this.texture = new THREE20.CanvasTexture(
3252
+ this.texture = new THREE21.CanvasTexture(
3018
3253
  image
3019
3254
  );
3020
3255
  const result = {
@@ -3126,7 +3361,7 @@ var ThreeJSLabelHandleImpl = class {
3126
3361
 
3127
3362
  // src/resources/ThreeJSLabelResource.ts
3128
3363
  import { CanvasText as CanvasText2 } from "@mml-io/mml-web";
3129
- import * as THREE21 from "three";
3364
+ import * as THREE22 from "three";
3130
3365
  var _ThreeJSLabelResource = class _ThreeJSLabelResource {
3131
3366
  constructor(options, onRemove, maxTextureSize = _ThreeJSLabelResource.DEFAULT_MAX_TEXTURE_SIZE) {
3132
3367
  this.onRemove = onRemove;
@@ -3160,22 +3395,22 @@ var _ThreeJSLabelResource = class _ThreeJSLabelResource {
3160
3395
  let texture;
3161
3396
  if (canvas.width === 0 || canvas.height === 0) {
3162
3397
  const emptyPixel = new Uint8Array([0, 0, 0, 0]);
3163
- texture = new THREE21.DataTexture(emptyPixel, 1, 1, THREE21.RGBAFormat);
3398
+ texture = new THREE22.DataTexture(emptyPixel, 1, 1, THREE22.RGBAFormat);
3164
3399
  } else {
3165
3400
  const ctx = canvas.getContext("2d", { willReadFrequently: true });
3166
3401
  const imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
3167
- texture = new THREE21.DataTexture(
3402
+ texture = new THREE22.DataTexture(
3168
3403
  imageData.data,
3169
3404
  canvas.width,
3170
3405
  canvas.height,
3171
- THREE21.RGBAFormat
3406
+ THREE22.RGBAFormat
3172
3407
  );
3173
3408
  }
3174
3409
  texture.flipY = true;
3175
- texture.colorSpace = THREE21.NoColorSpace;
3410
+ texture.colorSpace = THREE22.NoColorSpace;
3176
3411
  texture.premultiplyAlpha = true;
3177
- texture.magFilter = THREE21.LinearFilter;
3178
- texture.minFilter = THREE21.LinearMipmapLinearFilter;
3412
+ texture.magFilter = THREE22.LinearFilter;
3413
+ texture.minFilter = THREE22.LinearMipmapLinearFilter;
3179
3414
  texture.generateMipmaps = true;
3180
3415
  texture.needsUpdate = true;
3181
3416
  this.result = {
@@ -3480,7 +3715,7 @@ import {
3480
3715
  getRelativePositionAndRotationRelativeToObject,
3481
3716
  MElement as MElement3
3482
3717
  } from "@mml-io/mml-web";
3483
- import * as THREE22 from "three";
3718
+ import * as THREE23 from "three";
3484
3719
  var mouseMovePixelsThreshold = 10;
3485
3720
  var mouseMoveTimeThresholdMilliseconds = 500;
3486
3721
  var ThreeJSClickTrigger = class _ThreeJSClickTrigger {
@@ -3491,7 +3726,7 @@ var ThreeJSClickTrigger = class _ThreeJSClickTrigger {
3491
3726
  this.eventHandlerCollection = new EventHandlerCollection();
3492
3727
  this.mouseDownTime = null;
3493
3728
  this.mouseMoveDelta = 0;
3494
- this.raycaster = new THREE22.Raycaster();
3729
+ this.raycaster = new THREE23.Raycaster();
3495
3730
  this.eventHandlerCollection.add(clickTarget, "mousedown", this.handleMouseDown.bind(this));
3496
3731
  this.eventHandlerCollection.add(clickTarget, "mouseup", this.handleMouseUp.bind(this));
3497
3732
  this.eventHandlerCollection.add(clickTarget, "mousemove", this.handleMouseMove.bind(this));
@@ -3534,7 +3769,7 @@ var ThreeJSClickTrigger = class _ThreeJSClickTrigger {
3534
3769
  x = event.offsetX / width * 2 - 1;
3535
3770
  y = -(event.offsetY / height * 2 - 1);
3536
3771
  }
3537
- this.raycaster.setFromCamera(new THREE22.Vector2(x, y), this.camera);
3772
+ this.raycaster.setFromCamera(new THREE23.Vector2(x, y), this.camera);
3538
3773
  const intersections = this.raycaster.intersectObject(this.rootContainer, true);
3539
3774
  if (intersections.length > 0) {
3540
3775
  for (const intersection of intersections) {
@@ -3618,7 +3853,7 @@ var ThreeJSGraphicsInterface = {
3618
3853
  };
3619
3854
 
3620
3855
  // src/ThreeJSInteractionAdapter.ts
3621
- import * as THREE23 from "three";
3856
+ import * as THREE24 from "three";
3622
3857
  var _ThreeJSInteractionAdapter = class _ThreeJSInteractionAdapter {
3623
3858
  static interactionShouldShowDistance(interaction, camera, scene) {
3624
3859
  const worldPos = interaction.getContainer().getWorldPosition(_ThreeJSInteractionAdapter.worldPos);
@@ -3680,16 +3915,16 @@ var _ThreeJSInteractionAdapter = class _ThreeJSInteractionAdapter {
3680
3915
  return false;
3681
3916
  }
3682
3917
  };
3683
- _ThreeJSInteractionAdapter.worldPos = new THREE23.Vector3();
3684
- _ThreeJSInteractionAdapter.matrix = new THREE23.Matrix4();
3685
- _ThreeJSInteractionAdapter.frustum = new THREE23.Frustum();
3686
- _ThreeJSInteractionAdapter.raycaster = new THREE23.Raycaster();
3918
+ _ThreeJSInteractionAdapter.worldPos = new THREE24.Vector3();
3919
+ _ThreeJSInteractionAdapter.matrix = new THREE24.Matrix4();
3920
+ _ThreeJSInteractionAdapter.frustum = new THREE24.Frustum();
3921
+ _ThreeJSInteractionAdapter.raycaster = new THREE24.Raycaster();
3687
3922
  _ThreeJSInteractionAdapter.intersections = new Array();
3688
- _ThreeJSInteractionAdapter.direction = new THREE23.Vector3();
3923
+ _ThreeJSInteractionAdapter.direction = new THREE24.Vector3();
3689
3924
  var ThreeJSInteractionAdapter = _ThreeJSInteractionAdapter;
3690
3925
 
3691
3926
  // src/ThreeJSMemoryInspector.ts
3692
- import * as THREE24 from "three";
3927
+ import * as THREE25 from "three";
3693
3928
  var ThreeJSMemoryInspector = class _ThreeJSMemoryInspector {
3694
3929
  /**
3695
3930
  * Opens a new window with a comprehensive memory report including thumbnails
@@ -4180,7 +4415,7 @@ var ThreeJSMemoryInspector = class _ThreeJSMemoryInspector {
4180
4415
  });
4181
4416
  let sharedRenderer = null;
4182
4417
  try {
4183
- sharedRenderer = new THREE24.WebGLRenderer({ antialias: true, alpha: true });
4418
+ sharedRenderer = new THREE25.WebGLRenderer({ antialias: true, alpha: true });
4184
4419
  sharedRenderer.setSize(200, 200);
4185
4420
  sharedRenderer.setClearColor(2236962, 0);
4186
4421
  geometryMap.forEach((geometry, uuid) => {
@@ -4291,19 +4526,19 @@ var ThreeJSMemoryInspector = class _ThreeJSMemoryInspector {
4291
4526
  const scale = Math.min(maxSize / width, maxSize / height);
4292
4527
  const thumbWidth = Math.floor(width * scale);
4293
4528
  const thumbHeight = Math.floor(height * scale);
4294
- renderer = new THREE24.WebGLRenderer({ antialias: false, alpha: true });
4529
+ renderer = new THREE25.WebGLRenderer({ antialias: false, alpha: true });
4295
4530
  renderer.setSize(thumbWidth, thumbHeight);
4296
4531
  renderer.setClearColor(0, 0);
4297
- const scene = new THREE24.Scene();
4298
- const camera = new THREE24.OrthographicCamera(-0.5, 0.5, 0.5, -0.5, 0, 1);
4532
+ const scene = new THREE25.Scene();
4533
+ const camera = new THREE25.OrthographicCamera(-0.5, 0.5, 0.5, -0.5, 0, 1);
4299
4534
  camera.position.z = 0.5;
4300
- const geometry = new THREE24.PlaneGeometry(1, 1);
4301
- const material = new THREE24.MeshBasicMaterial({
4535
+ const geometry = new THREE25.PlaneGeometry(1, 1);
4536
+ const material = new THREE25.MeshBasicMaterial({
4302
4537
  map: texture,
4303
- side: THREE24.DoubleSide,
4538
+ side: THREE25.DoubleSide,
4304
4539
  transparent: true
4305
4540
  });
4306
- const plane = new THREE24.Mesh(geometry, material);
4541
+ const plane = new THREE25.Mesh(geometry, material);
4307
4542
  scene.add(plane);
4308
4543
  renderer.render(scene, camera);
4309
4544
  const canvas = renderer.domElement;
@@ -4322,27 +4557,27 @@ var ThreeJSMemoryInspector = class _ThreeJSMemoryInspector {
4322
4557
  }
4323
4558
  static createGeometryPreview(geometry, renderer) {
4324
4559
  try {
4325
- const tempScene = new THREE24.Scene();
4326
- const tempCamera = new THREE24.PerspectiveCamera(50, 1, 0.1, 1e3);
4560
+ const tempScene = new THREE25.Scene();
4561
+ const tempCamera = new THREE25.PerspectiveCamera(50, 1, 0.1, 1e3);
4327
4562
  renderer.setSize(200, 200);
4328
4563
  renderer.setClearColor(2236962, 0);
4329
- const material = new THREE24.MeshStandardMaterial({
4564
+ const material = new THREE25.MeshStandardMaterial({
4330
4565
  color: 15658734,
4331
4566
  roughness: 0.9,
4332
4567
  metalness: 0,
4333
- side: THREE24.DoubleSide,
4568
+ side: THREE25.DoubleSide,
4334
4569
  polygonOffset: true,
4335
4570
  polygonOffsetFactor: 1,
4336
4571
  polygonOffsetUnits: 1
4337
4572
  });
4338
- const mesh = new THREE24.Mesh(geometry, material);
4339
- const wireGeom = new THREE24.WireframeGeometry(geometry);
4340
- const wireMaterial = new THREE24.LineBasicMaterial({ color: 16777215 });
4341
- const wireframe = new THREE24.LineSegments(wireGeom, wireMaterial);
4573
+ const mesh = new THREE25.Mesh(geometry, material);
4574
+ const wireGeom = new THREE25.WireframeGeometry(geometry);
4575
+ const wireMaterial = new THREE25.LineBasicMaterial({ color: 16777215 });
4576
+ const wireframe = new THREE25.LineSegments(wireGeom, wireMaterial);
4342
4577
  wireframe.renderOrder = 1;
4343
4578
  geometry.computeBoundingSphere();
4344
4579
  let radius = 0;
4345
- let center = new THREE24.Vector3();
4580
+ let center = new THREE25.Vector3();
4346
4581
  if (geometry.boundingSphere) {
4347
4582
  radius = geometry.boundingSphere.radius;
4348
4583
  center.copy(geometry.boundingSphere.center);
@@ -4352,9 +4587,9 @@ var ThreeJSMemoryInspector = class _ThreeJSMemoryInspector {
4352
4587
  if (!box) {
4353
4588
  return null;
4354
4589
  }
4355
- center = new THREE24.Vector3();
4590
+ center = new THREE25.Vector3();
4356
4591
  box.getCenter(center);
4357
- const size = new THREE24.Vector3();
4592
+ const size = new THREE25.Vector3();
4358
4593
  box.getSize(size);
4359
4594
  radius = Math.max(size.x, size.y, size.z) * 0.5;
4360
4595
  }
@@ -4363,11 +4598,11 @@ var ThreeJSMemoryInspector = class _ThreeJSMemoryInspector {
4363
4598
  const fovRad = tempCamera.fov * Math.PI / 180;
4364
4599
  let distance = radius / Math.sin(fovRad / 2);
4365
4600
  distance *= 1.05;
4366
- const dir = new THREE24.Vector3(1, 1, 1).normalize();
4601
+ const dir = new THREE25.Vector3(1, 1, 1).normalize();
4367
4602
  tempCamera.position.copy(dir.multiplyScalar(distance));
4368
4603
  tempCamera.lookAt(0, 0, 0);
4369
- const ambientLight = new THREE24.AmbientLight(4210752, 0.6);
4370
- const directionalLight = new THREE24.DirectionalLight(16777215, 0.8);
4604
+ const ambientLight = new THREE25.AmbientLight(4210752, 0.6);
4605
+ const directionalLight = new THREE25.DirectionalLight(16777215, 0.8);
4371
4606
  directionalLight.position.set(1, 1, 1);
4372
4607
  tempScene.add(mesh);
4373
4608
  tempScene.add(wireframe);