gpt4 book ai didi

c# - 工具窗口的永久焦点

转载 作者:太空狗 更新时间:2023-10-29 21:45:16 25 4
gpt4 key购买 nike

有没有什么方法可以在 WinForms 中创建一个工具窗口,只要宿主表单有焦点,工具窗口也有焦点? Paint.NET 中的一个示例:

Focused tool window

我在 .Net 4.0 下使用 C# 作为后端应用程序语言。

最佳答案

旧版 Paint.Net 的源代码位于 openpdn Fork of Paint.NET 3.36.7

我试图将他们的方法从源代码中提取到我能收集到的最简洁的工作示例中:

调用类:

internal static class Win32 {
public const int WM_ACTIVATE = 0x006;
public const int WM_ACTIVATEAPP = 0x01C;
public const int WM_NCACTIVATE = 0x086;

[DllImport("user32.dll", SetLastError = false)]
internal static extern IntPtr SendMessageW(IntPtr hWnd, uint msg,
IntPtr wParam, IntPtr lParam);

[DllImport("user32.dll", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
internal extern static bool PostMessageW(IntPtr handle, uint msg,
IntPtr wParam, IntPtr lParam);
}

基本形式:

public partial class Form1 : Form {

public Form1() {
InitializeComponent();
}

private bool ignoreNcActivate = false;

protected override void WndProc(ref Message m) {
base.WndProc(ref m);

switch (m.Msg) {
case Win32.WM_NCACTIVATE:
if (m.WParam == IntPtr.Zero) {
if (ignoreNcActivate) {
ignoreNcActivate = false;
} else {
Win32.SendMessageW(this.Handle, Win32.WM_NCACTIVATE, new IntPtr(1), IntPtr.Zero);
}
}
break;
case Win32.WM_ACTIVATEAPP:
if (m.WParam == IntPtr.Zero) {
Win32.PostMessageW(this.Handle, Win32.WM_NCACTIVATE, IntPtr.Zero, IntPtr.Zero);
foreach (Form2 f in this.OwnedForms.OfType<Form2>()) {
f.ForceActiveBar = false;
Win32.PostMessageW(f.Handle, Win32.WM_NCACTIVATE, IntPtr.Zero, IntPtr.Zero);
}
ignoreNcActivate = true;
} else if (m.WParam == new IntPtr(1)) {
Win32.SendMessageW(this.Handle, Win32.WM_NCACTIVATE, new IntPtr(1), IntPtr.Zero);
foreach (Form2 f in this.OwnedForms.OfType<Form2>()) {
f.ForceActiveBar = true;
Win32.SendMessageW(f.Handle, Win32.WM_NCACTIVATE, new IntPtr(1), IntPtr.Zero);
}
}
break;
}
}

protected override void OnShown(EventArgs e) {
base.OnShown(e);
Form2 f = new Form2();
f.Show(this);
}
}

始终激活 Form2(除非应用未激活):

public partial class Form2 : Form {
internal bool ForceActiveBar { get; set; }

public Form2() {
InitializeComponent();
this.ShowInTaskbar = false;
this.ForceActiveBar = true;
}

protected override void WndProc(ref Message m) {
base.WndProc(ref m);
if (m.Msg == Win32.WM_NCACTIVATE) {
if (this.ForceActiveBar && m.WParam == IntPtr.Zero) {
Win32.SendMessageW(this.Handle, Win32.WM_NCACTIVATE, new IntPtr(1), IntPtr.Zero);
}
}
}
}

没有必要将 Form2 的 TopMost 设置为 true,因为它在显示时应该由主窗体拥有。此外,Form2 不是 MDI 子窗体。

关于c# - 工具窗口的永久焦点,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16710619/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com