From f7e8d3cefb543116d80a870d0de7ff6432820624 Mon Sep 17 00:00:00 2001 From: Vlad Zahorodnii Date: Thu, 21 Dec 2023 12:07:08 +0200 Subject: [PATCH] scene: Add SurfaceItem::destinationSize() Its main purpose is to reroute surface size updates through SurfaceItem so it can invalidate quads cache. Not all SurfaceItems currently discard them when needed. When proper item transform support lands, setDestinationSize() could also change the surface scale instead. --- src/scene/itemrenderer_qpainter.cpp | 2 +- src/scene/surfaceitem.cpp | 26 ++++++++++++++++++++------ src/scene/surfaceitem.h | 4 ++++ src/scene/surfaceitem_internal.cpp | 4 ++-- src/scene/surfaceitem_wayland.cpp | 5 ++--- src/scene/surfaceitem_x11.cpp | 4 ++-- 6 files changed, 31 insertions(+), 14 deletions(-) diff --git a/src/scene/itemrenderer_qpainter.cpp b/src/scene/itemrenderer_qpainter.cpp index 4fffbc9802..22c043aef0 100644 --- a/src/scene/itemrenderer_qpainter.cpp +++ b/src/scene/itemrenderer_qpainter.cpp @@ -140,7 +140,7 @@ void ItemRendererQPainter::renderSurfaceItem(QPainter *painter, SurfaceItem *sur surfaceItem->resetDamage(); const OutputTransform surfaceToBufferTransform = surfaceItem->bufferTransform(); - const QSizeF transformedSize = surfaceToBufferTransform.map(surfaceItem->size()); + const QSizeF transformedSize = surfaceToBufferTransform.map(surfaceItem->destinationSize()); painter->save(); switch (surfaceToBufferTransform.kind()) { diff --git a/src/scene/surfaceitem.cpp b/src/scene/surfaceitem.cpp index 27e7504a29..cde1f19bd4 100644 --- a/src/scene/surfaceitem.cpp +++ b/src/scene/surfaceitem.cpp @@ -16,6 +16,20 @@ SurfaceItem::SurfaceItem(Scene *scene, Item *parent) { } +QSizeF SurfaceItem::destinationSize() const +{ + return m_destinationSize; +} + +void SurfaceItem::setDestinationSize(const QSizeF &size) +{ + if (m_destinationSize != size) { + m_destinationSize = size; + setSize(size); + discardQuads(); + } +} + QRectF SurfaceItem::bufferSourceBox() const { return m_bufferSourceBox; @@ -60,8 +74,8 @@ void SurfaceItem::setBufferSize(const QSize &size) QRegion SurfaceItem::mapFromBuffer(const QRegion ®ion) const { const QRectF sourceBox = m_bufferToSurfaceTransform.map(m_bufferSourceBox, m_bufferSize); - const qreal xScale = size().width() / sourceBox.width(); - const qreal yScale = size().height() / sourceBox.height(); + const qreal xScale = m_destinationSize.width() / sourceBox.width(); + const qreal yScale = m_destinationSize.height() / sourceBox.height(); QRegion result; for (QRectF rect : region) { @@ -100,8 +114,8 @@ void SurfaceItem::addDamage(const QRegion ®ion) m_damage += region; const QRectF sourceBox = m_bufferToSurfaceTransform.map(m_bufferSourceBox, m_bufferSize); - const qreal xScale = sourceBox.width() / size().width(); - const qreal yScale = sourceBox.height() / size().height(); + const qreal xScale = sourceBox.width() / m_destinationSize.width(); + const qreal yScale = sourceBox.height() / m_destinationSize.height(); const QRegion logicalDamage = mapFromBuffer(region); const auto delegates = scene()->delegates(); @@ -214,8 +228,8 @@ WindowQuadList SurfaceItem::buildQuads() const quads.reserve(region.count()); const QRectF sourceBox = m_bufferToSurfaceTransform.map(m_bufferSourceBox, m_bufferSize); - const qreal xScale = sourceBox.width() / size().width(); - const qreal yScale = sourceBox.height() / size().height(); + const qreal xScale = sourceBox.width() / m_destinationSize.width(); + const qreal yScale = sourceBox.height() / m_destinationSize.height(); for (const QRectF rect : region) { WindowQuad quad; diff --git a/src/scene/surfaceitem.h b/src/scene/surfaceitem.h index 8de435f3c4..619517268f 100644 --- a/src/scene/surfaceitem.h +++ b/src/scene/surfaceitem.h @@ -26,6 +26,9 @@ class KWIN_EXPORT SurfaceItem : public Item Q_OBJECT public: + QSizeF destinationSize() const; + void setDestinationSize(const QSizeF &size); + QRectF bufferSourceBox() const; void setBufferSourceBox(const QRectF &box); @@ -72,6 +75,7 @@ protected: OutputTransform m_surfaceToBufferTransform; QRectF m_bufferSourceBox; QSize m_bufferSize; + QSizeF m_destinationSize; std::unique_ptr m_pixmap; std::unique_ptr m_previousPixmap; int m_referencePixmapCounter = 0; diff --git a/src/scene/surfaceitem_internal.cpp b/src/scene/surfaceitem_internal.cpp index 7f54dba9df..093f5ef64d 100644 --- a/src/scene/surfaceitem_internal.cpp +++ b/src/scene/surfaceitem_internal.cpp @@ -19,7 +19,7 @@ SurfaceItemInternal::SurfaceItemInternal(InternalWindow *window, Scene *scene, I connect(window, &Window::bufferGeometryChanged, this, &SurfaceItemInternal::handleBufferGeometryChanged); - setSize(window->bufferGeometry().size()); + setDestinationSize(window->bufferGeometry().size()); setBufferSourceBox(QRectF(QPointF(0, 0), window->bufferGeometry().size() * window->bufferScale())); setBufferSize((window->bufferGeometry().size() * window->bufferScale()).toSize()); } @@ -41,7 +41,7 @@ std::unique_ptr SurfaceItemInternal::createPixmap() void SurfaceItemInternal::handleBufferGeometryChanged() { - setSize(m_window->bufferGeometry().size()); + setDestinationSize(m_window->bufferGeometry().size()); setBufferSourceBox(QRectF(QPointF(0, 0), m_window->bufferGeometry().size() * m_window->bufferScale())); setBufferSize((m_window->bufferGeometry().size() * m_window->bufferScale()).toSize()); } diff --git a/src/scene/surfaceitem_wayland.cpp b/src/scene/surfaceitem_wayland.cpp index 590af657c3..e5a17d9b26 100644 --- a/src/scene/surfaceitem_wayland.cpp +++ b/src/scene/surfaceitem_wayland.cpp @@ -55,7 +55,7 @@ SurfaceItemWayland::SurfaceItemWayland(SurfaceInterface *surface, Scene *scene, } handleChildSubSurfacesChanged(); - setSize(surface->size()); + setDestinationSize(surface->size()); setBufferTransform(surface->bufferTransform()); setBufferSourceBox(surface->bufferSourceBox()); setBufferSize(surface->bufferSize()); @@ -82,8 +82,7 @@ SurfaceInterface *SurfaceItemWayland::surface() const void SurfaceItemWayland::handleSurfaceSizeChanged() { - setSize(m_surface->size()); - discardQuads(); + setDestinationSize(m_surface->size()); } void SurfaceItemWayland::handleBufferSizeChanged() diff --git a/src/scene/surfaceitem_x11.cpp b/src/scene/surfaceitem_x11.cpp index bebae8ee8b..c1df8c9ad1 100644 --- a/src/scene/surfaceitem_x11.cpp +++ b/src/scene/surfaceitem_x11.cpp @@ -34,7 +34,7 @@ SurfaceItemX11::SurfaceItemX11(X11Window *window, Scene *scene, Item *parent) m_isDamaged = true; } - setSize(window->bufferGeometry().size()); + setDestinationSize(window->bufferGeometry().size()); setBufferSourceBox(QRectF(QPointF(0, 0), window->bufferGeometry().size())); setBufferSize(window->bufferGeometry().size().toSize()); } @@ -142,7 +142,7 @@ void SurfaceItemX11::destroyDamage() void SurfaceItemX11::handleBufferGeometryChanged() { - setSize(m_window->bufferGeometry().size()); + setDestinationSize(m_window->bufferGeometry().size()); setBufferSourceBox(QRectF(QPointF(0, 0), m_window->bufferGeometry().size())); setBufferSize(m_window->bufferGeometry().size().toSize()); }