From 5400b58d3876914fea28aaa921cb72e890e52e4e Mon Sep 17 00:00:00 2001 From: lars-berger Date: Tue, 19 Dec 2023 20:25:23 +0800 Subject: [PATCH] feat: use non-blocking window messaging APIs (#462) --- GlazeWM.App.Watcher/WatcherStartup.cs | 3 +- GlazeWM.App.WindowManager/WmStartup.cs | 12 +++++- .../RedrawContainersHandler.cs | 2 +- GlazeWM.Domain/DependencyInjection.cs | 1 - .../CommandHandlers/CloseWindowHandler.cs | 2 +- .../CommandHandlers/SetMaximizedHandler.cs | 2 +- .../CommandHandlers/SetMinimizedHandler.cs | 2 +- .../CommandHandlers/ShowAllWindowsHandler.cs | 39 ------------------- .../CommandHandlers/ToggleMaximizedHandler.cs | 4 +- .../Windows/Commands/ShowAllWindowsCommand.cs | 8 ---- .../WindowsApi/WindowsApiService.cs | 7 ++-- 11 files changed, 22 insertions(+), 60 deletions(-) delete mode 100644 GlazeWM.Domain/Windows/CommandHandlers/ShowAllWindowsHandler.cs delete mode 100644 GlazeWM.Domain/Windows/Commands/ShowAllWindowsCommand.cs diff --git a/GlazeWM.App.Watcher/WatcherStartup.cs b/GlazeWM.App.Watcher/WatcherStartup.cs index eeed4de7f..c4dc747f5 100644 --- a/GlazeWM.App.Watcher/WatcherStartup.cs +++ b/GlazeWM.App.Watcher/WatcherStartup.cs @@ -93,8 +93,7 @@ private static async Task> GetInitialHandles(IpcClient clien private static void RestoreHandles(List handles) { foreach (var handle in handles) - // TODO: Change this. - ShowWindow(handle, ShowWindowFlags.ShowDefault); + ShowWindowAsync(handle, ShowWindowFlags.ShowNoActivate); } } } diff --git a/GlazeWM.App.WindowManager/WmStartup.cs b/GlazeWM.App.WindowManager/WmStartup.cs index b4ec77508..4d29513f4 100644 --- a/GlazeWM.App.WindowManager/WmStartup.cs +++ b/GlazeWM.App.WindowManager/WmStartup.cs @@ -19,6 +19,7 @@ public sealed class WmStartup { private readonly Bus _bus; private readonly KeybindingService _keybindingService; + private readonly WindowService _windowService; private readonly WindowEventService _windowEventService; private readonly UserConfigService _userConfigService; @@ -27,11 +28,13 @@ public sealed class WmStartup public WmStartup( Bus bus, KeybindingService keybindingService, + WindowService windowService, WindowEventService windowEventService, UserConfigService userConfigService) { _bus = bus; _keybindingService = keybindingService; + _windowService = windowService; _windowEventService = windowEventService; _userConfigService = userConfigService; } @@ -132,9 +135,16 @@ windowAnimations is WindowAnimations.True private void OnApplicationExit() { - _bus.Invoke(new ShowAllWindowsCommand()); + // Show all windows regardless of whether their workspace is displayed. + foreach (var window in _windowService.GetWindows()) + ShowWindowAsync(window.Handle, ShowWindowFlags.ShowNoActivate); + + // Clear border on the active window. _bus.Invoke(new SetActiveWindowBorderCommand(null)); + + // Destroy the system tray icon. _systemTrayIcon?.Remove(); + System.Windows.Forms.Application.Exit(); } } diff --git a/GlazeWM.Domain/Containers/CommandHandlers/RedrawContainersHandler.cs b/GlazeWM.Domain/Containers/CommandHandlers/RedrawContainersHandler.cs index 5f24c95bd..4404aba3c 100644 --- a/GlazeWM.Domain/Containers/CommandHandlers/RedrawContainersHandler.cs +++ b/GlazeWM.Domain/Containers/CommandHandlers/RedrawContainersHandler.cs @@ -46,7 +46,7 @@ public CommandResponse Handle(RedrawContainersCommand command) // Restore minimized/maximized windows. Needed to be able to move and resize them. foreach (var window in windowsToRestore) - ShowWindow(window.Handle, ShowWindowFlags.Restore); + ShowWindowAsync(window.Handle, ShowWindowFlags.Restore); foreach (var window in windowsToRedraw) { diff --git a/GlazeWM.Domain/DependencyInjection.cs b/GlazeWM.Domain/DependencyInjection.cs index 948ee68d3..6a1dfbe30 100644 --- a/GlazeWM.Domain/DependencyInjection.cs +++ b/GlazeWM.Domain/DependencyInjection.cs @@ -70,7 +70,6 @@ public static IServiceCollection AddDomainServices(this IServiceCollection servi services.AddSingleton, SetMinimizedHandler>(); services.AddSingleton, SetTilingHandler>(); services.AddSingleton, SetWindowSizeHandler>(); - services.AddSingleton, ShowAllWindowsHandler>(); services.AddSingleton, ToggleFloatingHandler>(); services.AddSingleton, ToggleMaximizedHandler>(); services.AddSingleton, UnmanageWindowHandler>(); diff --git a/GlazeWM.Domain/Windows/CommandHandlers/CloseWindowHandler.cs b/GlazeWM.Domain/Windows/CommandHandlers/CloseWindowHandler.cs index 66b2bea1e..104c43fa6 100644 --- a/GlazeWM.Domain/Windows/CommandHandlers/CloseWindowHandler.cs +++ b/GlazeWM.Domain/Windows/CommandHandlers/CloseWindowHandler.cs @@ -11,7 +11,7 @@ public CommandResponse Handle(CloseWindowCommand command) { var windowToClose = command.WindowToClose; - SendMessage(windowToClose.Handle, SendMessageType.Close, IntPtr.Zero, IntPtr.Zero); + SendNotifyMessage(windowToClose.Handle, SendMessageType.Close, IntPtr.Zero, IntPtr.Zero); return CommandResponse.Ok; } diff --git a/GlazeWM.Domain/Windows/CommandHandlers/SetMaximizedHandler.cs b/GlazeWM.Domain/Windows/CommandHandlers/SetMaximizedHandler.cs index 169886615..0200c60e5 100644 --- a/GlazeWM.Domain/Windows/CommandHandlers/SetMaximizedHandler.cs +++ b/GlazeWM.Domain/Windows/CommandHandlers/SetMaximizedHandler.cs @@ -10,7 +10,7 @@ public CommandResponse Handle(SetMaximizedCommand command) { var window = command.Window; - ShowWindow(window.Handle, ShowWindowFlags.Maximize); + ShowWindowAsync(window.Handle, ShowWindowFlags.Maximize); return CommandResponse.Ok; } diff --git a/GlazeWM.Domain/Windows/CommandHandlers/SetMinimizedHandler.cs b/GlazeWM.Domain/Windows/CommandHandlers/SetMinimizedHandler.cs index 5fa007a4f..d8c2b7325 100644 --- a/GlazeWM.Domain/Windows/CommandHandlers/SetMinimizedHandler.cs +++ b/GlazeWM.Domain/Windows/CommandHandlers/SetMinimizedHandler.cs @@ -10,7 +10,7 @@ public CommandResponse Handle(SetMinimizedCommand command) { var window = command.Window; - ShowWindow(window.Handle, ShowWindowFlags.Minimize); + ShowWindowAsync(window.Handle, ShowWindowFlags.Minimize); return CommandResponse.Ok; } diff --git a/GlazeWM.Domain/Windows/CommandHandlers/ShowAllWindowsHandler.cs b/GlazeWM.Domain/Windows/CommandHandlers/ShowAllWindowsHandler.cs deleted file mode 100644 index 2b5c3f683..000000000 --- a/GlazeWM.Domain/Windows/CommandHandlers/ShowAllWindowsHandler.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System; -using GlazeWM.Domain.Windows.Commands; -using GlazeWM.Infrastructure.Bussing; -using static GlazeWM.Infrastructure.WindowsApi.WindowsApiService; - -namespace GlazeWM.Domain.Windows.CommandHandlers -{ - internal sealed class ShowAllWindowsHandler : ICommandHandler - { - private readonly WindowService _windowService; - - public ShowAllWindowsHandler(WindowService windowService) - { - _windowService = windowService; - } - - public CommandResponse Handle(ShowAllWindowsCommand command) - { - // Show all windows regardless of whether their workspace is displayed. - foreach (var window in _windowService.GetWindows()) - { - const SetWindowPosFlags flags = SetWindowPosFlags.FrameChanged | SetWindowPosFlags.NoActivate | SetWindowPosFlags.NoCopyBits | - SetWindowPosFlags.NoZOrder | SetWindowPosFlags.NoOwnerZOrder | SetWindowPosFlags.NoSendChanging | SetWindowPosFlags.ShowWindow; - - SetWindowPos( - window.Handle, - IntPtr.Zero, - window.X, - window.Y, - window.Width, - window.Height, - flags - ); - } - - return CommandResponse.Ok; - } - } -} diff --git a/GlazeWM.Domain/Windows/CommandHandlers/ToggleMaximizedHandler.cs b/GlazeWM.Domain/Windows/CommandHandlers/ToggleMaximizedHandler.cs index e7717033c..1a758b70c 100644 --- a/GlazeWM.Domain/Windows/CommandHandlers/ToggleMaximizedHandler.cs +++ b/GlazeWM.Domain/Windows/CommandHandlers/ToggleMaximizedHandler.cs @@ -11,9 +11,9 @@ public CommandResponse Handle(ToggleMaximizedCommand command) var window = command.Window; if (window.HasWindowStyle(WindowStyles.Maximize)) - ShowWindow(window.Handle, ShowWindowFlags.Restore); + ShowWindowAsync(window.Handle, ShowWindowFlags.Restore); else - ShowWindow(window.Handle, ShowWindowFlags.Maximize); + ShowWindowAsync(window.Handle, ShowWindowFlags.Maximize); return CommandResponse.Ok; } diff --git a/GlazeWM.Domain/Windows/Commands/ShowAllWindowsCommand.cs b/GlazeWM.Domain/Windows/Commands/ShowAllWindowsCommand.cs deleted file mode 100644 index ab5558131..000000000 --- a/GlazeWM.Domain/Windows/Commands/ShowAllWindowsCommand.cs +++ /dev/null @@ -1,8 +0,0 @@ -using GlazeWM.Infrastructure.Bussing; - -namespace GlazeWM.Domain.Windows.Commands -{ - public class ShowAllWindowsCommand : Command - { - } -} diff --git a/GlazeWM.Infrastructure/WindowsApi/WindowsApiService.cs b/GlazeWM.Infrastructure/WindowsApi/WindowsApiService.cs index 5b9080378..781bf002b 100644 --- a/GlazeWM.Infrastructure/WindowsApi/WindowsApiService.cs +++ b/GlazeWM.Infrastructure/WindowsApi/WindowsApiService.cs @@ -246,12 +246,13 @@ public enum ShowWindowFlags : uint { Minimize = 2, Maximize = 3, - ShowDefault = 10, + ShowNoActivate = 8, Restore = 9, + ShowDefault = 10, } [DllImport("user32.dll")] - public static extern bool ShowWindow(IntPtr hWnd, ShowWindowFlags flags); + public static extern bool ShowWindowAsync(IntPtr hWnd, ShowWindowFlags flags); [DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern int GetWindowTextLength(IntPtr hWnd); @@ -399,7 +400,7 @@ public enum SendMessageType : uint } [DllImport("user32.dll", CharSet = CharSet.Auto)] - public static extern IntPtr SendMessage(IntPtr hWnd, SendMessageType msg, IntPtr wParam, IntPtr lParam); + public static extern IntPtr SendNotifyMessage(IntPtr hWnd, SendMessageType msg, IntPtr wParam, IntPtr lParam); [DllImport("user32.dll", SetLastError = true)] public static extern bool IsProcessDPIAware();