refactor: clean map gameplay architecture

This commit is contained in:
tom-boullay
2026-05-28 11:15:45 +02:00
parent d9cf87d2d6
commit 1a91b1d7ae
69 changed files with 791 additions and 1112 deletions
+2 -11
View File
@@ -1,15 +1,6 @@
import { useEffect, useMemo } from "react";
import { useMemo } from "react";
import * as THREE from "three";
import { disposeObject3D } from "@/utils/three/dispose";
export function useClonedObject<T extends THREE.Object3D>(object: T): T {
const clone = useMemo(() => object.clone(true) as T, [object]);
useEffect(() => {
return () => {
disposeObject3D(clone);
};
}, [clone]);
return clone;
return useMemo(() => object.clone(true) as T, [object]);
}
+35 -4
View File
@@ -16,6 +16,24 @@ interface TerrainHeightSampler {
getHeight: (x: number, z: number) => number | null;
}
interface CachedTerrainHeightSampler {
key: string;
sampler: TerrainHeightSampler;
}
const terrainSamplerCache = new WeakMap<
THREE.Object3D,
CachedTerrainHeightSampler
>();
function createTerrainSamplerCacheKey(
position: Vector3Tuple,
rotation: Vector3Tuple,
scale: Vector3Tuple,
): string {
return `${position.join(",")}|${rotation.join(",")}|${scale.join(",")}`;
}
function createTerrainHeightSampler(
scene: THREE.Object3D,
position: Vector3Tuple,
@@ -64,10 +82,23 @@ export function useTerrainHeightSampler(): TerrainHeightSampler {
const rotation = terrainNode?.rotation ?? DEFAULT_TERRAIN_ROTATION;
const scale = terrainNode?.scale ?? DEFAULT_TERRAIN_SCALE;
return useMemo(
() => createTerrainHeightSampler(scene, position, rotation, scale),
[position, rotation, scale, scene],
);
return useMemo(() => {
const key = createTerrainSamplerCacheKey(position, rotation, scale);
const cached = terrainSamplerCache.get(scene);
if (cached?.key === key) {
return cached.sampler;
}
const sampler = createTerrainHeightSampler(
scene,
position,
rotation,
scale,
);
terrainSamplerCache.set(scene, { key, sampler });
return sampler;
}, [position, rotation, scale, scene]);
}
export function useTerrainSnappedPosition(