diff options
author | Volker Hilsheimer <volker.hilsheimer@qt.io> | 2020-04-22 10:53:04 +0200 |
---|---|---|
committer | Volker Hilsheimer <volker.hilsheimer@qt.io> | 2020-05-13 15:07:55 +0000 |
commit | 92df790f46b3a8b17aec2f385d6472fd3f8647f6 (patch) | |
tree | 93b09b2ea2a3fb426368590a3967efbe8f364791 /tests/auto/widgets/kernel | |
parent | 01b2ea83aa0e8e1d624f6c25d78bb5184cd35483 (diff) |
QApplication: refactor delivery and propagation of wheel events
Handle wheel grabbing via wheel_widget in a single place, and
propagate events in the same way for all (spontaneous) events.
Handle ScrollMomentum the same way as ScrollUpdate to allow
partial sequences.
Fix the incorrect ignoring of wheel events by default; like all
other input events, they are now again accepted by default and
ignored in the default event handler implementation of QWidget.
This way, implementing the handle suffices to accept the event.
Note that QWidget::wheelEvent doesn't need to be changed, as the
event is ignored there today (an oversight of the change made in
f253f4c3, perhaps).
This also fixes changing of direction of a wheel event while
the event sequence is grabbed by a widget.
Change-Id: Ia0f03c14dede80322d690ca50d085898a0497dbe
Fixes: QTBUG-67032
Task-number: QTBUG-79102
Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io>
Diffstat (limited to 'tests/auto/widgets/kernel')
-rw-r--r-- | tests/auto/widgets/kernel/qapplication/tst_qapplication.cpp | 73 |
1 files changed, 55 insertions, 18 deletions
diff --git a/tests/auto/widgets/kernel/qapplication/tst_qapplication.cpp b/tests/auto/widgets/kernel/qapplication/tst_qapplication.cpp index e341e0b756..c9857b4379 100644 --- a/tests/auto/widgets/kernel/qapplication/tst_qapplication.cpp +++ b/tests/auto/widgets/kernel/qapplication/tst_qapplication.cpp @@ -2150,33 +2150,53 @@ void tst_QApplication::touchEventPropagation() For scenario 2 "outer", the expectation is that the outer scrollarea handles all wheel events. */ -using PhaseList = QList<Qt::ScrollPhase>; +struct WheelEvent +{ + WheelEvent(Qt::ScrollPhase p = Qt::NoScrollPhase, Qt::Orientation o = Qt::Vertical) + : phase(p), orientation(o) + {} + Qt::ScrollPhase phase = Qt::NoScrollPhase; + Qt::Orientation orientation = Qt::Vertical; +}; +using WheelEventList = QList<WheelEvent>; void tst_QApplication::wheelEventPropagation_data() { - qRegisterMetaType<PhaseList>(); + qRegisterMetaType<WheelEventList>(); QTest::addColumn<bool>("innerScrolls"); - QTest::addColumn<PhaseList>("phases"); + QTest::addColumn<WheelEventList>("events"); QTest::addRow("inner, classic") << true - << PhaseList{Qt::NoScrollPhase, Qt::NoScrollPhase, Qt::NoScrollPhase}; + << WheelEventList{{}, {}, {}}; QTest::addRow("outer, classic") << false - << PhaseList{Qt::NoScrollPhase, Qt::NoScrollPhase, Qt::NoScrollPhase}; + << WheelEventList{{}, {}, {}}; QTest::addRow("inner, kinetic") << true - << PhaseList{Qt::ScrollBegin, Qt::ScrollUpdate, Qt::ScrollMomentum, Qt::ScrollEnd}; + << WheelEventList{Qt::ScrollBegin, Qt::ScrollUpdate, Qt::ScrollMomentum, Qt::ScrollEnd}; QTest::addRow("outer, kinetic") << false - << PhaseList{Qt::ScrollBegin, Qt::ScrollUpdate, Qt::ScrollMomentum, Qt::ScrollEnd}; + << WheelEventList{Qt::ScrollBegin, Qt::ScrollUpdate, Qt::ScrollMomentum, Qt::ScrollEnd}; + QTest::addRow("inner, partial kinetic") + << true + << WheelEventList{Qt::ScrollUpdate, Qt::ScrollMomentum, Qt::ScrollEnd}; + QTest::addRow("outer, partial kinetic") + << false + << WheelEventList{Qt::ScrollUpdate, Qt::ScrollMomentum, Qt::ScrollEnd}; + QTest::addRow("inner, changing direction") + << true + << WheelEventList{Qt::ScrollUpdate, {Qt::ScrollUpdate, Qt::Horizontal}, Qt::ScrollMomentum, Qt::ScrollEnd}; + QTest::addRow("outer, changing direction") + << false + << WheelEventList{Qt::ScrollUpdate, {Qt::ScrollUpdate, Qt::Horizontal}, Qt::ScrollMomentum, Qt::ScrollEnd}; } void tst_QApplication::wheelEventPropagation() { QFETCH(bool, innerScrolls); - QFETCH(PhaseList, phases); + QFETCH(WheelEventList, events); const QSize baseSize(500, 500); const QPointF center(baseSize.width() / 2, baseSize.height() / 2); @@ -2199,7 +2219,7 @@ void tst_QApplication::wheelEventPropagation() largeWidget.setFixedSize(baseSize * 8); // classic wheel events will be grabbed by the widget under the mouse, so don't place a trap - if (phases.at(0) == Qt::NoScrollPhase) + if (events.at(0).phase == Qt::NoScrollPhase) trap.hide(); // kinetic wheel events should all go to the first widget; place a trap else @@ -2220,24 +2240,41 @@ void tst_QApplication::wheelEventPropagation() auto innerVBar = innerArea.verticalScrollBar(); innerVBar->setObjectName("innerArea_vbar"); QCOMPARE(innerVBar->isVisible(), innerScrolls); + auto innerHBar = innerArea.horizontalScrollBar(); + innerHBar->setObjectName("innerArea_hbar"); + QCOMPARE(innerHBar->isVisible(), innerScrolls); auto outerVBar = outerArea.verticalScrollBar(); outerVBar->setObjectName("outerArea_vbar"); QVERIFY(outerVBar->isVisible()); + auto outerHBar = outerArea.horizontalScrollBar(); + outerHBar->setObjectName("outerArea_hbar"); + QVERIFY(outerHBar->isVisible()); const QPointF global(outerArea.mapToGlobal(center.toPoint())); - QSignalSpy innerSpy(innerVBar, &QAbstractSlider::valueChanged); - QSignalSpy outerSpy(outerVBar, &QAbstractSlider::valueChanged); + QSignalSpy innerVSpy(innerVBar, &QAbstractSlider::valueChanged); + QSignalSpy innerHSpy(innerHBar, &QAbstractSlider::valueChanged); + QSignalSpy outerVSpy(outerVBar, &QAbstractSlider::valueChanged); + QSignalSpy outerHSpy(outerHBar, &QAbstractSlider::valueChanged); - int count = 0; - for (const auto &phase : qAsConst(phases)) { + int vcount = 0; + int hcount = 0; + + for (const auto &event : qAsConst(events)) { + const QPoint pixelDelta = event.orientation == Qt::Vertical ? QPoint(0, -scrollStep) : QPoint(-scrollStep, 0); + const QPoint angleDelta = event.orientation == Qt::Vertical ? QPoint(0, -120) : QPoint(-120, 0); QWindowSystemInterface::handleWheelEvent(outerArea.windowHandle(), center, global, - QPoint(0, -scrollStep), QPoint(0, -120), Qt::NoModifier, - phase); - ++count; + pixelDelta, angleDelta, Qt::NoModifier, + event.phase); + if (event.orientation == Qt::Vertical) + ++vcount; + else + ++hcount; QCoreApplication::processEvents(); - QCOMPARE(innerSpy.count(), innerScrolls ? count : 0); - QCOMPARE(outerSpy.count(), innerScrolls ? 0 : count); + QCOMPARE(innerVSpy.count(), innerScrolls ? vcount : 0); + QCOMPARE(innerHSpy.count(), innerScrolls ? hcount : 0); + QCOMPARE(outerVSpy.count(), innerScrolls ? 0 : vcount); + QCOMPARE(outerHSpy.count(), innerScrolls ? 0 : hcount); } } |