我有一段代码,它使用WinXP的SetForegroundWindow API将鼠标下的窗口置于前景。我已经测试了Vista,但是该API似乎不能正确完成任务。
AllowSetForeground没有帮助,我的进程是后台进程。
我应该使用什么来完成这个任务?
AllowSetForeground没有帮助,我的进程是后台进程。
我应该使用什么来完成这个任务?
尝试以下代码,看看它是否适用于您:
SetWindowPos(WndHandle,HWND_TOPMOST,0,0,0,0,SWP_NOMOVE | SWP_NOSIZE);
SetWindowPos(WndHandle,HWND_NOTOPMOST,0,0,0,0,SWP_SHOWWINDOW | SWP_NOMOVE | SWP_NOSIZE);
SetForegroundWindow()
失败了,你尝试过在调用SetForegroundWindow()
之后立即将窗口WS_EX_TOPMOST
设置为非最顶层吗? RECT rc;
m_pMainWnd->GetWindowRect(&rc);
int nBoxWidth = rc.left-rc.right;
int nBoxHeight = rc.bottom-rc.top;
int nBoxTop = rc.top;
int nBoxLeft = rc.left;
SetWindowPos(m_pMainWnd->GetSafeHwnd(), HWND_TOPMOST,
nBoxLeft, nBoxTop, nBoxWidth, nBoxHeight,
SWP_NOMOVE || SWP_NOSIZE);
SetWindowPos(m_pMainWnd->GetSafeHwnd(), HWND_NOTOPMOST,
nBoxLeft, nBoxTop, nBoxWidth, nBoxHeight,
SWP_SHOWWINDOW || SWP_NOMOVE || SWP_NOSIZE);
VOID SwitchToThisWindow(HWND hWnd, BOOL fAltTab);
适用于XP到Windows 7 http://msdn.microsoft.com/en-us/library/ms633553.aspx
将当前线程设置为睡眠状态,再将其设置为非最顶层的状态,这对我很有帮助:
OS.SetWindowPos(handle, OS.HWND_NOTOPMOST, 0, 0, 0, 0, OS.SWP_NOMOVE | OS.SWP_NOSIZE);
try {
Thread.sleep(100);
} catch (InterruptedException e) {
LOG.error("sleeping thread was interrupted", e);
}
OS.SetWindowPos(handle, OS.HWND_TOPMOST, 0, 0, 0, 0, OS.SWP_NOMOVE | OS.SWP_NOSIZE);
仅作警告:曾经有一个公共API可以做到这一点(SetForegroundWindow),但现在它不再将窗口置于前台。
现在窗口只会闪烁。
但这是有原因的。这样做的应用程序会从当前窗口“窃取”焦点(通常没有充分的理由),可能会导致各种问题。
因此,在尝试规避操作系统对此类行为的保护之前,请确保您不会惹恼您的用户。问问自己:“即使我的应用程序在后台,我真的需要跳到用户面前吗?”