找到一个 WPF 窗口的句柄

131

Windows Forms有一个属性win1.Handle,如果我没记错的话,它返回主窗口的句柄?

是否有一种相应的方法来获取WPF窗口的句柄?

我在网上找到了下面的代码,

IntPtr windowHandle = 
    new WindowInteropHelper(Application.Current.MainWindow).Handle;

但我认为那并没有帮助到我,因为我的应用程序有多个窗口。


29
让我给你一些友好的建议,Evan。不要做“货物崇拜编程”!剖析你在网上找到的代码,你可以清晰地看到它传递了Application.Current.MainWindow,由此可以推断出通过传递对不同窗口的引用,你就能得到答案。虽然我从未使用过WindowInteropHelper,但仍然能够通过推理来回答这个问题。 - Gregory Higley
2
你说得对,谢谢!我今天有点累 :)。 - Evan
8
没问题!我说这话并不是想批评你,只是想帮忙而已。我们都有时会有点盲目模仿别人的做法。 :) - Gregory Higley
6个回答

170

相比于传递 Application.Current.MainWindow,只需传递对应窗口的引用: new WindowInteropHelper(this).Handle 等即可。


我刚刚发现FileSave常用对话框需要引用顶层窗口,因此您可以传递应用程序的MainWindow的引用。只有在真正需要时才保存Interop服务。 - David A. Gray

51

你可以使用WindowsInteropHelper类与窗口进行交互:

// ... Window myWindow = get your Window instance...
IntPtr windowHandle = new WindowInteropHelper(myWindow).Handle;

目前,您正在请求应用程序的主窗口,其中始终只会有一个。但是,只要它是 System.Windows.Window 派生的窗口类,您可以在任何窗口上使用相同的技术。


感谢Reed Copsey。对于需要的人来说,VB.Net的代码如下:Dim windowHandle As IntPtr = New Interop.WindowInteropHelper(Me).Handle - Wild Teddy

17

你可以使用:

Process.GetCurrentProcess().MainWindowHandle

这在WPF窗口中不起作用,它总是返回空句柄。 - radj307

4

在我的应用中,我需要在启动期间获取主窗口的句柄,但无论我怎么尝试,new WindowInteropHelper(...).Handle 都只会返回一个空句柄,因为窗口还没有被初始化。

您可以使用 EnsureHandle() 方法,它将创建句柄(如果不存在),或者返回当前的句柄(如果已存在)。

var hWnd = new WindowInteropHelper(Application.Current.MainWindow).EnsureHandle();

一旦应用程序启动,它会继续使用同一个句柄而没有任何问题。


3

如果您因某种原因需要获取应用程序所有窗口的窗口句柄,可以使用Application.Windows属性获取所有窗口,然后像您已经演示的那样使用WindowInteropHandler来获取它们的句柄。


这里可能缺少的是获取控件的句柄(System.Windows.Controls.Control而不是System.Windows.Window)。 - David V. Corbin

0

在我的情况下,在OnLoaded()事件之后工作。在构造函数中,它会给出一个零句柄。

var winHandle = new WindowInteropHelper(this).Handle;

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接