我正在处理的项目的一部分涉及查找显示的每个窗口。我使用EnumWindows()
函数浏览每个窗口,并过滤掉在IsWindowVisible()
上不返回true的那些窗口。但即使如此,我仍然得到一些奇怪的结果,其中包括没有可见窗口的过程。这是代码:
int main()
{
EnumWindows(callback, NULL);
cin.get();
return 0;
}
BOOL CALLBACK callback(HWND hWnd, LPARAM lParam)
{
wchar_t windowTitle[256];
GetWindowText(hWnd, windowTitle, sizeof(windowTitle));
int length = ::GetWindowTextLength(hWnd);
wstring title(&windowTitle[0]);
if (!IsWindowVisible(hWnd) || length == 0) return TRUE;
WINDOWPLACEMENT wp;
GetWindowPlacement(hWnd, &wp);
cout << string(title.begin(), title.end()) << endl;
return TRUE;
}
这是结果:
C:\Users\qjohh\Documents\Visual Studio 2017\Projects\ConsoleApplication1\Debug\ConsoleApplication1.exe
ConsoleApplication1 (Running) - Microsoft Visual Studio
Settings
Settings
Movies & TV
Movies & TV
Calculator
Calculator
Microsoft Edge
Microsoft Edge
Netflix
Netflix
Microsoft Store
Microsoft Store
Program Manager
下面列出的所有属于Visual Studio的进程都没有打开的窗口,自从我的计算机启动以来,我什至没有启动它们。我做了一些挖掘,结果发现这些已被任务管理器视为后台进程(Program Manager
除外,我认为这是操作系统的核心进程)
是否可以将这些结果排除在我的搜索结果之外?
答案 0 :(得分:4)
我在使用EnumWindows
枚举Windows 10上的窗口时遇到了同样的问题:有时,Metro / Modern应用程序即使未运行,也会被列为正在运行。解?检查窗口是否具有DWM隐藏属性
这是我的EnumProc
(LPARAM
是指向打开的文件句柄的32位指针,用于编写标题;根据应用程序的需要进行必要的调整):
#include <Windows.h>
#include <strsafe.h>
#include <dwmapi.h>
#pragma comment(lib, "dwmapi.lib")
#define MAX_TITLE_LEN 100
BOOL CALLBACK EnumProc(HWND hWnd, LPARAM lParam)
{
LONG lStyle = GetWindowLongPtrW(hWnd, GWL_STYLE);
if ((lStyle & WS_VISIBLE) && (lStyle & WS_SYSMENU))
{
CONST CHAR CRLF[2] = { '\r', '\n' };
HANDLE hFile = *(HANDLE *)lParam;
DWORD dwWritten;
CHAR szTitle[MAX_TITLE_LEN];
HRESULT hr;
UINT uLen;
INT nCloaked;
// On Windows 10, ApplicationFrameWindow may run in the background and
// WS_VISIBLE will be true even if the window isn't actually visible,
// for various UWP apps. I don't know of any method for predicting when
// this will happen, and for which app(s).
//
// The only way to test if a window is actually *visible* in this case
// is to test for the DWM CLOAKED attribute.
DwmGetWindowAttribute(hWnd, DWMWA_CLOAKED, &nCloaked, sizeof(INT));
if (nCloaked)
return TRUE;
GetWindowTextA(hWnd, szTitle, MAX_TITLE_LEN);
hr = StringCbLengthA(szTitle, MAX_TITLE_LEN, &uLen);
if (SUCCEEDED(hr) && uLen > 0)
{
SetFilePointer(hFile, 0, NULL, FILE_END);
WriteFile(hFile, szTitle, uLen, &dwWritten, NULL);
WriteFile(hFile, CRLF, 2, &dwWritten, NULL);
}
}
return TRUE;
}
答案 1 :(得分:-1)
我认为您正在列出系统中的所有窗口,但也许其中一些不在当前桌面中。解释如下: Filtering/Parsing list produced from EnumWindows in C++
不可见窗口的另一种情况是当它在屏幕坐标外时,您可以将“窗口”和“屏幕矩形”相交。