From 98967a56197b674d98998a3d2d75f8ebac21528e Mon Sep 17 00:00:00 2001 From: Uwe Rathmann Date: Thu, 19 Sep 2024 10:49:36 +0200 Subject: [PATCH] QskArcRenderer API in line with QskBoxRenderer --- src/nodes/QskArcRenderNode.cpp | 51 ++++++----------------- src/nodes/QskArcRenderer.cpp | 75 +++++++++++++++++++++++++++------- src/nodes/QskArcRenderer.h | 19 ++++++--- 3 files changed, 86 insertions(+), 59 deletions(-) diff --git a/src/nodes/QskArcRenderNode.cpp b/src/nodes/QskArcRenderNode.cpp index 0d7ffddd..398284ff 100644 --- a/src/nodes/QskArcRenderNode.cpp +++ b/src/nodes/QskArcRenderNode.cpp @@ -14,7 +14,11 @@ class QskArcRenderNodePrivate final : public QskFillNodePrivate { public: - inline void resetValues() { hash = 0; } + inline void resetNode( QskArcRenderNode* node ) + { + hash = 0; + node->resetGeometry(); + } QskHashValue hash = 0; }; @@ -55,9 +59,7 @@ void QskArcRenderNode::updateNode( if ( rect.isEmpty() || metrics.isNull() || !( hasFill || hasBorder ) ) { - d->resetValues(); - QskSGNode::resetGeometry( this ); - + d->resetNode( this ); return; } @@ -77,45 +79,18 @@ void QskArcRenderNode::updateNode( d->hash = hash; - auto coloring = QskFillNode::Polychrome; - -#if 0 - if ( !( hasFill && hasBorder ) ) - { - if ( hasBorder || ( hasFill && gradient.isMonochrome() ) ) - coloring = QskFillNode::Monochrome; - } +#if 1 + const bool coloredGeometry = hasHint( PreferColoredGeometry ) + && QskArcRenderer::isGradientSupported( rect, metrics, gradient ); + Q_ASSERT( coloredGeometry ); // TODO ... #endif auto& geometry = *this->geometry(); - if ( coloring == QskFillNode::Polychrome ) - { - setColoring( coloring ); + setColoring( QskFillNode::Polychrome ); - QskArcRenderer::renderArc( rect, metrics, radial, - borderWidth, gradient, borderColor, geometry ); - } - else - { - if ( hasFill ) - { - setColoring( gradient.rgbStart() ); - - QskArcRenderer::renderArc( rect, metrics, radial, - borderWidth, gradient, borderColor, geometry ); - } - else - { - setColoring( borderColor ); - - QskArcRenderer::renderArc( rect, metrics, radial, - borderWidth, gradient, borderColor, geometry ); - } - } + QskArcRenderer::setColoredBorderAndFillLines( rect, metrics, radial, + borderWidth, borderColor, gradient, geometry ); markDirty( QSGNode::DirtyGeometry ); - markDirty( QSGNode::DirtyMaterial ); - - geometry.markVertexDataDirty(); } diff --git a/src/nodes/QskArcRenderer.cpp b/src/nodes/QskArcRenderer.cpp index 1a7963ce..db8c6306 100644 --- a/src/nodes/QskArcRenderer.cpp +++ b/src/nodes/QskArcRenderer.cpp @@ -11,7 +11,6 @@ #include "QskRgbValue.h" #include -#include static inline QskVertex::Line* qskAllocateLines( QSGGeometry& geometry, int lineCount ) @@ -466,8 +465,8 @@ bool QskArcRenderer::isGradientSupported( const QRectF& rect, if ( qskFuzzyCompare( direction.aspectRatio(), aspectRatio ) ) { /* - we should be able to create a list of stops from - this gradient that works for the renderer. TODO ... + we should be able to create a list of stops from + this gradient that works for the renderer. TODO ... */ } } @@ -483,17 +482,55 @@ bool QskArcRenderer::isGradientSupported( const QRectF& rect, return false; } -void QskArcRenderer::renderArc( const QRectF& rect, const QskArcMetrics& metrics, - bool radial, const QskGradient& gradient, QSGGeometry& geometry ) -{ - renderArc( rect, metrics, radial, 0, gradient, QColor(), geometry ); -} - -void QskArcRenderer::renderArc( const QRectF& rect, const QskArcMetrics& metrics, - bool radial, qreal borderWidth, const QskGradient& gradient, +void QskArcRenderer::setColoredBorderLines( const QRectF& rect, + const QskArcMetrics& metrics, bool radial, qreal borderWidth, const QColor& borderColor, QSGGeometry& geometry ) { geometry.setDrawingMode( QSGGeometry::DrawTriangleStrip ); + geometry.markVertexDataDirty(); + + if ( borderWidth <= 0.0 || !( borderColor.isValid() && borderColor.alpha() > 0 ) ) + { + qskAllocateColoredLines( geometry, 0 ); + return; + } + + const Renderer renderer( rect, metrics, radial, QskGradient(), borderColor ); + + if ( const auto lines = qskAllocateColoredLines( geometry, renderer.borderCount() ) ) + { + renderer.renderArc( metrics.thickness(), borderWidth, + static_cast< QskVertex::ColoredLine* >( nullptr ), lines ); + } +} + +void QskArcRenderer::setColoredFillLines( const QRectF& rect, const QskArcMetrics& metrics, + bool radial, const QskGradient& gradient, QSGGeometry& geometry ) +{ + geometry.setDrawingMode( QSGGeometry::DrawTriangleStrip ); + geometry.markVertexDataDirty(); + + if ( !gradient.isVisible() ) + { + qskAllocateColoredLines( geometry, 0 ); + return; + } + + const Renderer renderer( rect, metrics, radial, gradient, QColor( 0, 0, 0, 0 ) ); + + if ( const auto lines = qskAllocateColoredLines( geometry, renderer.fillCount() ) ) + { + renderer.renderArc( metrics.thickness(), 0.0, lines, + static_cast< QskVertex::ColoredLine* >( nullptr ) ); + } +} + +void QskArcRenderer::setColoredBorderAndFillLines( const QRectF& rect, + const QskArcMetrics& metrics, bool radial, qreal borderWidth, + const QColor& borderColor, const QskGradient& gradient, QSGGeometry& geometry ) +{ + geometry.setDrawingMode( QSGGeometry::DrawTriangleStrip ); + geometry.markVertexDataDirty(); const Renderer renderer( rect, metrics, radial, gradient, borderColor.isValid() ? borderColor : QColor( 0, 0, 0, 0 ) ); @@ -523,13 +560,20 @@ void QskArcRenderer::renderArc( const QRectF& rect, const QskArcMetrics& metrics } } -void QskArcRenderer::renderBorderGeometry( const QRectF& rect, +void QskArcRenderer::setBorderLines( const QRectF& rect, const QskArcMetrics& metrics, bool radial, qreal borderWidth, QSGGeometry& geometry ) { geometry.setDrawingMode( QSGGeometry::DrawTriangleStrip ); - + geometry.markVertexDataDirty(); + + if ( borderWidth <= 0.0 ) + { + qskAllocateLines( geometry, 0 ); + return; + } + const Renderer renderer( rect, metrics, radial, QskGradient(), 0 ); - + const auto lines = qskAllocateLines( geometry, renderer.borderCount() ); if ( lines ) { @@ -538,10 +582,11 @@ void QskArcRenderer::renderBorderGeometry( const QRectF& rect, } } -void QskArcRenderer::renderFillGeometry( const QRectF& rect, +void QskArcRenderer::setFillLines( const QRectF& rect, const QskArcMetrics& metrics, bool radial, qreal borderWidth, QSGGeometry& geometry ) { geometry.setDrawingMode( QSGGeometry::DrawTriangleStrip ); + geometry.markVertexDataDirty(); const Renderer renderer( rect, metrics, radial, QskRgb::Black, 0 ); diff --git a/src/nodes/QskArcRenderer.h b/src/nodes/QskArcRenderer.h index 1b0ce528..10b740f3 100644 --- a/src/nodes/QskArcRenderer.h +++ b/src/nodes/QskArcRenderer.h @@ -25,24 +25,31 @@ namespace QskArcRenderer - using shaders setting the colors */ - QSK_EXPORT void renderBorderGeometry( const QRectF&, + QSK_EXPORT void setBorderLines( const QRectF&, const QskArcMetrics&, bool radial, qreal borderWidth, QSGGeometry& ); - QSK_EXPORT void renderFillGeometry( const QRectF&, + QSK_EXPORT void setFillLines( const QRectF&, const QskArcMetrics&, bool radial, qreal borderWidth, QSGGeometry& ); /* Filling the geometry with color information: see QSGGeometry::defaultAttributes_ColoredPoint2D() + + Usually used in combination with QSGVertexColorMaterial */ QSK_EXPORT bool isGradientSupported( const QRectF&, const QskArcMetrics&, const QskGradient& ); - QSK_EXPORT void renderArc( const QRectF&, const QskArcMetrics&, bool radial, - qreal borderWidth, const QskGradient&, const QColor& borderColor, QSGGeometry& ); + QSK_EXPORT void setColoredBorderLines( const QRectF&, + const QskArcMetrics&, bool radial, qreal borderWidth, + const QColor& borderColor, QSGGeometry& ); - QSK_EXPORT void renderArc( const QRectF&, const QskArcMetrics&, bool radial, - const QskGradient&, QSGGeometry& ); + QSK_EXPORT void setColoredFillLines( const QRectF&, + const QskArcMetrics&, bool radial, const QskGradient&, QSGGeometry& ); + + QSK_EXPORT void setColoredBorderAndFillLines( const QRectF&, + const QskArcMetrics&, bool radial, qreal borderWidth, + const QColor& borderColor, const QskGradient&, QSGGeometry& ); } #endif