From d1fb4fcc9d3df60071b46a4392157a07ecd7efcd Mon Sep 17 00:00:00 2001 From: ronso0 Date: Sat, 12 Nov 2022 00:57:48 +0100 Subject: [PATCH 1/4] Knob: hide cursor on wheel event for .8s --- src/widget/knobeventhandler.h | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/src/widget/knobeventhandler.h b/src/widget/knobeventhandler.h index 5273edd4eae..447e6999837 100644 --- a/src/widget/knobeventhandler.h +++ b/src/widget/knobeventhandler.h @@ -1,11 +1,12 @@ #pragma once -#include -#include #include #include -#include +#include #include +#include +#include +#include #include "util/math.h" @@ -17,6 +18,8 @@ class KnobEventHandler { QPixmap blankPixmap(32, 32); blankPixmap.fill(QColor(0, 0, 0, 0)); m_blankCursor = QCursor(blankPixmap); + m_wheelCursorTimer.setSingleShot(true); + m_wheelCursorTimer.setInterval(800); } double valueFromMouseEvent(T* pWidget, QMouseEvent* e) { @@ -103,6 +106,7 @@ class KnobEventHandler { } void wheelEvent(T* pWidget, QWheelEvent* e) { + pWidget->setCursor(m_blankCursor); // For legacy (MIDI) reasons this is tuned to 127. double wheelDirection = e->angleDelta().y() / (120.0 * 127.0); double newValue = pWidget->getControlParameter() + wheelDirection; @@ -113,6 +117,13 @@ class KnobEventHandler { pWidget->setControlParameter(newValue); pWidget->inputActivity(); e->accept(); + m_wheelCursorTimer.start(); + m_wheelCursorTimer.callOnTimeout( + [pWidget]() { + if (pWidget) { + pWidget->unsetCursor(); + } + }); } private: @@ -123,4 +134,5 @@ class KnobEventHandler { QPoint m_startPos; QPoint m_prevPos; QCursor m_blankCursor; + QTimer m_wheelCursorTimer; }; From 7532a24b125fd4dc141752b6ca05e3b28a05fb96 Mon Sep 17 00:00:00 2001 From: ronso0 Date: Fri, 18 Nov 2022 14:20:05 +0100 Subject: [PATCH 2/4] Knob: unset (restore) cursor in QWidget::leaveEvent --- src/widget/knobeventhandler.h | 8 ++++++++ src/widget/wknob.cpp | 4 ++++ src/widget/wknob.h | 1 + src/widget/wknobcomposed.cpp | 4 ++++ src/widget/wknobcomposed.h | 1 + 5 files changed, 18 insertions(+) diff --git a/src/widget/knobeventhandler.h b/src/widget/knobeventhandler.h index 447e6999837..9a0751a7832 100644 --- a/src/widget/knobeventhandler.h +++ b/src/widget/knobeventhandler.h @@ -126,6 +126,14 @@ class KnobEventHandler { }); } + void leaveEvent(T* pWidget, QEvent* e) { + if (m_wheelCursorTimer.isActive()) { + m_wheelCursorTimer.stop(); + pWidget->unsetCursor(); + } + e->accept(); + } + private: // True if right mouse button is pressed. bool m_bRightButtonPressed; diff --git a/src/widget/wknob.cpp b/src/widget/wknob.cpp index f31d1d15ba7..f4a4fb7ee54 100644 --- a/src/widget/wknob.cpp +++ b/src/widget/wknob.cpp @@ -38,6 +38,10 @@ void WKnob::wheelEvent(QWheelEvent* e) { m_handler.wheelEvent(this, e); } +void WKnob::leaveEvent(QEvent* e) { + m_handler.leaveEvent(this, e); +} + void WKnob::inputActivity() { #ifdef __APPLE__ m_renderTimer.activity(); diff --git a/src/widget/wknob.h b/src/widget/wknob.h index 95ffe710794..84b341fcfa7 100644 --- a/src/widget/wknob.h +++ b/src/widget/wknob.h @@ -21,6 +21,7 @@ class WKnob : public WDisplay { protected: void wheelEvent(QWheelEvent *e) override; + void leaveEvent(QEvent* e) override; void mouseMoveEvent(QMouseEvent *e) override; void mousePressEvent(QMouseEvent *e) override; void mouseDoubleClickEvent(QMouseEvent* e) override; diff --git a/src/widget/wknobcomposed.cpp b/src/widget/wknobcomposed.cpp index cc318ac80dd..deaff61ec8c 100644 --- a/src/widget/wknobcomposed.cpp +++ b/src/widget/wknobcomposed.cpp @@ -227,6 +227,10 @@ void WKnobComposed::wheelEvent(QWheelEvent* e) { m_handler.wheelEvent(this, e); } +void WKnobComposed::leaveEvent(QEvent* e) { + m_handler.leaveEvent(this, e); +} + void WKnobComposed::inputActivity() { #ifdef __APPLE__ m_renderTimer.activity(); diff --git a/src/widget/wknobcomposed.h b/src/widget/wknobcomposed.h index cf3e287575c..da35a2175e7 100644 --- a/src/widget/wknobcomposed.h +++ b/src/widget/wknobcomposed.h @@ -28,6 +28,7 @@ class WKnobComposed : public WWidget { protected: void wheelEvent(QWheelEvent *e) override; + void leaveEvent(QEvent* e) override; void mouseMoveEvent(QMouseEvent *e) override; void mousePressEvent(QMouseEvent *e) override; void mouseDoubleClickEvent(QMouseEvent* e) override; From 5a68dad051824602413253b73016c9d0b3ba8f38 Mon Sep 17 00:00:00 2001 From: ronso0 Date: Fri, 18 Nov 2022 20:50:07 +0100 Subject: [PATCH 3/4] Knob: create wheel event cursor timer only when needed --- src/widget/knobeventhandler.h | 33 ++++++++++++++++++++++----------- 1 file changed, 22 insertions(+), 11 deletions(-) diff --git a/src/widget/knobeventhandler.h b/src/widget/knobeventhandler.h index 9a0751a7832..7a6f05c925a 100644 --- a/src/widget/knobeventhandler.h +++ b/src/widget/knobeventhandler.h @@ -10,16 +10,20 @@ #include "util/math.h" +// duration (ms) the cursor is blanked after a mouse wheel event +// 800 ms is the duration the parameter value is shown in the parameter name widget +// src/widget/weffectparameternamebase.cpp +constexpr int wheelEventCursorTimeout = 800; + template class KnobEventHandler { public: KnobEventHandler() - : m_bRightButtonPressed(false) { - QPixmap blankPixmap(32, 32); - blankPixmap.fill(QColor(0, 0, 0, 0)); - m_blankCursor = QCursor(blankPixmap); - m_wheelCursorTimer.setSingleShot(true); - m_wheelCursorTimer.setInterval(800); + : m_bRightButtonPressed(false), + m_pWheelCursorTimer(nullptr) { + QPixmap blankPixmap(32, 32); + blankPixmap.fill(QColor(0, 0, 0, 0)); + m_blankCursor = QCursor(blankPixmap); } double valueFromMouseEvent(T* pWidget, QMouseEvent* e) { @@ -106,6 +110,8 @@ class KnobEventHandler { } void wheelEvent(T* pWidget, QWheelEvent* e) { + // Hide/blank the cursor so the parameter value below the knob is not obscured. + // Restore the cursor when the timer runs out, or when the cursor leaves the widget. pWidget->setCursor(m_blankCursor); // For legacy (MIDI) reasons this is tuned to 127. double wheelDirection = e->angleDelta().y() / (120.0 * 127.0); @@ -117,8 +123,13 @@ class KnobEventHandler { pWidget->setControlParameter(newValue); pWidget->inputActivity(); e->accept(); - m_wheelCursorTimer.start(); - m_wheelCursorTimer.callOnTimeout( + if (!m_pWheelCursorTimer) { + m_pWheelCursorTimer = new QTimer(pWidget); + m_pWheelCursorTimer->setSingleShot(true); + m_pWheelCursorTimer->setInterval(wheelEventCursorTimeout); + } + m_pWheelCursorTimer->start(); + m_pWheelCursorTimer->callOnTimeout( [pWidget]() { if (pWidget) { pWidget->unsetCursor(); @@ -127,8 +138,8 @@ class KnobEventHandler { } void leaveEvent(T* pWidget, QEvent* e) { - if (m_wheelCursorTimer.isActive()) { - m_wheelCursorTimer.stop(); + if (m_pWheelCursorTimer && m_pWheelCursorTimer->isActive()) { + m_pWheelCursorTimer->stop(); pWidget->unsetCursor(); } e->accept(); @@ -142,5 +153,5 @@ class KnobEventHandler { QPoint m_startPos; QPoint m_prevPos; QCursor m_blankCursor; - QTimer m_wheelCursorTimer; + QTimer* m_pWheelCursorTimer; }; From 9fdf0c14b81a541520543726da86b0ddcc85296d Mon Sep 17 00:00:00 2001 From: ronso0 Date: Wed, 7 Dec 2022 11:07:32 +0100 Subject: [PATCH 4/4] KnobEventHandler: Qt::transparent instead of QColor --- src/widget/knobeventhandler.h | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/widget/knobeventhandler.h b/src/widget/knobeventhandler.h index 7a6f05c925a..0280e3203fe 100644 --- a/src/widget/knobeventhandler.h +++ b/src/widget/knobeventhandler.h @@ -1,6 +1,5 @@ #pragma once -#include #include #include #include @@ -22,7 +21,7 @@ class KnobEventHandler { : m_bRightButtonPressed(false), m_pWheelCursorTimer(nullptr) { QPixmap blankPixmap(32, 32); - blankPixmap.fill(QColor(0, 0, 0, 0)); + blankPixmap.fill(Qt::transparent); m_blankCursor = QCursor(blankPixmap); }