Save System Question ;)

Announcements, support questions, and discussion for the Dialogue System.
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

I started adding the changes to my own saver script as recommended...

However, I'm not quite certain how to "hook" the GetItemFromID from its current location to this one...

Its in a script file called InventoryItem.cs (here is its FULL content unedited)

Code: Select all

using System;
using System.Collections.Generic;
using UnityEngine;
using static GameDevTV.Inventories.Equipment;

namespace GameDevTV.Inventories
{
    /// <summary>
    /// A ScriptableObject that represents any item that can be put in an
    /// inventory.
    /// </summary>
    /// <remarks>
    /// In practice, you are likely to use a subclass such as `ActionItem` or
    /// `EquipableItem`.
    /// </remarks>
    public abstract class InventoryItem : ScriptableObject, ISerializationCallbackReceiver
    {
        // CONFIG DATA
        [Tooltip("Auto-generated UUID for saving/loading. Clear this field if you want to generate a new one.")]
        [SerializeField] string itemID = null;
        [Tooltip("Item name to be displayed in UI.")]
        [SerializeField] string displayName = null;
        [Tooltip("Item description to be displayed in UI.")]
        [SerializeField][TextArea] string description = null;
        [Tooltip("The UI icon to represent this item in the inventory.")]
        [SerializeField] Sprite icon = null;
        [Tooltip("The prefab that should be spawned when this item is dropped.")]
        [SerializeField] Pickup pickup = null;
        [Tooltip("If true, multiple items of this type can be stacked in the same inventory slot.")]
        [SerializeField] bool stackable = false;

        [Tooltip("WWise Audio Pickup Clip Name.")]
        [SerializeField] string WWisePickupClip = "";

        [SerializeField] ItemCategory category;

        // STATE
        static Dictionary<string, InventoryItem> itemLookupCache;

        // PUBLIC

        public ItemCategory GetCategory() => category;

        /// <summary>
        /// Get the inventory item instance from its UUID.
        /// </summary>
        /// <param name="itemID">
        /// String UUID that persists between game instances.
        /// </param>
        /// <returns>
        /// Inventory item instance corresponding to the ID.
        /// </returns>
        public static InventoryItem GetFromID(string itemID)
        {
            if (itemLookupCache == null)
            {
                itemLookupCache = new Dictionary<string, InventoryItem>();
                var itemList = Resources.LoadAll<InventoryItem>("");
                foreach (var item in itemList)
                {
                    if (itemLookupCache.ContainsKey(item.itemID))
                    {
                        Debug.LogError(string.Format("Looks like there's a duplicate GameDevTV.UI.InventorySystem ID for objects: {0} and {1}", itemLookupCache[item.itemID], item));
                        continue;
                    }

                    itemLookupCache[item.itemID] = item;
                }
            }

            if (itemID == null || !itemLookupCache.ContainsKey(itemID)) return null;
            return itemLookupCache[itemID];
        }

        /// <summary>
        /// Spawn the pickup gameobject into the world.
        /// </summary>
        /// <param name="position">Where to spawn the pickup.</param>
        /// <param name="number">How many instances of the item does the pickup represent.</param>
        /// <returns>Reference to the pickup object spawned.</returns>
        public Pickup SpawnPickup(Vector3 position, int number)
        {
            var pickup = Instantiate(this.pickup);
            pickup.transform.position = position;
            pickup.Setup(this, number);
            return pickup;
        }

        public Sprite GetIcon()
        {
            return icon;
        }

        public string GetItemID()
        {
            return itemID;
        }

        public bool IsStackable()
        {
            return stackable;
        }
        
        public string GetDisplayName()
        {
            return displayName;
        }

        public string GetDescription()
        {
            return description;
        }

        public string GetWWiseString()
        {
            return WWisePickupClip;
        }

        // PRIVATE
        
        void ISerializationCallbackReceiver.OnBeforeSerialize()
        {
            // Generate and save a new UUID if this is blank.
            if (string.IsNullOrWhiteSpace(itemID))
            {
                itemID = System.Guid.NewGuid().ToString();
            }
        }

        void ISerializationCallbackReceiver.OnAfterDeserialize()
        {
            // Require by the ISerializationCallbackReceiver but we don't need
            // to do anything with it.
        }
    }
}
so there is a "public static InventoryItem GetFromID(string itemID)"

I replaced your line :
GetItemFromID(string itemID)
with this :
pickup.item = InventoryItem.GetFromID(data.itemID);

