Index: /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineLogicFullscreen.cpp
===================================================================
--- /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineLogicFullscreen.cpp	(revision 50678)
+++ /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineLogicFullscreen.cpp	(revision 50679)
@@ -30,4 +30,5 @@
 # include "UIExtraDataEventHandler.h"
 # include "VBoxUtils.h"
+# include "UIFrameBuffer.h"
 # include <Carbon/Carbon.h>
 #endif /* Q_WS_MAC */
@@ -35,7 +36,4 @@
 UIMachineLogicFullscreen::UIMachineLogicFullscreen(QObject *pParent, UISession *pSession)
     : UIMachineLogic(pParent, pSession, UIVisualStateType_Fullscreen)
-#ifdef Q_WS_MAC
-    , m_fIsFullscreenInvalidated(false)
-#endif /* Q_WS_MAC */
 {
     /* Create multiscreen layout: */
@@ -129,31 +127,30 @@
     Q_UNUSED(fResult);
 
-    /* If there is/are still fullscreen window(s) present: */
-    if (!m_fullscreenMachineWindows.isEmpty())
-    {
-        /* Exit fullscreen mode if it was not invalidated yet: */
-        if (!m_fIsFullscreenInvalidated)
+    /* If that window was invalidated: */
+    if (m_invalidFullscreenMachineWindows.contains(pMachineWindow))
+    {
+        LogRel(("UIMachineLogicFullscreen::sltHandleNativeFullscreenDidExit: "
+                "Machine-window #%d exited invalidated fullscreen, revalidate it.\n",
+                (int)pMachineWindow->screenId()));
+
+        /* Exclude window from invalidation list: */
+        m_invalidFullscreenMachineWindows.remove(pMachineWindow);
+
+        /* Revalidate 'fullscreen' window: */
+        revalidateFullscreenWindow(pMachineWindow);
+    }
+    /* If there are no invalidated windows: */
+    else if (m_invalidFullscreenMachineWindows.isEmpty())
+    {
+        /* If there are 'fullscreen' windows: */
+        if (!m_fullscreenMachineWindows.isEmpty())
+        {
+            LogRel(("UIMachineLogicFullscreen::sltHandleNativeFullscreenDidExit: "
+                    "Machine-window exited fullscreen, asking others to exit too...\n"));
+
+            /* Ask window(s) to exit 'fullscreen' mode: */
             emit sigNotifyAboutNativeFullscreenShouldBeExited();
-    }
-    /* If there is/are no more fullscreen window(s) left: */
-    else
-    {
-        /* If fullscreen mode was just invalidated: */
-        if (m_fIsFullscreenInvalidated)
-        {
-            LogRel(("UIMachineLogicFullscreen::sltHandleNativeFullscreenDidExit: "
-                    "Machine-window(s) exited invalidated fullscreen, enter again...\n"));
-
-            /* Mark fullscreen mode valid again: */
-            m_fIsFullscreenInvalidated = false;
-            /* Reactivate 'presentation mode': */
-            setPresentationModeEnabled(true);
-            /* Make sure all machine-window(s) have proper geometry: */
-            foreach (UIMachineWindow *pMachineWindow, machineWindows())
-                pMachineWindow->showInNecessaryMode();
-            /* Ask all window(s) to re-enter fullscreen mode: */
-            emit sigNotifyAboutNativeFullscreenShouldBeEntered();
-        }
-        /* If fullscreen mode was manually exited: */
+        }
+        /* If there are no 'fullscreen' windows: */
         else
         {
@@ -181,5 +178,5 @@
         /* Request 'normal' (window) visual-state: */
         uisession()->setRequestedVisualState(UIVisualStateType_Normal);
-        /* Ask all window(s) to exit fullscreen mode: */
+        /* Ask window(s) to exit 'fullscreen' mode: */
         emit sigNotifyAboutNativeFullscreenShouldBeExited();
     }
@@ -196,5 +193,5 @@
         /* Request 'seamless' visual-state: */
         uisession()->setRequestedVisualState(UIVisualStateType_Seamless);
-        /* Ask all window(s) to exit fullscreen mode: */
+        /* Ask window(s) to exit 'fullscreen' mode: */
         emit sigNotifyAboutNativeFullscreenShouldBeExited();
     }
@@ -211,5 +208,5 @@
         /* Request 'scale' visual-state: */
         uisession()->setRequestedVisualState(UIVisualStateType_Scale);
-        /* Ask all window(s) to exit fullscreen mode: */
+        /* Ask window(s) to exit 'fullscreen' mode: */
         emit sigNotifyAboutNativeFullscreenShouldBeExited();
     }
@@ -248,4 +245,6 @@
 void UIMachineLogicFullscreen::sltScreenLayoutChanged()
 {
+    LogRel(("UIMachineLogicFullscreen: Multi-screen layout changed.\n"));
+
 #ifdef Q_WS_MAC
     /* For Lion and previous: */
@@ -258,13 +257,6 @@
         setPresentationModeEnabled(true);
     }
-    /* Invalidate fullscreen mode for ML and next: */
-    else if (shouldWeInvalidateFullscreenMode())
-        invalidateFullscreenMode();
-    else
-    {
-        /* Make sure all machine-window(s) have proper geometry: */
-        foreach (UIMachineWindow *pMachineWindow, machineWindows())
-            pMachineWindow->showInNecessaryMode();
-    }
+    /* Revalidate 'fullscreen' windows for ML and next: */
+    else revalidateFullscreenWindows();
 #else /* !Q_WS_MAC */
     /* Make sure all machine-window(s) have proper geometry: */
@@ -276,5 +268,5 @@
 void UIMachineLogicFullscreen::sltGuestMonitorChange(KGuestMonitorChangedEventType changeType, ulong uScreenId, QRect screenGeo)
 {
-    LogRelFlow(("UIMachineLogicFullscreen: Guest-screen count changed.\n"));
+    LogRel(("UIMachineLogicFullscreen: Guest-screen count changed.\n"));
 
     /* Update multi-screen layout before any window update: */
@@ -287,9 +279,6 @@
     if (vboxGlobal().osRelease() <= MacOSXRelease_Lion)
         UIMachineLogic::sltGuestMonitorChange(changeType, uScreenId, screenGeo);
-    /* Invalidate fullscreen mode for ML and next: */
-    else if (shouldWeInvalidateFullscreenMode())
-        invalidateFullscreenMode();
-    /* Call to base-class otherwise: */
-    else UIMachineLogic::sltGuestMonitorChange(changeType, uScreenId, screenGeo);
+    /* Revalidate 'fullscreen' windows for ML and next: */
+    else revalidateFullscreenWindows();
 #else /* !Q_WS_MAC */
     /* Call to base-class: */
@@ -300,5 +289,5 @@
 void UIMachineLogicFullscreen::sltHostScreenCountChanged()
 {
-    LogRelFlow(("UIMachineLogicFullscreen: Host-screen count changed.\n"));
+    LogRel(("UIMachineLogicFullscreen: Host-screen count changed.\n"));
 
     /* Update multi-screen layout before any window update: */
@@ -309,9 +298,6 @@
     if (vboxGlobal().osRelease() <= MacOSXRelease_Lion)
         UIMachineLogic::sltHostScreenCountChanged();
-    /* Invalidate fullscreen mode for ML and next: */
-    else if (shouldWeInvalidateFullscreenMode())
-        invalidateFullscreenMode();
-    /* Call to base-class otherwise: */
-    else UIMachineLogic::sltHostScreenCountChanged();
+    /* Revalidate 'fullscreen' windows for ML and next: */
+    else revalidateFullscreenWindows();
 #else /* !Q_WS_MAC */
     /* Call to base-class: */
@@ -397,8 +383,8 @@
         {
             /* Logic => window signals: */
-            connect(this, SIGNAL(sigNotifyAboutNativeFullscreenShouldBeEntered()),
-                    pMachineWindow, SLOT(sltEnterNativeFullscreen()));
-            connect(this, SIGNAL(sigNotifyAboutNativeFullscreenShouldBeExited()),
-                    pMachineWindow, SLOT(sltExitNativeFullscreen()));
+            connect(this, SIGNAL(sigNotifyAboutNativeFullscreenShouldBeEntered(UIMachineWindow*)),
+                    pMachineWindow, SLOT(sltEnterNativeFullscreen(UIMachineWindow*)));
+            connect(this, SIGNAL(sigNotifyAboutNativeFullscreenShouldBeExited(UIMachineWindow*)),
+                    pMachineWindow, SLOT(sltExitNativeFullscreen(UIMachineWindow*)));
             /* Window => logic signals: */
             connect(pMachineWindow, SIGNAL(sigNotifyAboutNativeFullscreenDidEnter()),
@@ -407,6 +393,6 @@
                     this, SLOT(sltHandleNativeFullscreenDidExit()));
         }
-        /* Ask all window(s) to enter fullscreen mode: */
-        emit sigNotifyAboutNativeFullscreenShouldBeEntered();
+        /* Revalidate 'fullscreen' windows: */
+        revalidateFullscreenWindows();
     }
 #endif /* Q_WS_MAC */
@@ -513,65 +499,91 @@
 }
 
-bool UIMachineLogicFullscreen::shouldWeInvalidateFullscreenMode() const
-{
-    /* Enumerate windows: */
+void UIMachineLogicFullscreen::revalidateFullscreenWindow(UIMachineWindow *pMachineWindow)
+{
+    LogRel(("UIMachineLogicFullscreen::revalidateFullscreenWindow #%d begin.\n", pMachineWindow->screenId()));
+
+    /* Make sure window is not already invalidated: */
+    if (m_invalidFullscreenMachineWindows.contains(pMachineWindow))
+        return;
+
+    /* Ignore window if it is in 'fullscreen transition': */
+    if (qobject_cast<UIMachineWindowFullscreen*>(pMachineWindow)->isInFullscreenTransition())
+        return;
+
+    /* Get screen ID: */
+    ulong uScreenID = pMachineWindow->screenId();
+
+    /* Validate window which can't be fullscreen: */
+    if (uScreenID != 0 && !darwinScreensHaveSeparateSpaces())
+    {
+        /* Make sure window have proper geometry: */
+        pMachineWindow->showInNecessaryMode();
+    }
+    /* Validate window which can be fullscreen: */
+    else
+    {
+        /* Validate window which is not in fullscreen: */
+        if (!darwinIsInFullscreenMode(pMachineWindow))
+        {
+            /* If that window
+             * 1. should really be shown and
+             * 2. is mapped to some host-screen: */
+            if (   uisession()->isScreenVisible(uScreenID)
+                && hasHostScreenForGuestScreen(uScreenID))
+            {
+                LogRel(("UIMachineLogicFullscreen::revalidateFullscreenWindow: "
+                        "Ask machine-window #%d to enter fullscreen.\n", (int)uScreenID));
+
+                /* Update 'presentation mode': */
+                setPresentationModeEnabled(true);
+
+                /* Make sure window have proper geometry and shown: */
+                pMachineWindow->showInNecessaryMode();
+
+                /* Ask window to enter 'fullscreen' mode: */
+                emit sigNotifyAboutNativeFullscreenShouldBeEntered(pMachineWindow);
+            }
+            /* Else make sure that window is hidden: */
+            else pMachineWindow->showInNecessaryMode();
+        }
+        /* Validate window which is in fullscreen: */
+        else
+        {
+            /* Variables to compare: */
+            const int iWantedHostScreenIndex = hostScreenForGuestScreen((int)uScreenID);
+            const int iCurrentHostScreenIndex = QApplication::desktop()->screenNumber(pMachineWindow);
+            const QSize frameBufferSize((int)uisession()->frameBuffer(uScreenID)->width(), (int)uisession()->frameBuffer(uScreenID)->height());
+            const QSize screenSize = QApplication::desktop()->screenGeometry(iWantedHostScreenIndex).size();
+
+            /* If that window
+             * 1. shouldn't really be shown or
+             * 2. isn't mapped to some host-screen or
+             * 3. should be located on another host-screen than currently or
+             * 4. have another frame-buffer size than actually should. */
+            if (   !uisession()->isScreenVisible(uScreenID)
+                || !hasHostScreenForGuestScreen(uScreenID)
+                || iWantedHostScreenIndex != iCurrentHostScreenIndex
+                || frameBufferSize != screenSize)
+            {
+                LogRel(("UIMachineLogicFullscreen::revalidateFullscreenWindow: "
+                        "Ask machine-window #%d to exit fullscreen.\n", (int)uScreenID));
+
+                /* Mark window as invalidated: */
+                m_invalidFullscreenMachineWindows << pMachineWindow;
+
+                /* Ask window to exit 'fullscreen' mode: */
+                emit sigNotifyAboutNativeFullscreenShouldBeExited(pMachineWindow);
+            }
+        }
+    }
+
+    LogRel(("UIMachineLogicFullscreen::revalidateFullscreenWindow #%d end.\n", pMachineWindow->screenId()));
+}
+
+void UIMachineLogicFullscreen::revalidateFullscreenWindows()
+{
+    /* Revalidate all fullscreen windows: */
     foreach (UIMachineWindow *pMachineWindow, machineWindows())
-    {
-        /* Cast to 'fullscreen' window: */
-        UIMachineWindowFullscreen *pFullscreenMachineWindow =
-            qobject_cast<UIMachineWindowFullscreen*>(pMachineWindow);
-        /* Ignore window(s) which are in 'fullscreen transition': */
-        if (pFullscreenMachineWindow->isInFullscreenTransition())
-            continue;
-
-        /* Get screen ID: */
-        ulong uScreenID = pMachineWindow->screenId();
-        /* Check window which can be fullscreen: */
-        if (uScreenID == 0 || darwinScreensHaveSeparateSpaces())
-        {
-            /* Check window which is not in fullscreen: */
-            if (!darwinIsInFullscreenMode(pMachineWindow))
-            {
-                /* Check if that window should really
-                 * be shown and is mapped to some host-screen: */
-                if (   uisession()->isScreenVisible(uScreenID)
-                    && hasHostScreenForGuestScreen(uScreenID))
-                    return true;
-            }
-            /* Check window which is in fullscreen: */
-            else
-            {
-                /* Check if that window shouldn't really
-                 * be shown or isn't mapped to some host-screen: */
-                if (   !uisession()->isScreenVisible(uScreenID)
-                    || !hasHostScreenForGuestScreen(uScreenID))
-                    return true;
-                /* Check if that window should be located
-                 * on another host-screen than currently. */
-                if (hostScreenForGuestScreen((int)uScreenID) !=
-                    QApplication::desktop()->screenNumber(pMachineWindow))
-                    return true;
-            }
-        }
-    }
-
-    /* False by default: */
-    return false;
-}
-
-void UIMachineLogicFullscreen::invalidateFullscreenMode()
-{
-    /* Make sure 'fullscreen' mode is not invalidated yet: */
-    if (m_fIsFullscreenInvalidated)
-        return;
-
-    LogRel(("UIMachineLogicFullscreen::invalidateFullscreenMode: "
-            "Fullscreen mode invalidated...\n"));
-
-    /* Mark 'fullscreen' mode as invalidated: */
-    m_fIsFullscreenInvalidated = true;
-
-    /* Ask all window(s) to exit fullscreen mode: */
-    emit sigNotifyAboutNativeFullscreenShouldBeExited();
+        revalidateFullscreenWindow(pMachineWindow);
 }
 #endif /* Q_WS_MAC */
Index: /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineLogicFullscreen.h
===================================================================
--- /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineLogicFullscreen.h	(revision 50678)
+++ /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineLogicFullscreen.h	(revision 50679)
@@ -31,8 +31,8 @@
 #ifdef RT_OS_DARWIN
 signals:
-    /** Mac OS X: Notifies listener about native fullscreen mode should be entered. */
-    void sigNotifyAboutNativeFullscreenShouldBeEntered();
-    /** Mac OS X: Notifies listener about native fullscreen mode should be exited. */
-    void sigNotifyAboutNativeFullscreenShouldBeExited();
+    /** Mac OS X: Notifies listeners about native fullscreen mode should be entered on @a pMachineWindow. */
+    void sigNotifyAboutNativeFullscreenShouldBeEntered(UIMachineWindow *pMachineWindow = 0);
+    /** Mac OS X: Notifies listeners about native fullscreen mode should be exited on @a pMachineWindow. */
+    void sigNotifyAboutNativeFullscreenShouldBeExited(UIMachineWindow *pMachineWindow = 0);
 #endif /* RT_OS_DARWIN */
 
@@ -104,8 +104,8 @@
     void setPresentationModeEnabled(bool fEnabled);
 
-    /** Mac OS X: Checks if 'fullscreen' mode should be invalidated. */
-    bool shouldWeInvalidateFullscreenMode() const;
-    /** Mac OS X: Invalidates 'fullscreen' mode. */
-    void invalidateFullscreenMode();
+    /** Mac OS X: Revalidates 'fullscreen' mode for @a pMachineWindow. */
+    void revalidateFullscreenWindow(UIMachineWindow *pMachineWindow);
+    /** Mac OS X: Revalidates 'fullscreen' mode for all windows. */
+    void revalidateFullscreenWindows();
 #endif /* Q_WS_MAC */
 
@@ -116,6 +116,6 @@
     /** Mac OS X: Contains machine-window(s) marked as 'fullscreen'. */
     QSet<UIMachineWindow*> m_fullscreenMachineWindows;
-    /** Mac OS X: Holds 'fullscreen' mode invalidation status. */
-    bool m_fIsFullscreenInvalidated;
+    /** Mac OS X: Contains machine-window(s) marked as 'invalid fullscreen'. */
+    QSet<UIMachineWindow*> m_invalidFullscreenMachineWindows;
 #endif /* Q_WS_MAC */
 
Index: /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineWindowFullscreen.cpp
===================================================================
--- /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineWindowFullscreen.cpp	(revision 50678)
+++ /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineWindowFullscreen.cpp	(revision 50679)
@@ -101,8 +101,12 @@
 
 #ifdef Q_WS_MAC
-void UIMachineWindowFullscreen::sltEnterNativeFullscreen()
+void UIMachineWindowFullscreen::sltEnterNativeFullscreen(UIMachineWindow *pMachineWindow)
 {
     /* Make sure this slot is called only under ML and next: */
     AssertReturnVoid(vboxGlobal().osRelease() > MacOSXRelease_Lion);
+
+    /* Make sure it is NULL or 'this' window passed: */
+    if (pMachineWindow && pMachineWindow != this)
+        return;
 
     /* Make sure this window should be shown at all: */
@@ -128,8 +132,12 @@
 }
 
-void UIMachineWindowFullscreen::sltExitNativeFullscreen()
+void UIMachineWindowFullscreen::sltExitNativeFullscreen(UIMachineWindow *pMachineWindow)
 {
     /* Make sure this slot is called only under ML and next: */
     AssertReturnVoid(vboxGlobal().osRelease() > MacOSXRelease_Lion);
+
+    /* Make sure it is NULL or 'this' window passed: */
+    if (pMachineWindow && pMachineWindow != this)
+        return;
 
     /* Mark window 'transitioned from fullscreen': */
Index: /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineWindowFullscreen.h
===================================================================
--- /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineWindowFullscreen.h	(revision 50678)
+++ /trunk/src/VBox/Frontends/VirtualBox/src/runtime/fullscreen/UIMachineWindowFullscreen.h	(revision 50679)
@@ -60,8 +60,8 @@
 
 #ifdef RT_OS_DARWIN
-    /** Mac OS X: Commands window to enter native 'fullscreen' mode if possible. */
-    void sltEnterNativeFullscreen();
-    /** Mac OS X: Commands window to exit native 'fullscreen' mode if possible. */
-    void sltExitNativeFullscreen();
+    /** Mac OS X: Commands @a pMachineWindow to enter native 'fullscreen' mode if possible. */
+    void sltEnterNativeFullscreen(UIMachineWindow *pMachineWindow);
+    /** Mac OS X: Commands @a pMachineWindow to exit native 'fullscreen' mode if possible. */
+    void sltExitNativeFullscreen(UIMachineWindow *pMachineWindow);
 #endif /* RT_OS_DARWIN */
 
