#💻・modding-dev
1 messages · Page 468 of 1
bruh 😭
elsewise hook into win_game() and add lose_game() right after
it says that lose_game() is a nil value
how do I get a random joker and modify it
do you know where?
this exists already but something something two cakes
functions/state_events.lua
how do i check how many suits of cards there are in a deck?
@red flower any idea
I’ve written code before that rigged the deck shuffle to put certain cards at the bottom for a boss blind. It involved some code injection tho
Ok it kinda works now, how to resize the Ace slightly?
Do you want to know the accurate number or effective number?
my best guess is to patch/hook draw_card but i think it's more complicated than that
Fuck
just how many cards in the deck has a suit
(when you choose a deck. counting the diamonds will return 13. thats what im trying to do)
Oh that would just be a basic for loop
With a counter
Checking if the card is the right suit or not
and how do i code that
what's wrong?
i just took code from vremade gros michel and wheel of fortune
what smods version
unno
update
is it possible to see what is in the event queue at any moment?
this maybe?
#💻・modding-dev message
where should this be slapped?
anywhere in the file
Guys Sorry if i ask again but i can't find anything, how to resize the Ace in the main title
hey all, idk if this is the right chat for this but can I post a sprite for one of my jokers i'm making and get feedback on it?
i recommend #⚙・modding-general for that
Is there any good resource on the UI for balatro?
why does this not have the background of the color shown?
return {
message = "X" .. number_format(lenient_bignum(card.ability.extra.Xchipsmult)) .. " Chips and Mult",
sound = "xchips",
Xchip_mod = lenient_bignum(card.ability.extra.Xchipsmult),
Xmult_mod = lenient_bignum(card.ability.extra.Xchipsmult),
colour = { 0.8, 0.45, 0.85, 1 }, -- plasma deck colors
}
it just displays as blue
how do you get odds to dynamically display in the description?
i'm looking at this example and it goes #2# in #3# even though the odds are listed as 6, and there's no 3rd thing in the config
You return G.GAME.probabilities.normal in loc_vars
really, I just downloaded the mod manager and I found this mod, even so I think I'll want to do my own for fun =]
calculate = function(self, card, context)
if context.end_of_round and context.game_over == false and context.main_eval and not context.blueprint then
if pseudorandom('broken_galaxy') < G.GAME.probabilities.normal / card.ability.extra.odds then
G.E_MANAGER:add_event(Event({ func = function()
SMODS.add_card{ set = 'Voucher', key = 'v_dlx_warp_glyph' }
return true
end }))
return { message = 'SWOOOOSH!' }
end
end
how do i make this add the voucher to the vouchers and not the joker slots?
Card.apply_to_run(nil, G.P_CENTERS['v_dlx_warp_glyph'])
thank you!
colour seems to be overriden when using _mod
try using xchips and xmult with remove_default_message = true
oh i see
it worked!!
oh my god thank you i've been trying to figure this out for so long 😭
n w
-# sob
i was actually worried it was a recent change i PR'd :3
does this clear/stop events?
How would I run code when a card's id is changed (ie, with Death)? In particular I am trying to apply XMult based on Queens added to the deck and I want deathing them to trigger an increase as well as just context.playing_card_added.
you could just check for how many queens are in deck on playingcardadded, removed and consumeable use
No.
when i called it thats what it seemed to do
G.E_MANAGER:clear_queue()
It's more like Canio where it's changes when the card is added/removed, not just the whole amount in the deck, but thanks anyway
oh... well ty id been looking for something like that!
hmm, well you could still check for those contexts and then add to mult if the base is a queen
so this should kill you given that lug is an empty table and G.GAME.luggage_card == nil, in this case it does yet i dont die
hello chat i come with a strange issue because ive been making jokers without really caring about the weird bugs they have and now that im getting closer to release i should probably fix them 🤭
so what's going on is i have a joker which retriggers the jokers to the left and right once every 4 hands, like loyalty card. however, from my understanding if the jokers arent the same context, whether the left one triggers or not, the right one never will.
Im getting an error for the ui test I made? Does anyone know why its happening?
i have code here that merges the effects because otherwise the code wont run at all and it throws a bunch of weird errors into the console but is there an alternative that would cause this to function?
this hook crashes with this error, can't figure out why it's being so wacky
Do you want to retrigger them or just copy their abilities?

