mirror of
https://github.com/bryanthaboi/gen1recomp.git
synced 2026-08-17 19:24:01 +02:00
CLOSES #1211, CLOSES #1228, CLOSES #1229, CLOSES #1232, CLOSES #1251, CLOSES #1265, CLOSES #1267, CLOSES #1276, CLOSES #1279, CLOSES #1282, CLOSES #1293, CLOSES #1296, CLOSES #1303, CLOSES #1329, CLOSES #1338, CLOSES #1341, CLOSES #1343, CLOSES #1344, CLOSES #1368, CLOSES #1385, CLOSES #1388, CLOSES #1389, CLOSES #1391
This commit is contained in:
@@ -0,0 +1,116 @@
|
||||
-- The post-battle grace period, which the port never re-armed after an
|
||||
-- UNSCRIPTED wild battle (#1229): World:tryWildEncounter's own
|
||||
-- self:startBattle({ wild = wild }) carries no onDone, so no VM resume ever
|
||||
-- ran the script's own `reloadmapafterbattle` (which is where the cart's
|
||||
-- SetUpFiveStepWildEncounterCooldown lives, engine/overworld/events.asm:1158-
|
||||
-- 1162), and the counter sat at zero for the very next step. What is
|
||||
-- asserted here is the real World:startBattle -> onDone chain, same as
|
||||
-- tests/gen2_canlose_test.lua exercises for the loss arm.
|
||||
--
|
||||
-- GOLD_CACHE=".../gold" luajit tests/gen2_wild_cooldown_bug1229_test.lua
|
||||
package.path = "./?.lua;./?/init.lua;" .. package.path
|
||||
|
||||
local S = require("tests.harness").suite("gen2 wild cooldown")
|
||||
local check, eq = S.check, S.eq
|
||||
|
||||
local World = require("src.world.gen2.World")
|
||||
local Mon = require("src.battle.gen2.Mon")
|
||||
local Screens = require("src.ui.Screens")
|
||||
|
||||
local cache = os.getenv("GOLD_CACHE")
|
||||
if not cache then
|
||||
local home = os.getenv("HOME") or ""
|
||||
cache = home .. "/Library/Application Support/LOVE/gold-dev/gold"
|
||||
end
|
||||
local probe = io.open(cache .. "/data/generated/pokemon.lua", "r")
|
||||
if not probe then
|
||||
check(true, "gold cache absent (SKIP)")
|
||||
S.finish()
|
||||
return
|
||||
end
|
||||
probe:close()
|
||||
|
||||
local function loadLua(rel) return assert(loadfile(cache .. "/" .. rel))() end
|
||||
local pokemon = loadLua("data/generated/pokemon.lua")
|
||||
local moves = loadLua("data/generated/moves.lua")
|
||||
|
||||
-- The battle screen as a registry fake, same shape gen2_canlose_test uses:
|
||||
-- the real World:startBattle pushes it and parks its onDone for the test.
|
||||
-- Screens.get caches by id process-wide, so a suite dofile'd earlier in
|
||||
-- tests/run_tests.lua can leave a stale "Gen2BattleState" behind.
|
||||
Screens.invalidate()
|
||||
local battleDone
|
||||
local registry = {
|
||||
Gen2BattleState = { new = function(_g, opts)
|
||||
battleDone = opts.onDone
|
||||
return { screenId = "Gen2BattleState" }
|
||||
end },
|
||||
}
|
||||
|
||||
local function makeStack()
|
||||
local stack = { items = {} }
|
||||
function stack:push(inst) self.items[#self.items + 1] = inst end
|
||||
function stack:pop()
|
||||
local top = self.items[#self.items]
|
||||
self.items[#self.items] = nil
|
||||
return top
|
||||
end
|
||||
return stack
|
||||
end
|
||||
|
||||
local function makeWorld()
|
||||
battleDone = nil
|
||||
local game = {
|
||||
data = { audio = {}, screens = registry, pokemon = pokemon, moves = moves },
|
||||
-- No roamer state and no map at all: World:pushBattleTransition needs
|
||||
-- self.map to push a wipe and finds none, so pushBattle() runs straight
|
||||
-- away, exactly like a headless battle would. World:restoreMapMusic and
|
||||
-- World:battleMusicContext both already guard a nil self.map.
|
||||
save = { player = { name = "GOLD", money = 3000 }, party = {} },
|
||||
stack = makeStack(),
|
||||
}
|
||||
local mon = Mon.new(game.data, "CYNDAQUIL", 5)
|
||||
check(mon ~= nil, "the cache can build the player's starter")
|
||||
game.save.party[1] = mon
|
||||
local w = World.new(game)
|
||||
return w, game
|
||||
end
|
||||
|
||||
-- ---- the unscripted path itself: World:tryWildEncounter's own call -------
|
||||
do
|
||||
local w, game = makeWorld()
|
||||
local wild = Mon.new(game.data, "MAGIKARP", 10)
|
||||
check(wild ~= nil, "the cache can build the wild mon")
|
||||
-- A grace period already partway spent, so a re-arm is the only way to
|
||||
-- land back on 5.
|
||||
w.wildCooldown = 2
|
||||
|
||||
check(w:startBattle({ wild = wild }),
|
||||
"the unscripted wild path starts a battle")
|
||||
check(battleDone ~= nil, "the battle screen is up")
|
||||
|
||||
battleDone("win")
|
||||
eq(w.wildCooldown, 5,
|
||||
"reloadmapafterbattle's SetUpFiveStepWildEncounterCooldown re-arms " ..
|
||||
"the counter (events.asm:1158-1162), even with no script waiting")
|
||||
end
|
||||
|
||||
-- ---- the counter itself, once re-armed: four blocked steps then a roll --
|
||||
do
|
||||
local w = makeWorld()
|
||||
w.wildCooldown = 5
|
||||
for step = 1, 4 do
|
||||
check(w:wildCooldownStep(),
|
||||
"step " .. step .. " of the grace period is still blocked")
|
||||
end
|
||||
check(not w:wildCooldownStep(), "the fifth step may roll")
|
||||
end
|
||||
|
||||
-- ---- a battle NOTHING started re-arms nothing: only startBattle's onDone -
|
||||
do
|
||||
local w = makeWorld()
|
||||
w.wildCooldown = 0
|
||||
check(w.wildCooldown == 0, "a fresh world never re-arms on its own")
|
||||
end
|
||||
|
||||
S.finish()
|
||||
Reference in New Issue
Block a user