diff options
author | Paul Olav Tvete <paul.tvete@gmail.com> | 2015-05-04 17:48:18 +0200 |
---|---|---|
committer | Paul Olav Tvete <paul.tvete@gmail.com> | 2015-05-04 17:55:02 +0200 |
commit | c05a8757b095cb554ea3e50f202a0683ca7d5bf7 (patch) | |
tree | 0cc94f6907d57030e7db4e67e59781c269ce9906 /src | |
parent | 3110a6642cb9424069ad89666e3cca01d1d6b420 (diff) |
Multi-screen fixes
Various fixes, including:
* Resize backingstore properly if screen has changed
* Trigger resize event on screen change if necessary
* Fix yet another race condition in screen detection
* Trying to fix screen mapping
Not completely finished, but I think it's better to
keep in sync, and not diverge too much.
Diffstat (limited to 'src')
-rw-r--r-- | src/gui/kernel/qcursor.cpp | 4 | ||||
-rw-r--r-- | src/gui/kernel/qguiapplication.cpp | 12 | ||||
-rw-r--r-- | src/gui/kernel/qhighdpiscaling.cpp | 57 | ||||
-rw-r--r-- | src/gui/kernel/qhighdpiscaling_p.h | 278 | ||||
-rw-r--r-- | src/gui/kernel/qplatformscreen.cpp | 18 | ||||
-rw-r--r-- | src/gui/kernel/qplatformscreen.h | 5 | ||||
-rw-r--r-- | src/gui/kernel/qplatformwindow.cpp | 10 | ||||
-rw-r--r-- | src/gui/kernel/qscreen_p.h | 8 | ||||
-rw-r--r-- | src/gui/kernel/qwindow.cpp | 28 | ||||
-rw-r--r-- | src/gui/kernel/qwindow_p.h | 1 | ||||
-rw-r--r-- | src/gui/kernel/qwindowsysteminterface.cpp | 34 | ||||
-rw-r--r-- | src/gui/kernel/qwindowsysteminterface_p.h | 2 | ||||
-rw-r--r-- | src/gui/painting/qbackingstore.cpp | 9 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbbackingstore.cpp | 4 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbwindow.cpp | 18 |
15 files changed, 401 insertions, 87 deletions
diff --git a/src/gui/kernel/qcursor.cpp b/src/gui/kernel/qcursor.cpp index 92e591f8ac..236b3b0565 100644 --- a/src/gui/kernel/qcursor.cpp +++ b/src/gui/kernel/qcursor.cpp @@ -180,7 +180,7 @@ QPoint QCursor::pos(const QScreen *screen) { if (screen) if (const QPlatformCursor *cursor = screen->handle()->cursor()) - return QHighDpi::fromNativePixels(cursor->pos()); + return QHighDpi::fromNativePixels(cursor->pos(), screen); return QGuiApplicationPrivate::lastCursorPosition.toPoint(); } @@ -232,7 +232,7 @@ void QCursor::setPos(QScreen *screen, int x, int y) { if (screen) { if (QPlatformCursor *cursor = screen->handle()->cursor()) { - const QPoint devicePos = QHighDpi::toNativePixels(QPoint(x, y)); + const QPoint devicePos = QHighDpi::toNativePixels(QPoint(x, y), screen); // Need to check, since some X servers generate null mouse move // events, causing looping in applications which call setPos() on // every mouse move event. diff --git a/src/gui/kernel/qguiapplication.cpp b/src/gui/kernel/qguiapplication.cpp index 1665909814..3415d015b7 100644 --- a/src/gui/kernel/qguiapplication.cpp +++ b/src/gui/kernel/qguiapplication.cpp @@ -957,10 +957,11 @@ QWindow *QGuiApplication::topLevelAt(const QPoint &pos) QList<QScreen *>::const_iterator screen = screens.constBegin(); QList<QScreen *>::const_iterator end = screens.constEnd(); - const QPoint devicePosition = QHighDpi::toNativePixels(pos); while (screen != end) { - if ((*screen)->geometry().contains(pos)) + if ((*screen)->geometry().contains(pos)) { + const QPoint devicePosition = QHighDpi::toNativePixels(pos, *screen); return (*screen)->handle()->topLevelAt(devicePosition); + } ++screen; } return 0; @@ -1814,7 +1815,7 @@ void QGuiApplicationPrivate::processMouseEvent(QWindowSystemInterfacePrivate::Mo points << point; QEvent::Type type; - QList<QTouchEvent::TouchPoint> touchPoints = QWindowSystemInterfacePrivate::convertTouchPoints(points, &type); + QList<QTouchEvent::TouchPoint> touchPoints = QWindowSystemInterfacePrivate::convertTouchPoints(points, &type, window); QWindowSystemInterfacePrivate::TouchEvent fake(window, e->timestamp, type, m_fakeTouchDevice, touchPoints, e->modifiers); fake.flags |= QWindowSystemInterfacePrivate::WindowSystemEvent::Synthetic; @@ -2025,6 +2026,11 @@ void QGuiApplicationPrivate::processWindowScreenChangedEvent(QWindowSystemInterf window->d_func()->setTopLevelScreen(screen, false /* recreate */); else // Fall back to default behavior, and try to find some appropriate screen window->setScreen(0); + // we may have changed scaling, so trigger resize event if needed + if (window->handle()) { + QWindowSystemInterfacePrivate::GeometryChangeEvent gce(window, QHighDpi::fromNativePixels(window->handle()->geometry(), window), QRect()); + processGeometryChangeEvent(&gce); + } } } diff --git a/src/gui/kernel/qhighdpiscaling.cpp b/src/gui/kernel/qhighdpiscaling.cpp index ff3f48b33f..54d06a8572 100644 --- a/src/gui/kernel/qhighdpiscaling.cpp +++ b/src/gui/kernel/qhighdpiscaling.cpp @@ -78,7 +78,7 @@ static inline qreal initialScaleFactor() qreal QHighDpiScaling::m_factor = initialScaleFactor(); bool QHighDpiScaling::m_autoFactor = qgetenv("QT_SCALE_FACTOR").toLower() == "auto"; -bool QHighDpiScaling::m_active = !qFuzzyCompare(QHighDpiScaling::m_factor, qreal(1)); +bool QHighDpiScaling::m_active = m_autoFactor || !qFuzzyCompare(QHighDpiScaling::m_factor, qreal(1)); bool QHighDpiScaling::m_perWindowActive = false; void QHighDpiScaling::setFactor(qreal factor) @@ -104,6 +104,44 @@ void QHighDpiScaling::setWindowFactor(QWindow *window, qreal factor) window->setProperty(scaleFactorProperty, QVariant(factor)); } + +/* + +QPoint QXcbScreen::mapToNative(const QPoint &pos) const +{ + const int dpr = int(devicePixelRatio()); + return (pos - m_geometry.topLeft()) * dpr + m_nativeGeometry.topLeft(); +} + +QPoint QXcbScreen::mapFromNative(const QPoint &pos) const +{ + const int dpr = int(devicePixelRatio()); + return (pos - m_nativeGeometry.topLeft()) / dpr + m_geometry.topLeft(); +} + + + */ + + +QPoint QHighDpiScaling::mapPositionToNative(const QPoint &pos, const QPlatformScreen *platformScreen) +{ + if (!platformScreen) + return pos; + const qreal scaleFactor = factor(platformScreen); + const QPoint topLeft = platformScreen->geometry().topLeft(); + return (pos - topLeft) * scaleFactor + topLeft; +} + +QPoint QHighDpiScaling::mapPositionFromNative(const QPoint &pos, const QPlatformScreen *platformScreen) +{ + if (!platformScreen) + return pos; + const qreal scaleFactor = factor(platformScreen); + const QPoint topLeft = platformScreen->geometry().topLeft(); + return (pos - topLeft) / scaleFactor + topLeft; +} + + qreal QHighDpiScaling::factor(const QScreen *screen) { if (m_autoFactor && screen && screen->handle()) @@ -111,6 +149,12 @@ qreal QHighDpiScaling::factor(const QScreen *screen) return m_factor; } +qreal QHighDpiScaling::factor(const QPlatformScreen *platformScreen) +{ + if (m_autoFactor && platformScreen) + return platformScreen->pixelDensity(); + return m_factor; +} qreal QHighDpiScaling::factor(const QWindow *window) { @@ -124,6 +168,17 @@ qreal QHighDpiScaling::factor(const QWindow *window) return f * (windowFactor.isValid() ? windowFactor.toReal() : 1); } +QPoint QHighDpiScaling::origin(const QScreen *screen) +{ + return screen->geometry().topLeft(); +} + +QPoint QHighDpiScaling::origin(const QPlatformScreen *platformScreen) +{ + return platformScreen->geometry().topLeft(); +} + + Q_GUI_EXPORT QSize QHighDpi::toNativePixelsConstrained(const QSize &size, const QWindow *window) { const int width = size.width(); diff --git a/src/gui/kernel/qhighdpiscaling_p.h b/src/gui/kernel/qhighdpiscaling_p.h index b29748fd29..f9b7b94a6f 100644 --- a/src/gui/kernel/qhighdpiscaling_p.h +++ b/src/gui/kernel/qhighdpiscaling_p.h @@ -49,6 +49,7 @@ #include <QtCore/qloggingcategory.h> #include <QtGui/qregion.h> #include <QtGui/qscreen.h> +#include <QtGui/qwindow.h> // This file implmements utility functions for high-dpi scaling on operating // systems that do not provide native scaling support. @@ -77,11 +78,19 @@ QT_BEGIN_NAMESPACE Q_DECLARE_LOGGING_CATEGORY(lcScaling); +class QScreen; +class QPlatformScreen; + class Q_GUI_EXPORT QHighDpiScaling { public: static bool isActive() { return m_active; } static qreal factor(const QWindow *window); static qreal factor(const QScreen *screen); + static qreal factor(const QPlatformScreen *platformScreen); + static QPoint origin(const QScreen *screen); + static QPoint origin(const QPlatformScreen *platformScreen); + static QPoint mapPositionFromNative(const QPoint &pos, const QPlatformScreen *platformScreen); + static QPoint mapPositionToNative(const QPoint &pos, const QPlatformScreen *platformScreen); static void setFactor(qreal factor); static void setWindowFactor(QWindow *window, qreal factor); private: @@ -97,112 +106,283 @@ private: namespace QHighDpi { -inline QRect fromNativePixels(const QRect &pixelRect, const QWindow *window = 0) +// inline QRect fromNativeGeometry(const QRect &pixelRect, const QPlatformScreen *platformScreen) +// { +// return QRect(pixelRect.topLeft(), pixelRect.size() / QHighDpiScaling::factor(platformScreen)); +// } + +// inline QRect toNativeGeometry(const QRect &pointRect, const QPlatformScreen *platformScreen) +// { +// return QRect(pointRect.topLeft(), pointRect.size() * QHighDpiScaling::factor(platformScreen)); +// } + +inline QPoint fromNative(const QPoint &pos, qreal scaleFactor, const QPoint &origin) { - const qreal scaleFactor = QHighDpiScaling::factor(window); - return QRect(pixelRect.topLeft() / scaleFactor, pixelRect.size() / scaleFactor); + return (pos - origin) / scaleFactor + origin; +} + +inline QPoint toNative(const QPoint &pos, qreal scaleFactor, const QPoint &origin) +{ + return (pos - origin) * scaleFactor + origin; +} + +inline QPoint fromNative(const QPoint &pos, qreal scaleFactor) +{ + return pos / scaleFactor; +} + +inline QPoint toNative(const QPoint &pos, qreal scaleFactor) +{ + return pos * scaleFactor; +} + +inline QSize fromNative(const QSize &size, qreal scaleFactor) +{ + return size / scaleFactor; // TODO: ### round up ### +} + +inline QSize toNative(const QSize &size, qreal scaleFactor) +{ + return size * scaleFactor; +} + +inline QRect fromNative(const QRect &rect, qreal scaleFactor, const QPoint &origin) +{ + return QRect(fromNative(rect.topLeft(), scaleFactor, origin), fromNative(rect.size(), scaleFactor)); } -inline QRect toNativePixels(const QRect &pointRect, const QWindow *window = 0) +inline QRect toNative(const QRect &rect, qreal scaleFactor, const QPoint &origin) +{ + return QRect(toNative(rect.topLeft(), scaleFactor, origin), toNative(rect.size(), scaleFactor)); + +} + + +inline QRect fromNative(const QRect &rect, const QScreen *screen, const QPoint &screenOrigin) +{ + return toNative(rect, QHighDpiScaling::factor(screen), screenOrigin); +} + +inline QRect fromNativeScreenGeometry(const QRect &nativeScreenGeometry, const QScreen *screen) +{ + return QRect(nativeScreenGeometry.topLeft(), fromNative(nativeScreenGeometry.size(), QHighDpiScaling::factor(screen))); +} + +inline QPointF fromNativeLocalPosition(const QPointF &pos, const QWindow *window) { const qreal scaleFactor = QHighDpiScaling::factor(window); - return QRect(pointRect.topLeft() * scaleFactor, pointRect.size() * scaleFactor); + return pos / scaleFactor; } -inline QRectF fromNativePixels(const QRectF &pixelRect, const QWindow *window = 0) +inline QPointF toNativeLocalPosition(const QPointF &pos, const QWindow *window) { const qreal scaleFactor = QHighDpiScaling::factor(window); - return QRectF(pixelRect.topLeft() / scaleFactor, pixelRect.size() / scaleFactor); + return pos * scaleFactor; +} + +inline QRect fromNativePixels(const QRect &pixelRect, const QPlatformScreen *platformScreen) +{ + const qreal scaleFactor = QHighDpiScaling::factor(platformScreen); + const QPoint origin = QHighDpiScaling::origin(platformScreen); + return QRect(fromNative(pixelRect.topLeft(), scaleFactor, origin), + fromNative(pixelRect.size(), scaleFactor)); } -inline QRectF toNativePixels(const QRectF &pointRect, const QWindow *window = 0) +inline QRect toNativePixels(const QRect &pointRect, const QPlatformScreen *platformScreen) { - const qreal scaleFactor = QHighDpiScaling::factor(window); - return QRectF(pointRect.topLeft() * scaleFactor, pointRect.size() * scaleFactor); + const qreal scaleFactor = QHighDpiScaling::factor(platformScreen); + const QPoint origin = QHighDpiScaling::origin(platformScreen); + return QRect(toNative(pointRect.topLeft(), scaleFactor, origin), + toNative(pointRect.size(), scaleFactor)); } -inline QSize fromNativePixels(const QSize &pixelSize, const QWindow *window = 0) +inline QRect fromNativePixels(const QRect &pixelRect, const QScreen *screen) +{ + const qreal scaleFactor = QHighDpiScaling::factor(screen); + const QPoint origin = QHighDpiScaling::origin(screen); + return QRect(fromNative(pixelRect.topLeft(), scaleFactor, origin), + fromNative(pixelRect.size(), scaleFactor)); +} + +inline QRect toNativePixels(const QRect &pointRect, const QScreen *screen) +{ + const qreal scaleFactor = QHighDpiScaling::factor(screen); + const QPoint origin = QHighDpiScaling::origin(screen); + return QRect(toNative(pointRect.topLeft(), scaleFactor, origin), + toNative(pointRect.size(), scaleFactor)); +} + +inline QRect fromNativePixels(const QRect &pixelRect, const QWindow *window) +{ + if (window->isTopLevel() && window->screen()) { + return fromNativePixels(pixelRect, window->screen()); + } else { + const qreal scaleFactor = QHighDpiScaling::factor(window); + return QRect(pixelRect.topLeft() / scaleFactor, fromNative(pixelRect.size(), scaleFactor)); + } +} + +inline QRectF toNativePixels(const QRectF &pointRect, const QScreen *screen) +{ + //######## + return toNativePixels(pointRect.toRect(), screen); +} + +inline QRect toNativePixels(const QRect &pointRect, const QWindow *window) +{ + if (window->isTopLevel() && window->screen()) { + return toNativePixels(pointRect, window->screen()); + } else { + const qreal scaleFactor = QHighDpiScaling::factor(window); + return QRect(pointRect.topLeft() * scaleFactor, toNative(pointRect.size(), scaleFactor)); + } +} + +inline QRectF fromNativePixels(const QRectF &pixelRect, const QScreen *screen) +{ + //######## + return fromNativePixels(pixelRect.toRect(), screen); +} + +inline QRectF fromNativePixels(const QRectF &pixelRect, const QWindow *window) +{ + if (window->isTopLevel() && window->screen()) { + return fromNativePixels(pixelRect, window->screen()); + } else { + const qreal scaleFactor = QHighDpiScaling::factor(window); + return QRectF(pixelRect.topLeft() / scaleFactor, pixelRect.size() / scaleFactor); + } +} + +inline QRectF toNativePixels(const QRectF &pointRect, const QWindow *window) +{ + if (window->isTopLevel() && window->screen()) { + return toNativePixels(pointRect, window->screen()); + } else { + const qreal scaleFactor = QHighDpiScaling::factor(window); + return QRectF(pointRect.topLeft() * scaleFactor, pointRect.size() * scaleFactor); + } +} + +inline QSize fromNativePixels(const QSize &pixelSize, const QWindow *window) { return pixelSize / QHighDpiScaling::factor(window); } // For converting minimum/maximum sizes of QWindow, limits to 0..QWINDOWSIZE_MAX -Q_GUI_EXPORT QSize toNativePixelsConstrained(const QSize &size, const QWindow *window = 0); +Q_GUI_EXPORT QSize toNativePixelsConstrained(const QSize &size, const QWindow *window); -inline QSize toNativePixels(const QSize &pointSize, const QWindow *window = 0) +inline QSize toNativePixels(const QSize &pointSize, const QWindow *window) { return pointSize * QHighDpiScaling::factor(window); } -inline QSizeF fromNativePixels(const QSizeF &pixelSize, const QWindow *window = 0) +inline QSizeF fromNativePixels(const QSizeF &pixelSize, const QWindow *window) { return pixelSize / QHighDpiScaling::factor(window); } -inline QSizeF toNativePixels(const QSizeF &pointSize, const QWindow *window = 0) +inline QSizeF toNativePixels(const QSizeF &pointSize, const QWindow *window) { return pointSize * QHighDpiScaling::factor(window); } -inline QPoint fromNativePixels(const QPoint &pixelPoint, const QWindow *window = 0) +inline QPoint fromNativePixels(const QPoint &pixelPoint, const QScreen *screen) +{ + return fromNative(pixelPoint, QHighDpiScaling::factor(screen), QHighDpiScaling::origin(screen)); +} + +inline QPoint fromNativePixels(const QPoint &pixelPoint, const QWindow *window) +{ + if (window->isTopLevel() && window->screen()) + return fromNativePixels(pixelPoint, window->screen()); + else + return pixelPoint / QHighDpiScaling::factor(window); +} + +inline QPoint toNativePixels(const QPoint &pointPoint, const QScreen *screen) +{ + return toNative(pointPoint, QHighDpiScaling::factor(screen), QHighDpiScaling::origin(screen)); +} + +inline QPoint toNativePixels(const QPoint &pointPoint, const QWindow *window) +{ + if (window->isTopLevel() && window->screen()) + return toNativePixels(pointPoint, window->screen()); + else + return pointPoint * QHighDpiScaling::factor(window); +} + +inline QPointF fromNativePixels(const QPointF &pixelPoint, const QScreen *screen) { - return pixelPoint / QHighDpiScaling::factor(window); + return fromNativePixels(pixelPoint.toPoint(), screen); //############### } -inline QPoint toNativePixels(const QPoint &pointPoint, const QWindow *window = 0) +inline QPointF fromNativePixels(const QPointF &pixelPoint, const QWindow *window) { - return pointPoint * QHighDpiScaling::factor(window); + if (window->isTopLevel() && window->screen()) + return fromNativePixels(pixelPoint, window->screen()); + else + return pixelPoint / QHighDpiScaling::factor(window); } -inline QPointF fromNativePixels(const QPointF &pixelPoint, const QWindow *window = 0) +inline QPointF toNativePixels(const QPointF &pointPoint, const QScreen *screen) { - return pixelPoint / QHighDpiScaling::factor(window); + return toNativePixels(pointPoint.toPoint(), screen); //########### } -inline QPointF toNativePixels(const QPointF &pointPoint, const QWindow *window = 0) +inline QPointF toNativePixels(const QPointF &pointPoint, const QWindow *window) { - return pointPoint * QHighDpiScaling::factor(window); + if (window->isTopLevel() && window->screen()) + return toNativePixels(pointPoint, window->screen()); + else + return pointPoint * QHighDpiScaling::factor(window); } -inline QMargins fromNativePixels(const QMargins &pixelMargins, const QWindow *window = 0) +inline QMargins fromNativePixels(const QMargins &pixelMargins, const QWindow *window) { const qreal scaleFactor = QHighDpiScaling::factor(window); return QMargins(pixelMargins.left() / scaleFactor, pixelMargins.top() / scaleFactor, pixelMargins.right() / scaleFactor, pixelMargins.bottom() / scaleFactor); } -inline QMargins toNativePixels(const QMargins &pointMargins, const QWindow *window = 0) +inline QMargins toNativePixels(const QMargins &pointMargins, const QWindow *window) { const qreal scaleFactor = QHighDpiScaling::factor(window); return QMargins(pointMargins.left() * scaleFactor, pointMargins.top() * scaleFactor, pointMargins.right() * scaleFactor, pointMargins.bottom() * scaleFactor); } - -inline QRegion fromNativePixels(const QRegion &pixelRegion, const QWindow *window = 0) +#if 1 + //############## expose regions need special handling +inline QRegion fromNativeLocalRegion(const QRegion &pixelRegion, const QWindow *window) { if (!QHighDpiScaling::isActive()) return pixelRegion; + qreal scaleFactor = QHighDpiScaling::factor(window); QRegion pointRegion; foreach (const QRect &rect, pixelRegion.rects()) - pointRegion += fromNativePixels(rect, window); + pointRegion += QRect(fromNative(rect.topLeft(), scaleFactor), + fromNative(rect.size(), scaleFactor)); return pointRegion; } -inline QRegion toNativePixels(const QRegion &pointRegion, const QWindow *window = 0) +inline QRegion toNativeLocalRegion(const QRegion &pointRegion, const QWindow *window) { if (!QHighDpiScaling::isActive()) return pointRegion; + qreal scaleFactor = QHighDpiScaling::factor(window); QRegion pixelRegon; foreach (const QRect &rect, pointRegion.rects()) - pixelRegon += toNativePixels(rect, window); + pixelRegon += QRect(toNative(rect.topLeft(), scaleFactor), + toNative(rect.size(), scaleFactor)); return pixelRegon; } - +#endif // Any T that has operator/() template <typename T> -T fromNativePixels(const T &pixelValue, const QWindow *window = 0) +T fromNativePixels(const T &pixelValue, const QWindow *window) { if (!QHighDpiScaling::isActive()) return pixelValue; @@ -211,9 +391,20 @@ T fromNativePixels(const T &pixelValue, const QWindow *window = 0) } + //##### ????? +template <typename T> +T fromNativePixels(const T &pixelValue, const QScreen *screen) +{ + if (!QHighDpiScaling::isActive()) + return pixelValue; + + return pixelValue / QHighDpiScaling::factor(screen); + +} + // Any T that has operator*() template <typename T> -T toNativePixels(const T &pointValue, const QWindow *window = 0) +T toNativePixels(const T &pointValue, const QWindow *window) { if (!QHighDpiScaling::isActive()) return pointValue; @@ -221,9 +412,19 @@ T toNativePixels(const T &pointValue, const QWindow *window = 0) return pointValue * QHighDpiScaling::factor(window); } +template <typename T> +T toNativePixels(const T &pointValue, const QScreen *screen) +{ + if (!QHighDpiScaling::isActive()) + return pointValue; + + return pointValue * QHighDpiScaling::factor(screen); +} + + // Any QVector<T> where T has operator/() template <typename T> -QVector<T> fromNativePixels(const QVector<T> &pixelValues, const QWindow *window = 0) +QVector<T> fromNativePixels(const QVector<T> &pixelValues, const QWindow *window) { if (!QHighDpiScaling::isActive()) return pixelValues; @@ -236,7 +437,7 @@ QVector<T> fromNativePixels(const QVector<T> &pixelValues, const QWindow *window // Any QVector<T> where T has operator*() template <typename T> -QVector<T> toNativePixels(const QVector<T> &pointValues, const QWindow *window = 0) +QVector<T> toNativePixels(const QVector<T> &pointValues, const QWindow *window) { if (!QHighDpiScaling::isActive()) return pointValues; @@ -247,10 +448,10 @@ QVector<T> toNativePixels(const QVector<T> &pointValues, const QWindow *window = return pixelValues; } - +#if 0 // Any QPair<T, U> where T and U has operator/() template <typename T, typename U> -QPair<T, U> fromNativePixels(const QPair<T, U> &pixelPair, const QWindow *window = 0) +QPair<T, U> fromNativePixels(const QPair<T, U> &pixelPair, const QWindow *window) { return qMakePair(fromNativePixels(pixelPair.first, window), fromNativePixels(pixelPair.second, window)); @@ -258,11 +459,12 @@ QPair<T, U> fromNativePixels(const QPair<T, U> &pixelPair, const QWindow *window // Any QPair<T, U> where T and U has operator*() template <typename T, typename U> -QPair<T, U> toNativePixels(const QPair<T, U> &pointPair, const QWindow *window = 0) +QPair<T, U> toNativePixels(const QPair<T, U> &pointPair, const QWindow *window) { return qMakePair(QHighDpi::toNativePixels(pointPair.first, window), QHighDpi::toNativePixels(pointPair.second, window)); } +#endif } QT_END_NAMESPACE diff --git a/src/gui/kernel/qplatformscreen.cpp b/src/gui/kernel/qplatformscreen.cpp index f545009f3a..bda7280e81 100644 --- a/src/gui/kernel/qplatformscreen.cpp +++ b/src/gui/kernel/qplatformscreen.cpp @@ -301,8 +301,8 @@ void QPlatformScreen::resizeMaximizedWindows() // 'screen()' still has the old geometry info while 'this' has the new geometry info const QRect oldGeometry = screen()->geometry(); const QRect oldAvailableGeometry = screen()->availableGeometry(); - const QRect newGeometry = QHighDpi::fromNativePixels(geometry()); - const QRect newAvailableGeometry = QHighDpi::fromNativePixels(availableGeometry()); + const QRect newGeometry = deviceIndependentGeometry(); + const QRect newAvailableGeometry = QHighDpi::fromNative(availableGeometry(), QHighDpiScaling::factor(this), newGeometry.topLeft()); // make sure maximized and fullscreen windows are updated for (int i = 0; i < windows.size(); ++i) { @@ -404,14 +404,24 @@ QRect QPlatformScreen::mapBetween(Qt::ScreenOrientation a, Qt::ScreenOrientation return rect; } +QRect QPlatformScreen::deviceIndependentGeometry() const +{ + qreal scaleFactor = QHighDpiScaling::factor(this); + QRect nativeGeometry = geometry(); + return QRect(nativeGeometry.topLeft(), QHighDpi::fromNative(nativeGeometry.size(), scaleFactor)); +} + + QRect QPlatformScreen::screenGeometry() const { - return QHighDpi::toNativePixels(screen()->geometry()); + qreal scaleFactor = QHighDpiScaling::factor(this); + QRect geometry = screen()->geometry(); + return QRect(geometry.topLeft(), QHighDpi::toNative(geometry.size(), scaleFactor)); } QRect QPlatformScreen::screenAvailableGeometry() const { - return QHighDpi::toNativePixels(screen()->availableGeometry()); + return QHighDpi::toNativePixels(screen()->availableGeometry(), this); } /*! diff --git a/src/gui/kernel/qplatformscreen.h b/src/gui/kernel/qplatformscreen.h index 8dceef26eb..b7bd157717 100644 --- a/src/gui/kernel/qplatformscreen.h +++ b/src/gui/kernel/qplatformscreen.h @@ -122,7 +122,10 @@ public: static QTransform transformBetween(Qt::ScreenOrientation a, Qt::ScreenOrientation b, const QRect &target); static QRect mapBetween(Qt::ScreenOrientation a, Qt::ScreenOrientation b, const QRect &rect); - // Screen property accessors. Platform plugins should use these + // The platform screen's geometry in device independent coordinates + QRect deviceIndependentGeometry() const; + + // Accessors for QScreen geometry in native coordinates. Platform plugins should use these // instead of accessing QScreen directly. QRect screenGeometry() const; QRect screenAvailableGeometry() const; diff --git a/src/gui/kernel/qplatformwindow.cpp b/src/gui/kernel/qplatformwindow.cpp index 22523ec21f..08f7cacc26 100644 --- a/src/gui/kernel/qplatformwindow.cpp +++ b/src/gui/kernel/qplatformwindow.cpp @@ -483,13 +483,17 @@ QString QPlatformWindow::formatWindowTitle(const QString &title, const QString & QPlatformScreen *QPlatformWindow::screenForGeometry(const QRect &newGeometry) const { QPlatformScreen *currentScreen = screen(); - if (!parent() && currentScreen && !currentScreen->geometry().intersects(newGeometry)) { + QPlatformScreen *fallback = currentScreen; + QPoint center = newGeometry.center(); + if (!parent() && currentScreen && !currentScreen->geometry().contains(center)) { Q_FOREACH (QPlatformScreen* screen, currentScreen->virtualSiblings()) { - if (screen->geometry().intersects(newGeometry)) + if (screen->geometry().contains(center)) return screen; + if (screen->geometry().intersects(newGeometry)) + fallback = screen; } } - return currentScreen; + return fallback; } /*! diff --git a/src/gui/kernel/qscreen_p.h b/src/gui/kernel/qscreen_p.h index 45c8746131..7a5fc88068 100644 --- a/src/gui/kernel/qscreen_p.h +++ b/src/gui/kernel/qscreen_p.h @@ -61,8 +61,8 @@ public: , orientationUpdateMask(0) { orientation = platformScreen->orientation(); - geometry = QHighDpi::fromNativePixels(platformScreen->geometry()); - availableGeometry = QHighDpi::fromNativePixels(platformScreen->availableGeometry()); + geometry = platformScreen->deviceIndependentGeometry(); + availableGeometry = QHighDpi::fromNative(platformScreen->availableGeometry(), QHighDpiScaling::factor(platformScreen), geometry.topLeft()); logicalDpi = platformScreen->logicalDpi(); refreshRate = platformScreen->refreshRate(); // safeguard ourselves against buggy platform behavior... @@ -80,8 +80,8 @@ public: void updateHighDpi() { - geometry = QHighDpi::fromNativePixels(platformScreen->geometry()); - availableGeometry = QHighDpi::fromNativePixels(platformScreen->availableGeometry()); + geometry = platformScreen->deviceIndependentGeometry(); + availableGeometry = QHighDpi::fromNative(platformScreen->availableGeometry(), QHighDpiScaling::factor(platformScreen), geometry.topLeft()); } void updatePrimaryOrientation(); diff --git a/src/gui/kernel/qwindow.cpp b/src/gui/kernel/qwindow.cpp index 920119464f..d29470b3ed 100644 --- a/src/gui/kernel/qwindow.cpp +++ b/src/gui/kernel/qwindow.cpp @@ -1432,7 +1432,13 @@ void QWindow::setGeometry(const QRect &rect) d->positionPolicy = QWindowPrivate::WindowFrameExclusive; if (d->platformWindow) { - d->platformWindow->setGeometry(QHighDpi::toNativePixels(rect, this)); + QRect nativeRect; + QScreen *newScreen = d->screenForGeometry(rect); + if (newScreen && isTopLevel()) + nativeRect = QHighDpi::toNativePixels(rect, newScreen); + else + nativeRect = QHighDpi::toNativePixels(rect, this); + d->platformWindow->setGeometry(nativeRect); } else { d->geometry = rect; @@ -1447,6 +1453,26 @@ void QWindow::setGeometry(const QRect &rect) } } +//######### This logic duplicated three times!!!!! +// equivalent to QPlatformWindow::screenForGeometry, but in platform independent coordinates +QScreen *QWindowPrivate::screenForGeometry(const QRect &newGeometry) +{ + Q_Q(QWindow); + QScreen *currentScreen = q->screen(); + QScreen *fallback = currentScreen; + QPoint center = newGeometry.center(); + if (!q->parent() && currentScreen && !currentScreen->geometry().contains(center)) { + Q_FOREACH (QScreen* screen, currentScreen->virtualSiblings()) { + if (screen->geometry().contains(center)) + return screen; + if (screen->geometry().intersects(newGeometry)) + fallback = screen; + } + } + return fallback; +} + + /*! Returns the geometry of the window, excluding its window frame. diff --git a/src/gui/kernel/qwindow_p.h b/src/gui/kernel/qwindow_p.h index 4fc63acf28..23a6d800c0 100644 --- a/src/gui/kernel/qwindow_p.h +++ b/src/gui/kernel/qwindow_p.h @@ -136,6 +136,7 @@ public: void connectToScreen(QScreen *topLevelScreen); void disconnectFromScreen(); void emitScreenChangedRecursion(QScreen *newScreen); + QScreen *screenForGeometry(const QRect &rect); virtual void clearFocusObject(); virtual QRectF closestAcceptableGeometry(const QRectF &rect) const; diff --git a/src/gui/kernel/qwindowsysteminterface.cpp b/src/gui/kernel/qwindowsysteminterface.cpp index a08708269b..74d302dcbd 100644 --- a/src/gui/kernel/qwindowsysteminterface.cpp +++ b/src/gui/kernel/qwindowsysteminterface.cpp @@ -168,7 +168,7 @@ void QWindowSystemInterface::handleMouseEvent(QWindow *w, ulong timestamp, const Qt::KeyboardModifiers mods, Qt::MouseEventSource source) { QWindowSystemInterfacePrivate::MouseEvent * e = - new QWindowSystemInterfacePrivate::MouseEvent(w, timestamp, QHighDpi::fromNativePixels(local, w), QHighDpi::fromNativePixels(global, w), b, mods, source); + new QWindowSystemInterfacePrivate::MouseEvent(w, timestamp, QHighDpi::fromNativeLocalPosition(local, w), QHighDpi::fromNativePixels(global, w), b, mods, source); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); } @@ -185,7 +185,7 @@ void QWindowSystemInterface::handleFrameStrutMouseEvent(QWindow *w, ulong timest QWindowSystemInterfacePrivate::MouseEvent * e = new QWindowSystemInterfacePrivate::MouseEvent(w, timestamp, QWindowSystemInterfacePrivate::FrameStrutMouse, - QHighDpi::fromNativePixels(local, w), QHighDpi::fromNativePixels(global, w), b, mods, source); + QHighDpi::fromNativeLocalPosition(local, w), QHighDpi::fromNativePixels(global, w), b, mods, source); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); } @@ -366,14 +366,14 @@ void QWindowSystemInterface::handleWheelEvent(QWindow *tlw, ulong timestamp, con // Simple case: vertical deltas only: if (angleDelta.y() != 0 && angleDelta.x() == 0) { - e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativePixels(local, tlw), QHighDpi::fromNativePixels(global, tlw), pixelDelta, angleDelta, angleDelta.y(), Qt::Vertical, mods, phase, source); + e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativeLocalPosition(local, tlw), QHighDpi::fromNativePixels(global, tlw), pixelDelta, angleDelta, angleDelta.y(), Qt::Vertical, mods, phase, source); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); return; } // Simple case: horizontal deltas only: if (angleDelta.y() == 0 && angleDelta.x() != 0) { - e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativePixels(local, tlw), QHighDpi::fromNativePixels(global, tlw), pixelDelta, angleDelta, angleDelta.x(), Qt::Horizontal, mods, phase, source); + e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativeLocalPosition(local, tlw), QHighDpi::fromNativePixels(global, tlw), pixelDelta, angleDelta, angleDelta.x(), Qt::Horizontal, mods, phase, source); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); return; } @@ -381,12 +381,12 @@ void QWindowSystemInterface::handleWheelEvent(QWindow *tlw, ulong timestamp, con // Both horizontal and vertical deltas: Send two wheel events. // The first event contains the Qt 5 pixel and angle delta as points, // and in addition the Qt 4 compatibility vertical angle delta. - e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativePixels(local, tlw), QHighDpi::fromNativePixels(global, tlw), pixelDelta, angleDelta, angleDelta.y(), Qt::Vertical, mods, phase, source); + e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativeLocalPosition(local, tlw), QHighDpi::fromNativePixels(global, tlw), pixelDelta, angleDelta, angleDelta.y(), Qt::Vertical, mods, phase, source); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); // The second event contains null pixel and angle points and the // Qt 4 compatibility horizontal angle delta. - e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativePixels(local, tlw), QHighDpi::fromNativePixels(global, tlw), QPoint(), QPoint(), angleDelta.x(), Qt::Horizontal, mods, phase, source); + e = new QWindowSystemInterfacePrivate::WheelEvent(tlw, timestamp, QHighDpi::fromNativeLocalPosition(local, tlw), QHighDpi::fromNativePixels(global, tlw), QPoint(), QPoint(), angleDelta.x(), Qt::Horizontal, mods, phase, source); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); } @@ -449,7 +449,7 @@ void QWindowSystemInterface::handleTouchEvent(QWindow *w, QTouchDevice *device, handleTouchEvent(w, time, device, points, mods); } -QList<QTouchEvent::TouchPoint> QWindowSystemInterfacePrivate::convertTouchPoints(const QList<QWindowSystemInterface::TouchPoint> &points, QEvent::Type *type) +QList<QTouchEvent::TouchPoint> QWindowSystemInterfacePrivate::convertTouchPoints(const QList<QWindowSystemInterface::TouchPoint> &points, QEvent::Type *type, const QWindow *window) { QList<QTouchEvent::TouchPoint> touchPoints; Qt::TouchPointStates states; @@ -464,16 +464,16 @@ QList<QTouchEvent::TouchPoint> QWindowSystemInterfacePrivate::convertTouchPoints p.setState(point->state); const QPointF screenPos = point->area.center(); - p.setScreenPos(QHighDpi::fromNativePixels(screenPos)); - p.setScreenRect(QHighDpi::fromNativePixels(point->area)); + p.setScreenPos(QHighDpi::fromNativePixels(screenPos, window)); + p.setScreenRect(QHighDpi::fromNativePixels(point->area, window)); // The local pos and rect are not set, they will be calculated // when the event gets processed by QGuiApplication. - p.setNormalizedPos(QHighDpi::fromNativePixels(point->normalPosition)); - p.setVelocity(QHighDpi::fromNativePixels(point->velocity)); + p.setNormalizedPos(QHighDpi::fromNativePixels(point->normalPosition, window)); + p.setVelocity(QHighDpi::fromNativePixels(point->velocity, window)); p.setFlags(point->flags); - p.setRawScreenPositions(QHighDpi::fromNativePixels(point->rawPositions)); + p.setRawScreenPositions(QHighDpi::fromNativePixels(point->rawPositions, window)); touchPoints.append(p); ++point; @@ -501,7 +501,7 @@ void QWindowSystemInterface::handleTouchEvent(QWindow *tlw, ulong timestamp, QTo return; QEvent::Type type; - QList<QTouchEvent::TouchPoint> touchPoints = QWindowSystemInterfacePrivate::convertTouchPoints(points, &type); + QList<QTouchEvent::TouchPoint> touchPoints = QWindowSystemInterfacePrivate::convertTouchPoints(points, &type, tlw); QWindowSystemInterfacePrivate::TouchEvent *e = new QWindowSystemInterfacePrivate::TouchEvent(tlw, timestamp, type, device, touchPoints, mods); @@ -534,7 +534,7 @@ void QWindowSystemInterface::handleScreenOrientationChange(QScreen *screen, Qt:: void QWindowSystemInterface::handleScreenGeometryChange(QScreen *screen, const QRect &geometry, const QRect &availableGeometry) { QWindowSystemInterfacePrivate::ScreenGeometryEvent *e = - new QWindowSystemInterfacePrivate::ScreenGeometryEvent(screen, QHighDpi::fromNativePixels(geometry), QHighDpi::fromNativePixels(availableGeometry)); + new QWindowSystemInterfacePrivate::ScreenGeometryEvent(screen, QHighDpi::fromNativeScreenGeometry(geometry, screen), QHighDpi::fromNative(availableGeometry, screen, geometry.topLeft())); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); } @@ -560,7 +560,7 @@ void QWindowSystemInterface::handleThemeChange(QWindow *tlw) void QWindowSystemInterface::handleExposeEvent(QWindow *tlw, const QRegion ®ion) { - QWindowSystemInterfacePrivate::ExposeEvent *e = new QWindowSystemInterfacePrivate::ExposeEvent(tlw, QHighDpi::fromNativePixels(region, tlw)); + QWindowSystemInterfacePrivate::ExposeEvent *e = new QWindowSystemInterfacePrivate::ExposeEvent(tlw, QHighDpi::fromNativeLocalRegion(region, tlw)); QWindowSystemInterfacePrivate::handleWindowSystemEvent(e); } @@ -667,7 +667,7 @@ void QWindowSystemInterface::handleTabletEvent(QWindow *w, ulong timestamp, cons { QWindowSystemInterfacePrivate::TabletEvent *e = new QWindowSystemInterfacePrivate::TabletEvent(w,timestamp, - QHighDpi::fromNativePixels(local, w), + QHighDpi::fromNativeLocalPosition(local, w), QHighDpi::fromNativePixels(global, w), device, pointerType, buttons, pressure, xTilt, yTilt, tangentialPressure, rotation, z, uid, modifiers); @@ -797,7 +797,7 @@ Q_GUI_EXPORT QDebug operator<<(QDebug dbg, const QWindowSystemInterface::TouchPo Q_GUI_EXPORT void qt_handleMouseEvent(QWindow *w, const QPointF & local, const QPointF & global, Qt::MouseButtons b, Qt::KeyboardModifiers mods = Qt::NoModifier) { - QWindowSystemInterface::handleMouseEvent(w, QHighDpi::toNativePixels(local, w), QHighDpi::toNativePixels(global, w), b, mods); + QWindowSystemInterface::handleMouseEvent(w, QHighDpi::toNativeLocalPosition(local, w), QHighDpi::toNativePixels(global, w), b, mods); } Q_GUI_EXPORT void qt_handleKeyEvent(QWindow *w, QEvent::Type t, int k, Qt::KeyboardModifiers mods, const QString & text = QString(), bool autorep = false, ushort count = 1) diff --git a/src/gui/kernel/qwindowsysteminterface_p.h b/src/gui/kernel/qwindowsysteminterface_p.h index 2ec402a1e9..0c87c191f3 100644 --- a/src/gui/kernel/qwindowsysteminterface_p.h +++ b/src/gui/kernel/qwindowsysteminterface_p.h @@ -486,7 +486,7 @@ public: static QWaitCondition eventsFlushed; static QMutex flushEventMutex; - static QList<QTouchEvent::TouchPoint> convertTouchPoints(const QList<QWindowSystemInterface::TouchPoint> &points, QEvent::Type *type); + static QList<QTouchEvent::TouchPoint> convertTouchPoints(const QList<QWindowSystemInterface::TouchPoint> &points, QEvent::Type *type, const QWindow *window); }; QT_END_NAMESPACE diff --git a/src/gui/painting/qbackingstore.cpp b/src/gui/painting/qbackingstore.cpp index cff99722f3..65a108f7ee 100644 --- a/src/gui/painting/qbackingstore.cpp +++ b/src/gui/painting/qbackingstore.cpp @@ -106,7 +106,7 @@ void QBackingStore::flush(const QRegion ®ion, QWindow *win, const QPoint &off } #endif - d_ptr->platformBackingStore->flush(win, QHighDpi::toNativePixels(region, d_ptr->window), offset); + d_ptr->platformBackingStore->flush(win, QHighDpi::toNativeLocalRegion(region, d_ptr->window), offset); } /*! @@ -182,7 +182,10 @@ QWindow* QBackingStore::window() const void QBackingStore::beginPaint(const QRegion ®ion) { - d_ptr->platformBackingStore->beginPaint(QHighDpi::toNativePixels(region, d_ptr->window)); + if (d_ptr->highDpiBackingstore && + d_ptr->highDpiBackingstore->devicePixelRatio() != d_ptr->window->devicePixelRatio()) + resize(size()); + d_ptr->platformBackingStore->beginPaint(QHighDpi::toNativeLocalRegion(region, d_ptr->window)); } /*! @@ -226,7 +229,7 @@ bool QBackingStore::scroll(const QRegion &area, int dx, int dy) Q_UNUSED(dx); Q_UNUSED(dy); - return d_ptr->platformBackingStore->scroll(QHighDpi::toNativePixels(area, d_ptr->window), QHighDpi::toNativePixels(dx, d_ptr->window), QHighDpi::toNativePixels(dy, d_ptr->window)); + return d_ptr->platformBackingStore->scroll(QHighDpi::toNativeLocalRegion(area, d_ptr->window), QHighDpi::toNativePixels(dx, d_ptr->window), QHighDpi::toNativePixels(dy, d_ptr->window)); } void QBackingStore::setStaticContents(const QRegion ®ion) diff --git a/src/plugins/platforms/xcb/qxcbbackingstore.cpp b/src/plugins/platforms/xcb/qxcbbackingstore.cpp index e59e5cb99c..e13afed4d4 100644 --- a/src/plugins/platforms/xcb/qxcbbackingstore.cpp +++ b/src/plugins/platforms/xcb/qxcbbackingstore.cpp @@ -315,7 +315,7 @@ void QXcbBackingStore::beginPaint(const QRegion ®ion) return; int dpr = int(m_image->image()->devicePixelRatio()); - const int windowDpr = int(QHighDpi::fromNativePixels(window()->devicePixelRatio())); + const int windowDpr = int(QHighDpi::fromNativePixels(window()->devicePixelRatio(), window())); if (windowDpr != dpr) { resize(window()->size(), QRegion()); dpr = int(m_image->image()->devicePixelRatio()); @@ -385,7 +385,7 @@ void QXcbBackingStore::flush(QWindow *window, const QRegion ®ion, const QPoin QSize imageSize = m_image->size() / dpr; //because we multiply with the DPR later QRegion clipped = region; - clipped &= QHighDpi::toNativePixels(QRect(0, 0, window->width(), window->height())); + clipped &= QRect(QPoint(), QHighDpi::toNativePixels(window->size(), window)); clipped &= QRect(0, 0, imageSize.width(), imageSize.height()).translated(-offset); QRect bounds = clipped.boundingRect(); diff --git a/src/plugins/platforms/xcb/qxcbwindow.cpp b/src/plugins/platforms/xcb/qxcbwindow.cpp index c3e61e5847..df64261e7a 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.cpp +++ b/src/plugins/platforms/xcb/qxcbwindow.cpp @@ -424,8 +424,8 @@ void QXcbWindow::create() } else if (minimumSize.width() > 0 || minimumSize.height() > 0) { rect.setSize(minimumSize); } else { - rect.setWidth(QHighDpi::toNativePixels(int(defaultWindowWidth))); - rect.setHeight(QHighDpi::toNativePixels(int(defaultWindowHeight))); + rect.setWidth(QHighDpi::toNativePixels(int(defaultWindowWidth), platformScreen->QPlatformScreen::screen())); + rect.setHeight(QHighDpi::toNativePixels(int(defaultWindowHeight), platformScreen->QPlatformScreen::screen())); } xcb_window_t xcb_parent_id = platformScreen->root(); @@ -680,11 +680,11 @@ void QXcbWindow::setGeometry(const QRect &rect) propagateSizeHints(); - QXcbScreen *currentScreen = xcbScreen(); + QXcbScreen *currentScreen = m_xcbScreen; QXcbScreen *newScreen = parent() ? parentScreen() : static_cast<QXcbScreen*>(screenForGeometry(rect)); if (!newScreen) - newScreen = currentScreen; + newScreen = xcbScreen(); m_xcbScreen = newScreen; const QRect xRect = mapToNative(rect, newScreen); @@ -2000,16 +2000,20 @@ void QXcbWindow::handleClientMessageEvent(const xcb_client_message_event_t *even QXcbScreen *QXcbWindow::screenForNativeGeometry(const QRect &newGeometry) const { QXcbScreen *currentScreen = xcbScreen(); + QXcbScreen *fallback = currentScreen; + QPoint center = newGeometry.center(); if (!currentScreen && QGuiApplication::primaryScreen()) currentScreen = static_cast<QXcbScreen*>(QGuiApplication::primaryScreen()->handle()); - if (currentScreen && !parent() && !currentScreen->nativeGeometry().intersects(newGeometry)) { + if (currentScreen && !parent() && !currentScreen->nativeGeometry().contains(center)) { Q_FOREACH (QPlatformScreen* screen, currentScreen->virtualSiblings()) { QXcbScreen *xcbScreen = static_cast<QXcbScreen*>(screen); - if (xcbScreen->nativeGeometry().intersects(newGeometry)) + if (xcbScreen->nativeGeometry().contains(center)) return xcbScreen; + if (xcbScreen->nativeGeometry().intersects(newGeometry)) + fallback = xcbScreen; } } - return currentScreen; + return fallback; } void QXcbWindow::handleConfigureNotifyEvent(const xcb_configure_notify_event_t *event) |