diff options
author | Benjamin Poulain <benjamin.poulain@nokia.com> | 2009-07-07 14:24:49 (GMT) |
---|---|---|
committer | Benjamin Poulain <benjamin.poulain@nokia.com> | 2009-07-07 15:04:14 (GMT) |
commit | fbc384f1bc1dd57e4af8e008b9db000b6ff82a37 (patch) | |
tree | ee7f8c03415f954e57d457711e9aa582778086c5 | |
parent | 424e2e68f9a3f556ad2d06e2fbceac0d48c060be (diff) | |
download | Qt-fbc384f1bc1dd57e4af8e008b9db000b6ff82a37.zip Qt-fbc384f1bc1dd57e4af8e008b9db000b6ff82a37.tar.gz Qt-fbc384f1bc1dd57e4af8e008b9db000b6ff82a37.tar.bz2 |
On Mac OS X, translate the wrect to the coordinates on screen
In the following configuration, wrect was off-screen and the widget was
not painted:
-scroll area "A"
-contains another scrollarea "B" with 2*WRECT_MAX < size < XCOORD_MAX
-the widget contained in B has size > XCOORD_MAX
-A is scrolled to the the bottom
To fix the issue, wrect is moved to the area where the top level window
is in the widget coordinate.
Task-number: 144779
Reviewed-by: nrc
-rw-r--r-- | src/gui/kernel/qwidget_mac.mm | 23 | ||||
-rw-r--r-- | tests/auto/qwidget/tst_qwidget.cpp | 35 |
2 files changed, 51 insertions, 7 deletions
diff --git a/src/gui/kernel/qwidget_mac.mm b/src/gui/kernel/qwidget_mac.mm index b0531ec..48e174b 100644 --- a/src/gui/kernel/qwidget_mac.mm +++ b/src/gui/kernel/qwidget_mac.mm @@ -3823,7 +3823,6 @@ void QWidgetPrivate::setWSGeometry(bool dontShow, const QRect &oldRect) Qt coordinate system for parent X coordinate system for parent (relative to parent's wrect). */ - QRect wrectRange(-WRECT_MAX,-WRECT_MAX, 2*WRECT_MAX, 2*WRECT_MAX); QRect wrect; //xrect is the X geometry of my X widget. (starts out in parent's Qt coord sys, and ends up in parent's X coord sys) QRect xrect = data.crect; @@ -3845,6 +3844,7 @@ void QWidgetPrivate::setWSGeometry(bool dontShow, const QRect &oldRect) parentWRect = QRect(tmpRect.origin.x, tmpRect.origin.y, tmpRect.size.width, tmpRect.size.height); } else { + const QRect wrectRange(-WRECT_MAX,-WRECT_MAX, 2*WRECT_MAX, 2*WRECT_MAX); parentWRect = wrectRange; } } else { @@ -3900,15 +3900,24 @@ void QWidgetPrivate::setWSGeometry(bool dontShow, const QRect &oldRect) } } - if (xrect.height() > XCOORD_MAX || xrect.width() > XCOORD_MAX) { + const QRect validRange(-XCOORD_MAX,-XCOORD_MAX, 2*XCOORD_MAX, 2*XCOORD_MAX); + if (!validRange.contains(xrect)) { // we are too big, and must clip - xrect &=wrectRange; + QPoint screenOffset(0, 0); // offset of the part being on screen + const QWidget *parentWidget = q->parentWidget(); + while (parentWidget) { + screenOffset -= parentWidget->data->crect.topLeft(); + parentWidget = parentWidget->parentWidget(); + } + QRect cropRect(screenOffset.x() - WRECT_MAX, + screenOffset.y() - WRECT_MAX, + 2*WRECT_MAX, + 2*WRECT_MAX); + + xrect &=cropRect; wrect = xrect; - wrect.translate(-data.crect.topLeft()); - //parent's X coord system is equal to parent's Qt coord - //sys, so we don't need to map xrect. + wrect.translate(-data.crect.topLeft()); // translate wrect in my Qt coordinates } - } // unmap if we are outside the valid window system coord system diff --git a/tests/auto/qwidget/tst_qwidget.cpp b/tests/auto/qwidget/tst_qwidget.cpp index 04ec77d..fa36496 100644 --- a/tests/auto/qwidget/tst_qwidget.cpp +++ b/tests/auto/qwidget/tst_qwidget.cpp @@ -353,6 +353,7 @@ private slots: void toplevelLineEditFocus(); void focusWidget_task254563(); + void rectOutsideCoordinatesLimit_task144779(); private: bool ensureScreenSize(int width, int height); @@ -9117,5 +9118,39 @@ void tst_QWidget::focusWidget_task254563() QVERIFY(top.focusWidget() != widget); //dangling pointer } +void tst_QWidget::rectOutsideCoordinatesLimit_task144779() +{ + QWidget main; + QPalette palette; + palette.setColor(QPalette::Window, Qt::red); + main.setPalette(palette); + main.resize(400, 400); + + QWidget *offsetWidget = new QWidget(&main); + offsetWidget->setGeometry(0, -14600, 400, 15000); + + // big widget is too big for the coordinates, it must be limited by wrect + // if wrect is not at the right position because of offsetWidget, bigwidget + // is not painted correctly + QWidget *bigWidget = new QWidget(offsetWidget); + bigWidget->setGeometry(0, 0, 400, 50000); + palette.setColor(QPalette::Window, Qt::green); + bigWidget->setPalette(palette); + bigWidget->setAutoFillBackground(true); + + main.show(); +#ifdef Q_WS_X11 + qt_x11_wait_for_window_manager(&main); +#endif + QTest::qWait(100); + QPixmap pixmap = QPixmap::grabWindow(main.winId()); + + QPixmap correct(main.size()); + correct.fill(Qt::green); + + QRect center(100, 100, 200, 200); // to avoid the decorations + QCOMPARE(pixmap.toImage().copy(center), correct.toImage().copy(center)); +} + QTEST_MAIN(tst_QWidget) #include "tst_qwidget.moc" |