从一些初步测试来看, EnumWindows
似乎总是以相反的实例化顺序返回窗口,即最近实例化的窗口在前。这是一个有效的观察结果吗?如果是这样,则在所有Windows版本中都适用吗?这是可靠的假设吗,即该行为是否记录在某处?
上下文:我正在处理以下情况:我触发第三方应用程序打开多个非模式窗口,并且一旦它们打开,我需要向这些窗口发送一些窗口消息,但是我无法确定将它们标识为它们的窗口类和标题都不会有所不同,我也不知道它们的预期坐标。但是,如果我可以依靠EnumWindows
的上述行为,则可以简单地使用EnumWindows
返回的第一个句柄,该句柄的类和标题与我的期望相符。这仍然留下了一些假设的漏洞,但我认为这已经足够了。尽管如此,欢迎提出其他建议。
最佳答案
它以Z顺序返回它们。首先是设置了WS_EX_TOPMOST
的最上面的窗口,直到设置了WS_EX_TOPMOST set
的最下面的窗口,然后是没有WS_EX_TOPMOST
的最上面的窗口,直到没有WS_EX_TOPMOST
的最下面的窗口。请注意,可见性不是决定性因素,因此在Z轴顺序上比可见窗口高的不可见窗口仍会出现在它之前。
编辑:
仅从EnumWindows
获得第一笔 yield 就极不可能随意使用它。您的新窗口不仅不大可能成为第一个返回窗口,而且您还处于竞争状态,在此期间可能会打开其他窗口。但是,您可以保留该应用程序所有已知窗口的列表,当需要查找新打开的窗口时,请调用EnumWindows
并将窗口句柄与列表中的句柄进行比较。当找到不在列表中的具有正确的类和标题(甚至可以使用GetWindowThreadProcessID
甚至检查它是否属于正确的进程)的标题时,便找到了新窗口。
但是,出于您的目的,安装CBT挂钩并注意HCBT_CREATEWND通知可能会为您提供更好的服务。有关更多信息,请参见 SetWindowsHookEx()
和the CBTProc
callback上的MSDN帮助。
关于枚举顺序的确定性级别:
关于此问题的许多评论和其他答案都提到了MSDN中缺少EnumWindows
返回窗口句柄的顺序的精确文档。实际上,关于 EnumWindows
和the EnumWindowsProc
callback的页面都对此问题保持沉默。我提供以下证据:
EnumChildWindows
上的页面暗指备注部分中的顺序:这意味着该顺序是Z顺序相关的。并且由于在hWndParent参数的描述中这样说:
可以假设
EnumWindows
采用相同的逻辑和顺序。 当然,这一点在学术上都是很学术的,因为
EnumWindows
可能不是解决OP问题的最佳解决方案-至少EnumThreadWindows
可能更合适-但是我认为值得其他人提及在这篇文章中关于windows - EnumWindows返回句柄的顺序有意义吗?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/295996/