From a32ee2a3449fbdd03b64159ff9fa8055fa1ca738 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Tr=C3=A8sAbhi?= <43380238+tresabhi@users.noreply.github.com>
Date: Mon, 22 Jan 2024 15:42:49 -0600
Subject: [PATCH] feat: non-pbr tank lighting and model cache
---
.../tankopedia/[id]/components/Lighting.tsx | 15 ++++++++---
.../[id]/components/Model/TankSandbox.tsx | 2 +-
.../components/ExternalModuleMask.tsx | 2 +-
.../TankArmor/components/SpacedArmorDepth.tsx | 2 +-
.../components/Model/components/TankModel.tsx | 2 +-
src/hooks/useArmor.ts | 10 ++++---
src/hooks/useModel.ts | 27 ++++++++++++++++---
7 files changed, 47 insertions(+), 13 deletions(-)
diff --git a/src/app/tools/tankopedia/[id]/components/Lighting.tsx b/src/app/tools/tankopedia/[id]/components/Lighting.tsx
index a78d6708e..27a0d7d4b 100644
--- a/src/app/tools/tankopedia/[id]/components/Lighting.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Lighting.tsx
@@ -1,15 +1,24 @@
-export function Lighting() {
+import { useModel } from '../../../../../hooks/useModel';
+import { Duel } from '../page';
+
+interface LightingProps {
+ duel: Duel;
+}
+
+export function Lighting({ duel }: LightingProps) {
+ const { hasPbr } = useModel(duel.protagonist.tank.id);
+
return (
<>
diff --git a/src/app/tools/tankopedia/[id]/components/Model/TankSandbox.tsx b/src/app/tools/tankopedia/[id]/components/Model/TankSandbox.tsx
index a246bfbee..6f8b5fd7c 100644
--- a/src/app/tools/tankopedia/[id]/components/Model/TankSandbox.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Model/TankSandbox.tsx
@@ -162,7 +162,7 @@ export function TankSandbox({ duel }: TankSandboxProps) {
>
-
+
(({ duel }) => {
});
const armorGltf = useArmor(duel.protagonist.tank.id);
- const modelGltf = useModel(duel.protagonist.tank.id);
+ const { gltf: modelGltf } = useModel(duel.protagonist.tank.id);
const armorNodes = Object.values(armorGltf.nodes);
const modelNodes = Object.values(modelGltf.nodes);
diff --git a/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor/components/SpacedArmorDepth.tsx b/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor/components/SpacedArmorDepth.tsx
index aec7a74b2..9f7d2903a 100644
--- a/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor/components/SpacedArmorDepth.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor/components/SpacedArmorDepth.tsx
@@ -120,7 +120,7 @@ export const SpacedArmorDepth = memo(({ duel }) => {
});
const armorGltf = useArmor(duel.protagonist.tank.id);
- const modelGltf = useModel(duel.protagonist.tank.id);
+ const { gltf: modelGltf } = useModel(duel.protagonist.tank.id);
const armorNodes = Object.values(armorGltf.nodes);
const modelNodes = Object.values(modelGltf.nodes);
diff --git a/src/app/tools/tankopedia/[id]/components/Model/components/TankModel.tsx b/src/app/tools/tankopedia/[id]/components/Model/components/TankModel.tsx
index 01ffcd21d..2ec51a609 100644
--- a/src/app/tools/tankopedia/[id]/components/Model/components/TankModel.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Model/components/TankModel.tsx
@@ -122,7 +122,7 @@ export const TankModel = memo(({ duel: { protagonist } }: TankModelProps) => {
tankModelDefinition.turrets[protagonist.turret.id];
const gunModelDefinition = turretModelDefinition.guns[protagonist.gun.id];
- const gltf = useModel(protagonist.tank.id);
+ const { gltf } = useModel(protagonist.tank.id);
const nodes = Object.values(gltf.nodes);
return (
diff --git a/src/hooks/useArmor.ts b/src/hooks/useArmor.ts
index ee4152582..420e6089e 100644
--- a/src/hooks/useArmor.ts
+++ b/src/hooks/useArmor.ts
@@ -1,7 +1,11 @@
-import { useLoader } from '@react-three/fiber';
-import { GLTFLoader } from 'three-stdlib';
+import { ObjectMap, useLoader } from '@react-three/fiber';
+import { GLTF, GLTFLoader } from 'three-stdlib';
import { asset } from '../core/blitzkrieg/asset';
+const cache: Record = {};
+
export function useArmor(id: number) {
- return useLoader(GLTFLoader, asset(`3d/tanks/armor/${id}.glb`));
+ const gltf = useLoader(GLTFLoader, asset(`3d/tanks/armor/${id}.glb`));
+ if (!cache[id]) cache[id] = gltf;
+ return cache[id];
}
diff --git a/src/hooks/useModel.ts b/src/hooks/useModel.ts
index 11b856fef..df2433686 100644
--- a/src/hooks/useModel.ts
+++ b/src/hooks/useModel.ts
@@ -1,7 +1,28 @@
-import { useLoader } from '@react-three/fiber';
-import { GLTFLoader } from 'three-stdlib';
+import { ObjectMap, useLoader } from '@react-three/fiber';
+import { Mesh, MeshStandardMaterial } from 'three';
+import { GLTF, GLTFLoader } from 'three-stdlib';
import { asset } from '../core/blitzkrieg/asset';
+const cache: Record<
+ number,
+ {
+ gltf: GLTF & ObjectMap;
+ hasPbr: boolean;
+ }
+> = {};
+
export function useModel(id: number) {
- return useLoader(GLTFLoader, asset(`3d/tanks/models/${id}.glb`));
+ const gltf = useLoader(GLTFLoader, asset(`3d/tanks/models/${id}.glb`));
+ if (!cache[id]) {
+ cache[id] = {
+ gltf,
+ hasPbr: Object.values(gltf.nodes).some(
+ (node) =>
+ node instanceof Mesh &&
+ node.material instanceof MeshStandardMaterial &&
+ node.material.roughnessMap !== null,
+ ),
+ };
+ }
+ return cache[id];
}