Save system (870022)

Hello everyone. I am searching for a way to create a solid save system for my project. This is not only a way to save a few values, but a full information about game status. In my project, there is only one scene in which progressively some levels are loaded - and others unloaded according to the player’s progress in-game. Some objects are available - others not always according to player progress in-game. Is there a way to save in file the full status of a game? PrayerPref is not enough solid. Any idea will be appreciated ++

Absolutely. But it’s a LOT of work. Very few games do it because it’s not useful.

Is there a way to make your car last forever? Yes, but it’s a LOT of work.

Like all engineering problems, one works until one reaches a suitable solution.

Load/Save steps:

https://discussions.unity.com/t/799896/4

When loading, you can never re-create a MonoBehaviour or ScriptableObject instance directly from JSON. The reason is they are hybrid C# and native engine objects, and when the JSON package calls new to make one, it cannot make the native engine portion of the object.

Instead you must first create the MonoBehaviour using AddComponent() on a GameObject instance, or use ScriptableObject.CreateInstance() to make your SO, then use the appropriate JSON “populate object” call to fill in its public fields.

If you want to use PlayerPrefs to save your game, it’s always better to use a JSON-based wrapper such as this one I forked from a fellow named Brett M Johnson on github:

https://gist.github.com/kurtdekker/7db0500da01c3eb2a7ac8040198ce7f6

Do not use the binary formatter/serializer: it is insecure, it cannot be made secure, and it makes debugging very difficult, plus it actually will NOT prevent people from modifying your save data on their computers.

https://docs.microsoft.com/en-us/dotnet/standard/serialization/binaryformatter-security-guide

Thank you for your reply Kurt-Dekker. I really appreciate it - even if I did not understand the half or your explanation because I have no skill using another save system except PlayerPref. I will take a look at your alternative using JSON. It seems really interesting. I have to think about a better system for my project. Thank you ++

1 Like

If you don’t like ones and zeros or player prefs create a text file, and relay important aspects of your game to it lieu. One example I made I was to store the index number of a list of colours, objects and so on; after a key letter or word. And then I would check to see if the text file existed, read the text file, and then grab the colour index of A the object index of A and so on. But you could put anything this, such as a vector 3. Or literally anything at all. You could in fact write your entire game to a text file so that it is entirely modifiable for the player, while all of the game logic is built around and produced after reading this text file.

Thank you Animal Man for the tips. It could be an interesting way to save a game. Actually I am creating my own system, exploiting what you explained to me in this thread. Thank you everyone ++

If you have no experience, it might be best to first use a prebuilt solution like something from the Asset Store, just to learn those concepts and see the limitations in action. Then you can always write your own.

At the same time, you can follow a few tutorials. Just a random one that I remember doing: Persisting Objects

But, don’t just take any single thing for an answer. Look at multiple approaches, make your own experiments and then apply what you’ve learned to your own project. Maybe at this point you want to implement a custom save system, maybe you no longer feel the need or found something perfect along the way.

My dev studio used different practices in the past:

Key-Value Storage
Something like PlayerPrefs, but custom. You can build things like GetInt(string key), but also more complex: GetVector, GetArray etc. Everything is stored in dictionaries and serialized to a file. All components go through this global system and save/load their individual state or some managers manage the process for sub-objects. It’s all spaghetti and might become too confusing, but it’s very flexible. You can turn this system into something designer-driven, e.g. let developers add keys and values directly in the inspector and assign them to prefabs, which on certain actions saves other values (e.g. a quest system or inventory collect thingy). Some topics like versioning the save file can become difficult with this approach, because everything is scattered, or you would have to add additional features from other approaches to make this possible.

Save Game As Single Source Of Truth
There’s a single class called GameState and it contains everything that needs to be saved, nested in a completely serializable hierarchy. All systems have a reference to this single class or parts of it, but there’s only one copy (a singleton potentially). This means, once loaded, all systems simply use this state and write to it, then somebody can save the structure to a file at any point. This system is very easy to understand, because nothing is copied and everyone has the most recent state of things etc. It’s also probably one of the fastest approaches performance-wise because there’s only a single step involved. However, it tightly couples all components to this big model or parts of it, which reduces flexibility. But things like versioning become easy, because now version 1 is just a single file and model, version 2 a different one and you can add upgraders in between and just pass the new data to the rest of the game.

