using System.Collections.Generic; using UnityEngine; using UnityEngine.SceneManagement; namespace Fungus { /// /// Serializable container for a Save Point. /// [System.Serializable] public class SavePointData { [SerializeField] protected string savePointKey; [SerializeField] protected string savePointDescription; [SerializeField] protected string sceneName; [SerializeField] protected List flowchartDatas = new List(); protected static SavePointData tempSavePointData; protected static void OnSceneLoaded(Scene scene, LoadSceneMode mode) { if (scene.name != tempSavePointData.SceneName) { return; } SceneManager.sceneLoaded -= OnSceneLoaded; var savePointData = tempSavePointData; for (int i = 0; i < savePointData.FlowchartDatas.Count; i++) { var flowchartData = savePointData.FlowchartDatas[i]; FlowchartData.Decode(flowchartData); } ExecuteBlocks(savePointData.savePointKey); } protected static SavePointData Create(string _savePointKey, string _savePointDescription, string _sceneName) { var savePointData = new SavePointData(); savePointData.savePointKey = _savePointKey; savePointData.savePointDescription = _savePointDescription; savePointData.sceneName = _sceneName; return savePointData; } #region Public methods /// /// Gets or sets the unique key for the Save Point. /// public string SavePointKey { get { return savePointKey; } set { savePointKey = value; } } /// /// Gets or sets the description for the Save Point. /// public string SavePointDescription { get { return savePointDescription; } set { savePointDescription = value; } } /// /// Gets or sets the scene name associated with the Save Point. /// public string SceneName { get { return sceneName; } set { sceneName = value; } } /// /// Gets or sets the encoded Flowchart data for the Save Point. /// public List FlowchartDatas { get { return flowchartDatas; } set { flowchartDatas = value; } } /// /// Encodes a new Save Point to data and converts it to JSON text format. /// public static string Encode(string _savePointKey, string _savePointDescription, string _sceneName) { var savePointData = Create(_savePointKey, _savePointDescription, _sceneName); var saveGameObjects = GameObject.FindObjectOfType(); if (saveGameObjects == null) { Debug.LogWarning("Failed to find a SaveGameObjects in current scene"); } else { saveGameObjects.Encode(savePointData); } return JsonUtility.ToJson(savePointData, true); } /// /// Decodes a Save Point from JSON text format and loads it. /// public static void Decode(string saveDataJSON) { tempSavePointData = JsonUtility.FromJson(saveDataJSON); SceneManager.sceneLoaded += OnSceneLoaded; SceneManager.LoadScene(tempSavePointData.SceneName); } /// /// Starts Block execution based on a Save Point Key /// The execution order is: /// 1. Save Point Loaded event handlers with a matching key. /// 2. First Save Point command (in any Block) with matching key. Execution starts at following command. /// 3. Any label in any block with name matching the key. Execution starts at following command. /// public static void ExecuteBlocks(string savePointKey) { // Execute Save Point Loaded event handlers with matching key. SavePointLoaded.NotifyEventHandlers(savePointKey); // Execute any block containing a SavePoint command matching the save key, with Resume From Here enabled var savePoints = Object.FindObjectsOfType(); for (int i = 0; i < savePoints.Length; i++) { var savePoint = savePoints[i]; if (savePoint.ResumeFromHere && string.Compare(savePoint.SavePointKey, savePointKey, true) == 0) { int index = savePoint.CommandIndex; var block = savePoint.ParentBlock; var flowchart = savePoint.GetFlowchart(); flowchart.ExecuteBlock(block, index + 1); // Assume there's only one SavePoint using this key break; } } // Execute any block containing a Label matching the save key var labels = Object.FindObjectsOfType