2010-03-04 18 views
22

Ich habe ein Fenster, das ich SetWindowPos(window, HWND_TOP, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), SWP_FRAMECHANGED);Win32: Vollbild- und verstecken Taskleiste

den ganzen Bildschirm bedeckt, ok, aber es dauert eine Weile (0,5 sec), als auch die Taskleiste zu decken.

Gibt es eine Möglichkeit, sofort über die Taskleiste zu kommen? Ich fand diese Einstellung HWND_TOPMOST tut es sofort, aber es bleibt über allen anderen Fenstern, auch wenn ich die App wechseln - das ist etwas, was ich nicht will. Wenn ich das Fenster zum ersten Mal verberge und es dann zeige, zwingt es das Fenster irgendwie neu zu zeichnen und bedeckt die Taskleiste sofort, aber es flackert (wegen des Versteckens). Gibt es eine andere Art und Weise?

Antwort

34

Bearbeiten 2.Es gibt sogar einen besseren Weg, Vollbild zu tun, die Chrom Art und Weise, Quelle von hier genommen:

http://src.chromium.org/viewvc/chrome/trunk/src/ui/views/win/fullscreen_handler.cc?revision=HEAD&view=markup

bearbeiten. Es ist wahrscheinlich besser, ein Vollbild-Fenster zu erstellen, wie BrendanMcK es zu dieser Antwort in einem Kommentar darauf hingewiesen, finden Sie unter diesem Link: http://blogs.msdn.com/b/oldnewthing/archive/2005/05/05/414910.aspx („Wie kann ich die Taskleiste mit einem Vollbild-Fenster bedecken?“)

Der neue Code der Link oben wäre:

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); 
} 

Alte Antwort unten - verwenden sie es nicht, bleibt nur der Ordnung halber, wie dies nicht zu tun.

Sie müssen Taskleiste und Menüleiste ausblenden, um sofort Vollbild zu sehen. Hier

ist der Code (verwendet WTL), rufen SetFullScreen (true) gehen in den Vollbildmodus:

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); 
     }  
    } 
}; 

Sie müssen auch einige Code hinzufügen Nachricht WM_CLOSE:

case WM_CLOSE: 
    ShowTaskBar(true); 

Es gibt einen Vorbehalt mit dieser Lösung, wenn Ihre Anwendung abstürzt oder durch Task-Manager getötet wird, dann verliert Benutzer Taskleiste auf seinem System dauerhaft! (es sei denn, er führt die Anwendung erneut aus, geht in den Vollbildmodus und beendet sich, dann wird er die Taskleiste wieder sehen).

Früher in meiner Antwort, die ich zeigte auf „atlwince.h“, aber diese Funktion funktionierte nur unter Windows CE, die ich oben arbeitet mit XP, Vista und 7.

+2

