aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRichard Moe Gustavsen <richard.gustavsen@qt.io>2022-03-14 12:22:50 +0100
committerRichard Moe Gustavsen <richard.gustavsen@qt.io>2022-04-05 14:09:30 +0000
commitbc93b587e655d21ceac06c9ab03f6c919e8a4f46 (patch)
tree9df642be25d90604d5f79b997db5e670339c6d4c
parentfe9d9b22f20ecfd119c4dcaf1d05f5b27906a49e (diff)
QQuickControl: let Control reject hover events
From testing Qt 6.1, a Control should not accept hover events, and as such, block hover events from propagating. This patch will make sure that QQuickControl rejects hover events, and thereby restore the behavior Qt had up till Qt 6.1. Fixes: QTBUG-101394 Fixes: QTBUG-100543 Fixes: QTBUG-100149 Fixes: QTBUG-98940 Fixes: QTBUG-98850 Fixes: QTBUG-95398 Change-Id: I2df9d0f9999ce074cab0c64accad9172b411fb63 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io> (cherry picked from commit 0c7b0a43064c8be452f4be74701f1dabce87f24c) Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
-rw-r--r--src/quicktemplates2/qquickcontrol.cpp7
-rw-r--r--tests/auto/quickcontrols2/CMakeLists.txt1
-rw-r--r--tests/auto/quickcontrols2/pointerhandlers/CMakeLists.txt39
-rw-r--r--tests/auto/quickcontrols2/pointerhandlers/data/controlandmousearea.qml49
-rw-r--r--tests/auto/quickcontrols2/pointerhandlers/data/controlinsidecontrol.qml31
-rw-r--r--tests/auto/quickcontrols2/pointerhandlers/tst_pointerhandlers.cpp195
-rw-r--r--tests/auto/quickcontrols2/qquickdrawer/tst_qquickdrawer.cpp2
7 files changed, 319 insertions, 5 deletions
diff --git a/src/quicktemplates2/qquickcontrol.cpp b/src/quicktemplates2/qquickcontrol.cpp
index 1286ce3907..51ba596af2 100644
--- a/src/quicktemplates2/qquickcontrol.cpp
+++ b/src/quicktemplates2/qquickcontrol.cpp
@@ -1957,21 +1957,20 @@ void QQuickControl::hoverEnterEvent(QHoverEvent *event)
{
Q_D(QQuickControl);
setHovered(d->hoverEnabled);
- event->setAccepted(d->hoverEnabled);
+ event->ignore();
}
void QQuickControl::hoverMoveEvent(QHoverEvent *event)
{
Q_D(QQuickControl);
setHovered(d->hoverEnabled && contains(event->position()));
- event->setAccepted(d->hoverEnabled);
+ event->ignore();
}
void QQuickControl::hoverLeaveEvent(QHoverEvent *event)
{
- Q_D(QQuickControl);
setHovered(false);
- event->setAccepted(d->hoverEnabled);
+ event->ignore();
}
#endif
diff --git a/tests/auto/quickcontrols2/CMakeLists.txt b/tests/auto/quickcontrols2/CMakeLists.txt
index b3b655f2cd..03baed703a 100644
--- a/tests/auto/quickcontrols2/CMakeLists.txt
+++ b/tests/auto/quickcontrols2/CMakeLists.txt
@@ -13,6 +13,7 @@ endif()
add_subdirectory(font)
add_subdirectory(palette)
add_subdirectory(platform)
+add_subdirectory(pointerhandlers)
add_subdirectory(pressandhold)
if(NOT ANDROID) # QTBUG-100176
add_subdirectory(qquickapplicationwindow)
diff --git a/tests/auto/quickcontrols2/pointerhandlers/CMakeLists.txt b/tests/auto/quickcontrols2/pointerhandlers/CMakeLists.txt
new file mode 100644
index 0000000000..7777ade3c2
--- /dev/null
+++ b/tests/auto/quickcontrols2/pointerhandlers/CMakeLists.txt
@@ -0,0 +1,39 @@
+#####################################################################
+## tst_pointerhandlers Test:
+#####################################################################
+
+# Collect test data
+file(GLOB_RECURSE test_data_glob
+ RELATIVE ${CMAKE_CURRENT_SOURCE_DIR}
+ data/*)
+list(APPEND test_data ${test_data_glob})
+
+qt_internal_add_test(tst_pointerhandlers
+ SOURCES
+ tst_pointerhandlers.cpp
+ DEFINES
+ QT_QMLTEST_DATADIR=\\\"${CMAKE_CURRENT_SOURCE_DIR}/data\\\"
+ PUBLIC_LIBRARIES
+ Qt::CorePrivate
+ Qt::Gui
+ Qt::GuiPrivate
+ Qt::QmlModelsPrivate
+ Qt::QmlPrivate
+ Qt::QuickPrivate
+ Qt::QuickTest
+ Qt::QuickTestUtilsPrivate
+ Qt::QuickControls2
+ Qt::QuickControls2Private
+ Qt::QuickTemplates2Private
+ TESTDATA ${test_data}
+)
+
+qt_internal_extend_target(tst_pointerhandlers CONDITION ANDROID OR IOS
+ DEFINES
+ QT_QMLTEST_DATADIR=\\\":/data\\\"
+)
+
+qt_internal_extend_target(tst_pointerhandlers CONDITION NOT ANDROID AND NOT IOS
+ DEFINES
+ QT_QMLTEST_DATADIR=\\\"${CMAKE_CURRENT_SOURCE_DIR}/data\\\"
+)
diff --git a/tests/auto/quickcontrols2/pointerhandlers/data/controlandmousearea.qml b/tests/auto/quickcontrols2/pointerhandlers/data/controlandmousearea.qml
new file mode 100644
index 0000000000..00c680453a
--- /dev/null
+++ b/tests/auto/quickcontrols2/pointerhandlers/data/controlandmousearea.qml
@@ -0,0 +1,49 @@
+import QtQuick
+import QtQuick.Controls
+
+Item {
+ width: 640
+ height: 480
+ visible: true
+
+ property alias outerMouseArea: outerMouseArea
+ property alias buttonInTheMiddle: buttonInTheMiddle
+ property alias innerMouseArea: innerMouseArea
+
+ MouseArea {
+ id: outerMouseArea
+ x: 10
+ y: 10
+ width: 200
+ height: 200
+ hoverEnabled: true
+ Rectangle {
+ anchors.fill: parent
+ border.width: 1
+ color: outerMouseArea.containsMouse ? "cyan" : "transparent"
+ }
+
+ Button {
+ id: buttonInTheMiddle
+ width: parent.width - 20
+ height: parent.height - 20
+ anchors.right: parent.right
+ anchors.bottom: parent.bottom
+ text: hovered ? "hovered" : ""
+
+ MouseArea {
+ id: innerMouseArea
+ width: parent.width - 20
+ height: parent.height - 20
+ anchors.right: parent.right
+ anchors.bottom: parent.bottom
+ hoverEnabled: true
+ Rectangle {
+ anchors.fill: parent
+ border.width: 1
+ color: innerMouseArea.containsMouse ? "yellow" : "transparent"
+ }
+ }
+ }
+ }
+}
diff --git a/tests/auto/quickcontrols2/pointerhandlers/data/controlinsidecontrol.qml b/tests/auto/quickcontrols2/pointerhandlers/data/controlinsidecontrol.qml
new file mode 100644
index 0000000000..69d855ec57
--- /dev/null
+++ b/tests/auto/quickcontrols2/pointerhandlers/data/controlinsidecontrol.qml
@@ -0,0 +1,31 @@
+import QtQuick
+import QtQuick.Controls
+
+Item {
+ width: 640
+ height: 480
+ visible: true
+
+ property alias outerButton: outerButton
+ property alias innerButton: innerButton
+
+ Button {
+ id: outerButton
+ x: 5
+ y: 5
+ width: 200
+ height: 200
+ hoverEnabled: true
+ text: hovered ? "hovered" : ""
+
+ Button {
+ id: innerButton
+ width: parent.width - 20
+ height: parent.height - 20
+ anchors.right: parent.right
+ anchors.bottom: parent.bottom
+ text: hovered ? "hovered" : ""
+ opacity: 0.5
+ }
+ }
+}
diff --git a/tests/auto/quickcontrols2/pointerhandlers/tst_pointerhandlers.cpp b/tests/auto/quickcontrols2/pointerhandlers/tst_pointerhandlers.cpp
new file mode 100644
index 0000000000..d2e28b7044
--- /dev/null
+++ b/tests/auto/quickcontrols2/pointerhandlers/tst_pointerhandlers.cpp
@@ -0,0 +1,195 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the QtQuick module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include <QtTest/QtTest>
+#include <QtQuickTest/quicktest.h>
+
+#include <QtQuick/qquickview.h>
+#include <QtQuick/private/qquickmousearea_p.h>
+
+#include <QtQml/qqmlengine.h>
+#include <QtQml/qqmlcontext.h>
+
+#include <QtQuickTemplates2/private/qquickbutton_p.h>
+
+#include <QtQuickTestUtils/private/qmlutils_p.h>
+#include <QtQuickTestUtils/private/viewtestutils_p.h>
+#include <QtQuickTestUtils/private/visualtestutils_p.h>
+
+using namespace QQuickViewTestUtils;
+using namespace QQuickVisualTestUtils;
+
+class tst_pointerhandlers : public QQmlDataTest
+{
+ Q_OBJECT
+public:
+ tst_pointerhandlers();
+
+private slots:
+ void hover_controlInsideControl();
+ void hover_controlAndMouseArea();
+};
+
+tst_pointerhandlers::tst_pointerhandlers()
+ : QQmlDataTest(QT_QMLTEST_DATADIR)
+{
+}
+
+void tst_pointerhandlers::hover_controlInsideControl()
+{
+ // Test that if you move the mouse over a control that is
+ // a child of another control, both controls end up hovered.
+ // A control should basically not block (accept) hover events.
+ QQuickView view(testFileUrl("controlinsidecontrol.qml"));
+ QCOMPARE(view.status(), QQuickView::Ready);
+ view.show();
+ QVERIFY(QTest::qWaitForWindowExposed(&view));
+
+ QQuickItem *rootItem = view.rootObject();
+ QVERIFY(rootItem);
+ QQuickWindow *window = rootItem->window();
+ QVERIFY(window);
+
+ const auto context = qmlContext(rootItem);
+ auto outerButton = context->contextProperty("outerButton").value<QQuickButton *>();
+ auto innerButton = context->contextProperty("innerButton").value<QQuickButton *>();
+ QVERIFY(outerButton);
+ QVERIFY(innerButton);
+
+ const QPoint posInWindow(1, 1);
+ const QPoint posOnOuterButton = rootItem->mapFromItem(outerButton, QPointF(0, 0)).toPoint();
+ const QPoint posOnInnerButton = rootItem->mapFromItem(innerButton, QPointF(0, 0)).toPoint();
+
+ // Start by moving the mouse to the window
+ QTest::mouseMove(window, posInWindow);
+ QCOMPARE(outerButton->isHovered(), false);
+ QCOMPARE(innerButton->isHovered(), false);
+
+ // Move the mouse over the outer control
+ QTest::mouseMove(window, posOnOuterButton);
+ QCOMPARE(outerButton->isHovered(), true);
+ QCOMPARE(innerButton->isHovered(), false);
+
+ // Move the mouse over the inner control
+ QTest::mouseMove(window, posOnInnerButton);
+ QCOMPARE(outerButton->isHovered(), true);
+ QCOMPARE(innerButton->isHovered(), true);
+
+ // Move the mouse over the outer control again
+ QTest::mouseMove(window, posOnOuterButton);
+ QCOMPARE(outerButton->isHovered(), true);
+ QCOMPARE(innerButton->isHovered(), false);
+
+ // Move the mouse outside all controls
+ QTest::mouseMove(window, posInWindow);
+ QCOMPARE(outerButton->isHovered(), false);
+ QCOMPARE(innerButton->isHovered(), false);
+}
+
+void tst_pointerhandlers::hover_controlAndMouseArea()
+{
+ QQuickView view(testFileUrl("controlandmousearea.qml"));
+ QCOMPARE(view.status(), QQuickView::Ready);
+ view.show();
+ QVERIFY(QTest::qWaitForWindowExposed(&view));
+
+ QQuickItem *rootItem = view.rootObject();
+ QVERIFY(rootItem);
+ QQuickWindow *window = rootItem->window();
+ QVERIFY(window);
+
+ const auto context = qmlContext(rootItem);
+ auto outerMouseArea = context->contextProperty("outerMouseArea").value<QQuickMouseArea *>();
+ auto buttonInTheMiddle = context->contextProperty("buttonInTheMiddle").value<QQuickButton *>();
+ auto innerMouseArea = context->contextProperty("innerMouseArea").value<QQuickMouseArea *>();
+ QVERIFY(outerMouseArea);
+ QVERIFY(buttonInTheMiddle);
+ QVERIFY(innerMouseArea);
+
+ const QPoint posInWindow(1, 1);
+ const QPoint posOnOuterMouseArea = rootItem->mapFromItem(outerMouseArea, QPointF(0, 0)).toPoint();
+ const QPoint posOnButtonInTheMiddle = rootItem->mapFromItem(buttonInTheMiddle, QPointF(0, 0)).toPoint();
+ const QPoint posOnInnerMouseArea = rootItem->mapFromItem(innerMouseArea, QPointF(0, 0)).toPoint();
+
+ // Start by moving the mouse to the window
+ QTest::mouseMove(window, posInWindow);
+ QCOMPARE(outerMouseArea->hovered(), false);
+ QCOMPARE(buttonInTheMiddle->isHovered(), false);
+ QCOMPARE(innerMouseArea->hovered(), false);
+
+ // Move the mouse over the outer mousearea
+ QTest::mouseMove(window, posOnOuterMouseArea);
+ QCOMPARE(outerMouseArea->hovered(), true);
+ QCOMPARE(buttonInTheMiddle->isHovered(), false);
+ QCOMPARE(innerMouseArea->hovered(), false);
+
+ // Move the mouse over the button in the middle
+ QTest::mouseMove(window, posOnButtonInTheMiddle);
+ QCOMPARE(outerMouseArea->hovered(), true);
+ QCOMPARE(buttonInTheMiddle->isHovered(), true);
+ QCOMPARE(innerMouseArea->hovered(), false);
+
+ // Move the mouse over the inner mousearea
+ QTest::mouseMove(window, posOnInnerMouseArea);
+ QCOMPARE(outerMouseArea->hovered(), true);
+ QCOMPARE(buttonInTheMiddle->isHovered(), true);
+ QCOMPARE(innerMouseArea->hovered(), true);
+
+ // Move the mouse over the button in the middle again
+ QTest::mouseMove(window, posOnButtonInTheMiddle);
+ QCOMPARE(outerMouseArea->hovered(), true);
+ QCOMPARE(buttonInTheMiddle->isHovered(), true);
+ QCOMPARE(innerMouseArea->hovered(), false);
+
+ // Move the mouse over the outer mousearea again
+ QTest::mouseMove(window, posOnOuterMouseArea);
+ QCOMPARE(outerMouseArea->hovered(), true);
+ QCOMPARE(buttonInTheMiddle->isHovered(), false);
+ QCOMPARE(innerMouseArea->hovered(), false);
+
+ // Move the mouse outside all items
+ QTest::mouseMove(window, posInWindow);
+ QCOMPARE(outerMouseArea->hovered(), false);
+ QCOMPARE(buttonInTheMiddle->isHovered(), false);
+ QCOMPARE(innerMouseArea->hovered(), false);
+}
+
+QTEST_MAIN(tst_pointerhandlers)
+
+#include "tst_pointerhandlers.moc"
diff --git a/tests/auto/quickcontrols2/qquickdrawer/tst_qquickdrawer.cpp b/tests/auto/quickcontrols2/qquickdrawer/tst_qquickdrawer.cpp
index edcd1e7173..249bd43c1f 100644
--- a/tests/auto/quickcontrols2/qquickdrawer/tst_qquickdrawer.cpp
+++ b/tests/auto/quickcontrols2/qquickdrawer/tst_qquickdrawer.cpp
@@ -603,7 +603,7 @@ void tst_QQuickDrawer::hover()
QTest::mouseMove(window, QPoint(2, 2));
QVERIFY(!backgroundButton->isHovered());
QVERIFY(drawerButton->isHovered());
- QVERIFY(!drawerItem->isHovered());
+ QVERIFY(drawerItem->isHovered());
QSignalSpy closedSpy(drawer, SIGNAL(closed()));
QVERIFY(closedSpy.isValid());