ogblind = Blind.disable
i forget which one is the term for blueprint copying but i am thinking explicitly what blueprint does
try
local merge = {}
if type(other_jokertrigger) == "table" and next(other_jokertrigger) then table.insert(merge, other_jokertrigger) end
if type(other_joker2trigger) == "table" and next(other_joker2trigger) then table.insert(merge, other_joker2trigger) end
return SMODS.merge_effects(merge)
worked, i see now why that was failing, wrong puncuation jumpscare
thanks
it works PERFECTLY thank you sooo much omg
trying to figure out what exactly is causing this whenever i try to view the deck and, while it may probably just me being stupid, i can't figure out where in the stacktrace this is coming from
from a few cursory searches i can tell it probably has something to do with transforms but i am not really sure
my mod aint showing up on the list
this text file contains the whole of the error. i disabled my mod and it still occurs
Can someone explain pseudorandom and how to use it when trying to get a 1 in 2 chance for something and 1 in 10 chance for something else
if pseudorandom("seed") < G.GAME.probabilities.normal / odds then
pseudorandom gives you a decimal number from 0 to 1 and you're checking if it's lower than 1/odds (without oops). If the odds are 1 in 2 then it checks if it's lower than 1/2 or 0.5.
Note: With the new probability API next smods update the if statement would be if SMODS.pseudorandom_probability(card, 'seed', 1, odds) then but it does the same under the hood.
ok thanks
sooooo, if I wanted this to set hands to 1, how would I start with that (I'm more used to C# & C++ not lua help I beg)
if context.main_scoring and context.cardarea == G.play then
if pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.xmult_odds then
return {
xmult = card.ability.extra.xmult
}
end
if pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.dollars_odds then
return {
dollars = card.ability.extra.dollars
}
end
end
why doesnt it proc?
ease_hands_played((-G.GAME.current_round.hands_left)+1)?
Is this an enhancement?
thanks for answering my really simple question lol
no, its a joker
yall how do i make G.GAME.blind.mult = mult * G.GAME.blind.mult but without error xd
context.main_scoring doesn't happen on jokers.
what's the intended effect?
half the blind
the requirements?
G.GAME.blind.chips = G.GAME.blind.chips / 2?
when it starts
ima try dis
oh
it aint do nothin
the print worked tho
that's updating the value and not the text
after that add G.GAME.blind.chip_text = number_format(G.GAME.blind.chips)
uhh what am i doing wrong ?
not
if pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.xmult_odds then
return {
xmult = card.ability.extra.xmult
}
end
if pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.dollars_odds then
return {
dollars = card.ability.extra.dollars
}
end
how can i do it so this only happens on 7s, i cant use context.other_card cause it says its a nil valie
also comma
oopsie
what context is this
context.cardarea == G.play
you need a more strict context check
if you want it to trigger for every 7 then context.individual and context.cardarea == G.play and context.other_card:get_id() == 7
- what you have
works, thx, but now it doesn't seems to want to get the texture i setted it to
oh ok thanks
i hate to ask for help but im a straight up noobie at lua so...
can i see the code
sure, witch , loc, main, this blind ?
the blind + the atlas
hey guys, can anyone explain why this is leaving the infamous ghost cards, i tried to find good references on how to do this sorta thing but i feel like im missing a line somewhere that actually tells the game to get rid of the cards. is there a better way to do this?
if context.individual and context.cardarea == G.play and not context.blueprint then
local target_card = context.other_card
G.E_MANAGER:add_event(Event({
trigger = 'after',
delay = 0.2,
func = function()
target_card:start_dissolve()
return true
end
}))
return {
remove = true,
message = "Destroyed!"
}
end
yes, don't destroy playing* cards during scoring using start_dissolve()
use context.destroy_card
is this any amount of overpowered
if so, how could I nerf it
either 1 in 5 at end of ante (right after the boss blind has been fought) or make it 1 in 15 or higher 👌
end of ante? what would the context even be for that
goated deltarune ref
context.end_of_round and context.main_eval and context.game_over == false and G.GAME.blind.boss
doesnt entirely work with mods that add more bosses per ante but eh
what's the key for atlas blind ?
i can do mod compat later
wdym
john balatro is unhappy with my code apparently (i assumed it was a key problem)
also blind sprites need to have the animation atlas field
been running into an issue with this joker where it's creating Weird cards at the end of the round (one for each time it's used, several if there are multiple copies of bulldozer) these cards are permanently face down (i tried flipping them over via tarot cards and theyre actually face down on both sides LOL) or alternatively theyre sometimes just unselectable and invisible, does anyone have any insight for whats going on here 🙏
straight up in the SMODS.atlas thingy ?
yes
how would i disable this boss blind?
i might be wrong but i think the problem is that you need to unhighlight original
whats the function for unhighlighting one specific card?
card:highlight(false)
it still does function but the messed up cards are still being added 💔
nvm, figured it out (had to manually blacklist boss disable effect jokers)
assuming what you were asking is just this
please dont return functions
oh is that an issue ok
i mean it's going to work but it doesnt do anything and it can lead to errors
🤭 gotcha
ugh i can't make it work
no idea tho
whats the issue
i have absolutely no idea how and where i have to put atlas_table = 'ANIMATION_ATLAS'
in SMODS.Atlas
bump
if context.cardarea == G.play and context.individual and context.other_card:get_id() == 7 then
if pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.xmult_odds then
return {
xmult = card.ability.extra.xmult
}
end
if pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.dollars_odds then
return {
dollars = card.ability.extra.dollars
}
end
end
whenever 7s are played the code works, but if i get multiple oops then it just procs xmult even though i want it to be able to proc both
still hasnt lauched it, i picked it up too
did it work
if context.individual and context.cardarea == G.play and context.other_card:get_id() == 7 then
return {
xmult = pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.xmult_odds and card.ability.extra.xmult or nil,
dollars = pseudorandom('GamblerAtHeart') < G.GAME.probabilities.normal / card.ability.extra.dollars_odds and card.ability.extra.dollars or nil
}
end
it also got a special BlindChips.png in the assets x1 and x2
Hi! How do i add text wrappint to an G.UIT.T UI Object? (If possible make it just two lines)
oh ok thanks
atlas = 'blind_chips' in the blind
u cant
no shot i forgot it
shit :(
ill do it manually then
is there another way to make both always the same size?
maxw?
and does only walso work?
it works as in it is a valid key but idk if it does the same
k thanks
ill just separate name and description
do i need to put the frames/sec too ?
yes i think
uhhhh right
oh sorry i didnt read the /sec
you only need to specify the total frame in the atlas
like
frames = (whatever number of frames there are) ?
i think so, check the docs
it is
Also another question: How the literal frick should I use G.UIT.O to render a card, just like jokers do, with soul_pos support?
I've checked the wiki, but It's very vague
- object: set the object to render.
This is a literal game object, like CardArea.
- role: set the relationship of the object to the UI.
Its value is a table containing at least: {role_type = [TYPE]} where type is either "Major", "Minor", or "Glued".
You probably don't need to use this.
Edit: Does this mean i need to put in the Card Object from Balatro? How could i use that
Hello, another quick question. If im making an Malverk compatible texture pack do I need to define every card texture that im going to change or can I define just the sprite sheet (if I change for example every tarot card)?
but now the blind is just drifting away from its place
sprite sheet should work afaik
hey would just like to bump this again as it's making testing very difficult and any help would be highly appreciated
im guessing since thats the top mod. try disabling entr
entropy, then, got it
i do that here but with a cardarea, idk if it works with an individual card
https://github.com/nh6574/JoyousSpring/blob/a2630a0a7873651ec8280a97ac8652988c2e3cc6/src/mod_info.lua#L47
probably does
ill look at that. thanks
either your size in the atlas is wrong, your sprite sheet is wrong or you put the x1 sheet in the x2 folder or the other way around
aight, testing
did some more looking up, is there really not an easier way to destroy scored cards than to make 4 different contexts and keep track of an array for them
surely theres a sneaky little function or something that just does it lol
why 4 different contexts
before, after, individual scoring, destroying
what's the effect you want
why in individual
how would i check if a scored card is enhanced? specifically like, just any enhancement that isnt None
because it is for joker forge and it being in individual means that it meshes with the system a lot nicer
next(SMODS.get_enhancements(card))
sick ok ty
well no
it's a different context
the bug has been caught 🪲
yeah i get that, the way i was thinking of doing it is. before context: initialise the array. individual: add other card to the array. destroy: destroy cards in the array. after: clean up the array
unless you can reference the currently scored card in the destroy context
yes you can
that's exactly what that context does
context.destroy_card and context.destroy_card:is_face() for example
then i can have the system just split into two contexts with the same conditions, just the destroyed card effect only gets code gennned into that context
i will test this out i think ive been overcomplicating this to a big extreme haha
anyway im dealing with a shader problem rn i hate shaders
does anyone know where the SMODS.Center draw function is called in the code
could you also reccommend a mod where a Card object is created? i am having a hard time figuring out how to do the args, specially since it wants me to give an x, y, width and height, which i thought would be automatical
so i need to define a card area so or so?
you can make a card object without defining an area
i think for x and y you can just give it 0,0 and then put it where you want and it does it automatically
imma try
found it
damn it's a drawstep draw order issue
i need to add a drawstep to vanillaremade..
like one last question. (i've never done such a thing before and like i just wanna know)
What even is SMODS.Center? There is no documentation on it on smods and I've never touched themm
Core class for jokers, consumables, vouchers, etc
hmmm makes sense. how do i define one? can i just give it an empty table?
no idea, you probably need to extend from it or something
<@&1133519078540185692>
Brother 😭 who’s tryna run rugpulls in the anti gambling game server
wha
me no read anything
i also want free money :<
so ig its the default things you define when making SMODS.Joker?
Can someone show me rq how mutibox tooltip definition for cards looks like?
yeah
amazing
oooh what you working on
I'd like to make some practice examples how to use what I made, but I need to do some work
So I'll describe API and then just let others do stuff
(who cares lol)
Hey all, I'm brand new to modding and am trying to get a basic grasp on creating some custom jokers. I've got a bit of a background in coding, but am new to LUA. I'm having a bit of a problem getting a second variable to push through for a localization string. Can anyone see what I'm screwing up?
https://github.com/aaroncampbell/AaronLearningMod/blob/main/jokers/jokers.lua#L33
https://github.com/aaroncampbell/AaronLearningMod/blob/main/localization/en-us.lua#L8
those tabs are sick sleepy
did you try getting a new instance of the joker
Hmmm, I restarted the app a few times in the process, but I do think I keep re-loading the last played hand. Let me try
btw is there a way i can delete samplejimbos from the internet
@red flower Thank you - that took care of it. I should have tried that earlier 
I assume samplejimbos is a bad example then - any better coded (but still fairly comprehensible for someone learning) examples I could look to?
They recently fixed it thanks to me sending an issue but it still has a couple of practices I don't like
I recommend:
https://github.com/Steamodded/examples/tree/master/Mods/ExampleJokersMod
https://github.com/nh6574/VanillaRemade/blob/main/src/jokers.lua
Thank you for the better/more-current examples - I'll work from those 🙂
alright so maybe there is a website or something that can helpme but I'm trying to make a joker give ^2 Mult (I've already got the downside made to not be op so yip) but I just can't figure this out, help please someone
do you have talisman
yes
this is my beautiful solution to destroying cards, does anybody know what the method is for destroying cards specifically on scored, instead of waiting until the hand is done to destroy them or is it too much effort for what its worth
calculate = function(self, card, context)
if context.destroy_card and context.destroy_card.should_destroy and not context.blueprint then
return true
end
if context.individual and context.cardarea == G.play and not context.blueprint then
context.other_card.should_destroy = false
context.other_card.should_destroy = true
return {
message = "Destroyed!"
}
end
end
return { e_mult = 2 } iirc
too much effort imo, everything destroys this way
thank you for the insight haha
also, while it's the same return { remove = true } is nicer than return true
will add it, i appreciate it
erm chat how do i fix this
Update SMODS to the dev version.
ah thx
What do I need to look into to change suit text colors with my mod? Just overriding suits_plural in the localization makes this mess
hi again: how can i remove the popup or add custom text to it, even if it's from another set or has another name/id?
Change G.C.SUITS.Clubs I think.
ignore the textures
got anew crash, how do i fix it
how would edit the weight of a booster in a voucher?
you are trying to get something from an undefinded variable called card
how do i import the lsp_def into the lua lsp server?
Where would be the place to do that? Just setting it in my INIT seems to do nothing
bump & why does it not recognize my atlas?
SMODS.Atlas {
key = 'fates',
px = 63,
py = 93,
path = 'fates.png'
}
local function fate_card_center(fate)
local ret = G.P_CENTERS['j_triboulet']
ret.set = 'Fates'
ret.name = fate.name
ret.atlas = 'fates'
ret.pos = { x = 0, y = 0 }
ret.soul_pos = { x = 1, y = 0 }
ret.config = {}
return ret
end
atlas would be modprefix_atlas here.
i completely forgot
do you also have an answer for the prev question?
Try seeing how the cards on the title don't do anything when hovered.
card.no_ui = true
k. it would be awesome tho if i would be able to define the text. any hints. also again tysm N' and somethingcom for helping so often <3
i dont really know how youre displaying the card
i dont think that its set in the center but, i am using triboulet and modifying its values
bump
weight?
yeah thats what i want to change
Switching the files for the cards is as simple as just going into the code and just putting a different png in there right?
why are you changing the set
i think its called weight
ik but how do i change it
so the game dosent confound it with jokers maybe? idk
no reason to
if you remove that i think it's going to display triboulets text
bump
do i just put it into the directory of my mod?
i think it needs to be at the top of your workspace folder
also you need to change the paths to the correct ones
is there a function for this?
i dont think so
you might need to patch get_pack
Do you have to do something specific to set sprites for a joker on load? I'm trying to load this joker with sprites for a specific center other than the Joker's own and it just kinda..... uses the default?
ah ok nvm
how are you doing it rn?
if card_table.ability.bootlegged_key then
reduced_set_ability(card, G.P_CENTERS[card_table.ability.bootlegged_key])
card.ability.bootlegged_key = card_table.ability.bootlegged_key
end
end```
and at the end of that function it does this:
card.config.center.pos = center.pos
sendDebugMessage('setting sprites for '..center.key)
card:set_sprites(center)
card:set_cost()
card.config.center.pos = old_pos```
Is Malverk unable to change this texture? I havent seen a key for it and even though I put the entire sprite sheet and not single jokers bcs of that and the texture still remains the default.
i have no idea if this will work but try adding
card.children.center.sprite_pos = center.pos
card.children.center:reset()
After the set_sprites call?
Same result. All the properties are the given center, but not the sprites?
hey so i am trying to make a modded joker thats almost exactly like blueprint but it works only for uncommon jokers, but i am not sure how to do the check, i am using the vanilla modded jokers for help but yeah.. any advice?
trying to make a joker that checks if hand Doesnt contain a certain suit but im thinking this has to be the wrong way to check because it's just always returning true
Oh wait I see
It's because it calls set sprites again at the end of the base load call
Using whatever the center's current atlas is
Hm
you could try changing card.children.center.atlas
what do you have rn
how could i make a voucher that makes certain jokers give xmult
i kinda of just have the code from the vanilla blueprint, and i am trying to use the code from baseball card to kind of detect uncommon jokers
or check for a pool in other_joker
(context.other_joker.config.center.pools or {}).pool_key
that should work in vouchers
it would just be
if other_joker.config.center.rarity == 2
so how would i use that to check for a certain pool
like would it be .center.pools.poolkey
ohh ok, i just have to put that before the calculate part right
replace pool_key with your pools key yeah
were you put it depends on how your code is structured that's why i asked what you have
oh ok
Sorry to bump, totally stuck on how to override this global variable in a way that the game recognizes
well, first of all if you have an smods INIT you're using really old syntax
oh hmm, just based it off of what was done in an old texture pack example resource since that's basically all i'm making, and up to this point it's worked ™
i can try and rebuild what little i have so far tho, based on modern examples
i would try to do that, sometimes that syntax causes errors
i think you need to change the color in function Game:start_up() by hooking or replace G.C.S0_1.Clubs and G.C.S0_2.Clubs
I'll give that a try first, and if no luck, I'll try and rewrite it - thanks for the pointers!
oh if you're making a texture pack for playing cards you can just use this btw https://github.com/Steamodded/smods/wiki/SMODS.DeckSkin
Oh, appreciated - tho I'm trying to do jokers as well and potentially other little assets around the game, so I think sticking with the way I'm going is probably best (if i understand the limitations of that tool correctly)?
Tho now that you point it out, I'm starting to wonder if my rendering issues are actually a result of the default deck skin in SMOD pushing its color via that module - maybe I should try also making my own Deck Skin file to push the color that way?
for other things you should look into Malverk
but yeah if you want to stick to what you're doing you can try making a DeckSkin just to change the color
how do I make my mod not crash with talisman?
Trying to create a negative mega spectral pack in the consumables slot, whats wrong here?
you can also add edition = 'e_negative' to add_card
i see
oh and you need to do area = G.consumebales
not what i said that has a typo
through really this isn't gonna make it work properly anyway
it's also going to spawn a million boosters
in the actually using it department
1 morbillion lovely patches
you'll also have to account for it being run during a blind
damn you cryptid
i wanted to add a util function to open a booster like a tag to smods
but it's wonky during a blind so i dont want to think about it
yeah the "in-blind" stuff would be finicky
thats why i didn't make gacha and mind available to use in blinds
first though i need to figure out why the fuck cryptid is breaking things
whatever this is
when is it not
i think this is a recent change actually
do you have both cryptid and smods updated
i dont think i was on latest commit for smods
trying that now
ok still getting that crash
and i updated cryptid yesterday so
Speaking of Cryptid, does anyone happen to know why my planet cards cause crashes with Cryptid installed? I'm almost positive it's their problem but they haven't given me an answer lol
This is the line given by someone who reported it:
[SMODS Cryptid "lib/gameset.lua"]:822: attempt to index local 'card' (a nil value)
I've tried investigating the line myself and came up empty handed
The code for the cards aren't anything special either
get_type_colour(self, card)
idk if that's how it's used in vanilla but that's what cryptid wants
wrong channel :P
from my testing opening a booster during a blind does weird stuff with treating your current hand as the hand that would be drawn in the booster pack but otherwise its just like fine
but i dont remember if i did 500 patches to fix it or not
because i did it all ages ago
you should just try doing it anyway and if it doesnt work then i did 500 patches
but i literally dont remember
define was made really early on
yeah
literally all in trying to do is put a booster pack in the consumable slot 
and actually be able to open it
we got berdly AND noelle??
watch what happens when i run a line of code I don't know
How do I summon a card with a custom rarity with SMODS.add_card?
SMODS.add_card{set = "Joker", rarity = "modprefix_key"}
Causes a crash when testing.
being able to open it is just ui stuff
iirc
i dont remember how much of that was custom
but it was some
can i see the rarity code and any of the jokers that have it
That seemed to work, thank ya plenty
you put the joker key instead of the rarity key
huh?
I need it to summon a specific Joker
well that wasn't clear from your question lol it seemed like you wanted to spawn a joker of a certain rarity not a specific card
anyway SMODS.add_card{ key = "j_modprefix_key"}
Works
is there a visual studio extension for steamodded?
theres one for lua
Have custom modifier types been made possible yet or am i going to have to figure out how to do that myself?
i dont think so
Like. Categories of modifiers
bumping this
I referenced castle pretty heavily but im not sure if is_suit works with this context
Make sure that the variable you're putting in there is correct
Like add a print for it to check it's being set correctly
If anyone here is good at modding cards and doing sprites I have a proposition if you help me make like some cards and stuff for a mod i will pay you with steam games or nitro so DM me 💀 (i have litterally no modding experience and i am too stupid to learn)
The mod itself is gonna be unbalanced chaos because I think that would be comedic 
An example of a card
Im Jeong Dae (Player 100): If you have $100 gain +100 mult for each card played 1 in 100 chance to be impaled with a metal pipe and die
i'm trying to rebalance the vanilla hands for sixty suits, why is flush appearing below 5oak here?
doesnt it list them by values?
5oak is worth more than flush
i could just be wrong but that was my understanding
yes
hm its printing false when it should it just gives the mult anyways? so it might be like setting it to true after and im not sure how id fix that
Okay well firstly I meant that checking what that global value is set to us important
Secondly isnt it setting your Boolean to true every time calculate runs because that's at the start?
Show the code, make sure everything is up to date
ohhhh wait i see
question: how do i make a blind disable more than 1 rank?
question may be pretty dumb but im new to modding
here
just trying to open a booster pack
code mostly copied from ethereal tag in vanillaremade
i got the exact same crash earlier while trying to do something completely different
It's only been a few minutes, please be patient
Not everyone can answer or has seen every question
i'm sorry like actually
Considering that the error is appearing from cryptid maybe try disabling it and testing again
cant, my mod depends on cryptid
Actually what sorry
like that i'm sorry sorry
I'm guessing cryptid messes with the create card function and you should look at cryptids code for creating boosters or wtv
how would i be able to reference hand size inside a config extra table?
Ah alright
Yeah no worries, I hope you get an answer that helps
I'm guessing learning about how boss blinds work and how cards are debuffed in general would be useful
yeah im tryna make a boss blind that only disables even cards
Can you explain what you mean please? Like do you want to change the hand size?
no! i wanna set a variable to be the hand size
try using create_card instead
Can't you just use the variable for the hand size in your code instead
same crash
Hmm, how can I force a card to draw above a specific cardarea
i am! but i can't reference it in the description
Yeah you can you just have to pass it into loc_vars like any other variable
oh okay then!!
ok this is driving me crazy lowkey it just never triggers now?
local variables are not kept between calculate calls
Okay wait, the question here is "how to ensure cards draw below specific other cards"
Hmmmmm
would i want to just have this be a main variable then?
put the variable in your joker's config
gotcha gotcha
ok got it working 🙏 dont know how i confused myself like this im thinkin i need more sleepy
sleep
thank you all
If anyone here is good at modding cards and doing sprites I have a proposition if you help me make like some cards and stuff for a mod i will pay you with steam games or nitro so DM me 💀 (i have litterally no modding experience and i am too stupid to learn)
The mod itself is gonna be unbalanced chaos because I think that would be comedic 
An example of a card
Im Jeong Dae (Player 100): If you have $100 gain +100 mult for each card played 1 in 100 chance to be impaled with a metal pipe and die
if icard:get_id() == card.ability.extra.currentrank then```
why does this code result in the error "attempt to index local 'c' (a number value)"
how do i reference the hand size in loc_vars while avoiding this error
Check if G.hand exists first
If it does then carry out what you're doing, if not then rely on a fallback value
the first value is the index, the second is the card


Yes.
unrelated but what do those stud texture cards do (i believe they are different from the normal ones)
+5 chips when played and -10 when discarded
as you could guess ti is not working
can i see the booster definition
im pretty sure the issue was that i didn't havea loc.txt file
ok, but that's not what i asked lol
when putting G.hand, the game doesn't freak out
it's when putting G.hand.config.card_limit that the game freaks out
i think this is somehow depleting my consumable slots
Right, so if you check to see if G.hand exists before trying to index it, you'll have a failsafe
where do i define my localization text?
can you actually register a keybind in a code?
yes SMODS.Keybind
like
i want so that whenever this got triggered
it presses it
no but
i have that but its not working
well if you dont show me the code i cant do anything
wdym
what exactly do you mean? how do i check such condition?
if G.hand then
Yeah
vremade's localization but vremade is replaced with my mod prefix
Do you have the group_key = "Name Pack" in Localization > misc > dictionary?
i want it so that if this joker got triggered, it presses the player's key (for example, Esc)
is that possible?
you would probably have to call one of the controller functions
doesnt sound hard but i couldn't tell you which one rn
its alright
hows the function typed out again
i mean that's what i cant tell you lol
it's one of the ones in controller.lua
is there a way to conditionally change a joker's description
does it work if you remove the group_key
Yes.
for example if a specific mod is detected use one description and if not use a different one
return a different key in loc_vars
i tried and it did not work out very well
Controller:key_press_update?
wdym
thanks
key = "keytoadifferentlocalizationentry"
return { key = condition and "j_modprefix_key_alt" or nil }
fuck i dont use localization yet
mood
you can just make one for just this
managed to solve it without doing anything said since all i wanted was to reference current xmult in the description lmao
thanks for the help anyways :]
how do i make message = localize('som ething'), a custom text
like perse, how would i make ti say "hi" insteadf of $10 or whatever
["som ething"] = "hi"
In Localization > misc > dictionary
can i do that without a localization fire
No.
what variable checks for how many cards you are currently holding in hand?
Where is the amount of currently owned consumables stored?
good night #💻・modding-dev ill go to sleep
#G.hand.cards
#G.consumeables.cards
im getting this error, and ive been trying to troubleshoot for too long!!!! idk what im doing!!!
Hmm... Do ranks and suits have a calculate function? Or something similar? I know its like. Very niche that they'd actually need one, so im not expecting them to have it. Im just curious
No.
Aw man. Worth a shot. I thought maybe they'd have one that is currently uncodumented
is there an unlock type for cards held in hand? if no, how would i approach making a card unlock given the amount of cards held in hand?
does the "key = 'a_mult'" in messages matter?
Yes.
and if it does waht are the options for those
attempting this horrible idea yet again, why dont the pool change functions here work?
why is everything in dictionary
SMODS.remove_pool takes a key, not a number.
the number is the rarity
im trying to remove the joker from the uncommon rarity pool and add it to the common rarity pool
Yes, you are inputting i into SMODS.remove_pool when you should be inputting v.key
ah
I'm working on a blueprint-like card that copies the jokers to the left and right of it, but funneling both the blueprint effects through SMODS.merge_effects() doesn't seem to be working. It's only returning the effects of ret1 instead of both ret1 and ret2
alright so this happened after a few tries
it worked for a bit but then ran into this
Code?
this is everything so far
Also, you can remove the loops and just input center.key
wdym
SMODS.remove_pool(pool, center.key)
bump
so something like this?
also im sorry for asking here so much
Remove break end end and , v
alright
bump
I'm still getting this crash after like 5-10 rerolls
You are inputting card.ability.extra.current into one of the functions.
i dont understand, is that not what im supposed to do?
its supposed to be setting card.ability.extra.current to the key of a random joker, then targeting that joker, and changing its rarity to common
time to bring this up again!!!
bump
oh awesome it works
massively shortened the code
i want to sleeeeeeeep
now, my current challenge is to keep track of each modified joker's original rarity, and set every joker back to their original rarity when a new game is started in a Game.start_run hook, which i already have here, How would i incorporate this into the joker's code?
does anyone know the variable for the starting hand size?
theres no one helpful online right now unfortunetly
you didn't return the chips value
you only returned the message
if you just want chips
the message is not needed
try G.GAME.starting_params.hand_size
how would i do that exactly? i tried putting the card.ability.bonus = card.ability.bonus + 10 in the return and it doesnt work
help
calculate = function(self, card, context)
if context.first_hand_drawn then
local eval = function()
return G.GAME.current_round.hands_played == 0 and not G.RESET_JIGGLES
end
juice_card_until(card, eval, true)
if #context.full_hand > 0 then
G.E_MANAGER:add_event(Event({
func = function()
for _, original_card in ipairs(context.full_hand) do
local copy_card = copy_card(original_card, nil, nil, G.playing_card)
copy_card:add_to_deck()
G.deck.config.card_limit = G.deck.config.card_limit + 1
table.insert(G.playing_cards, copy_card)
G.hand:emplace(copy_card)
copy_card.states.visible = nil
copy_card:start_materialize()
end
return true
end
}))
return {
message = localize('k_copied_ex'),
colour = G.C.PURPLE,
card = card
}
end
end
if context.entering_shop then
return {
func = function()
G.CONTROLLER:key_press_update("escape", true)
G.CONTROLLER:key_press_update("escape", false)
G.E_MANAGER:add_event(Event({
trigger = 'after',
delay = 0.1,
func = function() return true end
}))
end
}
end
end,
}
did i do something wrong
What object is this code from?
do you see the return { message = ... thingy
DNA
you don't need the message
Also it's context.starting_shop
oh
No, I'm referring to the object you're using it for.
YOUR A LAIFE SAVOR....
YOUR WELCOME
what im trying to do is add +10 to the chips when it scores
so
you want to add it
before scoring
i'd say use before to add numbers
also i'd say create a separate ability table but if it works it works
oh its for a joker that copies all played cards if its the first hand of the round
attempting to somehow restore modified rarities here back to their defaults when a new run is started, how would i accomplish that?
currently they stay as the modified rarities until you close your game
my idea would be to somehow add each modified joker to a table, storing their original rarities, calling that table when a new run is started, and changing each joker in the table to match their original rarities
but that is way beyond my expertise
still doesnt work :I
also just for cleanliness you should format the code so it's a bit easier to read
current issue: chips arent adding and sounds arebt playing
Why do you have a calculate function inside your calculate function?
im not sure how to define the end of the first calculate function
IT WORKS
nevermind why are the extra chips there
why are tyhey there??
How would I go about adding a button next to the Discard button
this code only works for scored cards does anyone know how to make it work for every played card
i never added extra chips into the description anywhere
WHY IS IT THER
E
bnm ghjyvtu6j7
context.full_hand not context.scoring_hand
thank you
Just gonna bump this if anyone can help
does anyone know how tyo fix this
its 12:12 am and im not going to sleep until tis done
Code?
Try putting all the variables in extra = {}
by that do yoyu mean
replacing bonus with extra>
No, config = {extra = {...}} instead of config = {...}
I think they mean instead of config = { your_vars } it'd be config = { extra = { your_vars } }
I'd suggest trying to print out ret1 and ret2 and seeing if they work properly. If they do, then print out the merge and see if that looks good, etc etc
(and then you'd be calling card.ability.extra.your_var instead of card.ability.your_var)
that did not work
Code?
I did not see your other message whoopsie
how do you get the current amout of money you have
G.GAME.dollars
You would probably have to hook ease_dollars
do you see whats wrong with my code?
You need to change things to be card.ability.extra.bonus instead of card.ability.bonus
tried to index feild extra (a number value
:'(
Change extra = 30 to bonus = 30
still broken
Code?
How would i get a joker to detect when a card is bought and duplicate it? know context.buying_card is the key but not sure how to set SMODS.add_card to add the newly bought card
context.buying_card is not the key?
No, put the extra table back.
it works
don't know how identify the detected bought card so i can use add_card to duplicate it, i know i use context.buying_card
Firstly, you don't use SMODS.add_card, Secondly, you use context.card to get the card.
Thirdly, you use copy_card to copy the card.
thanks
yall what do i use to make my first mod
Did what you suggested and I think SMODS.merge_effects() has a weird quirk where if the first arg is nil it'll make the whole thing return nil.
I remedied that by only returning ret1 if ret2 doesn't exist (and vice versa) and the merge effects function if they both exist.
Thanks for pushing me in the right direction!
should raise that in #1209564621644505158 that doesn't seem intentional. i think merge_effects should just ignore nils
That is very weird behavior. Nice job in figuring it out though! I second nope's comment
how would i go about adding a joker and it's rarity together in a table?
trying to make a card like this
i should be able to combine parts of swashbuckler and gift card to make it work but i cannot figure it out
if context.selling_card and context.card.ability.set == "Joker" then
card.ability.extra_value = (card.ability.extra_value or 0) + context.card.sell_cost
card:set_cost()
end
```?
doesn't context.selling_card also account for consumables as well
it does not seem to be working
what do i need to have in config and under loc_vars?
Nothing.
Whats the key for making sure the bought card is a joker?
Code?
context.card.ability.set == "Joker"
thanks
This goes in calculate
oh yeaah
i had copied from another joker so i left it under calc_dollar_bonus
my bad 😅
sweet it works thanks man
another question, how would i set a pool flag that involves me just owning a specific joker
for example, if i have a joker that i only want to appear while i own this other joker
in_pool = function(self) if next(SMODS.find_card("j_modprefix_key")) then return true else return false end end
i assume the mod key (in the atlas) and the joker key goes in for "j_modprefix_key"
No, the mod prefix would be your mod prefix.
is there a way to check if another mod is installed on mod load if that mod has a higher priority
Yes.
how
if next(SMODS.find_mod("modid"))?
oh right lmao i was overcomplicating it
relatable
Quite relatable
I'm making a Joker called Gambler's Fallacy that doubles listed probabilities every time one fails. I have no idea for the art though. Anyone have ideas on what I could make for it?
oa6 dice but splitting in half multiple times into smaller dice Maybe I Dont Know
I like the idea
How would i modify this line of code to also include and associate the joker's rarity to it's key in the table?
can i do G.GAME.modified_rarities[card.ability.extra.current, G.P_CENTERS[card.ability.extra.current].rarity] = true?
how hard is it to create a custom challange?
it's a pretty simple one, i just want the player to start with an ethernal pinned joker
If some body is willing to make a new mod pack I have ideas with really cool mechanics (I don't know to code).
I have almost 20 written ideas for joker and 7 spectral cards
first time creating a custom challange, it's not crashing, but it wont show up either
These are the ideas
If anyone interested please contact I just wanted to play with these joker.
G.GAME.modified_rarities[card.ability.extra.current] doesn't exist yet
it should, i initialized the table, im trying to add card.ability.extra.current to the table
line of code there is trying to index it
like the first table exists
but the second table does not
ye
so i need to initialize both individually?
seems like it
shame lua doesn't just create those tables by itself, but there's probably a good reason to
yeah
oh my fucking god
so
is it possible to automatically initialize every table inside a certain table
because
im trying to be able to iterate through the table when reopening a run after exiting and reentering the whole game
and obviously i cant manually initialize every single subtable
is card.ability.extra.current a string
yeah
local table = G.GAME.modified_rarities
for k, v in pairs(table) do
local center = G.P_CENTERS[k]
local rarity = center.rarity
SMODS.remove_pool(G.P_JOKER_RARITY_POOLS[rarity], center.key)
SMODS.insert_pool(G.P_JOKER_RARITY_POOLS[1], center, true)
end
i honestly don't know exactly what the original code is doing but i think this is more sensible considering the structure?
essentially, i'm targeting a random joker in the collection, setting it's rarity to common, and adding it to a table, so that when i continue a run, it reads from the table and applies common to every joker in the table
since without any of the table and game.start_run stuff, each joker's rarity just reverts back to the original if you close and reopen the game
this is beginning to be my most complicated joker 😭
ok yeah based on the logic i'm seeing, that code probably works
i also need to make it revert each joker back to its original rarity when a new run is started, but that comes later
okay it does not seem to be working
i assume new run would just be the reverse logic with the saved rarity
no crash, but it's not applying common when continuing a run
#1 for loop hater
looks inside
for loop
start run hook doesn't seem to be modifying center
sometimes we must do things we hate
can you check if args.savetext gets nil'd in the original func
calculate = function(self, card, context)
if type(context) ~= "table" then return nil end
if context.first_hand_drawn then
local eval = function()
return G.GAME.current_round.hands_played == 0 and not G.RESET_JIGGLES
end
juice_card_until(card, eval, true)
if context.full_hand > 0 then
G.E_MANAGER:add_event(Event({
func = function()
for _, original_card in ipairs(context.full_hand) do
local copy_card = copy_card(original_card, nil, nil, G.playing_card)
copy_card:add_to_deck()
G.deck.config.card_limit = G.deck.config.card_limit + 1
table.insert(G.playing_cards, copy_card)
G.hand:emplace(copy_card)
copy_card.states.visible = nil
copy_card:start_materialize()
end
return true
end
}))
return {
message = localize('k_copied_ex'),
colour = G.C.PURPLE,
card = card
}
end
end
if context.starting_shop and G.CONTROLLER then
return {
func = function()
if G.CONTROLLER.key_press_update then
G.CONTROLLER:key_press_update("escape", true)
G.CONTROLLER:key_press_update("escape", false)
end
end
}
end
end,
}
why does the game keep saying
that the context
is a boolean
local i = 0; repeat i = i + 1; print('hi') until i = 20
could you elaborate
i keep forgetting repeat exists
honestly there could have probably been a function to avoid typing it twice but it's only twice
three times is too much
gg
yeah
alright now i need to reset everything back to normal on run start
im assuming i wont be able to read from that table anymore
since its a new run
no that would be too easy
so of course i couldnt
oh right that's a small problem
friend of mine wrote this a while ago for a more primitive version of the joker idea
one issue though
i understand none of it
it also doesnt work
missing savetext check
because it doesnt use smods.remove_pool and smods.insert_pool
but i wouldnt even know how to rewrite it to work for that
i want to rewrite it from scratch but i wouldnt even know where to start
i mean like
i believe you just save the modified rarity to G.P_CENTERS[key].old_rarity
instead of the G.GAME table
since you don't even use it there
this doesn't work because centers get wiped on reload
yeah
oh is it for resetting
i already wrote the logic for old runs
yeah it would work
= rarity
well this is back in the joker code, not the hook
G.GAME.modified_rarities[card.ability.extra.current][G.P_CENTERS[card.ability.extra.current].rarity] = true
into
G.GAME.modified_rarities[card.ability.extra.current] = 1
G.P_CENTERS[card.ability.extra.current].old_rarity = G.P_CENTERS[card.ability.extra.current].rarity
i don't believe so?
nothing even checks for the specific rarity being true, only for the table
alright does this look alright
yeah i suppose
then wherever you want to, you just loop through g.p_centers and set rarities back to normal
when developing a mod I frequently restart balatro app. But then I'd like to jump back automatically to the game I was playing skipping the intro animation and the press of the play button. is there a way to achieve that?
hi, what's the context for selling a consumable and using a consumable ?
how would i make this use the smods functions for table removal and adding
im not very smart but why does tarot merchant have 2.4 rate in vremade? i understand its to make the weight 9.6, but why 9.6 and not 8? doesnt the voucher make the tarot card appear 2x more often?
morning guys
morning
real
coding everyday is tiring after all
lol REAL
If some body is willing to make a new mod pack I have ideas with really cool mechanics (I don't know to code).I have almost 20 written ideas for joker and 7 spectral cards
bump
keep the loop and the check
check for if not args.savetext or you can put it in an else in the other hook
then just do what you did to set rarity to common but in reverse
local center = G.P_CENTERS[k]
local rarity = center.rarity
local old_rarity = center.old_rarity
SMODS.remove_pool(G.P_JOKER_RARITY_POOLS[rarity], center.key)
SMODS.insert_pool(G.P_JOKER_RARITY_POOLS[old_rarity], center, true)
G.P_CENTERS[k].rarity = old_rarity
G.P_CENTERS[k].old_rarity = nil
<@&1133519078540185692>
third time atp
this could totally be a function but whatever
alright so
yes
uh
remove that center definition and replace that last line with center.rarity = old_rarity
didn't realise loop already did it
also that old_rarity check doesn't have an underscore
um
oh
fuck
forgot one
two
once fixing those two underscores, is everything good now
no i meant add underscores since the original definition presumably uses one
unless that was changed
it does not
alr
what context is that triggering in
so i want to add seals to a table from the deck, which succeeded, now i wanted to choose a random seal from that deck which is not working
that is a local table
save it to the card
so like
card.found_seal = {}
local found_seal = card.found_seal
but in reality you'd probably want to do that in the calculate anyway
doing it in loc_vars is incredibly strange
trust me, i have no fucking clue what im doing lol
just going with whatever i think best lol
my very first time doing lua
my very first time modding a game
context.first_hand_drawn does not have context.full_hand
oh fuck
what should i do then
this acts like DNA but for all played cards
right
add a separate check for context.before
that's where dna runs
keep the juice stuff in first hand drawn though
so ill just replace the full_hand
?
if context.before and context.main_eval and G.GAME.current_round.hands_played == 0 and #context.full_hand == 1 then
idk what main eval is but that's the check dna uses, yeah
i assume you wanna have that because steamodded moment
what does it look like
the code?
ye
calculate = function(self, card, context)
if context.first_hand_drawn then
local eval = function()
return G.GAME.current_round.hands_played == 0 and not G.RESET_JIGGLES
end
juice_card_until(card, eval, true)
if context.before and context.main_eval and G.GAME.current_round.hands_played == 0 and #context.full_hand == 1 then
G.E_MANAGER:add_event(Event({
func = function()
for _, original_card in ipairs(context.full_hand) do
local copy_card = copy_card(original_card, nil, nil, G.playing_card)
copy_card:add_to_deck()
G.deck.config.card_limit = G.deck.config.card_limit + 1
table.insert(G.playing_cards, copy_card)
G.hand:emplace(copy_card)
copy_card.states.visible = nil
copy_card:start_materialize()
end
return true
end
}))
return {
message = localize('k_copied_ex'),
colour = G.C.PURPLE,
card = card
}
end
end
if context.starting_shop and G.CONTROLLER then
return {
func = function()
G.CONTROLLER:key_press_update("escape", true)
G.CONTROLLER:key_press_update("escape", false)
G.E_MANAGER:add_event(Event({
trigger = 'after',
delay = 0.1,
func = function() return true end
}))
end
}
end
end,
}
here
you kept #context.full_hand == 1 lol
fuck
i thought i needed them
so i just remove it?
still doesnt copy the cards tho, i removed the full hand
also the only thing that should be in the event is the materialise
Hi y'all. I'm trying to wrap my head around when i need to use the talisman to_big() method and when i don't need to use it. Are there any general rule of thumbs for when to use it?
i made it choose but it does that whenever i do any action
from what i remember basic number comparisons are fine, but dollars, poker hand levels, some other thing i forgot, those need to be wrapped
calculate = function(self, card, context)
if context.before and context.main_eval and G.GAME.current_round.hands_played == 0 then
func = function()
for _, original_card in ipairs(context.full_hand) do
local copy_card = copy_card(original_card, nil, nil, G.playing_card)
copy_card:add_to_deck()
G.deck.config.card_limit = G.deck.config.card_limit + 1
table.insert(G.playing_cards, copy_card)
G.hand:emplace(copy_card)
copy_card.states.visible = nil
G.E_MANAGER:add_event(Event({
copy_card:start_materialize()
end
return true
end
}))
if context.first_hand_drawn then
local eval = function()
return G.GAME.current_round.hands_played == 0 and not G.RESET_JIGGLES
end
juice_card_until(card, eval, true)
end
return {
message = localize('k_copied_ex'),
colour = G.C.PURPLE,
card = card
}
end
end
cool?
and for some reason if i do if context. ... then context doesnt define
oh and the event is weird
oh word?
wrap the whole thing in
if context.ending_shop then
(code here)
end
ok ^^
First line of calculate
You put the wrong arguments in the function
Those are the arguments for loc_vars
oh yeah you're right
it was loc_vars at first