我有一个窗口,我SetWindowPos(window, HWND_TOP, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), SWP_FRAMECHANGED);
它覆盖了整个屏幕,确定,但是还需要一段时间(0.5秒)才能覆盖任务栏。
是否有一种方法可以立即通过任务栏?我发现设置HWND_TOPMOST
可以立即执行此操作,但是即使我切换了该应用程序,它仍然位于所有其他窗口之上-这是我不想要的。另外,如果我先隐藏窗口然后再显示它,它将以某种方式迫使窗口重新绘制并立即覆盖任务栏,但它会闪烁(由于隐藏)。还有其他方法吗?
Edit 2。还有一种更好的方法来进行全屏显示,铬的方式,取自这里:
。最好创建一个全屏窗口,因为BrendanMcK在对此答案的评论中指出了这一点,请参见以下链接:http://blogs.msdn.com/b/oldnewthing/archive/2005/05/05/414910.aspx(“如何用全屏窗口覆盖任务栏?”)void FullscreenHandler::SetFullscreenImpl(bool fullscreen, bool for_metro) { ScopedFullscreenVisibility visibility(hwnd_); // Save current window state if not already fullscreen. if (!fullscreen_) { // Save current window information. We force the window into restored mode // before going fullscreen because Windows doesn't seem to hide the // taskbar if the window is in the maximized state. saved_window_info_.maximized = !!::IsZoomed(hwnd_); if (saved_window_info_.maximized) ::SendMessage(hwnd_, WM_SYSCOMMAND, SC_RESTORE, 0); saved_window_info_.style = GetWindowLong(hwnd_, GWL_STYLE); saved_window_info_.ex_style = GetWindowLong(hwnd_, GWL_EXSTYLE); GetWindowRect(hwnd_, &saved_window_info_.window_rect); } fullscreen_ = fullscreen; if (fullscreen_) { // Set new window style and size. SetWindowLong(hwnd_, GWL_STYLE, saved_window_info_.style & ~(WS_CAPTION | WS_THICKFRAME)); SetWindowLong(hwnd_, GWL_EXSTYLE, saved_window_info_.ex_style & ~(WS_EX_DLGMODALFRAME | WS_EX_WINDOWEDGE | WS_EX_CLIENTEDGE | WS_EX_STATICEDGE)); // On expand, if we're given a window_rect, grow to it, otherwise do // not resize. if (!for_metro) { MONITORINFO monitor_info; monitor_info.cbSize = sizeof(monitor_info); GetMonitorInfo(MonitorFromWindow(hwnd_, MONITOR_DEFAULTTONEAREST), &monitor_info); gfx::Rect window_rect(monitor_info.rcMonitor); SetWindowPos(hwnd_, NULL, window_rect.x(), window_rect.y(), window_rect.width(), window_rect.height(), SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED); } } else { // Reset original window style and size. The multiple window size/moves // here are ugly, but if SetWindowPos() doesn't redraw, the taskbar won't be // repainted. Better-looking methods welcome. SetWindowLong(hwnd_, GWL_STYLE, saved_window_info_.style); SetWindowLong(hwnd_, GWL_EXSTYLE, saved_window_info_.ex_style); if (!for_metro) { // On restore, resize to the previous saved rect size. gfx::Rect new_rect(saved_window_info_.window_rect); SetWindowPos(hwnd_, NULL, new_rect.x(), new_rect.y(), new_rect.width(), new_rect.height(), SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED); } if (saved_window_info_.maximized) ::SendMessage(hwnd_, WM_SYSCOMMAND, SC_MAXIMIZE, 0); } }
编辑
使用上面的链接的新代码将是:
HWND CreateFullscreenWindow(HWND hwnd) { HMONITOR hmon = MonitorFromWindow(hwnd, MONITOR_DEFAULTTONEAREST); MONITORINFO mi = { sizeof(mi) }; if (!GetMonitorInfo(hmon, &mi)) return NULL; return CreateWindow(TEXT("static"), TEXT("something interesting might go here"), WS_POPUP | WS_VISIBLE, mi.rcMonitor.left, mi.rcMonitor.top, mi.rcMonitor.right - mi.rcMonitor.left, mi.rcMonitor.bottom - mi.rcMonitor.top, hwnd, NULL, g_hinst, 0); }
下面的旧答案-请勿使用,仅记录如何不执行此操作。
您必须隐藏任务栏和菜单栏才能立即查看全屏。
这里是代码(使用WTL),调用SetFullScreen(true)进入全屏模式:
template <class T, bool t_bHasSip = true> class CFullScreenFrame { public: bool m_fullscreen; LONG m_windowstyles; WINDOWPLACEMENT m_windowplacement; CFullScreenFrame() : m_fullscreen(false), m_windowstyles(0) { } void SetFullScreen(bool fullscreen) { ShowTaskBar(!fullscreen); T* pT = static_cast<T*>(this); if (fullscreen) { if (!m_fullscreen) { m_windowstyles = pT->GetWindowLongW(GWL_STYLE); pT->GetWindowPlacement(&m_windowplacement); } } // SM_CXSCREEN gives primary monitor, for multiple monitors use SM_CXVIRTUALSCREEN. RECT fullrect = { 0 }; SetRect(&fullrect, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN)); WINDOWPLACEMENT newplacement = m_windowplacement; newplacement.showCmd = SW_SHOWNORMAL; newplacement.rcNormalPosition = fullrect; if (fullscreen) { pT->SetWindowPlacement(&newplacement); pT->SetWindowLongW(GWL_STYLE, WS_VISIBLE); pT->UpdateWindow(); } else { if (m_fullscreen) { pT->SetWindowPlacement(&m_windowplacement); pT->SetWindowLongW(GWL_STYLE, m_windowstyles); pT->UpdateWindow(); } } m_fullscreen = fullscreen; } void ShowTaskBar(bool show) { HWND taskbar = FindWindow(_T("Shell_TrayWnd"), NULL); HWND start = FindWindow(_T("Button"), NULL); if (taskbar != NULL) { ShowWindow(taskbar, show ? SW_SHOW : SW_HIDE); UpdateWindow(taskbar); } if (start != NULL) { // Vista ShowWindow(start, show ? SW_SHOW : SW_HIDE); UpdateWindow(start); } } };
您还必须在WM_CLOSE消息中添加一些代码:
case WM_CLOSE: ShowTaskBar(true);
此解决方案有一个警告,如果您的应用程序崩溃或通过任务管理器被杀死,那么用户将永久失去其系统上的任务栏! (除非他再次运行您的应用程序,进入全屏并退出,然后他将再次看到任务栏)。
在我的回答中,我之前指向“ atlwince.h”,但该功能仅在Windows CE上有效,我上面粘贴的功能在XP,Vista和7上都可以正常工作。
是,HWND_TOPMOST
为我做了。这是一段代码,可以让我全屏(并且快速)工作:
[Raymond Chen在他的博客中描述了执行此操作的“正确”方法:
[我相信任务栏在其外壳挂钩告诉它“粗鲁的应用程序”时会避开它,这可能需要一些时间。