Index: trunk/src/VBox/Frontends/VirtualBox/include/VBoxConsoleView.h
===================================================================
--- trunk/src/VBox/Frontends/VirtualBox/include/VBoxConsoleView.h	(revision 9028)
+++ trunk/src/VBox/Frontends/VirtualBox/include/VBoxConsoleView.h	(revision 9036)
@@ -98,5 +98,5 @@
     void fixModifierState (LONG *codes, uint *count);
 
-    void toggleFSMode();
+    void toggleFSMode (const QSize &aSize = QSize());
 
     void setIgnoreMainwndResize (bool aYes) { mIgnoreMainwndResize = aYes; }
@@ -249,5 +249,4 @@
 
     QTimer *resize_hint_timer;
-    QTimer *mToggleFSModeTimer;
 
     VBoxDefs::RenderMode mode;
Index: trunk/src/VBox/Frontends/VirtualBox/include/VBoxConsoleWnd.h
===================================================================
--- trunk/src/VBox/Frontends/VirtualBox/include/VBoxConsoleWnd.h	(revision 9028)
+++ trunk/src/VBox/Frontends/VirtualBox/include/VBoxConsoleWnd.h	(revision 9036)
@@ -190,8 +190,6 @@
     void dbgLoggingToggled (bool);
 
-    void onEnterFullscreen();
     void onExitFullscreen();
-    void exitFullscreen();
-    void exitSeamless();
+    void unlockActionsSwitch();
 
     void setViewInSeamlessMode (const QRect &aTargetRect);
@@ -329,4 +327,5 @@
     bool mIsSeamlessSupported : 1;
     bool mIsGraphicsSupported : 1;
+    bool mIsWaitingModeResize : 1;
     int normal_wflags;
     bool was_max : 1;
Index: trunk/src/VBox/Frontends/VirtualBox/src/VBoxConsoleView.cpp
===================================================================
--- trunk/src/VBox/Frontends/VirtualBox/src/VBoxConsoleView.cpp	(revision 9028)
+++ trunk/src/VBox/Frontends/VirtualBox/src/VBoxConsoleView.cpp	(revision 9036)
@@ -684,10 +684,4 @@
              this, SLOT (doResizeHint()));
 
-    /* This timer is used as 'last resort' which toggles f/s mode
-       in case of guest additions are not responding. */
-    mToggleFSModeTimer = new QTimer (this);
-    connect (mToggleFSModeTimer, SIGNAL (timeout()),
-             this, SIGNAL (resizeHintDone()));
-
     /* setup rendering */
 
@@ -783,5 +777,5 @@
         setDesktopGeometry (DesktopGeo_Fixed, width, height);
     }
