feat(system-gaps): 복합 카드(피해+방어)·런 종료 후 메뉴 복귀(EndRun)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -120,7 +120,8 @@ export function simulateCombat(data, rng, stats) {
|
|||||||
const r = applyDamage(target.hp, target.block, c.damage || 0);
|
const r = applyDamage(target.hp, target.block, c.damage || 0);
|
||||||
target.hp = r.hp; target.block = r.block;
|
target.hp = r.hp; target.block = r.block;
|
||||||
if (target.hp <= 0) target.alive = false;
|
if (target.hp <= 0) target.alive = false;
|
||||||
if (stats) stats[id] = bump(stats[id], c.cost, c.damage || 0, 0);
|
if (c.block) pBlock += c.block;
|
||||||
|
if (stats) stats[id] = bump(stats[id], c.cost, c.damage || 0, c.block || 0);
|
||||||
} else {
|
} else {
|
||||||
pBlock += c.block || 0;
|
pBlock += c.block || 0;
|
||||||
if (stats) stats[id] = bump(stats[id], c.cost, 0, c.block || 0);
|
if (stats) stats[id] = bump(stats[id], c.cost, 0, c.block || 0);
|
||||||
|
|||||||
@@ -118,3 +118,16 @@ test('runBatch: 집계 필드·승률 범위', () => {
|
|||||||
test('runBatch: 동일 시드 동일 결과', () => {
|
test('runBatch: 동일 시드 동일 결과', () => {
|
||||||
assert.deepEqual(runBatch(100, 7), runBatch(100, 7));
|
assert.deepEqual(runBatch(100, 7), runBatch(100, 7));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('simulateCombat: 복합 카드(공격+방어) 블록이 적 공격을 흡수', () => {
|
||||||
|
const data = {
|
||||||
|
cards: { Combo: { name: '콤보', cost: 1, kind: 'Attack', damage: 1, block: 3 } },
|
||||||
|
starterDeck: ['Combo', 'Combo', 'Combo', 'Combo', 'Combo'],
|
||||||
|
monsters: [{ name: '적', maxHp: 9999, intents: [{ kind: 'Attack', value: 9 }] }],
|
||||||
|
};
|
||||||
|
const r = simulateCombat(data, mulberry32(1));
|
||||||
|
// 매 턴 3장(에너지3) → 블록 9 = 적 공격 9 전부 흡수 → 무피해로 MAX_TURNS 도달(draw), HP 유지.
|
||||||
|
// 블록 미적용이면 매턴 -9로 사망(win=false, draw 아님).
|
||||||
|
assert.equal(r.draw, true);
|
||||||
|
assert.equal(r.playerHpRemaining, 80);
|
||||||
|
});
|
||||||
|
|||||||
@@ -2430,6 +2430,9 @@ if c.kind == "Attack" then
|
|||||||
if c.damage ~= nil then
|
if c.damage ~= nil then
|
||||||
self:PlayAttackFx(self.TargetIndex, c.image, c.damage)
|
self:PlayAttackFx(self.TargetIndex, c.image, c.damage)
|
||||||
end
|
end
|
||||||
|
if c.block ~= nil then
|
||||||
|
self.PlayerBlock = self.PlayerBlock + c.block
|
||||||
|
end
|
||||||
self:ApplyRelics("cardPlayed")
|
self:ApplyRelics("cardPlayed")
|
||||||
elseif c.kind == "Skill" then
|
elseif c.kind == "Skill" then
|
||||||
if c.block ~= nil then
|
if c.block ~= nil then
|
||||||
@@ -2653,16 +2656,14 @@ if anyAlive == false then
|
|||||||
self:TeleportToActMap()
|
self:TeleportToActMap()
|
||||||
self:ShowMap()
|
self:ShowMap()
|
||||||
else
|
else
|
||||||
self:ShowResult("런 클리어!")
|
self:EndRun("런 클리어!")
|
||||||
self.RunActive = false
|
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
self:OfferReward()
|
self:OfferReward()
|
||||||
end
|
end
|
||||||
elseif self.PlayerHp <= 0 then
|
elseif self.PlayerHp <= 0 then
|
||||||
self.CombatOver = true
|
self.CombatOver = true
|
||||||
self:ShowResult("패배...")
|
self:EndRun("패배...")
|
||||||
self.RunActive = false
|
|
||||||
end`),
|
end`),
|
||||||
method('TeleportToActMap', `local maps = { ${ACT_MAPS.map((m) => `"${m}"`).join(', ')} }
|
method('TeleportToActMap', `local maps = { ${ACT_MAPS.map((m) => `"${m}"`).join(', ')} }
|
||||||
local target = maps[self.Floor]
|
local target = maps[self.Floor]
|
||||||
@@ -2682,6 +2683,9 @@ local entity = _EntityService:GetEntityByPath("/ui/DefaultGroup/CombatHud/Result
|
|||||||
if entity ~= nil then
|
if entity ~= nil then
|
||||||
entity.Enable = true
|
entity.Enable = true
|
||||||
end`, [{ Type: 'string', DefaultValue: null, SyncDirection: 0, Attributes: [], Name: 'text' }]),
|
end`, [{ Type: 'string', DefaultValue: null, SyncDirection: 0, Attributes: [], Name: 'text' }]),
|
||||||
|
method('EndRun', `self:ShowResult(text)
|
||||||
|
self.RunActive = false
|
||||||
|
_TimerService:SetTimerOnce(function() self:ShowMainMenu() end, 4)`, [{ Type: 'string', DefaultValue: null, SyncDirection: 0, Attributes: [], Name: 'text' }]),
|
||||||
method('RenderCombat', `for i = 1, ${MAX_MONSTERS} do
|
method('RenderCombat', `for i = 1, ${MAX_MONSTERS} do
|
||||||
local base = "/ui/DefaultGroup/CombatHud/MonsterSlot" .. tostring(i)
|
local base = "/ui/DefaultGroup/CombatHud/MonsterSlot" .. tostring(i)
|
||||||
local m = self.Monsters[i]
|
local m = self.Monsters[i]
|
||||||
|
|||||||
Reference in New Issue
Block a user