Files
gen1recomp/tests/drivers/em_cable_car.lua
T
bryanthaboi 690f0cd9a1 TOUCHDOWN
2026-09-27 16:07:31 -04:00

84 lines
4.2 KiB
Lua

local U = require("tests.drivers.util")
local X = require("tests.drivers.em_xa_util")
local d = X.new("em_cable_car", "/tmp/em_cable_car")
local function ride(game, fromMap, toMap, goingDown, tag)
local Core = require("src.core.game3.rse.cable_car")
Core.last = nil
d.check(X.goTo(d, game, fromMap, 6, 9, "up"), tag .. ": station loads (" .. fromMap .. ")")
U.wait(20)
local att = require("src.core.game3.objects").find(1)
local ax, ay = att and att.cellX or 6, att and att.cellY or 6
d.note(string.format("%s attendant at (%s,%s)", tag, tostring(ax), tostring(ay)))
X.goTo(d, game, fromMap, ax, ay + 1, "up")
U.wait(20)
local reached = X.mash(game, function() return Core.last ~= nil and Core.last.phase ~= "fade" end, 1500)
if not d.check(reached, tag .. ": attendant YES runs CableCarWarp + CableCar (" .. tostring(Core.last and Core.last.phase) .. ")") then
return false
end
d.check(Core.last.goingDown == goingDown, tag .. ": VAR_0x8004 direction reaches the scene (goingDown=" .. tostring(Core.last.goingDown) .. ")")
local sess = X.session()
local w = sess and sess.warpDestination
d.check(w and w.map == toMap and w.x == 6 and w.y == 4,
tag .. ": CableCarWarp targets " .. toMap .. " (6,4) (" .. tostring(w and w.map) .. ")")
local scene = Core.last.screen
if not d.check(scene ~= nil, tag .. ": cable car scene opened") then return false end
local dumpAt = {}
for f in (os.getenv("XA_DUMP_FRAMES") or ""):gmatch("%d+") do dumpAt[tonumber(f)] = true end
if next(dumpAt) then
local orig = scene.frame
scene.frame = function(self, inp)
orig(self, inp)
if dumpAt[self.frames] then
local data = self.m.ppu:snapshot():encode("png"):getString()
os.execute('mkdir -p "' .. d.dir .. '/raw" 2>/dev/null')
local h = io.open(string.format("%s/raw/%s_f%04d.png", d.dir, tag, self.frames), "wb")
if h then h:write(data) h:close() end
end
end
end
local shots = { { 40, "fade_in" }, { 200, "riding" }, { 380, "weather_change" }, { 560, "arriving" } }
local carX0, lastCarX
for _, s in ipairs(shots) do
X.waitFor(function() return scene.frames >= s[1] or scene.done end, 20000)
if scene.done then break end
local car = scene.car
if car then
carX0 = carX0 or car.x
lastCarX = car.x
d.note(string.format("%s frame %d car=(%d,%d) timer=%d weather=%d->%d ash=%s", tag, scene.frames, car.x, car.y,
scene.c.timer, scene.w.currWeather, scene.w.nextWeather, tostring(scene.w.ashSpritesCreated)))
end
d.still(game, tag .. "_" .. string.format("%02d", math.floor(s[1] / 10)) .. "_" .. s[2] .. ".png")
end
d.check(scene.player ~= nil and scene.player.inUse, tag .. ": player sprite rides in the car")
if goingDown then
d.check(carX0 and lastCarX and lastCarX > carX0, tag .. ": the car travels right and down (x " .. tostring(carX0) .. " -> " .. tostring(lastCarX) .. ")")
d.check(scene.w.currWeather == 2, tag .. ": ash clears to WEATHER_SUNNY by the bottom (" .. tostring(scene.w.currWeather) .. ")")
else
d.check(carX0 and lastCarX and lastCarX < carX0, tag .. ": the car travels left and up (x " .. tostring(carX0) .. " -> " .. tostring(lastCarX) .. ")")
d.check(scene.w.ashSpritesCreated, tag .. ": volcanic ash starts falling near the summit")
end
local done = X.waitFor(function() return Core.last.phase == "done" end, 30000)
d.check(done, tag .. ": scene fades out and warps (" .. tostring(Core.last.phase) .. ")")
X.settle(game, 900)
local s = X.session()
d.check(s and s.map == toMap, tag .. ": arrives at " .. toMap .. " (" .. tostring(s and s.map) .. ")")
local exited = X.waitFor(function() return X.var("VAR_CABLE_CAR_STATION_STATE") == 0 and not X.scriptRunning() end, 2400)
d.check(exited, tag .. ": station ON_FRAME walks the player out and resets VAR_CABLE_CAR_STATION_STATE (" ..
X.var("VAR_CABLE_CAR_STATION_STATE") .. ")")
d.shot(game, tag .. "_99_arrival.png")
return true
end
return function(game)
local sess = X.newGame(d, game, 0)
if not sess then return d.finish() end
local okUp = ride(game, "EM_ROUTE112_CABLE_CAR_STATION", "EM_MT_CHIMNEY_CABLE_CAR_STATION", false, "up")
if okUp then
ride(game, "EM_MT_CHIMNEY_CABLE_CAR_STATION", "EM_ROUTE112_CABLE_CAR_STATION", true, "down")
end
d.finish()
end