feat(editor): WTSC JSON round-trip closure

Adds --export-wtsc-json / --import-wtsc-json with the established
readEnumField template factoring int+name dual encoding for both
vehicleType ("taxi"/"zeppelin"/"boat"/"mount") and factionAccess
("both"/"alliance"/"horde"/"neutral"). Float coordinates
(originX/Y, destinationX/Y) preserved bit-for-bit through JSON.

All 3 presets (zeppelins/boats/taxis) byte-identical binary
roundtrip OK including BootyBay<->Ratchet Neutral cross-faction
boat coords (-14305.f, 570.f -> -984.f, -3835.f).

Live-tested scheduling-overflow detection: hand-mutated routeId=2
(OG<->Grom'Gol travel=90s capacity=40) interval to 60s, validator
correctly errored: "departureIntervalSec=60 < travelDurationSec=90
with finite capacity — vehicle pool overflow (next zeppelin
departs before prior arrives)".

CLI flag count 1353 -> 1355.
This commit is contained in:
Kelsi 2026-05-10 03:57:15 -07:00
parent 12e77e69ce
commit 85ac2e0248
3 changed files with 199 additions and 0 deletions

View file

@ -2555,6 +2555,10 @@ void printUsage(const char* argv0) {
std::printf(" Print WTSC entries (id / vehicleType / factionAccess / departureIntervalSec / travelDurationSec / capacity / name)\n");
std::printf(" --validate-wtsc <wtsc-base> [--json]\n");
std::printf(" Static checks: id+name+origin+destination required, vehicleType 0..3, factionAccess 0..3, no zero intervals/travel, no duplicate routeIds, no duplicate route names; CRITICAL scheduling invariant: when capacity > 0 the departureInterval >= travelDuration (else vehicle pool overflow — next zeppelin departs before prior arrives). Warns on same-map routes (originMapId == destinationMapId) — verify intentional\n");
std::printf(" --export-wtsc-json <wtsc-base> [out.json]\n");
std::printf(" Export binary .wtsc to a human-editable JSON sidecar (defaults to <base>.wtsc.json; emits both vehicleType and factionAccess as int + name string; floats preserved bit-for-bit)\n");
std::printf(" --import-wtsc-json <json-path> [out-base]\n");
std::printf(" Import a .wtsc.json sidecar back into binary .wtsc (vehicleType int OR \"taxi\"/\"zeppelin\"/\"boat\"/\"mount\"; factionAccess int OR \"both\"/\"alliance\"/\"horde\"/\"neutral\")\n");
std::printf(" --catalog-pluck <wXXX-file> <id> [--json]\n");
std::printf(" Extract one entry by id from any registered catalog format. Auto-detects magic, dispatches to the per-format --info-* handler internally, then prints just the matching entry. Primary-key field is auto-detected (first *Id field, or first numeric)\n");
std::printf(" --catalog-find <directory> <id> [--magic <WXXX>] [--json]\n");