From 91ac93670f681f037aa99eb6c9c74b82ecf356d7 Mon Sep 17 00:00:00 2001 From: tresabhi <43380238+tresabhi@users.noreply.github.com> Date: Fri, 12 Jun 2026 20:22:02 -0500 Subject: [PATCH] more control over model parts --- cspell.json | 4 ++- .../components/TankopediaSandbox/index.tsx | 7 ++--- .../src/hooks/useTankChassisModel.ts | 26 +++++++------------ .../website-ue/src/hooks/useTankGunModel.ts | 21 +++++++++++++++ .../website-ue/src/hooks/useTankHullModel.ts | 8 +++++- packages/website-ue/src/hooks/useTankModel.ts | 18 ++++++++----- .../src/hooks/useTankTurretModel.ts | 20 ++++++++++++++ 7 files changed, 76 insertions(+), 28 deletions(-) create mode 100644 packages/website-ue/src/hooks/useTankGunModel.ts create mode 100644 packages/website-ue/src/hooks/useTankTurretModel.ts diff --git a/cspell.json b/cspell.json index 29f356f50..b922dff13 100644 --- a/cspell.json +++ b/cspell.json @@ -12,7 +12,9 @@ "Lods", "Skia", "RMAO", - "Verts" + "Verts", + "drei", + "frameloop" ], "userWords": [ "WOTB", diff --git a/packages/website-ue/src/components/TankopediaSandbox/index.tsx b/packages/website-ue/src/components/TankopediaSandbox/index.tsx index 1384cbbce..4a346b7d4 100644 --- a/packages/website-ue/src/components/TankopediaSandbox/index.tsx +++ b/packages/website-ue/src/components/TankopediaSandbox/index.tsx @@ -6,8 +6,9 @@ import { OrbitControls } from "@react-three/drei"; import { Canvas } from "@react-three/fiber"; import { useProtagonist } from "../../hooks/useProtagonist"; import { useTankChassisModel } from "../../hooks/useTankChassisModel"; +import { useTankGunModel } from "../../hooks/useTankGunModel"; import { useTankHullModel } from "../../hooks/useTankHullModel"; -import { useTankModel } from "../../hooks/useTankModel"; +import { useTankTurretModel } from "../../hooks/useTankTurretModel"; import styles from "./index.module.css"; interface TankopediaSandboxProps { @@ -45,8 +46,8 @@ function Content({ parameters }: TankopediaSandboxProps) { const hull = useTankHullModel(); const chassis = useTankChassisModel(); - const turret = useTankModel(`/models/tanks/${tank.id}/${selectedTurret}.glb`); - const gun = useTankModel(`/models/tanks/${tank.id}/${selectedGun}.glb`); + const turret = useTankTurretModel(parameters); + const gun = useTankGunModel(parameters); return ( <> diff --git a/packages/website-ue/src/hooks/useTankChassisModel.ts b/packages/website-ue/src/hooks/useTankChassisModel.ts index 62f66c08a..d11a1c683 100644 --- a/packages/website-ue/src/hooks/useTankChassisModel.ts +++ b/packages/website-ue/src/hooks/useTankChassisModel.ts @@ -1,25 +1,17 @@ -import { Tankopedia } from "../stores/tankopedia"; import { useProtagonist } from "./useProtagonist"; import { useTankModel } from "./useTankModel"; export function useTankChassisModel() { const tank = useProtagonist(); - const scene = useTankModel(`/models/tanks/${tank.id}/chassis.glb`); - const isChassisDamaged = Tankopedia.use( - (state) => state.protagonist.status.chassis_damaged, - ); - // for (const child of scene.children) { - // if (child.name.endsWith("TrackCrashed")) { - // child.visible = isChassisDamaged; - // } + const map = { + Wheels: true, + LeftTracks: true, + RightTracks: true, + LeftTrackCrashed: false, + RightTrackCrashed: false, + CollisionMesh: false, + }; - // if (child.name.startsWith("Track")) { - // child.visible = !isChassisDamaged; - // } - // } - - console.log(scene); - - return scene; + return useTankModel(`/models/tanks/${tank.id}/chassis.glb`, map); } diff --git a/packages/website-ue/src/hooks/useTankGunModel.ts b/packages/website-ue/src/hooks/useTankGunModel.ts new file mode 100644 index 000000000..4d5a928e6 --- /dev/null +++ b/packages/website-ue/src/hooks/useTankGunModel.ts @@ -0,0 +1,21 @@ +import { + VisualChanges_TankPart, + type StageParameters, +} from "@protos/blitz_static_tank_upgrade_single_stage"; +import { useProtagonist } from "./useProtagonist"; +import { useTankModel } from "./useTankModel"; + +export function useTankGunModel(parameters: StageParameters) { + const tank = useProtagonist(); + const selected = parameters.visual_changes.find( + ({ tank_part }) => tank_part === VisualChanges_TankPart.TANK_PART_GUN, + ); + + const map = { + GunMesh: true, + MaskMesh: true, + CollisionMesh: false, + }; + + return useTankModel(`/models/tanks/${tank.id}/${selected!.name}.glb`, map); +} diff --git a/packages/website-ue/src/hooks/useTankHullModel.ts b/packages/website-ue/src/hooks/useTankHullModel.ts index 474b9893f..63fb4dbd5 100644 --- a/packages/website-ue/src/hooks/useTankHullModel.ts +++ b/packages/website-ue/src/hooks/useTankHullModel.ts @@ -3,5 +3,11 @@ import { useTankModel } from "./useTankModel"; export function useTankHullModel() { const tank = useProtagonist(); - return useTankModel(`/models/tanks/${tank.id}/hull.glb`); + + const map = { + Mesh: true, + CollisionMesh: false, + }; + + return useTankModel(`/models/tanks/${tank.id}/hull.glb`, map); } diff --git a/packages/website-ue/src/hooks/useTankModel.ts b/packages/website-ue/src/hooks/useTankModel.ts index 3f9ac701a..6a857e508 100644 --- a/packages/website-ue/src/hooks/useTankModel.ts +++ b/packages/website-ue/src/hooks/useTankModel.ts @@ -2,11 +2,11 @@ import { useLoader } from "@react-three/fiber"; import { Mesh, MeshStandardMaterial } from "three"; import { GLTFLoader } from "three-stdlib"; -export function useTankModel(url: string) { - const collision = false; +export function useTankModel(url: string, map: Record) { const gltf = useLoader(GLTFLoader, url); + const [root] = gltf.scene.children; - gltf.scene.traverse((child) => { + root.traverse((child) => { if ( child instanceof Mesh && child.material instanceof MeshStandardMaterial @@ -19,9 +19,15 @@ export function useTankModel(url: string) { child.receiveShadow = true; }); - for (const child of gltf.scene.children) { - child.visible = (child.name === "CollisionMesh") === collision; + for (const child of root.children) { + if (child.name in map) { + child.visible = map[child.name]; + continue; + } + + child.visible = false; + console.warn(`Root child ${child.name} isn't recognized`); } - return gltf.scene; + return root; } diff --git a/packages/website-ue/src/hooks/useTankTurretModel.ts b/packages/website-ue/src/hooks/useTankTurretModel.ts new file mode 100644 index 000000000..5bf347b60 --- /dev/null +++ b/packages/website-ue/src/hooks/useTankTurretModel.ts @@ -0,0 +1,20 @@ +import { + VisualChanges_TankPart, + type StageParameters, +} from "@protos/blitz_static_tank_upgrade_single_stage"; +import { useProtagonist } from "./useProtagonist"; +import { useTankModel } from "./useTankModel"; + +export function useTankTurretModel(parameters: StageParameters) { + const tank = useProtagonist(); + const selected = parameters.visual_changes.find( + ({ tank_part }) => tank_part === VisualChanges_TankPart.TANK_PART_TURRET, + ); + + const map = { + Mesh: true, + CollisionMesh: false, + }; + + return useTankModel(`/models/tanks/${tank.id}/${selected!.name}.glb`, map); +}