mirror of
https://github.com/blitzkit/blitzkit.git
synced 2026-10-21 10:47:04 +02:00
feat: read dvpl
This commit is contained in:
1 parent
ad0fc69596
commit
4bfe34ba53
5 files changed
+121
-24
No files matched your search
Vendored
+3
@@ -10,6 +10,8 @@
|
||||
"customperiod",
|
||||
"deburr",
|
||||
"diacriticless",
|
||||
"dvpl",
|
||||
"DVPLCRC",
|
||||
"Everytime",
|
||||
"fullstats",
|
||||
"fuzzysort",
|
||||
@@ -38,6 +40,7 @@
|
||||
"Smri",
|
||||
"startcase",
|
||||
"statsfull",
|
||||
"steamapps",
|
||||
"Stringifying",
|
||||
"strvk",
|
||||
"subnation",
|
||||
|
||||
@@ -65,12 +65,15 @@
|
||||
"@types/express": "^4.17.18",
|
||||
"@types/js-yaml": "^4.0.8",
|
||||
"@types/lodash": "^4.14.199",
|
||||
"@types/lz4": "^0.6.4",
|
||||
"@types/markdown-escape": "^1.1.0",
|
||||
"@types/node": "^20.6.5",
|
||||
"@types/react": "^18.2.22",
|
||||
"@vanilla-extract/next-plugin": "^2.3.1",
|
||||
"compare-versions": "^6.1.0",
|
||||
"crc": "^4.3.2",
|
||||
"knip": "^3.4.0",
|
||||
"lz4": "^0.6.5",
|
||||
"prettier": "^3.0.3",
|
||||
"prisma": "^5.4.1",
|
||||
"typescript": "^5.2.2"
|
||||
|
||||
+25
-24
@@ -1,13 +1,13 @@
|
||||
import { Octokit } from '@octokit/rest';
|
||||
import decompress from 'decompress';
|
||||
import { config } from 'dotenv';
|
||||
import { writeFileSync } from 'fs';
|
||||
import { readFile, readdir, rm } from 'fs/promises';
|
||||
import { readFile, readdir } from 'fs/promises';
|
||||
import { load } from 'js-yaml';
|
||||
import { argv, env } from 'process';
|
||||
import { ElementCompact, xml2js } from 'xml-js';
|
||||
import { parse } from 'yaml';
|
||||
import { NATION_IDS } from '../src/constants/nations';
|
||||
import { readDVPL } from '../src/core/blitz/readDVPL';
|
||||
import {
|
||||
TankDefinitions,
|
||||
Tier,
|
||||
@@ -16,39 +16,40 @@ import commitMultipleFiles, { FileChange } from './commitMultipleFiles';
|
||||
|
||||
config();
|
||||
|
||||
const DATA =
|
||||
'C:/Program Files (x86)/Steam/steamapps/common/World of Tanks Blitz/Data';
|
||||
const LANGUAGE = 'en';
|
||||
const TEMP = 'temp/blitz';
|
||||
|
||||
const publish = argv.includes('--publish');
|
||||
const apkFile = argv
|
||||
.find((argument) => argument.startsWith('--file'))
|
||||
?.split('=')[1];
|
||||
const noRewrite = argv.includes('--no-rewrite');
|
||||
const targets = argv
|
||||
.find((argument) => argument.startsWith('--target'))
|
||||
?.split('=')[1]
|
||||
.split(',');
|
||||
|
||||
if (!apkFile) throw new Error('No file specified');
|
||||
if (!targets) throw new Error('No target(s) specified');
|
||||
|
||||
const directoriesOfInterest = {
|
||||
vehicleDefinitions: 'assets/Data/XML/item_defs/vehicles',
|
||||
strings: 'assets/Data/Strings',
|
||||
tankParameters: 'assets/Data/3d/Tanks/Parameters',
|
||||
smallIcons: 'assets/Data/Gfx/UI/BattleScreenHUD/SmallTankIcons',
|
||||
bigIcons: 'assets/Data/Gfx/UI/BigTankIcons',
|
||||
flags: 'assets/Data/Gfx/Lobby/flags',
|
||||
vehicleDefinitions: 'XML/item_defs/vehicles',
|
||||
strings: 'Strings',
|
||||
tankParameters: '3d/Tanks/Parameters',
|
||||
smallIcons: 'Gfx/UI/BattleScreenHUD/SmallTankIcons',
|
||||
bigIcons: 'Gfx/UI/BigTankIcons',
|
||||
flags: 'Gfx/Lobby/flags',
|
||||
};
|
||||
const directoriesOfInterestArray = Object.values(directoriesOfInterest);
|
||||
|
||||
if (!noRewrite) {
|
||||
await rm(TEMP, { recursive: true, force: true });
|
||||
await decompress(apkFile, TEMP, {
|
||||
filter: (file) =>
|
||||
directoriesOfInterestArray.some((dir) => file.path.startsWith(dir)),
|
||||
});
|
||||
}
|
||||
console.log(
|
||||
(
|
||||
await readDVPL(
|
||||
`${DATA}/${directoriesOfInterest.strings}/${LANGUAGE}.yaml.dvpl`,
|
||||
)
|
||||
).toString(),
|
||||
);
|
||||
throw new Error('stop');
|
||||
|
||||
const strings = await readFile(
|
||||
`${TEMP}/${directoriesOfInterest.strings}/${LANGUAGE}.yaml`,
|
||||
`${DATA}/${directoriesOfInterest.strings}/${LANGUAGE}.yaml.dvpl`,
|
||||
'utf-8',
|
||||
).then((data) => load(data) as Record<string, string>);
|
||||
|
||||
const tankDefinitions: TankDefinitions = {};
|
||||
const tankIds: number[] = [];
|
||||
const images: Record<number, { big: string; small: string }> = {};
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
import { crc32 } from 'crc';
|
||||
import { readFile } from 'fs/promises';
|
||||
import { decodeBlock } from 'lz4';
|
||||
|
||||
/**
|
||||
* Thanks Maddoxkkm! Modernized heavily.
|
||||
*
|
||||
* https://github.com/Maddoxkkm/dvpl_converter/
|
||||
*/
|
||||
export async function readDVPL(file: string) {
|
||||
const buffer = await readFile(file);
|
||||
const footerBuffer = buffer.slice(buffer.length - 20, buffer.length);
|
||||
|
||||
if (
|
||||
footerBuffer.toString('utf8', 16, 20) !== 'DVPL' ||
|
||||
footerBuffer.length !== 20
|
||||
) {
|
||||
throw 'InvalidDVPLFooter';
|
||||
}
|
||||
|
||||
const footerData = {
|
||||
oSize: footerBuffer.readUInt32LE(0),
|
||||
cSize: footerBuffer.readUInt32LE(4),
|
||||
crc32: footerBuffer.readUInt32LE(8),
|
||||
type: footerBuffer.readUInt32LE(12),
|
||||
};
|
||||
const targetBlock = buffer.slice(0, buffer.length - 20);
|
||||
|
||||
if (targetBlock.length !== footerData.cSize) throw 'DVPLSizeMismatch';
|
||||
if (crc32(targetBlock) !== footerData.crc32) throw 'DVPLCRC32Mismatch';
|
||||
if (footerData.type === 0) {
|
||||
if (!(footerData.oSize === footerData.cSize && footerData.type === 0)) {
|
||||
throw 'DVPLTypeSizeMismatch';
|
||||
}
|
||||
|
||||
return targetBlock;
|
||||
} else if (footerData.type === 1 || footerData.type === 2) {
|
||||
const deDVPLBlock = Buffer.alloc(footerData.oSize);
|
||||
const DecompressedBlockSize = decodeBlock(targetBlock, deDVPLBlock);
|
||||
|
||||
if (DecompressedBlockSize !== footerData.oSize) {
|
||||
throw 'DVPLDecodeSizeMismatch';
|
||||
}
|
||||
|
||||
return deDVPLBlock;
|
||||
} else {
|
||||
throw new TypeError('Unknown DVPL format');
|
||||
}
|
||||
}
|
||||
@@ -2027,6 +2027,13 @@
|
||||
resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.202.tgz#f09dbd2fb082d507178b2f2a5c7e74bd72ff98f8"
|
||||
integrity sha512-OvlIYQK9tNneDlS0VN54LLd5uiPCBOp7gS5Z0f1mjoJYBrtStzgmJBxONW3U6OZqdtNzZPmn9BS/7WI7BFFcFQ==
|
||||
|
||||
"@types/lz4@^0.6.4":
|
||||
version "0.6.4"
|
||||
resolved "https://registry.yarnpkg.com/@types/lz4/-/lz4-0.6.4.tgz#eba8c0bb9e6a997e78107092953c8cfa92733a46"
|
||||
integrity sha512-vvxMIkowyHbY6zkCantyYwAK83N5E04bzFZSPJICG1SDpaL89L7lObs9DhLuhJhXHCQMkjzN3LYoAH6LjfwMFQ==
|
||||
dependencies:
|
||||
"@types/node" "*"
|
||||
|
||||
"@types/markdown-escape@^1.1.0":
|
||||
version "1.1.3"
|
||||
resolved "https://registry.yarnpkg.com/@types/markdown-escape/-/markdown-escape-1.1.3.tgz#b880ab7c1e23c76b1d663e5a5640107c493e0c3e"
|
||||
@@ -2781,6 +2788,11 @@ core-util-is@~1.0.0:
|
||||
resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.3.tgz#a6042d3634c2b27e9328f837b965fac83808db85"
|
||||
integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==
|
||||
|
||||
crc@^4.3.2:
|
||||
version "4.3.2"
|
||||
resolved "https://registry.yarnpkg.com/crc/-/crc-4.3.2.tgz#49b7821cbf2cf61dfd079ed93863bbebd5469b9a"
|
||||
integrity sha512-uGDHf4KLLh2zsHa8D8hIQ1H/HtFQhyHrc0uhHBcoKGol/Xnb+MPYfUMw7cvON6ze/GUESTudKayDcJC5HnJv1A==
|
||||
|
||||
cross-spawn@^7.0.0:
|
||||
version "7.0.3"
|
||||
resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6"
|
||||
@@ -2834,6 +2846,11 @@ csstype@^3.0.2, csstype@^3.0.7, csstype@^3.1.2:
|
||||
resolved "https://registry.yarnpkg.com/csstype/-/csstype-3.1.2.tgz#1d4bf9d572f11c14031f0436e1c10bc1f571f50b"
|
||||
integrity sha512-I7K1Uu0MBPzaFKg4nI5Q7Vs2t+3gWWW648spaF+Rg7pI9ds18Ugn+lvg4SHczUdKlHI5LWBXyqfS8+DufyBsgQ==
|
||||
|
||||
cuint@^0.2.2:
|
||||
version "0.2.2"
|
||||
resolved "https://registry.yarnpkg.com/cuint/-/cuint-0.2.2.tgz#408086d409550c2631155619e9fa7bcadc3b991b"
|
||||
integrity sha512-d4ZVpCW31eWwCMe1YT3ur7mUDnTXbgwyzaL320DrcRT45rfjYxkt5QWLrmOJ+/UEAI2+fQgKe/fCjR8l4TpRgw==
|
||||
|
||||
data-uri-to-buffer@^3.0.1:
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/data-uri-to-buffer/-/data-uri-to-buffer-3.0.1.tgz#594b8973938c5bc2c33046535785341abc4f3636"
|
||||
@@ -3937,6 +3954,16 @@ lru-cache@^6.0.0:
|
||||
dependencies:
|
||||
yallist "^4.0.0"
|
||||
|
||||
lz4@^0.6.5:
|
||||
version "0.6.5"
|
||||
resolved "https://registry.yarnpkg.com/lz4/-/lz4-0.6.5.tgz#ae8b7522681b6ab155023e6c56bf73087090122b"
|
||||
integrity sha512-KSZcJU49QZOlJSItaeIU3p8WoAvkTmD9fJqeahQXNu1iQ/kR0/mQLdbrK8JY9MY8f6AhJoMrihp1nu1xDbscSQ==
|
||||
dependencies:
|
||||
buffer "^5.2.1"
|
||||
cuint "^0.2.2"
|
||||
nan "^2.13.2"
|
||||
xxhashjs "^0.2.2"
|
||||
|
||||
magic-bytes.js@^1.5.0:
|
||||
version "1.6.0"
|
||||
resolved "https://registry.yarnpkg.com/magic-bytes.js/-/magic-bytes.js-1.6.0.tgz#ee4354ac41a9b86f410e2690bc25dc4c264fb55d"
|
||||
@@ -4168,6 +4195,11 @@ [email protected]:
|
||||
resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2"
|
||||
integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==
|
||||
|
||||
nan@^2.13.2:
|
||||
version "2.18.0"
|
||||
resolved "https://registry.yarnpkg.com/nan/-/nan-2.18.0.tgz#26a6faae7ffbeb293a39660e88a76b82e30b7554"
|
||||
integrity sha512-W7tfG7vMOGtD30sHoZSSc/JVYiyDPEyQVso/Zz+/uQd0B0L46gtC+pHha5FFMRpil6fm/AoEcRWyOVi4+E/f8w==
|
||||
|
||||
nanoid@^3.3.6, nanoid@^3.3.7:
|
||||
version "3.3.7"
|
||||
resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.7.tgz#d0c301a691bc8d54efa0a2226ccf3fe2fd656bd8"
|
||||
@@ -4896,6 +4928,7 @@ streamsearch@^1.1.0:
|
||||
integrity sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==
|
||||
|
||||
"string-width-cjs@npm:string-width@^4.2.0", string-width@^4.1.0:
|
||||
name string-width-cjs
|
||||
version "4.2.3"
|
||||
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
|
||||
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
|
||||
@@ -4946,6 +4979,7 @@ stringify-entities@^4.0.0:
|
||||
character-entities-legacy "^3.0.0"
|
||||
|
||||
"strip-ansi-cjs@npm:strip-ansi@^6.0.1", strip-ansi@^6.0.0, strip-ansi@^6.0.1:
|
||||
name strip-ansi-cjs
|
||||
version "6.0.1"
|
||||
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
|
||||
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
|
||||
@@ -5460,6 +5494,13 @@ xtend@^4.0.0:
|
||||
resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.2.tgz#bb72779f5fa465186b1f438f674fa347fdb5db54"
|
||||
integrity sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==
|
||||
|
||||
xxhashjs@^0.2.2:
|
||||
version "0.2.2"
|
||||
resolved "https://registry.yarnpkg.com/xxhashjs/-/xxhashjs-0.2.2.tgz#8a6251567621a1c46a5ae204da0249c7f8caa9d8"
|
||||
integrity sha512-AkTuIuVTET12tpsVIQo+ZU6f/qDmKuRUcjaqR+OIvm+aCBsZ95i7UVY5WJ9TMsSaZ0DA2WxoZ4acu0sPH+OKAw==
|
||||
dependencies:
|
||||
cuint "^0.2.2"
|
||||
|
||||
yallist@^3.0.2:
|
||||
version "3.1.1"
|
||||
resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd"
|
||||
|
||||
Reference in new issue
Block a user