summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJesse Plamondon-Willard <Pathoschild@users.noreply.github.com>2022-01-15 17:21:11 -0500
committerJesse Plamondon-Willard <Pathoschild@users.noreply.github.com>2022-01-15 17:21:11 -0500
commit4cffd6c2c092b18940f2dd1041e418f60573a87e (patch)
treee4d07afd879337f3dbe66f6cc89d458fb748c52e
parent8ebb9ce8d4c554b077e1e6286531c101d64c019d (diff)
downloadSMAPI-4cffd6c2c092b18940f2dd1041e418f60573a87e.tar.gz
SMAPI-4cffd6c2c092b18940f2dd1041e418f60573a87e.tar.bz2
SMAPI-4cffd6c2c092b18940f2dd1041e418f60573a87e.zip
add save recovery for missing custom farm type
-rw-r--r--docs/release-notes.md3
-rw-r--r--src/SMAPI.Mods.ErrorHandler/Patches/SaveGamePatcher.cs30
2 files changed, 30 insertions, 3 deletions
diff --git a/docs/release-notes.md b/docs/release-notes.md
index 06d75b15..aea4dbab 100644
--- a/docs/release-notes.md
+++ b/docs/release-notes.md
@@ -3,7 +3,8 @@
# Release notes
## Upcoming release
* For players:
- * Added auto-fix for custom maps which don't have a required tilesheet.
+ * Added automatic fix for custom maps which don't have a required tilesheet.
+ * Added automatic save recovery when the custom farm type isn't available anymore.
* Added the new game build number to the SMAPI console + log.
* Fixed extra newlines shown in the console in non-developer mode.
* Fixed macOS launch issue when using some terminals (thanks to bruce2409!).
diff --git a/src/SMAPI.Mods.ErrorHandler/Patches/SaveGamePatcher.cs b/src/SMAPI.Mods.ErrorHandler/Patches/SaveGamePatcher.cs
index 2a43cb10..0a7ed212 100644
--- a/src/SMAPI.Mods.ErrorHandler/Patches/SaveGamePatcher.cs
+++ b/src/SMAPI.Mods.ErrorHandler/Patches/SaveGamePatcher.cs
@@ -4,11 +4,11 @@ using System.Diagnostics.CodeAnalysis;
using System.Linq;
using HarmonyLib;
using Microsoft.Xna.Framework.Content;
+using StardewModdingAPI.Internal;
using StardewModdingAPI.Internal.Patching;
using StardewValley;
using StardewValley.Buildings;
using StardewValley.Locations;
-using SObject = StardewValley.Object;
namespace StardewModdingAPI.Mods.ErrorHandler.Patches
{
@@ -47,6 +47,11 @@ namespace StardewModdingAPI.Mods.ErrorHandler.Patches
original: this.RequireMethod<SaveGame>(nameof(SaveGame.loadDataToLocations)),
prefix: this.GetHarmonyMethod(nameof(SaveGamePatcher.Before_LoadDataToLocations))
);
+
+ harmony.Patch(
+ original: this.RequireMethod<SaveGame>(nameof(SaveGame.LoadFarmType)),
+ finalizer: this.GetHarmonyMethod(nameof(SaveGamePatcher.Finalize_LoadFarmType))
+ );
}
@@ -58,14 +63,35 @@ namespace StardewModdingAPI.Mods.ErrorHandler.Patches
/// <returns>Returns whether to execute the original method.</returns>
private static bool Before_LoadDataToLocations(List<GameLocation> gamelocations)
{
+ // missing locations/NPCs
IDictionary<string, string> npcs = Game1.content.Load<Dictionary<string, string>>("Data\\NPCDispositions");
-
if (SaveGamePatcher.RemoveBrokenContent(gamelocations, npcs))
SaveGamePatcher.OnContentRemoved();
return true;
}
+ /// <summary>The method to call after <see cref="SaveGame.LoadFarmType"/> throws an exception.</summary>
+ /// <param name="__exception">The exception thrown by the wrapped method, if any.</param>
+ /// <returns>Returns the exception to throw, if any.</returns>
+ private static Exception Finalize_LoadFarmType(Exception __exception)
+ {
+ // missing custom farm type
+ if (__exception?.Message?.Contains("not a valid farm type") == true && !int.TryParse(SaveGame.loaded.whichFarm, out _))
+ {
+ SaveGamePatcher.Monitor.Log(__exception.GetLogSummary(), LogLevel.Error);
+ SaveGamePatcher.Monitor.Log($"Removed invalid custom farm type '{SaveGame.loaded.whichFarm}' to avoid a crash when loading save '{Constants.SaveFolderName}'. (Did you remove a custom farm type mod?)", LogLevel.Warn);
+
+ SaveGame.loaded.whichFarm = Farm.default_layout.ToString();
+ SaveGame.LoadFarmType();
+ SaveGamePatcher.OnContentRemoved();
+
+ __exception = null;
+ }
+
+ return __exception;
+ }
+
/// <summary>Remove content which no longer exists in the game data.</summary>
/// <param name="locations">The current game locations.</param>
/// <param name="npcs">The NPC data.</param>