mirror of
https://github.com/blitzkit/blitzkit.git
synced 2026-10-21 10:47:04 +02:00
Compare commits
38
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
12ff9a90eb | ||
|
|
5ad5c701c9 | ||
|
|
7234c39ad8 | ||
|
|
c292adac41 | ||
|
|
1af104d4d6 | ||
|
|
7b7513f227 | ||
|
|
02f5cc0686 | ||
|
|
6f1d653d54 | ||
|
|
92c8b90bb3 | ||
|
|
1b807e6d0e | ||
|
|
0e7b020d60 | ||
|
|
eda5d10290 | ||
|
|
85e93cd827 | ||
|
|
bc2dd8c7b7 | ||
|
|
904d50f4c3 | ||
|
|
112472762d | ||
|
|
f6e5fabb65 | ||
|
|
e19d0d5895 | ||
|
|
aa6268a86b | ||
|
|
0f878485b3 | ||
|
|
0e119b6ba8 | ||
|
|
3397e7f67b | ||
|
|
de03a2ab95 | ||
|
|
d4e649804e | ||
|
|
c31d5705eb | ||
|
|
16be5faae6 | ||
|
|
e1b079ca02 | ||
|
|
00149a3d9d | ||
|
|
e3e94e2b49 | ||
|
|
5ce927be4e | ||
|
|
541da65bfc | ||
|
|
e4e92d76b4 | ||
|
|
273881c460 | ||
|
|
3aefe7d985 | ||
|
|
bfe31053a9 | ||
|
|
a5eac5572e | ||
|
|
c2c586c2e7 | ||
|
|
aaf0e52be4 |
No files matched your search
@@ -93,7 +93,7 @@ jobs:
|
|||||||
strategy:
|
strategy:
|
||||||
fail-fast: true
|
fail-fast: true
|
||||||
matrix:
|
matrix:
|
||||||
chunk: [default, api]
|
chunk: [default, api, models_tanks, models_legendary, models_maps]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- name: Free disk space
|
- name: Free disk space
|
||||||
|
|||||||
@@ -5,10 +5,10 @@ Thank you to [Mark Greene](https://github.com/Hitjack007) for your contributions
|
|||||||
## Features
|
## Features
|
||||||
|
|
||||||
- Combined game mode passive and active abilities into a single dropdown
|
- Combined game mode passive and active abilities into a single dropdown
|
||||||
- [Mark Greene] Added tier filters to the Guess game
|
- Added tier filters to the Guess game [Mark Greene]
|
||||||
- Changing tiers will break your streak
|
- Changing tiers will break your streak
|
||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [Mark Greene] module damage is now properly shown when sorting with it in the tank search
|
- module damage is now properly shown when sorting with it in the tank search [Mark Greene]
|
||||||
- Duplicate abilities in the tank filters are now removed
|
- Duplicate abilities in the tank filters are now removed
|
||||||
@@ -4,7 +4,7 @@ Thank you to [GonnaHetzMe](https://github.com/karelpak1) for your contributions
|
|||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [GonnaHetzMe] The turret for Centurion I is no longer offset from the body
|
- The turret for Centurion I is no longer offset from the body [GonnaHetzMe]
|
||||||
- Please allow up to 24 hours for the model to update
|
- Please allow up to 24 hours for the model to update
|
||||||
- Vertical Stabilizers now give the correct 12% buff instead of 15%
|
- Vertical Stabilizers now give the correct 12% buff instead of 15%
|
||||||
- Re-ordering tanks in Compare now works once again
|
- Re-ordering tanks in Compare now works once again
|
||||||
|
|||||||
@@ -15,5 +15,5 @@ Thank you to [Mark Greene](https://github.com/Hitjack007) for your contributions
|
|||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- The Tankopedia now smoothly resizes when enlarging on interaction
|
- The Tankopedia now smoothly resizes when enlarging on interaction
|
||||||
- [Mark Greene] Stock turrets now correctly mount the corresponding stock gun
|
- Stock turrets now correctly mount the corresponding stock gun [Mark Greene]
|
||||||
- The consumable and provision buttons in Compare are no longer tiny
|
- The consumable and provision buttons in Compare are no longer tiny
|
||||||
@@ -5,10 +5,10 @@ Thank you to [Mark Greene](https://github.com/Hitjack007) for your contributions
|
|||||||
## Features
|
## Features
|
||||||
|
|
||||||
- Reworked tank search filters to be far more compact to make way for new filters
|
- Reworked tank search filters to be far more compact to make way for new filters
|
||||||
- [Mark Greene] Added the ability to filter tanks by consumables
|
- Added the ability to filter tanks by consumables [Mark Greene]
|
||||||
- Added the ability to filter tanks by provisions and game-mode abilities and powers
|
- Added the ability to filter tanks by provisions and game-mode abilities and powers
|
||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- Consumable and provision icons in Compare are now properly sized
|
- Consumable and provision icons in Compare are now properly sized
|
||||||
- [Mark Greene] Provisions now properly affect terrain resistances
|
- Provisions now properly affect terrain resistances [Mark Greene]
|
||||||
@@ -13,11 +13,11 @@ Thank you to [GonnaHetzMe](https://github.com/karelpak1) for your contributions
|
|||||||
|
|
||||||
## Technical Features
|
## Technical Features
|
||||||
|
|
||||||
- [GonnaHetzMe] Enabling dev mode now displays the tank's non-numerical id
|
- Enabling dev mode now displays the tank's non-numerical id [GonnaHetzMe]
|
||||||
- [GonnaHetzMe] The dev id and the new dev name are now copyable on click
|
- The dev id and the new dev name are now copyable on click [GonnaHetzMe]
|
||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [GonnaHetzMe] Tech trees that start at tiers higher than tier 1 like the Blitz Nation ones now properly render their trees in Tankopedia
|
- Tech trees that start at tiers higher than tier 1 like the Blitz Nation ones now properly render their trees in Tankopedia [GonnaHetzMe]
|
||||||
- [GonnaHetzMe] The tank pitch/yaw inputs in the Tank Sandbox now initialize with the correct values instead of 0
|
- The tank pitch/yaw inputs in the Tank Sandbox now initialize with the correct values instead of 0 [GonnaHetzMe]
|
||||||
- [GonnaHetzMe] Large Repair Kits once again use the correct modern icon
|
- Large Repair Kits once again use the correct modern icon [GonnaHetzMe]
|
||||||
@@ -4,5 +4,5 @@ Thank you to [GonnaHetzMe](https://github.com/karelpak1) for your contributions
|
|||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [GonnaHetzMe] Tank hit points in Equalizer mode is now accurate to the game
|
- Tank hit points in Equalizer mode is now accurate to the game [GonnaHetzMe]
|
||||||
- Armor highlighting now reflects the actual thicknesses of tanks in Equalizer mode
|
- Armor highlighting now reflects the actual thicknesses of tanks in Equalizer mode
|
||||||
@@ -4,9 +4,9 @@ Thank you to [GonnaHetzMe](https://github.com/karelpak1) for your contributions
|
|||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [GonnaHetzMe] Tungsten shells are now properly cropped
|
- Tungsten shells are now properly cropped [GonnaHetzMe]
|
||||||
- Equalizer no longer gives insanely high penetration values
|
- Equalizer no longer gives insanely high penetration values
|
||||||
- The tank reveal animation no longer repeats when you scroll away and back to the tank sandbox
|
- The tank reveal animation no longer repeats when you scroll away and back to the tank sandbox
|
||||||
- [GonnaHetzMe] The RHM. Pzw.'s turret no longer has the floating plate
|
- The RHM. Pzw.'s turret no longer has the floating plate [GonnaHetzMe]
|
||||||
- Please give BlitzKit up to 1 hour to update the model
|
- Please give BlitzKit up to 1 hour to update the model
|
||||||
- [GonnaHetzMe] Tanks with inclined turret rings like the Minotauro now display the correct pitch in the tank sandbox inputs
|
- Tanks with inclined turret rings like the Minotauro now display the correct pitch in the tank sandbox inputs [GonnaHetzMe]
|
||||||
@@ -4,7 +4,7 @@ Thank you to [GonnaHetzMe](https://github.com/karelpak1) for your contributions
|
|||||||
|
|
||||||
## Features
|
## Features
|
||||||
|
|
||||||
- [GonnaHetzMe] Added tooltips to the module selector in Tankopedia
|
- Added tooltips to the module selector in Tankopedia [GonnaHetzMe]
|
||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
@@ -12,7 +12,7 @@ Thank you to [GonnaHetzMe](https://github.com/karelpak1) for your contributions
|
|||||||
- Removed tank visual and collision model caching
|
- Removed tank visual and collision model caching
|
||||||
- Guesser once again breaks streaks if not all tiers are selected
|
- Guesser once again breaks streaks if not all tiers are selected
|
||||||
- BlitzKit now properly unloads tank models from memory when visually hidden in Guesser
|
- BlitzKit now properly unloads tank models from memory when visually hidden in Guesser
|
||||||
- [GonnaHetzMe] Tanks with complex transparency like the Herdbreaker once again handle opacity correctly
|
- Tanks with complex transparency like the Herdbreaker once again handle opacity correctly [GonnaHetzMe]
|
||||||
- [GonnaHetzMe] Pieces of tank models that have transparency now handle culling properly (they're visible from both sides)
|
- Pieces of tank models that have transparency now handle culling properly (they're visible from both sides) [GonnaHetzMe]
|
||||||
- [GonnaHetzMe] Tanks with "cardboard" textures have been fixed, thanks to better PVR file parsing
|
- Tanks with "cardboard" textures have been fixed, thanks to better PVR file parsing [GonnaHetzMe]
|
||||||
- [GonnaHetzMe] Tank icons are now scaled correctly so small tanks are now properly zoomed out in contrast to bigger ones
|
- Tank icons are now scaled correctly so small tanks are now properly zoomed out in contrast to bigger ones [GonnaHetzMe]
|
||||||
@@ -8,13 +8,13 @@ Thank you to [Mark Greene](https://github.com/Hitjack007) for your contributions
|
|||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [Mark Greene] Clicking on the armor multiple times with HE no longer crashes BlitzKit
|
- Clicking on the armor multiple times with HE no longer crashes BlitzKit [Mark Greene]
|
||||||
- [Mark Greene] Ricochets that later intersect with external modules no longer falsely claim a successful damaging penetration
|
- Ricochets that later intersect with external modules no longer falsely claim a successful damaging penetration [Mark Greene]
|
||||||
- The lighting animation no longer stops prematurely when BlitzKit is unfocused
|
- The lighting animation no longer stops prematurely when BlitzKit is unfocused
|
||||||
- The spot light angle has been increased to more evenly light up larger tanks
|
- The spot light angle has been increased to more evenly light up larger tanks
|
||||||
- BlitzKit once again uses soft shadows, reducing the pixelated shadows
|
- BlitzKit once again uses soft shadows, reducing the pixelated shadows
|
||||||
- Fixed the weird patterns that formed on the tracks of tanks under self-shadows
|
- Fixed the weird patterns that formed on the tracks of tanks under self-shadows
|
||||||
- Increased the floor size and light decay to create the illusion that the floor is infinite
|
- Increased the floor size and light decay to create the illusion that the floor is infinite
|
||||||
- [Mark Greene] Safari no longer crashes when unloading textures for unloaded tanks
|
- Safari no longer crashes when unloading textures for unloaded tanks [Mark Greene]
|
||||||
- The gun depression transition between two constraints (like often behind tanks) now uses a gentler zoned and can never be 0
|
- The gun depression transition between two constraints (like often behind tanks) now uses a gentler zoned and can never be 0
|
||||||
- [Mark Greene] Armor plate names in Static Armor are now properly capitalized in English and translated to other languages
|
- Armor plate names in Static Armor are now properly capitalized in English and translated to other languages [Mark Greene]
|
||||||
+15
-15
@@ -4,27 +4,27 @@ Thank you to [Mark Greene](https://github.com/Hitjack007) for your contributions
|
|||||||
|
|
||||||
## Features
|
## Features
|
||||||
|
|
||||||
- [Mark Greene] Added Peekaboo DPM
|
- Added Peekaboo DPM [Mark Greene]
|
||||||
- Your Peekaboo DPM is lower than your normal DPM if your reload is faster than 10s as you'll have to wait for the remaining 10s for you to get unspotted before you can poke and shoot
|
- Your Peekaboo DPM is lower than your normal DPM if your reload is faster than 10s as you'll have to wait for the remaining 10s for you to get unspotted before you can poke and shoot
|
||||||
- [Mark Greene] The test and owned tank filters are now more intuitive as clicking on them now turns the clicked option on instead of off
|
- The test and owned tank filters are now more intuitive as clicking on them now turns the clicked option on instead of off [Mark Greene]
|
||||||
- [Mark Greene] Added a spall liner button to the Tankopedia beside the other equipment
|
- Added a spall liner button to the Tankopedia beside the other equipment [Mark Greene]
|
||||||
|
|
||||||
## Fixes
|
## Fixes
|
||||||
|
|
||||||
- [Mark Greene] BlitzKit Session now properly handles tanks removed from the game
|
- BlitzKit Session now properly handles tanks removed from the game [Mark Greene]
|
||||||
- [Mark Greene] Removed the Beta badge from the Equalizer button
|
- Removed the Beta badge from the Equalizer button [Mark Greene]
|
||||||
- Updated the background image for the Equalizer button to the actual banner of the new game mode
|
- Updated the background image for the Equalizer button to the actual banner of the new game mode
|
||||||
- [Mark Greene] The armor no longer disappears when you turn on Dynamic Armor System
|
- The armor no longer disappears when you turn on Dynamic Armor System [Mark Greene]
|
||||||
- [Mark Greene] Camouflage values in Tankopedia are now more descriptive when shooting
|
- Camouflage values in Tankopedia are now more descriptive when shooting [Mark Greene]
|
||||||
- [Mark Greene] The contact shadows on the ground no longer grow & darken when switching between tabs
|
- The contact shadows on the ground no longer grow & darken when switching between tabs [Mark Greene]
|
||||||
- The "Help Translate BlitzKit" text on the home page is now properly centered vertically
|
- The "Help Translate BlitzKit" text on the home page is now properly centered vertically
|
||||||
- [Mark Greene] The footer now says "Branch" instead of "CDN"
|
- The footer now says "Branch" instead of "CDN" [Mark Greene]
|
||||||
- [Mark Greene] The game version in the footer now displays a shorthand version instead of the entire version number
|
- The game version in the footer now displays a shorthand version instead of the entire version number [Mark Greene]
|
||||||
- [Mark Greene] The reload visualizer now displays just 1 decimal place
|
- The reload visualizer now displays just 1 decimal place [Mark Greene]
|
||||||
- [Mark Greene] The search bar no longer redirects to a seemingly random tank when clicking enter when searching
|
- The search bar no longer redirects to a seemingly random tank when clicking enter when searching [Mark Greene]
|
||||||
- [Mark Greene] Tank search now properly handles the full names of tanks like the Super Pershing
|
- Tank search now properly handles the full names of tanks like the Super Pershing [Mark Greene]
|
||||||
- [Mark Greene] The loading bar below the name of the tanks in Tankopedia is now sufficiently spaced below
|
- The loading bar below the name of the tanks in Tankopedia is now sufficiently spaced below [Mark Greene]
|
||||||
- [Mark Greene] The gun depression visualizer now properly handles the inherent tilt of tanks like the Minotauro
|
- The gun depression visualizer now properly handles the inherent tilt of tanks like the Minotauro [Mark Greene]
|
||||||
|
|
||||||
## Technical Features
|
## Technical Features
|
||||||
|
|
||||||
|
|||||||
+22
-3
@@ -4,14 +4,33 @@
|
|||||||
|
|
||||||
"paths": {
|
"paths": {
|
||||||
"default": null,
|
"default": null,
|
||||||
"api": null
|
|
||||||
|
"api": null,
|
||||||
|
|
||||||
|
"models_tanks": null,
|
||||||
|
"models_legendary": null,
|
||||||
|
"models_maps": null
|
||||||
},
|
},
|
||||||
|
|
||||||
"nodes": {
|
"nodes": {
|
||||||
"default": "blitzkit/deploy-node-beta.blitzkit.app",
|
"default": "blitzkit/deploy-node-beta.blitzkit.app",
|
||||||
"api": "blitzkit/deploy-node-api.beta.blitzkit.app"
|
|
||||||
|
"api": "blitzkit/deploy-node-api.beta.blitzkit.app",
|
||||||
|
|
||||||
|
"models_tanks": "blitzkit/deploy-node-tanks.models.beta.blitzkit.app",
|
||||||
|
"models_legendary": "blitzkit/deploy-node-legendary.models.beta.blitzkit.app",
|
||||||
|
"models_maps": "blitzkit/deploy-node-maps.models.beta.blitzkit.app"
|
||||||
},
|
},
|
||||||
|
|
||||||
"aliases": {
|
"aliases": {
|
||||||
|
"default": "/",
|
||||||
|
|
||||||
"api": "https://api.beta.blitzkit.app",
|
"api": "https://api.beta.blitzkit.app",
|
||||||
"static": "https://static.beta.blitzkit.app"
|
|
||||||
|
"models_tanks": "https://tanks.models.beta.blitzkit.app",
|
||||||
|
"models_legendary": "https://legendary.models.beta.blitzkit.app",
|
||||||
|
"models_maps": "https://maps.models.beta.blitzkit.app",
|
||||||
|
|
||||||
|
"static": "https://static.blitzkit.app"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4,11 +4,25 @@
|
|||||||
|
|
||||||
"paths": {
|
"paths": {
|
||||||
"default": null,
|
"default": null,
|
||||||
"api": "api"
|
|
||||||
|
"api": "api",
|
||||||
|
|
||||||
|
"models_tanks": "models/tanks",
|
||||||
|
"models_legendary": "models/legendary",
|
||||||
|
"models_maps": "models/maps"
|
||||||
},
|
},
|
||||||
|
|
||||||
"nodes": {},
|
"nodes": {},
|
||||||
|
|
||||||
"aliases": {
|
"aliases": {
|
||||||
|
"default": "/",
|
||||||
|
|
||||||
"api": "/api",
|
"api": "/api",
|
||||||
|
|
||||||
|
"models_tanks": "/models/tanks",
|
||||||
|
"models_legendary": "/models/legendary",
|
||||||
|
"models_maps": "/models/maps",
|
||||||
|
|
||||||
"static": "https://static.blitzkit.app"
|
"static": "https://static.blitzkit.app"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4,14 +4,33 @@
|
|||||||
|
|
||||||
"paths": {
|
"paths": {
|
||||||
"default": null,
|
"default": null,
|
||||||
"api": null
|
|
||||||
|
"api": null,
|
||||||
|
|
||||||
|
"models_tanks": null,
|
||||||
|
"models_legendary": null,
|
||||||
|
"models_maps": null
|
||||||
},
|
},
|
||||||
|
|
||||||
"nodes": {
|
"nodes": {
|
||||||
"default": "blitzkit/deploy-node-opentest.blitzkit.app",
|
"default": "blitzkit/deploy-node-opentest.blitzkit.app",
|
||||||
"api": "blitzkit/deploy-node-api.opentest.blitzkit.app"
|
|
||||||
|
"api": "blitzkit/deploy-node-api.opentest.blitzkit.app",
|
||||||
|
|
||||||
|
"models_tanks": "blitzkit/deploy-node-tanks.models.opentest.blitzkit.app",
|
||||||
|
"models_legendary": "blitzkit/deploy-node-legendary.models.opentest.blitzkit.app",
|
||||||
|
"models_maps": "blitzkit/deploy-node-maps.models.opentest.blitzkit.app"
|
||||||
},
|
},
|
||||||
|
|
||||||
"aliases": {
|
"aliases": {
|
||||||
|
"default": "/",
|
||||||
|
|
||||||
"api": "https://api.opentest.blitzkit.app",
|
"api": "https://api.opentest.blitzkit.app",
|
||||||
"static": "https://static.opentest.blitzkit.app"
|
|
||||||
|
"models_tanks": "https://tanks.models.opentest.blitzkit.app",
|
||||||
|
"models_legendary": "https://legendary.models.opentest.blitzkit.app",
|
||||||
|
"models_maps": "https://maps.models.opentest.blitzkit.app",
|
||||||
|
|
||||||
|
"static": "https://static.blitzkit.app"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4,14 +4,33 @@
|
|||||||
|
|
||||||
"paths": {
|
"paths": {
|
||||||
"default": null,
|
"default": null,
|
||||||
"api": null
|
|
||||||
|
"api": null,
|
||||||
|
|
||||||
|
"models_tanks": null,
|
||||||
|
"models_legendary": null,
|
||||||
|
"models_maps": null
|
||||||
},
|
},
|
||||||
|
|
||||||
"nodes": {
|
"nodes": {
|
||||||
"default": "blitzkit/deploy-node-preview.blitzkit.app",
|
"default": "blitzkit/deploy-node-preview.blitzkit.app",
|
||||||
"api": "blitzkit/deploy-node-api.preview.blitzkit.app"
|
|
||||||
|
"api": "blitzkit/deploy-node-api.preview.blitzkit.app",
|
||||||
|
|
||||||
|
"models_tanks": "blitzkit/deploy-node-tanks.models.preview.blitzkit.app",
|
||||||
|
"models_legendary": "blitzkit/deploy-node-legendary.models.preview.blitzkit.app",
|
||||||
|
"models_maps": "blitzkit/deploy-node-maps.models.preview.blitzkit.app"
|
||||||
},
|
},
|
||||||
|
|
||||||
"aliases": {
|
"aliases": {
|
||||||
|
"default": "/",
|
||||||
|
|
||||||
"api": "https://api.preview.blitzkit.app",
|
"api": "https://api.preview.blitzkit.app",
|
||||||
"static": "https://static.preview.blitzkit.app"
|
|
||||||
|
"models_tanks": "https://tanks.models.preview.blitzkit.app",
|
||||||
|
"models_legendary": "https://legendary.models.preview.blitzkit.app",
|
||||||
|
"models_maps": "https://maps.models.preview.blitzkit.app",
|
||||||
|
|
||||||
|
"static": "https://static.blitzkit.app"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4,14 +4,33 @@
|
|||||||
|
|
||||||
"paths": {
|
"paths": {
|
||||||
"default": null,
|
"default": null,
|
||||||
"api": null
|
|
||||||
|
"api": null,
|
||||||
|
|
||||||
|
"models_tanks": null,
|
||||||
|
"models_legendary": null,
|
||||||
|
"models_maps": null
|
||||||
},
|
},
|
||||||
|
|
||||||
"nodes": {
|
"nodes": {
|
||||||
"default": "blitzkit/deploy-node-blitzkit.app",
|
"default": "blitzkit/deploy-node-blitzkit.app",
|
||||||
"api": "blitzkit/deploy-node-api.blitzkit.app"
|
|
||||||
|
"api": "blitzkit/deploy-node-api.blitzkit.app",
|
||||||
|
|
||||||
|
"models_tanks": "blitzkit/deploy-node-tanks.models.blitzkit.app",
|
||||||
|
"models_legendary": "blitzkit/deploy-node-legendary.models.blitzkit.app",
|
||||||
|
"models_maps": "blitzkit/deploy-node-maps.models.blitzkit.app"
|
||||||
},
|
},
|
||||||
|
|
||||||
"aliases": {
|
"aliases": {
|
||||||
|
"default": "/",
|
||||||
|
|
||||||
"api": "https://api.blitzkit.app",
|
"api": "https://api.blitzkit.app",
|
||||||
|
|
||||||
|
"models_tanks": "https://tanks.models.blitzkit.app",
|
||||||
|
"models_legendary": "https://legendary.models.blitzkit.app",
|
||||||
|
"models_maps": "https://maps.models.blitzkit.app",
|
||||||
|
|
||||||
"static": "https://static.blitzkit.app"
|
"static": "https://static.blitzkit.app"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
+3
-2
@@ -4,12 +4,13 @@
|
|||||||
"license": "BlitzKit License",
|
"license": "BlitzKit License",
|
||||||
"private": true,
|
"private": true,
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"dev": "cd packages/website && bun run dev",
|
"dev": "cd packages/website && bun --bun run dev",
|
||||||
"build": "cd packages/website && bun run build",
|
"build": "cd packages/website && bun run build",
|
||||||
"discover-ids": "cd packages/scripts && bun run discover-ids",
|
"discover-ids": "cd packages/scripts && bun run discover-ids",
|
||||||
"build-protos": "cd packages/scripts && bun run build-protos",
|
"build-protos": "cd packages/scripts && bun run build-protos",
|
||||||
"record-performance": "cd packages/scripts && bun run record-performance",
|
"record-performance": "cd packages/scripts && bun run record-performance",
|
||||||
"download-client": "cd packages/scripts && bun run download-client"
|
"download-client": "cd packages/scripts && bun run download-client",
|
||||||
|
"clean-astro": "rm -rf packages/website/.astro packages/website/node_modules/.astro packages/website/node_modules/.vite"
|
||||||
},
|
},
|
||||||
"type": "module",
|
"type": "module",
|
||||||
"workspaces": [
|
"workspaces": [
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ export function metaSortTank(
|
|||||||
gameDefinitions: GameDefinitions,
|
gameDefinitions: GameDefinitions,
|
||||||
) {
|
) {
|
||||||
return tanks
|
return tanks
|
||||||
|
.sort((a, b) => a.id - b.id)
|
||||||
.sort((a, b) => b.tier - a.tier)
|
.sort((a, b) => b.tier - a.tier)
|
||||||
.sort(
|
.sort(
|
||||||
(a, b) => treeTypeOrder.indexOf(b.type) - treeTypeOrder.indexOf(a.type),
|
(a, b) => treeTypeOrder.indexOf(b.type) - treeTypeOrder.indexOf(a.type),
|
||||||
|
|||||||
@@ -54,6 +54,7 @@ export const TIER_ROMAN_NUMERALS: Record<number, string> = {
|
|||||||
8: "VIII",
|
8: "VIII",
|
||||||
9: "IX",
|
9: "IX",
|
||||||
10: "X",
|
10: "X",
|
||||||
|
11: "XI",
|
||||||
};
|
};
|
||||||
|
|
||||||
export const flags: Record<string, string> = {
|
export const flags: Record<string, string> = {
|
||||||
|
|||||||
@@ -215,6 +215,7 @@
|
|||||||
"title": "Settings",
|
"title": "Settings",
|
||||||
"description": "Change BlitzKit settings",
|
"description": "Change BlitzKit settings",
|
||||||
"dev_mode": "Development mode",
|
"dev_mode": "Development mode",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Language"
|
"language": "Language"
|
||||||
},
|
},
|
||||||
|
|
||||||
@@ -458,6 +459,8 @@
|
|||||||
},
|
},
|
||||||
|
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
|
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "Hull down",
|
"hull_down": "Hull down",
|
||||||
"face_hug": "Face hug",
|
"face_hug": "Face hug",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Settings",
|
"title": "Settings",
|
||||||
"description": "Change BlitzKit settings",
|
"description": "Change BlitzKit settings",
|
||||||
"dev_mode": "Modo de desarrollador",
|
"dev_mode": "Modo de desarrollador",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Idioma"
|
"language": "Idioma"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "Hull down",
|
"hull_down": "Hull down",
|
||||||
"face_hug": "Cara a cara",
|
"face_hug": "Cara a cara",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Paramètres",
|
"title": "Paramètres",
|
||||||
"description": "Modifier les paramètres de BlitzKit",
|
"description": "Modifier les paramètres de BlitzKit",
|
||||||
"dev_mode": "Mode développement",
|
"dev_mode": "Mode développement",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Langue"
|
"language": "Langue"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "Hull down",
|
"hull_down": "Hull down",
|
||||||
"face_hug": "Face hug",
|
"face_hug": "Face hug",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Settings",
|
"title": "Settings",
|
||||||
"description": "Change BlitzKit settings",
|
"description": "Change BlitzKit settings",
|
||||||
"dev_mode": "開発者モード",
|
"dev_mode": "開発者モード",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "言語 / Language"
|
"language": "言語 / Language"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "ハルダウン",
|
"hull_down": "ハルダウン",
|
||||||
"face_hug": "密着",
|
"face_hug": "密着",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Settings",
|
"title": "Settings",
|
||||||
"description": "Change BlitzKit settings",
|
"description": "Change BlitzKit settings",
|
||||||
"dev_mode": "Development mode",
|
"dev_mode": "Development mode",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Language"
|
"language": "Language"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "Hull down",
|
"hull_down": "Hull down",
|
||||||
"face_hug": "Face hug",
|
"face_hug": "Face hug",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Settings",
|
"title": "Settings",
|
||||||
"description": "Change BlitzKit settings",
|
"description": "Change BlitzKit settings",
|
||||||
"dev_mode": "Modo de desenvolvimento",
|
"dev_mode": "Modo de desenvolvimento",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Idioma"
|
"language": "Idioma"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "Casco para baixo",
|
"hull_down": "Casco para baixo",
|
||||||
"face_hug": "Abraço facial",
|
"face_hug": "Abraço facial",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Настройки",
|
"title": "Настройки",
|
||||||
"description": "Изменить настройки BlitzKit",
|
"description": "Изменить настройки BlitzKit",
|
||||||
"dev_mode": "Режим разработчика",
|
"dev_mode": "Режим разработчика",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Язык"
|
"language": "Язык"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "За холмом",
|
"hull_down": "За холмом",
|
||||||
"face_hug": "В упор",
|
"face_hug": "В упор",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "Налаштування",
|
"title": "Налаштування",
|
||||||
"description": "Змінити налаштування BlitzKit ",
|
"description": "Змінити налаштування BlitzKit ",
|
||||||
"dev_mode": "Режим розробника",
|
"dev_mode": "Режим розробника",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "Мова"
|
"language": "Мова"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "Від башти",
|
"hull_down": "Від башти",
|
||||||
"face_hug": "Клінч",
|
"face_hug": "Клінч",
|
||||||
|
|||||||
@@ -194,6 +194,7 @@
|
|||||||
"title": "设置",
|
"title": "设置",
|
||||||
"description": "更改 BlitzKit 设置",
|
"description": "更改 BlitzKit 设置",
|
||||||
"dev_mode": "开发者模式",
|
"dev_mode": "开发者模式",
|
||||||
|
"auto_load_models": "Auto-load models",
|
||||||
"language": "语言"
|
"language": "语言"
|
||||||
},
|
},
|
||||||
"common": {
|
"common": {
|
||||||
@@ -412,6 +413,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"sandbox": {
|
"sandbox": {
|
||||||
|
"load_model": "Load model",
|
||||||
"poses": {
|
"poses": {
|
||||||
"hull_down": "俯角视角",
|
"hull_down": "俯角视角",
|
||||||
"face_hug": "顶牛视角",
|
"face_hug": "顶牛视角",
|
||||||
|
|||||||
@@ -135,7 +135,7 @@ let regionI = 0;
|
|||||||
|
|
||||||
console.log("Starting discovery loop...");
|
console.log("Starting discovery loop...");
|
||||||
|
|
||||||
atMaxRate(async ({ _break: break1 }) => {
|
await atMaxRate(async ({ _break: break1 }) => {
|
||||||
if (regions.length === 0) {
|
if (regions.length === 0) {
|
||||||
console.log("All regions exhausted, exiting discovery loop...");
|
console.log("All regions exhausted, exiting discovery loop...");
|
||||||
return break1();
|
return break1();
|
||||||
@@ -166,18 +166,19 @@ atMaxRate(async ({ _break: break1 }) => {
|
|||||||
fields
|
fields
|
||||||
}&account_id=${accountIds}`;
|
}&account_id=${accountIds}`;
|
||||||
|
|
||||||
atMaxRate(async ({ _break: break2 }) => {
|
if (idRange.length < MAX_IDS_PER_CALL) {
|
||||||
if (idRange.length < MAX_IDS_PER_CALL) {
|
console.log(
|
||||||
console.log(
|
`Removing region ${region.domain} removed due to ID range exhaustion...`,
|
||||||
`Removing region ${region.domain} removed due to ID range exhaustion...`,
|
);
|
||||||
);
|
regions.splice(regionI, 1);
|
||||||
regions.splice(regionI, 1);
|
}
|
||||||
}
|
|
||||||
|
|
||||||
const response = await fetch(url);
|
await atMaxRate(async ({ _break: break2 }) => {
|
||||||
const data = (await response.json()) as QuickInfo;
|
const data = await fetch(url)
|
||||||
|
.then((response) => response.json() as Promise<QuickInfo>)
|
||||||
|
.catch(() => null);
|
||||||
|
|
||||||
if (data.status !== "ok") {
|
if (data === null || data.status !== "ok") {
|
||||||
console.warn("Failed API call; trying again...");
|
console.warn("Failed API call; trying again...");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,7 +20,9 @@ interface MethodContext {
|
|||||||
let lastT = 0;
|
let lastT = 0;
|
||||||
const maxDelta = 1000 / API_RATE;
|
const maxDelta = 1000 / API_RATE;
|
||||||
const DELTA_BUFFER = 0;
|
const DELTA_BUFFER = 0;
|
||||||
export async function atMaxRate(method: (context: MethodContext) => void) {
|
export async function atMaxRate(
|
||||||
|
method: (context: MethodContext) => void | Promise<void>,
|
||||||
|
) {
|
||||||
let isBroken = false;
|
let isBroken = false;
|
||||||
|
|
||||||
const context: MethodContext = {
|
const context: MethodContext = {
|
||||||
@@ -39,7 +41,7 @@ export async function atMaxRate(method: (context: MethodContext) => void) {
|
|||||||
await sleep(maxDelta - delta + DELTA_BUFFER);
|
await sleep(maxDelta - delta + DELTA_BUFFER);
|
||||||
}
|
}
|
||||||
|
|
||||||
method(context);
|
await method(context);
|
||||||
lastT = t;
|
lastT = t;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -27,9 +27,10 @@ import {
|
|||||||
TextField,
|
TextField,
|
||||||
} from "@radix-ui/themes";
|
} from "@radix-ui/themes";
|
||||||
import fuzzysort from "fuzzysort";
|
import fuzzysort from "fuzzysort";
|
||||||
import { debounce, times } from "lodash-es";
|
import { debounce } from "lodash-es";
|
||||||
import { useCallback, useEffect, useRef, useState } from "react";
|
import { useCallback, useEffect, useRef, useState } from "react";
|
||||||
import { awaitableTankNames } from "../core/awaitables/tankNames";
|
import { awaitableTankNames } from "../core/awaitables/tankNames";
|
||||||
|
import { awaitableTiers } from "../core/awaitables/tiers";
|
||||||
import { api } from "../core/blitzkit/api";
|
import { api } from "../core/blitzkit/api";
|
||||||
import { useLocale } from "../hooks/useLocale";
|
import { useLocale } from "../hooks/useLocale";
|
||||||
import { Guess, GuessState } from "../stores/guess";
|
import { Guess, GuessState } from "../stores/guess";
|
||||||
@@ -38,9 +39,10 @@ import { SearchResults } from "./SearchResults";
|
|||||||
|
|
||||||
const { go } = fuzzysort;
|
const { go } = fuzzysort;
|
||||||
|
|
||||||
const [tankNames, tankDefinitions] = await Promise.all([
|
const [tankNames, tankDefinitions, TIERS] = await Promise.all([
|
||||||
awaitableTankNames,
|
awaitableTankNames,
|
||||||
api.tankDefinitions(),
|
api.tankDefinitions(),
|
||||||
|
awaitableTiers,
|
||||||
]);
|
]);
|
||||||
|
|
||||||
const ids = Object.keys(tankDefinitions.tanks);
|
const ids = Object.keys(tankDefinitions.tanks);
|
||||||
@@ -193,8 +195,7 @@ export function Guesser() {
|
|||||||
</DropdownMenu.Trigger>
|
</DropdownMenu.Trigger>
|
||||||
|
|
||||||
<DropdownMenu.Content>
|
<DropdownMenu.Content>
|
||||||
{times(10, (index) => {
|
{TIERS.map((tier) => {
|
||||||
const tier = 10 - index;
|
|
||||||
const isSelected = tiers.includes(tier);
|
const isSelected = tiers.includes(tier);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -1,3 +1,27 @@
|
|||||||
<script>
|
<script>
|
||||||
|
import locales from "@blitzkit/i18n/locales.json";
|
||||||
|
import { getBestLocale } from "../core/i18n/getBestLocale";
|
||||||
|
|
||||||
|
const pathname = window.location.pathname;
|
||||||
|
const hasPreference = localStorage.getItem("preferred-locale") !== null;
|
||||||
|
const bestLocale = getBestLocale();
|
||||||
|
const currentLocale =
|
||||||
|
locales.supported.find(
|
||||||
|
({ locale }) =>
|
||||||
|
pathname === `/${locale}` || pathname.startsWith(`/${locale}/`),
|
||||||
|
)?.locale ?? locales.default;
|
||||||
|
|
||||||
|
if (
|
||||||
|
bestLocale !== currentLocale &&
|
||||||
|
(hasPreference || currentLocale === locales.default)
|
||||||
|
) {
|
||||||
|
const rawPath =
|
||||||
|
currentLocale === locales.default
|
||||||
|
? pathname
|
||||||
|
: pathname.slice(`/${currentLocale}`.length) || "/";
|
||||||
|
|
||||||
|
window.location.pathname = `${
|
||||||
|
bestLocale === locales.default ? "" : `/${bestLocale}`
|
||||||
|
}${rawPath}`;
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
@@ -25,8 +25,8 @@ import {
|
|||||||
Tooltip,
|
Tooltip,
|
||||||
type FlexProps,
|
type FlexProps,
|
||||||
} from "@radix-ui/themes";
|
} from "@radix-ui/themes";
|
||||||
import { times } from "lodash-es";
|
|
||||||
import { Fragment, type ComponentProps, type ReactNode } from "react";
|
import { Fragment, type ComponentProps, type ReactNode } from "react";
|
||||||
|
import { awaitableTiers } from "../../../core/awaitables/tiers";
|
||||||
import { api } from "../../../core/blitzkit/api";
|
import { api } from "../../../core/blitzkit/api";
|
||||||
import { useLocale } from "../../../hooks/useLocale";
|
import { useLocale } from "../../../hooks/useLocale";
|
||||||
import { App } from "../../../stores/app";
|
import { App } from "../../../stores/app";
|
||||||
@@ -171,7 +171,7 @@ const GUN_TYPES = Object.keys(
|
|||||||
|
|
||||||
const MAX_ICONS = 4;
|
const MAX_ICONS = 4;
|
||||||
|
|
||||||
const TIERS = times(10, (i) => 10 - i);
|
const TIERS = await awaitableTiers;
|
||||||
|
|
||||||
export function FilterControl() {
|
export function FilterControl() {
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -1,10 +1,12 @@
|
|||||||
import { TIER_ROMAN_NUMERALS } from "@blitzkit/core";
|
import { TIER_ROMAN_NUMERALS } from "@blitzkit/core";
|
||||||
import { Flex, IconButton, Text } from "@radix-ui/themes";
|
import { Flex, IconButton, Text } from "@radix-ui/themes";
|
||||||
import { times } from "lodash-es";
|
|
||||||
import { memo } from "react";
|
import { memo } from "react";
|
||||||
|
import { awaitableTiers } from "../../../core/awaitables/tiers";
|
||||||
import { TankFilters } from "../../../stores/tankFilters";
|
import { TankFilters } from "../../../stores/tankFilters";
|
||||||
import { TankSort } from "../../../stores/tankopediaSort";
|
import { TankSort } from "../../../stores/tankopediaSort";
|
||||||
|
|
||||||
|
const TIERS = await awaitableTiers;
|
||||||
|
|
||||||
export const TierFilter = memo(() => {
|
export const TierFilter = memo(() => {
|
||||||
const by = TankSort.use((state) => state.by);
|
const by = TankSort.use((state) => state.by);
|
||||||
const search = TankFilters.use((state) => state.search);
|
const search = TankFilters.use((state) => state.search);
|
||||||
@@ -19,8 +21,7 @@ export const TierFilter = memo(() => {
|
|||||||
overflow="hidden"
|
overflow="hidden"
|
||||||
style={{ borderRadius: "var(--radius-full)" }}
|
style={{ borderRadius: "var(--radius-full)" }}
|
||||||
>
|
>
|
||||||
{times(10, (index) => {
|
{TIERS.map((tier) => {
|
||||||
const tier = 10 - index;
|
|
||||||
const selected = tiers.includes(tier);
|
const selected = tiers.includes(tier);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
+3
-1
@@ -13,6 +13,7 @@ import { modelTransformEvent } from "../../../../../../../core/blitzkit/modelTra
|
|||||||
import { Var } from "../../../../../../../core/radix/var";
|
import { Var } from "../../../../../../../core/radix/var";
|
||||||
import { useLocale } from "../../../../../../../hooks/useLocale";
|
import { useLocale } from "../../../../../../../hooks/useLocale";
|
||||||
import { Duel } from "../../../../../../../stores/duel";
|
import { Duel } from "../../../../../../../stores/duel";
|
||||||
|
import { Tankopedia } from "../../../../../../../stores/tankopedia";
|
||||||
import type { MaybeSkeletonComponentProps } from "../../../../../../../types/maybeSkeletonComponentProps";
|
import type { MaybeSkeletonComponentProps } from "../../../../../../../types/maybeSkeletonComponentProps";
|
||||||
import { VisualizerCard } from "../VisualizerCard";
|
import { VisualizerCard } from "../VisualizerCard";
|
||||||
import { VisualizerCornerStat } from "../VisualizerCornerStat";
|
import { VisualizerCornerStat } from "../VisualizerCornerStat";
|
||||||
@@ -43,6 +44,7 @@ export function GunFlexibilityVisualizer({
|
|||||||
const tank = Duel.use((state) => state.protagonist.tank);
|
const tank = Duel.use((state) => state.protagonist.tank);
|
||||||
const turret = Duel.use((state) => state.protagonist.turret);
|
const turret = Duel.use((state) => state.protagonist.turret);
|
||||||
const gun = Duel.use((state) => state.protagonist.gun);
|
const gun = Duel.use((state) => state.protagonist.gun);
|
||||||
|
const modelRequested = Tankopedia.use((state) => state.modelRequested);
|
||||||
|
|
||||||
const tankModel = modelDefinition.models[tank.id];
|
const tankModel = modelDefinition.models[tank.id];
|
||||||
const turretModel = tankModel.turrets[turret.id];
|
const turretModel = tankModel.turrets[turret.id];
|
||||||
@@ -193,7 +195,7 @@ export function GunFlexibilityVisualizer({
|
|||||||
top="0"
|
top="0"
|
||||||
left="0"
|
left="0"
|
||||||
>
|
>
|
||||||
{!skeleton && <FlexibilityCanvas />}
|
{!skeleton && modelRequested && <FlexibilityCanvas />}
|
||||||
|
|
||||||
<Box
|
<Box
|
||||||
position="absolute"
|
position="absolute"
|
||||||
|
|||||||
+7
-13
@@ -28,23 +28,17 @@ export function Equalizer() {
|
|||||||
width="100%"
|
width="100%"
|
||||||
style={{
|
style={{
|
||||||
cursor: "pointer",
|
cursor: "pointer",
|
||||||
borderRadius: "var(--radius-3)",
|
borderRadius: "var(--radius-3) 0 0 var(--radius-3)",
|
||||||
backgroundImage: `url(${alias("api", `/gamemodes/Insanity/banner.webp`)})`,
|
backgroundImage: `
|
||||||
backgroundSize: "cover",
|
linear-gradient(90deg, var(--black-a3), var(--gray-1)),
|
||||||
|
url(${alias("api", `/gamemodes/Insanity/banner.webp`)})
|
||||||
|
`,
|
||||||
|
backgroundSize: "auto, fit",
|
||||||
backgroundPosition: "50% 25%",
|
backgroundPosition: "50% 25%",
|
||||||
overflow: "hidden",
|
overflow: "hidden",
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Flex
|
<Flex align="center" width="100%" justify="between" p="4" style={{}}>
|
||||||
align="center"
|
|
||||||
width="100%"
|
|
||||||
justify="between"
|
|
||||||
p="4"
|
|
||||||
style={{
|
|
||||||
background:
|
|
||||||
"linear-gradient(90deg, var(--black-a3), var(--gray-1))",
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<Text
|
<Text
|
||||||
style={{
|
style={{
|
||||||
textShadow: "0 0 var(--space-1) var(--black-a12)",
|
textShadow: "0 0 var(--space-1) var(--black-a12)",
|
||||||
|
|||||||
@@ -77,6 +77,7 @@ export function Options({ thicknessRange, canvas, skeleton }: OptionsProps) {
|
|||||||
const revealed = Tankopedia.use((state) => state.revealed);
|
const revealed = Tankopedia.use((state) => state.revealed);
|
||||||
const disturbed = Tankopedia.use((state) => state.disturbed);
|
const disturbed = Tankopedia.use((state) => state.disturbed);
|
||||||
const highGraphics = TankopediaPersistent.use((state) => state.highGraphics);
|
const highGraphics = TankopediaPersistent.use((state) => state.highGraphics);
|
||||||
|
const modelRequested = Tankopedia.use((state) => state.modelRequested);
|
||||||
const equalize = Duel.use((state) => state.equalize);
|
const equalize = Duel.use((state) => state.equalize);
|
||||||
const equalizer = Duel.use((state) => state.antagonist.tank.equalizer);
|
const equalizer = Duel.use((state) => state.antagonist.tank.equalizer);
|
||||||
|
|
||||||
@@ -283,7 +284,7 @@ export function Options({ thicknessRange, canvas, skeleton }: OptionsProps) {
|
|||||||
<SpallLinerSwitcher />
|
<SpallLinerSwitcher />
|
||||||
</Flex>
|
</Flex>
|
||||||
|
|
||||||
{!skeleton && (
|
{!skeleton && modelRequested && (
|
||||||
<Suspense>
|
<Suspense>
|
||||||
<DynamicArmorSwitcher />
|
<DynamicArmorSwitcher />
|
||||||
</Suspense>
|
</Suspense>
|
||||||
|
|||||||
+38
-4
@@ -1,11 +1,14 @@
|
|||||||
import { Flex, Heading } from "@radix-ui/themes";
|
import { UpdateIcon } from "@radix-ui/react-icons";
|
||||||
|
import { Button, Flex, Heading } from "@radix-ui/themes";
|
||||||
import { useLocale } from "../../../../../../hooks/useLocale";
|
import { useLocale } from "../../../../../../hooks/useLocale";
|
||||||
import { Duel } from "../../../../../../stores/duel";
|
import { Duel } from "../../../../../../stores/duel";
|
||||||
import { Tankopedia } from "../../../../../../stores/tankopedia";
|
import { Tankopedia } from "../../../../../../stores/tankopedia";
|
||||||
|
import type { MaybeSkeletonComponentProps } from "../../../../../../types/maybeSkeletonComponentProps";
|
||||||
import { Tracker } from "./components/Tracker";
|
import { Tracker } from "./components/Tracker";
|
||||||
|
|
||||||
export function Title() {
|
export function Title({ skeleton }: MaybeSkeletonComponentProps) {
|
||||||
const { unwrap } = useLocale();
|
const { unwrap, strings } = useLocale();
|
||||||
|
const modelRequested = Tankopedia.use((state) => state.modelRequested);
|
||||||
const protagonist = Duel.use((state) => state.protagonist.tank);
|
const protagonist = Duel.use((state) => state.protagonist.tank);
|
||||||
const revealed = Tankopedia.use((state) => state.revealed);
|
const revealed = Tankopedia.use((state) => state.revealed);
|
||||||
const disturbed = Tankopedia.use((state) => state.disturbed);
|
const disturbed = Tankopedia.use((state) => state.disturbed);
|
||||||
@@ -21,6 +24,8 @@ export function Title() {
|
|||||||
onPointerDown={(event) => {
|
onPointerDown={(event) => {
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
|
|
||||||
|
if (!modelRequested) return;
|
||||||
|
|
||||||
Tankopedia.mutate((draft) => {
|
Tankopedia.mutate((draft) => {
|
||||||
draft.revealed = true;
|
draft.revealed = true;
|
||||||
});
|
});
|
||||||
@@ -60,7 +65,36 @@ export function Title() {
|
|||||||
{name}
|
{name}
|
||||||
</Heading>
|
</Heading>
|
||||||
|
|
||||||
{!revealed && <Tracker fontSize={fontSize} />}
|
{!skeleton && !revealed && modelRequested && (
|
||||||
|
<Tracker fontSize={fontSize} />
|
||||||
|
)}
|
||||||
|
|
||||||
|
{!skeleton && !modelRequested && (
|
||||||
|
<Flex
|
||||||
|
position="absolute"
|
||||||
|
left="50%"
|
||||||
|
top="50%"
|
||||||
|
width="min(100%, 16rem)"
|
||||||
|
justify="center"
|
||||||
|
style={{
|
||||||
|
transform: `translate(-50%, calc(${fontSize} * 0.75 + var(--space-4) - 50%))`,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Button
|
||||||
|
variant="solid"
|
||||||
|
highContrast
|
||||||
|
onPointerDown={(event) => event.stopPropagation()}
|
||||||
|
onClick={() => {
|
||||||
|
Tankopedia.mutate((draft) => {
|
||||||
|
draft.modelRequested = true;
|
||||||
|
});
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<UpdateIcon />
|
||||||
|
{strings.website.tools.tankopedia.sandbox.load_model}
|
||||||
|
</Button>
|
||||||
|
</Flex>
|
||||||
|
)}
|
||||||
</Flex>
|
</Flex>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
+1
@@ -82,6 +82,7 @@ export function Lighting({ hasPbr }: Props) {
|
|||||||
blur={2 ** 1}
|
blur={2 ** 1}
|
||||||
resolution={2 ** 9}
|
resolution={2 ** 9}
|
||||||
depthWrite={false}
|
depthWrite={false}
|
||||||
|
renderOrder={1}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{animate && (
|
{animate && (
|
||||||
|
|||||||
+11
-5
@@ -51,11 +51,17 @@ export function TankModel() {
|
|||||||
|
|
||||||
invalidate();
|
invalidate();
|
||||||
|
|
||||||
if (material.map) material.map.offset.y += offset;
|
const textures = new Set([
|
||||||
if (material.aoMap) material.aoMap.offset.y += offset;
|
material.map,
|
||||||
if (material.normalMap) material.normalMap.offset.y += offset;
|
material.aoMap,
|
||||||
if (material.roughnessMap) material.roughnessMap.offset.y += offset;
|
material.normalMap,
|
||||||
if (material.metalnessMap) material.metalnessMap.offset.y += offset;
|
material.roughnessMap,
|
||||||
|
material.metalnessMap,
|
||||||
|
]);
|
||||||
|
|
||||||
|
for (const texture of textures) {
|
||||||
|
if (texture) texture.offset.y += offset;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function onPointerDown(event: ThreeEvent<PointerEvent>) {
|
function onPointerDown(event: ThreeEvent<PointerEvent>) {
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { Box, Flex } from "@radix-ui/themes";
|
import { Box, Flex } from "@radix-ui/themes";
|
||||||
import { times } from "lodash-es";
|
import { times } from "lodash-es";
|
||||||
import { useEffect, useMemo, useRef } from "react";
|
import { Suspense, useEffect, useMemo, useRef } from "react";
|
||||||
import { api } from "../../../core/blitzkit/api";
|
import { api } from "../../../core/blitzkit/api";
|
||||||
import { defaultEqualizer } from "../../../core/blitzkit/tankToDuelMember";
|
import { defaultEqualizer } from "../../../core/blitzkit/tankToDuelMember";
|
||||||
import { useFullScreen } from "../../../hooks/useFullScreen";
|
import { useFullScreen } from "../../../hooks/useFullScreen";
|
||||||
@@ -20,6 +20,7 @@ export function HeroSection({ skeleton }: MaybeSkeletonComponentProps) {
|
|||||||
const canvas = useRef<HTMLCanvasElement>(null!);
|
const canvas = useRef<HTMLCanvasElement>(null!);
|
||||||
const isFullScreen = useFullScreen();
|
const isFullScreen = useFullScreen();
|
||||||
const protagonist = Duel.use((state) => state.protagonist.tank);
|
const protagonist = Duel.use((state) => state.protagonist.tank);
|
||||||
|
const modelRequested = Tankopedia.use((state) => state.modelRequested);
|
||||||
const thicknessRange = useMemo(() => {
|
const thicknessRange = useMemo(() => {
|
||||||
const entries = Object.values(tankDefinitions.tanks);
|
const entries = Object.values(tankDefinitions.tanks);
|
||||||
const filtered = entries.filter(
|
const filtered = entries.filter(
|
||||||
@@ -131,13 +132,15 @@ export function HeroSection({ skeleton }: MaybeSkeletonComponentProps) {
|
|||||||
top="0"
|
top="0"
|
||||||
left="0"
|
left="0"
|
||||||
>
|
>
|
||||||
{!skeleton && (
|
{!skeleton && modelRequested && (
|
||||||
<TankSandbox ref={canvas} thicknessRange={thicknessRange} />
|
<Suspense>
|
||||||
|
<TankSandbox ref={canvas} thicknessRange={thicknessRange} />
|
||||||
|
</Suspense>
|
||||||
)}
|
)}
|
||||||
</Box>
|
</Box>
|
||||||
</Box>
|
</Box>
|
||||||
|
|
||||||
<Title />
|
<Title skeleton={skeleton} />
|
||||||
|
|
||||||
<Options
|
<Options
|
||||||
skeleton={skeleton}
|
skeleton={skeleton}
|
||||||
|
|||||||
@@ -127,7 +127,7 @@ export function Node({ id, highlight, nextIds, skeleton }: NodeProps) {
|
|||||||
</Text>
|
</Text>
|
||||||
</Flex>
|
</Flex>
|
||||||
|
|
||||||
{averages && nextTanks && tank.tier !== 10 && (
|
{averages && nextTanks && (
|
||||||
<Text color="gray" size="1" mt="2">
|
<Text color="gray" size="1" mt="2">
|
||||||
{skeleton && <Skeleton height="1em" width="4em" />}
|
{skeleton && <Skeleton height="1em" width="4em" />}
|
||||||
{!skeleton &&
|
{!skeleton &&
|
||||||
|
|||||||
@@ -191,7 +191,7 @@ export function TechTreeSection({ skeleton }: MaybeSkeletonComponentProps) {
|
|||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
|
|
||||||
{master.tier < 10 && (
|
{master.successors.length > 0 && (
|
||||||
<>
|
<>
|
||||||
<Arrow />
|
<Arrow />
|
||||||
{master.successors!.map((id, index) => (
|
{master.successors!.map((id, index) => (
|
||||||
|
|||||||
@@ -0,0 +1,12 @@
|
|||||||
|
import { times } from "lodash-es";
|
||||||
|
import { api } from "../blitzkit/api";
|
||||||
|
|
||||||
|
export const awaitableTiers = api.tankDefinitions().then((tankDefinitions) => {
|
||||||
|
let max = 0;
|
||||||
|
|
||||||
|
for (const tank of Object.values(tankDefinitions.tanks)) {
|
||||||
|
if (tank.tier > max) max = tank.tier;
|
||||||
|
}
|
||||||
|
|
||||||
|
return times(max, (index) => max - index);
|
||||||
|
});
|
||||||
@@ -3,11 +3,13 @@ import { useRef } from "react";
|
|||||||
|
|
||||||
export function useStableProgress() {
|
export function useStableProgress() {
|
||||||
const { loaded, total } = useProgress();
|
const { loaded, total } = useProgress();
|
||||||
|
const baseline = useRef(loaded);
|
||||||
const progress = useRef(0);
|
const progress = useRef(0);
|
||||||
|
const pending = total - baseline.current;
|
||||||
|
|
||||||
progress.current = Math.max(
|
progress.current = Math.max(
|
||||||
progress.current,
|
progress.current,
|
||||||
total === 0 ? 0 : (loaded / total) * 100
|
pending <= 0 ? 0 : ((loaded - baseline.current) / pending) * 100
|
||||||
);
|
);
|
||||||
|
|
||||||
return progress.current;
|
return progress.current;
|
||||||
|
|||||||
@@ -18,6 +18,10 @@ export function Page({ locale }: LocaleAcceptorProps) {
|
|||||||
|
|
||||||
function Content({ locale }: LocaleAcceptorProps) {
|
function Content({ locale }: LocaleAcceptorProps) {
|
||||||
const developerMode = App.useDeferred((state) => state.developerMode, false);
|
const developerMode = App.useDeferred((state) => state.developerMode, false);
|
||||||
|
const autoLoadModels = App.useDeferred(
|
||||||
|
(state) => state.autoLoadModels,
|
||||||
|
true,
|
||||||
|
);
|
||||||
const { strings } = useLocale();
|
const { strings } = useLocale();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@@ -36,6 +40,19 @@ function Content({ locale }: LocaleAcceptorProps) {
|
|||||||
/>
|
/>
|
||||||
</Flex>
|
</Flex>
|
||||||
|
|
||||||
|
<Flex align="center" gap="2" justify="between">
|
||||||
|
<Text>{strings.website.settings.auto_load_models}</Text>
|
||||||
|
<Switch
|
||||||
|
variant="classic"
|
||||||
|
checked={autoLoadModels}
|
||||||
|
onCheckedChange={(checked) =>
|
||||||
|
App.mutate((draft) => {
|
||||||
|
draft.autoLoadModels = checked;
|
||||||
|
})
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
</Flex>
|
||||||
|
|
||||||
<Flex align="center" gap="2" justify="between">
|
<Flex align="center" gap="2" justify="between">
|
||||||
<Text>{strings.website.settings.language}</Text>
|
<Text>{strings.website.settings.language}</Text>
|
||||||
<LocaleSwitcher locale={locale} />
|
<LocaleSwitcher locale={locale} />
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ export interface WargamingLogin {
|
|||||||
|
|
||||||
export interface App {
|
export interface App {
|
||||||
developerMode: boolean;
|
developerMode: boolean;
|
||||||
|
autoLoadModels: boolean;
|
||||||
policiesAgreementIndex: number;
|
policiesAgreementIndex: number;
|
||||||
logins: {
|
logins: {
|
||||||
wargaming?: WargamingLogin;
|
wargaming?: WargamingLogin;
|
||||||
@@ -17,6 +18,7 @@ export interface App {
|
|||||||
export const App = new Varuna<App>(
|
export const App = new Varuna<App>(
|
||||||
{
|
{
|
||||||
developerMode: false,
|
developerMode: false,
|
||||||
|
autoLoadModels: true,
|
||||||
policiesAgreementIndex: -1,
|
policiesAgreementIndex: -1,
|
||||||
logins: {},
|
logins: {},
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -1,6 +1,8 @@
|
|||||||
import type { TankDefinition } from "@blitzkit/core";
|
import type { TankDefinition } from "@blitzkit/core";
|
||||||
import { times } from "lodash-es";
|
|
||||||
import { Varuna } from "varuna";
|
import { Varuna } from "varuna";
|
||||||
|
import { awaitableTiers } from "../core/awaitables/tiers";
|
||||||
|
|
||||||
|
const tiers = await awaitableTiers;
|
||||||
|
|
||||||
export enum GuessState {
|
export enum GuessState {
|
||||||
Correct,
|
Correct,
|
||||||
@@ -25,5 +27,5 @@ export const Guess = new Varuna<Guess, TankDefinition>((tank) => ({
|
|||||||
correctGuesses: 0,
|
correctGuesses: 0,
|
||||||
streak: 0,
|
streak: 0,
|
||||||
helpingReveal: false,
|
helpingReveal: false,
|
||||||
tiers: times(10, (index) => index + 1),
|
tiers,
|
||||||
}));
|
}));
|
||||||
@@ -9,6 +9,7 @@ import type { ArmorType } from "../components/Armor/components/SpacedArmorScene"
|
|||||||
import type { ExternalModuleVariant } from "../components/Armor/components/SpacedArmorSceneComponent";
|
import type { ExternalModuleVariant } from "../components/Armor/components/SpacedArmorSceneComponent";
|
||||||
import type { XP_MULTIPLIERS } from "../components/Tankopedia/TechTreeSection";
|
import type { XP_MULTIPLIERS } from "../components/Tankopedia/TechTreeSection";
|
||||||
import { api } from "../core/blitzkit/api";
|
import { api } from "../core/blitzkit/api";
|
||||||
|
import { App } from "./app";
|
||||||
import { TankopediaDisplay } from "./tankopediaPersistent/constants";
|
import { TankopediaDisplay } from "./tankopediaPersistent/constants";
|
||||||
|
|
||||||
export interface ShotLayerBase {
|
export interface ShotLayerBase {
|
||||||
@@ -79,6 +80,7 @@ export enum TankopediaRelativeAgainst {
|
|||||||
interface Tankopedia {
|
interface Tankopedia {
|
||||||
disturbed: boolean;
|
disturbed: boolean;
|
||||||
revealed: boolean;
|
revealed: boolean;
|
||||||
|
modelRequested: boolean;
|
||||||
shot?: Shot;
|
shot?: Shot;
|
||||||
skills: Record<string, number>;
|
skills: Record<string, number>;
|
||||||
relativeAgainst: TankopediaRelativeAgainst;
|
relativeAgainst: TankopediaRelativeAgainst;
|
||||||
@@ -110,6 +112,7 @@ const skillDefinitions = await api.skillDefinitions();
|
|||||||
export const Tankopedia = new Varuna<Tankopedia, ModelDefinition>((model) => ({
|
export const Tankopedia = new Varuna<Tankopedia, ModelDefinition>((model) => ({
|
||||||
disturbed: false,
|
disturbed: false,
|
||||||
revealed: false,
|
revealed: false,
|
||||||
|
modelRequested: App.state.autoLoadModels,
|
||||||
relativeAgainst: TankopediaRelativeAgainst.Class,
|
relativeAgainst: TankopediaRelativeAgainst.Class,
|
||||||
editStatic: false,
|
editStatic: false,
|
||||||
skills: createDefaultSkills(skillDefinitions),
|
skills: createDefaultSkills(skillDefinitions),
|
||||||
|
|||||||
Reference in new issue
Block a user