Serializer Passed To Subsystems
Combine both approaches. Somewhere, a serializer loads a file and the reference to this class is passed to all implementers of ISaveable. Each class takes the data it needs or stores it. If its key/value based, the order doesn’t matter. If its binary, the ordering is important and probably impossible to implement. Some commercial products work by making the ordering deterministic via GUID keys or manually maintaining an orderer list of saveable components. In any case, you may be able to split the big monolith into multiple parts to make different systems more flexible.

File Format
I recommend pretty-printed JSON because its a good balance between performance and editing/debugging. You can even use a ScriptableObject as the data model and then serialize it to JSON. This makes it possible to store save games as assets in the project (maybe as starting points or for cheating/testing). You can see and edit values directly in the inspector. Unity’s JsonUtility is extremely fast and supports all types which show in the inspector (but this means its bound to the same limitations, no dictionaries for example). Other serializers handle more complex data types, but are slower, e.g. Json.Net.
For maximum performance, a custom binary solution is best. Nothing beats a handcrafted serializer which is hardcoded to every property in the game and writes out the minimum number of required bytes to represent the data. However, its also very maintenance heavy. Some libraries build on top of this idea. A search for “serializer” turns up many good results. To name a random one: MessagePack. Keep in mind, you can beat even the best serializer library performance-wise, but probably not in regards to time spent on implementing and maintenance.

Representing Game State
The most difficult task: how to represent Unity GameObject state with any system? Everything else is easy: score values, player progress data, inventory, achievements, all can usually be stored as some strings and ints. But scene state (position of GameObjects, active state, animations) are more difficult because the data needs to be converted and the internal Unity state recreated somehow. The most common and practical solution is to build systems for every part of your game. E.g. if the board spawner spawns board game tokens, it can also represent each token position in the save file and load it to spawn it from saved positions). A PlayerController can keep track of its position and rotation and write it to file and load that. You see, it becomes a nightmare for big games, but it works. Some things will give you headaches, like recreating animation state, coroutines, etc. All of these have solutions, but they are involved.
Some systems attempt to generalize the process. For example, they walk the entire GameObject hierarchy and store the Transform data of each object. Each known component type has some sort of Handler that knows how to serializer/deserializer its state. However, this also breaks down easily in a fight between tradeoffs. If you save everything you waste massive amounts of space and time. But to optimize the system you will need to mark things as saveable or not, or even individual properties, and now you’re building an entire editor system to configure the previously hardcoded save/load systems. If anyone (or Unity) introduces new components, you also need to add new specific handlers. This is probably the most complex way of doing things and only yields benefits if both game and team are large.

