Advise on consumables and packs, not just jokers
A Planet card or Celestial Pack feeds Constellation; Arcana supply feeds Fortune Teller; a Standard Pack permanently adds playing cards, which is what card_gen wanters grow on -- and what shrinks Erosion, so that pack gets a red caution when Erosion is owned (same verified mechanism as its joker clashes, card.lua:4318). The tooltip stays silent when no owned joker cares; Buffoon packs and vouchers are not advice material. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@@ -488,6 +488,51 @@ local function is_joker(card)
|
|||||||
return card.config and card.config.center and card.config.center.set == 'Joker'
|
return card.config and card.config.center and card.config.center.set == 'Joker'
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- Consumable advice ------------------------------------------------------------
|
||||||
|
|
||||||
|
-- A shop consumable or booster pack is fuel for the tag-driven jokers the
|
||||||
|
-- player already owns: a Planet card feeds Constellation, an Arcana Pack
|
||||||
|
-- feeds Fortune Teller, a Standard Pack permanently adds playing cards,
|
||||||
|
-- which is what card_gen wanters grow on. Booster centers carry their
|
||||||
|
-- family in `kind` (game.lua: p_celestial_* has kind = 'Celestial').
|
||||||
|
local CONSUMABLE_TAG = {
|
||||||
|
Planet = 'planet', Tarot = 'tarot_gen', Spectral = 'spectral_gen',
|
||||||
|
Celestial = 'planet', Arcana = 'tarot_gen', Standard = 'card_gen',
|
||||||
|
}
|
||||||
|
|
||||||
|
function JCA.consumable_tag(center)
|
||||||
|
if not center then return nil end
|
||||||
|
if center.set == 'Booster' then return CONSUMABLE_TAG[center.kind] end
|
||||||
|
return CONSUMABLE_TAG[center.set]
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Returns the owned jokers a consumable/pack feeds ({key, name} each, may be
|
||||||
|
-- empty) plus the tag that linked them, or nil when the card is not advice
|
||||||
|
-- material at all. Unknown (modded) jokers on the board are skipped, never
|
||||||
|
-- an error.
|
||||||
|
function JCA.consumable_partners(card)
|
||||||
|
local tag = JCA.consumable_tag(card.config and card.config.center)
|
||||||
|
if not tag then return nil end
|
||||||
|
local fed = {}
|
||||||
|
for _, j in ipairs((G.jokers and G.jokers.cards) or {}) do
|
||||||
|
local key = j.config and j.config.center and j.config.center.key
|
||||||
|
local entry = key and JCA.db[key]
|
||||||
|
if entry and entry.wants[tag] then
|
||||||
|
fed[#fed + 1] = {key = key, name = name_of(key)}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
return fed, tag
|
||||||
|
end
|
||||||
|
|
||||||
|
local function owns(key)
|
||||||
|
for _, j in ipairs((G.jokers and G.jokers.cards) or {}) do
|
||||||
|
if j.config and j.config.center and j.config.center.key == key then
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
end
|
||||||
|
return false
|
||||||
|
end
|
||||||
|
|
||||||
-- Hover tooltip ---------------------------------------------------------------
|
-- Hover tooltip ---------------------------------------------------------------
|
||||||
|
|
||||||
-- Wrap partner names into short tooltip lines.
|
-- Wrap partner names into short tooltip lines.
|
||||||
@@ -865,11 +910,45 @@ local function tooltip_rows(card)
|
|||||||
return rows
|
return rows
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- The consumable counterpart of tooltip_rows: names the owned jokers a
|
||||||
|
-- Planet/Tarot/Spectral card or its pack feeds. Quiet unless an owned joker
|
||||||
|
-- actually cares, so the tooltip adds nothing for everyone else.
|
||||||
|
local function consumable_rows(card)
|
||||||
|
local S = JCA.config.touch_mode and 1.4 or 1
|
||||||
|
local fed, tag = JCA.consumable_partners(card)
|
||||||
|
if not tag then return nil end
|
||||||
|
local rows = {}
|
||||||
|
local function text_row(str, colour)
|
||||||
|
rows[#rows + 1] = {{n = G.UIT.T, config = {
|
||||||
|
text = str, colour = colour or G.C.UI.TEXT_DARK, scale = 0.32 * S,
|
||||||
|
}}}
|
||||||
|
end
|
||||||
|
if #fed > 0 then
|
||||||
|
for i, l in ipairs(wrap_names(fed, 34, 2)) do
|
||||||
|
text_row((i == 1 and 'Feeds: ' or ' ') .. l)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
-- A Standard Pack permanently adds playing cards, and Erosion is paid per
|
||||||
|
-- card MISSING from the deck (card.lua:4318) -- the same verified mechanism
|
||||||
|
-- as its clashes with DNA/Marble/Certificate, from a pack instead.
|
||||||
|
if tag == 'card_gen' and owns('j_erosion') then
|
||||||
|
text_row("Caution: shrinks Erosion's Mult", G.C.RED)
|
||||||
|
end
|
||||||
|
if #rows == 0 then return nil end
|
||||||
|
rows.name = 'Combo Advisor'
|
||||||
|
return rows
|
||||||
|
end
|
||||||
|
|
||||||
local orig_gen_aut = Card.generate_UIBox_ability_table
|
local orig_gen_aut = Card.generate_UIBox_ability_table
|
||||||
function Card:generate_UIBox_ability_table(vars_only)
|
function Card:generate_UIBox_ability_table(vars_only)
|
||||||
-- vars_only returns multiple values; pass that path through untouched
|
-- vars_only returns multiple values; pass that path through untouched
|
||||||
if vars_only then return orig_gen_aut(self, vars_only) end
|
if vars_only then return orig_gen_aut(self, vars_only) end
|
||||||
local aut = orig_gen_aut(self)
|
local aut = orig_gen_aut(self)
|
||||||
|
if aut and aut.info and not is_joker(self)
|
||||||
|
and (in_buy_area(self) or (G.shop_booster and self.area == G.shop_booster)) then
|
||||||
|
local ok, rows = pcall(consumable_rows, self)
|
||||||
|
if ok and rows then aut.info[#aut.info + 1] = rows end
|
||||||
|
end
|
||||||
if aut and aut.info and is_joker(self) then
|
if aut and aut.info and is_joker(self) then
|
||||||
dbg('hover joker', self.config.center.key,
|
dbg('hover joker', self.config.center.key,
|
||||||
'in_buy_area=', in_buy_area(self), 'owned=', self.area == G.jokers)
|
'in_buy_area=', in_buy_area(self), 'owned=', self.area == G.jokers)
|
||||||
|
|||||||
@@ -623,6 +623,41 @@ field('j_jolly')
|
|||||||
looking = JCA.build_gaps()
|
looking = JCA.build_gaps()
|
||||||
eq(table.concat(looking, ','), 'pair', 'a lone cluster member still wants its cluster')
|
eq(table.concat(looking, ','), 'pair', 'a lone cluster member still wants its cluster')
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
section('Engine: consumable advice names the fed jokers')
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
local function consumable(set, kind)
|
||||||
|
return {config = {center = {set = set, kind = kind, key = 'c_test'}}}
|
||||||
|
end
|
||||||
|
|
||||||
|
field('j_constellation', 'j_fortune_teller', 'j_mod_unknown')
|
||||||
|
|
||||||
|
local fed, tag = JCA.consumable_partners(consumable('Planet'))
|
||||||
|
eq(tag, 'planet', 'a Planet card maps to the planet tag')
|
||||||
|
eq(#fed, 1, 'exactly one owned joker is fed by a Planet card')
|
||||||
|
eq(fed[1].key, 'j_constellation', 'and it is Constellation')
|
||||||
|
|
||||||
|
fed, tag = JCA.consumable_partners(consumable('Booster', 'Celestial'))
|
||||||
|
eq(tag, 'planet', 'a Celestial Pack counts as Planet supply')
|
||||||
|
eq(fed[1].key, 'j_constellation', 'the pack feeds Constellation too')
|
||||||
|
|
||||||
|
fed = JCA.consumable_partners(consumable('Tarot'))
|
||||||
|
eq(fed[1].key, 'j_fortune_teller', 'a Tarot card feeds Fortune Teller')
|
||||||
|
|
||||||
|
-- Advice material with nobody home: tag resolves, list stays empty.
|
||||||
|
fed, tag = JCA.consumable_partners(consumable('Spectral'))
|
||||||
|
eq(tag, 'spectral_gen', 'a Spectral card still resolves its tag')
|
||||||
|
eq(#fed, 0, 'but feeds nobody on this board')
|
||||||
|
|
||||||
|
-- A Standard Pack is card supply; a Buffoon Pack is not advice material.
|
||||||
|
fed, tag = JCA.consumable_partners(consumable('Booster', 'Standard'))
|
||||||
|
eq(tag, 'card_gen', 'a Standard Pack maps to card_gen')
|
||||||
|
eq(JCA.consumable_partners(consumable('Booster', 'Buffoon')), nil,
|
||||||
|
'a Buffoon Pack yields no consumable advice')
|
||||||
|
eq(JCA.consumable_partners({config = {center = {set = 'Voucher'}}}), nil,
|
||||||
|
'a Voucher yields no consumable advice')
|
||||||
|
|
||||||
--------------------------------------------------------------------------------
|
--------------------------------------------------------------------------------
|
||||||
section('Data: themes are reachable')
|
section('Data: themes are reachable')
|
||||||
--------------------------------------------------------------------------------
|
--------------------------------------------------------------------------------
|
||||||
|
|||||||
Reference in New Issue
Block a user