-    connect (QApplication::desktop(), SIGNAL (workAreaResized (int)),
+    connect (QApplication::desktop(), SIGNAL (resized (int)),
              this, SLOT (doResizeDesktop (int)));
 
@@ -1071,7 +1065,4 @@
                 LogFlow (("VBoxDefs::ResizeEventType: %d x %d x %d bpp\n",
                           re->width(), re->height(), re->bitsPerPixel()));
-
-                if (mToggleFSModeTimer->isActive())
-                    mToggleFSModeTimer->stop();
 
                 /* do frame buffer dependent resize */
@@ -2251,13 +2242,13 @@
  *  Called on enter/exit seamless/fullscreen mode.
  */
-void VBoxConsoleView::toggleFSMode()
+void VBoxConsoleView::toggleFSMode (const QSize &aSize)
 {
     if ((mIsAdditionsActive && mAutoresizeGuest) ||
         mMainWnd->isTrueFullscreen())
     {
-        QSize newSize = QSize();
-        if (mMainWnd->isTrueFullscreen() || mMainWnd->isTrueSeamless())
-        {
-            mNormalSize = frameSize();
+        QSize newSize;
+        if (aSize.isValid())
+        {
+            mNormalSize = aSize;
             newSize = maximumSize();
         }
@@ -2266,15 +2257,4 @@
         doResizeHint (newSize);
     }
-    /* Currently there is 2000 msec pause before timer transfers
-     * console into desired mode "if GA are active and auto-resize
-     * feature enabled" and 100 msec pause before it transfers
-     * console into this mode "if GA are not active or auto-resize
-     * feature disabled". 100 msec pause required for resizing
-     * before normalizing geometry. */
-    mToggleFSModeTimer->start (mIsAdditionsActive && mAutoresizeGuest ?
-        2000 : 100, true);
-
-    /// @todo (r=dsen) perform roll-back after 'entering' mode in case
-    //                 we got no resizing response from the guest.
 }
 
Index: trunk/src/VBox/Frontends/VirtualBox/src/VBoxConsoleWnd.cpp
===================================================================
--- trunk/src/VBox/Frontends/VirtualBox/src/VBoxConsoleWnd.cpp	(revision 9028)
+++ trunk/src/VBox/Frontends/VirtualBox/src/VBoxConsoleWnd.cpp	(revision 9036)
@@ -122,4 +122,5 @@
     , mIsSeamlessSupported (false)
     , mIsGraphicsSupported (false)
+    , mIsWaitingModeResize (false)
     , normal_wflags (getWFlags())
     , was_max (false)
@@ -1034,35 +1035,4 @@
 
 /**
- *  This slot is called just after entering the fullscreen/seamless mode,
- *  when the console was resized to required size.
- */
-void VBoxConsoleWnd::onEnterFullscreen()
-{
-    disconnect (console, SIGNAL (resizeHintDone()), 0, 0);
-    /* It isn't guaranteed that the guest os set the video mode that
-     * we requested. So after all the resizing stuff set the clipping
-     * mask and the spacing shifter to the corresponding values. */
-    setViewInSeamlessMode (QRect (console->mapToGlobal (QPoint (0, 0)), console->size()));
-#ifdef Q_WS_MAC
-    if (!mIsSeamless)
-    {
-        /* Fade back to the normal gamma */
-        CGDisplayFade (mFadeToken, 0.5, kCGDisplayBlendSolidColor, kCGDisplayBlendNormal, 0.0, 0.0, 0.0, false);
-        CGReleaseDisplayFadeReservation (mFadeToken);
-    }
-#endif
-
-    vmSeamlessAction->setEnabled (mIsSeamless);
-    vmFullscreenAction->setEnabled (mIsFullscreen);
-    if (mIsSeamless)
-        connect (console, SIGNAL (resizeHintDone()),
-                 this, SLOT (exitSeamless()));
-    /* disabled for now */
-    //else if (mIsFullscreen)
-    //    connect (console, SIGNAL (resizeHintDone()),
-    //             this, SLOT (exitFullscreen()));
-}
-
-/**
  *  This slot is called just after leaving the fullscreen/seamless mode,
  *  when the console was resized to previous size.
@@ -1070,5 +1040,19 @@
 void VBoxConsoleWnd::onExitFullscreen()
 {
-    disconnect (console, SIGNAL (resizeHintDone()), 0, 0);
+    console->setIgnoreMainwndResize (false);
+}
+
+void VBoxConsoleWnd::unlockActionsSwitch()
+{
+    if (mIsSeamless)
+        vmSeamlessAction->setEnabled (true);
+    else if (mIsFullscreen)
+        vmFullscreenAction->setEnabled (true);
+    else
+    {
+        vmSeamlessAction->setEnabled (mIsSeamlessSupported && mIsGraphicsSupported);
+        vmFullscreenAction->setEnabled (true);
+    }
+
 #ifdef Q_WS_MAC
     if (!mIsSeamless)
@@ -1079,31 +1063,4 @@
     }
 #endif
-
-    vmSeamlessAction->setEnabled (mIsSeamlessSupported && mIsGraphicsSupported);
-    vmFullscreenAction->setEnabled (true);
-
-    console->setIgnoreMainwndResize (false);
-    console->normalizeGeometry (true /* adjustPosition */);
-}
-
-/**
- *  This slot is called if the guest changes resolution while in fullscreen
- *  mode.
- */
-void VBoxConsoleWnd::exitFullscreen()
-{
-    Assert (0); /* disabled for now */
-    if (mIsFullscreen && vmFullscreenAction->isEnabled())
-        vmFullscreenAction->toggle();
-}
-
-/**
- *  This slot is called if the guest changes resolution while in seamless
- *  mode.
- */
-void VBoxConsoleWnd::exitSeamless()
-{
-    if (mIsSeamless && vmSeamlessAction->isEnabled())
-        vmSeamlessAction->toggle();
 }
 