22 Likes
Saving and loading an array (JSON)
Saving/Reading Prefab Data Unity 3D
need help with bool saving
Save system & permanent upgrades during development.
How to save current scene play
How can I save and load progress bar?
Unity freezing everytime i try to save a tilemap.
Storing Instantiated Buildings
What's the best way to build Stats system and Save/Load your Stats?
How to have multiple values in dictionary
Each scene with different saved data?
Vector3 export to WriteAllText
how to forbid start and awake
Button Destroy
Unity Button not marked as serializable?
can i save a unity scene during runtime?
Saving player position and scene
"Save Game Free" how to use??
Which is the best method to use for creating Save/Load game functionality
Can't Deserialize Sprite
Help with my SaveSystem?
How to get a prefab from code
Append Highscore and display results
Does C# support a wrapper class to make all members unchangable?
How can I save an object as is?
I need a "simple" save system for my game
What is the correct way to deserialise your save file?
How could I save enemies' positions and hp with PlayerPrefs
Saving player data between scenes
How can i save a gameobject in unity?
I don't know how to save/load my inventory
Does this saving system have any major flaws?
Save & Load System
What is the best way to save the state of world objects in Unity
How to create a save system for a sandbox survival game?
How do i save data in Unity?
Saving/Loading Dynamic Scriptable Objects
Creating passive items that assign effects and subscribe to events
Best Solutions to Backup Game Settings
Keeping Items when changing between scenes
Line Renderer Save (902728)
Unable to save games on mobile(both iOS and Android), works fine in editor. Using Odin Serializer.
How can I transfer a list of game objects between two scenes using GameManager?
Players all time stats
The best way to save data
Error on saving and loading due to clone of game object
Trouble with Loading Json Files
How to modify a game scene using a script?
Disabling objects forever
How do I save my instantiated object?
Saving Tilemap
[Resolved] save system help needed
Save arrays by Binary?
Can't access one class from another
Saving inventory between scenes in 2D game.
How to save a GameObject and its randomly generated sprite ?
should I save levels as json or in a script?
memorize objects or actions at scene change
Saving position from multiple scenes
No Save!
How to make a Multiplayer Save System to JSON No servers
Designing Dynamic Spell Unlocking and Progression System with ScriptableObject
Saving objects in the scene along with their components and the components' variables' values?
Saving and Loading Reference to Material/Asset (using Addressables?)
JsonUtility.ToJson() not serializing everything
Scene Progress Saving (through c#) Unclear
i need help... i try to load my game that i saved but i get a error.
SaveGame, it's not saving the player's status it just resets the values in the loader
Scriptable Object and Data Base
Save/Load gameobjects with references to prefabs/Scriptable objects
How can I make a save&load for chat messages from ChatGPT API?
Importing lists of custom objects from JSON
How to implement checkpoints
How can i save 2 numbers at once in playerprefs?
How do I write custom classes to a JSON file?
Does not find information to add to the list
Help to find best save system solution please
How would i make it so that dialogue appears once forever
How to Track Player Progress in a Deep Dungeon?
constructor gives null error
need help for saving highscore for different scenes
What is the best pattern for saving references to prefabs/scriptable objects
Save/Load System considerations
Which is the best way to save in-game world environment
Using scriptable objects in the other half of the game project
Good code for data saving
Save/Load Error
Saving multiple gameObjects in the Index of a list
Struggling with complex data
A Read File Text Problem when i build Game
Save and load system detail questions
saving drawings drawn in unity
custom .bin file location
Should I use scriptable object or just normal script to save my settings
How to save an Instantiated prefab as a child?
Player position issue on load save
How to save an int array to a JSON file for saving and loading
How to make the level selection screen?
Explain like I'm 5. How to save a players progress
How to make level saves
Saving Multiple Objects
Save data, each scene?
Why i cant destroy an object?
Need help with saving inventory
How do i save my map to json?
I want to save my grid of tiles which are different colour so it can be reloaded later acting as a level saver. Not sure how to do it though
Save/Load System Not Working
How to save and restore level state correctly?
How would you architect a game with a generated map like path of exile?
How can I update the database information in a installed App when the player pays for an upgrade
Handling Scenes and Data Persistence in Large-Scale Platformer Games
Saving object positions between scene loads (super amateur question)
Can anyone take a look at my scripts and help me out
Save & Load System on SceneUnloaded, SceneLoaded, and OnApplicationQuit Broke on Android Build
(Trying to learn)Saving player data/unlocks? No clue where to start
Reference Error, but I am unsure why
Saving and accessing sprites during runtime
Loading .json wont work in build
How to explicitly write changes into serialized fields manually during runtime?
I have a problem with my saving & loading system
Persistent player data management - design patterns and architecture
Problem with Asset: Simple and Powerful Inventory System by Jax's Studio
Need help deciding how to save
Need your help on my 2d Space rocket game
How to know if player has been in scene
Getting Adressables adress of an asset at runtime
Handle house interiors and customization Unity 2D
How do I build a save system for a complex 3D game?
How do you serialize a scene in json and references then load it all back?
Saving/Loading groups and lists of variable length?
How to store multiple values inside a gameobject
How to save object's position and make it return
3D array is referenced by two separate game objects

@Xarbrough_1 Thank you for this huge explanation. I did not expect anything today, but you made my day. I understand all the alternatives which you propose, but for my project, it seems to me that they are not suitable (at this stage). The main problem with which I am confronting is that I load different scenes according to the player’s progress in the game. So I have to save which scenes should be activated, which objects are available or not, player position, etc. It’s a nightmare. First, I will try to mix all your alternatives in a single way which I could use in my game. Usually I don’t like to buy assets which I could create by myself, but you are right - sometimes, it’s a way to manage our time in a better way. I will take a look at some assets so as to understand their pros and cons. Thank you for your help. I really appreciate all your clever explanations. I wish you the best ++

1 Like

That was a really good writeup. Appreciate you taking the time. The stuff you write needs to be seen!

If you don’t object (if you do, just pm me), from now on I am going to include a link to your above message when I give out my standard load/save blurb.

6 Likes