From bad2ac2a29b8775be97133e4c4cfb67a4a7406ee Mon Sep 17 00:00:00 2001 From: Jesse Plamondon-Willard Date: Sun, 24 Feb 2019 19:56:08 -0500 Subject: remove deprecated APIs (#606) --- src/SMAPI/Framework/Events/ManagedEvent.cs | 105 +++++++++++++++-------------- 1 file changed, 55 insertions(+), 50 deletions(-) (limited to 'src/SMAPI/Framework/Events/ManagedEvent.cs') diff --git a/src/SMAPI/Framework/Events/ManagedEvent.cs b/src/SMAPI/Framework/Events/ManagedEvent.cs index f9e7f6ec..2afe7a03 100644 --- a/src/SMAPI/Framework/Events/ManagedEvent.cs +++ b/src/SMAPI/Framework/Events/ManagedEvent.cs @@ -1,11 +1,12 @@ using System; +using System.Collections.Generic; using System.Linq; namespace StardewModdingAPI.Framework.Events { /// An event wrapper which intercepts and logs errors in handler code. /// The event arguments type. - internal class ManagedEvent : ManagedEventBase> + internal class ManagedEvent { /********* ** Fields @@ -13,6 +14,21 @@ namespace StardewModdingAPI.Framework.Events /// The underlying event. private event EventHandler Event; + /// A human-readable name for the event. + private readonly string EventName; + + /// Writes messages to the log. + private readonly IMonitor Monitor; + + /// The mod registry with which to identify mods. + protected readonly ModRegistry ModRegistry; + + /// The display names for the mods which added each delegate. + private readonly IDictionary, IModMetadata> SourceMods = new Dictionary, IModMetadata>(); + + /// The cached invocation list. + private EventHandler[] CachedInvocationList; + /********* ** Public methods @@ -22,7 +38,17 @@ namespace StardewModdingAPI.Framework.Events /// Writes messages to the log. /// The mod registry with which to identify mods. public ManagedEvent(string eventName, IMonitor monitor, ModRegistry modRegistry) - : base(eventName, monitor, modRegistry) { } + { + this.EventName = eventName; + this.Monitor = monitor; + this.ModRegistry = modRegistry; + } + + /// Get whether anything is listening to the event. + public bool HasListeners() + { + return this.CachedInvocationList?.Length > 0; + } /// Add an event handler. /// The event handler. @@ -91,71 +117,50 @@ namespace StardewModdingAPI.Framework.Events } } } - } - -#if !SMAPI_3_0_STRICT - /// An event wrapper which intercepts and logs errors in handler code. - internal class ManagedEvent : ManagedEventBase - { - /********* - ** Fields - *********/ - /// The underlying event. - private event EventHandler Event; /********* - ** Public methods + ** Private methods *********/ - /// Construct an instance. - /// A human-readable name for the event. - /// Writes messages to the log. - /// The mod registry with which to identify mods. - public ManagedEvent(string eventName, IMonitor monitor, ModRegistry modRegistry) - : base(eventName, monitor, modRegistry) { } - - /// Add an event handler. + /// Track an event handler. + /// The mod which added the handler. /// The event handler. - public void Add(EventHandler handler) + /// The updated event invocation list. + protected void AddTracking(IModMetadata mod, EventHandler handler, IEnumerable> invocationList) { - this.Add(handler, this.ModRegistry.GetFromStack()); + this.SourceMods[handler] = mod; + this.CachedInvocationList = invocationList?.ToArray() ?? new EventHandler[0]; } - /// Add an event handler. + /// Remove tracking for an event handler. /// The event handler. - /// The mod which added the event handler. - public void Add(EventHandler handler, IModMetadata mod) + /// The updated event invocation list. + protected void RemoveTracking(EventHandler handler, IEnumerable> invocationList) { - this.Event += handler; - this.AddTracking(mod, handler, this.Event?.GetInvocationList().Cast()); + this.CachedInvocationList = invocationList?.ToArray() ?? new EventHandler[0]; + if (!this.CachedInvocationList.Contains(handler)) // don't remove if there's still a reference to the removed handler (e.g. it was added twice and removed once) + this.SourceMods.Remove(handler); } - /// Remove an event handler. + /// Get the mod which registered the given event handler, if available. /// The event handler. - public void Remove(EventHandler handler) + protected IModMetadata GetSourceMod(EventHandler handler) { - this.Event -= handler; - this.RemoveTracking(handler, this.Event?.GetInvocationList().Cast()); + return this.SourceMods.TryGetValue(handler, out IModMetadata mod) + ? mod + : null; } - /// Raise the event and notify all handlers. - public void Raise() + /// Log an exception from an event handler. + /// The event handler instance. + /// The exception that was raised. + protected void LogError(EventHandler handler, Exception ex) { - if (this.Event == null) - return; - - foreach (EventHandler handler in this.CachedInvocationList) - { - try - { - handler.Invoke(null, EventArgs.Empty); - } - catch (Exception ex) - { - this.LogError(handler, ex); - } - } + IModMetadata mod = this.GetSourceMod(handler); + if (mod != null) + mod.LogAsMod($"This mod failed in the {this.EventName} event. Technical details: \n{ex.GetLogSummary()}", LogLevel.Error); + else + this.Monitor.Log($"A mod failed in the {this.EventName} event. Technical details: \n{ex.GetLogSummary()}", LogLevel.Error); } } -#endif } -- cgit