28using namespace Qt::StringLiterals;
40 mEffectPainter.reset();
60 if ( element.isNull() )
64 QDomElement effectElement = doc.createElement( u
"effect"_s );
65 effectElement.setAttribute( u
"type"_s,
type() );
67 element.appendChild( effectElement );
73 if ( element.isNull() )
87 mSourceImage = QImage();
95 mPrevPainter = context.
painter();
97 mTempPicture = std::make_unique< QPicture >();
99 mEffectPainter = std::make_unique< QPainter >();
100 mEffectPainter->begin( mTempPicture.get() );
108 if ( !mEffectPainter )
111 mEffectPainter->end();
112 mEffectPainter.reset();
116 mPrevPainter =
nullptr;
120 context.
painter()->setPen( Qt::NoPen );
121 context.
painter()->setBrush( Qt::NoBrush );
124 render( *mTempPicture, context );
127 mTempPicture.reset();
138 painter.drawPicture( 0, 0, mPicture );
145 if ( !mSourceImage.isNull() )
150 if ( mPicture.isNull() )
155 const QRectF bounds = imageBoundingRect( context );
156 mSourceImage = QImage(
static_cast< int >( std::ceil( bounds.width() ) ),
157 static_cast< int >( std::ceil( bounds.height() ) ), QImage::Format_ARGB32 );
158 mSourceImage.fill( Qt::transparent );
159 QPainter imagePainter( &mSourceImage );
160 imagePainter.setRenderHint( QPainter::Antialiasing );
161 imagePainter.translate( -bounds.left(), -bounds.top() );
162 imagePainter.drawPicture( 0, 0, mPicture );
169 return imageBoundingRect( context ).topLeft();
183QRectF QgsPaintEffect::imageBoundingRect(
const QgsRenderContext &context )
const
185 return boundingRect( mPicture.boundingRect(), context );
203 if ( mBlendMode != QPainter::CompositionMode_SourceOver || !
qgsDoubleNear( mOpacity, 1.0 ) )
215 QPainter *painter = context.
painter();
217 if ( mBlendMode == QPainter::CompositionMode_SourceOver &&
qgsDoubleNear( mOpacity, 1.0 ) )
228 painter->setCompositionMode( mBlendMode );
229 painter->drawImage(
imageOffset( context ), image );
241 props.insert( u
"enabled"_s,
mEnabled ?
"1" :
"0" );
242 props.insert( u
"draw_mode"_s, QString::number(
int(
mDrawMode ) ) );
243 props.insert( u
"blend_mode"_s, QString::number(
int( mBlendMode ) ) );
244 props.insert( u
"opacity"_s, QString::number( mOpacity ) );
251 const QPainter::CompositionMode mode =
static_cast< QPainter::CompositionMode
>( props.value( u
"blend_mode"_s ).toInt( &ok ) );
256 if ( props.contains( u
"transparency"_s ) )
258 const double transparency = props.value( u
"transparency"_s ).toDouble( &ok );
261 mOpacity = 1.0 - transparency;
266 const double opacity = props.value( u
"opacity"_s ).toDouble( &ok );
272 mEnabled = props.value( u
"enabled"_s, u
"1"_s ).toInt();
282 : mRenderContext( renderContext )
285 mPainter = renderContext.
painter();
290 : mRenderContext( renderContext )
293 mPainter = mRenderContext.painter();
295 mEffect->begin( mRenderContext );
300 Q_ASSERT( !mEffect );
303 mEffect->
begin( mRenderContext );
310 mEffect->end( mRenderContext );
@ RequiresRasterization
The effect requires raster-based rendering.
QFlags< PaintEffectFlag > PaintEffectFlags
Flags which control how paint effects behave.
QVariantMap properties() const override
Returns the properties describing the paint effect encoded in a string format.
QgsDrawSourceEffect()=default
double opacity() const
Returns the opacity for the effect.
void draw(QgsRenderContext &context) override
Handles drawing of the effect's result on to the specified render context.
QgsDrawSourceEffect * clone() const override
Duplicates an effect by creating a deep copy of the effect.
static QgsPaintEffect * create(const QVariantMap &map)
Creates a new QgsDrawSource effect from a properties string map.
void readProperties(const QVariantMap &props) override
Reads a string map of an effect's properties and restores the effect to the state described by the pr...
Qgis::PaintEffectFlags flags() const override
Returns flags which specify how the paint effect behaves.
QgsEffectPainter(QgsRenderContext &renderContext)
QgsEffectPainter constructor.
void setEffect(QgsPaintEffect *effect)
Sets the effect to be painted.
static void multiplyOpacity(QImage &image, double factor, QgsFeedback *feedback=nullptr)
Multiplies opacity of image pixel values by a factor.
Base class for visual effects which can be applied to QPicture drawings.
bool requiresQPainterDpiFix
void setDrawMode(DrawMode drawMode)
Sets the draw mode for the effect.
void setEnabled(bool enabled)
Sets whether the effect is enabled.
virtual bool saveProperties(QDomDocument &doc, QDomElement &element) const
Saves the current state of the effect to a DOM element.
void drawSource(QPainter &painter)
Draws the source QPicture onto the specified painter.
virtual void readProperties(const QVariantMap &props)=0
Reads a string map of an effect's properties and restores the effect to the state described by the pr...
virtual void begin(QgsRenderContext &context)
Begins intercepting paint operations to a render context.
QImage sourceAsImage(QgsRenderContext &context)
Returns the source QPicture rendered to a new QImage.
QPointF imageOffset(const QgsRenderContext &context) const
Returns the offset which should be used when drawing the source image on to a destination render cont...
DrawMode drawMode() const
Returns the draw mode for the effect.
virtual ~QgsPaintEffect()
virtual void end(QgsRenderContext &context)
Ends interception of paint operations to a render context, and draws the result to the render context...
bool enabled() const
Returns whether the effect is enabled.
virtual Qgis::PaintEffectFlags flags() const
Returns flags which specify how the paint effect behaves.
virtual void render(const QPicture &picture, QgsRenderContext &context)
Renders a picture using the effect.
virtual QRectF boundingRect(const QRectF &rect, const QgsRenderContext &context) const
Returns the bounding rect required for drawing the effect.
virtual QVariantMap properties() const =0
Returns the properties describing the paint effect encoded in a string format.
Q_DECL_DEPRECATED void fixQPictureDpi(QPainter *painter) const
Applies a workaround to a QPainter to avoid an issue with incorrect scaling when drawing QPictures.
DrawMode
Drawing modes for effects.
virtual void draw(QgsRenderContext &context)=0
Handles drawing of the effect's result on to the specified render context.
virtual QString type() const =0
Returns the effect type.
static void applyScaleFixForQPictureDpi(QPainter *painter)
Applies a workaround to a painter to avoid an issue with incorrect scaling when drawing QPictures.
static void drawPicture(QPainter *painter, const QPointF &point, const QPicture &picture)
Draws a picture onto a painter, correctly applying workarounds to avoid issues with incorrect scaling...
Contains information about the context of a rendering operation.
QPainter * painter()
Returns the destination QPainter for the render operation.
void setPainterFlagsUsingContext(QPainter *painter=nullptr) const
Sets relevant flags on a destination painter, using the flags and settings currently defined for the ...
QgsFeedback * feedback() const
Returns the feedback object that can be queried regularly during rendering to check if rendering shou...
void setPainter(QPainter *p)
Sets the destination QPainter for the render operation.
Scoped object for saving and restoring a QPainter object's state.
static void saveProperties(QVariantMap props, QDomDocument &doc, QDomElement &element)
Saves the map of properties to XML.
static QVariantMap parseProperties(const QDomElement &element)
Parses the properties from XML and returns a map.
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference).