#💻・modding-dev
1 messages · Page 493 of 1
wuh
I have comfy cozy warm but I also keep 3 fans running in my room for a chill
dms?
Yes
It's winter here
@chrome widget
No need for artificial cold
Zamn its a whole almost 90 degrees Fahrenheit here
yeah its 89 where i am
I do be
Hiii
👋
hi carrot
Finally taking my mod seriously. Or well, as seriously as one can take a silly Balala mod
bro im hearing this while i play balatro: https://youtu.be/XJKZbXQXMEI
See more from poppi:
https://www.drinkpoppi.com/
Instagram: https://www.instagram.com/drinkpoppi/
Facebook: https://www.facebook.com/drinkpoppi/
Twitter: https://twitter.com/drinkpoppi
TikTok: https://www.tiktok.com/@drinkpoppi
im also hearing this: https://youtu.be/F6KJJ3iwK4A
A revised version of one of the first songs I made for Forsaken! I'm glad I was able to fix this up a bit since the original was a bit rushed due to it being made during a time I did not have an FL license and had to make stuff in a day lol. I hope y'all like the new version!
Massive thanks to @key_after_key for help with guitars & percussion!
...
experimenting with stuff while polishing song for mod hows this
edward robinson 🤝
can anyone shed some insight in what the secondary colour actually does in the consumable set, from my knowledge, it only uses one colour anyways.
and also what does the shop rate number actually mean, i understand it is related to how often they show up in the shop, but what does the difference between a 4 and a 5 of this value actually mean practically
key = 'dreamer',
loc_txt = {
name = '{C:red}Dreamer{}',
text = {
'When a {C:attention}Blind{} is skipped, {C:green}1 in 6{} chance to spawn {C:rare}Frog Guy{}'
}
},
atlas = 'dreamer',
pos = { x = 0, y = 0 },
rarity = 'silly_unobtainable',
cost = 1,
unlocked = true,
discovered = true,
config = { extra = { odds = 4, } },
loc_vars = function(self, info_queue, card)
info_queue[#info_queue+1] = {key = 'silly_dreamer', set = 'Other', vars = { "ENA" }}
end,
calculate = function(self, card, context)
if context.skip_blind and not context.blueprint then
if (pseudorandom('silly_dreamer') < G.GAME.probabilities.normal / card.ability.extra.odds) then
SMODS.add_card { key = "j_silly_fiction" }
end
end
end
}```
is this right?
@manic rune
:3 am i missing something obvious here
idk
i didnt see, did you test without the pseudorandom?
i ont have any red squiggly lines
Am I only one who so lazy so not using lsp at all 
i use lsp because i lazy
no, but hold on
IT WORKS
we are good
thanks gang
I've been trying to make a consumable that increases the number of uses (same implementation as Seltzer) available for a joker, but it doesn't seem to actually modify the joker's variables.
for j in pairs(G.jokers) do
if j.name == 'Slingshot' then
G.E_MANAGER:add_event(Event({
trigger = 'after',
delay = 0.4,
j:set_ability(j,j.ability.extra.hands+card.ability.extra.use_mod),
j:juice_up(0.3, 0.4),
}))
end
end
end```
that's not how set_ability is used
you would just do j.ability.extra.hands = j.ability.extra.hands+card.ability.extra.use_mod instead of using set_ability
also j.name is probably wrong
oh and pairs(G.jokers) too
let me rewrite it
that's what I tried first but the code kept underlining it red, so I'm not sure what it's interpreting j as if this should be working
reight now im trying to make a joker that makes gold cards trigger every hand you play. to do this, im making it give $3 whenever a gold card is detected after playing a hand. however, this makes it so gold cards also trigger an additional time when its the last hand (this is unwanted). ive tried making it only work when its not context.end_of_round but it doesnt work because it triggers before the context would be true. ive also tried making sure the current chips do not exceed the blinds chip requirement, but this also doesnt work because it triggers the gold cards before jokers are scored. is there a context for triggering held cards after jokers are scored (or another way of doing this entirely)?
use = function(self, card, area, copier)
for _, joker in ipairs(G.jokers.cards) do
if joker.config.center.key == 'j_modprefix_key' then -- replace for your mod's prefix and joker key
joker.ability.extra.hands = joker.ability.extra.hands + card.ability.extra.use_mod
joker:juice_up(0.3, 0.4)
end
end
end
this is even simpler:
use = function(self, card, area, copier)
for _, joker in ipairs(SMODS.find_card('j_modprefix_key')) do -- replace for your mod's prefix and joker key
joker.ability.extra.hands = joker.ability.extra.hands + card.ability.extra.use_mod
joker:juice_up(0.3, 0.4)
end
end
Hey! When creating a new booster pack, I have 2 questions.
1- How do I create the "Raimon" pool as in this example, as it crashes right now.
2- How do I disable standard cards from showing
local Raimon = {
name = "Raimon Pack",
key = "team_pack_raimon",
kind = "Team",
atlas = "Boosters01",
pos = { x = 0, y = 0 },
config = { extra = 3, choose = 1, c_keys = {}},
cost = 4,
order = 1,
weight = 100,
draw_hand = true,
unlocked = true,
discovered = true,
create_card = function(self, card, i)
return create_card("Raimon", G.pack_cards, nil, nil, true, true, nil, nil)
end,
loc_vars = function(self, info_queue, card)
return { vars = { card.config.center.config.choose, card.ability.extra } }
end,
group_key = "k_team_pack",
}
huh, I really overcomplicated this for myself. Thanks for the help!
1- you would use an SMODS.ObjectType
2- standard cards shouldn't show up if the create_card return is correct
also how are you loading this table? I suspect you're using really old syntax which might cause problems
Oh I see, SMODS.ObjectType is missing. I'm using pokermon and cryptid as examples right now so don't really know if this is old
oh yeah then it's not old, cryptid's system is just overly complicated for most mods haha
how do i make shaders for an edition
I'll try adding ObjectType and see if it works
ty
The smods wiki has a page on that
Should be just in the smods.edition page actually
Good morning
so im noticing this is causing Joker to be in the shop like 100% of the time what do i do to fix that
isn't weight 1 equal to 100% chance for it to spawn?
It shouldn't
Does it spawn on every reroll
i meant like what is an .fs file?
the thing is i want this rarity to show up whenever a specific joker is around
but when there is none of that rarity, it just adds Joker to the shop
do i just make the thing that appears on the card and instead of it being a .png i set it to .fs?
like, when showman is around its fine but otherwise its just clogging my shop with Joker lmfoa
you want it to only show up with that joker?
also what does this mean "This defines the card to draw the edition on in the collection."
atlas = 'Joker', pos = { x = 0, y = 0 }
the rarity i made specifically synergizes with another joker i added, so i want this rarity to be more abundant when that joker's in hand
is there a way for me to just,not add weight to it if theres none of that rarity available ?
Usually in your collection for editions, the edition is put on the basic +4 mult joker
You can change that if you want
i dont 100% know but my guess is when youre looking at editions in the collection thats the joker it will be on
the way is to check if all jokers of that rarity are owned in get_weight
yes that is what im asking how to do
💀
I don't know what you don't know how to do haha, I answered your specific question
you would do something like what rare tag does https://github.com/nh6574/VanillaRemade/blob/a214d81d3816eb239d3c9e4d2aa6386807d83503/src/tags.lua#L34
-- -- Smoky
SMODS.Edition {
key = 'smoky',
loc_txt = {
name = 'Smoky',
label = 'Smoky',
text = {
'{X:mult,C:white}x2{} Mult',
}
},
shader = "smoky",
in_shop = true,
weight = 10,
config = { x_mult = 2, trigger = nil },
get_weight = function(self)
return G.GAME.edition_rate * self.weight
end,
loc_vars = function(self, info_queue)
return { vars = { self.config.x_mult } }
end,
calculate = function(self, card, context)
if
(
context.edition
and context.cardarea == G.jokers
and card.config.trigger
) or (
context.main_scoring
and context.cardarea == G.play
)
then
return { x_chips = self.config.x_mult }
end
if context.joker_main then
card.config.trigger = true
end
if context.after then
card.config.trigger = nil
end
end,
}
-- Shaders
-- -- Smoky Shader
SMODS.Shader({ key = 'smoky', path = 'smoky.fs' })```
Is there a way to change the weight of a booster for example if you have X joker?
Try defining the shader before the joker
I mean edition
-- -- Smoky
SMODS.Shader({ key = 'smoky', path = 'smoky.fs' })
SMODS.Edition {
key = 'smoky',
loc_txt = {
name = 'Smoky',
label = 'Smoky',
text = {
'{X:mult,C:white}x2{} Mult',
}
},
shader = "smoky",
in_shop = true,
weight = 10,
config = { x_mult = 2, trigger = nil },
get_weight = function(self)
return G.GAME.edition_rate * self.weight
end,
loc_vars = function(self, info_queue)
return { vars = { self.config.x_mult } }
end,
calculate = function(self, card, context)
if
(
context.edition
and context.cardarea == G.jokers
and card.config.trigger
) or (
context.main_scoring
and context.cardarea == G.play
)
then
return { x_chips = self.config.x_mult }
end
if context.joker_main then
card.config.trigger = true
end
if context.after then
card.config.trigger = nil
end
end,
}```
Same crash?
What does your fs file look like
Try renaming every instance of 'evil' to 'smoky'
Yeah shaders are a bit weird in that regard
how do i make a joker destroy itself if another joker has a specific edition
do you know how?
example of what i mean
<@&1133519078540185692>
What a speed
thank you
oh it was here too?
mods get free sinkhole token
it was in moddingchat
they usually check for channels that can be chatted in and then send messages through those, so usually if its in one itll make its way to another given enough time
i see
also hi toma
disregard this i remembered next find_card existed
hiiii
oh my god
wtf
whats the matter
appropiate pack name fr
i had to grind to get him here
bro is balaling it
i fear my run will end soon nonetheless
how do i make a joker destroy itself if another joker has a specific edition
is there somewhere that you set the id number of a modded rank? or is it automatically set somehow? or should i do the id differently than a number? (yes i know the below is just idenitifying aces, its just here to like show whati m talking about basically)
context.other_card:get_id() == 14
you mean it's priority? It should be part of the json
it's id is also set in the json file
id say your computer will explode but i remember that screenshot
you can read more about how to format the json in the steammodded wiki:
https://github.com/Steamodded/smods/wiki/Mod-Metadata
shes been havin a stroke during the talisman calc, dropping to like 10 frames
im not sure how that works exactly but you can do card.base.value == "modprefix_rankkey" iirc
how can i check other jokers for a specific edition
smth like
for _, v in pairs(G.jokers.cards) do
if v.edition and v.edition.youredition then
trigger here
end
end```
?
pls dont ping me unless it's relevant to the conversation
mb
so where would i put this
what are you trying to do
in a calculate?
im trying to make a joker destroy itself if another joker has a specific edition
i already know the destroy part
i mean you could put it in calculate yes
mmk
so what if i wanted a custom edition?
if you put it in calculate and dont specify a context its going to trigger for every action you do in game
-# i think
and if you put it in update its going to trigger every frame
what if i wanted it to trigger with a custom edition, is what i mean
<@&1133519078540185692>
<@&1133519078540185692>
damn
shoot him
haha i did it first
modprefix_edition
what
alr thanks
:(
im about to intervene on a cosmic level
understandable
oh dear
nah trust you need em all
i legit dont need this
uhh the game crashed and didnt give me a report
i have made a decision, you do
code?
hold on
well i guess i cant say anything else
key = 'frog_guy',
loc_txt = {
name = '{C:#000000}Frog Guy{}',
text = {
'{X:mult,C:white}X3{} Mult',
'Destroys if any Jokers have the {C:inactive}Smoky{} Edition (UNFINISHED)'
}
},
atlas = 'frog_guy',
pos = { x = 0, y = 0 },
rarity = 3,
cost = 7,
unlocked = true,
discovered = true,
pools = { ['SillyPool'] = true },
config = { extra = { Xmult = 3, } },
loc_vars = function(self, info_queue, center)
info_queue[#info_queue + 1] = { key = 'silly_dreamer', set = 'Other', vars = { "Froggy" } }
return { vars = { center.ability.extra.Xmult } }
end,
calculate = function(self, card, context)
if context.joker_main then
return {
card = card,
Xmult_mod = card.ability.extra.Xmult,
message = 'X' .. card.ability.extra.Xmult,
colour = G.C.MULT
}
end
for _, v in pairs(G.jokers.cards) do
if v.edition and v.edition.silly_smoky then
SMODS.destroy_cards(card)
play_sound('silly_cough', 1, 1)
end
end
end
}```
how do i do ^^^^ with talisman
did you die?
ah
i think its because its triggering a lot of times at once :?
js want me to put it in update?
that wouldnt change it
hmmm
Why did you ever make this function revo 😭
i dont know 😭
maybe try putting it in an event manager?
ight
What’s the problem?
this code crashes the game when the for_,... part is triggered, but doesn't give a crash report
It’s not within a context check so it’ll recursively trigger from destroying the cards iirc
it's not in a context so it triggers basically at everything
which essentially causes an avalanche
or just put it in a context
it won't be immediate but i think destroying immediately wouldn't be smart anyways
It’s destroy as soon as you click a card 🤣
yeah lol
what
it triggers with every action done in game
yeah
so it just
calculate is a function called at essentially every action, and if you don't put in a context it'll trigger at everything
this causes what's basically an explosion in the code
so you should probably figure out a context to throw it in
^this is true
like update?
that's not a context
context.setting_blind for example
that would make it be called every frame which again, you don't want
how would i go abt having a joker make certain rank cards be drawn first
if you still dont want to put it in a context figure out a way to make it trigger once
BLARGHHH
update is another function, a context is something like context.joker_main
so it doesnt crash
it signifies when certain actions are taken so things are executed at the right time
^
It’d be fine in update
I think the crash is specifically because destroying cards calls calculate again
nah we good
To check if they’re eternal or not
it's fine
probably would be a bit less satisfying for them to be destroyed immediately
oh yeah you should probably not destroy eternals
you could make a check or something too idk
how would i make aces be prioritized when drawing cards
you might want to check aikoyori's shenanigans
The eternal check is handled for you
These are sick
i didnt know SMODS.destroy_cards existed till yesterday
i've been using card:start_dissolve() 😔
it's pretty new
who is edward robinson
It's more than just an inside joke, it's a lifestyle.
50k Subs for Part 2!
yes
n when are you updating vanillaremade to use the new probability context 
pretty sure it does already
i merged it like 10 minutes after the update
lol
aiko's stuff is like rlly complicated and layered im not rlly gettin much looking at the repo
ty for the recommendation tho
speaking of, im cooking
i watched it live
youre cooking
ok this doesnt work, time to think about it again
you did a great job trying though!
did i
yes because you are beautiful and perfect and smart
thank you dilly
:D
any1 able to help me fix this?idk whats goin on
your logic is set up to where i think it only reaches the part for drawing aces
Kinda. Imagine new ranks and combine it like this.
i t hink that else referring to drawing the cards by default needs to be part of the logic that handles SMODS.find_card()
as in, you want to move the end after the else statement, to before it
and format from there ofc
actually i may be wrong, hm
this should work fine now i think?
Wait so you mean new ranks but with UI like the suits?
oh ok what i wanted to do wasnt hard, im just bad at math and i was overthinking it
see how smart you are
true!
=]
ik i have ts wrong, but idk what nor how to fix it
first hand drawn and final scoring step dont happen at the same time
i think it will destroy at end of round
so how can i combine both?
what's the intended effect?
to give $1 for every 50% of the blind requirement you've scored in the first hand
actually
id prefer it not to be just for the first hand
is that solved then
not yet
i've scored 360/300 in 1 hand, and got $60 instead of $2
ig the math is wrong
yeah % is not the correct operator
isnt that modulo
yeah
yeah it would be division
just divide by 100
but that could give me 0.5 money or smthing?
does anyone remember what the fix is for these weird lines on sprites ingame
round then
and yeah how to round in lua
ceiling or floor
yeah
i dont think it does
i think its in other lua versions
nope
i mean math.floor(x+0.5) is the same thing anyway
yeah i was gonna say that
how can show this long number. in game this number transforms to 3.14
isnt that how round was defined
make it a string with tostring()
works for Xchip and Xmult?
yes, but you should only do it in loc_vars
bruh
k. thanks
Actually is factorial a thing or did people already have this conversation already
factorial as in factorial mult?
i mean it's a thing in that you can do it but i dont think theres a api for it
i dont keep updated with talisman tho
factorial without talisman would just be instant naneinf most of the time
That's fair
Is there a way to calculate the rounds
To detect the number in rounds
I can't words
To detect the number on what round you are on
G.GAME.round?
Makes sense
god my keyboard has a hard time responding today
ironically enough the n key is barely working
Hi all, I assume asking for help for mods made with JokerForge is allowed
After exporting the mod, I'm receiving an error stating
'<name>' expected near '*'
Anybody know what could be causing this issue?
Pastebin of full crash log: https://pastebin.com/M82JyExh
Pastebin.com is the number one paste tool since 2002. Pastebin is a website where you can store text online for a set period of time.
Can we see the code? Also while it is allowed, I would recommend asking in the JokerForge thread instead
hello modding dev
what is the point of having a primary and a secondary colour for consumable set. i was told that one is the text colour and the other is the badge colour but after some testing, i cant see that at all
getting rid of secondary colour crashes because its a required field, but what is its purpose
The secondary colour is mostly everything, but I don't know what the primary one does.
this is what i found out, so whats the point of the primary and why does secondary control everything
the root of my question is, to simplify the process, should i only have a colour wheel for secondary colour and not primary colour when creating a new consumable set in joker forge
and then the code can hardcode primary to be like #fff or something
Probably, but the primary colour should probably be the same as the secondary colour.
Is it possible to square root or power
math.sqrt() and ^
Yes.
how can i create a random joker kinda like judgement
SMODS.add_card({set = "Joker"})
thx
true, thank you for that.
cant believe it took 2 and a half hours to implement the google chrome joker but we ball
lowk half the headache was having to listen to the alibi remix the whole time hdfghfdg
tedious playtesting
Did you hook CardArea:shuffle?
I think he likes aces
can someone help me make a config tab? it only needs to have one toggle, having trouble understanding how to do that
how would i get a count of the amount of cards of a certain rank in my deck?
I made a tarot card that gets rid of some of the required score, is there a way to create a gif on the score that will destroy itself after it's done playing?
which part, the UI or the config file?
in simpler terms I want to create an explosion on the score after the card is used
function rankedCardsInDeck(id_for_your_rank)
local cards = {};
for i, _c in ipairs(G.deck.cards) do
if _c:get_id() == id_for_your_rank then
table.insert(cards, _c)
end
end
return #cards or 0
end
i
forgot cloud 9 existed, im a little dumb ackackackack
this is written from scratch so probably better just to look at that other link lmfao
ui
SMODS.current_mod.config_tab = function()
return {
n = G.UIT.ROOT,
config = { r = 0.1, minw = 8, align = "tm", padding = 0.2, colour = G.C.BLACK },
nodes = {
{
n = G.UIT.R,
config = { padding = 0.2 },
nodes = {
{
n = G.UIT.C,
config = { align = "cm" },
nodes = {
{
n = G.UIT.R,
config = { align = "cm", padding = 0.01 },
nodes = {
create_toggle({
label = "Text",
ref_table = SMODS.Mods["modid"].config, -- replace your mod id
ref_value = 'config_name' -- replace for your config name in config.lua
})
}
},
}
},
}
},
}
}
end
How can I have a calculate_effect target a joker added within the same event?
add an event after the joker's added?
local other_joker = SMODS.add_card(...)
SMODS.calculate_effect({message = "hahaha"}, other_joker)
so i set the variable to the addcard i have already?
yes
got it
worked like a charm, ty
all good?
youre all good
hi dilly
why
hungie
damn 😭
.
hi smt i hope youve had a splendid day today
im writing effects :3
you give me the joy_effect every time i see you
spare change squidward gif
im joy_normal about you
D:
hear me out i give you 100, you write me a check for 250, i cash that, and return the difference to you
Idk who Edward Robinson is
How do I make one of these? The G.P_CENTERS.m_e"nhancement". (I tried searching for it; hence the 3 instead of e)
yes yes yes
I meant the
G.P_CENTERS. where does it come from?
That's just where all the Decks, Boosters, Consumables, Editions, Enhancements, Jokers and Vouchers are stored.
game is crashing because outgoing_joker is nil despite a valid outgoing_joker_key
Yes, but is that joker present?
yeah
Have you tried printing the key?
gb_find_eligible_shatters() is empty perhaps?
gb_find_eligible_shatters() was returning the key of the shattered joker and not of the original joker
quit with the reactions we get it
Reactions are kinda his thing
You get use to it
Yeah he is very shy
But we like him anyway
first time i get to #21#
new record
Can you get to 100
im not looking forward to the loc_vars
Whats the point..
So i put my name for it (it would be r_modletters__name?) after _CENTERS and then add it to the localization?
that is what i did
No, it would be classprefix_modprefix_key
oh e isntead of r
No, that's only for editions.
I have a problem
I have a jokre that has a chance to add a specific tarot card after a jack is scored
ok so it is k
and if it triggers one time it gives a good card
No.
but every jack after it's a diffrent random tarot card
so its m
If it's an enhancement, then yes.
mm
Ok so this was just seed
So in add _card
how do i give a specific tarot card
SMODS.add_card({key = "c_modprefix_key"})
not sure if this is the right place to ask but, im trying to add some documentation for what my jokers all do now that the mod is out but when i go to edit this page all the actual links are gone so im not sure where to go to add a link
you dont edit that page directly tho, you add a tag to your mod's page
Hi, I'm making a comic based Balatro mod and I have the first joker set up but it won't appear in game (I've tried using mods to get it and it still won't work). I'm super new to coding and am basically just copying other mods I have, but I have no idea what the issue is
can i see the code
of the joker or of the mod?
the entire mod if possible
Anyone know why vscode isn't reading definitions from a lsp folder when its in the workspace?
SMODS.Atlas({
key = "Superman",
path = "SupermanJoker1.png",
px = 71,
py = 95
}):register()
SMODS.Atlas({
key = "Batman",
path = "BatmanJoker1.png",
px = 71,
py = 95
}):register()
SMODS.Joker {
key = "Superman",
loc_txt = {
name = "Superman",
text = {
"Each Joker gives {X:mult,C:white}X#3#{} Mult"
},
},
config = {
xmult = 1.1,
odds = 1
},
unlocked = true,
loc_vars = function(card, info_queue, card)
return { vars = { G.GAME.probabilities.normal, card.ability.odds, card.ability.xmult } }
end,
locked_loc_vars = function(self, info_queue, card)
return { vars = { G.GAME.probabilities.normal } }
end,
rarity = 0,
blueprint_compat = true,
eternal_compat = true,
atlas = "jokers",
pos = { x = 9, y = 8 },
cost = 3,
calculate = function(self, card, context)
if context.other_joker and pseudorandom("Superman") < G.GAME.probabilities.normal/card.ability.odds then
G.E_MANAGER:add_event(Event({
func = function()
context.other_joker:juice_up(0.5, 0.5)
return true
end,
}))
return {
xmult = card.ability.xmult
}
end
end,
}
this is the main.lua folder, no idea how this works so i'm super sorry if this is complete nonsense lol
wrap in lua next time (copy this message)
this looks fine, do you have a json?
it doesn't, it needs to either be in the main folder or you need to add it to the workspace settings
How do I do either of those :?
yes, here it is
{
"id": "CB",
"name": "Comic Balatro",
"author": "Sam",
"description": "",
"prefix": "CB",
"main_file": "main.lua",
"badge_colour": "000000",
"badge_text_colour": "ffffff",
"dependencies": [],
"version": "1.0.0"
}
the MOD is showing up in the mod menu, but the actual jokers don't appear
can i see the file structure
oh also is the joker not appearing at all? or is it invisible?
Im sorry, I don't follow
hm i honestly dont see the problem, everything looks fine except aybe the joker's atlas but that should crash the game or ake it invisible
put this in your mod's folder and change the paths for the relative paths to the smods folder and the lovely dump
Im currently just trying to get vscode to use the definitions in general, not a particular mod currently, I have done the steps in https://discord.com/channels/1116389027176787968/1395058450232381461 and still can't get vscode to recognize the definitions
so since modding chat it a trainwreck right now im gonna ask here instead, is there a way (config option, mod, etc.) to change the amount of suits shown in the deck view? like instead of deck pages it just has the other suits in the same page?
What are contexts that get called very frequently, currently I have mod_probability, fix_probability, check_enhancement and check_eternal. Any I'm missing?
define frequently, does selecting a card in hand count?
Very frequently is not the right expression, more like, contexts for which a returned value does not immediately imply a visual effect for the player
Hovering over a card would be one for example
Maybe I should just check if the returned effect has a message
it's just not reading the definitions whatsoever, i have my mods folder opened in the workplace with the lsp folder and none of the functions defined inside the lsp are being defined
modify_scoring_hand sounds like that
the one that lets you splash/unsplash cards right
set_debuff too
debuff_hand and evaluate_poker_hand also do stuff without messages but with a visual effect
yes
oh it's debuff_hand
yes, like i said even if you have it in the same workspace it wont read it
it needs to be the same folder or it needs to be in your settings
I can't for the life of me get enhancers to load.
I've tried loading the file from the main mod file
it still doesn't add the enhancers
how can i create a joker with both edition and stickers, like i have this SMODS.add_card({key = "j_mr_bones", but i want it to be negative, and eternal
SMODS.add_card({key = 'j_mr_bones', edition = "e_negative", stickers = { 'eternal' }})
How do you add things to base game Jokers? (I want to add things to smeared joker)
(or hooking/patching the relevant functions)
God i wish there was an easier way to do this /ref
i hope that's just a joke lol
okay, complex question:
im trying to make a joker that when a hand is played, destroys a random card in hand of a specific suit
how would i go about doing that?
You would put all cards in hand of that suit in a table and destroy a random one.
Then do I just do this for the localization file? (Like how its done normally)
j_smeared = { name = "Smeared Joker", text = { "description", }, },
use context.destroy_card for this ^
yes
cool
is this a good way of filtering these kind of contexts in general? Or am I missing something
Anyway
Would a joker triggering in post_trigger ever return something besides jokers in context.other_ret
Yes.
what would be an example?
How would I add to smeared?
local card_is_suit_ref = Card.is_suit
function Card:is_suit(suit, bypass_debuff, flush_calc)
local ret = card_is_suit_ref(self, suit, bypass_debuff, flush_calc)
if not ret and not SMODS.has_no_suit(self) and next(SMODS.find_card("j_vremade_smeared")) then
return SMODS.smeared_check(self, suit)
end
return ret
end
Is the function of smeared from vanillaremade but idk what its actually doing nor how to modify it
If the joker had a blue seal and the joker triggered in end_of_round, it would also have seals
that would be with your mod right? What about in vanilla, is there any case
If the joker had rental and the joker triggered in end_of_round, it would also have rental
Ping me if anyone finds out anything
What is the goal?
just trying to have an effect whenever a joker triggers
triggering from the perspective of the player anyway
How does a message not count as triggering?
no, it does
i'm skipping the cases in which it returned a table and that table didn't have a message
only because some jokers can return nil, true to signify they triggered
Yes, but if it used mult, it wouldn't have a message.
Adding functionality to smeared so Hearts, Diamonds and Swords (new suit) are all "smeared" together and adding cups (another new suit) to the dark suits
that is a good point
Then you would hook SMODS.smeared_check
I guess I'd just make my own context by hooking card_eval_status_text then
I uh
dont know what that means
In LUA, it is a very important concept to understand that everything is a variable and all variables may be edited in runtime. This includes functions. With modding other peoples' LUA files, like Klei's basegame code, you may find yourself wanting to run your code before or after the original fun...
what's a good text or code editor for lua
perhaps
does in_pool = false make it so jokers cant appear in shop & wont be spawned via judgement and stuff
No.
It's in_pool = function(self) return false end
thanks goat
i want to try adding some form of consumable to the game, havent decided on theming yet though
I started to name the numerators and denominators n1 and d1 respectively once there was more than one chance in the description
its not that hard
ok idea: greek letter cards
i know, the resulting code just looks ugly
I had to do it for at least 30 jokers cus of the smods update too
fatnames for vars < tiny name and a lil comment explaining it imo
just me tho
just me tho
then dont ping me if you dont want my response lmao
btw is there a specific version of vsc thats good to use
i mean ur response completely disgards what i was saying;
my "imo" and "just me tho" imply that i know u dont agree with me lol
i see
and i said i hated comments, i dont know how that disregards what you were saying lol conversations involve exchange of opinions
ur voicin an opinion that i am already aware of i jus think its redundant
i dont like this server today, ill go back to coding
how do you check if a joker is in the leftmost joker slot?
card == G.jokers.cards[1]
ty
Jesus christ????
the first time i came in here talking abt my first ever joker implemented, i was fought for a while because it wasnt balanced or good in the slightest
doesnt feel like it was peaceful at all lmfao
hii winter how are you
Eepy
same
ive never had more than like #5# i think
also that code is for this
Okay yeah for Yugioh rules, makes sense
Does SMODS currently support multi-box descriptions or is that an extension you or someone else made?
Oh, cool. Simple
Looked back at your history, they just told you the wording wasn't accurate to what it was doing
not talking abt that part
talkin abt how i had to keep sayin its a meme joker and wasnt meant to be balanced n stuff
Anyway here's my current suit progress stuff
First one is for a final boss blind that obscures suits by showing alternate suits instead, second one is a blind that stops cards from scoring their base chips, third one is for a blind that makes cards have no ranks
👋
I like the suits
I just woke up from a big fat nap has everyone did big and large developments
The twitter suit 
^ Me when im shopping at J.C. Penney and the employee shows me the professional clothes section
This gave me a laugh
These seem very cool
Greetings eremel
if a probability is 0 in n, it always fails, right?
Still haven't decided if I want the obscured suits to just kind of replace one entire suit with one entire of the bespoke suits, or if I want it to literally randomly assign every card a new suit which is a lot more chaotic
Make it random each blind, replace 1 to 4 suits
Hello dilly
I do be silly
Look at my silly phone
I think youd need to obscure multiple suits, no?
Process of elimination would tell people the suit if its less i suppose
When a function is called, is it possible to see where it was called from?
yes
No what i mean is, it either does two things
- Replaces every suit with one entire new suit randomly (I.E. Hearts becomes Masks, Diamonds becomes Arrow, etc, choices change every time you play the blind
- Replaces every card individually with a new suit randomly
One is easier to parse over multiple hands, you can determine which suit is which. The second is a lot harder
I think i like the individual approach myself more
It is a final boss blind, but some are def harder than others (for example I've only ever had a close call with Cerulean Bell as a result of its effect like once in 1000 hours)
So I'm not sure what difficulty level I want to go with
Yeah individually sounds better, I’m not sure that replacing entire suits makes much difference
I am assuming they will still trigger standard suit effects though
sorry for posting a syntax error here, but i dont quite understand why this is failing, lua extension isnt helping me, it TELLS me there's a syntax error though but i dont know how to fix it, ive genuinely tried doing so many different things
why is there an end to your elseif the first two times
if something then
elseif something_else then
end
i think the brackets were tripping me up
i think using the debug library
which should be builtin
The error stack trace does so it’s definitely in there somewhere
Hiii
hiii
Dumb question, if I have math.random(0, 9), does it include 0 and 9?
i forget if it's inclusive inbetween or exclusive
pretty sure its inclusive
alright, and if i have {"Spades", "Hearts", "Clubs", "Diamonds"}, I assume Spades = 1 in the list, right?
pseudorandom_element is probably easier there
true
math.random is inclusive tho
Finally, we can call random with two integer arguments, l and u, to get a pseudo-random integer x such that l <= x <= u.
ok one moment
how do i actually concatenate this
Why are you using SMODS.calculate_effect instead of returning?
is there a difference
Yes.
It goes before everything else.
And it ignores joker order.
No, then it would go at the end of the round.
You shouldn't use it unless you need to not return.
Or you're in a place where returning wouldn't do joker effects.
Have you tried putting lenient_bignum() around the variables in the return?
ill try that
its somehow even worse now
this is what ive done
why is this hook seemingly not actually activating?
it still returns nan (or just zero sometimes) but it also just isnt even doing anything on chips anymore either now
G.GAME.blind.boss is only active when you're in a boss blind.
Are there any good references for a joker delete/add effect? I want a consumable to delete a chosen card and then replace it with the upgraded version.
id look into vanillaremade stuff, id probably look at the stuff for DNA joker (create card)and that one tarot card that destroys 2 cards
if ur specifically looking to make a joker card tho id look into that one that makes 2 common jokers at blind select
anyone got any idea why this isnt working? my joker has a random chance to debuff a whole hand, but i dont want to keep them debuffed for the rest of the game & also it changes sprite at the same time - im trying to go through all cards, check if theyre debuffed and remove the debuff and return the sprite n stuff back to normal
full calculate function if it helps
try removing the if playing_card.debuff if statement inside the loop
you need to use SMODS.get_probability_vars in your loc_vars
same thing
maybe just try passing nil instead of false
ive tried context.final_scoring_step too but it never seems to reach the code, when using sendInfoMessage i wasnt gettitng anything
oops
Is your card's sprite changing at least
nop
ah, you have your context.end_of_round check inside the context.repetition if statement
ok so its updating but am I supposed to use my local var in the probability condition ?
You don't, you just use the base variables.
It does that for you.
seperate question does anyone know where to even start with making dynatext localiseable (???? is that a word)
what does your dynatext definition look like
its horror i cant really fit it in one screenshot, its basically just manually assembling the whole description based on lines and individual colours 😭
my idea was to make a function where u pass an array from the loc file thats formatted like a regular description, then that structures the object but id like to know if theres a better approach bc i dont really know what im doing here lmao
which part of this do you want to localize
whole desc
im not translating it so ive been asked to take into consideration discrepancies with how long the descriptions will be in other languages too
trying to figure out why this makes score become nan
well uh, I don't know how you want to structure it
but you can put it under misc in the localization file
its aight i dont really know how to explain it 😭 ill try making the function as a proof of concept
Wait
and then you can just do localize('some_other_name', 'some_name') which will return that table
unless you were looking for something else
useful tyty
actually you can just put it under dictionary instead of "some_name", and then you can do localize('some_other_name') which is a bit shorter and more convenient
jamming 😎
those were some very depressing discards
bump
hi moddingdev
goodnight moddingdev
cursed by the rng box (timestamped)https://youtu.be/sCJqcDGgYtA?t=33
Hi tomatose
how might one spawn a specific joker
i tried SMODS.add_card([joker key]) but thats not working and is causing a crash
should be SMODS.add_card { key = 'j_prefix_key' }
is it the same for modded jokers? it crashes when i try spawning a custom joker but it worked just fine when i tried spawning a vanilla joker
Yes, but the key would be j_modprefix_key
What's changing rank and giving seals again
SMODS.change_base and card:set_seal
Your key is probably wrong
You can get the key by hovering over your joker and running eval dp.hovered.config.center.key in the DebugPlus console
Ah okay thank you
k yeah it works now
i significantly misunderstood the j_modprefix_key and was doing it wrong but this helped
Is SMODS.change_base talisman support or am I doing something wrong
SMODS.change_base('2')
Is it like this or different
SMODS.change_base(card, suit, rank)
Ah
It doesn't know what to change if you don't give it the card.
Right
Do I put them in "" or
Yes.
Is there a way for me to restrict Jokers in an ObjectType from appearing in Shops naturally?
Are those jokers your jokers?
I have this currently.
Yes
Those need to be a string.
Just put in_pool = function(self) return false end in the definitions of those jokers.
Perfect.
Do you know why when I set an edition the audio is always delayed and plays the noise when the score is done
Or is that just a Balatro thing
Are you putting it in an event?
Yes, but is it in an event?
Code?
G.E_MANAGER:add_event(Event({
func = function()
other_card:juice_up()
other_card:set_edition('e_polychrome')
other_card:set_ability('m_steel')
return true
end
}))
other_card:set_edition('e_polychrome', nil, true)
It telling it to not be silent and to be instant.
Ah
Well, no crashes, but not spawning the correct Jokers. Where'd I screw up?
So did that and the Jokers aren't in the shop, which is good.
Now the issue is not having them in the pack.
Are they not appearing in the pack or is the pack not spawning
Not appearing in pack.
Yep.
<@&1133519078540185692>
🔫
Thank you my goat
Nope!
Nvm you win this time
anywho, do you know how to fix it?
I don't think you need the SMODS.create_card
From the create card section
Just this
create_card = function(self, card)
return {
set = "GAP_Jokers",
skip_materialize = true,
area = G.pack_cards,
}
end,
Question mark
It's a maybe
Well... that didn't work
Hm
is there a way to check if a playing card returns a certain value? looking to check if a card gives money in any context (held in hand, being played, from a joker like business card, gold seals, etc)
I think you might need to wait for something cause I don't know
Not a gamer like they are
try adding a default card to your objecttype
Didn't work either.
What card spawned
Jimbo. Again.
what card did you put as default
Another Joker from my mod.
@daring fern You know what's wrong with this to where it only spawns Jimbo?
What shows up if you do eval G.P_CENTER_POOLS.GAP_Jokers with debugplus
Have you tried just doing pseudorandom_element on those keys and just creating the joker that it chose?
you mistyped it
Did you put the correct joker key in the cards table
And are those jokers being created before the object type definition
No, they're before the Joker code. Let me move it.
...How would I do that?
Actually I don't think it matters
my guess is that you have the wrong key
local keys = {
'j_modprefix_key1',
'j_modprefix_key2',
}
local key = pseudorandom_element(keys, "seed")
return {key = key}
```?
how would i go about making a booster pack only create jokers of a certain custom rarity
you can specify the rarity in what you return from create_card
i set my booster pack's name in the loc_txt but it says error as the name
everything else functionsthough
Code?
SMODS.Booster {
key = "alibi_pack_1",
weight = 0.6,
kind = 'eddy_alibi',
cost = 4,
loc_txt = {
name = "Alibi Pack",
text = {
"Choose {C:attention}#1#{} of up to",
"{C:attention}#2#{} {C:eddy_alibi}Alibi{C:joker} Jokers{}",
}
},
atlas = "Boosters",
pos = { x = 0, y = 0 },
config = { extra = 2, choose = 1 },
group_key = "k_alibi_pack",
loc_vars = function(self, info_queue, card)
local cfg = (card and card.ability) or self.config
return {
vars = { cfg.choose, cfg.extra }
};
end,
ease_background_colour = function(self)
ease_background_colour_blind(G.STATES.BUFFOON_PACK)
end,
create_card = function(self, card, i)
return { set = "Joker", area = G.pack_cards, skip_materialize = true, soulable = true, key_append = "eddy_alibi", rarity = "eddy_alibi" }
end,
}
can you send the enire crash
sure, one sec
im pretty sure its when the joker is retriggered specifically, because it doesnt crash when its not retriggered by anything
-# i wonder why
everythings fine except the error
Honestly I think this is an issue with steamodded
Add group_name in your loc_txt
kk ty
still errors :[
this is how i retriggered the joker if it helps
What's your code rn
which, i kinda doubt its wrong 🤔
the funny thing is that this is seele and bronya synergy 😭
it seems they arent meant for each other after all
the same as previous just with group_name added
Remove group_key
bump again
I had someone report this same exact crash yesterday, I wasn't able to reproduce it but I think you're onto something
For some reason retriggering jokers during context.repetition causes this
mhm, im guessing the not context.retrigger_joker check is not working properly here
since removing it wont crash the game anymore, although it retriggers like 5 times instead of 1 but thats probably unrelated :3
im genuinely so confused by this, and this isnt even the only joker that's doing it either
so you could probably replicate it by simply adding a not context.retrigger_joker check in context.repetition me think
I'm getting this issue: Could not open file resources/sounds/ckl_sure.ogg. Does not exist. does anyone know how to fix
local click = Controller.L_cursor_press
Controller.L_cursor_press = function(self, x, y)
click(self, x, y)
if G.GAME.blind and G.GAME.blind.name == "The Mark" then
play_sound('ckl_sure')
end
end
does that file exist at the specified path
is ckl your mod prefix and sure is the sound's key?
it should be play_sound("modprefix_key")
no because it doesn't be checking there, it should be checking assets/sounds/sure.ogg
yes
Are you using smods
yes but the thing is in a hook so i'm wondering if it's not picking up that it should be using the smods function
Can you show your SMODS.Sound definition
hey y'all, i'm trying to search through all extra variables in a joker and set any that contain "odds" to 1. for some reason, joker_left.ability.extra.k does nothing. how do i fix this?
for k, v in pairs(joker_left.ability.extra) do
if string.match(k, "odds") then
print("success!")
print(k) --prints the correct index
print(joker_left.ability.extra.k) --prints nil
print(joker_left.ability.extra.odds) --prints the correct value
joker_left.ability.extra.k = 1 --does nothing
odds_count = 1
end
end
SMODS.Sound{key = "sure", path = "assets/sounds/sure.ogg"}
Do extra[k]
Not .k
And yeah, the path should only be "sure.ogg"
thank you!
okay yeah that fixed the issue, thanks
what in the world is happening
this code is causing so many different issues that i cant identify
one of my jokers broke too
:3
which i hope isnt on my end
oh yeah rock have u seen the new seele art
so, whenever this joker scores, the chips and mult both become infinity, and the score becomes nan, im losing my mind trying to diagnose this, any help would be very appreciated
any chance you could make a small reproducible example of the crash
does the new 'context.joker_type_destroyed' context also check for consumables being destroyed? (on the release page it says "non-playing cards")
sure, lemme disable all the other mods to be sure
I'm pretty confident is not a mod issue
I was about to get out of bed and turn on my pc to make the example but I am too comfortable
Yes.
relatable
i just updated smods, why does it look weird??
Oh god eremel is not gonna be happy to hear that
Oh shit they updated the ui?
its a bit to_big
yeah
(i am going insane)
I agree
The icons are too big cus of your resolution
FUCK TALISMAN
damn.
Are u able to increase the resolution
ive never been anti talisman but these past few days have made me genuinely despise it
Welcome to the club
here you go
nop sadly
how do i convert a joker key into it's respective title
I'd send this code and the crash log in #1209564621644505158
if context.individual and context.cardarea == G.play and not context.blueprint then
if SMODS.has_enhancement(context.other_card, "m_stone") then
if i want to detect seals
how'd i do it
Someone who knows more than we do will look at it then
context.other_card.seal?
thats it?
if card.seal == "modprefix_key"
oh?
Uh oh
actually is it .ability.seal or .seal
It's card.seal
yeah i keep, mixing the two
Or card:get_seal
thanks
No one knows more about seals than john seals on every
true...
asking the cheese master about cheese
card.seal == "Red"?
morning guys
hi
took a break for a few days
Bro put "Red Seal"
WELL
this is why i ask
LMAO
im back and im nearly done with the mod
2 proplems left
like this right
whats wrong with this?
You mean localized name?
He didn't even put == "red" smh
localize { type = 'name_text', set = 'Joker', key = key }
yeah
THE RED IS FOR LATER
Cooked
i thought you have autocompletes 🥲 (actually i havent made it compatible with smods lsp yet)
well yeah
whoops
nxkoo.
LISTEN
Cooked
anyone?
works perfectly ty!
The crash report I got was without talisman
I said before you should probably hook Card:set_seal instead.
So I doubt it
forgot lol
now bumping this again
didnt work on it since then
ive tried so many different things
but what if it was
i wouldve genuinely Cash Out $4 there 😭
then i would have something to scream at
:3
Everyone suddenly trying to do seals now
so i red the tutorial u sent me, i dont get it
like what is this local SomeFunction_old = SomeObject.SomeFunction SomeObject.SomeFunction = function(self, arg1, arg2)
smods lsp refer card as Card while mine have prefixes (balatro.Card), i might need to push changes
Also if you made the keys of the double seal firstsealkeysecondsealkey it would be a lot easier.
you know what
this emptied my motivation
i aint drawing no more 🥀
WHAT DO YOU MEAN I CANT USE SEELE WITH BRONYA
THATS ILLEGAL
oh yeah gotta check something, i think the retriggers dont even work properly
they do
You're saving the old function, then overriding it
im looking at it and im like what the f is happening lol
Don't look just at the code, there is more text