The original only ever plays `in`; the clip then keeps and fades out by itself, and a new rank line restarts it. Exported as one 162-frame clip instead of the in/out pair, so the plate fades out after its keep span as on the cabinet. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
68 lines
2.3 KiB
Lua
68 lines
2.3 KiB
Lua
-- Score-rank badge (粋 / 雅 / 極) at the top-left of the player panel, shown as the
|
|
-- score crosses each rank line during play.
|
|
--
|
|
-- Original: enso/information/score.nulm `scorerank_1p` (498x264 panel stage at screen
|
|
-- y 276; placed at (152, -118) -> screen (152, 158) for 1P, `scorerank_2p` at
|
|
-- (152, 646) -> 922 for 2P). The game only ever plays the label `in`; the clip then
|
|
-- runs in (f4..28) -> keep (to f148) -> out (f149..165) on its own. Exported from
|
|
-- `in` as game/ending_anim/rank_hud (162 frames, last frame empty) with the seven
|
|
-- plate shapes (`scorerank_panel` rank_1..7); the plate is swapped per rank and a new
|
|
-- rank line simply restarts the clip, as the original's goto_label("in") does.
|
|
--
|
|
-- Rank lines (the engine's own table): 1 white 500 000, 2 bronze 600 000,
|
|
-- 3 silver 700 000, 4 gold 800 000, 5 pink 900 000, 6 purple 950 000,
|
|
-- 7 rainbow 1 000 000.
|
|
local ClipPlayer = require("game/clip_player")
|
|
|
|
local RankBadge = {}
|
|
RankBadge.__index = RankBadge
|
|
|
|
local THRESHOLDS = { 500000, 600000, 700000, 800000, 900000, 950000, 1000000 }
|
|
local PLATE_SHAPES = { 36, 38, 40, 42, 44, 46, 48 } -- rank 1..7
|
|
local BASE_SHAPE = 36
|
|
local POS = { [1] = { 152, 276 - 118 }, [2] = { 152, 276 + 646 } }
|
|
|
|
function RankBadge.rank_of(score)
|
|
local r = 0
|
|
for i, t in ipairs(THRESHOLDS) do
|
|
if score >= t then r = i end
|
|
end
|
|
return r
|
|
end
|
|
|
|
function RankBadge.available()
|
|
local ok, d = pcall(require, "game/ending_anim/rank_hud")
|
|
return ok and type(d) == "table" and d.frames ~= nil
|
|
end
|
|
|
|
function RankBadge.new(player_num, path)
|
|
local self = setmetatable({}, RankBadge)
|
|
local p = POS[player_num] or POS[1]
|
|
self.clip = ClipPlayer.new("game/ending_anim/rank_hud", path or "game", "rank_hud_anim", p[1], p[2])
|
|
if self.clip then self.clip.hold_last = true end
|
|
self.rank = 0
|
|
return self
|
|
end
|
|
|
|
function RankBadge:set_score(score, now)
|
|
local r = RankBadge.rank_of(score)
|
|
if r == self.rank then return end
|
|
self.rank = r
|
|
if r > 0 and self.clip then
|
|
self.clip.shape_map = { [BASE_SHAPE] = PLATE_SHAPES[r] }
|
|
self.clip:start(now)
|
|
end
|
|
end
|
|
|
|
function RankBadge:draw(now)
|
|
if self.clip and self.clip:started() and not self.clip:finished(now) then
|
|
self.clip:draw(now)
|
|
end
|
|
end
|
|
|
|
function RankBadge:destroy()
|
|
if self.clip then self.clip:destroy() end
|
|
end
|
|
|
|
return RankBadge
|