From b742abe77fd0bde0d5cf5657ec28759989bb370c Mon Sep 17 00:00:00 2001 From: MidoriKami <9083275+MidoriKami@users.noreply.github.com> Date: Thu, 21 Sep 2023 21:55:16 -0700 Subject: [PATCH 1/7] Add ClientStatePluginScoped (#1384) * Add ClientStatePluginScoped * Restore InvokeSafely * Add InvokeSafely for basic Action types. * Set delegates to null to prevent leaking memory * Resolve Merge --- Dalamud/Game/ClientState/ClientState.cs | 137 +++++++++++++++--- Dalamud/Game/DutyState/DutyState.cs | 2 +- .../Game/Network/Internal/NetworkHandlers.cs | 6 +- .../AgingSteps/EnterTerritoryAgingStep.cs | 4 +- .../AgingSteps/LoginEventAgingStep.cs | 2 +- .../AgingSteps/LogoutEventAgingStep.cs | 2 +- Dalamud/Plugin/Services/IClientState.cs | 8 +- Dalamud/Utility/EventHandlerExtensions.cs | 41 +++++- 8 files changed, 165 insertions(+), 37 deletions(-) diff --git a/Dalamud/Game/ClientState/ClientState.cs b/Dalamud/Game/ClientState/ClientState.cs index cef802c81..baf6f6634 100644 --- a/Dalamud/Game/ClientState/ClientState.cs +++ b/Dalamud/Game/ClientState/ClientState.cs @@ -8,24 +8,25 @@ using Dalamud.Game.Network.Internal; using Dalamud.Hooking; using Dalamud.IoC; using Dalamud.IoC.Internal; +using Dalamud.Logging.Internal; using Dalamud.Plugin.Services; using Dalamud.Utility; using FFXIVClientStructs.FFXIV.Client.Game; -using Serilog; +using Lumina.Excel.GeneratedSheets; + +using Action = System.Action; namespace Dalamud.Game.ClientState; /// /// This class represents the state of the game client at the time of access. /// -[PluginInterface] [InterfaceVersion("1.0")] [ServiceManager.BlockingEarlyLoadedService] -#pragma warning disable SA1015 -[ResolveVia] -#pragma warning restore SA1015 internal sealed class ClientState : IDisposable, IServiceType, IClientState { + private static readonly ModuleLog Log = new("ClientState"); + private readonly GameLifecycle lifecycle; private readonly ClientStateAddressResolver address; private readonly Hook setupTerritoryTypeHook; @@ -37,7 +38,7 @@ internal sealed class ClientState : IDisposable, IServiceType, IClientState private readonly NetworkHandlers networkHandlers = Service.Get(); private bool lastConditionNone = true; - private bool lastFramePvP = false; + private bool lastFramePvP; [ServiceManager.ServiceConstructor] private ClientState(SigScanner sigScanner, DalamudStartInfo startInfo, GameLifecycle lifecycle) @@ -63,22 +64,22 @@ internal sealed class ClientState : IDisposable, IServiceType, IClientState private delegate IntPtr SetupTerritoryTypeDelegate(IntPtr manager, ushort terriType); /// - public event EventHandler TerritoryChanged; + public event Action? TerritoryChanged; /// - public event EventHandler Login; + public event Action? Login; /// - public event EventHandler Logout; + public event Action? Logout; /// - public event Action EnterPvP; + public event Action? EnterPvP; /// - public event Action LeavePvP; + public event Action? LeavePvP; /// - public event EventHandler CfPop; + public event Action? CfPop; /// public ClientLanguage ClientLanguage { get; } @@ -128,16 +129,16 @@ internal sealed class ClientState : IDisposable, IServiceType, IClientState private IntPtr SetupTerritoryTypeDetour(IntPtr manager, ushort terriType) { this.TerritoryType = terriType; - this.TerritoryChanged?.InvokeSafely(this, terriType); + this.TerritoryChanged?.InvokeSafely(terriType); Log.Debug("TerritoryType changed: {0}", terriType); return this.setupTerritoryTypeHook.Original(manager, terriType); } - private void NetworkHandlersOnCfPop(object sender, Lumina.Excel.GeneratedSheets.ContentFinderCondition e) + private void NetworkHandlersOnCfPop(ContentFinderCondition e) { - this.CfPop?.InvokeSafely(this, e); + this.CfPop?.InvokeSafely(e); } private void FrameworkOnOnUpdateEvent(IFramework framework1) @@ -149,12 +150,12 @@ internal sealed class ClientState : IDisposable, IServiceType, IClientState if (condition == null || gameGui == null || data == null) return; - if (condition.Any() && this.lastConditionNone == true && this.LocalPlayer != null) + if (condition.Any() && this.lastConditionNone && this.LocalPlayer != null) { Log.Debug("Is login"); this.lastConditionNone = false; this.IsLoggedIn = true; - this.Login?.InvokeSafely(this, null); + this.Login?.InvokeSafely(); gameGui.ResetUiHideState(); this.lifecycle.ResetLogout(); @@ -165,7 +166,7 @@ internal sealed class ClientState : IDisposable, IServiceType, IClientState Log.Debug("Is logout"); this.lastConditionNone = true; this.IsLoggedIn = false; - this.Logout?.InvokeSafely(this, null); + this.Logout?.InvokeSafely(); gameGui.ResetUiHideState(); this.lifecycle.SetLogout(); @@ -189,3 +190,103 @@ internal sealed class ClientState : IDisposable, IServiceType, IClientState } } } + +/// +/// Plugin-scoped version of a GameConfig service. +/// +[PluginInterface] +[InterfaceVersion("1.0")] +[ServiceManager.ScopedService] +#pragma warning disable SA1015 +[ResolveVia] +#pragma warning restore SA1015 +internal class ClientStatePluginScoped : IDisposable, IServiceType, IClientState +{ + [ServiceManager.ServiceDependency] + private readonly ClientState clientStateService = Service.Get(); + + /// + /// Initializes a new instance of the class. + /// + internal ClientStatePluginScoped() + { + this.clientStateService.TerritoryChanged += this.TerritoryChangedForward; + this.clientStateService.Login += this.LoginForward; + this.clientStateService.Logout += this.LogoutForward; + this.clientStateService.EnterPvP += this.EnterPvPForward; + this.clientStateService.LeavePvP += this.ExitPvPForward; + this.clientStateService.CfPop += this.ContentFinderPopForward; + } + + /// + public event Action? TerritoryChanged; + + /// + public event Action? Login; + + /// + public event Action? Logout; + + /// + public event Action? EnterPvP; + + /// + public event Action? LeavePvP; + + /// + public event Action? CfPop; + + /// + public ClientLanguage ClientLanguage => this.clientStateService.ClientLanguage; + + /// + public ushort TerritoryType => this.clientStateService.TerritoryType; + + /// + public PlayerCharacter? LocalPlayer => this.clientStateService.LocalPlayer; + + /// + public ulong LocalContentId => this.clientStateService.LocalContentId; + + /// + public bool IsLoggedIn => this.clientStateService.IsLoggedIn; + + /// + public bool IsPvP => this.clientStateService.IsPvP; + + /// + public bool IsPvPExcludingDen => this.clientStateService.IsPvPExcludingDen; + + /// + public bool IsGPosing => this.clientStateService.IsGPosing; + + /// + public void Dispose() + { + this.clientStateService.TerritoryChanged -= this.TerritoryChangedForward; + this.clientStateService.Login -= this.LoginForward; + this.clientStateService.Logout -= this.LogoutForward; + this.clientStateService.EnterPvP -= this.EnterPvPForward; + this.clientStateService.LeavePvP -= this.ExitPvPForward; + this.clientStateService.CfPop -= this.ContentFinderPopForward; + + this.TerritoryChanged = null; + this.Login = null; + this.Logout = null; + this.EnterPvP = null; + this.LeavePvP = null; + this.CfPop = null; + } + + private void TerritoryChangedForward(ushort territoryId) => this.TerritoryChanged?.Invoke(territoryId); + + private void LoginForward() => this.Login?.Invoke(); + + private void LogoutForward() => this.Logout?.Invoke(); + + private void EnterPvPForward() => this.EnterPvP?.Invoke(); + + private void ExitPvPForward() => this.LeavePvP?.Invoke(); + + private void ContentFinderPopForward(ContentFinderCondition cfc) => this.CfPop?.Invoke(cfc); +} diff --git a/Dalamud/Game/DutyState/DutyState.cs b/Dalamud/Game/DutyState/DutyState.cs index c52ceff0f..3890a1f8b 100644 --- a/Dalamud/Game/DutyState/DutyState.cs +++ b/Dalamud/Game/DutyState/DutyState.cs @@ -120,7 +120,7 @@ internal unsafe class DutyState : IDisposable, IServiceType, IDutyState return this.contentDirectorNetworkMessageHook.Original(a1, a2, a3); } - private void TerritoryOnChangedEvent(object? sender, ushort e) + private void TerritoryOnChangedEvent(ushort territoryId) { if (this.IsDutyStarted) { diff --git a/Dalamud/Game/Network/Internal/NetworkHandlers.cs b/Dalamud/Game/Network/Internal/NetworkHandlers.cs index 1ccf6c6d5..77bf99c1b 100644 --- a/Dalamud/Game/Network/Internal/NetworkHandlers.cs +++ b/Dalamud/Game/Network/Internal/NetworkHandlers.cs @@ -44,7 +44,7 @@ internal class NetworkHandlers : IDisposable, IServiceType private NetworkHandlers(GameNetwork gameNetwork) { this.uploader = new UniversalisMarketBoardUploader(); - this.CfPop = (_, _) => { }; + this.CfPop = _ => { }; this.messages = Observable.Create(observer => { @@ -75,7 +75,7 @@ internal class NetworkHandlers : IDisposable, IServiceType /// /// Event which gets fired when a duty is ready. /// - public event EventHandler CfPop; + public event Action CfPop; /// /// Disposes of managed and unmanaged resources. @@ -430,7 +430,7 @@ internal class NetworkHandlers : IDisposable, IServiceType Service.GetNullable()?.Print($"Duty pop: {cfcName}"); } - this.CfPop.InvokeSafely(this, cfCondition); + this.CfPop.InvokeSafely(cfCondition); }).ContinueWith( task => Log.Error(task.Exception, "CfPop.Invoke failed"), TaskContinuationOptions.OnlyOnFaulted); diff --git a/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/EnterTerritoryAgingStep.cs b/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/EnterTerritoryAgingStep.cs index d301cb1ff..4f5c758d6 100644 --- a/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/EnterTerritoryAgingStep.cs +++ b/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/EnterTerritoryAgingStep.cs @@ -59,9 +59,9 @@ internal class EnterTerritoryAgingStep : IAgingStep this.subscribed = false; } - private void ClientStateOnTerritoryChanged(object sender, ushort e) + private void ClientStateOnTerritoryChanged(ushort territoryId) { - if (e == this.territory) + if (territoryId == this.territory) { this.hasPassed = true; } diff --git a/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LoginEventAgingStep.cs b/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LoginEventAgingStep.cs index c1dba389f..23b0b903a 100644 --- a/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LoginEventAgingStep.cs +++ b/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LoginEventAgingStep.cs @@ -51,7 +51,7 @@ internal class LoginEventAgingStep : IAgingStep } } - private void ClientStateOnOnLogin(object sender, EventArgs e) + private void ClientStateOnOnLogin() { this.hasPassed = true; } diff --git a/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LogoutEventAgingStep.cs b/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LogoutEventAgingStep.cs index 060c0bcc8..c4c6ebfce 100644 --- a/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LogoutEventAgingStep.cs +++ b/Dalamud/Interface/Internal/Windows/SelfTest/AgingSteps/LogoutEventAgingStep.cs @@ -51,7 +51,7 @@ internal class LogoutEventAgingStep : IAgingStep } } - private void ClientStateOnOnLogout(object sender, EventArgs e) + private void ClientStateOnOnLogout() { this.hasPassed = true; } diff --git a/Dalamud/Plugin/Services/IClientState.cs b/Dalamud/Plugin/Services/IClientState.cs index 881cad841..652a6c888 100644 --- a/Dalamud/Plugin/Services/IClientState.cs +++ b/Dalamud/Plugin/Services/IClientState.cs @@ -12,17 +12,17 @@ public interface IClientState /// /// Event that gets fired when the current Territory changes. /// - public event EventHandler TerritoryChanged; + public event Action TerritoryChanged; /// /// Event that fires when a character is logging in, and the local character object is available. /// - public event EventHandler Login; + public event Action Login; /// /// Event that fires when a character is logging out. /// - public event EventHandler Logout; + public event Action Logout; /// /// Event that fires when a character is entering PvP. @@ -37,7 +37,7 @@ public interface IClientState /// /// Event that gets fired when a duty is ready. /// - public event EventHandler CfPop; + public event Action CfPop; /// /// Gets the language of the client. diff --git a/Dalamud/Utility/EventHandlerExtensions.cs b/Dalamud/Utility/EventHandlerExtensions.cs index eefd245bb..d05ad6ea5 100644 --- a/Dalamud/Utility/EventHandlerExtensions.cs +++ b/Dalamud/Utility/EventHandlerExtensions.cs @@ -1,12 +1,9 @@ -using System; using System.Linq; using Dalamud.Game; using Dalamud.Plugin.Services; using Serilog; -using static Dalamud.Game.Framework; - namespace Dalamud.Utility; /// @@ -21,7 +18,7 @@ internal static class EventHandlerExtensions /// The EventHandler in question. /// Default sender for Invoke equivalent. /// Default EventArgs for Invoke equivalent. - public static void InvokeSafely(this EventHandler eh, object sender, EventArgs e) + public static void InvokeSafely(this EventHandler? eh, object sender, EventArgs e) { if (eh == null) return; @@ -40,7 +37,7 @@ internal static class EventHandlerExtensions /// Default sender for Invoke equivalent. /// Default EventArgs for Invoke equivalent. /// Type of EventArgs. - public static void InvokeSafely(this EventHandler eh, object sender, T e) + public static void InvokeSafely(this EventHandler? eh, object sender, T e) { if (eh == null) return; @@ -56,7 +53,7 @@ internal static class EventHandlerExtensions /// of a thrown Exception inside of an invocation. /// /// The Action in question. - public static void InvokeSafely(this Action act) + public static void InvokeSafely(this Action? act) { if (act == null) return; @@ -67,13 +64,31 @@ internal static class EventHandlerExtensions } } + /// + /// Replacement for Invoke() on event Actions to catch exceptions that stop event propagation in case + /// of a thrown Exception inside of an invocation. + /// + /// The Action in question. + /// Templated argument for Action. + /// Type of Action args. + public static void InvokeSafely(this Action? act, T argument) + { + if (act == null) + return; + + foreach (var action in act.GetInvocationList().Cast>()) + { + HandleInvoke(action, argument); + } + } + /// /// Replacement for Invoke() on OnUpdateDelegate to catch exceptions that stop event propagation in case /// of a thrown Exception inside of an invocation. /// /// The OnUpdateDelegate in question. /// Framework to be passed on to OnUpdateDelegate. - public static void InvokeSafely(this IFramework.OnUpdateDelegate updateDelegate, Framework framework) + public static void InvokeSafely(this IFramework.OnUpdateDelegate? updateDelegate, Framework framework) { if (updateDelegate == null) return; @@ -95,4 +110,16 @@ internal static class EventHandlerExtensions Log.Error(ex, "Exception during raise of {handler}", act.Method); } } + + private static void HandleInvoke(Action act, T argument) + { + try + { + act(argument); + } + catch (Exception ex) + { + Log.Error(ex, "Exception during raise of {handler}", act.Method); + } + } } From 43abb12710e1193f6e3ba898a932b3583826baba Mon Sep 17 00:00:00 2001 From: MidoriKami <9083275+MidoriKami@users.noreply.github.com> Date: Thu, 21 Sep 2023 21:55:56 -0700 Subject: [PATCH 2/7] Add GameConfigPluginScoped (#1383) * Add GameConfigPluginScoped * Proposed Resolution to sub-object events * Nullify delegates to prevent memory leaks --- Dalamud/Game/Config/GameConfig.cs | 224 ++++++++++++++++++++++- Dalamud/Game/Config/GameConfigSection.cs | 2 +- Dalamud/Plugin/Services/IGameConfig.cs | 17 +- 3 files changed, 235 insertions(+), 8 deletions(-) diff --git a/Dalamud/Game/Config/GameConfig.cs b/Dalamud/Game/Config/GameConfig.cs index b77b9c4af..831c1157b 100644 --- a/Dalamud/Game/Config/GameConfig.cs +++ b/Dalamud/Game/Config/GameConfig.cs @@ -12,11 +12,7 @@ namespace Dalamud.Game.Config; /// This class represents the game's configuration. /// [InterfaceVersion("1.0")] -[PluginInterface] [ServiceManager.EarlyLoadedService] -#pragma warning disable SA1015 -[ResolveVia] -#pragma warning restore SA1015 internal sealed class GameConfig : IServiceType, IGameConfig, IDisposable { private readonly GameConfigAddressResolver address = new(); @@ -36,15 +32,30 @@ internal sealed class GameConfig : IServiceType, IGameConfig, IDisposable this.address.Setup(sigScanner); this.configChangeHook = Hook.FromAddress(this.address.ConfigChangeAddress, this.OnConfigChanged); - this.configChangeHook?.Enable(); + this.configChangeHook.Enable(); }); } private unsafe delegate nint ConfigChangeDelegate(ConfigBase* configBase, ConfigEntry* configEntry); /// - public event EventHandler Changed; + public event EventHandler? Changed; + + /// + /// Unused internally, used as a proxy for System.Changed via GameConfigPluginScoped + /// + public event EventHandler? SystemChanged; + /// + /// Unused internally, used as a proxy for UiConfig.Changed via GameConfigPluginScoped + /// + public event EventHandler? UiConfigChanged; + + /// + /// Unused internally, used as a proxy for UiControl.Changed via GameConfigPluginScoped + /// + public event EventHandler? UiControlChanged; + /// public GameConfigSection System { get; private set; } @@ -192,3 +203,204 @@ internal sealed class GameConfig : IServiceType, IGameConfig, IDisposable return returnValue; } } + +/// +/// Plugin-scoped version of a GameConfig service. +/// +[PluginInterface] +[InterfaceVersion("1.0")] +[ServiceManager.ScopedService] +#pragma warning disable SA1015 +[ResolveVia] +#pragma warning restore SA1015 +internal class GameConfigPluginScoped : IDisposable, IServiceType, IGameConfig +{ + [ServiceManager.ServiceDependency] + private readonly GameConfig gameConfigService = Service.Get(); + + /// + /// Initializes a new instance of the class. + /// + internal GameConfigPluginScoped() + { + this.gameConfigService.Changed += this.ConfigChangedForward; + this.gameConfigService.System.Changed += this.SystemConfigChangedForward; + this.gameConfigService.UiConfig.Changed += this.UiConfigConfigChangedForward; + this.gameConfigService.UiControl.Changed += this.UiControlConfigChangedForward; + } + + /// + public event EventHandler? Changed; + + /// + public event EventHandler? SystemChanged; + + /// + public event EventHandler? UiConfigChanged; + + /// + public event EventHandler? UiControlChanged; + + /// + public GameConfigSection System => this.gameConfigService.System; + + /// + public GameConfigSection UiConfig => this.gameConfigService.UiConfig; + + /// + public GameConfigSection UiControl => this.gameConfigService.UiControl; + + /// + public void Dispose() + { + this.gameConfigService.Changed -= this.ConfigChangedForward; + this.gameConfigService.System.Changed -= this.SystemConfigChangedForward; + this.gameConfigService.UiConfig.Changed -= this.UiConfigConfigChangedForward; + this.gameConfigService.UiControl.Changed -= this.UiControlConfigChangedForward; + + this.Changed = null; + this.SystemChanged = null; + this.UiConfigChanged = null; + this.UiControlChanged = null; + } + + /// + public bool TryGet(SystemConfigOption option, out bool value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(SystemConfigOption option, out uint value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(SystemConfigOption option, out float value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(SystemConfigOption option, out string value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(SystemConfigOption option, out UIntConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(SystemConfigOption option, out FloatConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(SystemConfigOption option, out StringConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(UiConfigOption option, out bool value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiConfigOption option, out uint value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiConfigOption option, out float value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiConfigOption option, out string value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiConfigOption option, out UIntConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(UiConfigOption option, out FloatConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(UiConfigOption option, out StringConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(UiControlOption option, out bool value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiControlOption option, out uint value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiControlOption option, out float value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiControlOption option, out string value) + => this.gameConfigService.TryGet(option, out value); + + /// + public bool TryGet(UiControlOption option, out UIntConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(UiControlOption option, out FloatConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public bool TryGet(UiControlOption option, out StringConfigProperties? properties) + => this.gameConfigService.TryGet(option, out properties); + + /// + public void Set(SystemConfigOption option, bool value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(SystemConfigOption option, uint value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(SystemConfigOption option, float value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(SystemConfigOption option, string value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiConfigOption option, bool value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiConfigOption option, uint value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiConfigOption option, float value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiConfigOption option, string value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiControlOption option, bool value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiControlOption option, uint value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiControlOption option, float value) + => this.gameConfigService.Set(option, value); + + /// + public void Set(UiControlOption option, string value) + => this.gameConfigService.Set(option, value); + + private void ConfigChangedForward(object sender, ConfigChangeEvent data) => this.Changed?.Invoke(sender, data); + + private void SystemConfigChangedForward(object sender, ConfigChangeEvent data) => this.SystemChanged?.Invoke(sender, data); + + private void UiConfigConfigChangedForward(object sender, ConfigChangeEvent data) => this.UiConfigChanged?.Invoke(sender, data); + + private void UiControlConfigChangedForward(object sender, ConfigChangeEvent data) => this.UiControlChanged?.Invoke(sender, data); +} diff --git a/Dalamud/Game/Config/GameConfigSection.cs b/Dalamud/Game/Config/GameConfigSection.cs index ea79a7fc8..31e4a0b3f 100644 --- a/Dalamud/Game/Config/GameConfigSection.cs +++ b/Dalamud/Game/Config/GameConfigSection.cs @@ -51,7 +51,7 @@ public class GameConfigSection /// /// Event which is fired when a game config option is changed within the section. /// - public event EventHandler? Changed; + internal event EventHandler? Changed; /// /// Gets the number of config entries contained within the section. diff --git a/Dalamud/Plugin/Services/IGameConfig.cs b/Dalamud/Plugin/Services/IGameConfig.cs index 69a611114..8e9b48d83 100644 --- a/Dalamud/Plugin/Services/IGameConfig.cs +++ b/Dalamud/Plugin/Services/IGameConfig.cs @@ -12,10 +12,25 @@ namespace Dalamud.Plugin.Services; public interface IGameConfig { /// - /// Event which is fired when a game config option is changed. + /// Event which is fired when any game config option is changed. /// public event EventHandler Changed; + /// + /// Event which is fired when a system config option is changed. + /// + public event EventHandler SystemChanged; + + /// + /// Event which is fired when a UiConfig option is changed. + /// + public event EventHandler UiConfigChanged; + + /// + /// Event which is fired when a UiControl config option is changed. + /// + public event EventHandler UiControlChanged; + /// /// Gets the collection of config options that persist between characters. /// From 9181e1119564f21fbcbcf4265fbe1d74fe8f7470 Mon Sep 17 00:00:00 2001 From: MidoriKami <9083275+MidoriKami@users.noreply.github.com> Date: Thu, 21 Sep 2023 23:59:04 -0700 Subject: [PATCH 3/7] Remove Obsoletes --- Dalamud/Game/ClientState/Buddy/BuddyList.cs | 12 -- .../Game/ClientState/GamePad/GamepadState.cs | 48 -------- .../Game/ClientState/Objects/TargetManager.cs | 110 +----------------- .../Internal/DXGI/SwapChainSigResolver.cs | 34 ------ .../Interface/ImGuiFileDialog/FileDialog.cs | 10 -- Dalamud/Interface/Windowing/WindowSystem.cs | 8 -- 6 files changed, 5 insertions(+), 217 deletions(-) delete mode 100644 Dalamud/Game/Internal/DXGI/SwapChainSigResolver.cs diff --git a/Dalamud/Game/ClientState/Buddy/BuddyList.cs b/Dalamud/Game/ClientState/Buddy/BuddyList.cs index 489e75bc3..5d0098187 100644 --- a/Dalamud/Game/ClientState/Buddy/BuddyList.cs +++ b/Dalamud/Game/ClientState/Buddy/BuddyList.cs @@ -55,18 +55,6 @@ internal sealed partial class BuddyList : IServiceType, IBuddyList } } - /// - /// Gets a value indicating whether the local player's companion is present. - /// - [Obsolete("Use CompanionBuddy != null", false)] - public bool CompanionBuddyPresent => this.CompanionBuddy != null; - - /// - /// Gets a value indicating whether the local player's pet is present. - /// - [Obsolete("Use PetBuddy != null", false)] - public bool PetBuddyPresent => this.PetBuddy != null; - /// public BuddyMember? CompanionBuddy { diff --git a/Dalamud/Game/ClientState/GamePad/GamepadState.cs b/Dalamud/Game/ClientState/GamePad/GamepadState.cs index 8acb6ada5..b03db6df2 100644 --- a/Dalamud/Game/ClientState/GamePad/GamepadState.cs +++ b/Dalamud/Game/ClientState/GamePad/GamepadState.cs @@ -55,54 +55,6 @@ internal unsafe class GamepadState : IDisposable, IServiceType, IGamepadState public Vector2 RightStick => new(this.rightStickX, this.rightStickY); - /// - /// Gets the state of the left analogue stick in the left direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.LeftStick.X", false)] - public float LeftStickLeft => this.leftStickX < 0 ? -this.leftStickX / 100f : 0; - - /// - /// Gets the state of the left analogue stick in the right direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.LeftStick.X", false)] - public float LeftStickRight => this.leftStickX > 0 ? this.leftStickX / 100f : 0; - - /// - /// Gets the state of the left analogue stick in the up direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.LeftStick.Y", false)] - public float LeftStickUp => this.leftStickY > 0 ? this.leftStickY / 100f : 0; - - /// - /// Gets the state of the left analogue stick in the down direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.LeftStick.Y", false)] - public float LeftStickDown => this.leftStickY < 0 ? -this.leftStickY / 100f : 0; - - /// - /// Gets the state of the right analogue stick in the left direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.RightStick.X", false)] - public float RightStickLeft => this.rightStickX < 0 ? -this.rightStickX / 100f : 0; - - /// - /// Gets the state of the right analogue stick in the right direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.RightStick.X", false)] - public float RightStickRight => this.rightStickX > 0 ? this.rightStickX / 100f : 0; - - /// - /// Gets the state of the right analogue stick in the up direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.RightStick.Y", false)] - public float RightStickUp => this.rightStickY > 0 ? this.rightStickY / 100f : 0; - - /// - /// Gets the state of the right analogue stick in the down direction between 0 (not tilted) and 1 (max tilt). - /// - [Obsolete("Use IGamepadState.RightStick.Y", false)] - public float RightStickDown => this.rightStickY < 0 ? -this.rightStickY / 100f : 0; - /// /// Gets buttons pressed bitmask, set once when the button is pressed. See for the mapping. /// diff --git a/Dalamud/Game/ClientState/Objects/TargetManager.cs b/Dalamud/Game/ClientState/Objects/TargetManager.cs index a821ba806..fcb242c1e 100644 --- a/Dalamud/Game/ClientState/Objects/TargetManager.cs +++ b/Dalamud/Game/ClientState/Objects/TargetManager.cs @@ -39,35 +39,35 @@ internal sealed unsafe class TargetManager : IServiceType, ITargetManager public GameObject? Target { get => this.objectTable.CreateObjectReference((IntPtr)Struct->Target); - set => this.SetTarget(value); + set => Struct->Target = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)value?.Address; } /// public GameObject? MouseOverTarget { get => this.objectTable.CreateObjectReference((IntPtr)Struct->MouseOverTarget); - set => this.SetMouseOverTarget(value); + set => Struct->MouseOverTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)value?.Address; } /// public GameObject? FocusTarget { get => this.objectTable.CreateObjectReference((IntPtr)Struct->FocusTarget); - set => this.SetFocusTarget(value); + set => Struct->FocusTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)value?.Address; } /// public GameObject? PreviousTarget { get => this.objectTable.CreateObjectReference((IntPtr)Struct->PreviousTarget); - set => this.SetPreviousTarget(value); + set => Struct->PreviousTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)value?.Address; } /// public GameObject? SoftTarget { get => this.objectTable.CreateObjectReference((IntPtr)Struct->SoftTarget); - set => this.SetSoftTarget(value); + set => Struct->SoftTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)value?.Address; } /// @@ -85,104 +85,4 @@ internal sealed unsafe class TargetManager : IServiceType, ITargetManager } private FFXIVClientStructs.FFXIV.Client.Game.Control.TargetSystem* Struct => (FFXIVClientStructs.FFXIV.Client.Game.Control.TargetSystem*)this.Address; - - /// - /// Sets the current target. - /// - /// Actor to target. - [Obsolete("Use Target Property", false)] - public void SetTarget(GameObject? actor) => this.SetTarget(actor?.Address ?? IntPtr.Zero); - - /// - /// Sets the mouseover target. - /// - /// Actor to target. - [Obsolete("Use MouseOverTarget Property", false)] - public void SetMouseOverTarget(GameObject? actor) => this.SetMouseOverTarget(actor?.Address ?? IntPtr.Zero); - - /// - /// Sets the focus target. - /// - /// Actor to target. - [Obsolete("Use FocusTarget Property", false)] - public void SetFocusTarget(GameObject? actor) => this.SetFocusTarget(actor?.Address ?? IntPtr.Zero); - - /// - /// Sets the previous target. - /// - /// Actor to target. - [Obsolete("Use PreviousTarget Property", false)] - public void SetPreviousTarget(GameObject? actor) => this.SetTarget(actor?.Address ?? IntPtr.Zero); - - /// - /// Sets the soft target. - /// - /// Actor to target. - [Obsolete("Use SoftTarget Property", false)] - public void SetSoftTarget(GameObject? actor) => this.SetTarget(actor?.Address ?? IntPtr.Zero); - - /// - /// Sets the current target. - /// - /// Actor (address) to target. - [Obsolete("Use Target Property", false)] - public void SetTarget(IntPtr actorAddress) => Struct->Target = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)actorAddress; - - /// - /// Sets the mouseover target. - /// - /// Actor (address) to target. - [Obsolete("Use MouseOverTarget Property", false)] - public void SetMouseOverTarget(IntPtr actorAddress) => Struct->MouseOverTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)actorAddress; - - /// - /// Sets the focus target. - /// - /// Actor (address) to target. - [Obsolete("Use FocusTarget Property", false)] - public void SetFocusTarget(IntPtr actorAddress) => Struct->FocusTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)actorAddress; - - /// - /// Sets the previous target. - /// - /// Actor (address) to target. - [Obsolete("Use PreviousTarget Property", false)] - public void SetPreviousTarget(IntPtr actorAddress) => Struct->PreviousTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)actorAddress; - - /// - /// Sets the soft target. - /// - /// Actor (address) to target. - [Obsolete("Use SoftTarget Property", false)] - public void SetSoftTarget(IntPtr actorAddress) => Struct->SoftTarget = (FFXIVClientStructs.FFXIV.Client.Game.Object.GameObject*)actorAddress; - - /// - /// Clears the current target. - /// - [Obsolete("Use Target Property", false)] - public void ClearTarget() => this.SetTarget(IntPtr.Zero); - - /// - /// Clears the mouseover target. - /// - [Obsolete("Use MouseOverTarget Property", false)] - public void ClearMouseOverTarget() => this.SetMouseOverTarget(IntPtr.Zero); - - /// - /// Clears the focus target. - /// - [Obsolete("Use FocusTarget Property", false)] - public void ClearFocusTarget() => this.SetFocusTarget(IntPtr.Zero); - - /// - /// Clears the previous target. - /// - [Obsolete("Use PreviousTarget Property", false)] - public void ClearPreviousTarget() => this.SetPreviousTarget(IntPtr.Zero); - - /// - /// Clears the soft target. - /// - [Obsolete("Use SoftTarget Property", false)] - public void ClearSoftTarget() => this.SetSoftTarget(IntPtr.Zero); } diff --git a/Dalamud/Game/Internal/DXGI/SwapChainSigResolver.cs b/Dalamud/Game/Internal/DXGI/SwapChainSigResolver.cs deleted file mode 100644 index a2fc08646..000000000 --- a/Dalamud/Game/Internal/DXGI/SwapChainSigResolver.cs +++ /dev/null @@ -1,34 +0,0 @@ -using System.Diagnostics; -using System.Linq; - -using Serilog; - -namespace Dalamud.Game.Internal.DXGI; - -/// -/// The address resolver for native D3D11 methods to facilitate displaying the Dalamud UI. -/// -[Obsolete("This has been deprecated in favor of the VTable resolver.")] -internal sealed class SwapChainSigResolver : BaseAddressResolver, ISwapChainAddressResolver -{ - /// - public IntPtr Present { get; set; } - - /// - public IntPtr ResizeBuffers { get; set; } - - /// - protected override void Setup64Bit(SigScanner sig) - { - var module = Process.GetCurrentProcess().Modules.Cast().First(m => m.ModuleName == "dxgi.dll"); - - Log.Debug($"Found DXGI: 0x{module.BaseAddress.ToInt64():X}"); - - var scanner = new SigScanner(module); - - // This(code after the function head - offset of it) was picked to avoid running into issues with other hooks being installed into this function. - this.Present = scanner.ScanModule("41 8B F0 8B FA 89 54 24 ?? 48 8B D9 48 89 4D ?? C6 44 24 ?? 00") - 0x37; - - this.ResizeBuffers = scanner.ScanModule("48 8B C4 55 41 54 41 55 41 56 41 57 48 8D 68 B1 48 81 EC ?? ?? ?? ?? 48 C7 45 ?? ?? ?? ?? ?? 48 89 58 10 48 89 70 18 48 89 78 20 45 8B F9 45 8B E0 44 8B EA 48 8B F9 8B 45 7F 89 44 24 30 8B 75 77 89 74 24 28 44 89 4C 24"); - } -} diff --git a/Dalamud/Interface/ImGuiFileDialog/FileDialog.cs b/Dalamud/Interface/ImGuiFileDialog/FileDialog.cs index aec5e9af4..411f203cc 100644 --- a/Dalamud/Interface/ImGuiFileDialog/FileDialog.cs +++ b/Dalamud/Interface/ImGuiFileDialog/FileDialog.cs @@ -123,16 +123,6 @@ public partial class FileDialog return this.isOk; } - /// - /// Gets the result of the selection. - /// - /// The result of the selection (file or folder path). If multiple entries were selected, they are separated with commas. - [Obsolete("Use GetResults() instead.", true)] - public string GetResult() - { - return string.Join(',', this.GetResults()); - } - /// /// Gets the result of the selection. /// diff --git a/Dalamud/Interface/Windowing/WindowSystem.cs b/Dalamud/Interface/Windowing/WindowSystem.cs index 8e12d8f68..3e2a95a8d 100644 --- a/Dalamud/Interface/Windowing/WindowSystem.cs +++ b/Dalamud/Interface/Windowing/WindowSystem.cs @@ -94,14 +94,6 @@ public class WindowSystem /// public void RemoveAllWindows() => this.windows.Clear(); - /// - /// Get a window by name. - /// - /// The name of the . - /// The object with matching name or null. - [Obsolete("WindowSystem does not own your window - you should store a reference to it and use that instead.")] - public Window? GetWindow(string windowName) => this.windows.FirstOrDefault(w => w.WindowName == windowName); - /// /// Draw all registered windows using ImGui. /// From 64caf77a32d46482a3ad1d7e8f5530a7421edb23 Mon Sep 17 00:00:00 2001 From: Haselnussbomber Date: Fri, 22 Sep 2023 14:27:13 +0200 Subject: [PATCH 4/7] Update ClientStructs --- lib/FFXIVClientStructs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/FFXIVClientStructs b/lib/FFXIVClientStructs index fd5ba8a27..a1ddff097 160000 --- a/lib/FFXIVClientStructs +++ b/lib/FFXIVClientStructs @@ -1 +1 @@ -Subproject commit fd5ba8a27ec911a69eeb93ceb0202091279dfceb +Subproject commit a1ddff0974729a2e984d8cc1dc007eff19bd74ab From 4f8de2e20592f9d3b0c87b38bcfb5626e62475ec Mon Sep 17 00:00:00 2001 From: Kaz Wolfe Date: Fri, 22 Sep 2023 17:01:10 -0700 Subject: [PATCH 5/7] Obsolete (static) PluginLog for future removal - Mark PluginLog as obsoleted and pending removal, encouraging users to switch to IPluginLog. - Remove internal references to PluginLog. --- Dalamud.CorePlugin/PluginImpl.cs | 11 ++++++----- Dalamud/Logging/PluginLog.cs | 8 ++++++-- Dalamud/Utility/Signatures/SignatureHelper.cs | 9 +++------ 3 files changed, 15 insertions(+), 13 deletions(-) diff --git a/Dalamud.CorePlugin/PluginImpl.cs b/Dalamud.CorePlugin/PluginImpl.cs index 2f76a1087..e2b373d42 100644 --- a/Dalamud.CorePlugin/PluginImpl.cs +++ b/Dalamud.CorePlugin/PluginImpl.cs @@ -1,10 +1,8 @@ using System; using System.IO; - using Dalamud.Configuration.Internal; using Dalamud.Game.Command; using Dalamud.Interface.Windowing; -using Dalamud.Logging; using Dalamud.Plugin; using Dalamud.Plugin.Services; using Dalamud.Utility; @@ -52,6 +50,8 @@ namespace Dalamud.CorePlugin private readonly WindowSystem windowSystem = new("Dalamud.CorePlugin"); private Localization localization; + private IPluginLog pluginLog; + /// /// Initializes a new instance of the class. /// @@ -63,6 +63,7 @@ namespace Dalamud.CorePlugin { // this.InitLoc(); this.Interface = pluginInterface; + this.pluginLog = log; this.windowSystem.AddWindow(new PluginWindow()); @@ -76,7 +77,7 @@ namespace Dalamud.CorePlugin } catch (Exception ex) { - PluginLog.Error(ex, "kaboom"); + log.Error(ex, "kaboom"); } } @@ -130,13 +131,13 @@ namespace Dalamud.CorePlugin } catch (Exception ex) { - PluginLog.Error(ex, "Boom"); + this.pluginLog.Error(ex, "Boom"); } } private void OnCommand(string command, string args) { - PluginLog.Information("Command called!"); + this.pluginLog.Information("Command called!"); // this.window.IsOpen = true; } diff --git a/Dalamud/Logging/PluginLog.cs b/Dalamud/Logging/PluginLog.cs index 3ac98f15a..c3fe0c808 100644 --- a/Dalamud/Logging/PluginLog.cs +++ b/Dalamud/Logging/PluginLog.cs @@ -1,6 +1,5 @@ -using System; using System.Reflection; - +using Dalamud.Plugin.Services; using Serilog; using Serilog.Events; @@ -9,6 +8,11 @@ namespace Dalamud.Logging; /// /// Class offering various static methods to allow for logging in plugins. /// +/// +/// PluginLog has been obsoleted and replaced by the service. Developers are encouraged to +/// move over as soon as reasonably possible for performance reasons. +/// +[Obsolete("Static PluginLog will be removed in API 10. Developers should use IPluginLog.")] public static class PluginLog { #region "Log" prefixed Serilog style methods diff --git a/Dalamud/Utility/Signatures/SignatureHelper.cs b/Dalamud/Utility/Signatures/SignatureHelper.cs index bd99b8515..20b45e7fb 100755 --- a/Dalamud/Utility/Signatures/SignatureHelper.cs +++ b/Dalamud/Utility/Signatures/SignatureHelper.cs @@ -1,11 +1,8 @@ -using System; -using System.Linq; +using System.Linq; using System.Reflection; using System.Runtime.InteropServices; - using Dalamud.Game; using Dalamud.Hooking; -using Dalamud.Logging; using Dalamud.Utility.Signatures.Wrappers; using Serilog; @@ -23,7 +20,7 @@ public static class SignatureHelper /// . /// /// The object to initialise. - /// If warnings should be logged using . + /// If warnings should be logged. public static void Initialise(object self, bool log = true) { var scanner = Service.Get(); @@ -61,7 +58,7 @@ public static class SignatureHelper : message; if (fallible) { - PluginLog.Warning(errorMsg); + Log.Warning(errorMsg); } else { From 3618a510d0d56b70c0cd83a02297d321949d5e49 Mon Sep 17 00:00:00 2001 From: Kaz Wolfe Date: Fri, 22 Sep 2023 19:17:00 -0700 Subject: [PATCH 6/7] Make Custom Repo warning orange - Easier on the eyes, allegedly. --- .../Widgets/ThirdRepoSettingsEntry.cs | 21 ++++++++++--------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/Dalamud/Interface/Internal/Windows/Settings/Widgets/ThirdRepoSettingsEntry.cs b/Dalamud/Interface/Internal/Windows/Settings/Widgets/ThirdRepoSettingsEntry.cs index 617cbb045..afebeaedb 100644 --- a/Dalamud/Interface/Internal/Windows/Settings/Widgets/ThirdRepoSettingsEntry.cs +++ b/Dalamud/Interface/Internal/Windows/Settings/Widgets/ThirdRepoSettingsEntry.cs @@ -1,10 +1,8 @@ -using System; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Linq; using System.Numerics; using System.Threading.Tasks; - using CheapLoc; using Dalamud.Configuration; using Dalamud.Configuration.Internal; @@ -80,25 +78,28 @@ public class ThirdRepoSettingsEntry : SettingsEntry var disclaimerDismissed = config.ThirdRepoSpeedbumpDismissed.Value; ImGui.PushFont(InterfaceManager.IconFont); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, FontAwesomeIcon.ExclamationTriangle.ToIconString()); + ImGui.PushStyleColor(ImGuiCol.Text, ImGuiColors.DalamudOrange); + ImGuiHelpers.SafeTextWrapped(FontAwesomeIcon.ExclamationTriangle.ToIconString()); ImGui.PopFont(); ImGui.SameLine(); ImGuiHelpers.ScaledDummy(2); ImGui.SameLine(); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, Loc.Localize("DalamudSettingCustomRepoWarningReadThis", "READ THIS FIRST!")); + ImGuiHelpers.SafeTextWrapped(Loc.Localize("DalamudSettingCustomRepoWarningReadThis", "READ THIS FIRST!")); ImGui.SameLine(); ImGuiHelpers.ScaledDummy(2); ImGui.SameLine(); ImGui.PushFont(InterfaceManager.IconFont); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, FontAwesomeIcon.ExclamationTriangle.ToIconString()); + ImGuiHelpers.SafeTextWrapped(FontAwesomeIcon.ExclamationTriangle.ToIconString()); ImGui.PopFont(); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, Loc.Localize("DalamudSettingCustomRepoWarning", "We cannot take any responsibility for custom plugins and repositories.")); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, Loc.Localize("DalamudSettingCustomRepoWarning5", "If someone told you to copy/paste something here, it's very possible that you are being scammed or taken advantage of.")); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, Loc.Localize("DalamudSettingCustomRepoWarning2", "Plugins have full control over your PC, like any other program, and may cause harm or crashes.")); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, Loc.Localize("DalamudSettingCustomRepoWarning4", "They can delete your character, steal your FC or Discord account, and burn down your house.")); - ImGuiHelpers.SafeTextColoredWrapped(ImGuiColors.DalamudRed, Loc.Localize("DalamudSettingCustomRepoWarning3", "Please make absolutely sure that you only install plugins from developers you trust.")); + ImGuiHelpers.SafeTextWrapped(Loc.Localize("DalamudSettingCustomRepoWarning", "We cannot take any responsibility for custom plugins and repositories.")); + ImGuiHelpers.SafeTextWrapped(Loc.Localize("DalamudSettingCustomRepoWarning5", "If someone told you to copy/paste something here, it's very possible that you are being scammed or taken advantage of.")); + ImGuiHelpers.SafeTextWrapped(Loc.Localize("DalamudSettingCustomRepoWarning2", "Plugins have full control over your PC, like any other program, and may cause harm or crashes.")); + ImGuiHelpers.SafeTextWrapped(Loc.Localize("DalamudSettingCustomRepoWarning4", "They can delete your character, steal your FC or Discord account, and burn down your house.")); + ImGuiHelpers.SafeTextWrapped(Loc.Localize("DalamudSettingCustomRepoWarning3", "Please make absolutely sure that you only install plugins from developers you trust.")); + ImGui.PopStyleColor(); + if (!disclaimerDismissed) { const int speedbumpTime = 15; From d29422bc507582f1cc031880937f36b567ec8792 Mon Sep 17 00:00:00 2001 From: Kaz Wolfe Date: Fri, 22 Sep 2023 23:22:59 -0700 Subject: [PATCH 7/7] Add IPluginLog#Info - Shorthand for information log lines, because typing out `Information` is too much. --- Dalamud/Logging/ScopedPluginLogService.cs | 12 +++++++++--- Dalamud/Plugin/Services/IPluginLog.cs | 6 ++++++ 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/Dalamud/Logging/ScopedPluginLogService.cs b/Dalamud/Logging/ScopedPluginLogService.cs index 8c502fcf0..d6bb1f82d 100644 --- a/Dalamud/Logging/ScopedPluginLogService.cs +++ b/Dalamud/Logging/ScopedPluginLogService.cs @@ -1,6 +1,4 @@ -using System; - -using Dalamud.IoC; +using Dalamud.IoC; using Dalamud.IoC.Internal; using Dalamud.Plugin.Internal.Types; using Dalamud.Plugin.Services; @@ -90,6 +88,14 @@ public class ScopedPluginLogService : IServiceType, IPluginLog, IDisposable /// public void Information(Exception? exception, string messageTemplate, params object[] values) => this.Write(LogEventLevel.Information, exception, messageTemplate, values); + + /// + public void Info(string messageTemplate, params object[] values) => + this.Information(messageTemplate, values); + + /// + public void Info(Exception? exception, string messageTemplate, params object[] values) => + this.Information(exception, messageTemplate, values); /// public void Debug(string messageTemplate, params object[] values) => diff --git a/Dalamud/Plugin/Services/IPluginLog.cs b/Dalamud/Plugin/Services/IPluginLog.cs index 62f9e8728..d16e985af 100644 --- a/Dalamud/Plugin/Services/IPluginLog.cs +++ b/Dalamud/Plugin/Services/IPluginLog.cs @@ -76,6 +76,12 @@ public interface IPluginLog /// /// An (optional) exception that should be recorded alongside this event. void Information(Exception? exception, string messageTemplate, params object[] values); + + /// + void Info(string messageTemplate, params object[] values); + + /// + void Info(Exception? exception, string messageTemplate, params object[] values); /// /// Log a message to the Dalamud log for this plugin. This log level should be