Files
ark-stronghold-protocol/test/content/feedback5-swire2-revive-cost.test.js
T
sganggs 806a047717 feedback6 R21P: every operator fights at full potential (潜能 6) — the owner's decision of 2026-10-07 (GitHub #252, PR #255; no host slider): tools/build-data.mjs OPERATOR_POTENTIAL adds every character_table potentialRanks attribute step (部署费用 / 再部署时间 / ATK / HP / DEF / RES / ASPD, all ADDITION, before rounding) to every chess (normal and elite), 补位 and 自选 unit form and picks talent / trait / module-talent candidates up to requiredPotentialRank 5 (「天赋效果增强」); a summon picks its talent candidates at its owner's potential (their requiredPotentialRank mirrors the owner's — PRTS 凯尔希: Mon3tr 3.5 s / 1400) and takes none of the owner's attribute steps; the 原型干员 stand-ins have no potential ranks (unchanged). 刺玫 413 / 17 → 435 / 15 as in the tournament video, 砾 18 → 16 s, 至简 80 → 70 s. data/chess.json (256 records), backups.json (the 71 owned picks, 8 summons), tokens.json (5 summons) and the data translations en / ja / ko / zh-TW rebuilt — only potential-driven fields (JSON-compared); the 干员调配 局内数值 and detail cards read the records. op-wang.js reads her stock cap 「最多拥有8(+1)枚」 through the potential step (the pattern fell back to 7: she sat at the cap from the start). Docs: DATA §2 / §18 / tokens, PLAYING (detail card), research 03, kits README, shared/diy.js / standIn.js, the 71 自选 kit headers and the kit comments that quoted potential-0 numbers. Tests: test/full-potential.test.js (new, fails on the parent); data.test.js re-derivation adds the potential steps (+ respawnTime); every test that hard-coded a potential-0 number carries the full-potential one (from the data and the test's own formula; no check loosened); golden: moves almost everywhere — roster 49/49, bonds 46/46, fields 22/22, matches 18/18, diy 133/138 (each battle parts on a stat: roster-001 / roster-020 at tick 1 on 角峰's HP (生命上限+250), bond-arcaneShip-high at 4.73 s and diy-001 at 3.70 s on an enemy's HP from a higher ATK; diy-110 / 111 also by 望's cap; the matches through those battles); unchanged: standins 10/10 and diy-135…138 (no potential ranks), diy-012 (twelve 夜莺 never hit, never redeployed)
2026-10-07 18:35:39 +08:00

45 lines
2.3 KiB
JavaScript

// test/content/feedback5-swire2-revive-cost.test.js — 琳琅诗怀雅's 破财消灾 (「受到致命伤害时,若费用足够则消耗5点部署费用使生命恢复到
// 70%,每次触发该天赋时消耗的费用翻倍」; 80 % at full potential, the owner's decision of 2026-10-07): the doubled cost restarts at 5 with every deployment — PRTS 备注 「再部署时重置本天赋费用
// 消耗」 (community report of 2026-10-06 「进入联防阶段琳琅诗怀雅所需的复活费用应该重置,正常对局中死亡之后再部署复活费用也应该
// 重置」). A 联防 field is a battle of its own, so it always started at 5; a redeploy used to keep the doubled cost.
// Run: node --test test/content/feedback5-swire2-revive-cost.test.js
import { test } from 'node:test';
import assert from 'node:assert/strict';
import { makeBattle, checkInvariants } from '../helpers/battleHarness.js';
const ID = 'chess_char_3_04_a';
function field(kind = 'normal') {
const h = makeBattle({ kind, units: [{ chessId: ID, row: 10, col: 5 }], timeLimit: 300, autoFinish: false, flags: { dpInit: 60, dpMax: 99 } });
h.step();
return { h, u: h.unit(ID), ps: h.b.getPlayer('p1') };
}
/** A lethal hit with `dp` DP in the pool: returns the DP the talent took (0 when she fell). */
function lethal(h, u, ps, dp = 90) {
ps.dp = dp;
h.b.dealDamage(null, u, { amount: u.s.maxHp * 5, type: 'true', canDodge: false });
return u.alive ? dp - ps.dp : 0;
}
test('破财消灾 doubles within one deployment and restarts at 5 DP after a redeploy', () => {
const { h, u, ps } = field();
assert.equal(lethal(h, u, ps), 5, 'first save: 5 DP');
assert.ok(u.alive && Math.abs(u.hp - u.s.maxHp * 0.8) < 1e-6, 'back to 80 % HP (hp_ratio at full potential)');
assert.equal(lethal(h, u, ps), 10, 'second save of the same deployment: doubled');
h.b.retreat(u);
assert.ok(!u.alive);
ps.dp = 90;
assert.ok(h.runUntil(() => u.alive && u.deployed, 120), 'redeployed');
assert.equal(lethal(h, u, ps), 5, 'after the redeploy: 5 DP again (it used to cost 20)');
checkInvariants(h.b);
assert.equal(h.b.errors.length, 0);
});
test('a 联防 field starts at 5 DP: a battle of its own', () => {
const { h, u, ps } = field('unite');
assert.equal(lethal(h, u, ps), 5);
assert.equal(lethal(h, u, ps), 10);
});