VirtualBox

Ignore:
Timestamp:
Feb 9, 2011 11:02:31 AM (14 years ago)
Author:
vboxsync
Message:

FE/Qt: 4718: Mouse cursor issues with disabled mouse integration: Fixed bug with mouse-cursor clipping failure (win host) in case of VM window overlapped by always-on-top window(s).

Location:
trunk/src/VBox/Frontends/VirtualBox/src
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Frontends/VirtualBox/src/globals/VBoxGlobal.cpp

    r35897 r35906  
    843843    return result;
    844844}
     845
     846#ifdef Q_WS_WIN
     847/* Enumerate visible top-most windows: */
     848BOOL CALLBACK EnumWindowsProc(HWND hWnd, LPARAM /* lParam */)
     849{
     850    /* Ignore NULL HWNDs: */
     851    if (!hWnd)
     852        return TRUE;
     853
     854    /* Ignore hidden windows: */
     855    if (!IsWindowVisible(hWnd))
     856        return TRUE;
     857
     858    /* Get window style: */
     859    LONG uStyle = GetWindowLong(hWnd, GWL_STYLE);
     860    /* Ignore minimized windows: */
     861    if (uStyle & WS_MINIMIZE)
     862        return TRUE;
     863
     864    /* Get extended window style: */
     865    LONG uExtendedStyle = GetWindowLong(hWnd, GWL_EXSTYLE);
     866    /* Ignore non-top-most windows: */
     867    if (!(uExtendedStyle & WS_EX_TOPMOST))
     868        return TRUE;
     869
     870    /* Get that window rectangle: */
     871    RECT rect;
     872    GetWindowRect(hWnd, &rect);
     873    VBoxGlobal::m_sTopMostRects << QRect(QPoint(rect.left, rect.top), QPoint(rect.right - 1, rect.bottom - 1));
     874
     875    /* Proceed to the next window: */
     876    return TRUE;
     877}
     878
     879/* static */
     880QList<QRect> VBoxGlobal::m_sTopMostRects = QList<QRect>();
     881
     882/* static */
     883const QRegion VBoxGlobal::areaCoveredByTopMostWindows()
     884{
     885    /* Prepare the top-most region: */
     886    QRegion topMostRegion;
     887    /* Initialize the list of the top-most rectangles: */
     888    m_sTopMostRects.clear();
     889    /* Populate the list of top-most rectangles: */
     890    EnumWindows((WNDENUMPROC)EnumWindowsProc, 0);
     891    /* Update the top-most region with top-most rectangles: */
     892    for (int iRectIndex = 0; iRectIndex < m_sTopMostRects.size(); ++iRectIndex)
     893        topMostRegion += m_sTopMostRects[iRectIndex];
     894    /* Return top-most region: */
     895    return topMostRegion;
     896}
     897#endif /* Q_WS_WIN */
    845898
    846899/**
  • trunk/src/VBox/Frontends/VirtualBox/src/globals/VBoxGlobal.h

    r35897 r35906  
    178178    const QRect availableGeometry(int iScreen = 0) const;
    179179
     180#ifdef Q_WS_WIN
     181    static QList<QRect> m_sTopMostRects;
     182    static const QRegion areaCoveredByTopMostWindows();
     183#endif /* Q_WS_WIN */
     184
    180185#ifdef VBOX_WITH_DEBUGGER_GUI
    181186    bool isDebuggerEnabled(CMachine &aMachine);
  • trunk/src/VBox/Frontends/VirtualBox/src/runtime/UIMouseHandler.cpp

    r35750 r35906  
    692692        /* Bringing mouse to the opposite side to simulate the endless moving: */
    693693
    694         /* Acquiring visible viewport rectangle in local coordinates: */
    695         QRect viewportRectangle = m_viewports[uScreenId]->visibleRegion().boundingRect();
     694        /* Get visible-viewport-rectangle in global coordinates: */
     695        QRect viewportRectangle = m_mouseCursorClippingRect;
     696        /* Get top-left point of full-viewport-rectangle in global coordinates: */
    696697        QPoint viewportRectangleGlobalPos = m_views[uScreenId]->mapToGlobal(m_viewports[uScreenId]->pos());
    697         /* Shift viewport rectangle to global position to bound by available geometry: */
    698         viewportRectangle.translate(viewportRectangleGlobalPos);
    699         /* Acquiring viewport rectangle cropped by available geometry: */
    700         viewportRectangle = viewportRectangle.intersected(QApplication::desktop()->availableGeometry());
    701         /* Shift remaining viewport rectangle to local position as relative position is in local coordinates: */
     698        /* Shift visible-viewport-rectangle to local position because relative position is in local coordinates: */
    702699        viewportRectangle.translate(-viewportRectangleGlobalPos);
    703700
     
    873870    if (uisession()->isMouseCaptured())
    874871    {
    875         /* Acquiring visible viewport rectangle: */
     872        /* Get full-viewport-rectangle in local coordinates: */
    876873        QRect viewportRectangle = m_viewports[m_iMouseCaptureViewIndex]->visibleRegion().boundingRect();
     874        /* Get top-left point of full-viewport-rectangle in global coordinates: */
    877875        QPoint viewportRectangleGlobalPos = m_views[m_iMouseCaptureViewIndex]->mapToGlobal(m_viewports[m_iMouseCaptureViewIndex]->pos());
     876        /* Get full-viewport-rectangle in global coordinates: */
    878877        viewportRectangle.translate(viewportRectangleGlobalPos);
     878        /* Trim full-viewport-rectangle by available geometry: */
    879879        viewportRectangle = viewportRectangle.intersected(QApplication::desktop()->availableGeometry());
     880        /* Trim partial-viewport-rectangle by top-most windows: */
     881        QRegion viewportRegion(viewportRectangle);
     882        QRegion topMostRegion(VBoxGlobal::areaCoveredByTopMostWindows());
     883        viewportRegion -= topMostRegion;
     884        /* Check if partial-viewport-region consists of 1 rectangle: */
     885        if (viewportRegion.rectCount() > 1)
     886        {
     887            /* Choose the largest rectangle: */
     888            QVector<QRect> rects = viewportRegion.rects();
     889            QRect largestRect;
     890            for (int i = 0; i < rects.size(); ++i)
     891                largestRect = largestRect.width() * largestRect.height() < rects[i].width() * rects[i].height() ? rects[i] : largestRect;
     892            /* Assign the partial-viewport-region to the largest rect: */
     893            viewportRegion = largestRect;
     894        }
     895        /* Assign the partial-viewport-rectangle to the partial-viewport-region: */
     896        viewportRectangle = viewportRegion.boundingRect();
     897        /* Assign the visible-viewport-rectangle to the partial-viewport-rectangle: */
     898        m_mouseCursorClippingRect = viewportRectangle;
    880899        /* Prepare clipping area: */
    881         RECT rect = { viewportRectangle.left() + 1, viewportRectangle.top() + 1, viewportRectangle.right(), viewportRectangle.bottom() };
     900        RECT rect = { m_mouseCursorClippingRect.left() + 1, m_mouseCursorClippingRect.top() + 1, m_mouseCursorClippingRect.right(), m_mouseCursorClippingRect.bottom() };
    882901        ::ClipCursor(&rect);
    883902    }
  • trunk/src/VBox/Frontends/VirtualBox/src/runtime/UIMouseHandler.h

    r35740 r35906  
    2424#include <QPoint>
    2525#include <QMap>
     26#include <QRect>
    2627
    2728/* Local includes */
     
    110111     * we do not really grab the mouse in case of capturing it: */
    111112    void updateMouseCursorClipping();
     113    QRect m_mouseCursorClippingRect;
    112114#endif /* Q_WS_WIN */
    113115
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette