33 #include <QDomDocument> 34 #include <QDomElement> 41 , mMaximumScale( scaleMinDenom )
42 , mMinimumScale( scaleMaxDenom )
43 , mFilterExp( filterExp )
45 , mDescription( description )
46 , mElseRule( elseRule )
49 mFilterExp = QStringLiteral(
"ELSE" );
51 mRuleKey = QUuid::createUuid().toString();
57 qDeleteAll( mChildren );
63 if ( mFilterExp.trimmed().compare( QLatin1String(
"ELSE" ), Qt::CaseInsensitive ) == 0 )
68 else if ( mFilterExp.trimmed().isEmpty() )
76 mFilter = qgis::make_unique< QgsExpression >( mFilterExp );
82 mChildren.append( rule );
89 mChildren.insert( i, rule );
96 mChildren.removeAll( rule );
103 delete mChildren.takeAt( i );
109 mChildren.removeAll( rule );
110 rule->mParent =
nullptr;
117 Rule *rule = mChildren.takeAt( i );
118 rule->mParent =
nullptr;
127 if ( key == mRuleKey )
130 Q_FOREACH (
Rule *rule, mChildren )
139 void QgsRuleBasedRenderer::Rule::updateElseRules()
142 Q_FOREACH (
Rule *rule, mChildren )
151 mFilterExp = QStringLiteral(
"ELSE" );
160 off.fill( QChar(
' ' ), indent );
161 QString symbolDump = ( mSymbol ? mSymbol->dump() : QStringLiteral(
"[]" ) );
162 QString msg = off + QStringLiteral(
"RULE %1 - scale [%2,%3] - filter %4 - symbol %5\n" )
163 .arg( mLabel ).arg( mMaximumScale ).arg( mMinimumScale )
164 .arg( mFilterExp, symbolDump );
167 Q_FOREACH (
Rule *rule, mChildren )
169 lst.append( rule->
dump( indent + 2 ) );
171 msg += lst.join( QStringLiteral(
"\n" ) );
180 attrs.unite( mFilter->referencedColumns() );
182 attrs.unite( mSymbol->usedAttributes( context ) );
185 Q_FOREACH (
Rule *rule, mChildren )
194 if ( mFilter && mFilter->needsGeometry() )
197 Q_FOREACH (
Rule *rule, mChildren )
210 lst.append( mSymbol.get() );
212 Q_FOREACH (
Rule *rule, mChildren )
214 lst += rule->
symbols( context );
221 mSymbol.reset( sym );
226 mFilterExp = filterExp;
233 if ( currentLevel != -1 )
235 lst <<
QgsLegendSymbolItem( mSymbol.get(), mLabel, mRuleKey,
true, mMaximumScale, mMinimumScale, currentLevel, mParent ? mParent->mRuleKey : QString() );
238 for ( RuleList::const_iterator it = mChildren.constBegin(); it != mChildren.constEnd(); ++it )
249 if ( ! mFilter || mElseRule )
263 if ( !
qgsDoubleNear( mMaximumScale, 0.0 ) && mMaximumScale > scale )
265 if ( !
qgsDoubleNear( mMinimumScale, 0.0 ) && mMinimumScale < scale )
272 QgsSymbol *sym = mSymbol ? mSymbol->clone() :
nullptr;
273 Rule *newrule =
new Rule( sym, mMaximumScale, mMinimumScale, mFilterExp, mLabel, mDescription );
276 Q_FOREACH (
Rule *rule, mChildren )
283 QDomElement ruleElem = doc.createElement( QStringLiteral(
"rule" ) );
287 int symbolIndex = symbolMap.size();
288 symbolMap[QString::number( symbolIndex )] = mSymbol.get();
289 ruleElem.setAttribute( QStringLiteral(
"symbol" ), symbolIndex );
291 if ( !mFilterExp.isEmpty() )
292 ruleElem.setAttribute( QStringLiteral(
"filter" ), mFilterExp );
293 if ( mMaximumScale != 0 )
294 ruleElem.setAttribute( QStringLiteral(
"scalemindenom" ), mMaximumScale );
295 if ( mMinimumScale != 0 )
296 ruleElem.setAttribute( QStringLiteral(
"scalemaxdenom" ), mMinimumScale );
297 if ( !mLabel.isEmpty() )
298 ruleElem.setAttribute( QStringLiteral(
"label" ), mLabel );
299 if ( !mDescription.isEmpty() )
300 ruleElem.setAttribute( QStringLiteral(
"description" ), mDescription );
302 ruleElem.setAttribute( QStringLiteral(
"checkstate" ), 0 );
303 ruleElem.setAttribute( QStringLiteral(
"key" ), mRuleKey );
305 Q_FOREACH (
Rule *rule, mChildren )
307 ruleElem.appendChild( rule->
save( doc, symbolMap ) );
316 if (
symbols( context ).isEmpty() )
319 if ( !mFilterExp.isEmpty() )
321 if ( !props.value( QStringLiteral(
"filter" ), QLatin1String(
"" ) ).isEmpty() )
322 props[ QStringLiteral(
"filter" )] += QLatin1String(
" AND " );
323 props[ QStringLiteral(
"filter" )] += mFilterExp;
330 QDomElement ruleElem = doc.createElement( QStringLiteral(
"se:Rule" ) );
331 element.appendChild( ruleElem );
335 QDomElement nameElem = doc.createElement( QStringLiteral(
"se:Name" ) );
336 nameElem.appendChild( doc.createTextNode( mLabel ) );
337 ruleElem.appendChild( nameElem );
339 if ( !mLabel.isEmpty() || !mDescription.isEmpty() )
341 QDomElement descrElem = doc.createElement( QStringLiteral(
"se:Description" ) );
342 if ( !mLabel.isEmpty() )
344 QDomElement titleElem = doc.createElement( QStringLiteral(
"se:Title" ) );
345 titleElem.appendChild( doc.createTextNode( mLabel ) );
346 descrElem.appendChild( titleElem );
348 if ( !mDescription.isEmpty() )
350 QDomElement abstractElem = doc.createElement( QStringLiteral(
"se:Abstract" ) );
351 abstractElem.appendChild( doc.createTextNode( mDescription ) );
352 descrElem.appendChild( abstractElem );
354 ruleElem.appendChild( descrElem );
357 if ( !props.value( QStringLiteral(
"filter" ), QLatin1String(
"" ) ).isEmpty() )
364 mSymbol->toSld( doc, ruleElem, props );
368 Q_FOREACH (
Rule *rule, mChildren )
370 rule->
toSld( doc, element, props );
376 mActiveChildren.clear();
389 mSymbol->startRender( context, fields );
393 QStringList subfilters;
394 Q_FOREACH (
Rule *rule, mChildren )
397 if ( rule->
startRender( context, fields, subfilter ) )
400 mActiveChildren.append( rule );
401 subfilters.append( subfilter );
409 if ( subfilters.length() > 1 || !subfilters.value( 0 ).isEmpty() )
411 if ( subfilters.contains( QStringLiteral(
"TRUE" ) ) )
412 sf = QStringLiteral(
"TRUE" );
414 sf = subfilters.join( QStringLiteral(
") OR (" ) ).prepend(
'(' ).append(
')' );
424 if ( mSymbol || sf.isEmpty() )
425 filter = QStringLiteral(
"TRUE" );
431 else if ( !mFilterExp.trimmed().isEmpty() && !sf.isEmpty() )
432 filter = QStringLiteral(
"(%1) AND (%2)" ).arg( mFilterExp, sf );
433 else if ( !mFilterExp.trimmed().isEmpty() )
435 else if ( sf.isEmpty() )
436 filter = QStringLiteral(
"TRUE" );
440 filter = filter.trimmed();
447 QSet<int> symbolZLevelsSet;
453 for (
int i = 0; i < mSymbol->symbolLayerCount(); i++ )
455 symbolZLevelsSet.insert( mSymbol->symbolLayer( i )->renderingPass() );
460 QList<Rule *>::iterator it;
461 for ( it = mActiveChildren.begin(); it != mActiveChildren.end(); ++it )
466 return symbolZLevelsSet;
473 for (
int i = 0; i < mSymbol->symbolLayerCount(); i++ )
475 int normLevel = zLevelsToNormLevels.value( mSymbol->symbolLayer( i )->renderingPass() );
476 mSymbolNormZLevels.insert( normLevel );
481 Q_FOREACH (
Rule *rule, mActiveChildren )
493 bool rendered =
false;
496 if ( mSymbol && mIsActive )
499 Q_FOREACH (
int normZLevel, mSymbolNormZLevels )
502 renderQueue[normZLevel].jobs.append(
new RenderJob( featToRender, mSymbol.get() ) );
507 bool willrendersomething =
false;
510 Q_FOREACH (
Rule *rule, mChildren )
523 if ( !willrendersomething )
525 Q_FOREACH (
Rule *rule, mElseRules )
530 if ( !mIsActive || ( mSymbol && !rendered ) )
546 Q_FOREACH (
Rule *rule, mActiveChildren )
553 lst.removeOne( rule );
579 lst.append( mSymbol.get() );
581 Q_FOREACH (
Rule *rule, mActiveChildren )
593 lst.insert( mRuleKey );
595 Q_FOREACH (
Rule *rule, mActiveChildren )
597 bool validKey =
false;
601 lst.removeOne( rule );
632 listChildren = mActiveChildren;
634 Q_FOREACH (
Rule *rule, listChildren )
644 mSymbol->stopRender( context );
646 Q_FOREACH (
Rule *rule, mActiveChildren )
651 mActiveChildren.clear();
652 mSymbolNormZLevels.clear();
657 QString symbolIdx = ruleElem.attribute( QStringLiteral(
"symbol" ) );
659 if ( !symbolIdx.isEmpty() )
661 if ( symbolMap.contains( symbolIdx ) )
663 symbol = symbolMap.take( symbolIdx );
667 QgsDebugMsg(
"symbol for rule " + symbolIdx +
" not found!" );
671 QString filterExp = ruleElem.attribute( QStringLiteral(
"filter" ) );
672 QString
label = ruleElem.attribute( QStringLiteral(
"label" ) );
673 QString
description = ruleElem.attribute( QStringLiteral(
"description" ) );
674 int scaleMinDenom = ruleElem.attribute( QStringLiteral(
"scalemindenom" ), QStringLiteral(
"0" ) ).toInt();
675 int scaleMaxDenom = ruleElem.attribute( QStringLiteral(
"scalemaxdenom" ), QStringLiteral(
"0" ) ).toInt();
676 QString
ruleKey = ruleElem.attribute( QStringLiteral(
"key" ) );
677 Rule *rule =
new Rule( symbol, scaleMinDenom, scaleMaxDenom, filterExp, label, description );
679 if ( !ruleKey.isEmpty() )
680 rule->mRuleKey = ruleKey;
682 rule->
setActive( ruleElem.attribute( QStringLiteral(
"checkstate" ), QStringLiteral(
"1" ) ).toInt() );
684 QDomElement childRuleElem = ruleElem.firstChildElement( QStringLiteral(
"rule" ) );
685 while ( !childRuleElem.isNull() )
687 Rule *childRule =
create( childRuleElem, symbolMap );
696 childRuleElem = childRuleElem.nextSiblingElement( QStringLiteral(
"rule" ) );
708 l +=
c->descendants();
715 if ( ruleElem.localName() != QLatin1String(
"Rule" ) )
717 QgsDebugMsg( QString(
"invalid element: Rule element expected, %1 found!" ).arg( ruleElem.tagName() ) );
722 int scaleMinDenom = 0, scaleMaxDenom = 0;
726 QDomElement childElem = ruleElem.firstChildElement();
727 while ( !childElem.isNull() )
729 if ( childElem.localName() == QLatin1String(
"Name" ) )
733 if ( label.isEmpty() )
734 label = childElem.firstChild().nodeValue();
736 else if ( childElem.localName() == QLatin1String(
"Description" ) )
739 QDomElement titleElem = childElem.firstChildElement( QStringLiteral(
"Title" ) );
740 if ( !titleElem.isNull() )
742 label = titleElem.firstChild().nodeValue();
745 QDomElement abstractElem = childElem.firstChildElement( QStringLiteral(
"Abstract" ) );
746 if ( !abstractElem.isNull() )
748 description = abstractElem.firstChild().nodeValue();
751 else if ( childElem.localName() == QLatin1String(
"Abstract" ) )
754 description = childElem.firstChild().nodeValue();
756 else if ( childElem.localName() == QLatin1String(
"Title" ) )
759 label = childElem.firstChild().nodeValue();
761 else if ( childElem.localName() == QLatin1String(
"Filter" ) )
777 else if ( childElem.localName() == QLatin1String(
"MinScaleDenominator" ) )
780 int v = childElem.firstChild().nodeValue().toInt( &ok );
784 else if ( childElem.localName() == QLatin1String(
"MaxScaleDenominator" ) )
787 int v = childElem.firstChild().nodeValue().toInt( &ok );
791 else if ( childElem.localName().endsWith( QLatin1String(
"Symbolizer" ) ) )
797 childElem = childElem.nextSiblingElement();
802 if ( !layers.isEmpty() )
819 QgsDebugMsg( QString(
"invalid geometry type: found %1" ).arg( geomType ) );
825 return new Rule( symbol, scaleMinDenom, scaleMaxDenom, filterExp, label, description );
860 bool drawVertexMarker )
880 QList<int> symbolZLevels = symbolZLevelsSet.toList();
881 std::sort( symbolZLevels.begin(), symbolZLevels.end() );
885 QMap<int, int> zLevelsToNormLevels;
886 int maxNormLevel = -1;
887 Q_FOREACH (
int zLevel, symbolZLevels )
889 zLevelsToNormLevels[zLevel] = ++maxNormLevel;
891 QgsDebugMsgLevel( QString(
"zLevel %1 -> %2" ).arg( zLevel ).arg( maxNormLevel ), 4 );
917 for (
int i = 0; i < count; i++ )
965 Q_ASSERT( origDescendants.count() == clonedDescendants.count() );
966 for (
int i = 0; i < origDescendants.count(); ++i )
967 clonedDescendants[i]->setRuleKey( origDescendants[i]->ruleKey() );
990 rendererElem.setAttribute( QStringLiteral(
"type" ), QStringLiteral(
"RuleRenderer" ) );
991 rendererElem.setAttribute( QStringLiteral(
"symbollevels" ), (
mUsingSymbolLevels ? QStringLiteral(
"1" ) : QStringLiteral(
"0" ) ) );
992 rendererElem.setAttribute( QStringLiteral(
"forceraster" ), (
mForceRaster ? QStringLiteral(
"1" ) : QStringLiteral(
"0" ) ) );
997 rulesElem.setTagName( QStringLiteral(
"rules" ) );
998 rendererElem.appendChild( rulesElem );
1001 rendererElem.appendChild( symbolsElem );
1008 QDomElement
orderBy = doc.createElement( QStringLiteral(
"orderby" ) );
1010 rendererElem.appendChild( orderBy );
1012 rendererElem.setAttribute( QStringLiteral(
"enableorderby" ), (
mOrderByEnabled ? QStringLiteral(
"1" ) : QStringLiteral(
"0" ) ) );
1014 return rendererElem;
1025 return rule ? rule->
active() :
true;
1053 QDomElement symbolsElem = element.firstChildElement( QStringLiteral(
"symbols" ) );
1054 if ( symbolsElem.isNull() )
1059 QDomElement rulesElem = element.firstChildElement( QStringLiteral(
"rules" ) );
1076 Rule *root =
nullptr;
1078 QDomElement ruleElem = element.firstChildElement( QStringLiteral(
"Rule" ) );
1079 while ( !ruleElem.isNull() )
1086 root =
new Rule(
nullptr );
1091 ruleElem = ruleElem.nextSiblingElement( QStringLiteral(
"Rule" ) );
1123 if ( cat.
value().type() == QVariant::Int )
1124 value = cat.
value().toString();
1125 else if ( cat.
value().type() == QVariant::Double )
1128 value = QString::number( cat.
value().toDouble(),
'f', 4 );
1131 QString
filter = QStringLiteral(
"%1 = %2" ).arg( attr, value );
1148 else if ( !testExpr.
isField() )
1151 attr = QStringLiteral(
"(%1)" ).arg( attr );
1154 bool firstRange =
true;
1159 QString
filter = QStringLiteral(
"%1 %2 %3 AND %1 <= %4" ).arg( attr, firstRange ? QStringLiteral(
">=" ) : QStringLiteral(
">" ),
1161 QString::number( rng.
upperValue(),
'f', 4 ) );
1170 std::sort( scales.begin(), scales.end() );
1174 Q_FOREACH (
int scale, scales )
1178 if ( maxDenom != 0 && maxDenom <= scale )
1180 initialRule->
appendChild(
new Rule( symbol->
clone(), oldScale, scale, QString(), QStringLiteral(
"%1 - %2" ).arg( oldScale ).arg( scale ) ) );
1184 initialRule->
appendChild(
new Rule( symbol->
clone(), oldScale, maxDenom, QString(), QStringLiteral(
"%1 - %2" ).arg( oldScale ).arg( maxDenom ) ) );
1189 QString msg( QStringLiteral(
"Rule-based renderer:\n" ) );
1217 if ( renderer->
type() == QLatin1String(
"RuleRenderer" ) )
1221 else if ( renderer->
type() == QLatin1String(
"singleSymbol" ) )
1224 if ( !singleSymbolRenderer )
1230 else if ( renderer->
type() == QLatin1String(
"categorizedSymbol" ) )
1233 if ( !categorizedRenderer )
1251 for (
int i = 0; i < categorizedRenderer->
categories().size(); ++i )
1253 category = categorizedRenderer->
categories().value( i );
1260 if ( QVariant( category.
value() ).convert( QVariant::Double ) )
1262 value = category.
value().toString();
1270 if ( value == QLatin1String(
"''" ) )
1272 expression = QStringLiteral(
"ELSE" );
1276 expression = QStringLiteral(
"%1 = %2" ).arg( attr, value );
1292 else if ( renderer->
type() == QLatin1String(
"graduatedSymbol" ) )
1295 if ( !graduatedRenderer )
1307 else if ( !testExpr.
isField() )
1310 attr = QStringLiteral(
"(%1)" ).arg( attr );
1317 for (
int i = 0; i < graduatedRenderer->
ranges().size(); ++i )
1319 range = graduatedRenderer->
ranges().value( i );
1324 expression = attr +
" >= " + QString::number( range.
lowerValue(),
'f' ) +
" AND " + \
1325 attr +
" <= " + QString::number( range.
upperValue(),
'f' );
1329 expression = attr +
" > " + QString::number( range.
lowerValue(),
'f' ) +
" AND " + \
1330 attr +
" <= " + QString::number( range.
upperValue(),
'f' );
1346 else if ( renderer->
type() == QLatin1String(
"pointDisplacement" ) || renderer->
type() == QLatin1String(
"pointCluster" ) )
1349 if ( pointDistanceRenderer )
1352 else if ( renderer->
type() == QLatin1String(
"invertedPolygonRenderer" ) )
1355 if ( invertedPolygonRenderer )
1370 QString sizeExpression;
1371 switch ( symbol->
type() )
1377 if ( ! sizeScaleField.isEmpty() )
1379 sizeExpression = QStringLiteral(
"%1*(%2)" ).arg( msl->
size() ).arg( sizeScaleField );
1382 if ( ! rotationField.isEmpty() )
1389 if ( ! sizeScaleField.isEmpty() )
1396 sizeExpression = QStringLiteral(
"%1*(%2)" ).arg( lsl->
width() ).arg( sizeScaleField );
1405 sizeExpression = QStringLiteral(
"%1*(%2)" ).arg( msl->
size() ).arg( sizeScaleField );
QgsRuleBasedRenderer(QgsRuleBasedRenderer::Rule *root)
Constructs the renderer from given tree of rules (takes ownership)
An abstract base class for distance based point renderers (e.g., clusterer and displacement renderers...
Class for parsing and evaluation of expressions (formerly called "search strings").
bool hasParserError() const
Returns true if an error occurred when parsing the input expression.
The class is used as a container of context for various read/write operations on other objects...
QSet< QString > usedAttributes(const QgsRenderContext &context) const
Returns the attributes used to evaluate the expression of this rule.
double rendererScale() const
Returns the renderer map scale.
QDomElement save(QDomDocument &doc, QgsSymbolMap &symbolMap) const
QgsSymbolList originalSymbolsForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Equivalent of originalSymbolsForFeature() call extended to support renderers that may use more symbol...
QList< QgsLegendSymbolItem > QgsLegendSymbolList
bool filterNeedsGeometry() const override
Returns true if this renderer requires the geometry to apply the filter.
QgsFeatureRequest::OrderBy mOrderBy
static QString quotedColumnRef(QString name)
Returns a quoted column reference (in double quotes)
QgsRuleBasedRenderer::RuleList descendants() const
Returns all children, grand-children, grand-grand-children, grand-gra...
static bool createFunctionElement(QDomDocument &doc, QDomElement &element, const QString &function)
QgsRuleBasedRenderer::Rule * takeChild(QgsRuleBasedRenderer::Rule *rule)
take child rule out, set parent as null
virtual QgsSymbol * subSymbol()
Returns the symbol's sub symbol, if present.
QSet< QString > usedAttributes(const QgsRenderContext &context) const override
Returns a list of attributes required by this renderer.
QList< QgsRuleBasedRenderer::RenderLevel > RenderQueue
Rendering queue: a list of rendering levels.
static void applyScaleDependency(QDomDocument &doc, QDomElement &ruleElem, QgsStringMap &props)
Checks if the properties contain scaleMinDenom and scaleMaxDenom, if available, they are added into t...
const QgsRuleBasedRenderer::RuleList & children()
Returns all children rules of this rule.
bool renderFeature(const QgsFeature &feature, QgsRenderContext &context, int layer=-1, bool selected=false, bool drawVertexMarker=false) override
Render a feature using this renderer in the given context.
void setFeature(const QgsFeature &feature)
Convenience function for setting a feature for the context.
static void convertToDataDefinedSymbology(QgsSymbol *symbol, const QString &sizeScaleField, const QString &rotationField=QString())
helper function to convert the size scale and rotation fields present in some other renderers to data...
This class keeps data about a rules for rule-based renderer.
QString ruleKey() const
Unique rule identifier (for identification of rule within renderer)
QgsSymbol * symbol() const
QDomElement save(QDomDocument &doc, const QgsReadWriteContext &context) override
store renderer info to XML element
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference)
void setRuleKey(const QString &key)
Override the assigned rule key (should be used just internally by rule-based renderer) ...
QgsFeatureRequest::OrderBy orderBy() const
Gets the order in which features shall be processed by this renderer.
QString classAttribute() const
void toSld(QDomDocument &doc, QDomElement &element, QgsStringMap props) const
static bool isDefaultStack(QgsPaintEffect *effect)
Tests whether a paint effect matches the default effects stack.
static QgsProperty fromField(const QString &fieldName, bool isActive=true)
Returns a new FieldBasedProperty created from the specified field name.
QgsLegendSymbolList legendSymbolItems() const override
Returns a list of symbology items for the legend.
static void mergeScaleDependencies(int mScaleMinDenom, int mScaleMaxDenom, QgsStringMap &props)
Merges the local scale limits, if any, with the ones already in the map, if any.
QString classAttribute() const
static QgsProperty fromExpression(const QString &expression, bool isActive=true)
Returns a new ExpressionBasedProperty created from the specified expression.
QSet< QString > legendKeysForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Returns legend keys matching a specified feature.
QgsRuleBasedRenderer::FeatureToRender & ftr
Feature to render.
Container of fields for a vector layer.
#define RENDERER_TAG_NAME
void setUsingSymbolLevels(bool usingSymbolLevels)
void checkLegendSymbolItem(const QString &key, bool state=true) override
item in symbology was checked
QSet< int > collectZLevels()
Gets all used z-levels from this rule and children.
Rule * mRootRule
the root node with hierarchical list of rules
int symbolLayerCount() const
Returns total number of symbol layers contained in the symbol.
QList< FeatureToRender > mCurrentFeatures
static void clearSymbolMap(QgsSymbolMap &symbols)
double maximumScale() const
Returns the maximum map scale (i.e.
bool willRenderFeature(const QgsFeature &feature, QgsRenderContext *context=nullptr)
only tell whether a feature will be rendered without actually rendering it
QgsPaintEffect * mPaintEffect
The feature class encapsulates a single feature including its id, geometry and a list of field/values...
void setNormZLevels(const QMap< int, int > &zLevelsToNormLevels)
assign normalized z-levels [0..N-1] for this rule's symbol for quick access during rendering ...
QString description() const
A human readable description for this rule.
QString parserErrorString() const
Returns parser error.
QMap< QString, QString > QgsStringMap
virtual double width() const
bool isElse() const
Check if this rule is an ELSE rule.
bool startRender(QgsRenderContext &context, const QgsFields &fields, QString &filter)
prepare the rule for rendering and its children (build active children array)
void stopRender(QgsRenderContext &context) override
Must be called when a render cycle has finished, to allow the renderer to clean up.
bool active() const
Returns if this rule is active.
QList< QgsRuleBasedRenderer::Rule * > RuleList
QString dump(int indent=0) const
Dump for debug purpose.
As part of the API refactoring and improvements which landed in the Processing API was substantially reworked from the x version This was done in order to allow much of the underlying Processing framework to be ported into c
double lowerValue() const
int renderingPass() const
RenderResult
The result of rendering a rule.
QList< QgsSymbol * > QgsSymbolList
bool legendSymbolItemsCheckable() const override
items of symbology items in legend should be checkable
static QgsFeatureRenderer * createFromSld(QDomElement &element, QgsWkbTypes::GeometryType geomType)
QgsInvertedPolygonRenderer is a polygon-only feature renderer used to display features inverted...
#define QgsDebugMsgLevel(str, level)
const QgsCategoryList & categories() const
static QgsFeatureRenderer * create(QDomElement &element, const QgsReadWriteContext &context)
Creates a new rule-based renderer instance from XML.
static QDomElement saveSymbols(QgsSymbolMap &symbols, const QString &tagName, QDomDocument &doc, const QgsReadWriteContext &context)
Writes a collection of symbols to XML with specified tagName for the top-level element.
QgsRuleBasedRenderer::RuleList rulesForFeature(const QgsFeature &feature, QgsRenderContext *context=nullptr, bool onlyActive=true)
Returns the list of rules used to render the feature in a specific context.
double size() const
Returns the symbol size.
void renderFeatureWithSymbol(const QgsFeature &feature, QgsSymbol *symbol, QgsRenderContext &context, int layer, bool selected, bool drawVertexMarker)
Render the feature with the symbol using context.
QgsSymbolList symbols(const QgsRenderContext &context=QgsRenderContext()) const
A QgsRuleBasedRenderer rendering job, consisting of a feature to be rendered with a particular symbol...
void removeChild(QgsRuleBasedRenderer::Rule *rule)
delete child rule
QgsExpression * filter() const
A filter that will check if this rule applies.
~QgsRuleBasedRenderer() override
QList< QgsSymbolLayer * > QgsSymbolLayerList
When drawing a vector layer with rule-based renderer, it goes through the rules and draws features wi...
QList< QgsRuleBasedRenderer::RenderJob * > jobs
List of jobs to render, owned by this object.
bool isFilterOK(const QgsFeature &f, QgsRenderContext *context=nullptr) const
Check if a given feature shall be rendered by this rule.
QgsSymbol * symbol() const
double minimumScale() const
Returns the minimum map scale (i.e.
void insertChild(int i, QgsRuleBasedRenderer::Rule *rule)
add child rule, take ownership, sets this as parent
Render level: a list of jobs to be drawn at particular level for a QgsRuleBasedRenderer.
bool isScaleOK(double scale) const
Check if this rule applies for a given scale.
static QgsSymbolMap loadSymbols(QDomElement &element, const QgsReadWriteContext &context)
Reads a collection of symbols from XML and returns them in a map. Caller is responsible for deleting ...
QgsSymbolLayer * symbolLayer(int layer)
Returns a specific symbol layers contained in the symbol.
bool orderByEnabled() const
Returns whether custom ordering will be applied before features are processed by this renderer...
void stopRender(QgsRenderContext &context)
Stop a rendering process.
void setOrderBy(const QgsFeatureRequest::OrderBy &orderBy)
Define the order in which features shall be processed by this renderer.
QgsRuleBasedRenderer::Rule * takeChildAt(int i)
take child rule out, set parent as null
void setSymbol(QgsSymbol *sym)
Sets a new symbol (or NULL). Deletes old symbol.
QgsSymbol * symbolForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Returns symbol for current feature. Should not be used individually: there could be more symbols for ...
QString expression() const
Returns the original, unmodified expression string.
QgsExpressionContext & expressionContext()
Gets the expression context.
GeometryType
The geometry types are used to group QgsWkbTypes::Type in a coarse way.
static void refineRuleRanges(QgsRuleBasedRenderer::Rule *initialRule, QgsGraduatedSymbolRenderer *r)
take a rule and create a list of new rules based on the ranges from graduated symbol renderer ...
void setActive(bool state)
Sets if this rule is active.
QgsRuleBasedRenderer::Rule * clone() const
clone this rule, return new instance
QgsSymbolList symbolsForFeature(const QgsFeature &feature, QgsRenderContext *context=nullptr)
tell which symbols will be used to render the feature
const QgsFeatureRenderer * embeddedRenderer() const override
Returns the current embedded renderer (subrenderer) for this feature renderer.
The class stores information about one class/rule of a vector layer renderer in a unified way that ca...
Contains information about the context of a rendering operation.
Abstract base class for marker symbol layers.
void setIsElse(bool iselse)
Sets if this rule is an ELSE rule.
void startRender(QgsRenderContext &context, const QgsFields &fields) override
Must be called when a new render cycle is started.
void setLabel(const QString &label)
bool usingSymbolLevels() const
QgsSymbol * symbol
Symbol to render feature with (not owned by this object).
virtual void startRender(QgsRenderContext &context, const QgsFields &fields)
Must be called when a new render cycle is started.
virtual QgsSymbol * clone() const =0
Gets a deep copy of this symbol.
static QgsRuleBasedRenderer * convertFromRenderer(const QgsFeatureRenderer *renderer)
creates a QgsRuleBasedRenderer from an existing renderer.
void CORE_EXPORT save(QDomElement &elem) const
Serialize to XML.
bool isField() const
Checks whether an expression consists only of a single field reference.
double upperValue() const
virtual void stopRender(QgsRenderContext &context)
Must be called when a render cycle has finished, to allow the renderer to clean up.
QMap< QString, QgsSymbol *> QgsSymbolMap
bool needsGeometry() const
Returns true if this rule or one of its chilren needs the geometry to be applied. ...
static QString quotedString(QString text)
Returns a quoted version of a string (in single quotes)
void copyRendererData(QgsFeatureRenderer *destRenderer) const
Clones generic renderer data to another renderer.
QgsSymbolList symbolsForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Returns list of symbols used for rendering the feature.
bool legendSymbolItemChecked(const QString &key) override
items of symbology items in legend is checked
Rule(QgsSymbol *symbol, int maximumScale=0, int minimumScale=0, const QString &filterExp=QString(), const QString &label=QString(), const QString &description=QString(), bool elseRule=false)
Constructor takes ownership of the symbol.
QgsRuleBasedRenderer * clone() const override
Create a deep copy of this renderer.
QgsLegendSymbolList legendSymbolItems(int currentLevel=-1) const
QgsRuleBasedRenderer::Rule::RenderResult renderFeature(QgsRuleBasedRenderer::FeatureToRender &featToRender, QgsRenderContext &context, QgsRuleBasedRenderer::RenderQueue &renderQueue)
Render a given feature, will recursively call subclasses and only render if the constraints apply...
static void refineRuleCategories(QgsRuleBasedRenderer::Rule *initialRule, QgsCategorizedSymbolRenderer *r)
take a rule and create a list of new rules based on the categories from categorized symbol renderer ...
bool willRenderFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Returns whether the renderer will render a feature or not.
QString filter(const QgsFields &fields=QgsFields()) override
If a renderer does not require all the features this method may be overridden and return an expressio...
void setFilterExpression(const QString &filterExp)
Set the expression used to check if a given feature shall be rendered with this rule.
Feature for rendering by a QgsRuleBasedRenderer.
QgsSymbolList symbols(QgsRenderContext &context) const override
Returns list of symbols used by the renderer.
static void refineRuleScales(QgsRuleBasedRenderer::Rule *initialRule, QList< int > scales)
take a rule and create a list of new rules with intervals of scales given by the passed scale denomin...
void removeChildAt(int i)
delete child rule
const QgsFeatureRenderer * embeddedRenderer() const override
Returns the current embedded renderer (subrenderer) for this feature renderer.
static QgsRuleBasedRenderer::Rule * create(QDomElement &ruleElem, QgsSymbolMap &symbolMap)
Create a rule from an XML definition.
QgsRuleBasedRenderer::Rule * findRuleByKey(const QString &key)
Try to find a rule given its unique key.
static QgsExpression * expressionFromOgcFilter(const QDomElement &element, QgsVectorLayer *layer=nullptr)
Parse XML with OGC filter into QGIS expression.
const QgsRangeList & ranges() const
static bool createSymbolLayerListFromSld(QDomElement &element, QgsWkbTypes::GeometryType geomType, QgsSymbolLayerList &layers)
void setOrderByEnabled(bool enabled)
Sets whether custom ordering should be applied before features are processed by this renderer...
QgsSymbol * symbol() const
Returns the symbol which will be rendered for every feature.
void setLegendSymbolItem(const QString &key, QgsSymbol *symbol) override
Sets the symbol to be used for a legend symbol item.
virtual QgsFeatureRenderer * clone() const =0
Create a deep copy of this renderer.
void appendChild(QgsRuleBasedRenderer::Rule *rule)
add child rule, take ownership, sets this as parent
static QgsRuleBasedRenderer::Rule * createFromSld(QDomElement &element, QgsWkbTypes::GeometryType geomType)
Create a rule from the SLD provided in element and for the specified geometry type.
virtual void setDataDefinedProperty(Property key, const QgsProperty &property)
Sets a data defined property for the layer.
void toSld(QDomDocument &doc, QDomElement &element, const QgsStringMap &props=QgsStringMap()) const override
used from subclasses to create SLD Rule elements following SLD v1.1 specs
QString dump() const override
Returns debug information about this renderer.
virtual QString layerType() const =0
Returns a string that represents this layer type.
QSet< QString > legendKeysForFeature(const QgsFeature &feature, QgsRenderContext *context=nullptr)
Returns which legend keys match the feature.
virtual bool saveProperties(QDomDocument &doc, QDomElement &element) const
Saves the current state of the effect to a DOM element.