-1 weil Sie nicht mit der Taskleiste herumspielen sollten; es ist nicht in erster Linie erforderlich; Den Blog von Raymond Chen finden Sie hier: [Wie bedecke ich die Taskleiste mit einem Vollbild-Fenster?] (http://blogs.msdn.com/b/oldnewthing/archive/2005/05/05/414910.aspx) – BrendanMcK

+0

@ BrendanMcK: Ich habe meine Antwort bearbeitet. Haben Sie einen guten Tag. –

+0

Awesome, -1 in +1 umgewandelt. (Eigentlich war ich ein bisschen zu schnell mit dieser -1 an erster Stelle; ich hätte den Kommentar zuerst abgeben sollen. Ich glaube, ich bin überempfindlich geworden, Windows-Hacks über die Jahre zu sehen -!) – BrendanMcK

-3
  1. Rechtsklick auf die Taskleiste
  2. Eigenschaften
  3. deaktivieren Sie das Kontrollkästchen wählen, die „Halten Sie die Taskleiste auf der anderen Fenstern“, sagt.

Die Taskleiste gehört zum Benutzer, es ist bis zu ihnen zu haben nehmen sie 1/2 Sekunde bis zum automatischen Ausblenden zu sorgen, wenn Sie app Vollbild gehen. Wenn sie dieses Verhalten ändern wollen, können sie es ändern.

Wenn Sie in einem eingebetteten System arbeiten, haben Sie möglicherweise einen legitimen Grund, die Taskleiste zu verbergen. Aber in diesem Fall gibt es keinen Grund, die Taskleiste nicht einfach so zu konfigurieren, dass sie nicht immer oben ist. Sie können auch einen Blick auf werfen, wenn Sie einige dieser Einstellungen in Ihrem Code ändern möchten.

+0

OK, und jedes Mal, wenn Sie ein Spiel starten, möchten Sie diese drei Schritte vorher durchführen und danach den alten Zustand wiederherstellen? "Ja wirklich?" – user2328447

+0

user2328447, trollst du? Der Zustand der Taskleiste wird ignoriert, wenn ein Spiel im Vollbildmodus läuft - also wäre es sowohl blöd als auch kaputt für Spiele, sich mit der Taskleiste herumzuärgern - aber sicher hast du das schon bemerkt .... –

+0

Im gefensterten Vollbild ist die Taskleiste NICHT ignoriert. Welches ist genau das, wonach das ursprüngliche Poster gefragt hat? Mehrere Spiele verwenden dies. – user2328447

1

Ich glaube, die Taskleiste wird aus dem Weg kommen, wenn ihr Shell-Hook es von einer "unhöflichen App" erzählt, das könnte eine Weile dauern.

Was ist, wenn Sie mit dem Fenster HWND_TOPMOST beginnen und es nach 1 Sekunde nicht ganz oben machen?

13

Yup, HWND_TOPMOST tut es für mich. Hier ist ein Codeabschnitt, der im Vollbildmodus arbeiten gut (und schnell) für mich macht:


bool enterFullscreen(HWND hwnd, int fullscreenWidth, int fullscreenHeight, int colourBits, int refreshRate) { 
    DEVMODE fullscreenSettings; 
    bool isChangeSuccessful; 
    RECT windowBoundary; 

    EnumDisplaySettings(NULL, 0, &fullscreenSettings); 
    fullscreenSettings.dmPelsWidth  = fullscreenWidth; 
    fullscreenSettings.dmPelsHeight  = fullscreenHeight; 
    fullscreenSettings.dmBitsPerPel  = colourBits; 
    fullscreenSettings.dmDisplayFrequency = refreshRate; 
    fullscreenSettings.dmFields   = DM_PELSWIDTH | 
              DM_PELSHEIGHT | 
              DM_BITSPERPEL | 
              DM_DISPLAYFREQUENCY; 

    SetWindowLongPtr(hwnd, GWL_EXSTYLE, WS_EX_APPWINDOW | WS_EX_TOPMOST); 
    SetWindowLongPtr(hwnd, GWL_STYLE, WS_POPUP | WS_VISIBLE); 
    SetWindowPos(hwnd, HWND_TOPMOST, 0, 0, fullscreenWidth, fullscreenHeight, SWP_SHOWWINDOW); 
    isChangeSuccessful = ChangeDisplaySettings(&fullscreenSettings, CDS_FULLSCREEN) == DISP_CHANGE_SUCCESSFUL; 
    ShowWindow(hwnd, SW_MAXIMIZE); 

    return isChangeSuccessful; 
} 

Beachten Sie, dass dies die Auflösung ändern, wenn Sie die falschen Einstellungen erzählen. Dies ist, was ich in der Regel wollen, aber wenn Sie das nicht möchten, können Sie Ihre Auflösung herausfinden, unter Verwendung von (wo mainWindow von so etwas wie CreateWindow() oder CreateWindowEx() zurückgegeben):


windowHDC = GetDC(mainWindow); 
fullscreenWidth = GetDeviceCaps(windowHDC, HORZRES); 
fullscreenHeight = GetDeviceCaps(windowHDC, VERTRES); 
colourBits  = GetDeviceCaps(windowHDC, BITSPIXEL); 
refreshRate  = GetDeviceCaps(windowHDC, VREFRESH); 

Wenn Sie aussteigen wollen Vollbild-tun Sie etwas wie folgt aus:


bool exitFullscreen(HWND hwnd, int windowW, int windowY, int windowedWidth, int windowedHeight, int windowedPaddingX, int windowedPaddingY) { 
    bool isChangeSuccessful; 

    SetWindowLongPtr(hwnd, GWL_EXSTYLE, WS_EX_LEFT); 
    SetWindowLongPtr(hwnd, GWL_STYLE, WS_OVERLAPPEDWINDOW | WS_VISIBLE); 
    isChangeSuccessful = ChangeDisplaySettings(NULL, CDS_RESET) == DISP_CHANGE_SUCCESSFUL; 
    SetWindowPos(hwnd, HWND_NOTOPMOST, windowX, windowY, windowedWidth + windowedPaddingX, windowedHeight + windowedPaddingY, SWP_SHOWWINDOW); 
    ShowWindow(hwnd, SW_RESTORE); 

    return isChangeSuccessful; 
} 

stelle ich meinen Code zwischen Vollbild- und fenster~~POS=TRUNC mit einem Hotkey, und ich halte die fenster~~POS=TRUNC Variablen als global zu ändern, so dass bei einem Wechsel zu fenster~~POS=TRUNC Modus bleibt es gesetzt.

Dieser Code hat auch den Vorteil, im Äquivalent von "exklusiven Modus" (ich benutze XP, und habe es nicht auf den neueren Versionen von Windows), was bedeutet, es wird viel, viel schneller. Lass mich wissen, wenn ich Fehler gemacht habe, wenn ich den Code verdichte (von meinem viel größeren Code).

+0

Danke für die Antwort. Ich denke, der Grund, warum es funktioniert, ist, dass Sie die Größe des Fensters mindestens zweimal ändern "SetWindowPos() und ShowWindow()" (Ich weiß nicht, dass "ChangeDisplaySettings()"). Das Problem ist, was passiert, wenn ich bereits in "SW_MAXIMIZE" bin und was im Vollbildmodus angezeigt wird? –

+0

Ich habe irgendwo gelesen, dass es einen "Cache" des Fenstermanagers gibt. Ich hatte also gehofft, dass es einen Weg gibt, es zu zwingen, es aufzufrischen oder es anderweitig zu sagen, dass es die Taskleiste darunter neu streichen sollte. –

+0

Mit anderen Worten, es scheint mir, dass "SW_MAXIMIZE" etwas neben der Größenanpassung tut und ich würde gerne wissen, was ... –