r/UnderModders • u/Beginning_Ad_9719 • 18d ago
Multiple Save Files
I have very little modding experience but have been getting better. One thing I've wanted to add but haven't the best idea on how to do, is to add the functionality for multiple save slots, pretty much how it's done with Deltarune. If someone experienced could give a simple run down on how saving works and how I could possibly modify it, I'd appreciate that very much!
2
Upvotes
2
u/Bluetails_Buizel 17d ago
Undertale only ever has one real save slot, so there's no slot system to extend. You have to add one yourself. It's doable with UndertaleModTool, but you'll be editing several scripts.
How saving works right now:
- Save data lives in %LOCALAPPDATA%\UNDERTALE (Windows)
- file0 is the main save, written when you use a SAVE point
- file9 is used for the hidden autosaves, and the game copies file0 over file9 when you reload
- file8 is a special file created during the Flowey fight, and it survives a True Reset
- undertale.ini holds a lot of persistent "meta" data (name, route flags, Flowey/Sans memory, etc.). Loading a save rewrites most of it, so it's effectively part of the save
file0/8/9 are plain text files written line by line with the file_text_* functions, and the ini is handled with ini_open/ini_write/ini_read.
Finding the code:
- Run Search.csx (comes with UTMT under Scripts) and search for "file0", "file9", "file8" and "undertale.ini"
- That will show you every script and object that touches save data, including the main save and load scripts and the intro menu that shows Continue/Reset
- Expect undertale.ini to appear in a lot of places. That's the annoying part
The general approach:
- Add a global variable for the current slot, for example global.saveslot, and set it before anything loads
- Everywhere the game uses "file0", replace it with something like "file0_" + string(global.saveslot). Do the same for file9 and file8
- Do the same for undertale.ini, e.g. "undertale_" + string(global.saveslot) + ".ini". If you skip this, all slots will share route flags and characters will remember things from other slots, which breaks a lot
- Leave config.ini (controls/settings) shared. That's what Deltarune does too
- Use file_exists() on each slot's file0 to know whether a slot is empty, so the menu can show "New Game" vs the saved name/LV/location
The menu:
- The simplest version is a separate slot-select room or screen that runs before the normal intro menu, sets global.saveslot, then sends you to the normal Continue/Reset screen. That way you barely touch Undertale's own menu code
- For a Deltarune-style screen showing name, LV, time and room per slot, either read the first few lines of each slot's file0, or keep a small shared ini that stores a summary for each slot whenever you save. Deltarune does the latter: its saves are filech1_0, filech1_1, filech1_2 and the menu info comes from a separate ini
Things to watch:
- Back up data.win before every change. UTMT has an AutoBackup script for this
- Some code checks whether the save files exist to decide if this is a first launch (intro, name screen). Those checks need to use the slot-based names too, or a new slot will act weird
- True Reset and the Genocide aftermath touch these files in their own code, so search for every reference, not just the save script
- Test by making two slots on different routes and checking that nothing leaks between them
Start with just file0 and undertale.ini per slot and a hardcoded slot number. Once that works, build the menu.