【发布时间】:2019-02-11 00:46:56
【问题描述】:
我正在使用 MS Access 2016 VBA 自动访问外部应用程序。外部应用程序窗口有一个显示在子窗口中的视频。
如果我使用 spyxx.exe,我可以使用“查找工具”来获取视频控件的句柄(当然会改变)、标题(“面板”)、类(“wxWindowNR”)和样式(52000000 )。当我使用 spyxx.exe 返回的句柄时,我可以成功地使用该句柄将正确的应用程序带到顶部并激活它。但由于该句柄发生了变化,我需要使用 MS Access VBA 动态获取它。
我遇到的问题是,当我使用 FindWindowEx API 尝试获取子视频窗口的句柄时,我无法弄清楚如何获取 spyxx.exe 提供的相同句柄。这是我正在尝试的(以及主题的一些变体): 声明是:
Public Declare Function FindWindowEx Lib "user32.dll" Alias "FindWindowExA" (ByVal hwndParent As Long, ByVal hwndChildAfter As Long, ByVal lpszClass As String, ByVal lpszWindow As String) As Long
并且(尝试)获取子视频窗口句柄的代码是(其中 WinHand 是父窗口的句柄):
FindWindowEx(WinHand, 0, "wxWindowNR", "panel")
我知道 WinHand 对于父窗口是正确的,因为使用 WinHand 我可以使应用程序成为活动的最顶层窗口。但是,我永远无法让 FindWindowEx 返回 spyxx.exe 显示的句柄是子“面板”窗口的句柄。
当我将子窗口的名称留空时,它确实返回句柄,如下所示:
FindWindowEx(WinHand, 0, "wxWindowNR", "")
但绝不是 spyxx.exe 显示的正确句柄。
从一天中大部分时间在网上搜索,看来我可能需要使用 EnumChildWindows API 做一些事情,但我不知道如何在 MS Access VBA 中引用它,也不知道如何循环通过返回的窗口找到“面板”窗口句柄。
【问题讨论】:
-
你弄错了句柄?你拿什么把手?可能有另一个带有类名的窗口。你也应该在 Spy++ 中找到错误的句柄
-
感谢@xMRi。 Spy++ 确实没有 找到错误的句柄——这就是重点。我知道 Spy++ 返回的句柄是正确的,因为当我在 VBA 代码中使用 Spy++ 句柄时,该代码可以操作目标子窗口。我需要的是一种通过使用 VBA FindWindowEx 或 EnumChildWindows 获得 Spy++ 找到的相同句柄的方法。显然,FindWindowEx 现在返回的句柄不正确,但我无法确定如何更正它以找到 Spy++ 找到的句柄。这就是问题所在:如何让 VBA 找到 Spy++ 找到的相同(正确)句柄?
-
“你得到什么句柄?”当目标窗口关闭并重新打开时,该句柄编号(当然)会发生变化。但是 Spy++ 每次都能找到正确的句柄,但 VBA 从来没有使用 FindWindowEx 找到正确的句柄。我知道这一点是因为如果我使用 Spy++ 返回的句柄,我可以在 VBA 中操作目标窗口,但是,如果我使用 VBA 返回的句柄,我无法操作目标窗口。因此,VBA 必须返回错误的句柄,而 Spy++ 必须返回正确的句柄。问题是:如何让 VBA 返回 Spy++ 返回的正确句柄?
-
为什么投反对票?如果有人认为这是一个不好的问题,请发布为什么这是一个不好的问题,或者请发布明显的答案。
-
投反对票可能是因为您没有给我们提供足够的信息。你拿什么把手? FindWindow 永远不会返回不存在的东西......所以如果你得到一个结果,这个窗口就符合条件。而且由于您无法向我们展示可重现的代码,因此可能会导致否决票。滴滴你用GetWindow API函数自己遍历Window树?