diff options
Diffstat (limited to 'src/webenginewidgets')
3 files changed, 72 insertions, 35 deletions
diff --git a/src/webenginewidgets/api/qwebenginepage_p.h b/src/webenginewidgets/api/qwebenginepage_p.h index 3ddf4b3d6..847684198 100644 --- a/src/webenginewidgets/api/qwebenginepage_p.h +++ b/src/webenginewidgets/api/qwebenginepage_p.h @@ -106,7 +106,7 @@ public: QColor backgroundColor() const override; void loadStarted(const QUrl &provisionalUrl, bool isErrorPage = false) override; void loadCommitted() override { } - void loadVisuallyCommitted() override { } + void didFirstVisuallyNonEmptyPaint() override { } void loadFinished(bool success, const QUrl &url, bool isErrorPage = false, int errorCode = 0, const QString &errorDescription = QString()) override; void focusContainer() override; void unhandledKeyEvent(QKeyEvent *event) override; diff --git a/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp b/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp index a52fdef00..853553c47 100644 --- a/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp +++ b/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.cpp @@ -56,14 +56,19 @@ namespace QtWebEngineCore { -class RenderWidgetHostViewQuickItem : public QQuickItem { +class RenderWidgetHostViewQuickItem : public QQuickItem, public Compositor::Observer +{ public: RenderWidgetHostViewQuickItem(RenderWidgetHostViewQtDelegateClient *client) : m_client(client) { setFlag(ItemHasContents, true); // Mark that this item should receive focus when the parent QQuickWidget receives focus. setFocus(true); + + bind(client->compositorId()); } + ~RenderWidgetHostViewQuickItem() { unbind(); } + protected: bool event(QEvent *event) override { @@ -84,17 +89,80 @@ protected: { m_client->forwardEvent(event); } - QSGNode *updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *) override + void itemChange(ItemChange change, const ItemChangeData &value) override { - return m_client->updatePaintNode(oldNode); + QQuickItem::itemChange(change, value); + if (change == QQuickItem::ItemSceneChange) { + for (const QMetaObject::Connection &c : qAsConst(m_windowConnections)) + disconnect(c); + m_windowConnections.clear(); + if (value.window) { + m_windowConnections.append(connect( + value.window, &QQuickWindow::beforeRendering, this, + &RenderWidgetHostViewQuickItem::onBeforeRendering, Qt::DirectConnection)); + } + } } + QSGNode *updatePaintNode(QSGNode *oldNode, UpdatePaintNodeData *) override + { + auto comp = compositor(); + if (!comp) + return nullptr; + + QQuickWindow *win = QQuickItem::window(); + + // Delete old node before swapFrame to decrement refcount of + // QImage in software mode. + delete oldNode; + QSGImageNode *node = win->createImageNode(); + node->setOwnsTexture(true); + + comp->swapFrame(); + + if (comp->type() == Compositor::Type::Software) { + QImage image = comp->image(); + float pixPerDip = comp->devicePixelRatio(); + QSizeF sizeInDips = QSizeF(image.size()) / pixPerDip; + node->setRect(QRectF(QPointF(0, 0), sizeInDips)); + node->setTexture(win->createTextureFromImage(image)); + } else if (comp->type() == Compositor::Type::OpenGL) { + QSize texSize = comp->textureSize(); + float pixPerDip = comp->devicePixelRatio(); + QSizeF sizeInDips = QSizeF(texSize) / pixPerDip; + node->setRect(QRectF(QPointF(0, 0), sizeInDips)); + QQuickWindow::CreateTextureOptions texOpts; + if (comp->hasAlphaChannel()) + texOpts.setFlag(QQuickWindow::TextureHasAlphaChannel); + int texId = comp->textureId(); + node->setTexture(win->createTextureFromNativeObject(QQuickWindow::NativeObjectTexture, + texId, 0, texSize, texOpts)); + node->setTextureCoordinatesTransform(QSGImageNode::MirrorVertically); + } else { + Q_UNREACHABLE(); + } + return node; + } + void onBeforeRendering() + { + auto comp = compositor(); + if (!comp || comp->type() != Compositor::Type::OpenGL) + return; + comp->waitForTexture(); + } QVariant inputMethodQuery(Qt::InputMethodQuery query) const override { return m_client->inputMethodQuery(query); } + void readyToSwap() override + { + // Call update() on UI thread. + QMetaObject::invokeMethod(this, &QQuickItem::update, Qt::QueuedConnection); + } + private: RenderWidgetHostViewQtDelegateClient *m_client; + QList<QMetaObject::Connection> m_windowConnections; }; RenderWidgetHostViewQtDelegateWidget::RenderWidgetHostViewQtDelegateWidget(RenderWidgetHostViewQtDelegateClient *client, QWidget *parent) @@ -293,32 +361,6 @@ QWindow* RenderWidgetHostViewQtDelegateWidget::window() const return root ? root->windowHandle() : 0; } -QSGTexture *RenderWidgetHostViewQtDelegateWidget::createTextureFromImage(const QImage &image) -{ - return quickWindow()->createTextureFromImage(image, QQuickWindow::TextureCanUseAtlas); -} - -QSGLayer *RenderWidgetHostViewQtDelegateWidget::createLayer() -{ - QSGRenderContext *renderContext = QQuickWindowPrivate::get(quickWindow())->context; - return renderContext->sceneGraphContext()->createLayer(renderContext); -} - -QSGImageNode *RenderWidgetHostViewQtDelegateWidget::createImageNode() -{ - return quickWindow()->createImageNode(); -} - -QSGRectangleNode *RenderWidgetHostViewQtDelegateWidget::createRectangleNode() -{ - return quickWindow()->createRectangleNode(); -} - -void RenderWidgetHostViewQtDelegateWidget::update() -{ - m_rootItem->update(); -} - void RenderWidgetHostViewQtDelegateWidget::updateCursor(const QCursor &cursor) { QQuickWidget::setCursor(cursor); diff --git a/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.h b/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.h index 034fdd65c..57b272183 100644 --- a/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.h +++ b/src/webenginewidgets/render_widget_host_view_qt_delegate_widget.h @@ -79,11 +79,6 @@ public: void hide() override; bool isVisible() const override; QWindow* window() const override; - QSGTexture *createTextureFromImage(const QImage &) override; - QSGLayer *createLayer() override; - QSGImageNode *createImageNode() override; - QSGRectangleNode *createRectangleNode() override; - void update() override; void updateCursor(const QCursor &) override; void resize(int width, int height) override; void move(const QPoint &screenPos) override; |