如何将.NET应用程序窗口设置为最顶层?

摘要:本文介绍如何将窗口置于最顶层,以及解决在顶层显示时对锁屏登录界面的影响等问题。用于实现类似Launcher、系统工具等应用需要窗口层级比Windows开始菜单以及置顶任务栏还要高的场景 一般情况下的窗口置顶,可以设置WPF窗口属性Topmo
本文介绍如何将窗口置于最顶层,以及解决在顶层显示时对锁屏登录界面的影响等问题。用于实现类似Launcher、系统工具等应用需要窗口层级比Windows开始菜单以及置顶任务栏还要高的场景 一般情况下的窗口置顶,可以设置WPF窗口属性Topmost=true 也可以使用WIN32-SetWindowPos函数SetWindowPos 函数 (winuser.h) - Win32 apps | Microsoft Learn,设置窗口层级: 1 /// <summary>设置窗口位置</summary> 2 /// <param name="hwnd">窗口句柄</param> 3 /// <param name="hWndInsertAfter">跟随的窗口句柄</param> 4 /// <param name="x">X轴坐标</param> 5 /// <param name="y">Y轴坐标</param> 6 /// <param name="width">宽</param> 7 /// <param name="height">高</param> 8 /// <param name="uFlags">标志位</param> 9 /// <returns></returns> 10 [DllImport("user32.dll", SetLastError = true)] 11 public static extern bool SetWindowPos(IntPtr hwnd, IntPtr hWndInsertAfter, int x, int y, int width, int height, uint uFlags); hWndInsertAfter,需要置顶可以传入参数HWND_TOPMOST(-1)。设置后会在任务栏上方显示(注意:不是开始菜单显示时的任务栏,开始菜单显示后任务栏层级是超级高的,置顶层级需要再次提升,下面会讲到) 如果你软件的置顶需求是常驻,需要解决与其它置顶窗口的层级冲突、抢他们的层级,可以加个定时器: 1 private nint _handle; 2 private void MainWindow_Loaded(object sender, RoutedEventArgs e) 3 { 4 _handle = new WindowInteropHelper(this).Handle; 5 SetWindowPos(_handle, -1, 0, 0, 0, 0, 1); 6 //定时器置顶 7 var timer = new Timer(); 8 timer.Interval = 100; 9 timer.Elapsed += Timer_Elapsed; 10 timer.Start(); 11 } 12 private void Timer_Elapsed(object? sender, System.Timers.ElapsedEventArgs e) 13 { 14 SetWindowPos(_handle, -1, 0, 0, 0, 0, 1); 15 } 当然,这种窗口置顶方案,遇上比你更流氓的软件就GG了,会抢来抢去。 最上层置顶(比Windows开始菜单以及置顶任务栏还要高),根据我们MVP毅仔提供的方案让你的程序置顶到比系统界面都更上层,就像任务管理器/放大镜一样绝对置顶 - walterlv,我们简单补充整理: 1. 添加app.manifest,并修改requestedExecutionLevel为管理员启动权限、添加UI置顶权限,详细的可以了解/MANIFESTUAC(将 UAC 信息嵌入到清单中) | Microsoft Learn <requestedExecutionLevel level="requireAdministrator" uiAccess="true" /> 这里的窗口置顶可以设置比系统界面更高的置顶,也就是说可以比一些系统级别的置顶还要高,效果同任务管理器的绝对置顶。
阅读全文