rework service disposal
This commit is contained in:
		| @@ -220,6 +220,7 @@ public class FileCacheManager : IDisposable | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         WriteOutFullCsv(); | ||||
|     } | ||||
| } | ||||
|   | ||||
| @@ -6,29 +6,27 @@ using MareSynchronos.Utils; | ||||
|  | ||||
| namespace MareSynchronos.FileCache; | ||||
|  | ||||
| public class PeriodicFileScanner : IDisposable | ||||
| public class PeriodicFileScanner : MediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly IpcManager _ipcManager; | ||||
|     private readonly ConfigurationService _configService; | ||||
|     private readonly FileCacheManager _fileDbManager; | ||||
|     private readonly MareMediator _mediator; | ||||
|     private CancellationTokenSource? _scanCancellationTokenSource; | ||||
|     private Task? _fileScannerTask = null; | ||||
|     public ConcurrentDictionary<string, int> haltScanLocks = new(StringComparer.Ordinal); | ||||
|  | ||||
|     public PeriodicFileScanner(IpcManager ipcManager, ConfigurationService configService, FileCacheManager fileDbManager, MareMediator mediator) | ||||
|     public PeriodicFileScanner(IpcManager ipcManager, ConfigurationService configService, FileCacheManager fileDbManager, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         Logger.Verbose("Creating " + nameof(PeriodicFileScanner)); | ||||
|  | ||||
|         _ipcManager = ipcManager; | ||||
|         _configService = configService; | ||||
|         _fileDbManager = fileDbManager; | ||||
|         _mediator = mediator; | ||||
|  | ||||
|         _mediator.Subscribe<PenumbraInitializedMessage>(this, (_) => StartScan()); | ||||
|         _mediator.Subscribe<HaltScanMessage>(this, (msg) => HaltScan(((HaltScanMessage)msg).Source)); | ||||
|         _mediator.Subscribe<ResumeScanMessage>(this, (msg) => ResumeScan(((ResumeScanMessage)msg).Source)); | ||||
|         _mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => StartScan()); | ||||
|         Mediator.Subscribe<PenumbraInitializedMessage>(this, (_) => StartScan()); | ||||
|         Mediator.Subscribe<HaltScanMessage>(this, (msg) => HaltScan(((HaltScanMessage)msg).Source)); | ||||
|         Mediator.Subscribe<ResumeScanMessage>(this, (msg) => ResumeScan(((ResumeScanMessage)msg).Source)); | ||||
|         Mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => StartScan()); | ||||
|     } | ||||
|  | ||||
|     public void ResetLocks() | ||||
| @@ -76,9 +74,9 @@ public class PeriodicFileScanner : IDisposable | ||||
|     private TimeSpan _timeUntilNextScan = TimeSpan.Zero; | ||||
|     private int TimeBetweenScans => _configService.Current.TimeSpanBetweenScansInSeconds; | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(PeriodicFileScanner)); | ||||
|         base.Dispose(); | ||||
|  | ||||
|         _scanCancellationTokenSource?.Cancel(); | ||||
|     } | ||||
|   | ||||
| @@ -12,13 +12,12 @@ using MareSynchronos.WebAPI; | ||||
|  | ||||
| namespace MareSynchronos.Managers; | ||||
|  | ||||
| public class CachedPlayer : IDisposable | ||||
| public class CachedPlayer : MediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ApiController _apiController; | ||||
|     private readonly DalamudUtil _dalamudUtil; | ||||
|     private readonly IpcManager _ipcManager; | ||||
|     private readonly FileCacheManager _fileDbManager; | ||||
|     private readonly MareMediator _mediator; | ||||
|     private API.Data.CharacterData _cachedData = new(); | ||||
|     private PlayerRelatedObject? _currentCharacterEquipment; | ||||
|     private CancellationTokenSource? _downloadCancellationTokenSource = new(); | ||||
| @@ -30,14 +29,13 @@ public class CachedPlayer : IDisposable | ||||
|  | ||||
|     private Task? _penumbraRedrawEventTask; | ||||
|  | ||||
|     public CachedPlayer(OnlineUserIdentDto onlineUser, IpcManager ipcManager, ApiController apiController, DalamudUtil dalamudUtil, FileCacheManager fileDbManager, MareMediator mediator) | ||||
|     public CachedPlayer(OnlineUserIdentDto onlineUser, IpcManager ipcManager, ApiController apiController, DalamudUtil dalamudUtil, FileCacheManager fileDbManager, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         OnlineUser = onlineUser; | ||||
|         _ipcManager = ipcManager; | ||||
|         _apiController = apiController; | ||||
|         _dalamudUtil = dalamudUtil; | ||||
|         _fileDbManager = fileDbManager; | ||||
|         _mediator = mediator; | ||||
|     } | ||||
|  | ||||
|     public bool IsVisible | ||||
| @@ -173,7 +171,7 @@ public class CachedPlayer : IDisposable | ||||
|  | ||||
|         if (missingPluginsForData.Any()) | ||||
|         { | ||||
|             _mediator.Publish(new NotificationMessage("Missing plugins for " + PlayerName, | ||||
|             Mediator.Publish(new NotificationMessage("Missing plugins for " + PlayerName, | ||||
|                 $"Received data for {PlayerName} that contained information for plugins you have not installed. Install {string.Join(", ", missingPluginsForData)} to experience their character fully.", | ||||
|                 NotificationType.Warning, 10000)); | ||||
|         } | ||||
| @@ -202,9 +200,12 @@ public class CachedPlayer : IDisposable | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         if (string.IsNullOrEmpty(PlayerName)) return; | ||||
|  | ||||
|         base.Dispose(); | ||||
|  | ||||
|         Logger.Debug("Disposing " + PlayerName + " (" + OnlineUser + ")"); | ||||
|         try | ||||
|         { | ||||
| @@ -227,7 +228,7 @@ public class CachedPlayer : IDisposable | ||||
|         } | ||||
|         finally | ||||
|         { | ||||
|             _mediator.UnsubscribeAll(this); | ||||
|             Mediator.UnsubscribeAll(this); | ||||
|             _cachedData = new(); | ||||
|             var tempPlayerName = PlayerName; | ||||
|             PlayerName = string.Empty; | ||||
| @@ -244,7 +245,7 @@ public class CachedPlayer : IDisposable | ||||
|         PlayerCharacter = character; | ||||
|         Logger.Debug("Initializing Player " + this); | ||||
|  | ||||
|         _mediator.Subscribe<PenumbraRedrawMessage>(this, (msg) => IpcManagerOnPenumbraRedrawEvent(((PenumbraRedrawMessage)msg))); | ||||
|         Mediator.Subscribe<PenumbraRedrawMessage>(this, (msg) => IpcManagerOnPenumbraRedrawEvent(((PenumbraRedrawMessage)msg))); | ||||
|         _originalGlamourerData = _ipcManager.GlamourerGetCharacterCustomization(PlayerCharacter); | ||||
|         _currentCharacterEquipment = new PlayerRelatedObject(ObjectKind.Player, IntPtr.Zero, IntPtr.Zero, | ||||
|             () => _dalamudUtil.GetPlayerCharacterFromObjectTableByName(PlayerName)?.Address ?? IntPtr.Zero); | ||||
|   | ||||
| @@ -11,7 +11,7 @@ using MareSynchronos.Mediator; | ||||
|  | ||||
| namespace MareSynchronos.Managers; | ||||
|  | ||||
| public class IpcManager : IDisposable | ||||
| public class IpcManager : MediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ICallGateSubscriber<int> _glamourerApiVersion; | ||||
|     private readonly ICallGateSubscriber<string, GameObject?, object>? _glamourerApplyAll; | ||||
| @@ -57,18 +57,15 @@ public class IpcManager : IDisposable | ||||
|     private readonly ICallGateSubscriber<Character, string, object> _palettePlusPaletteChanged; | ||||
|  | ||||
|     private readonly DalamudUtil _dalamudUtil; | ||||
|     private readonly MareMediator _mediator; | ||||
|     private bool _inGposeQueueMode = false; | ||||
|     private ConcurrentQueue<Action> ActionQueue => _inGposeQueueMode ? _gposeActionQueue : _normalQueue; | ||||
|     private readonly ConcurrentQueue<Action> _normalQueue = new(); | ||||
|     private readonly ConcurrentQueue<Action> _gposeActionQueue = new(); | ||||
|  | ||||
|     public IpcManager(DalamudPluginInterface pi, DalamudUtil dalamudUtil, MareMediator mediator) | ||||
|     public IpcManager(DalamudPluginInterface pi, DalamudUtil dalamudUtil, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         Logger.Verbose("Creating " + nameof(IpcManager)); | ||||
|  | ||||
|         _mediator = mediator; | ||||
|  | ||||
|         _penumbraInit = Penumbra.Api.Ipc.Initialized.Subscriber(pi, () => PenumbraInit()); | ||||
|         _penumbraDispose = Penumbra.Api.Ipc.Disposed.Subscriber(pi, () => PenumbraDispose()); | ||||
|         _penumbraResolvePlayer = Penumbra.Api.Ipc.ResolvePlayerPath.Subscriber(pi); | ||||
| @@ -121,13 +118,13 @@ public class IpcManager : IDisposable | ||||
|  | ||||
|         if (Initialized) | ||||
|         { | ||||
|             _mediator.Publish(new PenumbraInitializedMessage()); | ||||
|             Mediator.Publish(new PenumbraInitializedMessage()); | ||||
|         } | ||||
|  | ||||
|         _dalamudUtil = dalamudUtil; | ||||
|         _mediator.Subscribe<FrameworkUpdateMessage>(this, (_) => HandleActionQueue()); | ||||
|         _mediator.Subscribe<GposeFrameworkUpdateMessage>(this, (_) => HandleGposeActionQueue()); | ||||
|         _mediator.Subscribe<ZoneSwitchEndMessage>(this, (_) => ClearActionQueue()); | ||||
|         Mediator.Subscribe<FrameworkUpdateMessage>(this, (_) => HandleActionQueue()); | ||||
|         Mediator.Subscribe<GposeFrameworkUpdateMessage>(this, (_) => HandleGposeActionQueue()); | ||||
|         Mediator.Subscribe<ZoneSwitchEndMessage>(this, (_) => ClearActionQueue()); | ||||
|     } | ||||
|  | ||||
|     private void HandleGposeActionQueue() | ||||
| @@ -147,7 +144,7 @@ public class IpcManager : IDisposable | ||||
|  | ||||
|     private void PenumbraModSettingChangedHandler() | ||||
|     { | ||||
|         _mediator.Publish(new PenumbraModSettingChangedMessage()); | ||||
|         Mediator.Publish(new PenumbraModSettingChangedMessage()); | ||||
|     } | ||||
|  | ||||
|     private void ClearActionQueue() | ||||
| @@ -162,7 +159,7 @@ public class IpcManager : IDisposable | ||||
|         { | ||||
|             if (ptr != IntPtr.Zero && string.Compare(arg1, arg2, ignoreCase: true, System.Globalization.CultureInfo.InvariantCulture) != 0) | ||||
|             { | ||||
|                 _mediator.Publish(new PenumbraResourceLoadMessage(ptr, arg1, arg2)); | ||||
|                 Mediator.Publish(new PenumbraResourceLoadMessage(ptr, arg1, arg2)); | ||||
|             } | ||||
|         }); | ||||
|     } | ||||
| @@ -238,9 +235,9 @@ public class IpcManager : IDisposable | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(IpcManager)); | ||||
|         base.Dispose(); | ||||
|  | ||||
|         int totalSleepTime = 0; | ||||
|         while (!ActionQueue.IsEmpty && totalSleepTime < 2000) | ||||
| @@ -500,31 +497,31 @@ public class IpcManager : IDisposable | ||||
|  | ||||
|     private void RedrawEvent(IntPtr objectAddress, int objectTableIndex) | ||||
|     { | ||||
|         _mediator.Publish(new PenumbraRedrawMessage(objectAddress, objectTableIndex)); | ||||
|         Mediator.Publish(new PenumbraRedrawMessage(objectAddress, objectTableIndex)); | ||||
|     } | ||||
|  | ||||
|     private void PenumbraInit() | ||||
|     { | ||||
|         _mediator.Publish(new PenumbraInitializedMessage()); | ||||
|         Mediator.Publish(new PenumbraInitializedMessage()); | ||||
|         _penumbraRedraw!.Invoke("self", RedrawType.Redraw); | ||||
|     } | ||||
|  | ||||
|     private void HeelsOffsetChange(float offset) | ||||
|     { | ||||
|         _mediator.Publish(new HeelsOffsetMessage(offset)); | ||||
|         Mediator.Publish(new HeelsOffsetMessage(offset)); | ||||
|     } | ||||
|  | ||||
|     private void OnCustomizePlusScaleChange(string? scale) | ||||
|     { | ||||
|         if (scale != null) scale = Convert.ToBase64String(Encoding.UTF8.GetBytes(scale)); | ||||
|         _mediator.Publish(new CustomizePlusMessage(scale)); | ||||
|         Mediator.Publish(new CustomizePlusMessage(scale)); | ||||
|     } | ||||
|  | ||||
|     private void OnPalettePlusPaletteChange(Character character, string palette) | ||||
|     { | ||||
|         if (character.Address == 0 || character.Address != _dalamudUtil.PlayerPointer) return; | ||||
|         if (palette != null) palette = Convert.ToBase64String(Encoding.UTF8.GetBytes(palette)); | ||||
|         _mediator.Publish(new PalettePlusMessage(palette)); | ||||
|         Mediator.Publish(new PalettePlusMessage(palette)); | ||||
|     } | ||||
|  | ||||
|     public void PalettePlusSetPalette(IntPtr character, string palette) | ||||
| @@ -575,7 +572,7 @@ public class IpcManager : IDisposable | ||||
|  | ||||
|     private void PenumbraDispose() | ||||
|     { | ||||
|         _mediator.Publish(new PenumbraDisposedMessage()); | ||||
|         Mediator.Publish(new PenumbraDisposedMessage()); | ||||
|         ActionQueue.Clear(); | ||||
|     } | ||||
| } | ||||
|   | ||||
| @@ -7,13 +7,13 @@ using MareSynchronos.Mediator; | ||||
| using MareSynchronos.Utils; | ||||
|  | ||||
| namespace MareSynchronos.Managers; | ||||
| public class NotificationService | ||||
| public class NotificationService : MediatorSubscriberBase | ||||
| { | ||||
|     private readonly UiBuilder _uiBuilder; | ||||
|     private readonly ChatGui _chatGui; | ||||
|     private readonly ConfigurationService _configurationService; | ||||
|  | ||||
|     public NotificationService(MareMediator mediator, UiBuilder uiBuilder, ChatGui chatGui, ConfigurationService configurationService) | ||||
|     public NotificationService(MareMediator mediator, UiBuilder uiBuilder, ChatGui chatGui, ConfigurationService configurationService) : base(mediator) | ||||
|     { | ||||
|         _uiBuilder = uiBuilder; | ||||
|         _chatGui = chatGui; | ||||
|   | ||||
| @@ -15,7 +15,8 @@ public class OnlinePlayerManager : MediatorSubscriberBase, IDisposable | ||||
|     private readonly FileCacheManager _fileDbManager; | ||||
|     private readonly PairManager _pairManager; | ||||
|  | ||||
|     public OnlinePlayerManager(ApiController apiController, DalamudUtil dalamudUtil, PlayerManager playerManager, FileCacheManager fileDbManager, PairManager pairManager, MareMediator mediator) : base(mediator) | ||||
|     public OnlinePlayerManager(ApiController apiController, DalamudUtil dalamudUtil, PlayerManager playerManager, | ||||
|         FileCacheManager fileDbManager, PairManager pairManager, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         Logger.Verbose("Creating " + nameof(OnlinePlayerManager)); | ||||
|  | ||||
| @@ -48,7 +49,6 @@ public class OnlinePlayerManager : MediatorSubscriberBase, IDisposable | ||||
|  | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(OnlinePlayerManager)); | ||||
|         base.Dispose(); | ||||
|     } | ||||
|  | ||||
|   | ||||
| @@ -17,25 +17,22 @@ using System.Collections.Concurrent; | ||||
|  | ||||
| namespace MareSynchronos.Managers; | ||||
|  | ||||
| public class PairManager : IDisposable | ||||
| public class PairManager : MediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ConcurrentDictionary<UserData, Pair> _allClientPairs = new(UserDataComparer.Instance); | ||||
|     private readonly ConcurrentDictionary<GroupData, GroupFullInfoDto> _allGroups = new(GroupDataComparer.Instance); | ||||
|     private readonly CachedPlayerFactory _cachedPlayerFactory; | ||||
|     private readonly PairFactory _pairFactory; | ||||
|     private readonly UiBuilder _uiBuilder; | ||||
|     private readonly ConfigurationService _configurationService; | ||||
|     private readonly MareMediator _mediator; | ||||
|  | ||||
|     public PairManager(CachedPlayerFactory cachedPlayerFactory, PairFactory pairFactory, UiBuilder uiBuilder, ConfigurationService configurationService, MareMediator mediator) | ||||
|     public PairManager(CachedPlayerFactory cachedPlayerFactory, PairFactory pairFactory, | ||||
|         ConfigurationService configurationService, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         _cachedPlayerFactory = cachedPlayerFactory; | ||||
|         _pairFactory = pairFactory; | ||||
|         _uiBuilder = uiBuilder; | ||||
|         _configurationService = configurationService; | ||||
|         _mediator = mediator; | ||||
|         _mediator.Subscribe<ZoneSwitchStartMessage>(this, (_) => DalamudUtilOnZoneSwitched()); | ||||
|         _mediator.Subscribe<DelayedFrameworkUpdateMessage>(this, (_) => DalamudUtilOnDelayedFrameworkUpdate()); | ||||
|         Mediator.Subscribe<ZoneSwitchStartMessage>(this, (_) => DalamudUtilOnZoneSwitched()); | ||||
|         Mediator.Subscribe<DelayedFrameworkUpdateMessage>(this, (_) => DalamudUtilOnDelayedFrameworkUpdate()); | ||||
|         _directPairsInternal = DirectPairsLazy(); | ||||
|         _groupPairsInternal = GroupPairsLazy(); | ||||
|     } | ||||
| @@ -137,8 +134,9 @@ public class PairManager : IDisposable | ||||
|         RecreateLazy(); | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         base.Dispose(); | ||||
|         DisposePairs(); | ||||
|     } | ||||
|  | ||||
| @@ -184,7 +182,7 @@ public class PairManager : IDisposable | ||||
|             var msg = !string.IsNullOrEmpty(note) | ||||
|                 ? $"{note} ({pair.UserData.AliasOrUID}) is now online" | ||||
|                 : $"{pair.UserData.AliasOrUID} is now online"; | ||||
|             _mediator.Publish(new NotificationMessage("User online", msg, NotificationType.Info, 5000)); | ||||
|             Mediator.Publish(new NotificationMessage("User online", msg, NotificationType.Info, 5000)); | ||||
|         } | ||||
|  | ||||
|         pair.CachedPlayer?.Dispose(); | ||||
|   | ||||
| @@ -10,7 +10,6 @@ using MareSynchronos.Mediator; | ||||
|  | ||||
| namespace MareSynchronos.Managers; | ||||
|  | ||||
|  | ||||
| public class PlayerManager : MediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ApiController _apiController; | ||||
| @@ -123,8 +122,6 @@ public class PlayerManager : MediatorSubscriberBase, IDisposable | ||||
|  | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(PlayerManager)); | ||||
|  | ||||
|         base.Dispose(); | ||||
|  | ||||
|         _playerChangedCts?.Cancel(); | ||||
|   | ||||
| @@ -75,6 +75,7 @@ public class ConfigurationService : IDisposable | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         Save(); | ||||
|         _periodicCheckCts.Cancel(); | ||||
|     } | ||||
|   | ||||
							
								
								
									
										156
									
								
								MareSynchronos/MarePlugin.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										156
									
								
								MareSynchronos/MarePlugin.cs
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,156 @@ | ||||
| using Dalamud.Game.Command; | ||||
| using Dalamud.Plugin; | ||||
| using Dalamud.Interface.ImGuiFileDialog; | ||||
| using MareSynchronos.Managers; | ||||
| using MareSynchronos.WebAPI; | ||||
| using Dalamud.Interface.Windowing; | ||||
| using MareSynchronos.UI; | ||||
| using MareSynchronos.Utils; | ||||
| using MareSynchronos.FileCache; | ||||
| using MareSynchronos.MareConfiguration; | ||||
| using MareSynchronos.Mediator; | ||||
| using Microsoft.Extensions.DependencyInjection; | ||||
|  | ||||
| namespace MareSynchronos; | ||||
|  | ||||
| public class MarePlugin : MediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ServiceProvider _serviceProvider; | ||||
|     private const string _commandName = "/mare"; | ||||
|     private IServiceScope? _runtimeServiceScope; | ||||
|  | ||||
|     public MarePlugin(ServiceProvider serviceProvider, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         _serviceProvider = serviceProvider; | ||||
|  | ||||
|         mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => Task.Run(WaitForPlayerAndLaunchCharacterManager)); | ||||
|         mediator.Subscribe<DalamudLoginMessage>(this, (_) => DalamudUtilOnLogIn()); | ||||
|         mediator.Subscribe<DalamudLogoutMessage>(this, (_) => DalamudUtilOnLogOut()); | ||||
|  | ||||
|         serviceProvider.GetRequiredService<SettingsUi>(); | ||||
|         serviceProvider.GetRequiredService<CompactUi>(); | ||||
|         serviceProvider.GetRequiredService<GposeUi>(); | ||||
|         serviceProvider.GetRequiredService<IntroUi>(); | ||||
|         serviceProvider.GetRequiredService<DownloadUi>(); | ||||
|         serviceProvider.GetRequiredService<NotificationService>(); | ||||
|     } | ||||
|  | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         base.Dispose(); | ||||
|  | ||||
|         _serviceProvider.GetRequiredService<CommandManager>().RemoveHandler(_commandName); | ||||
|  | ||||
|         _runtimeServiceScope?.Dispose(); | ||||
|         _serviceProvider.Dispose(); | ||||
|  | ||||
|         Logger.Debug("Shut down"); | ||||
|     } | ||||
|  | ||||
|     private void DalamudUtilOnLogIn() | ||||
|     { | ||||
|         Logger.Debug("Client login"); | ||||
|  | ||||
|         var pi = _serviceProvider.GetRequiredService<DalamudPluginInterface>(); | ||||
|         pi.UiBuilder.Draw += Draw; | ||||
|         pi.UiBuilder.OpenConfigUi += OpenUi; | ||||
|         _serviceProvider.GetRequiredService<CommandManager>().AddHandler(_commandName, new CommandInfo(OnCommand) | ||||
|         { | ||||
|             HelpMessage = "Opens the Mare Synchronos UI", | ||||
|         }); | ||||
|  | ||||
|         if (!_serviceProvider.GetRequiredService<ConfigurationService>().Current.HasValidSetup() | ||||
|             || !_serviceProvider.GetRequiredService<ServerConfigurationManager>().HasValidConfig()) | ||||
|         { | ||||
|             _serviceProvider.GetRequiredService<MareMediator>().Publish(new SwitchToIntroUiMessage()); | ||||
|             return; | ||||
|         } | ||||
|  | ||||
|         _serviceProvider.GetRequiredService<PeriodicFileScanner>().StartScan(); | ||||
|         Task.Run(WaitForPlayerAndLaunchCharacterManager); | ||||
|     } | ||||
|  | ||||
|     private void DalamudUtilOnLogOut() | ||||
|     { | ||||
|         Logger.Debug("Client logout"); | ||||
|         _runtimeServiceScope?.Dispose(); | ||||
|         var pi = _serviceProvider.GetRequiredService<DalamudPluginInterface>(); | ||||
|         pi.UiBuilder.Draw -= Draw; | ||||
|         pi.UiBuilder.OpenConfigUi -= OpenUi; | ||||
|         _serviceProvider.GetRequiredService<CommandManager>().RemoveHandler(_commandName); | ||||
|     } | ||||
|  | ||||
|     private async Task WaitForPlayerAndLaunchCharacterManager() | ||||
|     { | ||||
|         var dalamudUtil = _serviceProvider.GetRequiredService<DalamudUtil>(); | ||||
|         while (!dalamudUtil.IsPlayerPresent) | ||||
|         { | ||||
|             await Task.Delay(100).ConfigureAwait(false); | ||||
|         } | ||||
|  | ||||
|         try | ||||
|         { | ||||
|             Logger.Debug("Launching Managers"); | ||||
|  | ||||
|             _runtimeServiceScope?.Dispose(); | ||||
|             _runtimeServiceScope = _serviceProvider.CreateScope(); | ||||
|             _runtimeServiceScope.ServiceProvider.GetRequiredService<TransientResourceManager>(); | ||||
|             _runtimeServiceScope.ServiceProvider.GetRequiredService<PlayerManager>(); | ||||
|             _runtimeServiceScope.ServiceProvider.GetRequiredService<OnlinePlayerManager>(); | ||||
|         } | ||||
|         catch (Exception ex) | ||||
|         { | ||||
|             Logger.Warn(ex.Message); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     private void Draw() | ||||
|     { | ||||
|         _serviceProvider.GetRequiredService<WindowSystem>().Draw(); | ||||
|         _serviceProvider.GetRequiredService<FileDialogManager>().Draw(); | ||||
|     } | ||||
|  | ||||
|     private void OnCommand(string command, string args) | ||||
|     { | ||||
|         var splitArgs = args.ToLowerInvariant().Trim().Split(" ", StringSplitOptions.RemoveEmptyEntries); | ||||
|  | ||||
|         if (splitArgs == null || splitArgs.Length == 0) | ||||
|         { | ||||
|             // Interpret this as toggling the UI | ||||
|             OpenUi(); | ||||
|             return; | ||||
|         } | ||||
|  | ||||
|         if (string.Equals(splitArgs[0], "toggle", StringComparison.OrdinalIgnoreCase)) | ||||
|         { | ||||
|             var serverConfigurationManager = _serviceProvider.GetRequiredService<ServerConfigurationManager>(); | ||||
|             if (serverConfigurationManager.CurrentServer == null) return; | ||||
|             var fullPause = splitArgs.Length > 1 ? splitArgs[1] switch | ||||
|             { | ||||
|                 "on" => false, | ||||
|                 "off" => true, | ||||
|                 _ => !serverConfigurationManager.CurrentServer.FullPause, | ||||
|             } : !serverConfigurationManager.CurrentServer.FullPause; | ||||
|  | ||||
|             if (fullPause != serverConfigurationManager.CurrentServer.FullPause) | ||||
|             { | ||||
|                 serverConfigurationManager.CurrentServer.FullPause = fullPause; | ||||
|                 serverConfigurationManager.Save(); | ||||
|                 _ = _serviceProvider.GetRequiredService<ApiController>().CreateConnections(); | ||||
|             } | ||||
|         } | ||||
|         else if (string.Equals(splitArgs[0], "gpose", StringComparison.OrdinalIgnoreCase)) | ||||
|         { | ||||
|             _serviceProvider.GetRequiredService<GposeUi>().Toggle(); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     private void OpenUi() | ||||
|     { | ||||
|  | ||||
|         if (_serviceProvider.GetRequiredService<ConfigurationService>().Current.HasValidSetup()) | ||||
|             _serviceProvider.GetRequiredService<CompactUi>().Toggle(); | ||||
|         else | ||||
|             _serviceProvider.GetRequiredService<IntroUi>().Toggle(); | ||||
|     } | ||||
| } | ||||
| @@ -4,11 +4,11 @@ namespace MareSynchronos.Mediator; | ||||
|  | ||||
| public class MareMediator : IDisposable | ||||
| { | ||||
|     private record MediatorSubscriber(object Subscriber, Action<IMessage> Action); | ||||
|     private record MediatorSubscriber(IMediatorSubscriber Subscriber, Action<IMessage> Action); | ||||
|  | ||||
|     private readonly Dictionary<Type, HashSet<MediatorSubscriber>> _subscriberDict = new(); | ||||
|  | ||||
|     public void Subscribe<T>(object subscriber, Action<IMessage> action) where T : IMessage | ||||
|     public void Subscribe<T>(IMediatorSubscriber subscriber, Action<IMessage> action) where T : IMessage | ||||
|     { | ||||
|         _subscriberDict.TryAdd(typeof(T), new HashSet<MediatorSubscriber>()); | ||||
|  | ||||
| @@ -18,7 +18,7 @@ public class MareMediator : IDisposable | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     public void Unsubscribe<T>(object subscriber) where T : IMessage | ||||
|     public void Unsubscribe<T>(IMediatorSubscriber subscriber) where T : IMessage | ||||
|     { | ||||
|         if (_subscriberDict.TryGetValue(typeof(T), out var subscribers)) | ||||
|         { | ||||
| @@ -30,7 +30,7 @@ public class MareMediator : IDisposable | ||||
|     { | ||||
|         if (_subscriberDict.TryGetValue(message.GetType(), out var subscribers)) | ||||
|         { | ||||
|             foreach (var subscriber in subscribers) | ||||
|             foreach (var subscriber in subscribers.ToList()) | ||||
|             { | ||||
|                 try | ||||
|                 { | ||||
| @@ -44,9 +44,9 @@ public class MareMediator : IDisposable | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     internal void UnsubscribeAll(object subscriber) | ||||
|     internal void UnsubscribeAll(IMediatorSubscriber subscriber) | ||||
|     { | ||||
|         foreach (var kvp in _subscriberDict) | ||||
|         foreach (var kvp in _subscriberDict.ToList()) | ||||
|         { | ||||
|             kvp.Value.RemoveWhere(p => p.Subscriber == subscriber); | ||||
|         } | ||||
| @@ -54,6 +54,7 @@ public class MareMediator : IDisposable | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         _subscriberDict.Clear(); | ||||
|     } | ||||
| } | ||||
| @@ -1,16 +1,39 @@ | ||||
| namespace MareSynchronos.Mediator; | ||||
| using Dalamud.Interface.Windowing; | ||||
| using MareSynchronos.Utils; | ||||
|  | ||||
| public abstract class MediatorSubscriberBase : IDisposable | ||||
| namespace MareSynchronos.Mediator; | ||||
|  | ||||
| public abstract class MediatorSubscriberBase : IMediatorSubscriber | ||||
| { | ||||
|     public MareMediator Mediator { get; } | ||||
|     protected MediatorSubscriberBase(MareMediator mediator) | ||||
|     { | ||||
|         Mediator = mediator; | ||||
|     } | ||||
|  | ||||
|     protected readonly MareMediator Mediator; | ||||
|  | ||||
|     public virtual void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         Mediator.UnsubscribeAll(this); | ||||
|     } | ||||
| } | ||||
|  | ||||
| public abstract class WindowMediatorSubscriberBase : Window, IMediatorSubscriber | ||||
| { | ||||
|     public MareMediator Mediator { get; } | ||||
|     protected WindowMediatorSubscriberBase(MareMediator mediator, string name) : base(name) | ||||
|     { | ||||
|         Mediator = mediator; | ||||
|     } | ||||
|  | ||||
|     public virtual void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         Mediator.UnsubscribeAll(this); | ||||
|     } | ||||
| } | ||||
|  | ||||
| public interface IMediatorSubscriber : IDisposable | ||||
| { | ||||
|     MareMediator Mediator { get; } | ||||
| } | ||||
|   | ||||
| @@ -23,9 +23,8 @@ namespace MareSynchronos; | ||||
|  | ||||
| public sealed class Plugin : IDalamudPlugin | ||||
| { | ||||
|     private const string _commandName = "/mare"; | ||||
|     private IServiceScope? _runtimeServiceScope; | ||||
|     private readonly ServiceProvider _serviceProvider; | ||||
|     private readonly MarePlugin plugin; | ||||
|     public string Name => "Mare Synchronos"; | ||||
|  | ||||
|     public Plugin(DalamudPluginInterface pluginInterface, CommandManager commandManager, DataManager gameData, | ||||
|         Framework framework, ObjectTable objectTable, ClientState clientState, Condition condition, ChatGui chatGui) | ||||
| @@ -76,142 +75,18 @@ public sealed class Plugin : IDalamudPlugin | ||||
|         collection.AddScoped<PlayerManager>(); | ||||
|         collection.AddScoped<OnlinePlayerManager>(); | ||||
|  | ||||
|         _serviceProvider = collection.BuildServiceProvider(new ServiceProviderOptions() { ValidateOnBuild = true, ValidateScopes = true }); | ||||
|         var serviceProvider = collection.BuildServiceProvider(new ServiceProviderOptions() { ValidateOnBuild = true, ValidateScopes = true }); | ||||
|  | ||||
|         _serviceProvider.GetRequiredService<Dalamud.Localization>().SetupWithLangCode("en"); | ||||
|         _serviceProvider.GetRequiredService<DalamudPluginInterface>().UiBuilder.DisableGposeUiHide = true; | ||||
|         serviceProvider.GetRequiredService<Dalamud.Localization>().SetupWithLangCode("en"); | ||||
|         serviceProvider.GetRequiredService<DalamudPluginInterface>().UiBuilder.DisableGposeUiHide = true; | ||||
|  | ||||
|         var mediator = _serviceProvider.GetRequiredService<MareMediator>(); | ||||
|         mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => Task.Run(WaitForPlayerAndLaunchCharacterManager)); | ||||
|         mediator.Subscribe<DalamudLoginMessage>(this, (_) => DalamudUtilOnLogIn()); | ||||
|         mediator.Subscribe<DalamudLogoutMessage>(this, (_) => DalamudUtilOnLogOut()); | ||||
|  | ||||
|         _serviceProvider.GetRequiredService<SettingsUi>(); | ||||
|         _serviceProvider.GetRequiredService<CompactUi>(); | ||||
|         _serviceProvider.GetRequiredService<GposeUi>(); | ||||
|         _serviceProvider.GetRequiredService<IntroUi>(); | ||||
|         _serviceProvider.GetRequiredService<DownloadUi>(); | ||||
|         _serviceProvider.GetRequiredService<NotificationService>(); | ||||
|         var mediator = serviceProvider.GetRequiredService<MareMediator>(); | ||||
|         plugin = new MarePlugin(serviceProvider, mediator); | ||||
|     } | ||||
|  | ||||
|     public string Name => "Mare Synchronos"; | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + Name); | ||||
|  | ||||
|         _serviceProvider.GetRequiredService<CommandManager>().RemoveHandler(_commandName); | ||||
|  | ||||
|         _runtimeServiceScope?.Dispose(); | ||||
|         _serviceProvider.Dispose(); | ||||
|  | ||||
|         Logger.Debug("Shut down"); | ||||
|     } | ||||
|  | ||||
|     private void DalamudUtilOnLogIn() | ||||
|     { | ||||
|         Logger.Debug("Client login"); | ||||
|  | ||||
|         var pi = _serviceProvider.GetRequiredService<DalamudPluginInterface>(); | ||||
|         pi.UiBuilder.Draw += Draw; | ||||
|         pi.UiBuilder.OpenConfigUi += OpenUi; | ||||
|         _serviceProvider.GetRequiredService<CommandManager>().AddHandler(_commandName, new CommandInfo(OnCommand) | ||||
|         { | ||||
|             HelpMessage = "Opens the Mare Synchronos UI", | ||||
|         }); | ||||
|  | ||||
|         if (!_serviceProvider.GetRequiredService<ConfigurationService>().Current.HasValidSetup() | ||||
|             || !_serviceProvider.GetRequiredService<ServerConfigurationManager>().HasValidConfig()) | ||||
|         { | ||||
|             _serviceProvider.GetRequiredService<MareMediator>().Publish(new SwitchToIntroUiMessage()); | ||||
|             return; | ||||
|         } | ||||
|  | ||||
|         _serviceProvider.GetRequiredService<PeriodicFileScanner>().StartScan(); | ||||
|         Task.Run(WaitForPlayerAndLaunchCharacterManager); | ||||
|     } | ||||
|  | ||||
|     private void DalamudUtilOnLogOut() | ||||
|     { | ||||
|         Logger.Debug("Client logout"); | ||||
|         _runtimeServiceScope?.Dispose(); | ||||
|         var pi = _serviceProvider.GetRequiredService<DalamudPluginInterface>(); | ||||
|         pi.UiBuilder.Draw -= Draw; | ||||
|         pi.UiBuilder.OpenConfigUi -= OpenUi; | ||||
|         _serviceProvider.GetRequiredService<CommandManager>().RemoveHandler(_commandName); | ||||
|     } | ||||
|  | ||||
|     private async Task WaitForPlayerAndLaunchCharacterManager() | ||||
|     { | ||||
|         var dalamudUtil = _serviceProvider.GetRequiredService<DalamudUtil>(); | ||||
|         while (!dalamudUtil.IsPlayerPresent) | ||||
|         { | ||||
|             await Task.Delay(100).ConfigureAwait(false); | ||||
|         } | ||||
|  | ||||
|         try | ||||
|         { | ||||
|             Logger.Debug("Launching Managers"); | ||||
|  | ||||
|             _runtimeServiceScope?.Dispose(); | ||||
|             _runtimeServiceScope = _serviceProvider.CreateScope(); | ||||
|             _runtimeServiceScope.ServiceProvider.GetRequiredService<TransientResourceManager>(); | ||||
|             _runtimeServiceScope.ServiceProvider.GetRequiredService<PlayerManager>(); | ||||
|             _runtimeServiceScope.ServiceProvider.GetRequiredService<OnlinePlayerManager>(); | ||||
|         } | ||||
|         catch (Exception ex) | ||||
|         { | ||||
|             Logger.Warn(ex.Message); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     private void Draw() | ||||
|     { | ||||
|         _serviceProvider.GetRequiredService<WindowSystem>().Draw(); | ||||
|         _serviceProvider.GetRequiredService<FileDialogManager>().Draw(); | ||||
|     } | ||||
|  | ||||
|     private void OnCommand(string command, string args) | ||||
|     { | ||||
|         var splitArgs = args.ToLowerInvariant().Trim().Split(" ", StringSplitOptions.RemoveEmptyEntries); | ||||
|  | ||||
|         if (splitArgs == null || splitArgs.Length == 0) | ||||
|         { | ||||
|             // Interpret this as toggling the UI | ||||
|             OpenUi(); | ||||
|             return; | ||||
|         } | ||||
|  | ||||
|         if (string.Equals(splitArgs[0], "toggle", StringComparison.OrdinalIgnoreCase)) | ||||
|         { | ||||
|             var serverConfigurationManager = _serviceProvider.GetRequiredService<ServerConfigurationManager>(); | ||||
|             if (serverConfigurationManager.CurrentServer == null) return; | ||||
|             var fullPause = splitArgs.Length > 1 ? splitArgs[1] switch | ||||
|             { | ||||
|                 "on" => false, | ||||
|                 "off" => true, | ||||
|                 _ => !serverConfigurationManager.CurrentServer.FullPause, | ||||
|             } : !serverConfigurationManager.CurrentServer.FullPause; | ||||
|  | ||||
|             if (fullPause != serverConfigurationManager.CurrentServer.FullPause) | ||||
|             { | ||||
|                 serverConfigurationManager.CurrentServer.FullPause = fullPause; | ||||
|                 serverConfigurationManager.Save(); | ||||
|                 _ = _serviceProvider.GetRequiredService<ApiController>().CreateConnections(); | ||||
|             } | ||||
|         } | ||||
|         else if (string.Equals(splitArgs[0], "gpose", StringComparison.OrdinalIgnoreCase)) | ||||
|         { | ||||
|             _serviceProvider.GetRequiredService<GposeUi>().Toggle(); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     private void OpenUi() | ||||
|     { | ||||
|          | ||||
|         if (_serviceProvider.GetRequiredService<ConfigurationService>().Current.HasValidSetup()) | ||||
|             _serviceProvider.GetRequiredService<CompactUi>().Toggle(); | ||||
|         else | ||||
|             _serviceProvider.GetRequiredService<IntroUi>().Toggle(); | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         plugin.Dispose(); | ||||
|     } | ||||
| } | ||||
|   | ||||
| @@ -21,12 +21,11 @@ using MareSynchronos.WebAPI; | ||||
|  | ||||
| namespace MareSynchronos.UI; | ||||
|  | ||||
| public class CompactUi : Window, IDisposable | ||||
| public class CompactUi : WindowMediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ApiController _apiController; | ||||
|     private readonly PairManager _pairManager; | ||||
|     private readonly ServerConfigurationManager _serverManager; | ||||
|     private readonly MareMediator _mediator; | ||||
|     private readonly ConfigurationService _configService; | ||||
|     private readonly TagHandler _tagHandler; | ||||
|     public readonly Dictionary<string, bool> ShowUidForEntry = new(StringComparer.Ordinal); | ||||
| @@ -58,7 +57,7 @@ public class CompactUi : Window, IDisposable | ||||
|  | ||||
|     public CompactUi(WindowSystem windowSystem, | ||||
|         UiShared uiShared, ConfigurationService configService, ApiController apiController, PairManager pairManager, | ||||
|         ServerConfigurationManager serverManager, MareMediator mediator) : base("###MareSynchronosMainUI") | ||||
|         ServerConfigurationManager serverManager, MareMediator mediator) : base(mediator, "###MareSynchronosMainUI") | ||||
|     { | ||||
|  | ||||
| #if DEBUG | ||||
| @@ -89,7 +88,6 @@ public class CompactUi : Window, IDisposable | ||||
|         _apiController = apiController; | ||||
|         _pairManager = pairManager; | ||||
|         _serverManager = serverManager; | ||||
|         _mediator = mediator; | ||||
|         _tagHandler = new(_serverManager); | ||||
|  | ||||
|         _groupPanel = new(this, uiShared, _pairManager, _serverManager, _configService); | ||||
| @@ -97,10 +95,10 @@ public class CompactUi : Window, IDisposable | ||||
|         _selectPairsForGroupUi = new(_tagHandler); | ||||
|         _pairGroupsUi = new(_tagHandler, DrawPairedClient, apiController, _selectPairsForGroupUi); | ||||
|  | ||||
|         _mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => IsOpen = true); | ||||
|         _mediator.Subscribe<SwitchToIntroUiMessage>(this, (_) => IsOpen = false); | ||||
|         _mediator.Subscribe<GposeStartMessage>(this, (_) => UiShared_GposeStart()); | ||||
|         _mediator.Subscribe<GposeEndMessage>(this, (_) => UiShared_GposeEnd()); | ||||
|         Mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => IsOpen = true); | ||||
|         Mediator.Subscribe<SwitchToIntroUiMessage>(this, (_) => IsOpen = false); | ||||
|         Mediator.Subscribe<GposeStartMessage>(this, (_) => UiShared_GposeStart()); | ||||
|         Mediator.Subscribe<GposeEndMessage>(this, (_) => UiShared_GposeEnd()); | ||||
|  | ||||
|         SizeConstraints = new WindowSizeConstraints() | ||||
|         { | ||||
| @@ -122,9 +120,9 @@ public class CompactUi : Window, IDisposable | ||||
|         IsOpen = false; | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(CompactUi)); | ||||
|         base.Dispose(); | ||||
|         _windowSystem.RemoveWindow(this); | ||||
|     } | ||||
|  | ||||
| @@ -701,7 +699,7 @@ public class CompactUi : Window, IDisposable | ||||
|         ImGui.SetCursorPosY(originalPos.Y + uidTextSize.Y / 2 - buttonSize.Y / 2); | ||||
|         if (ImGuiComponents.IconButton(FontAwesomeIcon.Cog)) | ||||
|         { | ||||
|             _mediator.Publish(new OpenSettingsUiMessage()); | ||||
|             Mediator.Publish(new OpenSettingsUiMessage()); | ||||
|         } | ||||
|         UiShared.AttachToolTip("Open the Mare Synchronos Settings"); | ||||
|  | ||||
|   | ||||
| @@ -17,7 +17,7 @@ public class DownloadUi : Window, IDisposable | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(DownloadUi)); | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         _windowSystem.RemoveWindow(this); | ||||
|     } | ||||
|  | ||||
|   | ||||
| @@ -10,27 +10,25 @@ using MareSynchronos.Utils; | ||||
|  | ||||
| namespace MareSynchronos.UI; | ||||
|  | ||||
| public class GposeUi : Window, IDisposable | ||||
| public class GposeUi : WindowMediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly WindowSystem _windowSystem; | ||||
|     private readonly MareCharaFileManager _mareCharaFileManager; | ||||
|     private readonly DalamudUtil _dalamudUtil; | ||||
|     private readonly FileDialogManager _fileDialogManager; | ||||
|     private readonly ConfigurationService _configService; | ||||
|     private readonly MareMediator _mediator; | ||||
|  | ||||
|     public GposeUi(WindowSystem windowSystem, MareCharaFileManager mareCharaFileManager, | ||||
|         DalamudUtil dalamudUtil, FileDialogManager fileDialogManager, ConfigurationService configService, | ||||
|         MareMediator mediator) : base("Mare Synchronos Gpose Import UI###MareSynchronosGposeUI") | ||||
|         MareMediator mediator) : base(mediator, "Mare Synchronos Gpose Import UI###MareSynchronosGposeUI") | ||||
|     { | ||||
|         _windowSystem = windowSystem; | ||||
|         _mareCharaFileManager = mareCharaFileManager; | ||||
|         _dalamudUtil = dalamudUtil; | ||||
|         _fileDialogManager = fileDialogManager; | ||||
|         _configService = configService; | ||||
|         _mediator = mediator; | ||||
|         _mediator.Subscribe<GposeStartMessage>(this, (_) => StartGpose()); | ||||
|         _mediator.Subscribe<GposeEndMessage>(this, (_) => EndGpose()); | ||||
|         Mediator.Subscribe<GposeStartMessage>(this, (_) => StartGpose()); | ||||
|         Mediator.Subscribe<GposeEndMessage>(this, (_) => EndGpose()); | ||||
|         IsOpen = _dalamudUtil.IsInGpose; | ||||
|         Flags = ImGuiWindowFlags.AlwaysAutoResize; | ||||
|         _windowSystem.AddWindow(this); | ||||
| @@ -47,8 +45,9 @@ public class GposeUi : Window, IDisposable | ||||
|         IsOpen = _configService.Current.OpenGposeImportOnGposeStart; | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         base.Dispose(); | ||||
|         _windowSystem.RemoveWindow(this); | ||||
|     } | ||||
|  | ||||
|   | ||||
| @@ -13,13 +13,12 @@ using MareSynchronos.Mediator; | ||||
|  | ||||
| namespace MareSynchronos.UI; | ||||
|  | ||||
| internal class IntroUi : Window, IDisposable | ||||
| internal class IntroUi : WindowMediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly UiShared _uiShared; | ||||
|     private readonly ConfigurationService _configService; | ||||
|     private readonly PeriodicFileScanner _fileCacheManager; | ||||
|     private readonly ServerConfigurationManager _serverConfigurationManager; | ||||
|     private readonly MareMediator _mareMediator; | ||||
|     private readonly WindowSystem _windowSystem; | ||||
|     private bool _readFirstPage; | ||||
|  | ||||
| @@ -31,15 +30,14 @@ internal class IntroUi : Window, IDisposable | ||||
|     private readonly Dictionary<string, string> _languages = new(StringComparer.Ordinal) { { "English", "en" }, { "Deutsch", "de" }, { "Français", "fr" } }; | ||||
|     private int _currentLanguage; | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(IntroUi)); | ||||
|  | ||||
|         base.Dispose(); | ||||
|         _windowSystem.RemoveWindow(this); | ||||
|     } | ||||
|  | ||||
|     public IntroUi(WindowSystem windowSystem, UiShared uiShared, ConfigurationService configService, | ||||
|         PeriodicFileScanner fileCacheManager, ServerConfigurationManager serverConfigurationManager, MareMediator mareMediator) : base("Mare Synchronos Setup") | ||||
|         PeriodicFileScanner fileCacheManager, ServerConfigurationManager serverConfigurationManager, MareMediator mareMediator) : base(mareMediator, "Mare Synchronos Setup") | ||||
|     { | ||||
|         Logger.Verbose("Creating " + nameof(IntroUi)); | ||||
|  | ||||
| @@ -47,7 +45,6 @@ internal class IntroUi : Window, IDisposable | ||||
|         _configService = configService; | ||||
|         _fileCacheManager = fileCacheManager; | ||||
|         _serverConfigurationManager = serverConfigurationManager; | ||||
|         _mareMediator = mareMediator; | ||||
|         _windowSystem = windowSystem; | ||||
|         IsOpen = false; | ||||
|  | ||||
| @@ -59,8 +56,8 @@ internal class IntroUi : Window, IDisposable | ||||
|  | ||||
|         GetToSLocalization(); | ||||
|  | ||||
|         _mareMediator.Subscribe<SwitchToMainUiMessage>(this, (_) => IsOpen = false); | ||||
|         _mareMediator.Subscribe<SwitchToIntroUiMessage>(this, (_) => IsOpen = true); | ||||
|         Mediator.Subscribe<SwitchToMainUiMessage>(this, (_) => IsOpen = false); | ||||
|         Mediator.Subscribe<SwitchToIntroUiMessage>(this, (_) => IsOpen = true); | ||||
|  | ||||
|         _windowSystem.AddWindow(this); | ||||
|     } | ||||
| @@ -242,7 +239,7 @@ internal class IntroUi : Window, IDisposable | ||||
|         } | ||||
|         else | ||||
|         { | ||||
|             _mareMediator.Publish(new SwitchToMainUiMessage()); | ||||
|             Mediator.Publish(new SwitchToMainUiMessage()); | ||||
|             IsOpen = false; | ||||
|         } | ||||
|     } | ||||
|   | ||||
| @@ -14,12 +14,10 @@ using MareSynchronos.Managers; | ||||
| using MareSynchronos.API.Data.Comparer; | ||||
| using MareSynchronos.MareConfiguration; | ||||
| using MareSynchronos.Mediator; | ||||
| using Lumina.Excel.GeneratedSheets; | ||||
| using static System.Runtime.InteropServices.JavaScript.JSType; | ||||
|  | ||||
| namespace MareSynchronos.UI; | ||||
|  | ||||
| public class SettingsUi : Window, IDisposable | ||||
| public class SettingsUi : WindowMediatorSubscriberBase, IDisposable | ||||
| { | ||||
|     private readonly ConfigurationService _configService; | ||||
|     private readonly WindowSystem _windowSystem; | ||||
| @@ -27,7 +25,6 @@ public class SettingsUi : Window, IDisposable | ||||
|     private readonly MareCharaFileManager _mareCharaFileManager; | ||||
|     private readonly PairManager _pairManager; | ||||
|     private readonly ServerConfigurationManager _serverConfigurationManager; | ||||
|     private readonly MareMediator _mediator; | ||||
|     private readonly UiShared _uiShared; | ||||
|     public CharacterData? LastCreatedCharacterData { private get; set; } | ||||
|  | ||||
| @@ -39,7 +36,7 @@ public class SettingsUi : Window, IDisposable | ||||
|     public SettingsUi(WindowSystem windowSystem, | ||||
|         UiShared uiShared, ConfigurationService configService, | ||||
|         MareCharaFileManager mareCharaFileManager, PairManager pairManager, | ||||
|         ServerConfigurationManager serverConfigurationManager, MareMediator mediator) : base("Mare Synchronos Settings") | ||||
|         ServerConfigurationManager serverConfigurationManager, MareMediator mediator) : base(mediator, "Mare Synchronos Settings") | ||||
|     { | ||||
|         Logger.Verbose("Creating " + nameof(SettingsUi)); | ||||
|  | ||||
| @@ -54,15 +51,13 @@ public class SettingsUi : Window, IDisposable | ||||
|         _mareCharaFileManager = mareCharaFileManager; | ||||
|         _pairManager = pairManager; | ||||
|         _serverConfigurationManager = serverConfigurationManager; | ||||
|         _mediator = mediator; | ||||
|         _uiShared = uiShared; | ||||
|  | ||||
|  | ||||
|         _mediator.Subscribe<OpenSettingsUiMessage>(this, (_) => Toggle()); | ||||
|         _mediator.Subscribe<SwitchToIntroUiMessage>(this, (_) => IsOpen = false); | ||||
|         _mediator.Subscribe<GposeStartMessage>(this, (_) => UiShared_GposeStart()); | ||||
|         _mediator.Subscribe<GposeEndMessage>(this, (_) => UiShared_GposeEnd()); | ||||
|         _mediator.Subscribe<PlayerChangedMessage>(this, (msg) => LastCreatedCharacterData = ((PlayerChangedMessage)msg).Data); | ||||
|         Mediator.Subscribe<OpenSettingsUiMessage>(this, (_) => Toggle()); | ||||
|         Mediator.Subscribe<SwitchToIntroUiMessage>(this, (_) => IsOpen = false); | ||||
|         Mediator.Subscribe<GposeStartMessage>(this, (_) => UiShared_GposeStart()); | ||||
|         Mediator.Subscribe<GposeEndMessage>(this, (_) => UiShared_GposeEnd()); | ||||
|         Mediator.Subscribe<PlayerChangedMessage>(this, (msg) => LastCreatedCharacterData = ((PlayerChangedMessage)msg).Data); | ||||
|  | ||||
|         windowSystem.AddWindow(this); | ||||
|     } | ||||
| @@ -78,10 +73,9 @@ public class SettingsUi : Window, IDisposable | ||||
|         IsOpen = false; | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(SettingsUi)); | ||||
|  | ||||
|         base.Dispose(); | ||||
|         _windowSystem.RemoveWindow(this); | ||||
|     } | ||||
|  | ||||
| @@ -215,7 +209,7 @@ public class SettingsUi : Window, IDisposable | ||||
|                 { | ||||
|                     Task.Run(() => ApiController.UserDelete()); | ||||
|                     _deleteAccountPopupModalShown = false; | ||||
|                     _mediator.Publish(new SwitchToIntroUiMessage()); | ||||
|                     Mediator.Publish(new SwitchToIntroUiMessage()); | ||||
|                 } | ||||
|  | ||||
|                 ImGui.SameLine(); | ||||
|   | ||||
| @@ -656,6 +656,7 @@ public partial class UiShared : IDisposable | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         _pluginInterface.UiBuilder.BuildFonts -= BuildFont; | ||||
|     } | ||||
| } | ||||
|   | ||||
| @@ -20,6 +20,7 @@ public class DalamudLoggingProvider : ILoggerProvider | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         _loggers.Clear(); | ||||
|     } | ||||
| } | ||||
|   | ||||
| @@ -3,8 +3,6 @@ using Dalamud.Game.ClientState; | ||||
| using Dalamud.Game.ClientState.Conditions; | ||||
| using Dalamud.Game.ClientState.Objects; | ||||
| using Dalamud.Game.ClientState.Objects.SubKinds; | ||||
| using Dalamud.Game.Gui; | ||||
| using Dalamud.Game.Text.SeStringHandling; | ||||
| using FFXIVClientStructs.FFXIV.Client.Game.Character; | ||||
| using FFXIVClientStructs.FFXIV.Client.Game.Control; | ||||
| using Lumina.Excel.GeneratedSheets; | ||||
| @@ -270,6 +268,7 @@ public class DalamudUtil : IDisposable | ||||
|  | ||||
|     public void Dispose() | ||||
|     { | ||||
|         Logger.Verbose($"Disposing {GetType()}"); | ||||
|         _framework.Update -= FrameworkOnUpdate; | ||||
|     } | ||||
| } | ||||
|   | ||||
| @@ -186,7 +186,7 @@ public partial class ApiController | ||||
|  | ||||
|     public async Task DownloadFiles(int currentDownloadId, List<FileReplacementData> fileReplacementDto, CancellationToken ct) | ||||
|     { | ||||
|         _mediator.Publish(new HaltScanMessage("Download")); | ||||
|         Mediator.Publish(new HaltScanMessage("Download")); | ||||
|         try | ||||
|         { | ||||
|             await DownloadFilesInternal(currentDownloadId, fileReplacementDto, ct).ConfigureAwait(false); | ||||
| @@ -197,7 +197,7 @@ public partial class ApiController | ||||
|         } | ||||
|         finally | ||||
|         { | ||||
|             _mediator.Publish(new ResumeScanMessage("Download")); | ||||
|             Mediator.Publish(new ResumeScanMessage("Download")); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|   | ||||
| @@ -255,13 +255,13 @@ public partial class ApiController | ||||
|         switch (severity) | ||||
|         { | ||||
|             case MessageSeverity.Error: | ||||
|                 _mediator.Publish(new NotificationMessage("Warning from " + _serverManager.CurrentServer!.ServerName, message, NotificationType.Error, 7500)); | ||||
|                 Mediator.Publish(new NotificationMessage("Warning from " + _serverManager.CurrentServer!.ServerName, message, NotificationType.Error, 7500)); | ||||
|                 break; | ||||
|             case MessageSeverity.Warning: | ||||
|                 _mediator.Publish(new NotificationMessage("Warning from " + _serverManager.CurrentServer!.ServerName, message, NotificationType.Warning, 7500)); | ||||
|                 Mediator.Publish(new NotificationMessage("Warning from " + _serverManager.CurrentServer!.ServerName, message, NotificationType.Warning, 7500)); | ||||
|                 break; | ||||
|             case MessageSeverity.Information: | ||||
|                 _mediator.Publish(new NotificationMessage("Info from " + _serverManager.CurrentServer!.ServerName, message, NotificationType.Info, 5000)); | ||||
|                 Mediator.Publish(new NotificationMessage("Info from " + _serverManager.CurrentServer!.ServerName, message, NotificationType.Info, 5000)); | ||||
|                 break; | ||||
|         } | ||||
|  | ||||
|   | ||||
| @@ -15,7 +15,7 @@ using MareSynchronos.MareConfiguration; | ||||
| using MareSynchronos.Mediator; | ||||
|  | ||||
| namespace MareSynchronos.WebAPI; | ||||
| public partial class ApiController : IDisposable, IMareHubClient | ||||
| public partial class ApiController : MediatorSubscriberBase, IDisposable, IMareHubClient | ||||
| { | ||||
|     public const string MainServer = "Lunae Crescere Incipientis (Central Server EU)"; | ||||
|     public const string MainServiceUri = "wss://maresynchronos.com"; | ||||
| @@ -27,7 +27,6 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|     private readonly FileCacheManager _fileDbManager; | ||||
|     private readonly PairManager _pairManager; | ||||
|     private readonly ServerConfigurationManager _serverManager; | ||||
|     private readonly MareMediator _mediator; | ||||
|     private CancellationTokenSource _connectionCancellationTokenSource; | ||||
|     private HubConnection? _mareHub; | ||||
|  | ||||
| @@ -45,7 +44,8 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|  | ||||
|     private HttpClient _httpClient; | ||||
|  | ||||
|     public ApiController(ConfigurationService configService, DalamudUtil dalamudUtil, FileCacheManager fileDbManager, PairManager pairManager, ServerConfigurationManager serverManager, MareMediator mediator) | ||||
|     public ApiController(ConfigurationService configService, DalamudUtil dalamudUtil, FileCacheManager fileDbManager, | ||||
|         PairManager pairManager, ServerConfigurationManager serverManager, MareMediator mediator) : base(mediator) | ||||
|     { | ||||
|         Logger.Verbose("Creating " + nameof(ApiController)); | ||||
|  | ||||
| @@ -54,11 +54,10 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|         _fileDbManager = fileDbManager; | ||||
|         _pairManager = pairManager; | ||||
|         _serverManager = serverManager; | ||||
|         _mediator = mediator; | ||||
|         _connectionCancellationTokenSource = new CancellationTokenSource(); | ||||
|  | ||||
|         _mediator.Subscribe<DalamudLoginMessage>(this, (_) => DalamudUtilOnLogIn()); | ||||
|         _mediator.Subscribe<DalamudLogoutMessage>(this, (_) => DalamudUtilOnLogOut()); | ||||
|         Mediator.Subscribe<DalamudLoginMessage>(this, (_) => DalamudUtilOnLogIn()); | ||||
|         Mediator.Subscribe<DalamudLogoutMessage>(this, (_) => DalamudUtilOnLogOut()); | ||||
|         ServerState = ServerState.Offline; | ||||
|         _verifiedUploadedHashes = new(StringComparer.Ordinal); | ||||
|         _httpClient = new(); | ||||
| @@ -304,14 +303,12 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|         _ = ClientHealthCheck(_healthCheckTokenSource.Token); | ||||
|  | ||||
|         _initialized = true; | ||||
|         _mediator.Publish(new ConnectedMessage()); | ||||
|         Mediator.Publish(new ConnectedMessage()); | ||||
|     } | ||||
|  | ||||
|     public void Dispose() | ||||
|     public override void Dispose() | ||||
|     { | ||||
|         Logger.Verbose("Disposing " + nameof(ApiController)); | ||||
|  | ||||
|         ServerState = ServerState.Offline; | ||||
|         base.Dispose(); | ||||
|         Task.Run(async () => await StopConnection(_connectionCancellationTokenSource.Token, ServerState.Disconnected).ConfigureAwait(false)); | ||||
|         _connectionCancellationTokenSource?.Cancel(); | ||||
|         _healthCheckTokenSource?.Cancel(); | ||||
| @@ -341,7 +338,7 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|         CurrentDownloads.Clear(); | ||||
|         _uploadCancellationTokenSource?.Cancel(); | ||||
|         _healthCheckTokenSource?.Cancel(); | ||||
|         _mediator.Publish(new DisconnectedMessage()); | ||||
|         Mediator.Publish(new DisconnectedMessage()); | ||||
|         _pairManager.ClearPairs(); | ||||
|         ServerState = ServerState.Offline; | ||||
|         Logger.Info("Connection closed"); | ||||
| @@ -353,11 +350,11 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|         _connectionDto = null; | ||||
|         _healthCheckTokenSource?.Cancel(); | ||||
|         ServerState = ServerState.Reconnecting; | ||||
|         _mediator.Publish(new NotificationMessage("Connection lost", "Connection lost to " + _serverManager.CurrentServer!.ServerName, NotificationType.Error, 5000)); | ||||
|         Mediator.Publish(new NotificationMessage("Connection lost", "Connection lost to " + _serverManager.CurrentServer!.ServerName, NotificationType.Error, 5000)); | ||||
|         Logger.Warn("Connection closed... Reconnecting"); | ||||
|         Logger.Warn(arg?.Message ?? string.Empty); | ||||
|         Logger.Warn(arg?.StackTrace ?? string.Empty); | ||||
|         _mediator.Publish(new DisconnectedMessage()); | ||||
|         Mediator.Publish(new DisconnectedMessage()); | ||||
|         _pairManager.ClearPairs(); | ||||
|         return Task.CompletedTask; | ||||
|     } | ||||
| @@ -387,7 +384,7 @@ public partial class ApiController : IDisposable, IMareHubClient | ||||
|             await _mareHub.DisposeAsync().ConfigureAwait(false); | ||||
|             CurrentUploads.Clear(); | ||||
|             CurrentDownloads.Clear(); | ||||
|             _mediator.Publish(new DisconnectedMessage()); | ||||
|             Mediator.Publish(new DisconnectedMessage()); | ||||
|             _pairManager.ClearPairs(); | ||||
|             _mareHub = null; | ||||
|         } | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 rootdarkarchon
					rootdarkarchon