From 8e6d2b9873642ca3f37c6c57e48e426bd852f4bd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tr=C3=A8sAbhi?= <43380238+tresabhi@users.noreply.github.com> Date: Wed, 10 Jan 2024 14:25:48 -0600 Subject: [PATCH] feat: some armor rules --- package.json | 1 + .../components/Model/components/TankArmor.tsx | 22 +++- .../tankopedia/[id]/components/VersusBar.tsx | 5 + src/app/tools/tankopedia/[id]/page.tsx | 5 +- src/components/ArmorMesh.tsx | 119 +++++++++++++++++- src/stores/tankopedia.ts | 2 + yarn.lock | 64 +++++++++- 7 files changed, 205 insertions(+), 13 deletions(-) diff --git a/package.json b/package.json index 38cc2b880..f1f9a8751 100644 --- a/package.json +++ b/package.json @@ -63,6 +63,7 @@ "satori": "^0.10.8", "sharp": "^0.33.1", "three": "^0.159.0", + "three-custom-shader-material": "^5.4.0", "three-stdlib": "^2.28.11", "vite-node": "^0.34.5", "vitepress": "^1.0.0-rc.20", diff --git a/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor.tsx b/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor.tsx index 7ea7b21b9..f1d5cae89 100644 --- a/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor.tsx +++ b/src/app/tools/tankopedia/[id]/components/Model/components/TankArmor.tsx @@ -22,8 +22,12 @@ export function TankArmor() { if (!state.areTanksAssigned) return; return state.protagonist; }); + const antagonist = useTankopedia((state) => { + if (!state.areTanksAssigned) return; + return state.antagonist; + }); - if (!protagonist) return null; + if (!protagonist || !antagonist) return null; const gltf = useLoader( GLTFLoader, @@ -80,15 +84,25 @@ export function TankArmor() { {nodes.map((node) => { const isHull = node.name.startsWith('hull_'); + const armorId = parseInt(node.name.match(/.+_armor_(\d+)/)![1]); const isVisible = isHull; + const thickness = tankModelDefinition.armor.thickness[armorId] ?? 0; if (!isVisible) return null; return ( - + ); })} - + {/* {nodes.map((node) => { const isCurrentTurret = node.name.startsWith( `turret_${turretModelDefinition.model @@ -133,7 +147,7 @@ export function TankArmor() { ); })} - + */} ); diff --git a/src/app/tools/tankopedia/[id]/components/VersusBar.tsx b/src/app/tools/tankopedia/[id]/components/VersusBar.tsx index 8b6067b2c..398a9da67 100644 --- a/src/app/tools/tankopedia/[id]/components/VersusBar.tsx +++ b/src/app/tools/tankopedia/[id]/components/VersusBar.tsx @@ -132,6 +132,8 @@ export function VersusBar() { tank.turrets.at(-1)!; draft.antagonist.gun = draft.antagonist.turret.guns.at(-1)!; + draft.antagonist.shell = + draft.antagonist.gun.shells[0]; }); setVersusTankSearchResults([]); versusTankSearchInput.current!.value = ''; @@ -176,6 +178,8 @@ export function VersusBar() { draft.antagonist.turret = turret; draft.antagonist.gun = turret.guns.at(-1)!; + draft.antagonist.shell = + draft.antagonist.gun.shells[0]; }); }} selected={antagonist.turret.id === turret.id} @@ -210,6 +214,7 @@ export function VersusBar() { mutateTankopedia((draft) => { if (!draft.areTanksAssigned) return; draft.antagonist.gun = gun; + draft.antagonist.shell = gun.shells[0]; }); }} selected={antagonist.gun.id === gun.id} diff --git a/src/app/tools/tankopedia/[id]/page.tsx b/src/app/tools/tankopedia/[id]/page.tsx index d7ba0668d..c9b3b309d 100644 --- a/src/app/tools/tankopedia/[id]/page.tsx +++ b/src/app/tools/tankopedia/[id]/page.tsx @@ -33,7 +33,10 @@ export default function Page({ params }: { params: { id: string } }) { draft.protagonist.tank = awaitedTankDefinitions[id]; draft.protagonist.turret = draft.protagonist.tank.turrets.at(-1)!; draft.protagonist.gun = draft.protagonist.turret.guns.at(-1)!; - draft.antagonist = draft.protagonist; + draft.antagonist = { + ...draft.protagonist, + shell: draft.protagonist.gun.shells[0], + }; }); return () => { diff --git a/src/components/ArmorMesh.tsx b/src/components/ArmorMesh.tsx index d081d5dbc..e6190284a 100644 --- a/src/components/ArmorMesh.tsx +++ b/src/components/ArmorMesh.tsx @@ -1,8 +1,39 @@ +// // Vertex shader +// varying vec3 vNormal; // declare a varying variable to pass the normal vector +// void main() { +// vNormal = normal; // assign the normal vector to the varying variable +// gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0); // transform the vertex position +// } + +// // Fragment shader +// varying vec3 vNormal; // declare the same varying variable to receive the normal vector +// void main() { +// vec3 cameraDir = -viewPosition; // get the camera direction vector by negating the view position +// float angle = acos(dot(vNormal, cameraDir)); // calculate the angle of the fragment using the dot product and the acos function +// vec3 color = mix(vec3(1.0, 0.0, 0.0), vec3(0.0, 0.0, 1.0), angle / PI); // create a gradient color from red to blue based on the angle +// gl_FragColor = vec4(color, 1.0); // set the fragment color +// } + import { MeshProps } from '@react-three/fiber'; +import { MeshBasicMaterial } from 'three'; +import CustomShaderMaterial from 'three-custom-shader-material'; -interface ArmorMeshProps extends MeshProps {} +interface ArmorMeshProps extends MeshProps { + thickness: number; + penetration: number; + ricochet: number; + caliber: number; + normalization: number; +} -export function ArmorMesh(props: ArmorMeshProps) { +export function ArmorMesh({ + thickness, + penetration, + caliber, + ricochet, + normalization, + ...props +}: ArmorMeshProps) { return ( <> @@ -10,13 +41,89 @@ export function ArmorMesh(props: ArmorMeshProps) { - 2.0 * thickness; + bool threeCaliberRule = caliber > 3.0 * thickness; + float finalNormalization = normalization; + + if (twoCaliberRule) { + finalNormalization = (normalization * 1.4 * caliber) / (2.0 * thickness); + } + + if ( + angle >= ricochet + && !threeCaliberRule + ) { + penetrationChance = 1.0; + } + + csm_FragColor *= vec4(1.0, 0.0, 0.0, penetrationChance * 0.5); + } + `} + /> + + {/* + /> */} + {/* */} ); diff --git a/src/stores/tankopedia.ts b/src/stores/tankopedia.ts index acf1a73b1..20c85898f 100644 --- a/src/stores/tankopedia.ts +++ b/src/stores/tankopedia.ts @@ -3,6 +3,7 @@ import { create } from 'zustand'; import { TankType, TreeTypeString } from '../components/Tanks'; import { GunDefinition, + ShellDefinition, TankDefinition, Tier, TurretDefinition, @@ -45,6 +46,7 @@ type Tankopedia = { tank: TankDefinition; turret: TurretDefinition; gun: GunDefinition; + shell: ShellDefinition; }; } | { areTanksAssigned: false } diff --git a/yarn.lock b/yarn.lock index 9a12dcdec..4f6ad2ea5 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3967,6 +3967,23 @@ glsl-noise@^0.0.0: resolved "https://registry.yarnpkg.com/glsl-noise/-/glsl-noise-0.0.0.tgz#367745f3a33382c0eeec4cb54b7e99cfc1d7670b" integrity sha512-b/ZCF6amfAUb7dJM/MxRs7AetQEahYzJ8PtgfrmEdtw6uyGOr+ZSGtgjFm6mfsBkxJ4d2W7kg+Nlqzqvn3Bc0w== +glsl-token-functions@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/glsl-token-functions/-/glsl-token-functions-1.0.1.tgz#2f1614746b96e14f059a6d62af79b65457f0c9a0" + integrity sha512-EigGhp1g+aUVeUNY7H1o5tL/bnwIB3/FcRREPr2E7Du+/UDXN24hDkaZ3e4aWHDjHr9lJ6YHXMISkwhUYg9UOg== + +glsl-token-string@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/glsl-token-string/-/glsl-token-string-1.0.1.tgz#59441d2f857de7c3449c945666021ece358e48ec" + integrity sha512-1mtQ47Uxd47wrovl+T6RshKGkRRCYWhnELmkEcUAPALWGTFe2XZpH3r45XAwL2B6v+l0KNsCnoaZCSnhzKEksg== + +glsl-tokenizer@^2.1.5: + version "2.1.5" + resolved "https://registry.yarnpkg.com/glsl-tokenizer/-/glsl-tokenizer-2.1.5.tgz#1c2e78c16589933c274ba278d0a63b370c5fee1a" + integrity sha512-XSZEJ/i4dmz3Pmbnpsy3cKh7cotvFlBiZnDOwnj/05EwNp2XrhQ4XKJxT7/pDt4kp4YcpRSKz8eTV7S+mwV6MA== + dependencies: + through2 "^0.6.3" + gopd@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/gopd/-/gopd-1.0.1.tgz#29ff76de69dac7489b7c0918a5788e56477c332c" @@ -4187,7 +4204,7 @@ inflight@^1.0.4: once "^1.3.0" wrappy "1" -inherits@2, inherits@2.0.4, inherits@^2.0.3, inherits@~2.0.3: +inherits@2, inherits@2.0.4, inherits@^2.0.3, inherits@~2.0.1, inherits@~2.0.3: version "2.0.4" resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== @@ -4263,6 +4280,11 @@ is-stream@^1.1.0: resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-1.1.0.tgz#12d4a3dd4e68e0b79ceb8dbc84173ae80d91ca44" integrity sha512-uQPm8kcs47jx38atAcWTVxyltQYoPT68y9aWYdV6yWXSyW8mzSat0TL6CiWdZeCdF3KrAvpVtnHbTv4RN+rqdQ== +isarray@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-0.0.1.tgz#8a18acfca9a8f4177e09abfc6038939b05d1eedf" + integrity sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ== + isarray@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11" @@ -4870,6 +4892,11 @@ object-assign@^4, object-assign@^4.0.1, object-assign@^4.1.1: resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" integrity sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg== +object-hash@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/object-hash/-/object-hash-3.0.0.tgz#73f97f753e7baffc0e2cc9d6e079079744ac82e9" + integrity sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw== + object-inspect@^1.9.0: version "1.13.1" resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.13.1.tgz#b96c6109324ccfef6b12216a956ca4dc2ff94bc2" @@ -5325,6 +5352,16 @@ readable-stream@3, readable-stream@^3.0.0, readable-stream@^3.6.0: string_decoder "^1.1.1" util-deprecate "^1.0.1" +"readable-stream@>=1.0.33-1 <1.1.0-0": + version "1.0.34" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.0.34.tgz#125820e34bc842d2f2aaafafe4c2916ee32c157c" + integrity sha512-ok1qVCJuRkNmvebYikljxJA/UEsKwLl2nI1OmaqAu4/UE+h0wKCHok4XkL/gvi39OacXvw59RJUOFUkDib2rHg== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.1" + isarray "0.0.1" + string_decoder "~0.10.x" + readable-stream@^2.3.0, readable-stream@^2.3.5: version "2.3.8" resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.8.tgz#91125e8042bba1b9887f49345f6277027ce8be9b" @@ -5730,6 +5767,11 @@ string_decoder@^1.1.1: dependencies: safe-buffer "~5.2.0" +string_decoder@~0.10.x: + version "0.10.31" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-0.10.31.tgz#62e203bc41766c6c28c9fc84301dab1c5310fa94" + integrity sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ== + string_decoder@~1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8" @@ -5831,6 +5873,16 @@ tar-stream@^1.5.2: to-buffer "^1.1.1" xtend "^4.0.0" +three-custom-shader-material@^5.4.0: + version "5.4.0" + resolved "https://registry.yarnpkg.com/three-custom-shader-material/-/three-custom-shader-material-5.4.0.tgz#ee571c335a028a9b75c703b2ba83199176000847" + integrity sha512-Yn1lFlKOk3Vul3npEGAmbbFUZ5S2+yjPgM2XqJEZEYRSUUH2vk+WVYrtTB6Bcq15wa7hLUXAKoctAvbRmBmbYA== + dependencies: + glsl-token-functions "^1.0.1" + glsl-token-string "^1.0.1" + glsl-tokenizer "^2.1.5" + object-hash "^3.0.0" + three-mesh-bvh@^0.6.7: version "0.6.8" resolved "https://registry.yarnpkg.com/three-mesh-bvh/-/three-mesh-bvh-0.6.8.tgz#f27d18ca75bdc59316dff0f561af8fb316621a54" @@ -5865,6 +5917,14 @@ three@^0.159.0: resolved "https://registry.yarnpkg.com/three/-/three-0.159.0.tgz#6576b1210805b14f0765bac41fd0e4ec18e43b2e" integrity sha512-eCmhlLGbBgucuo4VEA9IO3Qpc7dh8Bd4VKzr7WfW4+8hMcIfoAVi1ev0pJYN9PTTsCslbcKgBwr2wNZ1EvLInA== +through2@^0.6.3: + version "0.6.5" + resolved "https://registry.yarnpkg.com/through2/-/through2-0.6.5.tgz#41ab9c67b29d57209071410e1d7a7a968cd3ad48" + integrity sha512-RkK/CCESdTKQZHdmKICijdKKsCRVHs5KsLZ6pACAmF/1GPUQhonHSXWNERctxEp7RmvjdNbZTL5z9V7nSCXKcg== + dependencies: + readable-stream ">=1.0.33-1 <1.1.0-0" + xtend ">=4.0.0 <4.1.0-0" + through2@^4.0.0: version "4.0.2" resolved "https://registry.yarnpkg.com/through2/-/through2-4.0.2.tgz#a7ce3ac2a7a8b0b966c80e7c49f0484c3b239764" @@ -6360,7 +6420,7 @@ ws@^8.14.2: resolved "https://registry.yarnpkg.com/ws/-/ws-8.15.1.tgz#271ba33a45ca0cc477940f7f200cd7fba7ee1997" integrity sha512-W5OZiCjXEmk0yZ66ZN82beM5Sz7l7coYxpRkzS+p9PP+ToQry8szKh+61eNktr7EA9DOwvFGhfC605jDHbP6QQ== -xtend@^4.0.0: +"xtend@>=4.0.0 <4.1.0-0", xtend@^4.0.0: version "4.0.2" resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.2.tgz#bb72779f5fa465186b1f438f674fa347fdb5db54" integrity sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==