However, now i'm getting a weird error in the data section at the top : (see screenshot)
error.jpg
error.jpg (139.09 KiB) Viewed 1024 times
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

Sorry for the dual reply in a row...

After a quick search, i figured out the ItemID in question was the one from my inventoryitem.cs i had just pasted...

I changed that one to "public"... and it worked!

AND EVERYTHING WORKS!! :)
EDIT : {
(well... pretty much everything)
seems like it only restores it "once"... if i save and reload a 2nd time, its not there at all...
I'll try to figure this one out by analysing the save data...
also found that my "boolean" instantiated doesnt seem to ever be used...

Pasting my new "SAVE DATA" (i removed all duplicate items to make it much smaller)

Code: Select all

{
    "m_version": 1,
    "m_sceneName": "HugoPlayground",
    "m_list": [
        {
            "key": "WoodenCrate_2062DestructibleSaver",
            "sceneIndex": -1,
            "data": "{\n    \"destroyed\": true,\n    \"position\": {\n        \"x\": 13.120795249938965,\n        \"y\": -0.00045359134674072266,\n        \"z\": 3.399622678756714\n    }\n}"
        },
        {
            "key": "WhiskyBottle_2286DestructibleSaver",
            "sceneIndex": -1,
            "data": "{\n    \"destroyed\": true,\n    \"position\": {\n        \"x\": 12.010724067687989,\n        \"y\": -0.11645475029945374,\n        \"z\": 5.306109428405762\n    }\n}"
        },
        {
            "key": "SaveDataPrefab_30374",
            "sceneIndex": -1,
            "data": "Variable={Alert=\"\", Actor=\"\", Conversant=\"\", ActorIndex=\"\", ConversantIndex=\"\"}; Actor={Shuma={Name=\"Shuma\", Pictures=\"[]\", Description=\"\", IsPlayer=true}, NPCTest={Name=\"NPCTest\", Pictures=\"[]\", Description=\"\", IsPlayer=false}, Orenda={Name=\"Orenda\", Pictures=\"[]\", Description=\"\", IsPlayer=false}, Wanji={Name=\"Wanji\", Pictures=\"[]\", Description=\"\", IsPlayer=false}}; StatusTable = \"\"; RelationshipTable = \"\"; "
        },
        {
            "key": "ShumaPositionSaver",
            "sceneIndex": -1,
            "data": "{\n    \"positions\": [\n        {\n            \"scene\": 0,\n            \"position\": {\n                \"x\": 8.51918888092041,\n                \"y\": 0.00010001659393310547,\n                \"z\": 1.0648798942565919\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.9999405741691589,\n                \"z\": 0.0,\n                \"w\": -0.01090139802545309\n            }\n        }\n    ]\n}"
        },
        {
            "key": "FireSpiritGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"2465b702-faba-4166-b2c5-9434b965c543\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "WoodSwordGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "ArmorGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"a02c4c97-fb2e-419e-81d5-7bfb899a7ff0\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "PotionGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"138e3d6a-f5ef-4afa-a32e-202218118a97\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "SaveDataPrefabSpawnedObjectManager",
            "sceneIndex": -1,
            "data": "{\n    \"list\": [\n        {\n            \"prefabName\": \"Pickup Spawner Destructible\",\n            \"position\": {\n                \"x\": 13.120795249938965,\n                \"y\": 0.9995464086532593,\n                \"z\": 3.399622678756714\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.0,\n                \"z\": 0.0,\n                \"w\": 1.0\n            },\n            \"guid\": \"0dc852f1-a71d-4d15-9a7b-9640872fd26f\",\n            \"item\": {\n                \"instanceID\": 0\n            },\n            \"number\": 0\n        },\n        {\n            \"prefabName\": \"Pickup Spawner Destructible\",\n            \"position\": {\n                \"x\": 12.010724067687989,\n                \"y\": 0.8835452795028687,\n                \"z\": 5.306109428405762\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.0,\n                \"z\": 0.0,\n                \"w\": 1.0\n            },\n            \"guid\": \"8500e8e5-0400-4357-b8d3-2c8e72fd0782\",\n            \"item\": {\n                \"instanceID\": 0\n            },\n            \"number\": 0\n        }\n    ]\n}"
        },
        {
            "key": "Pickup Spawner Destructible(Clone)SpawnedObject0dc852f1-a71d-4d15-9a7b-9640872fd26f",
            "sceneIndex": -1,
            "data": ""
        },
        {
            "key": "Pickup Spawner Destructible(Clone)ShumaPickupSaver0dc852f1-a71d-4d15-9a7b-9640872fd26f",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": true\n}"
        },
        {
            "key": "Pickup Spawner Destructible(Clone)SpawnedObject8500e8e5-0400-4357-b8d3-2c8e72fd0782",
            "sceneIndex": -1,
            "data": ""
        },
        {
            "key": "Pickup Spawner Destructible(Clone)ShumaPickupSaver8500e8e5-0400-4357-b8d3-2c8e72fd0782",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": true\n}"
        }
    ]
}
We see that boolinstantiated works when it was "just" spawned... but the position isnt being saved in... so whenever it gets reloaded a second time, without the spawned save data prefab manager, then its not restored properly...

I THINK I might be able to fix that by re-adding the position manually
}

