Search Unity

Saving a RPG all enemy positions

Discussion in 'General Discussion' started by not_DiSE, Feb 18, 2019.

  1. not_DiSE

    not_DiSE

    Joined:
    Feb 18, 2019
    Posts:
    17
    Hello , I am new to unity and I am making a RPG game . I have already done saving the HP and others with PlayerPrefs . But now I need to save positions of all enemies , their HP ... . How do I save these ?
     
  2. Joe-Censored

    Joe-Censored

    Joined:
    Mar 26, 2013
    Posts:
    11,847
    You'd serialize all this data to save to disk in some manner. The exact manner is up to you, and may depend on what platform you are building for. You should look into Unity's built in JSON support as a starting point, though there's plenty of other ways.
     
    Pixelith likes this.
  3. Samuel411

    Samuel411

    Joined:
    Dec 20, 2012
    Posts:
    646
    I made a blog post about using binary serialization but it can easily be converted to be used for Json using the JSON.NET extension.

    Here's the blog post: http://samuelarminana.com/index.php/2019/02/03/binary-serialization-in-unity/.

    It should cover everything in terms of how you'd go about doing this. I also made another post for object specific savings which I use in my game currently that piggy backs off my serialization post. Here it is, https://samuelarminana.com/index.php/2019/01/25/dynamic-objects-saving-and-loading/.

    You might want to ask on the Programming section of the forums as well.
     
  4. BrandStone

    BrandStone

    Joined:
    Jul 21, 2014
    Posts:
    79
    Step 1 (on save)
    Go through all your enemy positions and save them in a save file (as described above)

    Step 2 (on load)
    Go through the saved positions and spawn the enemies.

    Quite simple if you have a save system in place.
     
  5. infinitypbr

    infinitypbr

    Joined:
    Nov 28, 2012
    Posts:
    3,149
    While I don't know the best answer, please do NOT use PlayerPrefs for this :D I made that mistake years ago, and it's one of the reasons I couldn't upgrade my game once I got better at coding, as it was way too boilerplate.
     
    angrypenguin and BrandStone like this.
  6. BrandStone

    BrandStone

    Joined:
    Jul 21, 2014
    Posts:
    79
    Yep, player prefs are mostly for saving stuf like resolution or sound volume although i also save those in a binary file.
     
  7. SamohtVII

    SamohtVII

    Joined:
    Jun 30, 2014
    Posts:
    370
    What about this. This is how I save some more complex data in my game...

    Code (CSharp):
    1. var data = JsonUtility.ToJson(saveData);
    2. PlayerPrefs.SetString("GameData", data);
    Code (CSharp):
    1. [Serializable]
    2. public struct SaveData
    3. {
    4.     public List<CarListData> CarList;
    5. }
    6. [Serializable]
    7. public struct CarListData
    8. {
    9.     public int carId;
    10.     public List<string> carColors;
    11. }
     
  8. Antony-Blackett

    Antony-Blackett

    Joined:
    Feb 15, 2011
    Posts:
    1,778
    The first question you should ask is: Does it need to be done? Is it ok just have save locations in places where there are no enemies to worry about saving. Is it ok to load and have enemies respawn in their default locations?

    If you really do need to save them then go ahead, but often it is easiest to avoid a hard problem rather than solve it.
     
    pcg likes this.
  9. angrypenguin

    angrypenguin

    Joined:
    Dec 29, 2011
    Posts:
    15,620
    That will "work", in so far as the data will get saved somewhere, and it will be read back. However, a few things to consider:
    • PlayerPrefs gets stored in different places on different platforms. On Windows it is stored in the Registry. It's not nice to force your players to store big chunks of your data there because the Registry is not meant for that.
    • On some platforms PlayerPrefs are really slow to read and write due to where they're stored. Not a big deal if you're reading some settings at load time, but pretty bad if you need to access them a lot.
    • It also makes it difficult for Windows players to copy / transfer / back up their game progress. For non-Windows platforms, it might make it harder for you to provide save-game transfer services (eg: cloud syncing).
    • Not all data can be nicely saved as a string, so you may run into limitations there.
    • Last I checked, Unity doesn't have a way to find out what all of your PlayerPrefs keys are. You can use a key you already know, or you can clear all keys. While not impossible, this makes it painful to manage large amounts of data in PlayerPrefs.
    .NET / Mono comes with a fully functional file IO library, which is a very good thing to learn to use anyway.
     
  10. You also can utilize the Google Proto serialization. Nowadays it's fairly easy to use even in C# and Unity. Especially with @5argon's excellent extension: https://github.com/5argon/protobuf-unity

    I was able to set it up recently in 2019.3 for testing purposes under 20 minutes. Proto files are building automatically. The serialization is more compact than the YAML, JSON or XML, it's excellent to write out into either file stream or network stream.
    Also the proto messages are fairly standard and type-safe. So if you want to build a serious serialization-system give it a try. I think it does worth it.
     
    Last edited by a moderator: Jul 8, 2019
    ChrisDirkis and 5argon like this.
  11. infinitypbr

    infinitypbr

    Joined:
    Nov 28, 2012
    Posts:
    3,149
    I would suggest not using PlayerPrefs for this.

    This is my current code for saving / loading data:

    Code (CSharp):
    1. public void SaveGameData(int id)
    2.     {
    3.         Debug.Log("Saving Game : " + id);
    4.         string dataAsJson = JsonUtility.ToJson(data);                           // writes all of data as json
    5.         string filePath = Application.dataPath + "/gamedata" + id + ".json";    // File path for the saved game file
    6.         File.WriteAllText(filePath, dataAsJson);                                // Save the file.  Will overwrite existing file.
    7.         if (File.Exists(filePath))                                              // if the file exists
    8.         {
    9.             Debug.Log("Saving Game Done");
    10.         }
    11.         else
    12.         {
    13.             Debug.Log("File now found!");
    14.         }
    15.         LoadGameList();
    16.     }
    17.  
    18. public void LoadGame(int id)
    19.     {
    20.         string filePath = Application.dataPath + "/gamedata" + id + ".json";    // File path to the saved game file
    21.         if (File.Exists(filePath))                                              // if the file exists
    22.         {
    23.             string dataAsJson = File.ReadAllText(filePath);                     // Read the file as json
    24.             Data newList = JsonUtility.FromJson<Data>(dataAsJson);              // Set the json data into a new Data variable called newList
    25.             data = newList;                                                     // Replace data with newList, effectively loading the game.
    26.         }
    27.     }
    28.  
    It may not be the best, as i'm not crazy experienced in coding, but it works well for me and seems to be efficient for a large-scale RPG project.

    In this case,
    data
    is all the stored data for the game -- one class that holds all the information that needs to be saved. It's updated during gameplay, and saved / loaded with this code.
     
  12. Kondor0

    Kondor0

    Joined:
    Feb 20, 2010
    Posts:
    601
    Check this old vid:


    Basically you have to:
    - Create a serializable class with all the data that's needed for a game session: player health, enemy positions, scene to load, etc.
    - Add code to save it or load it as a binary file (some people use JSON but in my case binary files are more than enough, I shipped 2 games with that and so far I have no problems).
     
    frosted and infinitypbr like this.
  13. N1warhead

    N1warhead

    Joined:
    Mar 12, 2014
    Posts:
    3,884
    https://github.com/WarheadDesignz/UnISave Could always check this out. Not sure how many people still use this.
    But you simply stick a script into the scene and stick a script onto things that are instantiated and it simply just works.

    (I believe I have it set up to work with key presses), I believe SpaceBar is Save.
    From testing it can save and load thousands of objects and their properties in like 0.5 to 2 seconds depending on your computer. At least that's what I remember, might be more like 5 seconds I don't recall exactly. But it works.

    It's a complete custom solution. No JSon Serializing, etc.
     
    Last edited: Jul 9, 2019