diff --git a/packages/engine/src/avatar/components/AvatarAnimationComponent.ts b/packages/engine/src/avatar/components/AvatarAnimationComponent.ts index 6a77ddd35a..b51d43720c 100755 --- a/packages/engine/src/avatar/components/AvatarAnimationComponent.ts +++ b/packages/engine/src/avatar/components/AvatarAnimationComponent.ts @@ -174,11 +174,12 @@ export const AvatarRigComponent = defineComponent({ setObjectLayers(helper, ObjectLayers.AvatarHelper) Engine.instance.scene.add(helper) rigComponent.helper.set(helper) - } - if ((!visible?.value || !debugEnabled.value || pending?.value) && rigComponent.helper.value) { - rigComponent.helper.value.removeFromParent() - rigComponent.helper.set(none) + return () => { + helper.dispose() + helper.removeFromParent() + rigComponent.helper.set(none) + } } }, [visible, debugEnabled, pending]) diff --git a/packages/engine/src/scene/components/MountPointComponent.ts b/packages/engine/src/scene/components/MountPointComponent.ts index 0511d4161a..9bbf3d9df0 100755 --- a/packages/engine/src/scene/components/MountPointComponent.ts +++ b/packages/engine/src/scene/components/MountPointComponent.ts @@ -74,18 +74,18 @@ export const MountPointComponent = defineComponent({ const mountPoint = useComponent(entity, MountPointComponent) useEffect(() => { - if (debugEnabled.value && !mountPoint.helper.value) { - const helper = new ArrowHelper(new Vector3(0, 0, 1), new Vector3(0, 0, 0), 0.5, 0xffffff) - helper.name = `mount-point-helper-${entity}` + if (!debugEnabled.value || mountPoint.helper.value) return - setObjectLayers(helper, ObjectLayers.NodeHelper) - addObjectToGroup(entity, helper) + const helper = new ArrowHelper(new Vector3(0, 0, 1), new Vector3(0, 0, 0), 0.5, 0xffffff) + helper.name = `mount-point-helper-${entity}` - mountPoint.helper.set(helper) - } + setObjectLayers(helper, ObjectLayers.NodeHelper) + addObjectToGroup(entity, helper) + + mountPoint.helper.set(helper) - if (!debugEnabled.value && mountPoint.helper.value) { - removeObjectFromGroup(entity, mountPoint.helper.value) + return () => { + removeObjectFromGroup(entity, mountPoint.helper.value!) mountPoint.helper.set(none) } }, [debugEnabled]) diff --git a/packages/engine/src/scene/systems/SceneObjectSystem.tsx b/packages/engine/src/scene/systems/SceneObjectSystem.tsx index 7f5afd7f4f..caa527a266 100644 --- a/packages/engine/src/scene/systems/SceneObjectSystem.tsx +++ b/packages/engine/src/scene/systems/SceneObjectSystem.tsx @@ -71,6 +71,33 @@ export const disposeMaterial = (material: Material) => { material.dispose() } +export const disposeObject3D = (obj: Object3D) => { + const mesh = obj as Mesh + + if (mesh.material) { + if (Array.isArray(mesh.material)) { + mesh.material.forEach(disposeMaterial) + } else { + disposeMaterial(mesh.material) + } + } + + if (mesh.geometry) { + mesh.geometry.dispose() + for (const key in mesh.geometry.attributes) { + mesh.geometry.deleteAttribute(key) + } + } + + const skinnedMesh = obj as SkinnedMesh + if (skinnedMesh.isSkinnedMesh) { + skinnedMesh.skeleton?.dispose() + } + + const light = obj as Light // anything with dispose function + if (typeof light.dispose === 'function') light.dispose() +} + export function setupObject(obj: Object3DWithEntity, forceBasicMaterials = false) { const mesh = obj as any as Mesh /** @todo do we still need this? */ @@ -130,23 +157,7 @@ function SceneObjectReactor(props: { entity: Entity; obj: Object3DWithEntity }) if (layer.has(obj)) layer.delete(obj) } - obj.traverse((object3D: Object3D) => { - const mesh = object3D as Mesh - if (Array.isArray(mesh.material)) { - mesh.material.forEach(disposeMaterial) - } else if (mesh.material) { - disposeMaterial(mesh.material) - } - mesh.geometry?.dispose() - - const skinnedMesh = object3D as SkinnedMesh - if (skinnedMesh.isSkinnedMesh) { - skinnedMesh.skeleton?.dispose() - } - - const light = object3D as Light // anything with dispose function - if (typeof light.dispose === 'function') light.dispose() - }) + obj.traverse(disposeObject3D) } }, [])