I might *most probably* be back before this game is done... hope you dont mind too much...
I just hope if i keep working that one day I am close to being as good as you are ;)

Thanks you again so much for all your help!
User avatar
Tony Li
Posts: 21977
Joined: Thu Jul 18, 2013 1:27 pm

Re: Save System Question ;)

Post by Tony Li »

Glad to help! It looks like the position is being saved, right?

Code: Select all

{
    "key": "SaveDataPrefabSpawnedObjectManager",
    "sceneIndex": -1,
    "data": "{\n    \"list\": [\n        {\n            \"prefabName\": \"Pickup Spawner Destructible\",\n            \"position\": {\n                \"x\": 13.120795249938965,\n                \"y\": 0.9995464086532593,\n                \"z\": 3.399622678756714\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.0,\n                \"z\": 0.0,\n                \"w\": 1.0\n            },\n            \"guid\": \"0dc852f1-a71d-4d15-9a7b-9640872fd26f\",\n            \"item\": {\n                \"instanceID\": 0\n            },\n            \"number\": 0\n        },\n        {\n            \"prefabName\": \"Pickup Spawner Destructible\",\n            \"position\": {\n                \"x\": 12.010724067687989,\n                \"y\": 0.8835452795028687,\n                \"z\": 5.306109428405762\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.0,\n                \"z\": 0.0,\n                \"w\": 1.0\n            },\n            \"guid\": \"8500e8e5-0400-4357-b8d3-2c8e72fd0782\",\n            \"item\": {\n                \"instanceID\": 0\n            },\n            \"number\": 0\n        }\n    ]\n}"
},
But that might be from the first run.
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

yeah exactly... if i restart, then this is what it looks like after :

Code: Select all

{
    "m_version": 1,
    "m_sceneName": "HugoPlayground",
    "m_list": [
        {
            "key": "WoodenCrate_2062DestructibleSaver",
            "sceneIndex": -1,
            "data": "{\n    \"destroyed\": true,\n    \"position\": {\n        \"x\": 13.121221542358399,\n        \"y\": 0.5234753489494324,\n        \"z\": 3.398189067840576\n    }\n}"
        },
        {
            "key": "WhiskyBottle_2286DestructibleSaver",
            "sceneIndex": -1,
            "data": "{\n    \"destroyed\": true,\n    \"position\": {\n        \"x\": 12.134303092956543,\n        \"y\": 0.7618709206581116,\n        \"z\": 5.3154377937316898\n    }\n}"
        },
        {
            "key": "SaveDataPrefab_30374",
            "sceneIndex": -1,
            "data": "Variable={Alert=\"\", Actor=\"\", Conversant=\"\", ActorIndex=\"\", ConversantIndex=\"\"}; Actor={Shuma={Name=\"Shuma\", Pictures=\"[]\", Description=\"\", IsPlayer=true}, NPCTest={Name=\"NPCTest\", Pictures=\"[]\", Description=\"\", IsPlayer=false}, Orenda={Name=\"Orenda\", Pictures=\"[]\", Description=\"\", IsPlayer=false}, Wanji={Name=\"Wanji\", Pictures=\"[]\", Description=\"\", IsPlayer=false}}; StatusTable = \"\"; RelationshipTable = \"\"; "
        },
        {
            "key": "ShumaPositionSaver",
            "sceneIndex": -1,
            "data": "{\n    \"positions\": [\n        {\n            \"scene\": 0,\n            \"position\": {\n                \"x\": 9.392098426818848,\n                \"y\": 0.00010001659393310547,\n                \"z\": 1.3458504676818848\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.8628214597702026,\n                \"z\": 0.0,\n                \"w\": 0.5055087804794312\n            }\n        }\n    ]\n}"
        },
        {
            "key": "FireSpiritGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"2465b702-faba-4166-b2c5-9434b965c543\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "WoodSwordGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "ArmorGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"a02c4c97-fb2e-419e-81d5-7bfb899a7ff0\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "PotionGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"138e3d6a-f5ef-4afa-a32e-202218118a97\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "SaveDataPrefabSpawnedObjectManager",
            "sceneIndex": -1,
            "data": "{\n    \"list\": []\n}"
        },
        {
            "key": "Pickup Spawner Destructible(Clone)SpawnedObject0dc852f1-a71d-4d15-9a7b-9640872fd26f",
            "sceneIndex": -1,
            "data": ""
        },
        {
            "key": "Pickup Spawner Destructible(Clone)ShumaPickupSaver0dc852f1-a71d-4d15-9a7b-9640872fd26f",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "Pickup Spawner Destructible(Clone)SpawnedObject8500e8e5-0400-4357-b8d3-2c8e72fd0782",
            "sceneIndex": -1,
            "data": ""
        },
        {
            "key": "Pickup Spawner Destructible(Clone)ShumaPickupSaver8500e8e5-0400-4357-b8d3-2c8e72fd0782",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 0.0,\n        \"y\": 0.0,\n        \"z\": 0.0\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        }
    ]
}
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

After updating my saving script and reloading a couple of times, this is what it now looks like...

Saving Script :
added this in RecordData : data.position = pickup.gameObject.transform.position;

and updated the Applydata as such :

Code: Select all

public override void ApplyData(string s)
        {
            /// This method should process the string representation of saved data and apply
            /// it to the current state of the game. You can use SaveSystem.Deserialize()
            /// to deserialize the string to an object that specifies the state to apply to
            /// the game.
            /// 

            if (string.IsNullOrEmpty(s)) return; // No data to apply.
            Data data = SaveSystem.Deserialize<Data>(s);
            if (data == null) return; // Serialized string isn't valid.

            PickupSpawner pickup = GetComponent<PickupSpawner>(); // Call GetComponent once and cache value.

            pickup.item = InventoryItem.GetFromID(data.itemID);
            pickup.number = data.number;
            pickup.gameObject.transform.position = data.position;

            if (data.boolPickupPickedUp)
            {
                pickup.boolPickupPickedUp = true;
                if (pickup.boolPickupSpawned == false)
                {
                    pickup.SpawnPickup();
                }
                pickup.DestroyPickup();
            }
            else if (pickup.boolPickupSpawned == false)
            {
                pickup.SpawnPickup();
            }
        }
SaveGame :

Code: Select all

{
    "m_version": 1,
    "m_sceneName": "HugoPlayground",
    "m_list": [
        {
            "key": "WhiskyBottle_2286DestructibleSaver",
            "sceneIndex": -1,
            "data": "{\n    \"destroyed\": true,\n    \"position\": {\n        \"x\": 11.956254959106446,\n        \"y\": 0.6780540943145752,\n        \"z\": 5.321850299835205\n    }\n}"
        },
        {
            "key": "WoodenCrate_2062DestructibleSaver",
            "sceneIndex": -1,
            "data": "{\n    \"destroyed\": true,\n    \"position\": {\n        \"x\": 13.119370460510254,\n        \"y\": 0.49531644582748415,\n        \"z\": 3.400576114654541\n    }\n}"
        },
        {
            "key": "SaveDataPrefab_30374",
            "sceneIndex": -1,
            "data": "Variable={Alert=\"\", Actor=\"\", Conversant=\"\", ActorIndex=\"\", ConversantIndex=\"\"}; Actor={Shuma={Name=\"Shuma\", Pictures=\"[]\", Description=\"\", IsPlayer=true}, NPCTest={Name=\"NPCTest\", Pictures=\"[]\", Description=\"\", IsPlayer=false}, Orenda={Name=\"Orenda\", Pictures=\"[]\", Description=\"\", IsPlayer=false}, Wanji={Name=\"Wanji\", Pictures=\"[]\", Description=\"\", IsPlayer=false}}; StatusTable = \"\"; RelationshipTable = \"\"; "
        },
        {
            "key": "ShumaPositionSaver",
            "sceneIndex": -1,
            "data": "{\n    \"positions\": [\n        {\n            \"scene\": 0,\n            \"position\": {\n                \"x\": -8.13034439086914,\n                \"y\": 0.00009989738464355469,\n                \"z\": -2.0434980392456056\n            },\n            \"rotation\": {\n                \"x\": 0.0,\n                \"y\": 0.853636622428894,\n                \"z\": 0.0,\n                \"w\": -0.5208690166473389\n            }\n        }\n    ]\n}"
        },
        {
            "key": "FireSpiritGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": -15.5,\n        \"y\": 0.0,\n        \"z\": 2.4100000858306886\n    },\n    \"itemID\": \"2465b702-faba-4166-b2c5-9434b965c543\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "WoodSwordGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": -20.989999771118165,\n        \"y\": 0.0,\n        \"z\": 2.359999895095825\n    },\n    \"itemID\": \"85c14cc5-025b-4f55-9cfe-d4ece7d71d7e\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "ArmorGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": -20.920000076293947,\n        \"y\": 0.0,\n        \"z\": 5.239999771118164\n    },\n    \"itemID\": \"a02c4c97-fb2e-419e-81d5-7bfb899a7ff0\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "PotionGroundPickupShumaPickupSaver",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": -15.3100004196167,\n        \"y\": 0.0,\n        \"z\": 5.079999923706055\n    },\n    \"itemID\": \"138e3d6a-f5ef-4afa-a32e-202218118a97\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "SaveDataPrefabSpawnedObjectManager",
            "sceneIndex": -1,
            "data": "{\n    \"list\": []\n}"
        },
        {
            "key": "Pickup Spawner Destructible(Clone)SpawnedObject4c94948b-9038-4a41-b935-632048537464",
            "sceneIndex": -1,
            "data": ""
        },
        {
            "key": "Pickup Spawner Destructible(Clone)ShumaPickupSaver4c94948b-9038-4a41-b935-632048537464",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 12.06537914276123,\n        \"y\": 1.0016944408416749,\n        \"z\": 5.369279861450195\n    },\n    \"itemID\": \"138e3d6a-f5ef-4afa-a32e-202218118a97\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": false,\n    \"boolInstanciated\": false\n}"
        },
        {
            "key": "Pickup Spawner Destructible(Clone)SpawnedObject1252a8f7-7f19-4f1d-b40c-dbd120de13b1",
            "sceneIndex": -1,
            "data": ""
        },
        {
            "key": "Pickup Spawner Destructible(Clone)ShumaPickupSaver1252a8f7-7f19-4f1d-b40c-dbd120de13b1",
            "sceneIndex": -1,
            "data": "{\n    \"position\": {\n        \"x\": 13.128199577331543,\n        \"y\": 0.9371959567070007,\n        \"z\": 3.3629634380340578\n    },\n    \"itemID\": \"138e3d6a-f5ef-4afa-a32e-202218118a97\",\n    \"number\": 1,\n    \"boolPickupPickedUp\": true,\n    \"boolInstanciated\": false\n}"
        }
    ]
}
it should work... but the prefab "pickup spawner destructible" isnt getting re-instantiated after its initial first reload...

--EDIT :

I think i figured it out!
in your script "SpawnedObjectManager", on reloading a scene, the objects that gets respawned are not placed back into the "spawned object" list... so on the next save, they are no longer part of the save...

--EDIT2 :
No matter what I try, the SpawnedObjectManager refuses to re-add the SpawnedItem to the SpawnedObject list on a reload... I tried a debug on that whole thing... and it "should" add it back...
In the Start() of the SpawnedObject, there is this line "SpawnedObjectManager.AddSpawnedObjectData(this);"
it is being run twice... the first time it runs fine, yet the second time i see
if (m_instance == null || spawnedObject == null) return; (m_instance IS == to null) so it skips it...


--EDIT3 :
Finally solved it!!
I changed the SpawnedObjectManager (Add Spawned Data) to the following :

Code: Select all

 public static void AddSpawnedObjectData(SpawnedObject spawnedObject)
        {
                if (spawnedObject == null)
                {
                    return;
                }
                if (m_instance == null)
                {
                    m_instance = FindObjectOfType<SpawnedObjectManager>();
                }
            m_instance.m_spawnedObjects.Add(spawnedObject);
        }
This worked... i can reload over and over... and the item stay there! :)
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

Alright -- semi-new-question (still with the saving system, but the next logical step after the pickups since those now work perfectly) - see "edits" from previous post --- Im sorry for always asking for help/support... if you want an extra donation for all the help you give me, feel free to reach out in private with your paypal email i'll gladly send some money your way! :)

I think I mentioned before that the inventory system was made by another tutorial online by gamedev.tv
They also have their own saving system (much more rudimentary that the one provided with the Dialogue system)
But i'd like to adapt the "Inventory" saving that they use, and make it work with the DialogueSystem saving...

Here is how they save the inventory
(again, let me know if i need to share more or copy paste other part to properly understand how they do it) :

Code: Select all

[System.Serializable]
        private struct InventorySlotRecord
        {
            public string itemID;
            public int number;
        }

        object ISaveable.CaptureState()
        {
            var slotStrings = new InventorySlotRecord[inventorySize];
            for (int i = 0; i < inventorySize; i++)
            {
                if (slots[i].item != null)
                {
                    slotStrings[i].itemID = slots[i].item.GetItemID();
                    slotStrings[i].number = slots[i].number;
                }
            }
            return slotStrings;
        }

        void ISaveable.RestoreState(object state)
        {
            var slotStrings = (InventorySlotRecord[])state;
            for (int i = 0; i < inventorySize; i++)
            {
                InventorySlot tempslot = slots[i];
                tempslot.item = InventoryItem.GetFromID(slotStrings[i].itemID);
                tempslot.number = slotStrings[i].number;
                slots[i] = tempslot;
            }
            if (inventoryUpdated != null)
            {
                inventoryUpdated();
            }
        }
