From 60eabf5382ff58c02000a25d4c98b8aa2416f13e Mon Sep 17 00:00:00 2001 From: Marco Martin Date: Fri, 6 Nov 2009 18:57:35 +0000 Subject: [PATCH] void registerAsDragHandle(QGraphicsItem *item); easy way to keep the flickable scrolling even with clickable sub items svn path=/trunk/KDE/kdelibs/; revision=1045776 --- widgets/scrollwidget.cpp | 47 ++++++++++++++++++++++++++++++++++++++++ widgets/scrollwidget.h | 20 +++++++++++++++++ 2 files changed, 67 insertions(+) diff --git a/widgets/scrollwidget.cpp b/widgets/scrollwidget.cpp index 1b752aa0e..e5167870b 100644 --- a/widgets/scrollwidget.cpp +++ b/widgets/scrollwidget.cpp @@ -21,6 +21,7 @@ //Qt #include #include +#include #include #include #include @@ -227,6 +228,7 @@ public: Qt::ScrollBarPolicy horizontalScrollBarPolicy; QString styleSheet; QRectF rectToBeVisible; + QSetdragHandles; bool dragging; int animId; static const int borderSize = 4; @@ -343,6 +345,33 @@ void ScrollWidget::ensureItemVisible(QGraphicsItem *item) QTimer::singleShot(0, this, SLOT(makeRectVisible())); } +void ScrollWidget::registerAsDragHandle(QGraphicsItem *item) +{ + if (!d->widget || !item) { + return; + } + + QGraphicsItem *parentOfItem = item->parentItem(); + while (parentOfItem != d->widget) { + if (!parentOfItem) { + return; + } + + parentOfItem = parentOfItem->parentItem(); + } + + item->installSceneEventFilter(this); + d->dragHandles.insert(item); +} + +void ScrollWidget::unregisterAsDragHandle(QGraphicsItem *item) +{ + if (item) { + item->removeSceneEventFilter(this); + d->dragHandles.remove(item); + } +} + QRectF ScrollWidget::viewportGeometry() const { QRectF result; @@ -453,6 +482,24 @@ void ScrollWidget::wheelEvent(QGraphicsSceneWheelEvent *event) } +bool ScrollWidget::sceneEventFilter(QGraphicsItem *watched, QEvent *event) +{ + if (!scene()) { + return false; + } + + if (d->dragHandles.contains(watched)) { + if (event->type() == QEvent::GraphicsSceneMousePress || + event->type() == QEvent::GraphicsSceneMouseMove || + event->type() == QEvent::GraphicsSceneMouseRelease) { + if (scene()) { + scene()->sendEvent(this, event); + } + } + } + return false; +} + bool ScrollWidget::eventFilter(QObject *watched, QEvent *event) { if (!d->widget) { diff --git a/widgets/scrollwidget.h b/widgets/scrollwidget.h index ea38d3c71..37cdf95d6 100644 --- a/widgets/scrollwidget.h +++ b/widgets/scrollwidget.h @@ -118,6 +118,25 @@ public: */ void ensureItemVisible(QGraphicsItem *item); + /** + * Register an item as a drag handle, it means mouse events will pass trough it + * and will be possible to drag the view by dragging the item itself. + * The item will still receive mouse clicks if the mouse didn't move + * between press and release. + * + * @param item the drag handle item. widget() must be an ancestor if it in + * the parent hierarchy. if item doesn't accept mose press events + * it's not necessary to call this function. + * @since 4.4 + */ + void registerAsDragHandle(QGraphicsItem *item); + + /** + * Unregister the given item as drag handle (if it was registered) + * @since 4.4 + */ + void unregisterAsDragHandle(QGraphicsItem *item); + /** * The geometry of the viewport. * @since 4.4 @@ -172,6 +191,7 @@ protected: bool eventFilter(QObject *watched, QEvent *event); void focusInEvent(QFocusEvent *event); QSizeF sizeHint(Qt::SizeHint which, const QSizeF & constraint) const; + bool sceneEventFilter(QGraphicsItem *watched, QEvent *event); private: ScrollWidgetPrivate * const d;