summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJesse Plamondon-Willard <github@jplamondonw.com>2018-06-06 21:45:03 -0400
committerJesse Plamondon-Willard <github@jplamondonw.com>2018-06-06 21:45:03 -0400
commitcd62dcc8cfa35a9b423f4d15359ec3083b4c6d44 (patch)
treef5eb9c233aeaa44b9d0c22278b86c5648d5ac393
parent9e525533e10ade49c733a34373e0fb749748918e (diff)
downloadSMAPI-cd62dcc8cfa35a9b423f4d15359ec3083b4c6d44.tar.gz
SMAPI-cd62dcc8cfa35a9b423f4d15359ec3083b4c6d44.tar.bz2
SMAPI-cd62dcc8cfa35a9b423f4d15359ec3083b4c6d44.zip
add simple Harmony wrapper for validation, error-handling, etc (#541)
-rw-r--r--src/SMAPI/Constants.cs3
-rw-r--r--src/SMAPI/Framework/Patching/GamePatcher.cs45
-rw-r--r--src/SMAPI/Framework/Patching/IHarmonyPatch.cs15
-rw-r--r--src/SMAPI/Program.cs14
-rw-r--r--src/SMAPI/StardewModdingAPI.csproj2
5 files changed, 71 insertions, 8 deletions
diff --git a/src/SMAPI/Constants.cs b/src/SMAPI/Constants.cs
index 786c1a39..d96c5839 100644
--- a/src/SMAPI/Constants.cs
+++ b/src/SMAPI/Constants.cs
@@ -103,6 +103,9 @@ namespace StardewModdingAPI
/// <summary>The target game platform.</summary>
internal static Platform Platform { get; } = EnvironmentUtility.DetectPlatform();
+ /// <summary>The game's assembly name.</summary>
+ internal static string GameAssemblyName => Constants.Platform == Platform.Windows ? "Stardew Valley" : "StardewValley";
+
/*********
** Internal methods
diff --git a/src/SMAPI/Framework/Patching/GamePatcher.cs b/src/SMAPI/Framework/Patching/GamePatcher.cs
new file mode 100644
index 00000000..71ca8e55
--- /dev/null
+++ b/src/SMAPI/Framework/Patching/GamePatcher.cs
@@ -0,0 +1,45 @@
+using System;
+using Harmony;
+
+namespace StardewModdingAPI.Framework.Patching
+{
+ /// <summary>Encapsulates applying Harmony patches to the game.</summary>
+ internal class GamePatcher
+ {
+ /*********
+ ** Properties
+ *********/
+ /// <summary>Encapsulates monitoring and logging.</summary>
+ private readonly IMonitor Monitor;
+
+
+ /*********
+ ** Public methods
+ *********/
+ /// <summary>Construct an instance.</summary>
+ /// <param name="monitor">Encapsulates monitoring and logging.</param>
+ public GamePatcher(IMonitor monitor)
+ {
+ this.Monitor = monitor;
+ }
+
+ /// <summary>Apply all loaded patches to the game.</summary>
+ /// <param name="patches">The patches to apply.</param>
+ public void Apply(params IHarmonyPatch[] patches)
+ {
+ HarmonyInstance harmony = HarmonyInstance.Create("io.smapi");
+ foreach (IHarmonyPatch patch in patches)
+ {
+ try
+ {
+ patch.Apply(harmony);
+ }
+ catch (Exception ex)
+ {
+ this.Monitor.Log($"Couldn't apply runtime patch '{patch.Name}' to the game. Some SMAPI features may not work correctly. See log file for details.", LogLevel.Error);
+ this.Monitor.Log(ex.GetLogSummary(), LogLevel.Trace);
+ }
+ }
+ }
+ }
+}
diff --git a/src/SMAPI/Framework/Patching/IHarmonyPatch.cs b/src/SMAPI/Framework/Patching/IHarmonyPatch.cs
new file mode 100644
index 00000000..cb42f40e
--- /dev/null
+++ b/src/SMAPI/Framework/Patching/IHarmonyPatch.cs
@@ -0,0 +1,15 @@
+using Harmony;
+
+namespace StardewModdingAPI.Framework.Patching
+{
+ /// <summary>A Harmony patch to apply.</summary>
+ internal interface IHarmonyPatch
+ {
+ /// <summary>A unique name for this patch.</summary>
+ string Name { get; }
+
+ /// <summary>Apply the Harmony patch.</summary>
+ /// <param name="harmony">The Harmony instance.</param>
+ void Apply(HarmonyInstance harmony);
+ }
+}
diff --git a/src/SMAPI/Program.cs b/src/SMAPI/Program.cs
index cc59c0cd..bf673fe6 100644
--- a/src/SMAPI/Program.cs
+++ b/src/SMAPI/Program.cs
@@ -24,6 +24,7 @@ using StardewModdingAPI.Framework.ModData;
using StardewModdingAPI.Framework.Models;
using StardewModdingAPI.Framework.ModHelpers;
using StardewModdingAPI.Framework.ModLoading;
+using StardewModdingAPI.Framework.Patching;
using StardewModdingAPI.Framework.Reflection;
using StardewModdingAPI.Framework.Serialisation;
using StardewModdingAPI.Internal;
@@ -152,6 +153,10 @@ namespace StardewModdingAPI
};
this.EventManager = new EventManager(this.Monitor, this.ModRegistry);
+ // apply game patches
+ new GamePatcher(this.Monitor).Apply(
+ );
+
// init JSON parser
JsonConverter[] converters = {
new StringEnumConverter<Buttons>(),
@@ -359,14 +364,7 @@ namespace StardewModdingAPI
Console.ResetColor();
Program.PressAnyKeyToExit(showMessage: true);
}
-
- // get game assembly name
- const string gameAssemblyName =
-#if SMAPI_FOR_WINDOWS
- "Stardew Valley";
-#else
- "StardewValley";
-#endif
+ string gameAssemblyName = Constants.GameAssemblyName;
// game not present
if (Type.GetType($"StardewValley.Game1, {gameAssemblyName}", throwOnError: false) == null)
diff --git a/src/SMAPI/StardewModdingAPI.csproj b/src/SMAPI/StardewModdingAPI.csproj
index d2a65f48..125e7746 100644
--- a/src/SMAPI/StardewModdingAPI.csproj
+++ b/src/SMAPI/StardewModdingAPI.csproj
@@ -107,6 +107,8 @@
<Compile Include="Framework\ContentManagers\GameContentManager.cs" />
<Compile Include="Framework\ContentManagers\IContentManager.cs" />
<Compile Include="Framework\ContentManagers\ModContentManager.cs" />
+ <Compile Include="Framework\Patching\GamePatcher.cs" />
+ <Compile Include="Framework\Patching\IHarmonyPatch.cs" />
<Compile Include="Framework\Serialisation\ColorConverter.cs" />
<Compile Include="Framework\Serialisation\PointConverter.cs" />
<Compile Include="Framework\Serialisation\RectangleConverter.cs" />