SAVE/LOAD System ?

SAVE/LOAD System ?

Я тут пилю симулятор потихоньку (без выходных 24/7) и решил сразу сделать редактор сценариев и всякого такого. Так вот сохранение Исследований, модулей и прочих вещей у меня вызывало некоторые проблемы, хотя я и раньше уже писал подобные системы, но более простые.

[ExecuteInEditMode] public class ModuleEngine : Module { public int Power = 100; public int FuelTaking = 1; public SaveDataEngine SD; public override void SaveJSON() { ID = GetInstanceID(); SD = new SaveDataEngine( Name, GetInstanceID(), Prefab.name , Cost, ProductionTime, FuelTaking, Power); string jsonData = JsonUtility.ToJson(SD, true); File.WriteAllText(Path.Combine(ScenarioManager.instance.CurrentScenario.CurrentFolder, GetInstanceID() + ".Module"), jsonData); Debug.Log("File Saved at: " + Path.Combine(ScenarioManager.instance.CurrentScenario.CurrentFolder, GetInstanceID() + ".Module")); } public override void LoadJSON() { SD = JsonUtility.FromJson<SaveDataEngine>(File.ReadAllText(JsonFilePath)); ID = SD.ID; Name = SD.Name; ProductionTime = SD.ProductionTime; Power = SD.Power; FuelTaking = SD.FuelTaking; Cost = SD.Cost; Prefab = Resources.Load<GameObject>("Modules/" + SD.PrefabName); if(Icon==null) Debug.LogError("Нет иконки у объекта :"+ name); foreach (var item in ScenarioManager.instance.CurrentScenario.Researches) { if (item.SD.ModulesID.Exists(X => X == SD.ID)) { item.ModulesOpen.Add(this); item.researchButton.Refresh(); transform.SetParent(item.transform); } } } [System.Serializable] public class SaveDataEngine: SaveData { public int Cost; public int[] ProductionTime; public int Power; public int FuelTaking; public SaveDataEngine(string name, int id, string prefabName, int cost, int []productionTime, int fuelTaking, int power) { ID = id; Name = name; PrefabName = prefabName; Cost = cost; ProductionTime = productionTime; Power = power; FuelTaking = fuelTaking; } }

В общем сохраняю я каждую сущность в JSON с последующей десериализацией, вот только в Unity есть проблема - невозможно MonoBehavior десериализовать без наличия физически соответствующего объекта в сцене. Представим что у меня есть очень много Module - которые реализуются как наследники от базового класса и они отличаются друг от друга. Как видно из кода я создаю внутри каждого такого класса свой SaveData класс наследник от базового.

Почему? чтобы обойти невозможность десеарелизации Монобехов, я знаю что можно создать пустой класс в сцене и десериализовать, в него, а потом уже зная его класс создать непосредственно нужный и скопировать/удалить фейк монобех. Но это меня прям вымораживает, поэтому я и создал SaveData чтобы десериализовать его напрямую без создание фейковых монобехов, однако и это выглядит чересчур костыльно.

Мне кажется что есть более простые пути, но я их в упор не вижу. Спасибо.

1212 показов
2K2K открытий
35 комментариев

Комментарий недоступен

Ответить

потому что они физически существуют в сценах как игровые объекты

Ответить

Бро, можно юзать JSON .NET For Unity https://assetstore.unity.com/packages/tools/input-management/json-net-for-unity-11347 
Он умеет сохранять и дочерние классы
https://stackoverflow.com/questions/8513042/json-net-serialize-deserialize-derived-types

Ответить

вчера потыкался с ним и удалил, ничего особого он не добавляет по возможностям

Ответить

Как вариант можно попробовать сделать атрибут для полей, которые хочется сохранять (или просто все сериализуемые поля) и позже через assembly.getTypes (не помню точно) автоматически их в проекте собирать (по атрибуту или каким-то ещё признакам) и сохранять.

Ещё мне кажется, что эффективнее в игре все объекты хранить в виде словаря какого-то, а в момент сохранения в json конвертить этот словарь, а не каждый объект отдельно

Ответить

суть задачи в том чтобы наследников было сколько угодно типов и чтобы их можно было легко из JSON доставать и создавать не описывая в каждом классе все каждый раз заново, мне кажется я уже придумал как это всё обойти, сейчас пробую. Думаю можно просто при SaveJSON - прямо в имени файла писать имя класса и тогда любой файл сам себя сможет воссоздать прямо из базового класса. Эффективность сохранения файлов в PC игре на HDRP у меня не на первом месте)

Ответить

Комментарий недоступен

Ответить