Некоторые люди не принимают близко к сердцу мои предупреждения о переключении очередей ввода - номер пять в списке вещей, которые должен знать любой Win32 программист. И тогда они обнаруживают, что их приложения перестают отвечать.
// Код в курсиве неверен procedure TryToStealFocus(const AWnd: HWND); var FGWnd: HWND; FGThread: DWORD; CurrentThread: DWORD; begin // Сначала пробуем простой SetForegroundWindow SetForegroundWindow(AWnd); FGWnd := GetForegroundWindow; if FGWnd = AWnd then Exit; // Это не сработало - если окно переднего плана принадлежит // другому потоку, то подключаемся к этому потоку и пробуем снова CurrentThread := GetCurrentThreadId; FGThread := GetWindowThreadProcessId(FGWnd, nil); if dwFGThread = CurrentThread then Exit; AttachThreadInput(CurrentThread, FGThread, True); SetForegroundWindow(AWnd); // <- зависает тут AttachThreadInput(CurrentThread, FGThread, False); end;Их данные использования от клиентов показали, что функция часто зависает на втором вызове
SetForegroundWindow
. Моё упражнение к вам: объяснить почему (а вот ещё один с такой же проблемой).(Заметьте, что оба человека пытаются обойти блокировку выскакивания окна на передний план, чтобы они могли плюнуть своим окном в лицо пользователя).
[i][b]"Заметьте, что оба человека пытаются обойти блокировку выскакивания окна на передний план, чтобы они могли плюнуть своим окном в лицо пользователя"[/b][/i]
ОтветитьУдалитьблин, а как же программа от хуавейчика это делает? да ещё и по нескольку раз - так настойчиво, что хочется её прибить. Авторы программ от модемов Huawei известны навязыванием окружающему миру своего стиля общения с компьютором. Одну из их повадок, выключение содержимого окон при перетаскивании, уже удалось побороть: достаточно прописать в куда-нибудь в автозапуск программулину с таким кодом SystemParametersInfo(SPI_SETDRAGFULLWINDOWS,Integer(true),nil,0) а вот со второй пока проблемы.
if WindowState = wsMinimized then
WindowState := wsNormal;
SetForegroundWindow(Handle);
Activate;