The problem is that those come from "ISaveable" which is their save system type...
I need to "deconstruct" that (or copy paste it) and make a compatible version to work with this new save system...

It should be pretty easy since there is only a string and integer to save... but im not certain how to write it up to access it from my new InventorySaver I made... Any tips/suggestions would be greatly appreciated ;)
User avatar
Tony Li
Posts: 21977
Joined: Thu Jul 18, 2013 1:27 pm

Re: Save System Question ;)

Post by Tony Li »

Hi,

I think you could write a simple saver that calls the CaptureState() and RestoreState() methods. Roughly:

Code: Select all

public class InventorySaver : Saver
{
    [System.Serializable]
    public class Data
    {
        public InventorySlotRecord[inventorySize] slots;
    }
    
    public override string RecordData()
    {
        var data = new Data();
        data.slots = (InventorySlotRecord[])YourInventory.Capture();
        return SaveSystem.Serialize(data);
    }
    
    public override void ApplyData(string s)
    {  // (Skipping checks for empty string, etc.)
        var data = SaveSystem.Deserialize<Data>(s);
        YourInventory.RestoreState(data.slots);
    }
}
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

I tried what you suggested, added all of your code to replace my "inventory saver"...

Then tried to fix the errors until i got something that would compile :) lol...

here is the result :

Code: Select all

using System;
using UnityEngine;
using PixelCrushers;
using GameDevTV.Inventories;
using System.Collections.Generic;

namespace PixelCrushers
{
    public class ShumaInventorySaver : Saver
    {
        [System.Serializable]
        public struct InventorySlotRecord
        {
            public string itemID;
            public int number;
        }

        [System.Serializable]
        public class Data
        {
            public InventorySlotRecord[] slots;
        }

        public override string RecordData()
        {
            var data = new Data();
            Inventory inventory = FindObjectOfType<Inventory>();
            int size = inventory.inventorySize;
            data.slots = new InventorySlotRecord[size];

            data.slots = (InventorySlotRecord[])inventory.CaptureState();
            return SaveSystem.Serialize(data);
        }

        public override void ApplyData(string s)
        {
            if (string.IsNullOrEmpty(s)) return; // No data to apply.
            Data data = SaveSystem.Deserialize<Data>(s);
            if (data == null) return; // Serialized string isn't valid.

            Inventory inventory = FindObjectOfType<Inventory>();
            inventory.RestoreState(data.slots);
        }
    }
}
/**/
However when comes the time to "save", i get an exception :
InvalidCastException: Specified cast is not valid.
which points to "this line" : data.slots = (InventorySlotRecord[])inventory.CaptureState();
so i must have done something wrong...
User avatar
Tony Li
Posts: 21977
Joined: Thu Jul 18, 2013 1:27 pm

Re: Save System Question ;)

Post by Tony Li »

That was just a rough concept example, not complete code. You might find it easier to cleaner to copy the code that's inside the CaptureState() and RestoreState() methods instead of using those exact methods themselves.
User avatar
HawkX
Posts: 147
Joined: Mon Feb 27, 2017 1:50 pm
Location: Quebec
Contact:

Re: Save System Question ;)

Post by HawkX »

hehe i see :)
alright i'll try to do that and rebuild a new saver copying the Capture/Restore from the inventory to the saver and report back later when i have something.... working or crashing! hehe...
Post Reply