Учитывая действительный hwnd
, как мы можем проверить, действительно ли это окно с альтернативной вкладкой?
Один из моих предыдущих методов заключался в том, чтобы получить класс окна, которому принадлежит hwnd
, а затем сравнить его со следующими значениями: MultitaskingViewFrame
, ForegroundStaging
, TaskSwitcherWnd
и TaskSwitcherOverlayWnd
.
Однако я пришел к выводу, что имена классов не уникальны в системе, и действительно можно RegisterClassEx
класс с тем же именем, что и приведенные выше имена, что означает, что мой метод выше даст ложные срабатывания.
К сожалению, моя цель состоит в том, чтобы точно обнаружить окно Alt-Tab/переключение задач/ForegroundStaging, вместо того, чтобы найти, какое окно попадает в список Alt-Tab.
Я рекомендую использовать функцию SetWinEventHook, чтобы правильно получить информацию об активном отображении.
HWINEVENTHOOK SetWinEventHook(
DWORD eventMin,
DWORD eventMax,
HMODULE hmodWinEventProc,
WINEVENTPROC pfnWinEventProc,
DWORD idProcess,
DWORD idThread,
DWORD dwFlags
);
DWORD eventMin,
DWORD eventMax,
Достаточно указать в качестве аргументов константы EVENT_SYSTEM_FOREGROUND.
Я на самом деле получаю hwnd
s от SetWinEventHook
. В частности, я установил крючок для EVENT_SYSTEM_FOREGROUND
. Если я нажимаю alt-tab, окно переключается быстро, но обратный вызов запускается для окна переключателя задач и какого-либо другого невидимого окна с классом ForegroundStaging. В основном я хочу отфильтровать эти окна, но мне также нужно учитывать мошеннические процессы, которые пытаются маскироваться под ForegroundStaging и т. д.
Если я нажму alt-tab, окно быстро переключается, но обратный вызов запускается для окна Task Switcher и некоторых других невидимых окон с класс ForegroundStaging.
Для невидимых окон вы можете использовать IsWindowVisible для фильтрации.
Для окна переключателя задач вы можете сравнить их имена заголовков с фильтром.
Некоторый код:
void __stdcall Wineventproc(HWINEVENTHOOK hWinEventHook, DWORD event, HWND hwnd, LONG idObject, LONG idChild, DWORD idEventThread, DWORD dwmsEventTime)
{
if (event == EVENT_SYSTEM_FOREGROUND)
{
if (IsWindowVisible(hwnd))
{
TCHAR title[512] = {};
int index = GetWindowText(hwnd, title, 512);
if (_tcsncmp(title, TEXT("Task Switching"), 14))
{
title[index] = L'\n';
title[index + 1] = L'\0';
OutputDebugString(title);
}
}
}
}
но мне также нужно учитывать мошеннические процессы, которые пытаются маскироваться как ForegroundStaging и т. д.
Это сложный вопрос. Ни один антивирус или технология защиты не совершенны. Требуется время, чтобы выявить и заблокировать вредоносные сайты и приложения или доверять недавно выпущенным программам и сертификатам. При наличии почти 2 миллиардов веб-сайтов в Интернете и программного обеспечения, которое постоянно обновляется и выпускается, невозможно получить информацию о каждом отдельном сайте и программе.
Другими словами, непросто эффективно идентифицировать истинную личность каждого неизвестного приложения.
Я нашел работающее решение проблемы: дополнительно отфильтровать по пути процесса с помощью GetWindowModuleFileNameW.
грубый псевдокод:
if window.class() in [..] && GetWindowModuleFileNameW(window.hwnd) == "C:\Windows\explorer.exe" {
ignore()
}
Процессы не могут подделать свой путь, так что это работает.
Это хорошее решение, вы сравниваете заголовок «Переключение задач» и имя класса «XamlExplorerHostIslandWindow» — как насчет локализованных версий Windows, они остаются такими же, например, на японском Win11?
Заголовок окна обычно надежен, процессы могут легко его редактировать. Я помню, как проверял имена классов окон на французском языке, те, которые использует Windows, такие как Task Explorer, Windows Explorer и т. д., Все еще на английском языке. Возможно, из-за того, что имена классов обычно не выставляются пользователю. Имена классов также могут быть подделаны, поэтому приведенная выше проверка на использование GetWindowModuleFileNameW
используется как лучшая гарантия. Я не уверен насчет XamlExplorerHostIslandWindow, это имя класса для Explorer в Win11?
Да, я разрабатываю для Win11, так что там используется новое имя класса... Вы знаете, какое имя класса было для Win7?
Загляните в блог и попробуйте функцию
IsAltTabWindow
.