diff --git a/playground/parrots/BlurredOverlay.cpp b/playground/parrots/BlurredOverlay.cpp index 5e385344..a849e95b 100644 --- a/playground/parrots/BlurredOverlay.cpp +++ b/playground/parrots/BlurredOverlay.cpp @@ -91,7 +91,17 @@ class BlurredOverlayPrivate final : public QQuickItemPrivate, public QQuickItemC layer->setHasMipmaps( false ); layer->setMirrorHorizontal( false ); layer->setMirrorVertical( true ); - layer->setSamples( 0 ); + + if ( q_func()->window()->format().samples() > 2 ) + { + /* + We want to disable multisampling as it doesn't make any sense + in combination with blurring afterwards. Unfortunately + QSGLayer uses the samples from the window when setting samples + below 2 here. + */ + layer->setSamples( 2 ); + } return layer; } @@ -100,19 +110,15 @@ class BlurredOverlayPrivate final : public QQuickItemPrivate, public QQuickItemC { Q_Q( BlurredOverlay ); - layer->setLive( live ); + const auto pixelRatio = q->window()->effectiveDevicePixelRatio(); + + layer->setLive( true ); layer->setItem( QQuickItemPrivate::get( grabbedItem )->itemNode() ); - auto r = grabRect; - if ( r.isEmpty() ) - r = QRectF(0, 0, grabbedItem->width(), grabbedItem->height() ); + const auto rect = QRectF( q->position(), q->size() ); + layer->setRect( rect ); - layer->setRect( r ); - - QSize textureSize( qCeil( qAbs( r.width() ) ), - qCeil( qAbs( r.height() ) ) ); - - const auto pixelRatio = q->window()->effectiveDevicePixelRatio(); + QSize textureSize( qCeil( rect.width() ), qCeil( rect.height() ) ); textureSize *= pixelRatio; const QSize minTextureSize = sceneGraphContext()->minimumFBOSize(); @@ -130,10 +136,7 @@ class BlurredOverlayPrivate final : public QQuickItemPrivate, public QQuickItemC } QPointer< QQuickItem > grabbedItem; - QRectF grabRect; - - const bool live = true; - bool covering = true; + bool covering = false; Q_DECLARE_PUBLIC(BlurredOverlay) }; @@ -169,41 +172,18 @@ void BlurredOverlay::setGrabbedItem( QQuickItem* item ) update(); } -QRectF BlurredOverlay::grabRect() const -{ - return d_func()->grabRect; -} - -void BlurredOverlay::setGrabRect( const QRectF& rect ) -{ - Q_D( BlurredOverlay ); - - QRectF r; - if ( !rect.isEmpty() ) - r = rect; - - if ( r == d->grabRect ) - return; - - if ( r.isEmpty() != d->grabRect.isEmpty() ) - d->setCovering( r.isEmpty() ); - - d->grabRect = r; - - if ( d->grabbedItem ) - update(); -} - -void BlurredOverlay::resetGrabRect() -{ - setGrabRect( QRectF() ); -} - void BlurredOverlay::geometryChange( const QRectF& newGeometry, const QRectF& oldGeometry ) { - update(); Inherited::geometryChange( newGeometry, oldGeometry ); + + /* + When newGeometry covers the grabbedItem completely we could + set covering to true. TODO ... + */ + + if ( d_func()->grabbedItem ) + update(); } QSGNode* BlurredOverlay::updatePaintNode( QSGNode* oldNode, UpdatePaintNodeData* ) @@ -229,22 +209,16 @@ QSGNode* BlurredOverlay::updatePaintNode( QSGNode* oldNode, UpdatePaintNodeData* this, &QQuickItem::update ); } - auto layer = static_cast< QSGLayer* >( node->texture() ); - - d->updateTexture( layer ); + auto itemNode = static_cast< TransformNode* >( d->itemNode() ); + if ( !itemNode->isBlocked ) { - auto itemNode = static_cast< TransformNode* >( d->itemNode() ); - - /* - When we are a child of grabbedItem we end up in a recursion - that fails when initializing the texture twice. No problem - as we explicitly do not want to become part of it. - - Disabling our subtree avoids the problem with the initialization - - the texture contains some artifacts from our own children. TODO ... - */ itemNode->isBlocked = true; + + auto layer = static_cast< QSGLayer* >( node->texture() ); + + d->updateTexture( layer ); + layer->updateTexture(); itemNode->isBlocked = false; } diff --git a/playground/parrots/BlurredOverlay.h b/playground/parrots/BlurredOverlay.h index f0a9a7cd..0993eeb1 100644 --- a/playground/parrots/BlurredOverlay.h +++ b/playground/parrots/BlurredOverlay.h @@ -22,10 +22,6 @@ class BlurredOverlay : public QQuickItem QQuickItem* grabbedItem() const; void setGrabbedItem( QQuickItem* ); - QRectF grabRect() const; - void setGrabRect( const QRectF& ); - void resetGrabRect(); - protected: void geometryChange( const QRectF&, const QRectF& ) override; QSGNode* updatePaintNode( QSGNode*, UpdatePaintNodeData* ) override; diff --git a/playground/parrots/BlurredTextureNode.cpp b/playground/parrots/BlurredTextureNode.cpp index b0d89226..17fa2857 100644 --- a/playground/parrots/BlurredTextureNode.cpp +++ b/playground/parrots/BlurredTextureNode.cpp @@ -58,6 +58,10 @@ namespace { setFlag( UpdatesGraphicsPipelineState, true ); + /* + Using our own shaders - we do not want to add a dependency + to the quickeffects module. + */ setShaderFileName( VertexStage, ":/shaders/blur.vert.qsb" ); setShaderFileName( FragmentStage, ":/shaders/blur.frag.qsb" ); } diff --git a/playground/parrots/main.cpp b/playground/parrots/main.cpp index b2e2dd30..78c4545a 100644 --- a/playground/parrots/main.cpp +++ b/playground/parrots/main.cpp @@ -37,7 +37,6 @@ class ButtonBox : public QskLinearBox label->setSizePolicy( QskSizePolicy::Fixed, QskSizePolicy::Fixed ); label->setLayoutAlignmentHint( Qt::AlignCenter ); - auto button = new QskPushButton( "Button", this ); button->setLayoutAlignmentHint( Qt::AlignHCenter | Qt::AlignBottom ); } @@ -57,33 +56,21 @@ class Overlay : public BlurredOverlay void geometryChange( const QRectF& newRect, const QRectF& oldRect ) override { Inherited::geometryChange( newRect, oldRect ); - setGrabRect( grabbedItem()->mapRectFromItem( this, newRect ) ); + + const auto rect = qskItemRect( this ); + + const auto children = childItems(); + for ( auto child : children ) + { + if ( qskIsAdjustableByLayout( child ) ) + { + const auto r = qskConstrainedItemRect( child, rect ); + qskSetItemGeometry( child, r ); + } + } } }; -class BlurredBox : public QskControl -{ - using Inherited = QskControl; - - public: - BlurredBox( QQuickItem* parent = nullptr ) - : QskControl( parent ) - { - setFlag( QQuickItem::ItemHasContents, false ); - setAutoLayoutChildren( true ); - - m_overlay = new Overlay( this ); - } - - void setGrabbedItem( QQuickItem* item ) - { - m_overlay->setGrabbedItem( item ); - } - - private: - Overlay* m_overlay; -}; - class BackgroundItem : public QskControl { using Inherited = QskControl; @@ -147,15 +134,10 @@ class MainView : public QskControl m_background = new BackgroundItem( this ); -#if 1 - m_blurredBox = new BlurredBox( this ); -#else - // unsatisfying: see comment in BlurredOverlay::updatePaintNode TODO ... - m_blurredBox = new BlurredBox( m_background ); -#endif - m_blurredBox->setGrabbedItem( m_background ); + m_overlay = new Overlay( m_background ); + m_overlay->setGrabbedItem( m_background ); - (void )new ButtonBox( m_blurredBox ); + (void )new ButtonBox( m_overlay ); } protected: @@ -166,12 +148,12 @@ class MainView : public QskControl QRectF blurredRect( QPointF(), 0.7 * size() ); blurredRect.moveCenter( rect().center() ); - m_blurredBox->setGeometry( blurredRect ); + qskSetItemGeometry( m_overlay, blurredRect ); } private: BackgroundItem* m_background; - BlurredBox* m_blurredBox; + Overlay* m_overlay; }; int main( int argc, char** argv )