using System; using System.Collections.Generic; using System.Linq; using System.Threading; using System.Threading.Tasks; using LavishScriptAPI; using LavishVMAPI; using Microsoft.Extensions.Hosting; using Microsoft.Extensions.Logging; using MRBot.UI; namespace MRBot.Services; internal sealed class WindowManagerService : BackgroundService { private readonly IHostApplicationLifetime _applicationLifetime; private readonly ILogger _logger; private readonly List _activeWindows = new(); private readonly List _inactiveWindows; public WindowManagerService(IEnumerable windows, IHostApplicationLifetime applicationLifetime, ILogger logger) { _applicationLifetime = applicationLifetime; _logger = logger; _inactiveWindows = windows.ToList(); } private void RemoveWindow(object sender, LSEventArgs args) { var window = sender as IWindow; if(window == null) return; _activeWindows.Remove(window); _inactiveWindows.Add(window); window.Hide(); window?.Dispose(); if (_activeWindows.Count == 0) { _applicationLifetime.StopApplication(); } } private void OpenWindow(string windowName) { var window = _inactiveWindows.FirstOrDefault(w => w.Name == windowName); if (window == null) return; _inactiveWindows.Remove(window); _activeWindows.Add(window); window.Show(); window.OnWindowClose += RemoveWindow; } public override Task StartAsync(CancellationToken cancellationToken) { _logger.LogInformation("Starting window manager"); return base.StartAsync(cancellationToken); } private void ServiceLoopAsync(CancellationToken stoppingToken) { while (!stoppingToken.IsCancellationRequested) { Thread.Sleep(500); Frame.Wait(false); } } protected override async Task ExecuteAsync(CancellationToken stoppingToken) { OpenWindow(WindowNames.MainWindow); await Task.Factory.StartNew(() => { ServiceLoopAsync(stoppingToken); }, stoppingToken, TaskCreationOptions.LongRunning, TaskScheduler.Default); } public override void Dispose() { foreach (var window in _activeWindows) { window.OnWindowClose -= RemoveWindow; window.Dispose(); } base.Dispose(); } }