Add new blinds and decks, rewrite almost everything
This commit is contained in:
parent
29888941f0
commit
341a12bf65
14 changed files with 702 additions and 107 deletions
|
|
@ -1,13 +1,39 @@
|
||||||
return {
|
return {
|
||||||
descriptions = {
|
descriptions = {
|
||||||
|
Back = {
|
||||||
|
b_Roland_blossom = {
|
||||||
|
name = "Blossom Deck",
|
||||||
|
text = {
|
||||||
|
"{C:attention}Small{} and {C:attention}Big Blinds{} are",
|
||||||
|
"replaced with {C:attention}Boss Blinds",
|
||||||
|
"that are {C:dark_edition}debuffed #1# times",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
b_Roland_go = {
|
||||||
|
name = "placeholder",
|
||||||
|
text = {"grr"},
|
||||||
|
},
|
||||||
|
},
|
||||||
Blind = {
|
Blind = {
|
||||||
bl_Roland_improbable = {
|
bl_Roland_improbable = {
|
||||||
name = "The Improbable",
|
name = "The Improbable",
|
||||||
text = {"{C:attention}All probabilities", "cannot happen"},
|
text = {"All probabilities", "cannot happen"},
|
||||||
},
|
},
|
||||||
bl_Roland_nimble = {
|
bl_Roland_nimble = {
|
||||||
name = "The Nimble",
|
name = "The Nimble",
|
||||||
text = {"The first {C:attention}5 cards", "drawn are {C:attention}played"},
|
text = {"The first 5 cards", "drawn are played"},
|
||||||
|
},
|
||||||
|
bl_Roland_divide = {
|
||||||
|
name = "The Great Divide",
|
||||||
|
text = {"Half of the deck", "is {C:discard}discarded"},
|
||||||
|
},
|
||||||
|
bl_Roland_tranquilizer = {
|
||||||
|
name = "The Tranquilizer",
|
||||||
|
text = {"#1#s are debuffed", "Changes based on", "most common rank"},
|
||||||
|
},
|
||||||
|
bl_Roland_xerox = {
|
||||||
|
name = "The Xerox",
|
||||||
|
text = {"Discarded cards", "are copied"},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
Joker = {
|
Joker = {
|
||||||
|
|
@ -80,6 +106,9 @@ return {
|
||||||
c_Roland_Jokerful = "Jokerful",
|
c_Roland_Jokerful = "Jokerful",
|
||||||
c_Roland_Pastries = "Sweet Pastries",
|
c_Roland_Pastries = "Sweet Pastries",
|
||||||
},
|
},
|
||||||
|
v_dictionary = {
|
||||||
|
b_Roland_most_common_card = "(Rank)",
|
||||||
|
},
|
||||||
v_text = {
|
v_text = {
|
||||||
ch_c_Roland_Jokerful = {"Only the {C:common}default Joker{} can appear in shops"},
|
ch_c_Roland_Jokerful = {"Only the {C:common}default Joker{} can appear in shops"},
|
||||||
ch_c_Roland_Pastries = {"All blinds, cards, and tags are of {C:gold}Bakery{} or {C:blue}Roland"},
|
ch_c_Roland_Pastries = {"All blinds, cards, and tags are of {C:gold}Bakery{} or {C:blue}Roland"},
|
||||||
|
|
|
||||||
66
lovely.toml
Normal file
66
lovely.toml
Normal file
|
|
@ -0,0 +1,66 @@
|
||||||
|
[manifest]
|
||||||
|
version = "1.0.0"
|
||||||
|
dump_lua = true
|
||||||
|
priority = -2
|
||||||
|
|
||||||
|
# Huge shoutouts to the fantastic Cryptid mod and [MathIsFun0](https://github.com/MathIsFun0)
|
||||||
|
# in particular because this would be so annoying to figure out on your own.
|
||||||
|
# The following patches are all adapted from:
|
||||||
|
# https://github.com/SpectralPack/Cryptid/blob/84895c0349971341e4e09a041a8c94c07ebf0f3f/lovely/stake.toml#L210-L284
|
||||||
|
[[patches]]
|
||||||
|
[patches.pattern]
|
||||||
|
target = "game.lua"
|
||||||
|
pattern = "self.GAME.round_resets.blind_choices.Boss = get_new_boss()"
|
||||||
|
position = "before"
|
||||||
|
payload = '''
|
||||||
|
if G.GAME.modifiers.Roland_blossom_deck then
|
||||||
|
self.GAME.round_resets.blind_choices.Small = get_new_boss()
|
||||||
|
self.GAME.round_resets.blind_choices.Big = get_new_boss()
|
||||||
|
end
|
||||||
|
'''
|
||||||
|
match_indent = true
|
||||||
|
|
||||||
|
[[patches]]
|
||||||
|
[patches.pattern]
|
||||||
|
target = "functions/common_events.lua"
|
||||||
|
pattern = "G.GAME.round_resets.blind_choices.Boss = get_new_boss()"
|
||||||
|
position = "before"
|
||||||
|
payload = '''
|
||||||
|
if G.GAME.modifiers.Roland_blossom_deck then
|
||||||
|
G.GAME.round_resets.blind_choices.Small = get_new_boss()
|
||||||
|
G.GAME.round_resets.blind_choices.Big = get_new_boss()
|
||||||
|
end
|
||||||
|
'''
|
||||||
|
match_indent = true
|
||||||
|
|
||||||
|
[[patches]]
|
||||||
|
[patches.pattern]
|
||||||
|
target = "functions/state_events.lua"
|
||||||
|
pattern = "if G.GAME.blind:get_type() == 'Boss' then"
|
||||||
|
position = "at"
|
||||||
|
payload = "if G.GAME.blind_on_deck == 'Boss' then"
|
||||||
|
match_indent = true
|
||||||
|
|
||||||
|
[[patches]]
|
||||||
|
[patches.pattern]
|
||||||
|
target = "functions/state_events.lua"
|
||||||
|
pattern = "if G.GAME.round_resets.ante == G.GAME.win_ante and G.GAME.blind:get_type() == 'Boss' then"
|
||||||
|
position = "at"
|
||||||
|
payload = "if G.GAME.round_resets.ante >= G.GAME.win_ante and G.GAME.blind_on_deck == 'Boss' then"
|
||||||
|
match_indent = true
|
||||||
|
|
||||||
|
[[patches]]
|
||||||
|
[patches.pattern]
|
||||||
|
target = "functions/state_events.lua"
|
||||||
|
pattern = "if G.GAME.round_resets.blind == G.P_BLINDS.bl_small then"
|
||||||
|
position = "at"
|
||||||
|
payload = "if G.GAME.blind_on_deck == 'Small' then"
|
||||||
|
match_indent = true
|
||||||
|
|
||||||
|
[[patches]]
|
||||||
|
[patches.pattern]
|
||||||
|
target = "functions/state_events.lua"
|
||||||
|
pattern = "elseif G.GAME.round_resets.blind == G.P_BLINDS.bl_big then"
|
||||||
|
position = "at"
|
||||||
|
payload = "elseif G.GAME.blind_on_deck == 'Big' then"
|
||||||
|
match_indent = true
|
||||||
|
|
@ -6,7 +6,7 @@
|
||||||
"author": [
|
"author": [
|
||||||
"Emik"
|
"Emik"
|
||||||
],
|
],
|
||||||
"version": "1.5.1",
|
"version": "2.0.0~dev",
|
||||||
"badge_colour": "8BE9FD",
|
"badge_colour": "8BE9FD",
|
||||||
"main_file": "src/main.lua",
|
"main_file": "src/main.lua",
|
||||||
"badge_text_colour": "44475A",
|
"badge_text_colour": "44475A",
|
||||||
|
|
|
||||||
|
|
@ -1 +1 @@
|
||||||
Subproject commit 4f3eae046476664b720a96f91b0e04f388709bbb
|
Subproject commit cfb7fca10b3b694b25587c39074762a4962ca6c1
|
||||||
66
src/back.lua
Normal file
66
src/back.lua
Normal file
|
|
@ -0,0 +1,66 @@
|
||||||
|
local _, q = unpack(... or require "src.functional")
|
||||||
|
|
||||||
|
-- SMODS.Atlas {
|
||||||
|
-- key = "back",
|
||||||
|
-- path = "back.png",
|
||||||
|
-- px = 71,
|
||||||
|
-- py = 95,
|
||||||
|
-- }
|
||||||
|
SMODS.Back {
|
||||||
|
key = "blossom",
|
||||||
|
name = "Blossom",
|
||||||
|
atlas = "void",
|
||||||
|
pos = {x = 0, y = 0},
|
||||||
|
config = {extra = {times = 2}},
|
||||||
|
loc_vars = function(self, _, _)
|
||||||
|
return {vars = {self.config.extra.times}}
|
||||||
|
end,
|
||||||
|
apply = function(_, _)
|
||||||
|
G.GAME.modifiers.Roland_blossom_deck = true
|
||||||
|
save_run()
|
||||||
|
end,
|
||||||
|
calculate = function(self, _, context)
|
||||||
|
local function disable()
|
||||||
|
for _ = 1, self.config.extra.times do
|
||||||
|
G.GAME.blind:disable()
|
||||||
|
end
|
||||||
|
|
||||||
|
play_sound("timpani")
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
|
||||||
|
if not context.setting_blind then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local blinds = G.GAME.round_resets.blind_states
|
||||||
|
|
||||||
|
if blinds.Small == "Current" or blinds.Big == "Current" then
|
||||||
|
q(disable)
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
SMODS.Back {
|
||||||
|
key = "go",
|
||||||
|
name = "Go",
|
||||||
|
atlas = "void",
|
||||||
|
pos = {x = 0, y = 0},
|
||||||
|
apply = function(_, _)
|
||||||
|
local function add_credit_card()
|
||||||
|
local card = create_card("Joker", G.jokers, nil, nil, nil, nil, "j_credit_card", "Roland_go")
|
||||||
|
card:add_to_deck()
|
||||||
|
card:start_materialize()
|
||||||
|
G.jokers:emplace(card)
|
||||||
|
save_run()
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
|
||||||
|
q(add_credit_card)
|
||||||
|
end,
|
||||||
|
calculate = function(_, _, context)
|
||||||
|
if context.starting_shop then
|
||||||
|
ease_dollars(-G.GAME.dollars)
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
}
|
||||||
184
src/blind.lua
184
src/blind.lua
|
|
@ -1,3 +1,5 @@
|
||||||
|
local _, q = unpack(... or require "src.functional")
|
||||||
|
|
||||||
SMODS.Atlas {
|
SMODS.Atlas {
|
||||||
px = 34,
|
px = 34,
|
||||||
py = 34,
|
py = 34,
|
||||||
|
|
@ -7,8 +9,39 @@ SMODS.Atlas {
|
||||||
atlas_table = "ANIMATION_ATLAS",
|
atlas_table = "ANIMATION_ATLAS",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
local function common_rank()
|
||||||
|
local tally = {}
|
||||||
|
local to_name = {}
|
||||||
|
|
||||||
|
--- Tallies up a card area's cards.
|
||||||
|
---@param card_area CardArea
|
||||||
|
local function tally_up(card_area)
|
||||||
|
for _, v in ipairs(card_area.cards) do
|
||||||
|
if not SMODS.has_no_rank(v) then
|
||||||
|
local id = v:get_id()
|
||||||
|
tally[id] = (tally[id] or 0) + 1
|
||||||
|
to_name[id] = v.base.value
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
tally_up(G.deck)
|
||||||
|
tally_up(G.hand)
|
||||||
|
tally_up(G.discard)
|
||||||
|
local max_key, max_value = -1 / 0, -1 / 0
|
||||||
|
|
||||||
|
for k, v in pairs(tally) do
|
||||||
|
if v > max_value or k > max_key and v == max_value then
|
||||||
|
max_key = k
|
||||||
|
max_value = v
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
return max_key, to_name[max_key]
|
||||||
|
end
|
||||||
|
|
||||||
local function disable_improbable()
|
local function disable_improbable()
|
||||||
G.GAME.improbable = nil
|
G.GAME.modifiers.Roland_improbable = nil
|
||||||
local orig = (getmetatable(G.GAME.probabilities) or {}).orig
|
local orig = (getmetatable(G.GAME.probabilities) or {}).orig
|
||||||
|
|
||||||
if orig then
|
if orig then
|
||||||
|
|
@ -16,12 +49,16 @@ local function disable_improbable()
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local function is_locked()
|
||||||
|
return G.STATE ~= G.STATES.SELECTING_HAND or G.CONTROLLER.locked or (G.GAME.STOP_USE and G.GAME.STOP_USE > 0)
|
||||||
|
end
|
||||||
|
|
||||||
if cry_prob then
|
if cry_prob then
|
||||||
local orig_prob = cry_prob
|
local orig_prob = cry_prob
|
||||||
|
|
||||||
---@diagnostic disable-next-line: lowercase-global
|
---@diagnostic disable-next-line: lowercase-global
|
||||||
cry_prob = function(owned, den, rigged)
|
cry_prob = function(owned, den, rigged)
|
||||||
return G.GAME.improbable and 0 or orig_prob(owned, den, rigged)
|
return G.GAME.modifiers.Roland_improbable and 0 or orig_prob(owned, den, rigged)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
@ -32,7 +69,7 @@ function Game:update(dt)
|
||||||
orig_update(self, dt)
|
orig_update(self, dt)
|
||||||
local orig = G.GAME.probabilities
|
local orig = G.GAME.probabilities
|
||||||
|
|
||||||
if not G.GAME.improbable or getmetatable(orig) then
|
if not G.GAME.modifiers.Roland_improbable or getmetatable(orig) then
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
@ -59,13 +96,13 @@ SMODS.Blind {
|
||||||
boss_colour = HEX("009966"),
|
boss_colour = HEX("009966"),
|
||||||
atlas = "blind",
|
atlas = "blind",
|
||||||
pos = {x = 0, y = 0},
|
pos = {x = 0, y = 0},
|
||||||
pronouns = "any_all",
|
pronouns = "it_its",
|
||||||
mult = 2,
|
mult = 2,
|
||||||
dollars = 5,
|
dollars = 5,
|
||||||
defeat = disable_improbable,
|
defeat = disable_improbable,
|
||||||
disable = disable_improbable,
|
disable = disable_improbable,
|
||||||
set_blind = function(_)
|
set_blind = function(_)
|
||||||
G.GAME.improbable = true
|
G.GAME.modifiers.Roland_improbable = true
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -86,7 +123,7 @@ SMODS.Blind {
|
||||||
end,
|
end,
|
||||||
drawn_to_hand = function(self)
|
drawn_to_hand = function(self)
|
||||||
local function force_hand()
|
local function force_hand()
|
||||||
if G.STATE ~= G.STATES.SELECTING_HAND or G.CONTROLLER.locked or (G.GAME.STOP_USE and G.GAME.STOP_USE > 0) then
|
if is_locked() then
|
||||||
return false
|
return false
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
@ -99,15 +136,146 @@ SMODS.Blind {
|
||||||
end
|
end
|
||||||
|
|
||||||
G.FUNCS.play_cards_from_highlighted(nil)
|
G.FUNCS.play_cards_from_highlighted(nil)
|
||||||
return true
|
|
||||||
end
|
end
|
||||||
|
|
||||||
if not self.disabled then
|
if not self.disabled then
|
||||||
self.disabled = true
|
self.disabled = true
|
||||||
G.E_MANAGER:add_event(Event({func = force_hand, blocking = false}))
|
q {func = force_hand, blocking = false}
|
||||||
end
|
end
|
||||||
end,
|
end,
|
||||||
set_blind = function(self)
|
set_blind = function(self)
|
||||||
self.disabled = false
|
self.disabled = false
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SMODS.Blind {
|
||||||
|
key = "divide",
|
||||||
|
boss = {min = 4, max = 10},
|
||||||
|
boss_colour = HEX("0291fb"),
|
||||||
|
atlas = "blind",
|
||||||
|
pos = {x = 0, y = 1},
|
||||||
|
pronouns = "they_them",
|
||||||
|
mult = 2,
|
||||||
|
dollars = 5,
|
||||||
|
disable = function()
|
||||||
|
local function disable()
|
||||||
|
for i = 1, #G.discard.cards do
|
||||||
|
draw_card(G.discard, G.hand, i / #G.discard.cards * 100, "up", false, G.discard.cards[i], nil, nil, true)
|
||||||
|
end
|
||||||
|
|
||||||
|
for i = 1, #G.discard.cards do
|
||||||
|
draw_card(G.hand, G.deck, i / #G.discard.cards * 100, "up", false, G.discard.cards[i])
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
q(disable)
|
||||||
|
end,
|
||||||
|
set_blind = function()
|
||||||
|
local function force_hand()
|
||||||
|
local length = (#G.deck.cards - 2) / 2
|
||||||
|
|
||||||
|
for i = 0, length do
|
||||||
|
local card = G.deck.cards[#G.deck.cards - i]
|
||||||
|
draw_card(G.deck, G.hand, i / length * 100, "down", false, card, nil, nil, true)
|
||||||
|
end
|
||||||
|
|
||||||
|
for i = 0, length do
|
||||||
|
local card = G.deck.cards[#G.deck.cards - i]
|
||||||
|
draw_card(G.hand, G.discard, i / length * 100, "down", false, card, nil, nil, true)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Allows the background to ease in first before drawing cards.
|
||||||
|
q(force_hand)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
SMODS.Blind {
|
||||||
|
key = "tranquilizer",
|
||||||
|
boss = {min = 4, max = 10},
|
||||||
|
boss_colour = HEX("0291fb"),
|
||||||
|
atlas = "blind",
|
||||||
|
pos = {x = 0, y = 1},
|
||||||
|
pronouns = "they_them",
|
||||||
|
mult = 2,
|
||||||
|
dollars = 5,
|
||||||
|
collection_loc_vars = function(_)
|
||||||
|
return {
|
||||||
|
vars = {localize {
|
||||||
|
type = "variable", key = "b_Roland_most_common_card",
|
||||||
|
}},
|
||||||
|
}
|
||||||
|
end,
|
||||||
|
loc_vars = function(_)
|
||||||
|
local _, name = common_rank()
|
||||||
|
return {vars = {localize(name or "Ace", "ranks")}}
|
||||||
|
end,
|
||||||
|
disable = function(self)
|
||||||
|
self.disabled = true
|
||||||
|
end,
|
||||||
|
calculate = function(self, _, context)
|
||||||
|
if not context.card_added and
|
||||||
|
not context.drawing_cards and
|
||||||
|
not context.playing_card_added and
|
||||||
|
not context.pre_discard and
|
||||||
|
not context.press_play then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local needs_text_change = false
|
||||||
|
|
||||||
|
local function process(card_area)
|
||||||
|
for _, v in pairs(card_area.cards) do
|
||||||
|
local debuff = v.debuff
|
||||||
|
v:set_debuff(self:recalc_debuff(v, false))
|
||||||
|
needs_text_change = needs_text_change or debuff ~= v.debuff
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
process(G.deck)
|
||||||
|
process(G.hand)
|
||||||
|
process(G.discard)
|
||||||
|
|
||||||
|
if needs_text_change then
|
||||||
|
G.GAME.blind:wiggle()
|
||||||
|
G.GAME.blind:set_text()
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
recalc_debuff = function(self, card)
|
||||||
|
local id, _ = common_rank()
|
||||||
|
return not self.disabled and id == card:get_id()
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
SMODS.Blind {
|
||||||
|
key = "xerox",
|
||||||
|
boss = {min = 2, max = 10},
|
||||||
|
boss_colour = HEX("0291fb"),
|
||||||
|
atlas = "blind",
|
||||||
|
pos = {x = 0, y = 1},
|
||||||
|
pronouns = "they_them",
|
||||||
|
mult = 2,
|
||||||
|
dollars = 5,
|
||||||
|
disable = function(self)
|
||||||
|
self.disabled = true
|
||||||
|
end,
|
||||||
|
calculate = function(_, blind, context)
|
||||||
|
if blind.disabled or not context.pre_discard then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local cards_added = {}
|
||||||
|
local length = #G.hand.highlighted
|
||||||
|
|
||||||
|
for i = 1, length do
|
||||||
|
local copy = copy_card(G.hand.highlighted[i])
|
||||||
|
copy:add_to_deck()
|
||||||
|
table.insert(G.hand, copy)
|
||||||
|
table.insert(cards_added, copy)
|
||||||
|
table.insert(G.playing_cards, copy)
|
||||||
|
draw_card(G.hand, G.discard, i / length * 100, "down", false, copy, nil, nil, true)
|
||||||
|
end
|
||||||
|
|
||||||
|
playing_card_joker_effects(cards_added)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,4 @@
|
||||||
|
local f, q = unpack(... or require "src.functional")
|
||||||
local jokerful = {banned_cards = {}}
|
local jokerful = {banned_cards = {}}
|
||||||
local pastries = {banned_cards = {}, banned_tags = {}, banned_other = {}}
|
local pastries = {banned_cards = {}, banned_tags = {}, banned_other = {}}
|
||||||
|
|
||||||
|
|
@ -34,13 +35,16 @@ SMODS.Challenge {
|
||||||
pronouns = "she_them",
|
pronouns = "she_them",
|
||||||
}
|
}
|
||||||
|
|
||||||
G.E_MANAGER:add_event(Event {
|
q {
|
||||||
trigger = "immediate",
|
trigger = "immediate",
|
||||||
func = function()
|
func = function()
|
||||||
F.foreach(F.filter(G.P_CENTERS, is_joker), adder(jokerful.banned_cards))
|
f {
|
||||||
F.foreach(F.filter(G.P_TAGS, is_banned_from_pastry), adder(pastries.banned_tags))
|
{G.P_CENTERS, is_joker, jokerful.banned_cards},
|
||||||
F.foreach(F.filter(G.P_BLINDS, is_banned_from_pastry), adder(pastries.banned_other))
|
{G.P_TAGS, is_banned_from_pastry, pastries.banned_tags},
|
||||||
F.foreach(F.filter(G.P_CENTERS, is_center_banned_from_pastry), adder(pastries.banned_cards))
|
{G.P_BLINDS, is_banned_from_pastry, pastries.banned_other},
|
||||||
return true
|
{G.P_CENTERS, is_center_banned_from_pastry, pastries.banned_cards},
|
||||||
|
}:foreach(function(v)
|
||||||
|
f(v[1]):filter(v[2]):foreach(adder(v[3]))
|
||||||
|
end)
|
||||||
end,
|
end,
|
||||||
})
|
}
|
||||||
|
|
|
||||||
81
src/functional.lua
Normal file
81
src/functional.lua
Normal file
|
|
@ -0,0 +1,81 @@
|
||||||
|
local function protect(fun)
|
||||||
|
return function()
|
||||||
|
local res, ret = pcall(fun)
|
||||||
|
|
||||||
|
if not res then
|
||||||
|
sendErrorMessage(tostring(ret), "Roland")
|
||||||
|
end
|
||||||
|
|
||||||
|
return not res or ret ~= false
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
local function protect_ev(fun)
|
||||||
|
if type(fun) == "table" then
|
||||||
|
fun.func = protect(fun.func)
|
||||||
|
fun = getmetatable(fun) == Event and fun or Event(fun)
|
||||||
|
elseif type(fun) == "function" then
|
||||||
|
fun = Event {func = protect(fun)}
|
||||||
|
else
|
||||||
|
error("Expected a function or event, got a " .. type(fun), 3)
|
||||||
|
end
|
||||||
|
|
||||||
|
return fun
|
||||||
|
end
|
||||||
|
|
||||||
|
local luaf = assert(SMODS.load_file("src/LuaFunctional/functional.lua"))()
|
||||||
|
|
||||||
|
if false then
|
||||||
|
---Returns the elements from the given `list`. This function is equivalent to
|
||||||
|
---```lua
|
||||||
|
--- return list[i], list[i+1], ···, list[j]
|
||||||
|
---```
|
||||||
|
---
|
||||||
|
---
|
||||||
|
---[View documents](command:extension.lua.doc?["en-us/52/manual.html/pdf-unpack"])
|
||||||
|
---
|
||||||
|
---@generic T1, T2, T3, T4, T5, T6, T7, T8, T9, T10
|
||||||
|
---@param list {
|
||||||
|
--- [1]?: T1,
|
||||||
|
--- [2]?: T2,
|
||||||
|
--- [3]?: T3,
|
||||||
|
--- [4]?: T4,
|
||||||
|
--- [5]?: T5,
|
||||||
|
--- [6]?: T6,
|
||||||
|
--- [7]?: T7,
|
||||||
|
--- [8]?: T8,
|
||||||
|
--- [9]?: T9,
|
||||||
|
--- [10]?: T10,
|
||||||
|
---}
|
||||||
|
---@param i? integer
|
||||||
|
---@param j? integer
|
||||||
|
---@return T1, T2, T3, T4, T5, T6, T7, T8, T9, T10
|
||||||
|
---@nodiscard
|
||||||
|
function unpack(list, i, j)
|
||||||
|
error({list, i, j})
|
||||||
|
end
|
||||||
|
|
||||||
|
luaf = require "src.LuaFunctional.functional"
|
||||||
|
end
|
||||||
|
|
||||||
|
--- Creates a non-numerically-indexed query from the given table.
|
||||||
|
---@param obj table
|
||||||
|
---@param f_pairs? fun(t: table): unknown
|
||||||
|
---@param numeric boolean?
|
||||||
|
---@return Query
|
||||||
|
local function f(obj, f_pairs, numeric)
|
||||||
|
return f_pairs and luaf.from(obj, f_pairs, numeric ~= false) or luaf.pairs(obj)
|
||||||
|
end
|
||||||
|
|
||||||
|
--- Queues an event to be run.
|
||||||
|
--- Note that events added this way implicitly `return true` unless you explicitly `return false`, unlike the vanilla ones.
|
||||||
|
--- @param fun (fun():boolean?)|Event The event or a function to run turn into an event.
|
||||||
|
--- @param front boolean|nil `true` to add the event to the front of the queue, rather than the end.
|
||||||
|
local function q(fun, front)
|
||||||
|
G.E_MANAGER:add_event(protect_ev(fun), nil, front)
|
||||||
|
end
|
||||||
|
|
||||||
|
---@class Query<K, V>: metatable
|
||||||
|
local _ = luaf._proto
|
||||||
|
|
||||||
|
return {f, q}
|
||||||
|
|
@ -1,3 +1,5 @@
|
||||||
|
local f, q = unpack(... or require "src.functional")
|
||||||
|
|
||||||
local function can_use()
|
local function can_use()
|
||||||
return not ((G.play and #G.play.cards > 0 or
|
return not ((G.play and #G.play.cards > 0 or
|
||||||
G.CONTROLLER.locked or
|
G.CONTROLLER.locked or
|
||||||
|
|
@ -8,14 +10,12 @@ local function can_use()
|
||||||
end
|
end
|
||||||
|
|
||||||
local function common_hand()
|
local function common_hand()
|
||||||
return (G.GAME or {}).current_round and F.reduce(
|
return (G.GAME or {}).current_round and f(G.GAME.hands):reduce(
|
||||||
G.GAME.hands,
|
|
||||||
{name = "High Card", order = -1 / 0, played = 0},
|
{name = "High Card", order = -1 / 0, played = 0},
|
||||||
function(a, v, k)
|
function(a, v, k)
|
||||||
return (a.played < v.played or (a.played == v.played) and (a.order > v.order)) and
|
return (a.played < v.played or (a.played == v.played) and (a.order > v.order)) and
|
||||||
{name = k, order = v.order, played = v.played} or a
|
{name = k, order = v.order, played = v.played} or a
|
||||||
end,
|
end
|
||||||
pairs
|
|
||||||
).name or "High Card"
|
).name or "High Card"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
@ -70,7 +70,7 @@ SMODS.Joker {
|
||||||
local quotes = loc_self.quotes
|
local quotes = loc_self.quotes
|
||||||
|
|
||||||
local merge = G.jokers
|
local merge = G.jokers
|
||||||
and #F.filter(G.jokers.cards, is_mergeable_with(card)) > 0
|
and f(G.jokers.cards):filter(is_mergeable_with(card)):any()
|
||||||
and loc_self.merge or {}
|
and loc_self.merge or {}
|
||||||
|
|
||||||
local normal = (merge[1] or sinister) and {} or
|
local normal = (merge[1] or sinister) and {} or
|
||||||
|
|
@ -96,15 +96,17 @@ SMODS.Joker {
|
||||||
end,
|
end,
|
||||||
calculate = function(_, _, context)
|
calculate = function(_, _, context)
|
||||||
if type(G.escapey_debugger) == "function" then
|
if type(G.escapey_debugger) == "function" then
|
||||||
G.escapey_debugger(F.reduce(context, "", function(acc, _, next) return acc .. ", " .. next end, pairs):sub(2))
|
G.escapey_debugger(f(context):reduce("", function(acc, _, next)
|
||||||
|
return acc .. ", " .. next
|
||||||
|
end):sub(2))
|
||||||
end
|
end
|
||||||
end,
|
end,
|
||||||
---@param card Card
|
---@param card Card
|
||||||
Bakery_can_use = function(_, card)
|
Bakery_can_use = function(_, card)
|
||||||
return not card.debuff and can_use() and (
|
return not card.debuff and can_use() and (
|
||||||
#G.GAME.tags ~= 0 or
|
#G.GAME.tags ~= 0 or
|
||||||
F.any(G.consumeables.cards, destructible) or
|
f(G.consumeables.cards):filter(destructible):any() or
|
||||||
F.any(F.filter(G.jokers.cards, is_mergeable_with(card)))
|
f(G.jokers.cards):filter(is_mergeable_with(card)):any()
|
||||||
)
|
)
|
||||||
end,
|
end,
|
||||||
---@param card Card
|
---@param card Card
|
||||||
|
|
@ -113,8 +115,8 @@ SMODS.Joker {
|
||||||
return "DEBUFFED"
|
return "DEBUFFED"
|
||||||
end
|
end
|
||||||
|
|
||||||
return #G.GAME.tags == 0 and #F.filter(G.consumeables.cards, destructible) == 0 and
|
return #G.GAME.tags == 0 and not f(G.consumeables.cards):filter(destructible):any() and
|
||||||
F.any(F.filter(G.jokers.cards, is_mergeable_with(card))) and "FUSE" or "ESCAPE"
|
f(G.jokers.cards):filter(is_mergeable_with(card)):any() and "FUSE" or "ESCAPE"
|
||||||
end,
|
end,
|
||||||
---@param card Card
|
---@param card Card
|
||||||
Bakery_use_joker = function(_, card)
|
Bakery_use_joker = function(_, card)
|
||||||
|
|
@ -122,7 +124,7 @@ SMODS.Joker {
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
local consumables = F.filter(G.consumeables.cards, destructible)
|
local consumables = f(G.consumeables.cards):filter(destructible):into()
|
||||||
local consumable_count = #consumables
|
local consumable_count = #consumables
|
||||||
local tag_count = #G.GAME.tags
|
local tag_count = #G.GAME.tags
|
||||||
|
|
||||||
|
|
@ -130,15 +132,12 @@ SMODS.Joker {
|
||||||
local level_sum, sell_sum = 0, 0
|
local level_sum, sell_sum = 0, 0
|
||||||
local any_carbon = is_carbon(card)
|
local any_carbon = is_carbon(card)
|
||||||
|
|
||||||
F.foreach(
|
f(G.jokers.cards):filter(is_mergeable_with(card)):foreach(function(v)
|
||||||
F.filter(G.jokers.cards, is_mergeable_with(card)),
|
any_carbon = any_carbon or is_carbon(v)
|
||||||
function(v)
|
level_sum = level_sum + v.ability.extra.level_up_by * (v.getEvalQty and v:getEvalQty() or 1)
|
||||||
any_carbon = any_carbon or is_carbon(v)
|
sell_sum = sell_sum + v.sell_cost * (v.getEvalQty and v:getEvalQty() or 1)
|
||||||
level_sum = level_sum + v.ability.extra.level_up_by * (v.getEvalQty and v:getEvalQty() or 1)
|
v:start_dissolve({HEX("57ecab")}, nil, 1.6)
|
||||||
sell_sum = sell_sum + v.sell_cost * (v.getEvalQty and v:getEvalQty() or 1)
|
end)
|
||||||
v:start_dissolve({HEX("57ecab")}, nil, 1.6)
|
|
||||||
end
|
|
||||||
)
|
|
||||||
|
|
||||||
if not any_carbon then
|
if not any_carbon then
|
||||||
card.ability.extra.level_up_by = card.ability.extra.level_up_by + level_sum
|
card.ability.extra.level_up_by = card.ability.extra.level_up_by + level_sum
|
||||||
|
|
@ -178,7 +177,6 @@ SMODS.Joker {
|
||||||
play_sound("cancel", 1.66, 0.5)
|
play_sound("cancel", 1.66, 0.5)
|
||||||
v.HUD_tag.states.visible = false
|
v.HUD_tag.states.visible = false
|
||||||
v:remove()
|
v:remove()
|
||||||
return true
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
@ -201,27 +199,21 @@ SMODS.Joker {
|
||||||
local trigger = #G.GAME.tags >= 30 and "immediate" or "before"
|
local trigger = #G.GAME.tags >= 30 and "immediate" or "before"
|
||||||
local delay = #G.GAME.tags >= 30 and 0 or 1 / #G.GAME.tags
|
local delay = #G.GAME.tags >= 30 and 0 or 1 / #G.GAME.tags
|
||||||
|
|
||||||
F.foreach(
|
f(G.GAME.tags):foreach(function(v)
|
||||||
G.GAME.tags,
|
q {
|
||||||
function(v)
|
trigger = trigger,
|
||||||
destroyed = destroyed + 1
|
blocking = #G.GAME.tags < 30,
|
||||||
|
delay = delay,
|
||||||
|
func = fast_delete(v),
|
||||||
|
}
|
||||||
|
|
||||||
G.E_MANAGER:add_event(Event {
|
destroyed = destroyed + 1
|
||||||
trigger = trigger,
|
end)
|
||||||
blocking = #G.GAME.tags < 30,
|
|
||||||
delay = delay,
|
|
||||||
func = fast_delete(v),
|
|
||||||
})
|
|
||||||
end
|
|
||||||
)
|
|
||||||
else
|
else
|
||||||
F.foreach(
|
f(consumables):foreach(function(v)
|
||||||
consumables,
|
v:start_dissolve({HEX("57ecab")}, nil, 1.6)
|
||||||
function(v)
|
destroyed = destroyed + 1
|
||||||
destroyed = destroyed + 1
|
end)
|
||||||
v:start_dissolve({HEX("57ecab")}, nil, 1.6)
|
|
||||||
end
|
|
||||||
)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
level_up_hand(card, hand, nil, destroyed * card.ability.extra.level_up_by)
|
level_up_hand(card, hand, nil, destroyed * card.ability.extra.level_up_by)
|
||||||
|
|
@ -250,7 +242,7 @@ SMODS.Joker {
|
||||||
local vars = {normal}
|
local vars = {normal}
|
||||||
|
|
||||||
for i = #vars, 9 do
|
for i = #vars, 9 do
|
||||||
vars[i + 1] = math.pow(odds, i)
|
table.insert(vars, math.pow(odds, i))
|
||||||
end
|
end
|
||||||
|
|
||||||
return {vars = vars}
|
return {vars = vars}
|
||||||
|
|
@ -262,13 +254,16 @@ SMODS.Joker {
|
||||||
|
|
||||||
local extra = card.ability.extra
|
local extra = card.ability.extra
|
||||||
local xmult = extra.odds
|
local xmult = extra.odds
|
||||||
|
local numerator = 1
|
||||||
|
|
||||||
for _ = 1, 31 do
|
for _ = 1, 31 do
|
||||||
if SMODS.pseudorandom_probability(card, "j_Roland_martingale", 1, extra.odds, "Martingale") then
|
if SMODS.pseudorandom_probability(card, "j_Roland_martingale", 1, extra.odds, "Martingale") then
|
||||||
break
|
break
|
||||||
end
|
end
|
||||||
|
|
||||||
SMODS.calculate_effect({card = card, repetitions = 1, message = "1/" .. number_format(xmult)}, card)
|
numerator = numerator * (extra.odds - G.GAME.probabilities.normal)
|
||||||
|
local message = number_format(numerator) .. "/" .. number_format(xmult)
|
||||||
|
SMODS.calculate_effect({card = card, repetitions = 1, message = message}, card)
|
||||||
xmult = xmult * extra.odds
|
xmult = xmult * extra.odds
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
||||||
16
src/main.lua
16
src/main.lua
|
|
@ -1,13 +1,13 @@
|
||||||
F = assert(SMODS.load_file("src/LuaFunctional/functional.lua"))()
|
local qol = assert(SMODS.load_file("src/functional.lua"))() or require "src.functional"
|
||||||
assert(SMODS.load_file("src/challenge.lua"))()
|
|
||||||
assert(SMODS.load_file("src/spectral.lua"))()
|
qol[1] {"challenge", "spectral", "blind", "joker", "back", "seal"}:foreach(function(v)
|
||||||
assert(SMODS.load_file("src/blind.lua"))()
|
assert(SMODS.load_file("src/" .. v .. ".lua"))(qol)
|
||||||
assert(SMODS.load_file("src/joker.lua"))()
|
end)
|
||||||
|
|
||||||
if Balatest then
|
if Balatest then
|
||||||
assert(SMODS.load_file("src/tests/joker.tests.lua"))()
|
qol[1] {"joker", "blind", "spectral"}:foreach(function(v)
|
||||||
assert(SMODS.load_file("src/tests/blind.tests.lua"))()
|
assert(SMODS.load_file("src/tests/" .. v .. ".tests.lua"))(qol)
|
||||||
assert(SMODS.load_file("src/tests/spectral.tests.lua"))()
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
SMODS.Joker:take_ownership("joker", {cost = 1}, true)
|
SMODS.Joker:take_ownership("joker", {cost = 1}, true)
|
||||||
|
|
|
||||||
34
src/seal.lua
Normal file
34
src/seal.lua
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
-- SMODS.Atlas {
|
||||||
|
-- px = 71,
|
||||||
|
-- py = 95,
|
||||||
|
-- key = "seal",
|
||||||
|
-- path = "seal.png",
|
||||||
|
-- }
|
||||||
|
SMODS.Seal {
|
||||||
|
name = "Frost",
|
||||||
|
key = "frost",
|
||||||
|
badge_colour = HEX("12f254"),
|
||||||
|
atlas = "void",
|
||||||
|
pos = {x = 0, y = 0},
|
||||||
|
calculate = function(_, card, context)
|
||||||
|
if not context.blind_defeated or card.area ~= G.deck then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local tag = Tag(get_next_tag_key("Roland_frost"))
|
||||||
|
|
||||||
|
if tag.name == "Orbital Tag" then
|
||||||
|
local hands = {}
|
||||||
|
|
||||||
|
for k, v in pairs(G.GAME.hands) do
|
||||||
|
if v.visible then
|
||||||
|
table.insert(hands, k)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
tag.ability.orbital_hand = pseudorandom_element(hands, pseudoseed("Roland_frost"))
|
||||||
|
end
|
||||||
|
|
||||||
|
add_tag(tag)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
@ -1,3 +1,5 @@
|
||||||
|
local f, q = unpack(... or require "src.functional")
|
||||||
|
|
||||||
local function can_use()
|
local function can_use()
|
||||||
return not ((G.play and #G.play.cards > 0 or
|
return not ((G.play and #G.play.cards > 0 or
|
||||||
G.CONTROLLER.locked or
|
G.CONTROLLER.locked or
|
||||||
|
|
@ -39,24 +41,22 @@ SMODS.Consumable {
|
||||||
end,
|
end,
|
||||||
use = function(_, card, _, _)
|
use = function(_, card, _, _)
|
||||||
for _, v in ipairs(Bakery_API.get_highlighted()) do
|
for _, v in ipairs(Bakery_API.get_highlighted()) do
|
||||||
G.E_MANAGER:add_event(Event {
|
q {
|
||||||
delay = 0.1,
|
delay = 0.1,
|
||||||
func = function()
|
func = function()
|
||||||
v:set_edition({negative = true})
|
v:set_edition({negative = true})
|
||||||
v:juice_up(0.5, 0.5)
|
v:juice_up(0.5, 0.5)
|
||||||
return true
|
|
||||||
end,
|
end,
|
||||||
})
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
G.E_MANAGER:add_event(Event {
|
q {
|
||||||
delay = 0.1,
|
delay = 0.1,
|
||||||
func = function()
|
func = function()
|
||||||
G.hand:change_size(card.ability.extra.hand)
|
G.hand:change_size(card.ability.extra.hand)
|
||||||
Bakery_API.unhighlight_all()
|
Bakery_API.unhighlight_all()
|
||||||
return true
|
|
||||||
end,
|
end,
|
||||||
})
|
}
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -92,14 +92,14 @@ SMODS.Consumable {
|
||||||
end
|
end
|
||||||
|
|
||||||
local function void()
|
local function void()
|
||||||
local cards = F.filter(G.playing_cards, destructible)
|
local cards = f(G.playing_cards):filter(destructible):into()
|
||||||
|
|
||||||
local function calculate_joker(v)
|
local function calculate_joker(v)
|
||||||
v:calculate_joker({remove_playing_cards = true, removed = cards})
|
v:calculate_joker({remove_playing_cards = true, removed = cards})
|
||||||
end
|
end
|
||||||
|
|
||||||
F.foreach(cards, destroy)
|
f(cards):foreach(destroy)
|
||||||
F.foreach(G.jokers.cards, calculate_joker)
|
f(G.jokers.cards):foreach(calculate_joker)
|
||||||
|
|
||||||
for _ = 1, card.ability.extra.amount do
|
for _ = 1, card.ability.extra.amount do
|
||||||
local cryptid = create_card(
|
local cryptid = create_card(
|
||||||
|
|
@ -117,17 +117,15 @@ SMODS.Consumable {
|
||||||
cryptid:add_to_deck()
|
cryptid:add_to_deck()
|
||||||
G.consumeables:emplace(cryptid)
|
G.consumeables:emplace(cryptid)
|
||||||
end
|
end
|
||||||
|
|
||||||
return true
|
|
||||||
end
|
end
|
||||||
|
|
||||||
play_sound("Roland_void", 1, 0.7)
|
play_sound("Roland_void", 1, 0.7)
|
||||||
|
|
||||||
G.E_MANAGER:add_event(Event({
|
q {
|
||||||
delay = 0.27,
|
delay = 0.27,
|
||||||
timer = "REAL",
|
timer = "REAL",
|
||||||
trigger = "after",
|
trigger = "after",
|
||||||
func = void,
|
func = void,
|
||||||
}))
|
}
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,20 @@ Balatest.TestPlay {
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "improbable"},
|
||||||
|
name = "improbable_disabled",
|
||||||
|
blind = "bl_Roland_improbable",
|
||||||
|
jokers = {"j_oops", "j_oops", "j_oops", "j_chicot"},
|
||||||
|
deck = {cards = {{s = "S", r = "2", e = "m_lucky"}, {s = "S", r = "3"}}},
|
||||||
|
execute = function()
|
||||||
|
Balatest.play_hand {"2S"}
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_chips(7 * 21)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
Balatest.TestPlay {
|
Balatest.TestPlay {
|
||||||
category = {"blind", "nimble"},
|
category = {"blind", "nimble"},
|
||||||
name = "nimble",
|
name = "nimble",
|
||||||
|
|
@ -59,3 +73,143 @@ Balatest.TestPlay {
|
||||||
Balatest.assert_chips(2720)
|
Balatest.assert_chips(2720)
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "nimble"},
|
||||||
|
name = "nimble_disabled",
|
||||||
|
blind = "bl_Roland_nimble",
|
||||||
|
jokers = {"j_chicot"},
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_chips(0)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "divide"},
|
||||||
|
name = "divide",
|
||||||
|
blind = "bl_Roland_divide",
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_eq(#G.discard.cards, 26)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "divide"},
|
||||||
|
name = "divide_odd",
|
||||||
|
blind = "bl_Roland_divide",
|
||||||
|
deck = {cards = {
|
||||||
|
{s = "S", r = "2"},
|
||||||
|
{s = "S", r = "2"},
|
||||||
|
{s = "S", r = "2"},
|
||||||
|
{s = "S", r = "2"},
|
||||||
|
{s = "S", r = "2"},
|
||||||
|
}},
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_eq(#G.discard.cards, 2)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "divide"},
|
||||||
|
name = "divide_disabled",
|
||||||
|
blind = "bl_Roland_divide",
|
||||||
|
jokers = {"j_chicot"},
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_eq(#G.discard.cards, 0)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "tranquilizer"},
|
||||||
|
name = "tranquilizer",
|
||||||
|
blind = "bl_Roland_tranquilizer",
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
for k, v in pairs(G.hand.cards) do
|
||||||
|
local message = v.debuff and
|
||||||
|
"Card " .. k .. " should not be debuffed" or
|
||||||
|
"Card " .. k .. " should be debuffed"
|
||||||
|
|
||||||
|
Balatest.assert(v.debuff == (v.base.value == "Ace"), message)
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "tranquilizer"},
|
||||||
|
name = "tranquilizer_change",
|
||||||
|
blind = "bl_Roland_tranquilizer",
|
||||||
|
jokers = {"j_dna", "j_dna"},
|
||||||
|
deck = {cards = {
|
||||||
|
{s = "S", r = "2"},
|
||||||
|
{s = "S", r = "3"},
|
||||||
|
{s = "S", r = "3"},
|
||||||
|
}},
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
Balatest.play_hand {"2S"}
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
for k, v in pairs(G.hand.cards) do
|
||||||
|
local message = v.debuff and
|
||||||
|
"Card " .. k .. " should not be debuffed" or
|
||||||
|
"Card " .. k .. " should be debuffed"
|
||||||
|
|
||||||
|
Balatest.assert(v.debuff == (v.base.value == "2"), message)
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "tranquilizer"},
|
||||||
|
name = "tranquilizer_disabled",
|
||||||
|
blind = "bl_Roland_tranquilizer",
|
||||||
|
jokers = {"j_chicot"},
|
||||||
|
execute = function()
|
||||||
|
Balatest.wait_for_input()
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
for k, v in pairs(G.hand.cards) do
|
||||||
|
Balatest.assert(not v.debuff, "Card " .. k .. " should not be debuffed")
|
||||||
|
end
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "xerox"},
|
||||||
|
name = "xerox",
|
||||||
|
blind = "bl_Roland_xerox",
|
||||||
|
execute = function()
|
||||||
|
Balatest.discard {"2S"}
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_eq(#G.playing_cards, 53)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"blind", "xerox"},
|
||||||
|
name = "xerox_disabled",
|
||||||
|
blind = "bl_Roland_xerox",
|
||||||
|
jokers = {"j_chicot"},
|
||||||
|
execute = function()
|
||||||
|
Balatest.discard {"2S"}
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_eq(#G.playing_cards, 52)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,31 +2,6 @@ if not Balatest then
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
Balatest.TestPlay {
|
|
||||||
category = {"joker", "martingale"},
|
|
||||||
name = "martingale_oops",
|
|
||||||
jokers = {"j_Roland_martingale", "j_oops"},
|
|
||||||
execute = function()
|
|
||||||
Balatest.play_hand {"2S"}
|
|
||||||
end,
|
|
||||||
assert = function()
|
|
||||||
Balatest.assert_chips(7 * 2)
|
|
||||||
end,
|
|
||||||
}
|
|
||||||
|
|
||||||
Balatest.TestPlay {
|
|
||||||
category = {"joker", "martingale"},
|
|
||||||
name = "martingale_improbable",
|
|
||||||
blind = "bl_Roland_improbable",
|
|
||||||
jokers = {"j_Roland_martingale"},
|
|
||||||
execute = function()
|
|
||||||
Balatest.play_hand {"2S"}
|
|
||||||
end,
|
|
||||||
assert = function()
|
|
||||||
Balatest.assert_chips(7 * math.pow(2, 32))
|
|
||||||
end,
|
|
||||||
}
|
|
||||||
|
|
||||||
Balatest.TestPlay {
|
Balatest.TestPlay {
|
||||||
category = {"joker", "escapey", "escape"},
|
category = {"joker", "escapey", "escape"},
|
||||||
name = "escapey_none",
|
name = "escapey_none",
|
||||||
|
|
@ -350,3 +325,28 @@ Balatest.TestPlay {
|
||||||
Balatest.assert_eq(G.jokers.cards[1].ability.extra.level_up_by, 1)
|
Balatest.assert_eq(G.jokers.cards[1].ability.extra.level_up_by, 1)
|
||||||
end,
|
end,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"joker", "martingale"},
|
||||||
|
name = "martingale_oops",
|
||||||
|
jokers = {"j_Roland_martingale", "j_oops"},
|
||||||
|
execute = function()
|
||||||
|
Balatest.play_hand {"2S"}
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_chips(7 * 2)
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
||||||
|
Balatest.TestPlay {
|
||||||
|
category = {"joker", "martingale"},
|
||||||
|
name = "martingale_improbable",
|
||||||
|
blind = "bl_Roland_improbable",
|
||||||
|
jokers = {"j_Roland_martingale"},
|
||||||
|
execute = function()
|
||||||
|
Balatest.play_hand {"2S"}
|
||||||
|
end,
|
||||||
|
assert = function()
|
||||||
|
Balatest.assert_chips(7 * math.pow(2, 32))
|
||||||
|
end,
|
||||||
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue