diff options
author | Laszlo Agocs <laszlo.agocs@qt.io> | 2017-06-08 11:00:41 +0200 |
---|---|---|
committer | Liang Qi <liang.qi@qt.io> | 2017-06-08 11:48:54 +0200 |
commit | 8a5837467d153c50c869625390a584b0335b77b7 (patch) | |
tree | d8aca950cb88dfdc3a001a5cdedf02d7a8894d36 /src/quick/items | |
parent | 5af4c9b237a23ce12ca7c56eb6c9ecda17743228 (diff) | |
parent | 55490690f81eba168b06a90e4a66cefc20b38252 (diff) |
Merge remote-tracking branch 'origin/dev' into wip/scenegraphng
Conflicts:
src/quick/scenegraph/adaptations/software/qsgsoftwarerenderablenode.cpp
Change-Id: Id8107cb0de0fbfe7120a90a137b49c2b915ff2d3
Diffstat (limited to 'src/quick/items')
-rw-r--r-- | src/quick/items/qquickanimatedimage_p.h | 1 | ||||
-rw-r--r-- | src/quick/items/qquickevents.cpp | 3 | ||||
-rw-r--r-- | src/quick/items/qquickevents_p_p.h | 25 | ||||
-rw-r--r-- | src/quick/items/qquickitem.cpp | 91 | ||||
-rw-r--r-- | src/quick/items/qquickrectangle.cpp | 19 | ||||
-rw-r--r-- | src/quick/items/qquickrectangle_p.h | 6 | ||||
-rw-r--r-- | src/quick/items/qquickrectangle_p_p.h | 1 | ||||
-rw-r--r-- | src/quick/items/qquickview.cpp | 1 | ||||
-rw-r--r-- | src/quick/items/qquickwindow.cpp | 71 | ||||
-rw-r--r-- | src/quick/items/qquickwindow_p.h | 4 |
10 files changed, 146 insertions, 76 deletions
diff --git a/src/quick/items/qquickanimatedimage_p.h b/src/quick/items/qquickanimatedimage_p.h index 143fe8904d..54da093259 100644 --- a/src/quick/items/qquickanimatedimage_p.h +++ b/src/quick/items/qquickanimatedimage_p.h @@ -97,7 +97,6 @@ Q_SIGNALS: void playingChanged(); void pausedChanged(); void frameChanged(); - void sourceSizeChanged(); private Q_SLOTS: void movieUpdate(); diff --git a/src/quick/items/qquickevents.cpp b/src/quick/items/qquickevents.cpp index ac0505da82..448b63c347 100644 --- a/src/quick/items/qquickevents.cpp +++ b/src/quick/items/qquickevents.cpp @@ -861,8 +861,9 @@ QTouchEvent *QQuickPointerTouchEvent::touchEventForItem(QQuickItem *item, bool i } parent = parent->parentItem(); } - bool filterRelevant = isFiltering && grabberIsChild; + // when filtering, send points that are grabbed by a child and points that are not grabbed but inside + bool filterRelevant = isFiltering && (grabberIsChild || (!p->grabber() && item->contains(item->mapFromScene(p->scenePos())))); if (!(isGrabber || isPressInside || filterRelevant)) continue; diff --git a/src/quick/items/qquickevents_p_p.h b/src/quick/items/qquickevents_p_p.h index cf6f83e5b1..3735d68a85 100644 --- a/src/quick/items/qquickevents_p_p.h +++ b/src/quick/items/qquickevents_p_p.h @@ -332,9 +332,9 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPointerEvent : public QObject Q_PROPERTY(Qt::MouseButtons buttons READ buttons) public: - QQuickPointerEvent(QObject *parent = nullptr) + QQuickPointerEvent(QObject *parent = nullptr, QQuickPointerDevice *device = nullptr) : QObject(parent) - , m_device(nullptr) + , m_device(device) , m_event(nullptr) , m_button(Qt::NoButton) , m_pressedButtons(Qt::NoButton) @@ -385,8 +385,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPointerMouseEvent : public QQuickPointerEvent { Q_OBJECT public: - QQuickPointerMouseEvent(QObject *parent = nullptr) - : QQuickPointerEvent(parent), m_mousePoint(new QQuickEventPoint(this)) { } + QQuickPointerMouseEvent(QObject *parent = nullptr, QQuickPointerDevice *device = nullptr) + : QQuickPointerEvent(parent, device), m_mousePoint(new QQuickEventPoint(this)) { } QQuickPointerEvent *reset(QEvent *) override; bool isPressEvent() const override; @@ -411,8 +411,8 @@ class Q_QUICK_PRIVATE_EXPORT QQuickPointerTouchEvent : public QQuickPointerEvent { Q_OBJECT public: - QQuickPointerTouchEvent(QObject *parent = nullptr) - : QQuickPointerEvent(parent) + QQuickPointerTouchEvent(QObject *parent = nullptr, QQuickPointerDevice *device = nullptr) + : QQuickPointerEvent(parent, device) , m_pointCount(0) , m_synthMouseEvent(QEvent::MouseMove, QPointF(), Qt::NoButton, Qt::NoButton, Qt::NoModifier) { } @@ -500,18 +500,10 @@ public: QQuickPointerDevice(DeviceType devType, PointerType pType, Capabilities caps, int maxPoints, int buttonCount, const QString &name, qint64 uniqueId = 0) : m_deviceType(devType), m_pointerType(pType), m_capabilities(caps) , m_maximumTouchPoints(maxPoints), m_buttonCount(buttonCount), m_name(name) - , m_uniqueId(QPointingDeviceUniqueId::fromNumericId(uniqueId)), m_event(nullptr) + , m_uniqueId(QPointingDeviceUniqueId::fromNumericId(uniqueId)) { - if (m_deviceType == Mouse) { - m_event = new QQuickPointerMouseEvent; - } else if (m_deviceType == TouchScreen || m_deviceType == TouchPad) { - m_event = new QQuickPointerTouchEvent; - } else { - Q_ASSERT(false); - } } - ~QQuickPointerDevice() { delete m_event; } DeviceType type() const { return m_deviceType; } PointerType pointerType() const { return m_pointerType; } Capabilities capabilities() const { return m_capabilities; } @@ -520,7 +512,6 @@ public: int buttonCount() const { return m_buttonCount; } QString name() const { return m_name; } QPointingDeviceUniqueId uniqueId() const { return m_uniqueId; } - QQuickPointerEvent *pointerEvent() const { return m_event; } static QQuickPointerDevice *touchDevice(QTouchDevice *d); static QList<QQuickPointerDevice *> touchDevices(); @@ -535,8 +526,6 @@ private: int m_buttonCount; QString m_name; QPointingDeviceUniqueId m_uniqueId; - // the device-specific event instance which is reused during event delivery - QQuickPointerEvent *m_event; Q_DISABLE_COPY(QQuickPointerDevice) }; diff --git a/src/quick/items/qquickitem.cpp b/src/quick/items/qquickitem.cpp index 4e52109582..a8a862bb2f 100644 --- a/src/quick/items/qquickitem.cpp +++ b/src/quick/items/qquickitem.cpp @@ -146,8 +146,8 @@ QQuickTransform::QQuickTransform(QQuickTransformPrivate &dd, QObject *parent) QQuickTransform::~QQuickTransform() { Q_D(QQuickTransform); - for (QQuickItem *item : qAsConst(d->items)) { - QQuickItemPrivate *p = QQuickItemPrivate::get(item); + for (int ii = 0; ii < d->items.count(); ++ii) { + QQuickItemPrivate *p = QQuickItemPrivate::get(d->items.at(ii)); p->transforms.removeOne(this); p->dirty(QQuickItemPrivate::Transform); } @@ -156,8 +156,8 @@ QQuickTransform::~QQuickTransform() void QQuickTransform::update() { Q_D(QQuickTransform); - for (QQuickItem *item : qAsConst(d->items)) { - QQuickItemPrivate *p = QQuickItemPrivate::get(item); + for (int ii = 0; ii < d->items.count(); ++ii) { + QQuickItemPrivate *p = QQuickItemPrivate::get(d->items.at(ii)); p->dirty(QQuickItemPrivate::Transform); } } @@ -169,7 +169,9 @@ QQuickContents::QQuickContents(QQuickItem *item) QQuickContents::~QQuickContents() { - for (QQuickItem *child : m_item->childItems()) { + QList<QQuickItem *> children = m_item->childItems(); + for (int i = 0; i < children.count(); ++i) { + QQuickItem *child = children.at(i); QQuickItemPrivate::get(child)->removeItemChangeListener(this, QQuickItemPrivate::Geometry | QQuickItemPrivate::Destroyed); } } @@ -192,8 +194,9 @@ bool QQuickContents::calcHeight(QQuickItem *changed) } else { qreal top = std::numeric_limits<qreal>::max(); qreal bottom = -std::numeric_limits<qreal>::max(); - const QList<QQuickItem*> children = m_item->childItems(); - for (QQuickItem *child : qAsConst(children)) { + QList<QQuickItem *> children = m_item->childItems(); + for (int i = 0; i < children.count(); ++i) { + QQuickItem *child = children.at(i); qreal y = child->y(); if (y + child->height() > bottom) bottom = y + child->height(); @@ -226,8 +229,9 @@ bool QQuickContents::calcWidth(QQuickItem *changed) } else { qreal left = std::numeric_limits<qreal>::max(); qreal right = -std::numeric_limits<qreal>::max(); - const QList<QQuickItem*> children = m_item->childItems(); - for (QQuickItem *child : qAsConst(children)) { + QList<QQuickItem *> children = m_item->childItems(); + for (int i = 0; i < children.count(); ++i) { + QQuickItem *child = children.at(i); qreal x = child->x(); if (x + child->width() > right) right = x + child->width(); @@ -246,7 +250,9 @@ void QQuickContents::complete() { QQuickItemPrivate::get(m_item)->addItemChangeListener(this, QQuickItemPrivate::Children); - for (QQuickItem *child : m_item->childItems()) { + QList<QQuickItem *> children = m_item->childItems(); + for (int i = 0; i < children.count(); ++i) { + QQuickItem *child = children.at(i); QQuickItemPrivate::get(child)->addItemChangeListener(this, QQuickItemPrivate::Geometry | QQuickItemPrivate::Destroyed); //###what about changes to visibility? } @@ -1347,7 +1353,8 @@ void QQuickKeysAttached::componentComplete() #if QT_CONFIG(im) Q_D(QQuickKeysAttached); if (d->item) { - for (QQuickItem *targetItem : qAsConst(d->targets)) { + for (int ii = 0; ii < d->targets.count(); ++ii) { + QQuickItem *targetItem = d->targets.at(ii); if (targetItem && (targetItem->flags() & QQuickItem::ItemAcceptsInputMethod)) { d->item->setFlag(QQuickItem::ItemAcceptsInputMethod); break; @@ -1369,10 +1376,11 @@ void QQuickKeysAttached::keyPressed(QKeyEvent *event, bool post) // first process forwards if (d->item && d->item->window()) { d->inPress = true; - for (QQuickItem *targetItem : qAsConst(d->targets)) { - if (targetItem && targetItem->isVisible()) { + for (int ii = 0; ii < d->targets.count(); ++ii) { + QQuickItem *i = d->targets.at(ii); + if (i && i->isVisible()) { event->accept(); - QCoreApplication::sendEvent(targetItem, event); + QCoreApplication::sendEvent(i, event); if (event->isAccepted()) { d->inPress = false; return; @@ -1412,10 +1420,11 @@ void QQuickKeysAttached::keyReleased(QKeyEvent *event, bool post) if (d->item && d->item->window()) { d->inRelease = true; - for (QQuickItem *targetItem : qAsConst(d->targets)) { - if (targetItem && targetItem->isVisible()) { + for (int ii = 0; ii < d->targets.count(); ++ii) { + QQuickItem *i = d->targets.at(ii); + if (i && i->isVisible()) { event->accept(); - QCoreApplication::sendEvent(targetItem, event); + QCoreApplication::sendEvent(i, event); if (event->isAccepted()) { d->inRelease = false; return; @@ -1439,7 +1448,8 @@ void QQuickKeysAttached::inputMethodEvent(QInputMethodEvent *event, bool post) Q_D(QQuickKeysAttached); if (post == m_processPost && d->item && !d->inIM && d->item->window()) { d->inIM = true; - for (QQuickItem *targetItem : qAsConst(d->targets)) { + for (int ii = 0; ii < d->targets.count(); ++ii) { + QQuickItem *targetItem = d->targets.at(ii); if (targetItem && targetItem->isVisible() && (targetItem->flags() & QQuickItem::ItemAcceptsInputMethod)) { QCoreApplication::sendEvent(targetItem, event); if (event->isAccepted()) { @@ -1458,12 +1468,13 @@ QVariant QQuickKeysAttached::inputMethodQuery(Qt::InputMethodQuery query) const { Q_D(const QQuickKeysAttached); if (d->item) { - for (QQuickItem *targetItem : qAsConst(d->targets)) { - if (targetItem && targetItem->isVisible() && (targetItem->flags() & QQuickItem::ItemAcceptsInputMethod) && targetItem == d->imeItem) { - //### how robust is targetItem == d->imeItem check? - QVariant v = targetItem->inputMethodQuery(query); + for (int ii = 0; ii < d->targets.count(); ++ii) { + QQuickItem *i = d->targets.at(ii); + if (i && i->isVisible() && (i->flags() & QQuickItem::ItemAcceptsInputMethod) && i == d->imeItem) { + //### how robust is i == d->imeItem check? + QVariant v = i->inputMethodQuery(query); if (v.userType() == QVariant::RectF) - v = d->item->mapRectFromItem(targetItem, v.toRectF()); //### cost? + v = d->item->mapRectFromItem(i, v.toRectF()); //### cost? return v; } } @@ -1637,9 +1648,11 @@ void QQuickItemPrivate::setImplicitLayoutMirror(bool mirror, bool inherit) if (isMirrorImplicit) setLayoutMirror(inherit ? inheritedLayoutMirror : false); - for (QQuickItem *child : qAsConst(childItems)) { - QQuickItemPrivate *childPrivate = QQuickItemPrivate::get(child); - childPrivate->setImplicitLayoutMirror(inheritedLayoutMirror, inheritMirrorFromParent); + for (int i = 0; i < childItems.count(); ++i) { + if (QQuickItem *child = qmlobject_cast<QQuickItem *>(childItems.at(i))) { + QQuickItemPrivate *childPrivate = QQuickItemPrivate::get(child); + childPrivate->setImplicitLayoutMirror(inheritedLayoutMirror, inheritMirrorFromParent); + } } } @@ -2395,7 +2408,8 @@ QQuickItem::~QQuickItem() remove themselves from our list of transforms when that list has already been destroyed after ~QQuickItem() has run. */ - for (QQuickTransform *t : qAsConst(d->transforms)) { + for (int ii = 0; ii < d->transforms.count(); ++ii) { + QQuickTransform *t = d->transforms.at(ii); QQuickTransformPrivate *tp = QQuickTransformPrivate::get(t); tp->items.removeOne(this); } @@ -2886,8 +2900,8 @@ QList<QQuickItem *> QQuickItemPrivate::paintOrderChildItems() const // If none of the items have set Z then the paint order list is the same as // the childItems list. This is by far the most common case. bool haveZ = false; - for (QQuickItem *childItem : qAsConst(childItems)) { - if (QQuickItemPrivate::get(childItem)->z() != 0.) { + for (int i = 0; i < childItems.count(); ++i) { + if (QQuickItemPrivate::get(childItems.at(i))->z() != 0.) { haveZ = true; break; } @@ -2988,7 +3002,8 @@ void QQuickItemPrivate::refWindow(QQuickWindow *c) if (!parentItem) QQuickWindowPrivate::get(window)->parentlessItems.insert(q); - for (QQuickItem *child : qAsConst(childItems)) { + for (int ii = 0; ii < childItems.count(); ++ii) { + QQuickItem *child = childItems.at(ii); QQuickItemPrivate::get(child)->refWindow(c); } @@ -3040,7 +3055,8 @@ void QQuickItemPrivate::derefWindow() paintNode = 0; - for (QQuickItem *child : qAsConst(childItems)) { + for (int ii = 0; ii < childItems.count(); ++ii) { + QQuickItem *child = childItems.at(ii); QQuickItemPrivate::get(child)->derefWindow(); } @@ -3485,7 +3501,8 @@ void QQuickItemPrivate::transform_clear(QQmlListProperty<QQuickTransform> *prop) QQuickItem *that = static_cast<QQuickItem *>(prop->object); QQuickItemPrivate *p = QQuickItemPrivate::get(that); - for (QQuickTransform *t : qAsConst(p->transforms)) { + for (int ii = 0; ii < p->transforms.count(); ++ii) { + QQuickTransform *t = p->transforms.at(ii); QQuickTransformPrivate *tp = QQuickTransformPrivate::get(t); tp->items.removeOne(that); } @@ -5850,9 +5867,8 @@ bool QQuickItemPrivate::setEffectiveVisibleRecur(bool newEffectiveVisible) } bool childVisibilityChanged = false; - for (QQuickItem *childItem : qAsConst(childItems)) { - childVisibilityChanged |= QQuickItemPrivate::get(childItem)->setEffectiveVisibleRecur(newEffectiveVisible); - } + for (int ii = 0; ii < childItems.count(); ++ii) + childVisibilityChanged |= QQuickItemPrivate::get(childItems.at(ii))->setEffectiveVisibleRecur(newEffectiveVisible); itemChange(QQuickItem::ItemVisibleHasChanged, effectiveVisible); #if QT_CONFIG(accessibility) @@ -5901,8 +5917,8 @@ void QQuickItemPrivate::setEffectiveEnableRecur(QQuickItem *scope, bool newEffec } } - for (QQuickItem *childItem : qAsConst(childItems)) { - QQuickItemPrivate::get(childItem)->setEffectiveEnableRecur( + for (int ii = 0; ii < childItems.count(); ++ii) { + QQuickItemPrivate::get(childItems.at(ii))->setEffectiveEnableRecur( (flags & QQuickItem::ItemIsFocusScope) && scope ? q : scope, newEffectiveEnable); } @@ -6343,6 +6359,7 @@ void QQuickItem::setFlags(Flags flags) \qmlproperty real QtQuick::Item::height Defines the item's position and size. + The default value is \c 0. The (x,y) position is relative to the \l parent. diff --git a/src/quick/items/qquickrectangle.cpp b/src/quick/items/qquickrectangle.cpp index 0c532bcd4c..65284eb532 100644 --- a/src/quick/items/qquickrectangle.cpp +++ b/src/quick/items/qquickrectangle.cpp @@ -1,6 +1,5 @@ /**************************************************************************** ** -** Copyright (C) 2017 Crimson AS <info@crimson.no> ** Copyright (C) 2016 The Qt Company Ltd. ** Contact: https://www.qt.io/licensing/ ** @@ -270,9 +269,11 @@ QGradientStops QQuickGradient::gradientStops() const void QQuickGradient::doUpdate() { - static_cast<QQuickItem*>(parent())->update(); + emit updated(); } +int QQuickRectanglePrivate::doUpdateSlotIdx = -1; + /*! \qmltype Rectangle \instantiates QQuickRectangle @@ -326,6 +327,11 @@ QQuickRectangle::QQuickRectangle(QQuickItem *parent) setFlag(ItemHasContents); } +void QQuickRectangle::doUpdate() +{ + update(); +} + /*! \qmlproperty bool QtQuick::Rectangle::antialiasing @@ -390,7 +396,16 @@ void QQuickRectangle::setGradient(QQuickGradient *gradient) Q_D(QQuickRectangle); if (d->gradient == gradient) return; + static int updatedSignalIdx = -1; + if (updatedSignalIdx < 0) + updatedSignalIdx = QMetaMethod::fromSignal(&QQuickGradient::updated).methodIndex(); + if (d->doUpdateSlotIdx < 0) + d->doUpdateSlotIdx = QQuickRectangle::staticMetaObject.indexOfSlot("doUpdate()"); + if (d->gradient) + QMetaObject::disconnect(d->gradient, updatedSignalIdx, this, d->doUpdateSlotIdx); d->gradient = gradient; + if (d->gradient) + QMetaObject::connect(d->gradient, updatedSignalIdx, this, d->doUpdateSlotIdx); update(); } diff --git a/src/quick/items/qquickrectangle_p.h b/src/quick/items/qquickrectangle_p.h index 627f778e44..724a06013c 100644 --- a/src/quick/items/qquickrectangle_p.h +++ b/src/quick/items/qquickrectangle_p.h @@ -129,6 +129,9 @@ public: QGradientStops gradientStops() const; +Q_SIGNALS: + void updated(); + private: void doUpdate(); @@ -169,6 +172,9 @@ Q_SIGNALS: protected: QSGNode *updatePaintNode(QSGNode *, UpdatePaintNodeData *) Q_DECL_OVERRIDE; +private Q_SLOTS: + void doUpdate(); + private: Q_DISABLE_COPY(QQuickRectangle) Q_DECLARE_PRIVATE(QQuickRectangle) diff --git a/src/quick/items/qquickrectangle_p_p.h b/src/quick/items/qquickrectangle_p_p.h index e771beec87..3c1aaf7661 100644 --- a/src/quick/items/qquickrectangle_p_p.h +++ b/src/quick/items/qquickrectangle_p_p.h @@ -76,6 +76,7 @@ public: QQuickGradient *gradient; QQuickPen *pen; qreal radius; + static int doUpdateSlotIdx; }; QT_END_NAMESPACE diff --git a/src/quick/items/qquickview.cpp b/src/quick/items/qquickview.cpp index 8313b53a7d..fca1805fc9 100644 --- a/src/quick/items/qquickview.cpp +++ b/src/quick/items/qquickview.cpp @@ -496,6 +496,7 @@ void QQuickViewPrivate::setRootObject(QObject *obj) if (QQuickItem *sgItem = qobject_cast<QQuickItem *>(obj)) { root = sgItem; sgItem->setParentItem(q->QQuickWindow::contentItem()); + QQml_setParent_noEvent(sgItem, q->QQuickWindow::contentItem()); } else if (qobject_cast<QWindow *>(obj)) { qWarning() << "QQuickView does not support using windows as a root item." << endl << endl diff --git a/src/quick/items/qquickwindow.cpp b/src/quick/items/qquickwindow.cpp index 2c929113f6..2cb518d691 100644 --- a/src/quick/items/qquickwindow.cpp +++ b/src/quick/items/qquickwindow.cpp @@ -526,6 +526,7 @@ void QQuickWindowPrivate::init(QQuickWindow *c, QQuickRenderControl *control) Q_Q(QQuickWindow); contentItem = new QQuickRootItem; + QQml_setParent_noEvent(contentItem, c); QQmlEngine::setObjectOwnership(contentItem, QQmlEngine::CppOwnership); QQuickItemPrivate *contentItemPrivate = QQuickItemPrivate::get(contentItem); contentItemPrivate->window = q; @@ -751,13 +752,13 @@ void QQuickWindowPrivate::setMouseGrabber(QQuickItem *grabber) if (grabber && touchMouseId != -1 && touchMouseDevice) { // update the touch item for mouse touch id to the new grabber - qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << touchMouseId << "->" << q->mouseGrabberItem(); - auto point = touchMouseDevice->pointerEvent()->pointById(touchMouseId); + qCDebug(DBG_TOUCH_TARGET) << "TP (mouse)" << hex << touchMouseId << "->" << q->mouseGrabberItem(); + auto point = pointerEventInstance(touchMouseDevice)->pointById(touchMouseId); if (point) point->setGrabber(grabber); fromTouch = true; } else { - QQuickPointerEvent *event = QQuickPointerDevice::genericMouseDevice()->pointerEvent(); + QQuickPointerEvent *event = pointerEventInstance(QQuickPointerDevice::genericMouseDevice()); Q_ASSERT(event->pointCount() == 1); event->point(0)->setGrabber(grabber); } @@ -784,7 +785,7 @@ void QQuickWindowPrivate::grabTouchPoints(QQuickItem *grabber, const QVector<int continue; } if (id == touchMouseId) { - auto point = touchMouseDevice->pointerEvent()->pointById(id); + auto point = pointerEventInstance(touchMouseDevice)->pointById(id); auto touchMouseGrabber = point->grabber(); if (touchMouseGrabber) { point->setGrabber(nullptr); @@ -798,7 +799,7 @@ void QQuickWindowPrivate::grabTouchPoints(QQuickItem *grabber, const QVector<int const auto touchDevices = QQuickPointerDevice::touchDevices(); for (auto device : touchDevices) { - auto point = device->pointerEvent()->pointById(id); + auto point = pointerEventInstance(device)->pointById(id); if (!point) continue; QQuickItem *oldGrabber = point->grabber(); @@ -824,7 +825,7 @@ void QQuickWindowPrivate::removeGrabber(QQuickItem *grabber, bool mouse, bool to if (Q_LIKELY(touch)) { const auto touchDevices = QQuickPointerDevice::touchDevices(); for (auto device : touchDevices) { - auto pointerEvent = device->pointerEvent(); + auto pointerEvent = pointerEventInstance(device); for (int i = 0; i < pointerEvent->pointCount(); ++i) { if (pointerEvent->point(i)->grabber() == grabber) { pointerEvent->point(i)->setGrabber(nullptr); @@ -1493,13 +1494,13 @@ QQuickItem *QQuickWindow::mouseGrabberItem() const Q_D(const QQuickWindow); if (d->touchMouseId != -1 && d->touchMouseDevice) { - QQuickPointerEvent *event = d->touchMouseDevice->pointerEvent(); + QQuickPointerEvent *event = d->pointerEventInstance(d->touchMouseDevice); auto point = event->pointById(d->touchMouseId); Q_ASSERT(point); return point->grabber(); } - QQuickPointerEvent *event = QQuickPointerDevice::genericMouseDevice()->pointerEvent(); + QQuickPointerEvent *event = d->pointerEventInstance(QQuickPointerDevice::genericMouseDevice()); Q_ASSERT(event->pointCount()); return event->point(0)->grabber(); } @@ -1883,7 +1884,7 @@ bool QQuickWindowPrivate::deliverTouchCancelEvent(QTouchEvent *event) // A TouchCancel event will typically not contain any points. // Deliver it to all items that have active touches. - QQuickPointerEvent *pointerEvent = QQuickPointerDevice::touchDevice(event->device())->pointerEvent(); + QQuickPointerEvent *pointerEvent = pointerEventInstance(QQuickPointerDevice::touchDevice(event->device())); QVector<QQuickItem *> grabbers = pointerEvent->grabbers(); for (QQuickItem *grabber: qAsConst(grabbers)) { @@ -1979,8 +1980,14 @@ bool QQuickWindowPrivate::compressTouchEvent(QTouchEvent *event) void QQuickWindowPrivate::handleTouchEvent(QTouchEvent *event) { translateTouchEvent(event); - if (event->touchPoints().size()) - lastMousePosition = event->touchPoints().at(0).pos(); + if (event->touchPoints().size()) { + auto point = event->touchPoints().at(0); + if (point.state() == Qt::TouchPointReleased) { + lastMousePosition = QPointF(); + } else { + lastMousePosition = point.pos(); + } + } qCDebug(DBG_TOUCH) << event; @@ -2107,6 +2114,32 @@ void QQuickWindowPrivate::flushFrameSynchronousEvents() } } +QQuickPointerEvent *QQuickWindowPrivate::pointerEventInstance(QQuickPointerDevice *device) const +{ + // the list of devices should be very small so a linear search should be ok + for (QQuickPointerEvent *e: pointerEventInstances) { + if (e->device() == device) + return e; + } + + QQuickPointerEvent *ev = nullptr; + QQuickWindow *q = const_cast<QQuickWindow*>(q_func()); + switch (device->type()) { + case QQuickPointerDevice::Mouse: + ev = new QQuickPointerMouseEvent(q, device); + break; + case QQuickPointerDevice::TouchPad: + case QQuickPointerDevice::TouchScreen: + ev = new QQuickPointerTouchEvent(q, device); + break; + default: + // TODO tablet event types + break; + } + pointerEventInstances << ev; + return ev; +} + /*! \internal Returns a QQuickPointerEvent instance suitable for wrapping and delivering \a event. @@ -2117,25 +2150,29 @@ void QQuickWindowPrivate::flushFrameSynchronousEvents() QQuickPointerEvent *QQuickWindowPrivate::pointerEventInstance(QEvent *event) const { QQuickPointerDevice *dev = nullptr; + QQuickPointerEvent *ev = nullptr; switch (event->type()) { case QEvent::MouseButtonPress: case QEvent::MouseButtonRelease: case QEvent::MouseButtonDblClick: case QEvent::MouseMove: dev = QQuickPointerDevice::genericMouseDevice(); + ev = pointerEventInstance(dev); break; case QEvent::TouchBegin: case QEvent::TouchUpdate: case QEvent::TouchEnd: case QEvent::TouchCancel: dev = QQuickPointerDevice::touchDevice(static_cast<QTouchEvent *>(event)->device()); + ev = pointerEventInstance(dev); break; // TODO tablet event types default: break; } - Q_ASSERT(dev); - return dev->pointerEvent()->reset(event); + + Q_ASSERT(ev); + return ev->reset(event); } void QQuickWindowPrivate::deliverPointerEvent(QQuickPointerEvent *event) @@ -2227,7 +2264,7 @@ void QQuickWindowPrivate::deliverTouchEvent(QQuickPointerTouchEvent *event) QQuickEventPoint *point = event->point(i); if (point->state() == QQuickEventPoint::Released) { int id = point->pointId(); - qCDebug(DBG_TOUCH_TARGET) << "TP" << id << "released"; + qCDebug(DBG_TOUCH_TARGET) << "TP" << hex << id << "released"; point->setGrabber(nullptr); if (id == touchMouseId) { touchMouseId = -1; @@ -2610,7 +2647,7 @@ bool QQuickWindowPrivate::sendFilteredTouchEvent(QQuickItem *target, QQuickItem if (touchMouseUnset) { // the point was grabbed as a pure touch point before, now it will be treated as mouse // but the old receiver still needs to be informed - if (auto oldGrabber = touchMouseDevice->pointerEvent()->pointById(tp.id())->grabber()) + if (auto oldGrabber = pointerEventInstance(touchMouseDevice)->pointById(tp.id())->grabber()) oldGrabber->touchUngrabEvent(); } touchMouseUnset = false; // We want to leave touchMouseId and touchMouseDevice set @@ -3862,7 +3899,7 @@ QSGTexture *QQuickWindow::createTextureFromImage(const QImage &image, CreateText initialized or OpenGL is not in use. \note This function only has an effect when using the default OpenGL scene graph - adpation. + adaptation. \sa sceneGraphInitialized(), QSGTexture */ @@ -3970,7 +4007,7 @@ void QQuickWindow::setDefaultAlphaBuffer(bool useAlpha) graph renderer. Clear these manually on demand. \note This function only has an effect when using the default OpenGL scene graph - adpation. + adaptation. \sa QQuickWindow::beforeRendering() */ diff --git a/src/quick/items/qquickwindow_p.h b/src/quick/items/qquickwindow_p.h index be915903c6..b3ff5a2b35 100644 --- a/src/quick/items/qquickwindow_p.h +++ b/src/quick/items/qquickwindow_p.h @@ -162,6 +162,10 @@ public: void flushFrameSynchronousEvents(); void deliverDelayedTouchEvent(); + // the device-specific event instances which are reused during event delivery + mutable QVector<QQuickPointerEvent *> pointerEventInstances; + QQuickPointerEvent *pointerEventInstance(QQuickPointerDevice *device) const; + // delivery of pointer events: QQuickPointerEvent *pointerEventInstance(QEvent *ev) const; void deliverPointerEvent(QQuickPointerEvent *); |