#💻・modding-dev
1 messages · Page 93 of 1
what would be the right context
oh wait I cant read nvm
i need it to give mult during joker_main
i based the code on gros michel2 from the steamodded example mod
this like is g.scoring_hand[i] = g.play.cards[i] iirc which is the effect that makes it so every played card is scored
there's zero possible way it could be splash
I'm 99% sure this issue is being caused by banana tree
was that screenshot from the lua dump?
yes
and the highlighted line is 1445
reproduced it on red deck with no sleeve on red stake
it has to be banana tree
you've got an extra end before your return
huh
so you're returning this in EVERY context
oh
if you had proper indentation it'd be obvious
also why do you track how many cards have been splashed in two variables?
that might be a logic error
I don't see the need for your remaining variable
And once again the day was saved thanks to the Powerpuff Modders
uhh
hold on
oh
it crashed when i played a splashed card
but this crash it different i can fix this one :D
i can't fix this one i don't understand it
crashing on 475 which is this one and it says it's a nil value??
well it says "attempt to index field extra (a nil value)"
but i defined the value properly and it works in the joker description
you redefine card in your loop
oh
to a playing card in the full hand
yup
it works now
i think i want to change one more thing about it though (before i test if the pool flag is working)
currently on the hand it goes extinct
it goes extinct before giving mult
i want it to give mult first, then die
but you can't execute code after a return can you
the destruction needs to be in context.after
gotcha gotcha
oh shit i think i see
did you fix it?
yeah
cool cool
i just forgot that it returns multiple things
the pool flag worked okay
how tf do i make a blueprint?! as a smods joker
nvm
i got it
i took some insparation from cryptid
why does it not undisable wtfff
my modded jokers show up as incompatible with jokers like blueprint and brainstorm but they work just fine, is there a way i can make them show as compatible?
is this on steamodded 1.0.0 or 0.9.8
that looks like steamodded 0.9.8
nvm i think i got it
other mod made on 0.9.8 was worked on 1.0.0, but this doesn't work
(other mods are here: https://discord.com/channels/1116389027176787968/1220733310360359033)
ur code prob: "if flipped then disable"
okay, I will make by 1.0.0 code
question, how do i check for the amount of jokers you have?
#G.jokers.cards
and the joker limit is G.jokers.config.card_limit i think
like the amount of slots?
joker slots yeah
nice
#G.jokers.cards is how many you have cause the # is length
and it's a thing with all your jokers in it
thanks!
what do i use to update the amount of money during a blind?
like business card or to do list
ease_dollars
that works but its not quite what i had in mind, im using this for a joker and theres no indication for it being caused by the joker
you can throw a card_eval_status_text in for a visual message on the joker too
thank you
just like me, start with a crazy mod idea, and then begin easy against your will lol
or you can first learn coding and come back 🤷♂️
so true
get stupid idea (preferrably a joker for beginners)
learn about stupid idea
create stupid idea
become famous
lol

this 4th step is still getting me
same........
one day ill be cryptid.....
right?
one day i'll make good enough art 😭 anyway how do I force deselect cards
figured it out
CardArea:unhighlight_all()
Does this break that one boss with the card must be highlighted?
actually, yeah, it probably does
this extra card selection stuff is all really out of my territory
i don't know how to fix it so i think i'll just leave it
selling this specific joker to deselect this specific card from this specific boss blind is very specific that i think its chill
it's essentially the same as "all cards debuffed until 1 joker sold" so /shrug
as a sanity check, can you verifty file integrity in steam?
chat how the fuck does the fish work
nvm im stupid
how do i get a drawn card tho
half of pot of greed
My suggestion is to try and make an one-Joker mod
okay so how do we make a deck add playing cards to the deck
specifically, at the beginning of a run
for that matter, how do you do things at the beginning of a run in general
i somehow just now remembered that sixsuits does exactly what i'm trying to do and i can just look at that
i've been trying to think of a mod that already did the thing for days <.<
how can i check to see if a card is a playing card?
ok got that figured out, do cards from the playing card booster packs have card.playing_card?
i know its not going to work
but imma try anyways
just like expected, didn't work
just retriggered the first joker a phew times
you never change the card.ability.extra.queue in your retrigger block
what?
when you enter this calculate function in the context you want (context.retrigger_joker_check) the queue is set to 1, and you return before oyu ever change it
so.. put the return at the end of the code with like a:
wait no, i don't make any sense
don't return in the else block
again, you're only changing the queue value when you get a match and return
so this is infinitely repeating if the context.other_card isn't your first joker
ooh so i should put the repeat above the context.retrigger_joker_check line and add queue + 1 right under it
what are you trying to do?
just retrigger all jokers
look at cryptid's retrigger stuff, I'm sure there'll be something in there that does this
oh ye canvas
@wintry solar I have a question about Enhancements. In the documentation, you say config can hold default values that are calculated automatically, but both in the calculate example and in Ortalab you manually define {extra = {x_mult = …}} and calculate it
I never use the default stuff
Well, but it's there, so I would like to understand how it works
The documentation wasn't clear to me
afaik you can simply put config = {xmult = 2}, and it'll work
But I guess if I define x_mult inside config, then I don't need calculate unless the Enhancement does something else?
I believe so
Something like this (WIP)
looks good, give it a try
is there any way to remove the yellow squiggly line under every global variable 😭
The nameplate needs work. Now let me test it
yeah I don't know why the name plates have a title in the collection
It's something to do with Enhancement API using SMODS.Center's generate_ui function, which forced the name to show up even when they shouldn't.
I didn't even notice the name plate on the bottom
I was talking about the white one on top
The x_mult didn't x_mult
Are contexts for cards in the deck or discard pile evaluated?
It starts at 1 so it should only work after you defeat a Boss
But if it doesn't look everywhere then I guess nothing got upgraded
you'd have to patch your own upgrade evaluation in
I just realized I wrote something stupid
Lemme fix the code and try again
But I guess I will need to end up patching anyways
you will
Also I don't think the description automatically updates to show the default bonuses?
what do you mean?
I thought Bonus and Hiker shared a variable
Or maybe they just have the same name
But are in different tables
@wintry solar how do I change the name plate color?
White on white is hard to read
that name plate shouldn't be there
errrm, any vscode experts know why my explorer button is showing my git stuff and I can't browse my project?
send screenshot
did you accidently drag the tabs into the thing?
Ok so it seems Lovely won't work on apple arcade macOS
Only modifying files directly will work
Hii, im planning on making a reskin mod of the game with my assets n whatnot, but I dont know a lot abt the modding stuff here, is there any kinda beginners guide or somewhere i could get started on coding wise? Art's literally all done already
Steamodded has a wiki but it's kind of incomplete in some areas. https://github.com/Steamopollys/Steamodded/wiki/01.-Getting-started If you want to just replace all the sprites take a look at this example mod https://github.com/Steamopollys/Steamodded/tree/main/example_mods/Mods/NegateTexturePack and also take a peek at https://discord.com/channels/1116389027176787968/1300851004186820690
ohh alrighty!! thank you v much :D
How would I detect if both the small and big blind are skipped?
There's an object you can check somewhere
I forget what
But probably somewhere in G.GAME
anyone know where I can find a blank template for jokers to draw my own textures for them?
Made a shitty copy of one incase anybody needs
Where does the game trigger the fire effect for score
At the score counter
How would I detect whenever money is earned? I want to make a joker that gains 1 chip for every $1 you earn
hmm
you could try making a new context by hooking into the ease_dollar function thing?
i should probably figure out localization files at some point
i don't understand how these things work
what we did works as far as we can tell but it involved deleting some of the code we had lifted from bunco
in_pool = function(self, args)
if args and args.initial_deck then
return false
end
return exotic_in_pool()
end
this is from the old suit code
the question is: what does args and args.initial_deck actually check?
(in case it matters, the current version is:
in_pool = function(self, args)
if G.GAME.starting_params.treat_Deck then
return true
end
return exotic_in_pool()
end```
and treat_Deck is set to true by the deck that adds the suit)
we played through a run and didn't find any unexpected behavior
I've come to the conclusion that this is a bit out of my league for being the literal first joker I am attemping to code
Nevermind figured it out
how can i add custom challenge rules? ex. no planet cards
Does anyone have tips for learning how to code new jokers in? I’m having trouble getting started 😭
example mod with vanilla jokers recreated in smods format
refer to it for things like probabilities, incrementing a value, end of round and mid round money, etc
also this https://www.balaui.dev
i learned about this recently its very helpful
it'll give you code structure for things
maybe a bit late since you already got it working but still
the question is: what does
args and args.initial_deckactually check?
it checks if args is not nil (so, in_pool is called with argument), andin_poolcheck is called by SMODS with the argumentinitial_deck = truewhen the playing cards first populated by the deck in general
For Bunco's code case - otherwise (like in shops, standard packs, Grim, etc), it fell out of that block and return the result of exotic_in_pool() function instead, where additional suit can spawn when exotic suit system is active (played spectrum hand once)
You might want to change that part of your code as well if you aren't tying it to Bunco's exotic suit
Oh thats sick as balls tysm
i see, i think
i did copy the exotics unlocking system since i wanted my custom suit to have similar "unlock during run" traits
though i never really decided whether or not i actively want it to unlock at the same time as fleurons and halberds if someone is playing both mods
woo
M
hey, how would i make it so press_play's effect doesn't trigger if the hand is debuffed (and thus it doesn't crash the game from having a hand with no cards scored)?
SMODS.Blind {
name = 'The Fracture',
key = 'bs_fra',
atlas = 'frabossatl',
dollars = 5,
mult = 1,
boss = { min = 1, max = 10 },
loc_txt = {
name = 'The Fracture',
text = {'Destroy first scored card',
'Must have 2+ scoring cards'}
},
discovered = true,
boss_colour = HEX('672A62'),
debuff_hand = function (self, cards, hand, handname, check)
if #cards < 2 then
return true
else
return false
end
return false
end,
press_play = function (self)
G.E_MANAGER:add_event(Event({func = function() G.play.cards[1]:start_dissolve(); return true end }))
return true
end
}
Where are the valid hands stored? Like all hands that have been unlocked for that run?
Hey, I'm trying to have my Joker destroy played hearts cards and add it to Xmult, I tried putting this into my .lau file, but when I hover over it in-game, it crashes.
this is the error message
Send your code
key = "P5JokerMod",
path = "p5card.png",
px = 71,
py = 95,
}
SMODS.Joker {
key = 'P5JokerMod',
loc_txt = {
name = 'Phantom theif',
text = {
"NOW {X:mult,C:white} X#1# {100} Mult WILL: destroys playes {C:hearts}Heart{} cards and adds {X:mult,C:white} X#1# {} Mult "
}
},
config = { extra = { Xmult = 100, Xmult_gain = 1 } },
loc_vars = function(self, info_queue, card)
return { vars = { card.ability.extra.Xmult, card.ablity.extra.Xmult_gain } }
end,
rarity = 1,
atlas = 'P5JokerMod',
pos = { x = 0, y = 0 },
cost = 2,
calculate = function(self, card, context)
if context.joker_main then
return {
Xmult_mod = card.ability.extra.Xmult,
message = localize { type = 'variable', key = 'a_xmult', vars = { card.ability.extra.Xmult } }
}
end
end
}```
it might be the text because I haven't changed it to the new one
wasn't it
^
god damn it
thank you
I also thought card.ablity.extra.Xmult_gain was it because I don't think a card existed with that
persona mod? 👀
Yes, it’s based off Joker from Persona 5.The idea for it is to have him destroy played heart cards (stealing your hearts) and adding them to xmult (like vampire)
makes sense
If you have any insight feel free to share
I would also like to make a challenge where you have a deck full of hearts and star off with the Joker
i'm more experienced with 4 than 5
I managed to get everythin goin and put the texture pack in game (not using Malverk's texture pack manager though..)
Ive been lookin around but haven't been able to find it, how can i rename the existing jokers so they'd fit with the ones I made? (for example Luchador to Luchadora since it's a female character in that joker lol, or renaming the legendary jokers n stuff)
You could either take ownership with SMODS.Joker:take_ownership('joker_key',{code here}), I think loc_txt.name = 'whatever' might work, if not, just do loc_txt = {} and then grab the description and name from the localization files and throw them in.
Alternatively, you can do function SMODS.current_mod.process_loc_text() followed by SMODS.process_loc_text(G.localization.descriptions.Joker.joker_key, "name", "NameReplacement"), but it's a bit overkill for just switching joker names, but it's useful if you want to change the name of anything else, say an effect that gets triggered, like if you wanted to change Gros Michel's extinct for some reason.
does SMODS.Mods["<mod here>"] search by mod name, mod ID, folder name or something else
oh thanks a lot!! :D helps a lot
My first assumption would be most likely ID, then mod name, then possibly folder name, I don't think it'd be that hard to test for, though. Just try renaming your mod ID and name and such and see when it can find it and when it can't.
well that's what I have been doing
but none of those three have worked
What are you trying to do?
check if a mod, in this case, SDM_0's stuff, is loaded
There's something about dependencies somewhere, I assume you mean for compatibility reasons, give me a second to find an example,
yeah for this I can't have them marked as dependencies because that disables the mod if the dependency isn't found
i did also increase the priority to even higher than cryptid in case loading after/before the mod caused it and that didn't work
I'm pretty sure there's a SMODS specific line to check for it, but, I can't remember where I saw it,
Actually, double checked, though I checked Galdur instead, SMODS.Mods[ID] should work, are you specifically searching for SMODS.Mods['sdm0sstuff']?
i tried that and I also tried SMODS.Mods["SDM_0's Stuff"] and SMODS.Mods["SDM_0-s_stuff"]
none worked
Maybe try setting it to a lower priority as well.
the priority of this mod is like e308 is that not enough to load after
Probably, I'll download SDM0 specifically and see if I can find it.
After a lot of testing, I've realized, it's a lot easier to check a mod when you have it installed - I was testing in my dev copy of the executable, and, installed it into my normal copy, so, obviously, it wasn't finding anything. Still, though, this worked perfectly fine for me.
hhuh
well then i'm lost
maybe i just need to update steamodded
i'll try that before anything else
Possibly, and if it still doesn't work, maybe either directly copy and paste your code or send a screenshot?
That’ll also match when the mod isn’t loaded but is installed
You need to do the can load stuff
does someone know how to add text in description of modded ranks?
what would you add
+0 chips?
i want the 0 to have every suit, like a wild card
i implemented that, it's working very well
why would you want a second wildcard 😭
Also, does the current version of steammodded not have a way to replace the seals and the soul sprites? (The ones in the enhancements picture) Looking at the API, it seems to talk abt jokers n consumables, but not seals or the floating soul sprite
i'm trying to apply Xmult when a certain rank is scored but its not working
the return works if its activated with context.joker_main but thats when the joker is triggered
nvm i got it working
whats the context if i want to check each scoring card before they are scored? like how vampire clears all the enhancements before the cards are scored
thank you
will do that in the future
actually where can i find the source code for jokers in the game?
If you open the .exe as a zip/archive using something like 7zip or winrar you can access all the source code
thank you
guys i might start using lovely patches
wish me luck yall im boutta explode this pc
how do you make Sprites 😭
How are you trying to make a sprite
one, it's probably easier to use steamodded for atlases than lovely
and two, did you make a double-size copy for the 2x assets
trying to make it so the values of a joker increases when a blind is defeated but its upgrading multiple times
ong im so used to not needing the steamodded wiki that i forget to check it time to time
well im trying to make a sprite like this
G.ASSET_ATLAS['littleguy'] = {} --line 7514
G.ASSET_ATLAS['littleguy'].name = 'littleguy'
local filename = 'littleguy.png'
G.ASSET_ATLAS['littleguy'].image = love.graphics.newImage(jimbomod.path.."assets/"..G.SETTINGS.GRAPHICS.texture_scaling.."x/"..filename, {mipmaps = true, dpiscale = G.SETTINGS.GRAPHICS.texture_scaling}) --line 7517
G.ASSET_ATLAS['littleguy'].px = 177
G.ASSET_ATLAS['littleguy'].py = 100``` but i do not know how to make it load a sprite
nvm i just added a check
my title as the worst balatro modder of all time ™️ shall remain
why aren't you using SMODS.Atlas?
would I need to make a new game object for having my joker take played hearts cards and delete them?
any help?
i don't think you would? i'd imagine you'd be able to check your hand and then use the G.play.cards[x]:start_dissolve() function to destroy the card, right?
would it not be '''card.ability.extra.Xmult_gain'''
for trying to delete cards? no that's for multiplicative mult scaling jokers (eg. hologram)
oh ok
so I would put G.play.cards[x]:start_dissolve() in loc_vars = function(self, info_queue, card)
return { vars =
I'm just a beginner but why would it be else false then false again?
no, if you want to destroy a card it would be in the calculate() function of a joker
also you would replace x in there with the preferred card
the preferred card being the joker's key
i presume you have talisman enabled?
yeah it requires it
dont do to_big(G.GAME.blind.chips) = num
then what do i do
just do G.GAME.blind.chips = num
but what if its a big num
G.GAME.blind.chips = to_big(G.GAME.blind.chips) * to_big(0.95)
so what if its a big num?
you wouldnt be changing the blind's chips, you would be changing the result of to_big(blind's chips)
i'm kinda struggling here, i could use some advice
nevermind, figured it out!
it's this ```lua
press_play = function (self)
G.E_MANAGER:add_event(Event({func = function()
if #G.play.cards > 1 then
G.play.cards[1]:start_dissolve()
end
return true
end}))
return true
end
i have a :start_dissovolve() event in context.after but its activates before the cards have been scored
the message appears at the right time but the card is destroyed pretty much as soon as the hand is played
Neee to add it to an event so it doesn't disolve until the last queued event is run
i'll have to look into how to create an event but thank you
have ran into another issue, when the round ends and the cards return to the deck it comes back up to 52 despite there only being 51 in there
1 sec
yeah thats a ghost card
will have a look at how the cards in game do this sort of thing
game's haunted
like sixth sense
ok i'm now using context.destroying_card instead of context.after which stops ghost cards from being created
however after destroying the intended card it then destroys the entire hand
i think it chains off of each other
how do i make a G.Game value
It's just G.GAME.key = whatever value. Can't be local, though, since it's meant to be a global.
yeah thanks
do you know how i could tell how many of a aspecific joker i have
having trouble with this, is anyone able to tell me why this is happening?
how do i add eternal to info queue
I ran into this problem before. It's actually pretty simple. You have to set a variable on the card itself
Like so
wouldn't it be smth like info_queue[#info_queue+1] = { key = "eternal", set = "Other", vars = {} }
How would I pull a random tarot card
Where's the array I need to call pseudorandom_element on
Nvm realized I can just use the way emperor does it
you used () instead of {} for your return table
Hi friends! Im new to balatro modding and want to try my hand at making a custom deck with textures.
I know to open the archive and edit the 8bit decks, but i dont have the actual dimensions for when a suit is counted as a new texture. Would anyone happen to know that ratio? like is it 500 x 500? etc.
I guess in short, im looking the pixel dimensions for the idividual cards, and not the entire sprite sheet
71x95
Thank you!
It’s there a place that says all functions and where to put theme in your code?
can you elaborate a bit more?
Like each function that’s used for certain jokers and have it listed out so you know what to add to the code and where
if you're talking about documentation: https://github.com/Steamopollys/Steamodded/wiki/05.-SMODS.Center
Let me check it out and I’ll see thanks
how would I implement a card for every played heart card it destroys it and adds to a mult (like vampire
I would start by looking at the code for vampire
Looking through the card.lau in the source code, it seems it uses something {self.ability.extra, self.ability,x_mult}
calculate = function(self,card,context)
---context.after is after the hand is scored
---not context.blueprint means this part cannot be copied by Blueprint
if context.after and not context.blueprint then
---loops through every card in played hand
for index, card2 in ipairs(context.full_hand) do
---check for hearts suit, card2 is the value in the current loop
if card2:is_suit("Hearts") then
---destroy the card
G.start.dissolve(card2)
---increment xmult value by adding increase to the xmult value
card.ability.extra.xmult = card.ability.extra.xmult + card.ability.extra.increase
end
end
end
---return the xmult if it's above 1, this removes unnecessary animations/calculations if the xmult is 1, because no change would be made anyway
if context.joker_main and card.ability.extra.xmult >= 1 then
return {
---text pops up below the joker to show it's giving xmult
message = localize{type='variable',key='a_xmult',vars={card.ability.extra.xmult}},
x_mult = card.ability.extra.xmult,
---card = card tells the game the message refers to this joker
card = card,
}
end
end
something like this probably
this assumes your joker has config = { extra = { xmult = 1, increase = 0.25 } } where increase is the value it increments by
it should start at xmult 1
you do also need to actually return the xmult during joker main though which is really easy
edited the message to include that part i'm not sure if it'll work or not i'm just writing from memory
card.ability refers to the values in config, and you should put all joker values in the extra table in there
because the extra table is saved when the game is reloaded
cards in card.lua use self.ability.extra instead of card.ability.extra, if you ever copy code from card.lua you'll usually need to change self to card
steamodded stuff /shrug
Assuming I did it right, I wasnt able to fix the problem
You'd likely wanna add a debounce if you wanna stop the chaining
code would likely turn into smth like
if context.destroying_card and not already_destroying then
already_destroying = true;
G.E_MANAGER:add_event(Event({
func = function()
context.full_hand[#context.full_hand]:start_dissolve();
already_destroying = false;
return true;
end
});
end
which'd then make it so it wont destroy more than the 1 card
Is there a way to give myself my custom joker using DebugPlus? Also, are there any common reasons for the message "Failed to connect to the debug server"?
open collection/tmj, find the joker, hover over it and hit C
tyty!
thank you!
helped me find a solution that worked
Is there a way to display the +mult value of a playing card? The +mult applies correctly but from checking the code there don't seem to be any display strings
how would i make it so that a joker can only appear in the shop if a stone card is in their full deck?
like stone joker
check what stone joker does i guess
enhancement_gate = "m_stone"
thank you
Also, are there any common reasons for the message "Failed to connect to the debug server"?
This message pops up when you don't have the optional debug server running. It doesn't break anything, it's just a scary message haha
The actual debug server: https://github.com/Steamopollys/Steamodded/blob/main/debug/tk_debug_window.py
Hey all
Trying to see if this all work with some stuff, but idk how to even test it
What mods add new handtypes?
where is the config stored for a consumeable card?
would it be smth like card.config or card.ability.config
it depends where you're referring to it
it's only card as a prefix because the value is defined as card in function = (self,card,context) (at least I think that's how it works)
like on vouchers because it's redeem = function(self), you refer to its own values as self.config.extra
if it's in a loop say like for index, value in ipairs(G.consumeables) do (i don't actually know if that's the name for the consumable area or not)
then it would be value.config.extra or value.ability.extra
I don't 100% know any of this but this is my best guess from successfully implementing vouchers
so then you can do for index, value in ipairs(G.consumeables) do and it'll be value.config.extra try that
trying to make it so i can use a gemstone consumable directly from a pack, not going well lol
unless i'm really stupid, i should be putting G.pack_cards.highlighted[1] instead of c1 lol
nvm i figured it out, thanks for the help
balatro in 2024
illusion of free choice
anyways is there a way to force a set of consumable cards (ex. planet) to not spawn in a challenge?
THIS WILL BE CRYPTID IN 2014!
chat how do I check the stake sticker of a specific joker
Carefully
Damn I wish I could play mods with the Apple Arcade Mac version but injecting into it doesn't work
You can only modify the lua
Vanilla (M is crossed so no M)
Moderate
Madness
Monstrosity

explain
IDK
There some functions I don’t remember the name of that’ll give you the key of the stake
do you know where i can find them
core/overrides.lua in smods
Some updates on modding Apple Arcade on macOS. You can pass --game with a path to a custom game folder inside ~/Library/Containers/com.playstack.balatroarcade/ and it will use the lua files from there
you can probably just take a normal install of love and see if you can get it to load the game.love, and then put lovely in that one
The game folder is uncompressed in the Apple Arcade version
oh intresting
Issue with Lovely is that isn't it injected with native code?
no the issue with it is there no framework for it to find offsets for lua functions
the love engine in the apple arcade version is a bit different that the standlone version and due to this lovely can't get info it needs
ok can you check smth then
Sure
in the apple arade version of the app does Contents/Frameworks/Lua.framework exist?
Nope
yeah lovely needs that to function
try downloaidng this version of love https://github.com/love2d/love/releases/download/11.5/love-11.5-macos.zip, and pointing it at balatro's files. If it works then try setting up lovely (you might need to change the paths in the run_lovely.sh)
not sure how the issue is related to my message'
Attempt to index nil field platform
Using a different version of love probably won't work because it's modified to support Apple apis
Oh I see
The iOS and Apple Arcade version on macOS are the same
(The same in the sense that the lua code is the same)
Well it doesn't matter anymore because I got my steam key from humble
Damn the save files are not compatible between steam and Apple Arcade
they are probably stored in diffewrent spots
What I mean is the files aren't compatible
oh really?
I tried copying Apple Arcade to steam and nothing
could you send them
can https://balatro.shorty.systems/ parse them
there should not be nans in the save
There is no meta or profile in the apple arcade save
the website can't load all valid save files
intresting there is no meta or profile
the site should be able to open every .jkr file the game makes (other than a few weird ones from the demos)
but it's kinda a hacky parser so some things dont work right
It can open settings.jkr
it can open the save.jkr in 3 as well
this file isn't resposible for what's unlocked or not
What file is?
that would explain why there was no meta or profile
Thank goodness I made a backup of my saves
The backup did not have meta or profile
Cloudkit maybe
can you launch it offline?
looks like something is in there
which profile did you want?
hmm it has some kind of header not sure how to tell when the actual file starts
That showed up on my saves
Also I may have actually lost my save data now
@rough furnace can I dm you about some things?
Oh I didn't lose my saves I was just dumb and was running my modded version that has different save locations
Ok so it is using Cloudkit since my modded saves are showing up in ./Preferences/com.playstack.balatroarcade.plist
Ok figured where it's saved
It's stored in that plist file as binary data
Would anyone know the cause of this and how to fix it?
where would I put this in my code (assuming it's ok with you to just put this in there)
the calculate function is where the joker's ability goes
and yeah idm
ok thank you for the help
The two sides
https://www.balaui.dev/joker for code base
what is this?
a link
... I meant a link to what
So just confirmed it's in the plist file
get_joker_win_sticker?
its arguments are (_center, index), what do those mean
well center would be the cards center (probably card.config.center)
i don't know what that means so just
how do I run this for splash
looks liek the index is optional
what do i need to put in :set_ability({}) to actually set the ability?
I see thanks (did actually click on it)
do you have a splash or just what splashes would be?
set ability is run when the joker appears in a pack or the shop, you just put code in there to do things
just what splashes would be
i need this to be able to run even when you dont have splash
you'd have to look up it's center
just a sec
G.P_CENTERS.j_splash should work
yeah
I'm going to hack together a save extractor for Apple Arcade macOS version
~/Library/Containers/com.playstack.balatroarcade/Data/Library/Preferences/com.playstack.balatroarcade.plist is the path to the save file
how would i apply an enhancement to a card via a joker? before they are scored like an inverted vampire
i have it working for editions but i dont know what to use to enhancements
like mida's mask?
yes
i'd guess either card.ability.name == "Steel Card" or card.config.center = G.P_CENTERS.m_steel
i should look at how the game does that actually i forgot about mask
as an example for steel cards
thank you
that makes more sense
having another issue now I set the ability and edition at the same time but the edition appears before the ability does?https://gyazo.com/0f16f922b86e0ac5f46e93c1c1610b4f
putting the set_edition in the event causes it to appear at the right time but the effect doesn't apply to the played hand
:set_ability and :set_edition both have arguments by which they can (optionally) delay the visualization.
For some reason, the argument names and order are completely different, so you doing , nil, true for both messes it up.
Check the basegame code and you'll see what the issue is and how to solve it
Where did all of you get your start with modding? I'm trying to finally get around to making my mods, but figuring out where to start is a nightmare
A simple Joker. Steamodded has example mods for you to work with.
I very much did not but I would probably recommened taking a look at Steamoddeds examples and wiki https://github.com/Steamopollys/Steamodded/tree/main/example_mods/Mods https://github.com/Steamopollys/Steamodded/wiki/01.-Getting-started#creating-your-first-mod
Thank you!
Already huge place to start, though I wanna ask: how possible is it to modify existing content?
yep
the second argument for :set_edition appears to be if it will play its sound and juice up
most objects can be taken over using steamodded and if you want to modify stuff further you can use lovely or overwrite functions
probably silent then
Alright, alright, neat. I suppose it'd be fastest to post the planned patch notes for my mod before I go any further and see how possible everything is
lets just say pretty much anything is possible, as logn as you have enough time and deitcation
Reyna Cruz The Balatro Fan Patch Mod Patch Notes This is the outline for a mod I’ve made as a balancing exercise for Balatro! I’ll have to write patch notes eventually, so this is an excellent start to get practice for that eventuality. Special thanks to the Balatro University discord and all ...
This is what I'm planning so far, though I haven't updated joker pricings, which are probably going to change.
I don't think you can delay edition application in the same way you can enhancement
no jokers in game apply an edition so i cant reference it for that. when the spectral card "aura" applies an edition it simply just has the edition and true
thats unfortunate
I predict the trickiest thing to do will be to indicate which spectral card will be created with Sixth Sense and Seance in the joker description
Just went through the jokers:
Joker: probably need a lovely patch
Marble: Probably just take ownership reimplement calculate_joker
Loyalty Card: Probably just take ownership reimplement calculate_joker
Misprint: I think take ownership and change config works
Sixth Sense: This may be a bit trickier, but for the most part, just reimplement calculate_joker + loc_vars.
Seance: Same as above
Ancient: I think this would need a lovely patch.
Certificate: See Sixth Sense
Throwback: I think take ownership and change config works
Rough Gemstone: I think take ownership and change config works
Glass Joker: Probably needs a lovely patch to keep track when any glass shatters + calculate_joker change
Matador: Probably just a lovely patch(?)
Chicot: Probably a lot of lovely patches. Maybe could take ownership of blinds. WOuld need mods to add support```
the rest ```
Nebula: I think just take ownershop and change a config (not too familar with decks)
Antimatter: Probably needs a lovely patch. Make sure to account for antimatter not unlocked
Ouija: This might need a lovely patch. Debuffing is weird
Hex: Same as above
Wild card: Lovely patch
Blue Seal: Take ownership reiplement whatever methods seals use
Etheral Tag: Take ownership and reiplement (I think tags can do thata)
Why is ti NIL
any chance you spawned the card before it had the config option set?
thats a fair point
great
daisy_discount isn't defined
its = 1
where is it set?
thats not G.GAME.daisy_discount
and does that match anything?
also did you make a new game after adding the patch?
yeah
the variable need to be G.GAME?
well the one you're trying to use is
did you start a new game?
Damn, thanks so much!
how do i check if a card has a valid rank (ex. doesn't have stone or another enhancement that disables rank)
stone gives cards a negative id number
if other mods make cards rankless they'll probably copy that
(if your mod makes cards rankless you can just check for whatever you do :p )
smods apparently has a field no_rank on enhancements
IM GOING TO FUCKING LOSE MY MIND MY PATHC IS NOT PATCHING
check the lua dump
its not patching
there might be another mod patching at the same spot that could affect your mod's ability to match its pattern
check the place where you expect the patch to be
its unchanged
card:get_id() <= -100 is how I detect stone cards
but ima cry ina ball in teh cornner
Enhancements can have a no_rank variable in their config so you can check for that and cover modded enhancements with no rank
what's wrong with
if context.before then
for k, v in ipairs(context.scoring_hand) do
v:set_ability(G.P_CENTERS.m_bonus)
v:set_edition({polychrome = true})
end
end
```???
how is this failing there is nothign wrong with my patch
[manifest]
version = "1.0.0"
dump_lua = true
priority = 0
[[patches]]
[patches.pattern]
target = 'game.lua'
pattern = '''discount_percent = 0,'''
position = 'after'
payload = '''
daisy_discount = 1,
'''
match_indent = true
[[patches]]
[patches.pattern]
target = 'card.lua'
pattern = '''self.cost = math.max(1, math.floor((self.base_cost + self.extra_cost + 0.5)*(100-G.GAME.discount_percent)/100))'''
position = 'after'
payload = '''self.cost = self.cost / daisy_discount'''
match_indent = true
is it not G.GAME.daisy_discount? 🤔
(to read the value, not to set it)
would this work?
for k, v in ipairs(G.playing_cards) do
if v.ability.name ~= "Stone Card" and not v.ability.no_rank then
table.insert(rank_suffix, v)
end
end
il try that
i tried that but its the same result, polychrome visually appears early ☹️
no_rank is in card.config.center, not card.ability. But from the look of it this should work.
i think editions and abilities are just treated differently
so it should be
for k, v in ipairs(G.playing_cards) do
if v.ability.name ~= "Stone Card" and not v.config.center.no_rank then
table.insert(rank_suffix, v)
end
end
yea
nope
same crash
i fucging hate modding now
when does this crash?
well that might explain it haha
looks like this for me, is that not what you want?
seems to patch for me 👀
what does your folder structure look like?
Omfg
oh how strange, i must have made a mistake somewhere then. thank you😃, will look back at my code when i can. what you have there is the same as what you posted right?
it was even in the uploaded file 😭
Yup, exactly like in the code snippet I uploaded earlier
how can i check when a joker si gettin added or destroyed
Still having trouble with this, idk whats wrong with it 😭
Try updating Steamodded
Do I need to update the code at all? I have the latest version
Hi guys, is there a getting started modding for balatro guide?
loc_vars = function(fel, info_queue card)?
That was supposed to be self, idk why it got changed back 😭
That didnt fix it though 😔
Check out these two.
https://github.com/Steamopollys/Steamodded/wiki/01.-Getting-started
https://github.com/Steamopollys/Steamodded/tree/main/example_mods/Mods
Same exact error, or did it change?
Same error
This isn't tied to the code you screenshotted tho
This is from the loader
This is well before the mod file is loaded
What's your header?
So this is something else entirely? It doesn’t show up when the mod isn’t in
Specifically, some mod failed to load
This is an older screenshot (cant use my computer atm) but header is the same
Mod author needs to be in [] brackets.
And said failure has mod.load_issues.dependencies set to nil instead of a table
How would I go about fixing that then?
I don't know, I haven't seen an error like this
Does the mod load by json by any chance?
I see some mod with prefix "ExtraCredit" but it doesn't show up on crash log
I found it!
Whatever mod is loading through json cannot find it's main_file
Also, looking at the line numbers, it's missing --- STEAMODDED HEADER as the very first line.
That seems like something that'd cause it to not load rather than a crash, but, there's been weirder things.
there we go
#⚙・modding-general message
you pass the colours through in loc vars
return {vars = {X, Y, colour = {colour1, colour2}}} iirc
I would probably just embed the color data in the strings for each suit no?
It's colour = {ColourVariable}, but, yeah.
that's what I said?
Yeah it’s essentially the same thing just dif var names
Colour only reads 1 object, which has to be a variable that changes, I'm pretty sure, so the colour2 wouldn't get used. But I might be wrong.
it reads however many you pass, you just use V:1 V:2 etc.
Makes sense, thought you were passing both to V:1. My fault.
no worries!
do lovely patches work if they're not in the first folder?
Don't think they do, but it might've been changed since I tried it which was quite a while ago - But, it either checks for lovely.toml or a folder called lovely and reads all .toml files inside of it - useful for organizing a mod, not as useful if you're trying to group your mods up into specific folders.
ahhh gotcha
What mods do you have?
is there any one looking for a modeler
i hear that the 2d in love2d stands for 3 dimensional
is there a way to add a joker to the soul?
A Legendary Joker?
yeah
Add a Legendary Joker
done
i already tried spawning it from soul but after the base 5 it started returning the default joker
how does one go about making a soul-alike that summons from a specific card pool? i looked at #1292971421349445785's poke balls and #1219749193204371456's gateway, but i couldn't really work out what they were doing
-# (actually maybe spaghetti would be a better model, I'll look at that one when i get a bit)
as for this i'm reasonably sure that being legendary is the only condition for the soul to be able to summon a legendary; i'll double check but i recall being able to summon lucky in my mod without doing anything special (e: yes confirmed, the soul can summon this cat)
how i make a animation atlas? i cannot look it up since the wiki is outdated
i assume its the same as a normal atlas but with frames?
the wiki has stuff for animation atlases
no response since, i mean i need a modeler for a model pls
this game is 2d, it doesn't use models
let them cook
Depending on what you want it needs to be a custom pool
yes true
how do i construct that pool?
i already know what jokers i want to put in it
undeniable combo
basically, the create_card function has this big ass thing in the start of it
so basically:
if not forced_key and soulable and (not G.GAME.banned_keys['c_soul']) then
if (_type == 'CardType' or _type == 'Spectral') and not (G.GAME.used_jokers['c_thecardkey'] and not next(find_joker("Showman"))) then
if pseudorandom('soul_'.._type..G.GAME.round_resets.ante) > 0.997 then
forced_key = 'c_thecardkey'
end
end
end
Lovely, steammodded, and the custom one
did it like cryptid does, idk what went wrong? ._.
hm
it looks the same as how i did it in my mod, too
what's 777.png look like?
that looks fine enough
where is it located in your mod's file structure, and does it have both a 1x and 2x version?
ye it does
Idk what's going on
certainly looks the same!
._.
what fixed it for you?
minirebel's lovely is outdated but crimson heart's isn't
other than that you have the same versions
i don't know what's different, i never got this error
damn, didn't know that lol, never noticed
How are you trying to use it?
my version of steamodded is 1122a
maybe updating will fix it
(and if it doesn't, well, you'll still have updated steamodded, which is useful)
just a animated joker
I don’t remember if the game can handle animated jokers by default
I would air on the side of it can’t
broke my game lol, no mods anymore
oof
would suck for aura (animated jokers) if so
Aura works around it by updating the position every frame
I’d imagine that’s also what math does for his animated jokers in cryptid
They have their own update and draw functions iirc
hologram is animated but i think it uses a shader
it doesn't have animation frames
Hologram isn’t an animated sprite
hologram, legendary jokers and soul card have another texture on top of the card
legendaries aren't even animated, they just have two layers
yes that's what i'm saying
hologram does a flickering thing and soul beats
that's more than simply having a second layer
oh that
that's the shader
(i use soul_pos for my many placeholders, so i am quite familiar with that function :p )
its fine if not possible tho
does someone know how i could add text here
ouch
uh oh!
i used a spectral card and i crashed
Why is there a nil in your spectral pack
its supposed to be a special spectral thing
i have like 3 of those special spectrals
i forgot about nil though 😭
m7
ig am remaking the jokers i lost and wth? it looks good, i think i had them like before
1105 is the row with G.jokers.cards[schemetic - 1]
chat, is it possible to make a lovely patch about other lovely patches
steamodded has this negative thing that allows negative playing cards to give +1 handsize
Simple question: How do i target another item's loc_Var?
See, I wanna get the config for investment tag for a card I have
yeah uh
you dont
you kinda have to hardcode it
unless its modded
(afaik)
depends, you can probably patch such that you have a goto before the smods patch attached to a label that you patch in after and just skip over the SMODS line
okay then what about this
no that wouldn't work
I was gonna say have a variable that checks a specific config
take ownership
lol i added a # where it wasn't needed
now that i think about it it'd be easier to replace said goto with "if false then" and said label with "end"
redefine loc_var
I don't wanna just take ownership
loc_vars = function(self, info_queue, card)
return{"Investment Tag's config.dollars"}
end,
that's all i wanna do basically
okay and i don't wanna do that because i don't know anything about it
It's like defining a Joker
Steamodded uses the vanilla base and only replaces what you tell it to
I think there's an option to do it quietly
if you don't want to attach a modded badge to it
only reason I was asking was because of Misprint Deck in Cryptid and stuff like that
But tbh, not worth my time. Just gonna just put the number in as is.
make it Future Me's problem
because once again, I don't know anything on what or how ownership works
and idk if me doing that will break other mods, which is kinda bad for a lib to do
I think you just need to do
SMODS.Joker.take_ownership(`joker`, {
loc_vars = function(self, info_queue, card)
return {vars = {…}}
end
},
false)
it's the other way around
if you don't take ownership, you can break other mods
huh?
It's not a joker i'm doing though
If two mods try to change a Joker, and they don't communicate, unexpected things can happen
You can change it to whatever it is
including tag?
then we should test and make it expected :D
lol
Should be, there exists SMODS.Tag
Take ownership manages conflicts as AFAIK the first mod to try to change a specific value is the one allowed to do it
ok so how is this gonna help me ?
Well, it allows you to redefine the loc_vars function of whatever Tag
but i don't wanna edit the tag
You don't edit the Tag, only its loc_vars function
ok I'm not understanding
I'm making a consumable to have the description of Investment tag to make it nice to look at
YES
lol
I want the variable from Investment tag
That way Investment Card and Investment tag have the same number
I think I just hardcoded when I tried to do it XD but in theory the object exists somewhere and can be accessed
elseif name_to_check == 'Investment Tag' then loc_vars = {self.config.dollars}
Since it's a Tag, I don't think the Tag pool is every emptied, so you can probably iterate over the pool, find the Tag, then retrieve the value
Actually you don't need to iterate since you have the key
So you just access the object directly from the Tag pool
Hm?
Hmm?
I haven't put anything in
So for Investment tag having "loc_vars = {self.config.dollars}"
I put then...
idk
I'm having dumb crim moment lol
Let me see
Why don’t you just calculate it in the loc vars yourself?
Becuase all it does is give you a tag
I just wanted it to have the effect of the tag in the description
Yeah so just do the calculation that the tag would do
What? self.config.dollars?
No, however that is calculated
You can, but what are you trying to adjust?
I think I found it
G.P_TAGS[_tag]
That's where Tag prototypes are
So you can find the config there
Thus G.P_TAGS['tag_investment'].config.dollars should be the variable you want
@wooden nexus
also format the loc_vars output correctly
yeah... if i can figure that lol
It's on the wiki
negative card things
Now I've learned how to do this
thas basically it
My Milk gets stronger
Hopefully this will work for the other tags too
Because I know I'll need to do it for other tags
Yes but what specifically?
I'm such a great coder
im tryna make a joker that makes spades act as negative cards
You can duplicate the patches then in that case
omg i think i found an easier way
didnt need to do anything interesting really
In calculate function of a Joker, if modifying own values, is it better to use self instead of card?
card
...as I was using, whew.
self refers to the framework of the object itself stored in G.P_CENTERS, whilst card is the individual object that you're calculating
Was just wanting a "juice up" animation on a Joker when during the Voucher purchase, the card = self part confused me on the wiki.
if you look at the games calculate_joker function, self there is equivalnt to what card is in SMODS calculate_joker
this is due to differences in what the function belongs to
chat i got two new things to do
i need to display custom info queue and i need to display multiple info queue
can't figure out how to do that
display on a card you control or another card?\
you can add as much as you want to info queue
Also that
a joker that is in my mod
You should just be able to push it in your loc vars function iirc
well I tried that but it didn't really work
You can define a new one like I do here https://github.com/WilsontheWolf/JamMod/blob/master/Jokers.lua#L14 (or in a localization file)
Send code
infolist is a list with a bunch of entries that have name and text fields
from looking at how other jokers do it it made sense that it'd be set up that way
but it doesn't display anything so /shrug
yes i closed locvars properly it's just cropped
The values your pushing should look something like
so i need a key
what's that for
how does the code know where the key is from
my mod doesn't use a separate localisation file so idk
i probably should use a separate file for localisation idk if anyone cares enough about my mod to translate it
whats the internal id of oops all 6's? i cant find it in the source code (i.e: j_vampire)
j_oops
You can add entries without a localization file if you want
thank you
what does your infolist look like?
yeah i'm gonna try that and see if it works
but how would I loop it such that it goes through all of them
is that possible
Yes
loop through a list of keys
damn I've been stalling with steamodded quite a lot, we should get beta out
secret
what does the set field mean
if anything
we should wait for the meta tags pr (there will never be a beta)
Can the path to a sound contain a subfolder too?
try it and see
it should
dep branch is one month stale
i don't even remember if there was something that was yet to be done for that
[SMODS _ "core/game_object.lua"]:410: Could not open WAVE
The path is defined as "plus95/Windows 95 menu command.wav" and the path is valid under the sounds folder.
oh yeah that too
show directory structure
might just merge and see if any issues come up :zany_joker:
was it ever finished?
hmmm
see if it works without the sub directory
and if not the spaces could be throwing it off maybe
not sure
seems unlikely
Moved to root of sounds, still crash. Removed spaces (i.e. Windows95menucommand.wav), nothing.
That is what I was actually wanting to avoid by using the .wav files directly.
i think so, but I don't think it's all been properly tested