@@ -1158,5 +1115,6 @@
             QResizeEvent *re = (QResizeEvent *) e;
 
-            if (!isMaximized() && !isTrueFullscreen() && !isTrueSeamless())
+            if (!mIsWaitingModeResize && !isMaximized() &&
+                !isTrueFullscreen() && !isTrueSeamless())
             {
                 normal_size = re->size();
@@ -1164,4 +1122,13 @@
                 dbgAdjustRelativePos();
 #endif
+            }
+
+            if (mIsWaitingModeResize)
+            {
+                if (!mIsFullscreen && !mIsSeamless)
+                {
+                    mIsWaitingModeResize = false;
+                    QTimer::singleShot (0, this, SLOT (onExitFullscreen()));
+                }
             }
             break;
@@ -1975,6 +1942,5 @@
 bool VBoxConsoleWnd::toggleFullscreenMode (bool aOn, bool aSeamless)
 {
-    disconnect (console, SIGNAL (resizeHintDone()), 0, 0);
-    /* Check if the Guest Video RAM enough for the fullscreen/seamless mode. */
+    QSize initialSize = size();
     if (aSeamless || console->isAutoresizeGuestActive())
     {
@@ -2073,14 +2039,19 @@
     bool wasHidden = isHidden();
 
+    /* Temporarily disable the mode-related action to make sure
+     * user can not leave the mode before he enter it and inside out. */
+    aSeamless ? vmSeamlessAction->setEnabled (false) :
+                vmFullscreenAction->setEnabled (false);
+
+    /* Calculate initial console size */
+    QSize consoleSize;
+
     if (aOn)
     {
-        /* Temporarily disable the mode-related action to make sure
-         * user can not leave the mode before he enter it. */
-        aSeamless ? vmSeamlessAction->setEnabled (false) :
-                    vmFullscreenAction->setEnabled (false);
+        consoleSize = console->frameSize();
+        consoleSize -= QSize (console->frameWidth() * 2, console->frameWidth() * 2);
+
         /* Toggle console to manual resize mode. */
         console->setIgnoreMainwndResize (true);
-        connect (console, SIGNAL (resizeHintDone()),
-                 this, SLOT (onEnterFullscreen()));
 
         /* Memorize the maximized state. */
@@ -2104,5 +2075,6 @@
          * we requested. So after all the resizing stuff set the clipping
          * mask and the spacing shifter to the corresponding values. */
-        setViewInSeamlessMode (dtw->availableGeometry (this));
+        if (aSeamless)
+            setViewInSeamlessMode (scrGeo);
 
 #ifdef Q_WS_WIN32
@@ -2145,6 +2117,4 @@
         console->setHScrollBarMode (QScrollView::AlwaysOff);
 
-        /* Going fullscreen */
-        setWindowState (windowState() ^ WindowFullScreen);
 #ifdef Q_WS_MAC /* setMask seems to not include the far border pixels. */
 //        QRect maskRect = dtw->screenGeometry (this);
@@ -2180,18 +2150,8 @@
 //        setMask (dtw->screenGeometry (this));
 #endif
-
-        qApp->processEvents();
-        console->toggleFSMode();
     }
     else
     {
-        /* Temporarily disable the mode-related action to make sure
-         * user can not enter the mode before he leave it. */
-        aSeamless ? vmSeamlessAction->setEnabled (false) :
-                    vmFullscreenAction->setEnabled (false);
-        /* Toggle console to manual resize mode. */
-        connect (console, SIGNAL (resizeHintDone()), this, SLOT (onExitFullscreen()));
-
-        /* Reset the shifting spacer. */
+        /* Reset the shifting spacers. */
         mShiftingSpacerLeft->changeSize (0, 0, QSizePolicy::Fixed, QSizePolicy::Fixed);
         mShiftingSpacerTop->changeSize (0, 0, QSizePolicy::Fixed, QSizePolicy::Fixed);
@@ -2236,11 +2196,23 @@
             ((QWidget *) obj)->show();
         hidden_children.clear();
-
-        /* Going normal || maximized */
-        setWindowState (windowState() ^ WindowFullScreen);
-
-        qApp->processEvents();
-        console->toggleFSMode();
-    }
+    }
+
+    /* Process all console attributes changes and sub-widget hidings */
+    qApp->processEvents();
+
+    /* Send guest size hint */
+    console->toggleFSMode (consoleSize);
+
+    /* Waiting for host resize if it awaited during mode entering/exiting */
+    if ((mIsFullscreen || mIsSeamless) && (consoleSize != initialSize))
+        mIsWaitingModeResize = true;
+
+    if (!mIsWaitingModeResize)
+        onExitFullscreen();
+
+    setWindowState (windowState() ^ WindowFullScreen);
+
+    /* Unlock FS actions locked during modes toggling */
+    QTimer::singleShot (300, this, SLOT (unlockActionsSwitch()));
 
 #ifdef Q_WS_MAC /* wasHidden is wrong on the mac it seems. */
@@ -2276,32 +2248,27 @@
 void VBoxConsoleWnd::setViewInSeamlessMode (const QRect &aTargetRect)
 {
-	LogFlowThisFunc(("mIsSeamless=%s\n", mIsSeamless ? "true" : "false"));
-    if (mIsSeamless)
-    {
-        /* It isn't guaranteed that the guest os set the video mode that
-         * we requested. So after all the resizing stuff set the clipping
-         * mask and the spacing shifter to the corresponding values. */
-        QDesktopWidget *dtw = QApplication::desktop();
-        QRect sRect = dtw->screenGeometry (this);
-        QRect aRect (aTargetRect);
-        mMaskShift.scale (aTargetRect.left(), aTargetRect.top(), QSize::ScaleFree);
+    /* It isn't guaranteed that the guest os set the video mode that
+     * we requested. So after all the resizing stuff set the clipping
+     * mask and the spacing shifter to the corresponding values. */
+    QDesktopWidget *dtw = QApplication::desktop();
+    QRect sRect = dtw->screenGeometry (this);
+    QRect aRect (aTargetRect);
+    mMaskShift.scale (aTargetRect.left(), aTargetRect.top(), QSize::ScaleFree);
 #ifdef Q_WS_MAC
-        /* On mac os x this isn't necessary cause the screen starts
-         * by y=0 always regardless if there is the global menubar or not. */
-        aRect.setRect (aRect.left(), 0, aRect.width(), aRect.height() + aRect.top());
+    /* On mac os x this isn't necessary cause the screen starts
+     * by y=0 always regardless if there is the global menubar or not. */
+    aRect.setRect (aRect.left(), 0, aRect.width(), aRect.height() + aRect.top());
 #endif // Q_WS_MAC
-        /* Set the clipping mask */
-        mStrictedRegion = aRect;
-        /* Set the shifting spacer */
-        mShiftingSpacerLeft->changeSize (RT_ABS (sRect.left() - aRect.left()), 0,
-                                         QSizePolicy::Fixed, QSizePolicy::Preferred);
-        mShiftingSpacerTop->changeSize (0, RT_ABS (sRect.top() - aRect.top()),
-                                        QSizePolicy::Preferred, QSizePolicy::Fixed);
-        mShiftingSpacerRight->changeSize (RT_ABS (sRect.right() - aRect.right()), 0,
-                                          QSizePolicy::Fixed, QSizePolicy::Preferred);
-        mShiftingSpacerBottom->changeSize (0, RT_ABS (sRect.bottom() - aRect.bottom()),
-                                           QSizePolicy::Preferred, QSizePolicy::Fixed);
-    }
-    LogFlowFuncLeave();
+    /* Set the clipping mask */
+    mStrictedRegion = aRect;
+    /* Set the shifting spacer */
+    mShiftingSpacerLeft->changeSize (RT_ABS (sRect.left() - aRect.left()), 0,
+                                     QSizePolicy::Fixed, QSizePolicy::Preferred);
+    mShiftingSpacerTop->changeSize (0, RT_ABS (sRect.top() - aRect.top()),
+                                    QSizePolicy::Preferred, QSizePolicy::Fixed);
+    mShiftingSpacerRight->changeSize (RT_ABS (sRect.right() - aRect.right()), 0,
+                                      QSizePolicy::Fixed, QSizePolicy::Preferred);
+    mShiftingSpacerBottom->changeSize (0, RT_ABS (sRect.bottom() - aRect.bottom()),
+                                       QSizePolicy::Preferred, QSizePolicy::Fixed);
 }
 
