Update Healer Man server
This commit is contained in:
1 parent
a64b2cb575
commit
71246e5b75
502 files changed
+4245
-19
No files matched your search
@@ -1,5 +1,6 @@
|
||||
import assert from "node:assert/strict";
|
||||
import fs from "node:fs";
|
||||
import os from "node:os";
|
||||
import path from "node:path";
|
||||
import test from "node:test";
|
||||
import { fileURLToPath } from "node:url";
|
||||
@@ -8,6 +9,7 @@ import {
|
||||
decodeWotlkSpellVisualKitRow,
|
||||
parseDbc,
|
||||
parseRunewakerImageRecords,
|
||||
runewakerSoundPathsForModel,
|
||||
} from "./generate-manifest.mjs";
|
||||
|
||||
const projectRoot = path.resolve(path.dirname(fileURLToPath(import.meta.url)), "..", "..");
|
||||
@@ -180,6 +182,26 @@ test("classifies paths from fixed RuneWaker ImageObject records", () => {
|
||||
assert.deepEqual(records.get(573727), ["model/fx/skill/fire/act_fireball01_f_i.ros"]);
|
||||
});
|
||||
|
||||
test("matches RuneWaker sound siblings without guessing unrelated cues", () => {
|
||||
const root = fs.mkdtempSync(path.join(os.tmpdir(), "rom-sound-fixture-"));
|
||||
try {
|
||||
const soundRoot = path.join(root, "sound", "fx", "skill", "fire");
|
||||
fs.mkdirSync(soundRoot, { recursive: true });
|
||||
fs.writeFileSync(path.join(soundRoot, "act_fireball_t_hit.ros.mp3"), "fixture");
|
||||
assert.deepEqual(runewakerSoundPathsForModel(
|
||||
"model/fx/skill/fire/act_fireball_t_hit.ros", root,
|
||||
), ["sound/fx/skill/fire/act_fireball_t_hit.ros.mp3"]);
|
||||
assert.deepEqual(runewakerSoundPathsForModel(
|
||||
"model/fx/skill/fire/act_other_t_hit.ros", root,
|
||||
), []);
|
||||
assert.deepEqual(runewakerSoundPathsForModel(
|
||||
"model/../../sound/fx/skill/fire/act_fireball_t_hit.ros", root,
|
||||
), []);
|
||||
} finally {
|
||||
fs.rmSync(root, { recursive: true, force: true });
|
||||
}
|
||||
});
|
||||
|
||||
test("decodes WotLK MD20 particle tracks from their real record offsets", () => {
|
||||
const decoded = decodeWotlkM2Effects(wotlkParticleFixture(), "fixture");
|
||||
const particle = decoded.particles[0];
|
||||
@@ -320,3 +342,45 @@ test("generated coverage packages every referenced source sound", () => {
|
||||
assert.ok(fs.existsSync(path.join(projectRoot, "public", sound.url)));
|
||||
}
|
||||
});
|
||||
|
||||
test("primary-five RuneWaker spells retain source phases and packaged sound cues", () => {
|
||||
const manifest = JSON.parse(fs.readFileSync(path.join(projectRoot, "public/assets/game/combat-effects/manifest.json"), "utf8"));
|
||||
const entry = (id) => manifest.entries.find((candidate) => candidate.key === `runewaker:${id}`);
|
||||
assert.ok(entry(490261).phases["cast-start"].some((asset) => asset.model === "model/fx/skill/holy/act_casting_c_hand.ros"));
|
||||
assert.ok(entry(490261).sounds.some((sound) => sound.phase === "cast-start" && sound.url));
|
||||
assert.ok(entry(491128).phases.release.some((asset) => asset.model.includes("act_gustwindarrow_f_hit_point_i.ros")));
|
||||
assert.ok(entry(491128).phases.impact.some((asset) => asset.model.includes("act_gustwindarrow_t_hit_point_e.ros")));
|
||||
assert.ok(entry(490495).sounds.some((sound) => sound.sourcePath === "sound/fx/skill/holy/act_godshield_c_down.mp3"));
|
||||
});
|
||||
|
||||
test("only browser-verified RuneWaker particle phases use original graphs", () => {
|
||||
const manifest = JSON.parse(fs.readFileSync(path.join(projectRoot, "public/assets/game/combat-effects/manifest.json"), "utf8"));
|
||||
const expected = new Set([
|
||||
"491147:cast-start:model/fx/skill/holy/act_casting_c_hand.ros",
|
||||
"490261:cast-start:model/fx/skill/holy/act_casting_c_hand.ros",
|
||||
"490281:cast-start:model/fx/skill/holy/act_casting_c_hand.ros",
|
||||
"490150:cast-start:model/fx/skill/physical/act_charge02_c_down.ros",
|
||||
"490175:impact:model/fx/hit_fx/act_shieldstorm_t_freeze_hit_e.ros",
|
||||
"491168:release:model/fx/skill/wind/act_electric_ball_f_i.ros",
|
||||
]);
|
||||
const actual = new Set();
|
||||
for (const entry of manifest.entries.filter((candidate) => candidate.source === "runewaker")) {
|
||||
for (const [phase, assets] of Object.entries(entry.phases ?? {})) for (const asset of assets) {
|
||||
if (!asset.effectGraphUrl) continue;
|
||||
const key = `${entry.spellId}:${phase}:${asset.model}`;
|
||||
actual.add(key);
|
||||
assert.equal(asset.effectKind, "runewaker-particles");
|
||||
if (entry.spellId === 490175) assert.equal(asset.scale, 2.5);
|
||||
const graph = JSON.parse(fs.readFileSync(path.join(projectRoot, "public", asset.effectGraphUrl.slice(1)), "utf8"));
|
||||
assert.equal(graph.rendererReady, true);
|
||||
assert.equal(graph.sourceModel, asset.model);
|
||||
}
|
||||
}
|
||||
assert.deepEqual(actual, expected);
|
||||
for (const spellId of [491147, 490261, 490281]) {
|
||||
const entry = manifest.entries.find((candidate) => candidate.key === `runewaker:${spellId}`);
|
||||
assert.ok(entry.sounds.some((sound) => sound.phase === "cast-start"
|
||||
&& sound.sourcePath === "sound/fx/skill/holy/act_casting_c_hand.wav"
|
||||
&& sound.loopDuringCast === true));
|
||||
}
|
||||
});
|
||||
Reference in new issue
Block a user