QGIS API Documentation 3.28.0-Firenze (ed3ad0430f)
qgstextbackgroundsettings.cpp
Go to the documentation of this file.
1/***************************************************************************
2 qgstextbackgroundsettings.cpp
3 -----------------
4 begin : May 2020
5 copyright : (C) Nyall Dawson
6 email : nyall dot dawson at gmail dot com
7 ***************************************************************************
8 * *
9 * This program is free software; you can redistribute it and/or modify *
10 * it under the terms of the GNU General Public License as published by *
11 * the Free Software Foundation; either version 2 of the License, or *
12 * (at your option) any later version. *
13 * *
14 ***************************************************************************/
15
17#include "qgstextrenderer_p.h"
18#include "qgsvectorlayer.h"
19#include "qgspallabeling.h"
20#include "qgssymbollayerutils.h"
21#include "qgsfillsymbollayer.h"
22#include "qgspainting.h"
25#include "qgsapplication.h"
26
28{
29 d = new QgsTextBackgroundSettingsPrivate();
30
31 // Create a default fill symbol to preserve API promise until QGIS 4.0
32 QgsSimpleFillSymbolLayer *fill = new QgsSimpleFillSymbolLayer( d->fillColor, Qt::SolidPattern, d->strokeColor );
33 fill->setStrokeWidth( d->strokeWidth );
34 fill->setStrokeWidthUnit( d->strokeWidthUnits );
35 fill->setStrokeWidthMapUnitScale( d->strokeWidthMapUnitScale );
36 fill->setStrokeStyle( !qgsDoubleNear( d->strokeWidth, 0.0 ) ? Qt::SolidLine : Qt::NoPen );
37 fill->setPenJoinStyle( d->joinStyle );
38
40 fillSymbol->changeSymbolLayer( 0, fill );
42}
43
45 : d( other.d )
46{
47
48}
49
51{
52 d = other.d;
53 return *this;
54}
55
57{
58
59}
60
62{
63 if ( !d->enabled == other.enabled()
64 || d->type != other.type()
65 || d->svgFile != other.svgFile()
66 || d->sizeType != other.sizeType()
67 || d->size != other.size()
68 || d->sizeUnits != other.sizeUnit()
69 || d->sizeMapUnitScale != other.sizeMapUnitScale()
70 || d->rotationType != other.rotationType()
71 || d->rotation != other.rotation()
72 || d->offset != other.offset()
73 || d->offsetUnits != other.offsetUnit()
74 || d->offsetMapUnitScale != other.offsetMapUnitScale()
75 || d->radii != other.radii()
76 || d->radiiUnits != other.radiiUnit()
77 || d->radiiMapUnitScale != other.radiiMapUnitScale()
78 || d->blendMode != other.blendMode()
79 || d->fillColor != other.fillColor()
80 || d->strokeColor != other.strokeColor()
81 || d->opacity != other.opacity()
82 || d->strokeWidth != other.strokeWidth()
83 || d->strokeWidthUnits != other.strokeWidthUnit()
84 || d->strokeWidthMapUnitScale != other.strokeWidthMapUnitScale()
85 || d->joinStyle != other.joinStyle() )
86 return false;
87
88 if ( static_cast< bool >( d->paintEffect ) != static_cast< bool >( other.paintEffect() )
89 || ( d->paintEffect && d->paintEffect->properties() != other.paintEffect()->properties() ) )
90 return false;
91
92 if ( static_cast< bool >( d->markerSymbol ) != static_cast< bool >( other.markerSymbol() )
93 || ( d->markerSymbol && QgsSymbolLayerUtils::symbolProperties( d->markerSymbol.get() ) != QgsSymbolLayerUtils::symbolProperties( other.markerSymbol() ) ) )
94 return false;
95
96 if ( static_cast< bool >( d->fillSymbol ) != static_cast< bool >( other.fillSymbol() )
97 || ( d->fillSymbol && QgsSymbolLayerUtils::symbolProperties( d->fillSymbol.get() ) != QgsSymbolLayerUtils::symbolProperties( other.fillSymbol() ) ) )
98 return false;
99
100 return true;
101}
102
104{
105 return !( *this == other );
106}
107
109{
110 return d->enabled;
111}
112
114{
115 d->enabled = enabled;
116}
117
119{
120 return d->type;
121}
122
124{
125 d->type = type;
126}
127
129{
130 return d->svgFile;
131}
132
133void QgsTextBackgroundSettings::setSvgFile( const QString &file )
134{
135 d->svgFile = file;
136}
137
139{
140 return d->markerSymbol.get();
141}
142
144{
145 d->markerSymbol.reset( symbol );
146}
147
149{
150 return d->fillSymbol.get();
151}
152
154{
155 d->fillSymbol.reset( symbol );
156}
157
159{
160 return d->sizeType;
161}
162
164{
165 d->sizeType = type;
166}
167
169{
170 return d->size;
171}
172
174{
175 d->size = size;
176}
177
179{
180 return d->sizeUnits;
181}
182
184{
185 d->sizeUnits = unit;
186}
187
189{
190 return d->sizeMapUnitScale;
191}
192
194{
195 d->sizeMapUnitScale = scale;
196}
197
199{
200 return d->rotationType;
201}
202
204{
205 d->rotationType = type;
206}
207
209{
210 return d->rotation;
211}
212
214{
215 d->rotation = rotation;
216}
217
219{
220 return d->offset;
221}
222
224{
225 d->offset = offset;
226}
227
229{
230 return d->offsetUnits;
231}
232
234{
235 d->offsetUnits = units;
236}
237
239{
240 return d->offsetMapUnitScale;
241}
242
244{
245 d->offsetMapUnitScale = scale;
246}
247
249{
250 return d->radii;
251}
252
254{
255 d->radii = radii;
256}
257
259{
260 return d->radiiUnits;
261}
262
264{
265 d->radiiUnits = units;
266}
267
269{
270 return d->radiiMapUnitScale;
271}
272
274{
275 d->radiiMapUnitScale = scale;
276}
277
279{
280 return d->opacity;
281}
282
284{
285 d->opacity = opacity;
286}
287
288QPainter::CompositionMode QgsTextBackgroundSettings::blendMode() const
289{
290 return d->blendMode;
291}
292
293void QgsTextBackgroundSettings::setBlendMode( QPainter::CompositionMode mode )
294{
295 d->blendMode = mode;
296}
297
299{
300 return d->fillColor;
301}
302
304{
305 d->fillColor = color;
306 if ( d->fillSymbol && d->fillSymbol->symbolLayers().at( 0 )->layerType() == QLatin1String( "SimpleFill" ) )
307 {
308 qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) )->setColor( color );
309 }
310}
311
313{
314 return d->strokeColor;
315}
316
318{
319 d->strokeColor = color;
320 if ( d->fillSymbol && d->fillSymbol->symbolLayers().at( 0 )->layerType() == QLatin1String( "SimpleFill" ) )
321 {
322 qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) )->setStrokeColor( color );
323 }
324}
325
327{
328 return d->strokeWidth;
329}
330
332{
333 d->strokeWidth = width;
334 if ( d->fillSymbol && d->fillSymbol->symbolLayers().at( 0 )->layerType() == QLatin1String( "SimpleFill" ) )
335 {
336 QgsSimpleFillSymbolLayer *fill = qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) );
337 fill->setStrokeWidth( width );
338 fill->setStrokeStyle( !qgsDoubleNear( width, 0.0 ) ? Qt::SolidLine : Qt::NoPen );
339 }
340}
341
343{
344 return d->strokeWidthUnits;
345}
346
348{
349 d->strokeWidthUnits = units;
350 if ( d->fillSymbol && d->fillSymbol->symbolLayers().at( 0 )->layerType() == QLatin1String( "SimpleFill" ) )
351 {
352 qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) )->setStrokeWidthUnit( units );
353 }
354}
355
357{
358 return d->strokeWidthMapUnitScale;
359}
360
362{
363 d->strokeWidthMapUnitScale = scale;
364 if ( d->fillSymbol && d->fillSymbol->symbolLayers().at( 0 )->layerType() == QLatin1String( "SimpleFill" ) )
365 {
366 qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) )->setStrokeWidthMapUnitScale( scale );
367 }
368}
369
371{
372 return d->joinStyle;
373}
374
375void QgsTextBackgroundSettings::setJoinStyle( Qt::PenJoinStyle style )
376{
377 d->joinStyle = style;
378 if ( d->fillSymbol && d->fillSymbol->symbolLayers().at( 0 )->layerType() == QLatin1String( "SimpleFill" ) )
379 {
380 qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) )->setPenJoinStyle( style );
381 }
382}
383
385{
386 return d->paintEffect.get();
387}
388
390{
391 d->paintEffect.reset( effect );
392}
393
395{
396 d->enabled = layer->customProperty( QStringLiteral( "labeling/shapeDraw" ), QVariant( false ) ).toBool();
397 d->type = static_cast< ShapeType >( layer->customProperty( QStringLiteral( "labeling/shapeType" ), QVariant( ShapeRectangle ) ).toUInt() );
398 d->svgFile = layer->customProperty( QStringLiteral( "labeling/shapeSVGFile" ), QVariant( "" ) ).toString();
399 d->sizeType = static_cast< SizeType >( layer->customProperty( QStringLiteral( "labeling/shapeSizeType" ), QVariant( SizeBuffer ) ).toUInt() );
400 d->size = QSizeF( layer->customProperty( QStringLiteral( "labeling/shapeSizeX" ), QVariant( 0.0 ) ).toDouble(),
401 layer->customProperty( QStringLiteral( "labeling/shapeSizeY" ), QVariant( 0.0 ) ).toDouble() );
402
403 if ( layer->customProperty( QStringLiteral( "labeling/shapeSizeUnit" ) ).toString().isEmpty() )
404 {
405 d->sizeUnits = QgsTextRendererUtils::convertFromOldLabelUnit( layer->customProperty( QStringLiteral( "labeling/shapeSizeUnits" ), 0 ).toUInt() );
406 }
407 else
408 {
409 d->sizeUnits = QgsUnitTypes::decodeRenderUnit( layer->customProperty( QStringLiteral( "labeling/shapeSizeUnit" ) ).toString() );
410 }
411
412 if ( layer->customProperty( QStringLiteral( "labeling/shapeSizeMapUnitScale" ) ).toString().isEmpty() )
413 {
414 //fallback to older property
415 const double oldMin = layer->customProperty( QStringLiteral( "labeling/shapeSizeMapUnitMinScale" ), 0.0 ).toDouble();
416 d->sizeMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
417 const double oldMax = layer->customProperty( QStringLiteral( "labeling/shapeSizeMapUnitMaxScale" ), 0.0 ).toDouble();
418 d->sizeMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
419 }
420 else
421 {
422 d->sizeMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( layer->customProperty( QStringLiteral( "labeling/shapeSizeMapUnitScale" ) ).toString() );
423 }
424 d->rotationType = static_cast< RotationType >( layer->customProperty( QStringLiteral( "labeling/shapeRotationType" ), QVariant( RotationSync ) ).toUInt() );
425 d->rotation = layer->customProperty( QStringLiteral( "labeling/shapeRotation" ), QVariant( 0.0 ) ).toDouble();
426 d->offset = QPointF( layer->customProperty( QStringLiteral( "labeling/shapeOffsetX" ), QVariant( 0.0 ) ).toDouble(),
427 layer->customProperty( QStringLiteral( "labeling/shapeOffsetY" ), QVariant( 0.0 ) ).toDouble() );
428
429 if ( layer->customProperty( QStringLiteral( "labeling/shapeOffsetUnit" ) ).toString().isEmpty() )
430 {
431 d->offsetUnits = QgsTextRendererUtils::convertFromOldLabelUnit( layer->customProperty( QStringLiteral( "labeling/shapeOffsetUnits" ), 0 ).toUInt() );
432 }
433 else
434 {
435 d->offsetUnits = QgsUnitTypes::decodeRenderUnit( layer->customProperty( QStringLiteral( "labeling/shapeOffsetUnit" ) ).toString() );
436 }
437
438 if ( layer->customProperty( QStringLiteral( "labeling/shapeOffsetMapUnitScale" ) ).toString().isEmpty() )
439 {
440 //fallback to older property
441 const double oldMin = layer->customProperty( QStringLiteral( "labeling/shapeOffsetMapUnitMinScale" ), 0.0 ).toDouble();
442 d->offsetMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
443 const double oldMax = layer->customProperty( QStringLiteral( "labeling/shapeOffsetMapUnitMaxScale" ), 0.0 ).toDouble();
444 d->offsetMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
445 }
446 else
447 {
448 d->offsetMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( layer->customProperty( QStringLiteral( "labeling/shapeOffsetMapUnitScale" ) ).toString() );
449 }
450 d->radii = QSizeF( layer->customProperty( QStringLiteral( "labeling/shapeRadiiX" ), QVariant( 0.0 ) ).toDouble(),
451 layer->customProperty( QStringLiteral( "labeling/shapeRadiiY" ), QVariant( 0.0 ) ).toDouble() );
452
453
454 if ( layer->customProperty( QStringLiteral( "labeling/shapeRadiiUnit" ) ).toString().isEmpty() )
455 {
456 d->radiiUnits = QgsTextRendererUtils::convertFromOldLabelUnit( layer->customProperty( QStringLiteral( "labeling/shapeRadiiUnits" ), 0 ).toUInt() );
457 }
458 else
459 {
460 d->radiiUnits = QgsUnitTypes::decodeRenderUnit( layer->customProperty( QStringLiteral( "labeling/shapeRadiiUnit" ) ).toString() );
461 }
462
463 if ( layer->customProperty( QStringLiteral( "labeling/shapeRadiiMapUnitScale" ) ).toString().isEmpty() )
464 {
465 //fallback to older property
466 const double oldMin = layer->customProperty( QStringLiteral( "labeling/shapeRadiiMapUnitMinScale" ), 0.0 ).toDouble();
467 d->radiiMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
468 const double oldMax = layer->customProperty( QStringLiteral( "labeling/shapeRadiiMapUnitMaxScale" ), 0.0 ).toDouble();
469 d->radiiMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
470 }
471 else
472 {
473 d->radiiMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( layer->customProperty( QStringLiteral( "labeling/shapeRadiiMapUnitScale" ) ).toString() );
474 }
475 d->fillColor = QgsTextRendererUtils::readColor( layer, QStringLiteral( "labeling/shapeFillColor" ), Qt::white, true );
476 d->strokeColor = QgsTextRendererUtils::readColor( layer, QStringLiteral( "labeling/shapeBorderColor" ), Qt::darkGray, true );
477 d->strokeWidth = layer->customProperty( QStringLiteral( "labeling/shapeBorderWidth" ), QVariant( .0 ) ).toDouble();
478 if ( layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthUnit" ) ).toString().isEmpty() )
479 {
480 d->strokeWidthUnits = QgsTextRendererUtils::convertFromOldLabelUnit( layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthUnits" ), 0 ).toUInt() );
481 }
482 else
483 {
484 d->strokeWidthUnits = QgsUnitTypes::decodeRenderUnit( layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthUnit" ) ).toString() );
485 }
486 if ( layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthMapUnitScale" ) ).toString().isEmpty() )
487 {
488 //fallback to older property
489 const double oldMin = layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthMapUnitMinScale" ), 0.0 ).toDouble();
490 d->strokeWidthMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
491 const double oldMax = layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthMapUnitMaxScale" ), 0.0 ).toDouble();
492 d->strokeWidthMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
493 }
494 else
495 {
496 d->strokeWidthMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( layer->customProperty( QStringLiteral( "labeling/shapeBorderWidthMapUnitScale" ) ).toString() );
497 }
498 d->joinStyle = static_cast< Qt::PenJoinStyle >( layer->customProperty( QStringLiteral( "labeling/shapeJoinStyle" ), QVariant( Qt::BevelJoin ) ).toUInt() );
499
500 if ( layer->customProperty( QStringLiteral( "labeling/shapeOpacity" ) ).toString().isEmpty() )
501 {
502 d->opacity = ( 1 - layer->customProperty( QStringLiteral( "labeling/shapeTransparency" ) ).toInt() / 100.0 ); //0 -100
503 }
504 else
505 {
506 d->opacity = ( layer->customProperty( QStringLiteral( "labeling/shapeOpacity" ) ).toDouble() );
507 }
508 d->blendMode = QgsPainting::getCompositionMode(
509 static_cast< QgsPainting::BlendMode >( layer->customProperty( QStringLiteral( "labeling/shapeBlendMode" ), QVariant( QgsPainting::BlendNormal ) ).toUInt() ) );
510
511 if ( layer->customProperty( QStringLiteral( "labeling/shapeEffect" ) ).isValid() )
512 {
513 QDomDocument doc( QStringLiteral( "effect" ) );
514 doc.setContent( layer->customProperty( QStringLiteral( "labeling/shapeEffect" ) ).toString() );
515 const QDomElement effectElem = doc.firstChildElement( QStringLiteral( "effect" ) ).firstChildElement( QStringLiteral( "effect" ) );
516 setPaintEffect( QgsApplication::paintEffectRegistry()->createEffect( effectElem ) );
517 }
518 else
519 setPaintEffect( nullptr );
520}
521
522void QgsTextBackgroundSettings::readXml( const QDomElement &elem, const QgsReadWriteContext &context )
523{
524 const QDomElement backgroundElem = elem.firstChildElement( QStringLiteral( "background" ) );
525 d->enabled = backgroundElem.attribute( QStringLiteral( "shapeDraw" ), QStringLiteral( "0" ) ).toInt();
526 d->type = static_cast< ShapeType >( backgroundElem.attribute( QStringLiteral( "shapeType" ), QString::number( ShapeRectangle ) ).toUInt() );
527 d->svgFile = QgsSymbolLayerUtils::svgSymbolNameToPath( backgroundElem.attribute( QStringLiteral( "shapeSVGFile" ) ), context.pathResolver() );
528 d->sizeType = static_cast< SizeType >( backgroundElem.attribute( QStringLiteral( "shapeSizeType" ), QString::number( SizeBuffer ) ).toUInt() );
529 d->size = QSizeF( backgroundElem.attribute( QStringLiteral( "shapeSizeX" ), QStringLiteral( "0" ) ).toDouble(),
530 backgroundElem.attribute( QStringLiteral( "shapeSizeY" ), QStringLiteral( "0" ) ).toDouble() );
531
532 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeSizeUnit" ) ) )
533 {
534 d->sizeUnits = QgsTextRendererUtils::convertFromOldLabelUnit( backgroundElem.attribute( QStringLiteral( "shapeSizeUnits" ) ).toUInt() );
535 }
536 else
537 {
538 d->sizeUnits = QgsUnitTypes::decodeRenderUnit( backgroundElem.attribute( QStringLiteral( "shapeSizeUnit" ) ) );
539 }
540
541 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeSizeMapUnitScale" ) ) )
542 {
543 //fallback to older property
544 const double oldMin = backgroundElem.attribute( QStringLiteral( "shapeSizeMapUnitMinScale" ), QStringLiteral( "0" ) ).toDouble();
545 d->sizeMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
546 const double oldMax = backgroundElem.attribute( QStringLiteral( "shapeSizeMapUnitMaxScale" ), QStringLiteral( "0" ) ).toDouble();
547 d->sizeMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
548 }
549 else
550 {
551 d->sizeMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( backgroundElem.attribute( QStringLiteral( "shapeSizeMapUnitScale" ) ) );
552 }
553 d->rotationType = static_cast< RotationType >( backgroundElem.attribute( QStringLiteral( "shapeRotationType" ), QString::number( RotationSync ) ).toUInt() );
554 d->rotation = backgroundElem.attribute( QStringLiteral( "shapeRotation" ), QStringLiteral( "0" ) ).toDouble();
555 d->offset = QPointF( backgroundElem.attribute( QStringLiteral( "shapeOffsetX" ), QStringLiteral( "0" ) ).toDouble(),
556 backgroundElem.attribute( QStringLiteral( "shapeOffsetY" ), QStringLiteral( "0" ) ).toDouble() );
557
558 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeOffsetUnit" ) ) )
559 {
560 d->offsetUnits = QgsTextRendererUtils::convertFromOldLabelUnit( backgroundElem.attribute( QStringLiteral( "shapeOffsetUnits" ) ).toUInt() );
561 }
562 else
563 {
564 d->offsetUnits = QgsUnitTypes::decodeRenderUnit( backgroundElem.attribute( QStringLiteral( "shapeOffsetUnit" ) ) );
565 }
566
567 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeOffsetMapUnitScale" ) ) )
568 {
569 //fallback to older property
570 const double oldMin = backgroundElem.attribute( QStringLiteral( "shapeOffsetMapUnitMinScale" ), QStringLiteral( "0" ) ).toDouble();
571 d->offsetMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
572 const double oldMax = backgroundElem.attribute( QStringLiteral( "shapeOffsetMapUnitMaxScale" ), QStringLiteral( "0" ) ).toDouble();
573 d->offsetMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
574 }
575 else
576 {
577 d->offsetMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( backgroundElem.attribute( QStringLiteral( "shapeOffsetMapUnitScale" ) ) );
578 }
579 d->radii = QSizeF( backgroundElem.attribute( QStringLiteral( "shapeRadiiX" ), QStringLiteral( "0" ) ).toDouble(),
580 backgroundElem.attribute( QStringLiteral( "shapeRadiiY" ), QStringLiteral( "0" ) ).toDouble() );
581
582 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeRadiiUnit" ) ) )
583 {
584 d->radiiUnits = QgsTextRendererUtils::convertFromOldLabelUnit( backgroundElem.attribute( QStringLiteral( "shapeRadiiUnits" ) ).toUInt() );
585 }
586 else
587 {
588 d->radiiUnits = QgsUnitTypes::decodeRenderUnit( backgroundElem.attribute( QStringLiteral( "shapeRadiiUnit" ) ) );
589 }
590 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeRadiiMapUnitScale" ) ) )
591 {
592 //fallback to older property
593 const double oldMin = backgroundElem.attribute( QStringLiteral( "shapeRadiiMapUnitMinScale" ), QStringLiteral( "0" ) ).toDouble();
594 d->radiiMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
595 const double oldMax = backgroundElem.attribute( QStringLiteral( "shapeRadiiMapUnitMaxScale" ), QStringLiteral( "0" ) ).toDouble();
596 d->radiiMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
597 }
598 else
599 {
600 d->radiiMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( backgroundElem.attribute( QStringLiteral( "shapeRadiiMapUnitScale" ) ) );
601 }
602 d->fillColor = QgsSymbolLayerUtils::decodeColor( backgroundElem.attribute( QStringLiteral( "shapeFillColor" ), QgsSymbolLayerUtils::encodeColor( Qt::white ) ) );
603 d->strokeColor = QgsSymbolLayerUtils::decodeColor( backgroundElem.attribute( QStringLiteral( "shapeBorderColor" ), QgsSymbolLayerUtils::encodeColor( Qt::darkGray ) ) );
604 d->strokeWidth = backgroundElem.attribute( QStringLiteral( "shapeBorderWidth" ), QStringLiteral( "0" ) ).toDouble();
605
606 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeBorderWidthUnit" ) ) )
607 {
608 d->strokeWidthUnits = QgsTextRendererUtils::convertFromOldLabelUnit( backgroundElem.attribute( QStringLiteral( "shapeBorderWidthUnits" ) ).toUInt() );
609 }
610 else
611 {
612 d->strokeWidthUnits = QgsUnitTypes::decodeRenderUnit( backgroundElem.attribute( QStringLiteral( "shapeBorderWidthUnit" ) ) );
613 }
614 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeBorderWidthMapUnitScale" ) ) )
615 {
616 //fallback to older property
617 const double oldMin = backgroundElem.attribute( QStringLiteral( "shapeBorderWidthMapUnitMinScale" ), QStringLiteral( "0" ) ).toDouble();
618 d->strokeWidthMapUnitScale.minScale = oldMin != 0 ? 1.0 / oldMin : 0;
619 const double oldMax = backgroundElem.attribute( QStringLiteral( "shapeBorderWidthMapUnitMaxScale" ), QStringLiteral( "0" ) ).toDouble();
620 d->strokeWidthMapUnitScale.maxScale = oldMax != 0 ? 1.0 / oldMax : 0;
621 }
622 else
623 {
624 d->strokeWidthMapUnitScale = QgsSymbolLayerUtils::decodeMapUnitScale( backgroundElem.attribute( QStringLiteral( "shapeBorderWidthMapUnitScale" ) ) );
625 }
626 d->joinStyle = static_cast< Qt::PenJoinStyle >( backgroundElem.attribute( QStringLiteral( "shapeJoinStyle" ), QString::number( Qt::BevelJoin ) ).toUInt() );
627
628 if ( !backgroundElem.hasAttribute( QStringLiteral( "shapeOpacity" ) ) )
629 {
630 d->opacity = ( 1 - backgroundElem.attribute( QStringLiteral( "shapeTransparency" ) ).toInt() / 100.0 ); //0 -100
631 }
632 else
633 {
634 d->opacity = ( backgroundElem.attribute( QStringLiteral( "shapeOpacity" ) ).toDouble() );
635 }
636
637 d->blendMode = QgsPainting::getCompositionMode(
638 static_cast< QgsPainting::BlendMode >( backgroundElem.attribute( QStringLiteral( "shapeBlendMode" ), QString::number( QgsPainting::BlendNormal ) ).toUInt() ) );
639
640 const QDomElement effectElem = backgroundElem.firstChildElement( QStringLiteral( "effect" ) );
641 if ( !effectElem.isNull() )
642 setPaintEffect( QgsApplication::paintEffectRegistry()->createEffect( effectElem ) );
643 else
644 setPaintEffect( nullptr );
645
646 setMarkerSymbol( nullptr );
647 setFillSymbol( nullptr );
648 const QDomNodeList symbols = backgroundElem.elementsByTagName( QStringLiteral( "symbol" ) );
649 for ( int i = 0; i < symbols.size(); ++i )
650 {
651 if ( symbols.at( i ).isElement() )
652 {
653 const QDomElement symbolElement = symbols.at( i ).toElement();
654 const QString symbolElementName = symbolElement.attribute( QStringLiteral( "name" ) );
655 if ( symbolElementName == QLatin1String( "markerSymbol" ) )
656 {
657 setMarkerSymbol( QgsSymbolLayerUtils::loadSymbol< QgsMarkerSymbol >( symbolElement, context ) );
658 }
659 else if ( symbolElementName == QLatin1String( "fillSymbol" ) )
660 {
661 setFillSymbol( QgsSymbolLayerUtils::loadSymbol< QgsFillSymbol >( symbolElement, context ) );
662 }
663 }
664 }
665
666 if ( !d->fillSymbol )
667 {
668 QgsSimpleFillSymbolLayer *fill = new QgsSimpleFillSymbolLayer( d->fillColor, Qt::SolidPattern, d->strokeColor );
669 fill->setStrokeWidth( d->strokeWidth );
670 fill->setStrokeWidthUnit( d->strokeWidthUnits );
671 fill->setStrokeWidthMapUnitScale( d->strokeWidthMapUnitScale );
672 fill->setStrokeStyle( !qgsDoubleNear( d->strokeWidth, 0.0 ) ? Qt::SolidLine : Qt::NoPen );
673 fill->setPenJoinStyle( d->joinStyle );
674
676 fillSymbol->changeSymbolLayer( 0, fill );
678 }
679}
680
681QDomElement QgsTextBackgroundSettings::writeXml( QDomDocument &doc, const QgsReadWriteContext &context ) const
682{
683 QDomElement backgroundElem = doc.createElement( QStringLiteral( "background" ) );
684 backgroundElem.setAttribute( QStringLiteral( "shapeDraw" ), d->enabled );
685 backgroundElem.setAttribute( QStringLiteral( "shapeType" ), static_cast< unsigned int >( d->type ) );
686 backgroundElem.setAttribute( QStringLiteral( "shapeSVGFile" ), QgsSymbolLayerUtils::svgSymbolPathToName( d->svgFile, context.pathResolver() ) );
687 backgroundElem.setAttribute( QStringLiteral( "shapeSizeType" ), static_cast< unsigned int >( d->sizeType ) );
688 backgroundElem.setAttribute( QStringLiteral( "shapeSizeX" ), d->size.width() );
689 backgroundElem.setAttribute( QStringLiteral( "shapeSizeY" ), d->size.height() );
690 backgroundElem.setAttribute( QStringLiteral( "shapeSizeUnit" ), QgsUnitTypes::encodeUnit( d->sizeUnits ) );
691 backgroundElem.setAttribute( QStringLiteral( "shapeSizeMapUnitScale" ), QgsSymbolLayerUtils::encodeMapUnitScale( d->sizeMapUnitScale ) );
692 backgroundElem.setAttribute( QStringLiteral( "shapeRotationType" ), static_cast< unsigned int >( d->rotationType ) );
693 backgroundElem.setAttribute( QStringLiteral( "shapeRotation" ), d->rotation );
694 backgroundElem.setAttribute( QStringLiteral( "shapeOffsetX" ), d->offset.x() );
695 backgroundElem.setAttribute( QStringLiteral( "shapeOffsetY" ), d->offset.y() );
696 backgroundElem.setAttribute( QStringLiteral( "shapeOffsetUnit" ), QgsUnitTypes::encodeUnit( d->offsetUnits ) );
697 backgroundElem.setAttribute( QStringLiteral( "shapeOffsetMapUnitScale" ), QgsSymbolLayerUtils::encodeMapUnitScale( d->offsetMapUnitScale ) );
698 backgroundElem.setAttribute( QStringLiteral( "shapeRadiiX" ), d->radii.width() );
699 backgroundElem.setAttribute( QStringLiteral( "shapeRadiiY" ), d->radii.height() );
700 backgroundElem.setAttribute( QStringLiteral( "shapeRadiiUnit" ), QgsUnitTypes::encodeUnit( d->radiiUnits ) );
701 backgroundElem.setAttribute( QStringLiteral( "shapeRadiiMapUnitScale" ), QgsSymbolLayerUtils::encodeMapUnitScale( d->radiiMapUnitScale ) );
702 backgroundElem.setAttribute( QStringLiteral( "shapeFillColor" ), QgsSymbolLayerUtils::encodeColor( d->fillColor ) );
703 backgroundElem.setAttribute( QStringLiteral( "shapeBorderColor" ), QgsSymbolLayerUtils::encodeColor( d->strokeColor ) );
704 backgroundElem.setAttribute( QStringLiteral( "shapeBorderWidth" ), d->strokeWidth );
705 backgroundElem.setAttribute( QStringLiteral( "shapeBorderWidthUnit" ), QgsUnitTypes::encodeUnit( d->strokeWidthUnits ) );
706 backgroundElem.setAttribute( QStringLiteral( "shapeBorderWidthMapUnitScale" ), QgsSymbolLayerUtils::encodeMapUnitScale( d->strokeWidthMapUnitScale ) );
707 backgroundElem.setAttribute( QStringLiteral( "shapeJoinStyle" ), static_cast< unsigned int >( d->joinStyle ) );
708 backgroundElem.setAttribute( QStringLiteral( "shapeOpacity" ), d->opacity );
709 backgroundElem.setAttribute( QStringLiteral( "shapeBlendMode" ), QgsPainting::getBlendModeEnum( d->blendMode ) );
710 if ( d->paintEffect && !QgsPaintEffectRegistry::isDefaultStack( d->paintEffect.get() ) )
711 d->paintEffect->saveProperties( doc, backgroundElem );
712
713 if ( d->markerSymbol )
714 backgroundElem.appendChild( QgsSymbolLayerUtils::saveSymbol( QStringLiteral( "markerSymbol" ), d->markerSymbol.get(), doc, context ) );
715
716 if ( d->fillSymbol )
717 backgroundElem.appendChild( QgsSymbolLayerUtils::saveSymbol( QStringLiteral( "fillSymbol" ), d->fillSymbol.get(), doc, context ) );
718
719 return backgroundElem;
720}
721
723{
724 if ( !d->fillSymbol || d->fillSymbol->symbolLayers().at( 0 )->layerType() != QLatin1String( "SimpleFill" ) )
725 return;
726 QgsSimpleFillSymbolLayer *fill = qgis::down_cast< QgsSimpleFillSymbolLayer * >( d->fillSymbol->symbolLayers().at( 0 ) );
727
729 {
732 {
735 }
736
739 {
742 }
743
746 {
749 }
750
753 {
756 }
757 }
758}
759
761{
762 if ( properties.isActive( QgsPalLayerSettings::ShapeDraw ) )
763 {
764 context.expressionContext().setOriginalValueVariable( d->enabled );
765 d->enabled = properties.valueAsBool( QgsPalLayerSettings::ShapeDraw, context.expressionContext(), d->enabled );
766 }
767
768 if ( properties.isActive( QgsPalLayerSettings::ShapeSizeX ) )
769 {
770 context.expressionContext().setOriginalValueVariable( d->size.width() );
771 d->size.setWidth( properties.valueAsDouble( QgsPalLayerSettings::ShapeSizeX, context.expressionContext(), d->size.width() ) );
772 }
773 if ( properties.isActive( QgsPalLayerSettings::ShapeSizeY ) )
774 {
775 context.expressionContext().setOriginalValueVariable( d->size.height() );
776 d->size.setHeight( properties.valueAsDouble( QgsPalLayerSettings::ShapeSizeY, context.expressionContext(), d->size.height() ) );
777 }
778
779 QVariant exprVal = properties.value( QgsPalLayerSettings::ShapeSizeUnits, context.expressionContext() );
780 if ( !QgsVariantUtils::isNull( exprVal ) )
781 {
782 const QString units = exprVal.toString();
783 if ( !units.isEmpty() )
784 {
785 bool ok;
787 if ( ok )
788 d->sizeUnits = res;
789 }
790 }
791
792 exprVal = properties.value( QgsPalLayerSettings::ShapeKind, context.expressionContext() );
793 if ( !QgsVariantUtils::isNull( exprVal ) )
794 {
795 const QString skind = exprVal.toString().trimmed();
796 if ( !skind.isEmpty() )
797 {
798 d->type = QgsTextRendererUtils::decodeShapeType( skind );
799 }
800 }
801
802 exprVal = properties.value( QgsPalLayerSettings::ShapeSizeType, context.expressionContext() );
803 if ( !QgsVariantUtils::isNull( exprVal ) )
804 {
805 const QString stype = exprVal.toString().trimmed();
806 if ( !stype.isEmpty() )
807 {
809 }
810 }
811
812 // data defined shape SVG path?
813 context.expressionContext().setOriginalValueVariable( d->svgFile );
814 exprVal = properties.value( QgsPalLayerSettings::ShapeSVGFile, context.expressionContext() );
815 if ( !QgsVariantUtils::isNull( exprVal ) )
816 {
817 const QString svgfile = exprVal.toString().trimmed();
818 d->svgFile = QgsSymbolLayerUtils::svgSymbolNameToPath( svgfile, context.pathResolver() );
819 }
820
822 {
823 context.expressionContext().setOriginalValueVariable( d->rotation );
824 d->rotation = properties.valueAsDouble( QgsPalLayerSettings::ShapeRotation, context.expressionContext(), d->rotation );
825 }
826 exprVal = properties.value( QgsPalLayerSettings::ShapeRotationType, context.expressionContext() );
827 if ( !QgsVariantUtils::isNull( exprVal ) )
828 {
829 const QString rotstr = exprVal.toString().trimmed();
830 if ( !rotstr.isEmpty() )
831 {
832 d->rotationType = QgsTextRendererUtils::decodeBackgroundRotationType( rotstr );
833 }
834 }
835
836 exprVal = properties.value( QgsPalLayerSettings::ShapeOffset, context.expressionContext() );
837 if ( !QgsVariantUtils::isNull( exprVal ) )
838 {
839 bool ok = false;
840 const QPointF res = QgsSymbolLayerUtils::toPoint( exprVal, &ok );
841 if ( ok )
842 {
843 d->offset = res;
844 }
845 }
846 exprVal = properties.value( QgsPalLayerSettings::ShapeOffsetUnits, context.expressionContext() );
847 if ( !QgsVariantUtils::isNull( exprVal ) )
848 {
849 const QString units = exprVal.toString();
850 if ( !units.isEmpty() )
851 {
852 bool ok;
854 if ( ok )
855 d->offsetUnits = res;
856 }
857 }
858
859 exprVal = properties.value( QgsPalLayerSettings::ShapeRadii, context.expressionContext() );
860 if ( !QgsVariantUtils::isNull( exprVal ) )
861 {
862 bool ok = false;
863 const QSizeF res = QgsSymbolLayerUtils::toSize( exprVal, &ok );
864 if ( ok )
865 {
866 d->radii = res;
867 }
868 }
869
870 exprVal = properties.value( QgsPalLayerSettings::ShapeRadiiUnits, context.expressionContext() );
871 if ( !QgsVariantUtils::isNull( exprVal ) )
872 {
873 const QString units = exprVal.toString();
874 if ( !units.isEmpty() )
875 {
876 bool ok;
878 if ( ok )
879 d->radiiUnits = res;
880 }
881 }
882
884 {
885 context.expressionContext().setOriginalValueVariable( d->opacity * 100 );
886 const QVariant val = properties.value( QgsPalLayerSettings::ShapeOpacity, context.expressionContext(), d->opacity * 100 );
887 if ( !QgsVariantUtils::isNull( val ) )
888 {
889 d->opacity = val.toDouble() / 100.0;
890 }
891 }
892
893 // for non-SVG background types, those data defined properties will not having an impact,
894 // instead use data defined properties within symbols
896 {
898 d->fillColor = properties.valueAsColor( QgsPalLayerSettings::ShapeFillColor, context.expressionContext(), d->fillColor );
899 }
901 {
903 d->strokeColor = properties.valueAsColor( QgsPalLayerSettings::ShapeStrokeColor, context.expressionContext(), d->strokeColor );
904 }
905
907 {
908 context.expressionContext().setOriginalValueVariable( d->strokeWidth );
909 d->strokeWidth = properties.valueAsDouble( QgsPalLayerSettings::ShapeStrokeWidth, context.expressionContext(), d->strokeWidth );
910 }
911 exprVal = properties.value( QgsPalLayerSettings::ShapeStrokeWidthUnits, context.expressionContext() );
912 if ( !QgsVariantUtils::isNull( exprVal ) )
913 {
914 const QString units = exprVal.toString();
915 if ( !units.isEmpty() )
916 {
917 bool ok;
919 if ( ok )
920 d->strokeWidthUnits = res;
921 }
922 }
923
925 {
926 exprVal = properties.value( QgsPalLayerSettings::ShapeBlendMode, context.expressionContext() );
927 const QString blendstr = exprVal.toString().trimmed();
928 if ( !blendstr.isEmpty() )
929 d->blendMode = QgsSymbolLayerUtils::decodeBlendMode( blendstr );
930 }
931
933 {
934 exprVal = properties.value( QgsPalLayerSettings::ShapeJoinStyle, context.expressionContext() );
935 const QString joinstr = exprVal.toString().trimmed();
936 if ( !joinstr.isEmpty() )
937 {
938 d->joinStyle = QgsSymbolLayerUtils::decodePenJoinStyle( joinstr );
939 }
940 }
941}
942
944{
945 QSet< QString > fields;
946 if ( d->markerSymbol )
947 {
948 fields.unite( d->markerSymbol->usedAttributes( context ) );
949 }
950 if ( d->fillSymbol )
951 {
952 fields.unite( d->fillSymbol->usedAttributes( context ) );
953 }
954 return fields;
955}
QColor valueAsColor(int key, const QgsExpressionContext &context, const QColor &defaultColor=QColor(), bool *ok=nullptr) const
Calculates the current value of the property with the specified key and interprets it as a color.
bool valueAsBool(int key, const QgsExpressionContext &context, bool defaultValue=false, bool *ok=nullptr) const
Calculates the current value of the property with the specified key and interprets it as an boolean.
double valueAsDouble(int key, const QgsExpressionContext &context, double defaultValue=0.0, bool *ok=nullptr) const
Calculates the current value of the property with the specified key and interprets it as a double.
static QgsPaintEffectRegistry * paintEffectRegistry()
Returns the application's paint effect registry, used for managing paint effects.
void setOriginalValueVariable(const QVariant &value)
Sets the original value variable value for the context.
A fill symbol type, for rendering Polygon and MultiPolygon geometries.
Definition: qgsfillsymbol.h:30
Q_INVOKABLE QVariant customProperty(const QString &value, const QVariant &defaultValue=QVariant()) const
Read a custom property from layer.
Struct for storing maximum and minimum scales for measurements in map units.
A marker symbol type, for rendering Point and MultiPoint geometries.
static bool isDefaultStack(QgsPaintEffect *effect)
Tests whether a paint effect matches the default effects stack.
Base class for visual effects which can be applied to QPicture drawings.
virtual QVariantMap properties() const =0
Returns the properties describing the paint effect encoded in a string format.
static QgsPainting::BlendMode getBlendModeEnum(QPainter::CompositionMode blendMode)
Returns a BlendMode corresponding to a QPainter::CompositionMode.
Definition: qgspainting.cpp:80
static QPainter::CompositionMode getCompositionMode(QgsPainting::BlendMode blendMode)
Returns a QPainter::CompositionMode corresponding to a BlendMode.
Definition: qgspainting.cpp:20
BlendMode
Blending modes enum defining the available composition modes that can be used when rendering a layer.
Definition: qgspainting.h:37
@ ShapeOpacity
Shape opacity.
A grouped map of multiple QgsProperty objects, each referenced by a integer key value.
bool hasProperty(int key) const override
Returns true if the collection contains a property with the specified key.
QgsProperty property(int key) const override
Returns a matching property from the collection, if one exists.
QVariant value(int key, const QgsExpressionContext &context, const QVariant &defaultValue=QVariant()) const override
Returns the calculated value of the property with the specified key from within the collection.
void setProperty(int key, const QgsProperty &property)
Adds a property to the collection and takes ownership of it.
bool isActive(int key) const override
Returns true if the collection contains an active property with the specified key.
A store for object properties.
Definition: qgsproperty.h:230
The class is used as a container of context for various read/write operations on other objects.
const QgsPathResolver & pathResolver() const
Returns path resolver for conversion between relative and absolute paths.
Contains information about the context of a rendering operation.
QgsExpressionContext & expressionContext()
Gets the expression context.
const QgsPathResolver & pathResolver() const
Returns the path resolver for conversion between relative and absolute paths during rendering operati...
void setStrokeWidthMapUnitScale(const QgsMapUnitScale &scale)
void setPenJoinStyle(Qt::PenJoinStyle style)
void setStrokeWidth(double strokeWidth)
void setStrokeStyle(Qt::PenStyle strokeStyle)
void setStrokeWidthUnit(QgsUnitTypes::RenderUnit unit)
Sets the units for the width of the fill's stroke.
static Qt::PenJoinStyle decodePenJoinStyle(const QString &str)
static QString encodeMapUnitScale(const QgsMapUnitScale &mapUnitScale)
static QColor decodeColor(const QString &str)
static QString svgSymbolPathToName(const QString &path, const QgsPathResolver &pathResolver)
Determines an SVG symbol's name from its path.
static QPointF toPoint(const QVariant &value, bool *ok=nullptr)
Converts a value to a point.
static QgsMapUnitScale decodeMapUnitScale(const QString &str)
static QSizeF toSize(const QVariant &value, bool *ok=nullptr)
Converts a value to a size.
static QPainter::CompositionMode decodeBlendMode(const QString &s)
static QString svgSymbolNameToPath(const QString &name, const QgsPathResolver &pathResolver)
Determines an SVG symbol's path from its name.
static QString encodeColor(const QColor &color)
static QDomElement saveSymbol(const QString &symbolName, const QgsSymbol *symbol, QDomDocument &doc, const QgsReadWriteContext &context)
Writes a symbol definition to XML.
static QString symbolProperties(QgsSymbol *symbol)
Returns a string representing the symbol.
@ PropertyJoinStyle
Line join style.
@ PropertyStrokeWidth
Stroke width.
@ PropertyFillColor
Fill color.
@ PropertyStrokeColor
Stroke color.
QgsPropertyCollection & dataDefinedProperties()
Returns a reference to the symbol layer's property collection, used for data defined overrides.
bool changeSymbolLayer(int index, QgsSymbolLayer *layer)
Deletes the current layer at the specified index and replaces it with layer.
Definition: qgssymbol.cpp:809
Container for settings relating to a text background object.
QgsMapUnitScale strokeWidthMapUnitScale() const
Returns the map unit scale object for the shape stroke width.
void setFillSymbol(QgsFillSymbol *symbol)
Sets the current fill symbol for the background shape.
RotationType rotationType() const
Returns the method used for rotating the background shape.
QString svgFile() const
Returns the absolute path to the background SVG file, if set.
QSizeF size() const
Returns the size of the background shape.
QSizeF radii() const
Returns the radii used for rounding the corners of shapes.
QSet< QString > referencedFields(const QgsRenderContext &context) const
Returns all field names referenced by the configuration (e.g.
QgsMapUnitScale radiiMapUnitScale() const
Returns the map unit scale object for the shape radii.
void upgradeDataDefinedProperties(QgsPropertyCollection &properties)
Upgrade data defined properties when reading a project file saved in QGIS prior to version 3....
void setOpacity(double opacity)
Sets the background shape's opacity.
void setStrokeColor(const QColor &color)
Sets the color used for outlining the background shape.
QgsUnitTypes::RenderUnit strokeWidthUnit() const
Returns the units used for the shape's stroke width.
void setSizeMapUnitScale(const QgsMapUnitScale &scale)
Sets the map unit scale object for the shape size.
QPainter::CompositionMode blendMode() const
Returns the blending mode used for drawing the background shape.
Qt::PenJoinStyle joinStyle() const
Returns the join style used for drawing the background shape.
SizeType
Methods for determining the background shape size.
@ SizeBuffer
Shape size is determined by adding a buffer margin around text.
bool enabled() const
Returns whether the background is enabled.
void readXml(const QDomElement &elem, const QgsReadWriteContext &context)
Read settings from a DOM element.
void setJoinStyle(Qt::PenJoinStyle style)
Sets the join style used for drawing the background shape.
void setRadiiUnit(QgsUnitTypes::RenderUnit units)
Sets the units used for the shape's radii.
double opacity() const
Returns the background shape's opacity.
bool operator!=(const QgsTextBackgroundSettings &other) const
void updateDataDefinedProperties(QgsRenderContext &context, const QgsPropertyCollection &properties)
Updates the format by evaluating current values of data defined properties.
void setStrokeWidthMapUnitScale(const QgsMapUnitScale &scale)
Sets the map unit scale object for the shape stroke width.
QgsUnitTypes::RenderUnit offsetUnit() const
Returns the units used for the shape's offset.
double rotation() const
Returns the rotation for the background shape, in degrees clockwise.
QColor fillColor() const
Returns the color used for filing the background shape.
void setMarkerSymbol(QgsMarkerSymbol *symbol)
Sets the current marker symbol for the background shape.
void setRadii(QSizeF radii)
Sets the radii used for rounding the corners of shapes.
SizeType sizeType() const
Returns the method used to determine the size of the background shape (e.g., fixed size or buffer aro...
QgsTextBackgroundSettings & operator=(const QgsTextBackgroundSettings &other)
ShapeType type() const
Returns the type of background shape (e.g., square, ellipse, SVG).
double strokeWidth() const
Returns the width of the shape's stroke (stroke).
void setSizeType(SizeType type)
Sets the method used to determine the size of the background shape (e.g., fixed size or buffer around...
ShapeType
Background shape types.
void setFillColor(const QColor &color)
Sets the color used for filing the background shape.
void setPaintEffect(QgsPaintEffect *effect)
Sets the current paint effect for the background shape.
void setStrokeWidthUnit(QgsUnitTypes::RenderUnit units)
Sets the units used for the shape's stroke width.
QColor strokeColor() const
Returns the color used for outlining the background shape.
QDomElement writeXml(QDomDocument &doc, const QgsReadWriteContext &context) const
Write settings into a DOM element.
void setRotationType(RotationType type)
Sets the method used for rotating the background shape.
void setOffsetMapUnitScale(const QgsMapUnitScale &scale)
Sets the map unit scale object for the shape offset.
QgsFillSymbol * fillSymbol() const
Returns the fill symbol to be rendered in the background.
void setBlendMode(QPainter::CompositionMode mode)
Sets the blending mode used for drawing the background shape.
void readFromLayer(QgsVectorLayer *layer)
Reads settings from a layer's custom properties (for QGIS 2.x projects).
QgsMapUnitScale sizeMapUnitScale() const
Returns the map unit scale object for the shape size.
void setType(ShapeType type)
Sets the type of background shape to draw (e.g., square, ellipse, SVG).
QgsUnitTypes::RenderUnit sizeUnit() const
Returns the units used for the shape's size.
RotationType
Methods for determining the rotation of the background shape.
@ RotationSync
Shape rotation is synced with text rotation.
bool operator==(const QgsTextBackgroundSettings &other) const
QgsUnitTypes::RenderUnit radiiUnit() const
Returns the units used for the shape's radii.
void setEnabled(bool enabled)
Sets whether the text background will be drawn.
QgsMarkerSymbol * markerSymbol() const
Returns the marker symbol to be rendered in the background.
void setRadiiMapUnitScale(const QgsMapUnitScale &scale)
Sets the map unit scale object for the shape radii.
void setRotation(double rotation)
Sets the rotation for the background shape, in degrees clockwise.
void setOffset(QPointF offset)
Sets the offset used for drawing the background shape.
void setSize(QSizeF size)
Sets the size of the background shape.
void setSizeUnit(QgsUnitTypes::RenderUnit unit)
Sets the units used for the shape's size.
const QgsPaintEffect * paintEffect() const
Returns the current paint effect for the background shape.
void setSvgFile(const QString &file)
Sets the path to the background SVG file.
QgsMapUnitScale offsetMapUnitScale() const
Returns the map unit scale object for the shape offset.
void setStrokeWidth(double width)
Sets the width of the shape's stroke (stroke).
QPointF offset() const
Returns the offset used for drawing the background shape.
void setOffsetUnit(QgsUnitTypes::RenderUnit units)
Sets the units used for the shape's offset.
static QgsTextBackgroundSettings::ShapeType decodeShapeType(const QString &string)
Decodes a string representation of a background shape type to a type.
static QColor readColor(QgsVectorLayer *layer, const QString &property, const QColor &defaultColor=Qt::black, bool withAlpha=true)
Converts an encoded color value from a layer property.
static QgsTextBackgroundSettings::RotationType decodeBackgroundRotationType(const QString &string)
Decodes a string representation of a background rotation type to a type.
static QgsTextBackgroundSettings::SizeType decodeBackgroundSizeType(const QString &string)
Decodes a string representation of a background size type to a type.
static QgsUnitTypes::RenderUnit convertFromOldLabelUnit(int val)
Converts a unit from an old (pre 3.0) label unit.
static Q_INVOKABLE QString encodeUnit(QgsUnitTypes::DistanceUnit unit)
Encodes a distance unit to a string.
static Q_INVOKABLE QgsUnitTypes::RenderUnit decodeRenderUnit(const QString &string, bool *ok=nullptr)
Decodes a render unit from a string.
RenderUnit
Rendering size units.
Definition: qgsunittypes.h:168
static bool isNull(const QVariant &variant)
Returns true if the specified variant should be considered a NULL value.
Represents a vector layer which manages a vector based data sets.
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference)
Definition: qgis.h:2527