LoadInto Erasing Nested Value Type

Discussion and help for Easy Save 3
Post Reply
gabrielgardner
Posts: 2
Joined: Wed May 05, 2021 5:05 pm

LoadInto Erasing Nested Value Type

Post by gabrielgardner »

Hi,

I am using Easy Save 3 to handle the saving and loading of ScriptableObject assets. I am running into a bug where loading a ScriptableObject through LoadInto erases the values of a list of a nested value type that has a custom ES3 Type script defined for it.

The main ScriptableObject is named "LevelData", and I have configured a custom ES3 Type Script to save the fields of level data that I would like to have saved. Here is the read method below:

Code: Select all

protected override void ReadScriptableObject<T>(ES3Reader reader, object obj)
		{
			var instance = (LevelData)obj;
			foreach(string propertyName in reader.Properties)
			{
				switch(propertyName)
				{
					
					case "Unlocked":
						instance.Unlocked = reader.Read<System.Boolean>(ES3Type_bool.Instance);
						break;
					case "HighScore":
						instance.HighScore = reader.Read<System.Int32>(ES3Type_int.Instance);
						break;
					case "CoOpHighScore":
						instance.CoOpHighScore = reader.Read<System.Int32>(ES3Type_int.Instance);
						break;
					case "ScoreGoalsAndLinks":
						instance.ScoreGoalsAndLinks = reader.Read<System.Collections.Generic.List<LevelData.LevelScoreGoal>>();
						break;
					case "_DEBUG_SAVE_FLAG":
						instance._DEBUG_SAVE_FLAG = reader.Read<System.Boolean>(ES3Type_bool.Instance);
						break;
					default:
						reader.Skip();
						break;
				}
			}
		}
Inside of the LevelData class, I have defined a subclass called LevelScoreGoal:

Code: Select all

[System.Serializable]
    public class LevelScoreGoal
    {
        public int ScoreGoalOnePlayer;
        public int ScoreGoalTwoPlayer;
        public int NumberOfLinks;
        public string UnlockKey;
        public LinkState State;

        public enum LinkState
        {
            Locked,
            Revealing,
            Unlocked
        }
        
        ...
LevelScoreGoal has a custom ES3 Type Script as well, since the only thing that needs to be saved is the field State. Here is the custom read function for LevelScoreGoal:

Code: Select all

protected override void ReadObject<T>(ES3Reader reader, object obj)
		{
			var instance = (LevelData.LevelScoreGoal)obj;
			foreach(string propertyName in reader.Properties)
			{
				switch(propertyName)
				{
					
					case "State":
						instance.State = reader.Read<LevelData.LevelScoreGoal.LinkState>();
						break;
					default:
						reader.Skip();
						break;
				}
			}
		}
Saving works fine, and a saved LevelData looks like this:

Code: Select all

"Level_Data_Level2Demo" : {
		"__type" : "LevelData,Assembly-CSharp",
		"value" : {
			"_ES3Ref" : "5353275289805580540",
			"_ES3Ref" : "5353275289805580540",
			"Unlocked" : false,
			"HighScore" : 0,
			"CoOpHighScore" : 0,
			"ScoreGoalsAndLinks" : [
				{
					"State" : 0
				},{
					"State" : 0
				},{
					"State" : 0
				}
			],
			"_DEBUG_SAVE_FLAG" : false
		}
	},
The problem arises when I try to load a saved LevelData during runtime. I use LoadInto<LevelData> because I already have a reference to the ScriptableObject asset in the project. The loading works correctly (including for non-saved fields) until it loads the list of LevelScoreGoals called "ScoreGoalsAndLinks". It ends up erasing all of the fields inside the LevelScoreGoals within that list except the one I have told ES3 to save, the State field.

Given that LoadInto loads the non-saving fields correctly in the outer LevelData class, it is confusing to me that an inner class would have its fields erased except for the one that is marked to save. Is it possible to get Easy Save to load into the ScoreGoalsAndLinks correctly without needing to save every field in every LevelScoreGoal, or make LevelScoreGoal a reference type (which doesn't make sense for my setup).

Thanks for your help!
Gabriel
User avatar
Joel
Moodkie Staff
Posts: 4826
Joined: Wed Nov 07, 2012 10:32 pm

Re: LoadInto Erasing Nested Value Type

Post by Joel »

Hi there,

ES3.LoadInto loads into the fields of the object provided as a parameter, not the fields of the objects in those fields. If you want to load into these separately then you would need to save them separately.

All the best,
Joel
Joel @ Moodkie Interactive
Purchase Easy Save | Contact | Guides | Docs | Getting started
gabrielgardner
Posts: 2
Joined: Wed May 05, 2021 5:05 pm

Re: LoadInto Erasing Nested Value Type

Post by gabrielgardner »

Hi Joel,

Thanks for the reply. I realize that LoadInto will not work for the fields of nested objects, but I was hoping it then wouldn't clear the fields of those nested objects. I guess I will find another workaround. Thanks for your help!

Cheers,
Gabriel
Post Reply