diff options
Diffstat (limited to 'src/quick/items/qquickwindow_p.h')
-rw-r--r-- | src/quick/items/qquickwindow_p.h | 348 |
1 files changed, 156 insertions, 192 deletions
diff --git a/src/quick/items/qquickwindow_p.h b/src/quick/items/qquickwindow_p.h index 63760a3b68..8ba4e56515 100644 --- a/src/quick/items/qquickwindow_p.h +++ b/src/quick/items/qquickwindow_p.h @@ -1,41 +1,5 @@ -/**************************************************************************** -** -** Copyright (C) 2016 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$ -** -****************************************************************************/ +// Copyright (C) 2020 The Qt Company Ltd. +// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only #ifndef QQUICKWINDOW_P_H #define QQUICKWINDOW_P_H @@ -51,186 +15,182 @@ // We mean it. // -#include "qquickitem.h" -#include "qquickwindow.h" -#include "qquickevents_p_p.h" - +#include <QtQuick/private/qquickdeliveryagent_p_p.h> +#include <QtQuick/private/qquickevents_p_p.h> #include <QtQuick/private/qsgcontext_p.h> +#include <QtQuick/private/qquickpaletteproviderprivatebase_p.h> +#include <QtQuick/private/qquickrendertarget_p.h> +#include <QtQuick/private/qquickgraphicsdevice_p.h> +#include <QtQuick/private/qquickgraphicsconfiguration_p.h> +#include <QtQuick/qquickitem.h> +#include <QtQuick/qquickwindow.h> #include <QtCore/qthread.h> #include <QtCore/qmutex.h> #include <QtCore/qwaitcondition.h> #include <QtCore/qrunnable.h> -#include <private/qwindow_p.h> -#include <private/qopengl_p.h> -#include <qopenglcontext.h> -#include <QtGui/qopenglframebufferobject.h> +#include <QtCore/qstack.h> + +#include <QtGui/private/qevent_p.h> +#include <QtGui/private/qpointingdevice_p.h> +#include <QtGui/private/qwindow_p.h> #include <QtGui/qevent.h> #include <QtGui/qstylehints.h> #include <QtGui/qguiapplication.h> QT_BEGIN_NAMESPACE -class QOpenGLVertexArrayObjectHelper; +class QOpenGLContext; class QQuickAnimatorController; class QQuickDragGrabber; class QQuickItemPrivate; -class QQuickPointerDevice; +class QPointingDevice; class QQuickRenderControl; class QQuickWindowIncubationController; class QQuickWindowPrivate; -class QQuickWindowRenderLoop; class QSGRenderLoop; class QTouchEvent; +class QRhi; +class QRhiSwapChain; +class QRhiRenderBuffer; +class QRhiRenderPassDescriptor; +class QRhiTexture; + +Q_DECLARE_LOGGING_CATEGORY(lcQuickWindow) //Make it easy to identify and customize the root item if needed -class QQuickRootItem : public QQuickItem +class Q_QUICK_EXPORT QQuickRootItem : public QQuickItem { Q_OBJECT + QML_ANONYMOUS + QML_ADDED_IN_VERSION(2, 0) public: QQuickRootItem(); + public Q_SLOTS: void setWidth(int w) {QQuickItem::setWidth(qreal(w));} void setHeight(int h) {QQuickItem::setHeight(qreal(h));} }; -class Q_QUICK_PRIVATE_EXPORT QQuickCustomRenderStage +struct QQuickWindowRenderTarget { -public: - virtual ~QQuickCustomRenderStage() {} - virtual bool render() = 0; - virtual bool swap() = 0; + enum class ResetFlag { + KeepImplicitBuffers = 0x01 + }; + Q_DECLARE_FLAGS(ResetFlags, ResetFlag) + void reset(QRhi *rhi, ResetFlags flags = {}); + + struct { + QRhiRenderTarget *renderTarget = nullptr; + bool owns = false; + int multiViewCount = 1; + } rt; + struct { + QRhiTexture *texture = nullptr; + QRhiRenderBuffer *renderBuffer = nullptr; + QRhiRenderPassDescriptor *rpDesc = nullptr; + } res; + struct ImplicitBuffers { + QRhiRenderBuffer *depthStencil = nullptr; + QRhiTexture *depthStencilTexture = nullptr; + QRhiTexture *multisampleTexture = nullptr; + void reset(QRhi *rhi); + } implicitBuffers; + struct { + QPaintDevice *paintDevice = nullptr; + bool owns = false; + } sw; }; -class Q_QUICK_PRIVATE_EXPORT QQuickWindowPrivate : public QWindowPrivate +Q_DECLARE_OPERATORS_FOR_FLAGS(QQuickWindowRenderTarget::ResetFlags) + +class Q_QUICK_EXPORT QQuickWindowPrivate + : public QWindowPrivate + , public QQuickPaletteProviderPrivateBase<QQuickWindow, QQuickWindowPrivate> { public: Q_DECLARE_PUBLIC(QQuickWindow) enum CustomEvents { - FullUpdateRequest = QEvent::User + 1 + FullUpdateRequest = QEvent::User + 1, + TriggerContextCreationFailure = QEvent::User + 2 }; static inline QQuickWindowPrivate *get(QQuickWindow *c) { return c->d_func(); } + static inline const QQuickWindowPrivate *get(const QQuickWindow *c) { return c->d_func(); } QQuickWindowPrivate(); ~QQuickWindowPrivate() override; + void setPalette(QQuickPalette *p) override; + void updateWindowPalette(); + void updateChildrenPalettes(const QPalette &parentPalette) override; + void init(QQuickWindow *, QQuickRenderControl *control = nullptr); QQuickRootItem *contentItem; QSet<QQuickItem *> parentlessItems; QQmlListProperty<QObject> data(); - QQuickItem *activeFocusItem; + // primary delivery agent for the whole scene, used by default for events that arrive in this window; + // but any subscene root can have a QQuickItemPrivate::ExtraData::subsceneDeliveryAgent + QQuickDeliveryAgent *deliveryAgent = nullptr; + QQuickDeliveryAgentPrivate *deliveryAgentPrivate() const + { return deliveryAgent ? static_cast<QQuickDeliveryAgentPrivate *>(QQuickDeliveryAgentPrivate::get(deliveryAgent)) : nullptr; } - void deliverKeyEvent(QKeyEvent *e); - - // Keeps track of the item currently receiving mouse events -#if QT_CONFIG(cursor) - QQuickItem *cursorItem; -#endif -#if QT_CONFIG(draganddrop) - QQuickDragGrabber *dragGrabber; -#endif - int touchMouseId; - QQuickPointerDevice *touchMouseDevice; - bool checkIfDoubleTapped(ulong newPressEventTimestamp, QPoint newPressPos); - ulong touchMousePressTimestamp; - QPoint touchMousePressPos; // in screen coordiantes - void cancelTouchMouseSynthesis(); - - // Mouse positions are saved in widget coordinates - QPointF lastMousePosition; - bool deliverTouchAsMouse(QQuickItem *item, QQuickPointerEvent *pointerEvent); - bool isDeliveringTouchAsMouse() const { return touchMouseId != -1 && touchMouseDevice; } - void translateTouchEvent(QTouchEvent *touchEvent); - void grabTouchPoints(QObject *grabber, const QVector<int> &ids); - void removeGrabber(QQuickItem *grabber, bool mouse = true, bool touch = true); - void sendUngrabEvent(QQuickItem *grabber, bool touch); - static QMouseEvent *cloneMouseEvent(QMouseEvent *event, QPointF *transformedLocalPos = nullptr); - void deliverToPassiveGrabbers(const QVector<QPointer <QQuickPointerHandler> > &passiveGrabbers, QQuickPointerEvent *pointerEvent); - void deliverMouseEvent(QQuickPointerMouseEvent *pointerEvent); - bool sendFilteredMouseEvent(QEvent *event, QQuickItem *receiver, QQuickItem *filteringParent); - bool sendFilteredPointerEvent(QQuickPointerEvent *event, QQuickItem *receiver, QQuickItem *filteringParent = nullptr); - bool sendFilteredPointerEventImpl(QQuickPointerEvent *event, QQuickItem *receiver, QQuickItem *filteringParent); - bool deliverSinglePointEventUntilAccepted(QQuickPointerEvent *); - - // entry point of events to the window - void handleTouchEvent(QTouchEvent *); - void handleMouseEvent(QMouseEvent *); - bool compressTouchEvent(QTouchEvent *); - void flushFrameSynchronousEvents(); - void deliverDelayedTouchEvent(); - - // the device-specific event instances which are reused during event delivery - mutable QVector<QQuickPointerEvent *> pointerEventInstances; - QQuickPointerEvent *queryPointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType = QEvent::None) const; - QQuickPointerEvent *pointerEventInstance(QQuickPointerDevice *device, QEvent::Type eventType = QEvent::None) const; - - // delivery of pointer events: - QQuickPointerEvent *pointerEventInstance(QEvent *ev) const; - void deliverPointerEvent(QQuickPointerEvent *); - void deliverTouchEvent(QQuickPointerTouchEvent *); - bool deliverTouchCancelEvent(QTouchEvent *); - bool deliverPressOrReleaseEvent(QQuickPointerEvent *, bool handlersOnly = false); - void deliverUpdatedTouchPoints(QQuickPointerTouchEvent *event); - void deliverMatchingPointsToItem(QQuickItem *item, QQuickPointerEvent *pointerEvent, bool handlersOnly = false); - - QVector<QQuickItem *> pointerTargets(QQuickItem *, QQuickEventPoint *point, bool checkMouseButtons, bool checkAcceptsTouch) const; - QVector<QQuickItem *> mergePointerTargets(const QVector<QQuickItem *> &list1, const QVector<QQuickItem *> &list2) const; - - // hover delivery - bool deliverHoverEvent(QQuickItem *, const QPointF &scenePos, const QPointF &lastScenePos, Qt::KeyboardModifiers modifiers, ulong timestamp, bool &accepted); - bool sendHoverEvent(QEvent::Type, QQuickItem *, const QPointF &scenePos, const QPointF &lastScenePos, - Qt::KeyboardModifiers modifiers, ulong timestamp, bool accepted); - bool clearHover(ulong timestamp = 0); - -#if QT_CONFIG(draganddrop) - void deliverDragEvent(QQuickDragGrabber *, QEvent *); - bool deliverDragEvent(QQuickDragGrabber *, QQuickItem *, QDragMoveEvent *); -#endif #if QT_CONFIG(cursor) - void updateCursor(const QPointF &scenePos); - QQuickItem *findCursorItem(QQuickItem *item, const QPointF &scenePos); + QQuickItem *cursorItem = nullptr; + QQuickPointerHandler *cursorHandler = nullptr; + void updateCursor(const QPointF &scenePos, QQuickItem *rootItem = nullptr); + QPair<QQuickItem*, QQuickPointerHandler*> findCursorItemAndHandler(QQuickItem *item, const QPointF &scenePos) const; #endif - QList<QQuickItem*> hoverItems; - enum FocusOption { - DontChangeFocusProperty = 0x01, - DontChangeSubFocusItem = 0x02 - }; - Q_DECLARE_FLAGS(FocusOptions, FocusOption) - - void setFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason, FocusOptions = nullptr); - void clearFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason, FocusOptions = nullptr); - static void notifyFocusChangesRecur(QQuickItem **item, int remaining); void clearFocusObject() override; - - void updateFocusItemTransform(); + void setFocusToTarget(FocusTarget, Qt::FocusReason) override; void dirtyItem(QQuickItem *); void cleanup(QSGNode *); + void ensureCustomRenderTarget(); + void setCustomCommandBuffer(QRhiCommandBuffer *cb); + void polishItems(); void forcePolish(); + void invalidateFontData(QQuickItem *item); void syncSceneGraph(); - void renderSceneGraph(const QSize &size); + void renderSceneGraph(); bool isRenderable() const; bool emitError(QQuickWindow::SceneGraphError error, const QString &msg); + enum TextureFromNativeTextureFlag { + NativeTextureIsExternalOES = 0x01 + }; + Q_DECLARE_FLAGS(TextureFromNativeTextureFlags, TextureFromNativeTextureFlag) + + QSGTexture *createTextureFromNativeTexture(quint64 nativeObjectHandle, + int nativeLayoutOrState, + uint nativeFormat, + const QSize &size, + QQuickWindow::CreateTextureOptions options, + TextureFromNativeTextureFlags flags = {}) const; + QSGTexture *createTextureFromNativeTexture(quint64 nativeObjectHandle, + int nativeLayoutOrState, + const QSize &size, + QQuickWindow::CreateTextureOptions options, + TextureFromNativeTextureFlags flags = {}) const { + return createTextureFromNativeTexture(nativeObjectHandle, nativeLayoutOrState, 0, size, options, flags); + } + QQuickItem::UpdatePaintNodeData updatePaintNodeData; QQuickItem *dirtyItemList; QList<QSGNode *> cleanupNodeList; QVector<QQuickItem *> itemsToPolish; - QVector<QQuickItem *> hasFiltered; // during event delivery to a single receiver, the filtering parents for which childMouseEventFilter was already called - QVector<QQuickItem *> skipDelivery; // during delivery of one event to all receivers, Items to which we know delivery is no longer necessary - qreal devicePixelRatio; + qreal lastReportedItemDevicePixelRatio; QMetaObject::Connection physicalDpiChangedConnection; void updateDirtyNodes(); @@ -241,81 +201,71 @@ public: void updateDirtyNode(QQuickItem *); void fireFrameSwapped() { Q_EMIT q_func()->frameSwapped(); } - void fireOpenGLContextCreated(QOpenGLContext *context) { Q_EMIT q_func()->openglContextCreated(context); } void fireAboutToStop() { Q_EMIT q_func()->sceneGraphAboutToStop(); } + void clearGrabbers(QPointerEvent *event); + + void updateChildWindowStackingOrder(QQuickItem *item = nullptr); + + int multiViewCount(); + QRhiRenderTarget *activeCustomRhiRenderTarget(); + QSGRenderContext *context; QSGRenderer *renderer; - QByteArray customRenderMode; // Default renderer supports "clip", "overdraw", "changes", "batches" and blank. + QByteArray visualizationMode; // Default renderer supports "clip", "overdraw", "changes", "batches" and blank. QSGRenderLoop *windowManager; QQuickRenderControl *renderControl; - QQuickAnimatorController *animationController; - QScopedPointer<QTouchEvent> delayedTouch; - - int pointerEventRecursionGuard; - QQuickCustomRenderStage *customRenderStage; + QScopedPointer<QQuickAnimatorController> animationController; QColor clearColor; - uint clearBeforeRendering : 1; - - uint persistentGLContext : 1; + uint persistentGraphics : 1; uint persistentSceneGraph : 1; + uint inDestructor : 1; - uint lastWheelEventAccepted : 1; - bool componentCompleted : 1; - - bool allowChildEventFiltering : 1; - bool allowDoubleClick : 1; + // Storage for setRenderTarget(QQuickRenderTarget). + // Gets baked into redirect.renderTarget by ensureCustomRenderTarget() when rendering the next frame. + QQuickRenderTarget customRenderTarget; - Qt::FocusReason lastFocusReason; + struct Redirect { + QRhiCommandBuffer *commandBuffer = nullptr; + QQuickWindowRenderTarget rt; + bool renderTargetDirty = false; + } redirect; - QOpenGLFramebufferObject *renderTarget; - uint renderTargetId; - QSize renderTargetSize; + QQuickGraphicsDevice customDeviceObjects; - QOpenGLVertexArrayObjectHelper *vaoHelper; + QQuickGraphicsConfiguration graphicsConfig; mutable QQuickWindowIncubationController *incubationController; static bool defaultAlphaBuffer; static QQuickWindow::TextRenderType textRenderType; - static bool dragOverThreshold(qreal d, Qt::Axis axis, QMouseEvent *event, int startDragThreshold = -1); - - template <typename TEventPoint> - static bool dragOverThreshold(qreal d, Qt::Axis axis, const TEventPoint *p, int startDragThreshold = -1) - { - QStyleHints *styleHints = qApp->styleHints(); - bool overThreshold = qAbs(d) > (startDragThreshold >= 0 ? startDragThreshold : styleHints->startDragDistance()); - const bool dragVelocityLimitAvailable = (styleHints->startDragVelocity() > 0); - if (!overThreshold && dragVelocityLimitAvailable) { - qreal velocity = axis == Qt::XAxis ? p->velocity().x() : p->velocity().y(); - overThreshold |= qAbs(velocity) > styleHints->startDragVelocity(); - } - return overThreshold; - } - - static bool dragOverThreshold(const QQuickEventPoint *point) - { - QPointF delta = point->scenePosition() - point->scenePressPosition(); - return (QQuickWindowPrivate::dragOverThreshold(delta.x(), Qt::XAxis, point) || - QQuickWindowPrivate::dragOverThreshold(delta.y(), Qt::YAxis, point)); - } - - static bool dragOverThreshold(QVector2D delta); + // vvv currently in use in Controls 2; TODO remove + static bool dragOverThreshold(qreal d, Qt::Axis axis, const QEventPoint *tp, int startDragThreshold = -1) + { return QQuickDeliveryAgentPrivate::dragOverThreshold(d, axis, *tp, startDragThreshold); } + static bool dragOverThreshold(qreal d, Qt::Axis axis, QMouseEvent *event, int startDragThreshold = -1) + { return QQuickDeliveryAgentPrivate::dragOverThreshold(d, axis, event, startDragThreshold); } + void clearFocusInScope(QQuickItem *scope, QQuickItem *item, Qt::FocusReason reason) + { deliveryAgentPrivate()->clearFocusInScope(scope, item, reason); } + // ^^^ currently in use in Controls 2; TODO remove // data property static void data_append(QQmlListProperty<QObject> *, QObject *); - static int data_count(QQmlListProperty<QObject> *); - static QObject *data_at(QQmlListProperty<QObject> *, int); + static qsizetype data_count(QQmlListProperty<QObject> *); + static QObject *data_at(QQmlListProperty<QObject> *, qsizetype); static void data_clear(QQmlListProperty<QObject> *); + static void data_replace(QQmlListProperty<QObject> *, qsizetype, QObject *); + static void data_removeLast(QQmlListProperty<QObject> *); + + static void rhiCreationFailureMessage(const QString &backendName, + QString *translatedMessage, + QString *untranslatedMessage); - static void contextCreationFailureMessage(const QSurfaceFormat &format, - QString *translatedMessage, - QString *untranslatedMessage, - bool isEs); + static void emitBeforeRenderPassRecording(void *ud); + static void emitAfterRenderPassRecording(void *ud); QMutex renderJobMutex; QList<QRunnable *> beforeSynchronizingJobs; @@ -325,6 +275,20 @@ public: QList<QRunnable *> afterSwapJobs; void runAndClearJobs(QList<QRunnable *> *jobs); + QOpenGLContext *openglContext(); + + QQuickWindow::GraphicsStateInfo rhiStateInfo; + QRhi *rhi = nullptr; + QRhiSwapChain *swapchain = nullptr; + QRhiRenderBuffer *depthStencilForSwapchain = nullptr; + QRhiRenderPassDescriptor *rpDescForSwapchain = nullptr; + uint hasActiveSwapchain : 1; + uint hasRenderableSwapchain : 1; + uint swapchainJustBecameRenderable : 1; + uint updatesEnabled : 1; + bool pendingFontUpdate = false; + bool windowEventDispatch = false; + QPointer<QQuickPalette> windowPaletteRef; private: static void cleanupNodesOnShutdown(QQuickItem *); @@ -343,7 +307,7 @@ public: } }; -Q_DECLARE_OPERATORS_FOR_FLAGS(QQuickWindowPrivate::FocusOptions) +Q_DECLARE_OPERATORS_FOR_FLAGS(QQuickWindowPrivate::TextureFromNativeTextureFlags) QT_END_NAMESPACE |