summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorShawn Rutledge <shawn.rutledge@qt.io>2022-01-31 16:09:38 +0100
committerQt Cherry-pick Bot <cherrypick_bot@qt-project.org>2022-02-03 18:07:47 +0000
commita28fd4e54d00f5a23bd191f9dbba5552b927def8 (patch)
treea877f0e8590ef50a87918c1aa33bf657305568d0
parentad1a7e84a9b084ebb946a20e97cbb7fdb6458f8e (diff)
Add a QHoverEvent ctor taking global mouse position; deprecate the other
The QSinglePointEvent ctor assumes that the given globalPos is correct, so it was wrong that the QHoverEvent ctor passed along a local position as global. It's better to require globalPos as an argument; and in fact it seems that everywhere we construct a QHoverEvent, global position is available, or possible to get by transformation (which is better than resorting to QCursor::pos()). Also, don't convert to QPoint: pointer events have qreal resolution and there's no reason to truncate them. Fixes: QTBUG-100324 Change-Id: I919455da36265988d3d149eb97563c9ed0d2c660 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io> (cherry picked from commit 0a64a044b6c1c44b0a2bb2be5e70fda920f5f6bf) Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
-rw-r--r--src/gui/kernel/qevent.cpp22
-rw-r--r--src/gui/kernel/qevent.h6
-rw-r--r--src/widgets/kernel/qapplication.cpp18
-rw-r--r--tests/auto/widgets/itemviews/qheaderview/tst_qheaderview.cpp6
-rw-r--r--tests/auto/widgets/widgets/qmainwindow/tst_qmainwindow.cpp4
5 files changed, 42 insertions, 14 deletions
diff --git a/src/gui/kernel/qevent.cpp b/src/gui/kernel/qevent.cpp
index 5e7c2a574c..ec2711b582 100644
--- a/src/gui/kernel/qevent.cpp
+++ b/src/gui/kernel/qevent.cpp
@@ -1069,6 +1069,27 @@ Qt::MouseEventFlags QMouseEvent::flags() const
QEvent::HoverLeave, or QEvent::HoverMove.
The \a pos is the current mouse cursor's position relative to the
+ receiving widget, \a oldPos is its previous such position, and
+ \a globalPos is the mouse position in absolute coordinates.
+ \a modifiers hold the state of all keyboard modifiers at the time
+ of the event.
+*/
+QHoverEvent::QHoverEvent(Type type, const QPointF &pos, const QPointF &globalPos, const QPointF &oldPos,
+ Qt::KeyboardModifiers modifiers, const QPointingDevice *device)
+ : QSinglePointEvent(type, device, pos, pos, globalPos, Qt::NoButton, Qt::NoButton, modifiers), m_oldPos(oldPos)
+{
+}
+
+#if QT_DEPRECATED_SINCE(6, 3)
+/*!
+ \deprecated [6.3] Use the other constructor instead (global position is required).
+
+ Constructs a hover event object originating from \a device.
+
+ The \a type parameter must be QEvent::HoverEnter,
+ QEvent::HoverLeave, or QEvent::HoverMove.
+
+ The \a pos is the current mouse cursor's position relative to the
receiving widget, while \a oldPos is its previous such position.
\a modifiers hold the state of all keyboard modifiers at the time
of the event.
@@ -1078,6 +1099,7 @@ QHoverEvent::QHoverEvent(Type type, const QPointF &pos, const QPointF &oldPos,
: QSinglePointEvent(type, device, pos, pos, pos, Qt::NoButton, Qt::NoButton, modifiers), m_oldPos(oldPos)
{
}
+#endif
/*!
\internal
diff --git a/src/gui/kernel/qevent.h b/src/gui/kernel/qevent.h
index 2f8630bad0..3c6ddac644 100644
--- a/src/gui/kernel/qevent.h
+++ b/src/gui/kernel/qevent.h
@@ -281,9 +281,15 @@ class Q_GUI_EXPORT QHoverEvent : public QSinglePointEvent
{
Q_EVENT_DISABLE_COPY(QHoverEvent);
public:
+ QHoverEvent(Type type, const QPointF &pos, const QPointF &globalPos, const QPointF &oldPos,
+ Qt::KeyboardModifiers modifiers = Qt::NoModifier,
+ const QPointingDevice *device = QPointingDevice::primaryPointingDevice());
+#if QT_DEPRECATED_SINCE(6, 3)
+ QT_DEPRECATED_VERSION_X_6_3("Use the other constructor")
QHoverEvent(Type type, const QPointF &pos, const QPointF &oldPos,
Qt::KeyboardModifiers modifiers = Qt::NoModifier,
const QPointingDevice *device = QPointingDevice::primaryPointingDevice());
+#endif
~QHoverEvent();
QHoverEvent *clone() const override { return new QHoverEvent(*this); }
diff --git a/src/widgets/kernel/qapplication.cpp b/src/widgets/kernel/qapplication.cpp
index f3deab05a1..62870a25b7 100644
--- a/src/widgets/kernel/qapplication.cpp
+++ b/src/widgets/kernel/qapplication.cpp
@@ -2073,7 +2073,7 @@ void QApplicationPrivate::dispatchEnterLeave(QWidget* enter, QWidget* leave, con
if (w->testAttribute(Qt::WA_Hover) &&
(!QApplication::activePopupWidget() || QApplication::activePopupWidget() == w->window())) {
Q_ASSERT(instance());
- QHoverEvent he(QEvent::HoverLeave, QPoint(-1, -1), w->mapFromGlobal(QApplicationPrivate::instance()->hoverGlobalPos),
+ QHoverEvent he(QEvent::HoverLeave, QPointF(-1, -1), globalPosF, w->mapFromGlobal(globalPosF),
QGuiApplication::keyboardModifiers());
qApp->d_func()->notify_helper(w, &he);
}
@@ -2081,19 +2081,19 @@ void QApplicationPrivate::dispatchEnterLeave(QWidget* enter, QWidget* leave, con
}
if (!enterList.isEmpty()) {
// Guard against QGuiApplicationPrivate::lastCursorPosition initialized to qInf(), qInf().
- const QPoint globalPos = qIsInf(globalPosF.x())
- ? QPoint(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX)
- : globalPosF.toPoint();
- const QPoint windowPos = qAsConst(enterList).back()->window()->mapFromGlobal(globalPos);
+ const QPointF globalPos = qIsInf(globalPosF.x())
+ ? QPointF(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX)
+ : globalPosF;
+ const QPointF windowPos = qAsConst(enterList).back()->window()->mapFromGlobal(globalPos);
for (auto it = enterList.crbegin(), end = enterList.crend(); it != end; ++it) {
auto *w = *it;
if (!QApplication::activeModalWidget() || QApplicationPrivate::tryModalHelper(w, nullptr)) {
const QPointF localPos = w->mapFromGlobal(globalPos);
- QEnterEvent enterEvent(localPos, windowPos, globalPosF);
+ QEnterEvent enterEvent(localPos, windowPos, globalPos);
QCoreApplication::sendEvent(w, &enterEvent);
if (w->testAttribute(Qt::WA_Hover) &&
(!QApplication::activePopupWidget() || QApplication::activePopupWidget() == w->window())) {
- QHoverEvent he(QEvent::HoverEnter, localPos, QPoint(-1, -1),
+ QHoverEvent he(QEvent::HoverEnter, localPos, QPointF(-1, -1), globalPos,
QGuiApplication::keyboardModifiers());
qApp->d_func()->notify_helper(w, &he);
}
@@ -2843,11 +2843,11 @@ bool QApplication::notify(QObject *receiver, QEvent *e)
w = static_cast<QWidget *>(receiver);
relpos = mouse->position().toPoint();
- QPoint diff = relpos - w->mapFromGlobal(d->hoverGlobalPos);
+ QPoint diff = relpos - w->mapFromGlobal(mouse->globalPosition().toPoint());
while (w) {
if (w->testAttribute(Qt::WA_Hover) &&
(!QApplication::activePopupWidget() || QApplication::activePopupWidget() == w->window())) {
- QHoverEvent he(QEvent::HoverMove, relpos, relpos - diff, mouse->modifiers());
+ QHoverEvent he(QEvent::HoverMove, relpos, mouse->globalPosition(), relpos - diff, mouse->modifiers());
d->notify_helper(w, &he);
}
if (w->isWindow() || w->testAttribute(Qt::WA_NoMousePropagation))
diff --git a/tests/auto/widgets/itemviews/qheaderview/tst_qheaderview.cpp b/tests/auto/widgets/itemviews/qheaderview/tst_qheaderview.cpp
index 8856a8ef6a..d81c10573e 100644
--- a/tests/auto/widgets/itemviews/qheaderview/tst_qheaderview.cpp
+++ b/tests/auto/widgets/itemviews/qheaderview/tst_qheaderview.cpp
@@ -1511,11 +1511,11 @@ void tst_QHeaderView::testEvent()
void protected_QHeaderView::testEvent()
{
// No crashy please
- QHoverEvent enterEvent(QEvent::HoverEnter, QPoint(), QPoint());
+ QHoverEvent enterEvent(QEvent::HoverEnter, QPoint(), QPoint(), QPoint());
event(&enterEvent);
- QHoverEvent eventLeave(QEvent::HoverLeave, QPoint(), QPoint());
+ QHoverEvent eventLeave(QEvent::HoverLeave, QPoint(), QPoint(), QPoint());
event(&eventLeave);
- QHoverEvent eventMove(QEvent::HoverMove, QPoint(), QPoint());
+ QHoverEvent eventMove(QEvent::HoverMove, QPoint(), QPoint(), QPoint());
event(&eventMove);
}
diff --git a/tests/auto/widgets/widgets/qmainwindow/tst_qmainwindow.cpp b/tests/auto/widgets/widgets/qmainwindow/tst_qmainwindow.cpp
index f2a7981b4c..6bfe7f5371 100644
--- a/tests/auto/widgets/widgets/qmainwindow/tst_qmainwindow.cpp
+++ b/tests/auto/widgets/widgets/qmainwindow/tst_qmainwindow.cpp
@@ -1859,11 +1859,11 @@ void tst_QMainWindow::setCursor()
QVERIFY(QTest::qWaitForWindowActive(&mw));
QCOMPARE(cur.shape(), mw.cursor().shape());
- QHoverEvent enterE(QEvent::HoverEnter, QPoint(10,10), QPoint());
+ QHoverEvent enterE(QEvent::HoverEnter, QPoint(10,10), QPoint(), QPoint());
mw.event(&enterE);
QCOMPARE(cur.shape(), mw.cursor().shape());
- QHoverEvent leaveE(QEvent::HoverLeave, QPoint(), QPoint());
+ QHoverEvent leaveE(QEvent::HoverLeave, QPoint(), QPoint(), QPoint());
mw.event(&leaveE);
QCOMPARE(cur.shape(), mw.cursor().shape());
}