Files
ark-stronghold-protocol/public/js/render/promote.js
T
sganggs 620f88c0d8 Playtest #6 follow-up (v2.5.1): leader HP review — 直接乘算, one debuff instance, 999 layer cap, 限伤; elite to the board; 假想敌:胄 kit
- co-op leaders died within seconds: leader HP is the official data (40 values pinned); bond / strategy / item /
  机变 / 特质 "+X%" bonuses now add up (PRTS 直接乘算) instead of compounding; a same-named enemy debuff keeps one
  (strongest) instance per target (奥术 across a pair field); leader parts pass damage 1:1; fixed co-op pool (the user's call)
- official limits read from the client: each bond stops at 999 layers (MAX_GARRISON_STACK); a leader hit of 300000+ in
  boss / hidden battles is cancelled (MAX_BATTLE_DAMAGE, 限伤) — shared/constants.js switches, research 11
- a merge that consumes a deployed copy puts the elite on that tile and facing (user-confirmed); gold target highlight,
  promotion effect
- 假想敌:胄 per PRTS: one shell, shells within range, any drone death costs 2 % max HP, 剑/锤 sorties and 瘫痪
- DESIGN §20.10–§20.14; 2842 unit tests, all 28 browser suites green; Chrome = Node on boss fields
2026-10-02 04:19:28 +08:00

35 lines
2.1 KiB
JavaScript

// public/js/render/promote.js — which prep pieces were just promoted (精锐晋升), for the merge cue of render/app.js setPrep.
//
// A merge replaces the consumed normal copies by ONE new elite piece in the same m.private update: on the board tile of
// the consumed copy that deploys first when a copy was deployed (PRTS 卫戍协议/帮助 "若消耗已部署至作战区的干员,则发送至
// 作战区对应位置"; server board.js mergeTile), else in the hand / temp. So a promotion = a chess piece with a new uid that is
// an elite, while normal copies of the same operator (same baseId) vanished from the previous state. The cue then plays
// on the elite (fx.promote: gold pillar + rings, streaks from the vanished copies) instead of the plain deploy flash.
/**
* @param {Array<{ uid: number, area: string, piece: any }>} prev entries of the previous setPrep (render/app.js prepPieces)
* @param {Array<{ uid: number, area: string, piece: any }>} next entries of this setPrep
* @param {(id: string) => any} chessOf chess record lookup (`baseId`, `isGolden`)
* @returns {Map<number, Array<{ uid: number, area: string, piece: any }>>} new elite uid → the vanished copies (prev entries)
*/
export function promotionsOf(prev, next, chessOf) {
const out = new Map();
if (!Array.isArray(prev) || !prev.length || !Array.isArray(next)) return out;
const before = new Set(prev.map((e) => e.uid));
const now = new Set(next.map((e) => e.uid));
const baseOf = (id) => chessOf(id)?.baseId || id;
const isElite = (p) => !!(p?.golden || chessOf(p?.id)?.isGolden);
const gone = prev.filter((e) => e.piece?.kind === 'chess' && !now.has(e.uid) && !isElite(e.piece));
if (!gone.length) return out;
const used = new Set();
for (const e of next) {
if (e.piece?.kind !== 'chess' || before.has(e.uid) || !isElite(e.piece)) continue;
const base = baseOf(e.piece.id);
const copies = gone.filter((g) => !used.has(g.uid) && baseOf(g.piece.id) === base);
if (!copies.length) continue;
for (const g of copies) used.add(g.uid);
out.set(e.uid, copies);
}
return out;
}