43#include <QDomDocument>
46#include <QRegularExpression>
55 mUuid = !
uuid.isEmpty() ?
uuid : QUuid::createUuid().toString();
59 : mValue( cat.mValue )
60 , mSymbol( cat.mSymbol ? cat.mSymbol->clone() : nullptr )
61 , mLabel( cat.mLabel )
62 , mRender( cat.mRender )
131 if ( !
mSymbol.get() || props.value( QStringLiteral(
"attribute" ), QString() ).toString().isEmpty() )
134 QString attrName = props[ QStringLiteral(
"attribute" )].toString();
145 else if ( attrExpression.
isField() )
148 qgis::down_cast<const QgsExpressionNodeColumnRef *>( attrExpression.
rootNode() )->name()
152 QDomElement ruleElem = doc.createElement( QStringLiteral(
"se:Rule" ) );
154 QDomElement nameElem = doc.createElement( QStringLiteral(
"se:Name" ) );
155 nameElem.appendChild( doc.createTextNode(
mLabel ) );
156 ruleElem.appendChild( nameElem );
158 QDomElement descrElem = doc.createElement( QStringLiteral(
"se:Description" ) );
159 QDomElement titleElem = doc.createElement( QStringLiteral(
"se:Title" ) );
160 QString descrStr = QStringLiteral(
"%1 is '%2'" ).arg( attrName,
mValue.toString() );
161 titleElem.appendChild( doc.createTextNode( !
mLabel.isEmpty() ?
mLabel : descrStr ) );
162 descrElem.appendChild( titleElem );
163 ruleElem.appendChild( descrElem );
167 if (
mValue.userType() == QMetaType::Type::QVariantList )
169 const QVariantList list =
mValue.toList();
170 if ( list.size() == 1 )
176 QStringList valuesList;
177 valuesList.reserve( list.size() );
178 for (
const QVariant &v : list )
182 filterFunc = QStringLiteral(
"%1 IN (%2)" ).arg( attrName,
183 valuesList.join(
',' ) );
188 filterFunc = QStringLiteral(
"ELSE" );
200 mSymbol->toSld( doc, ruleElem, props );
208 element.appendChild( ruleElem );
215 , mAttrName( attrName )
224 QgsDebugError( QStringLiteral(
"invalid symbol in a category! ignoring..." ) );
233 QgsCategoryList::const_iterator catIt =
mCategories.constBegin();
236 if (
QgsSymbol *catSymbol = catIt->symbol() )
254 const QVariant val = cat.value();
255 if ( val.userType() == QMetaType::Type::QVariantList )
257 const QVariantList list = val.toList();
258 for (
const QVariant &v : list )
260 mSymbolHash.insert( v.toString(), ( cat.renderState() ||
mCounting ) ? cat.symbol() : nullptr );
265 mSymbolHash.insert( val.toString(), ( cat.renderState() ||
mCounting ) ? cat.symbol() : nullptr );
283 foundMatchingSymbol =
false;
291 QgsDebugError( QStringLiteral(
"there are no hashed symbols!!!" ) );
300 foundMatchingSymbol =
true;
330 QVariant value = valueForFeature( feature, context );
332 bool foundCategory =
false;
336 if ( !foundCategory )
374 if ( catIndex < 0 || catIndex >=
mCategories.size() )
382 if ( catIndex < 0 || catIndex >=
mCategories.size() )
390 if ( catIndex < 0 || catIndex >=
mCategories.size() )
398 if ( catIndex < 0 || catIndex >=
mCategories.size() )
408 QgsDebugError( QStringLiteral(
"invalid symbol in a category! ignoring..." ) );
417 if ( catIndex < 0 || catIndex >=
mCategories.size() )
446 if ( order == Qt::AscendingOrder )
458 return QString::localeAwareCompare( c1.
label(), c2.
label() ) < 0;
468 if ( order == Qt::AscendingOrder )
497 cat.symbol()->startRender( context, fields );
507 cat.symbol()->stopRender( context );
514 QSet<QString> attributes;
526 QgsCategoryList::const_iterator catIt =
mCategories.constBegin();
553 QString s = QStringLiteral(
"CATEGORIZED: idx %1\n" ).arg(
mAttrName );
576 QVariantMap newProps = props;
577 newProps[ QStringLiteral(
"attribute" )] =
mAttrName;
582 it->
toSld( doc, element, newProps );
589 bool isExpression = ( attrNum == -1 );
591 bool hasDefault =
false;
592 bool defaultActive =
false;
593 bool allActive =
true;
594 bool noneActive =
true;
598 QString activeValues;
599 QString inactiveValues;
606 defaultActive = cat.renderState();
609 noneActive = noneActive && !cat.renderState();
610 allActive = allActive && cat.renderState();
612 const bool isList = cat.value().userType() == QMetaType::Type::QVariantList;
615 if ( !cat.renderState() )
621 const QVariantList list = cat.value().toList();
622 for (
const QVariant &v : list )
624 if ( !inactiveValues.isEmpty() )
625 inactiveValues.append(
',' );
632 if ( !inactiveValues.isEmpty() )
633 inactiveValues.append(
',' );
635 inactiveValues.append( value );
645 const QVariantList list = cat.value().toList();
646 for (
const QVariant &v : list )
648 if ( !activeValues.isEmpty() )
649 activeValues.append(
',' );
656 if ( !activeValues.isEmpty() )
657 activeValues.append(
',' );
659 activeValues.append( value );
665 QString attr = isExpression ?
mAttrName : QStringLiteral(
"\"%1\"" ).arg(
mAttrName );
667 if ( allActive && hasDefault )
671 else if ( noneActive )
673 return QStringLiteral(
"FALSE" );
675 else if ( defaultActive )
677 return QStringLiteral(
"(%1) NOT IN (%2) OR (%1) IS NULL" ).arg( attr, inactiveValues );
681 return QStringLiteral(
"(%1) IN (%2)" ).arg( attr, activeValues );
692 lst.append( cat.symbol() );
718 QDomElement symbolsElem = element.firstChildElement( QStringLiteral(
"symbols" ) );
719 if ( symbolsElem.isNull() )
722 QDomElement catsElem = element.firstChildElement( QStringLiteral(
"categories" ) );
723 if ( catsElem.isNull() )
730 const auto valueFromString = [](
const QString & value,
const QString & valueType ) -> QVariant
732 if ( valueType == QLatin1String(
"double" ) )
735 const auto val { value.toDouble( &ok ) };
741 else if ( valueType == QLatin1String(
"ulong" ) )
744 const auto val { value.toULongLong( &ok ) };
750 else if ( valueType == QLatin1String(
"long" ) )
753 const auto val { value.toLongLong( &ok ) };
759 else if ( valueType == QLatin1String(
"bool" ) )
761 if ( value.toLower() == QLatin1String(
"false" ) )
763 if ( value.toLower() == QLatin1String(
"true" ) )
766 else if ( valueType == QLatin1String(
"NULL" ) )
774 QDomElement catElem = catsElem.firstChildElement();
776 while ( !catElem.isNull() )
778 if ( catElem.tagName() == QLatin1String(
"category" ) )
781 if ( catElem.hasAttribute( QStringLiteral(
"value" ) ) )
783 value = valueFromString( catElem.attribute( QStringLiteral(
"value" ) ), catElem.attribute( QStringLiteral(
"type" ), QString() ) ) ;
788 QDomElement valElem = catElem.firstChildElement();
789 while ( !valElem.isNull() )
791 if ( valElem.tagName() == QLatin1String(
"val" ) )
793 values << valueFromString( valElem.attribute( QStringLiteral(
"value" ) ), valElem.attribute( QStringLiteral(
"type" ), QString() ) );
795 valElem = valElem.nextSiblingElement();
797 if ( !values.isEmpty() )
800 QString symbolName = catElem.attribute( QStringLiteral(
"symbol" ) );
801 QString label = catElem.attribute( QStringLiteral(
"label" ) );
802 bool render = catElem.attribute( QStringLiteral(
"render" ) ) != QLatin1String(
"false" );
803 QString uuid = catElem.attribute( QStringLiteral(
"uuid" ), QString::number( i++ ) );
804 if ( symbolMap.contains( symbolName ) )
806 QgsSymbol *symbol = symbolMap.take( symbolName );
810 catElem = catElem.nextSiblingElement();
813 QString attrName = element.attribute( QStringLiteral(
"attr" ) );
821 QDomElement sourceSymbolElem = element.firstChildElement( QStringLiteral(
"source-symbol" ) );
822 if ( !sourceSymbolElem.isNull() )
825 if ( sourceSymbolMap.contains( QStringLiteral(
"0" ) ) )
833 QDomElement sourceColorRampElem = element.firstChildElement( QStringLiteral(
"colorramp" ) );
834 if ( !sourceColorRampElem.isNull() && sourceColorRampElem.attribute( QStringLiteral(
"name" ) ) == QLatin1String(
"[source]" ) )
839 QDomElement rotationElem = element.firstChildElement( QStringLiteral(
"rotation" ) );
840 if ( !rotationElem.isNull() && !rotationElem.attribute( QStringLiteral(
"field" ) ).isEmpty() )
852 QDomElement sizeScaleElem = element.firstChildElement( QStringLiteral(
"sizescale" ) );
853 if ( !sizeScaleElem.isNull() && !sizeScaleElem.attribute( QStringLiteral(
"field" ) ).isEmpty() )
859 sizeScaleElem.attribute( QStringLiteral(
"field" ) ) );
865 sizeScaleElem.attribute( QStringLiteral(
"field" ) ) );
869 QDomElement ddsLegendSizeElem = element.firstChildElement( QStringLiteral(
"data-defined-size-legend" ) );
870 if ( !ddsLegendSizeElem.isNull() )
883 rendererElem.setAttribute( QStringLiteral(
"type" ), QStringLiteral(
"categorizedSymbol" ) );
884 rendererElem.setAttribute( QStringLiteral(
"attr" ),
mAttrName );
888 const auto stringForType = [](
const QMetaType::Type
type ) -> QString
890 if (
type == QMetaType::Type::QChar ||
type == QMetaType::Type::Int ||
type == QMetaType::Type::LongLong )
892 return QStringLiteral(
"long" );
894 else if (
type == QMetaType::Type::UInt ||
type == QMetaType::Type::ULongLong )
896 return QStringLiteral(
"ulong" );
898 else if (
type == QMetaType::Type::Double )
900 return QStringLiteral(
"double" ) ;
902 else if (
type == QMetaType::Type::Bool )
904 return QStringLiteral(
"bool" );
908 return QStringLiteral(
"string" );
917 QDomElement catsElem = doc.createElement( QStringLiteral(
"categories" ) );
918 QgsCategoryList::const_iterator it =
mCategories.constBegin();
922 QString symbolName = QString::number( i );
925 QDomElement catElem = doc.createElement( QStringLiteral(
"category" ) );
926 if ( cat.
value().userType() == QMetaType::Type::QVariantList )
928 const QVariantList list = cat.
value().toList();
929 for (
const QVariant &v : list )
931 QDomElement valueElem = doc.createElement( QStringLiteral(
"val" ) );
932 valueElem.setAttribute( QStringLiteral(
"value" ), v.toString() );
933 valueElem.setAttribute( QStringLiteral(
"type" ), stringForType(
static_cast<QMetaType::Type
>( v.userType() ) ) );
934 catElem.appendChild( valueElem );
942 catElem.setAttribute( QStringLiteral(
"value" ),
"NULL" );
943 catElem.setAttribute( QStringLiteral(
"type" ),
"NULL" );
947 catElem.setAttribute( QStringLiteral(
"value" ), cat.
value().toString() );
948 catElem.setAttribute( QStringLiteral(
"type" ), stringForType(
static_cast<QMetaType::Type
>( cat.
value().userType() ) ) );
951 catElem.setAttribute( QStringLiteral(
"symbol" ), symbolName );
952 catElem.setAttribute( QStringLiteral(
"label" ), cat.
label() );
953 catElem.setAttribute( QStringLiteral(
"render" ), cat.
renderState() ?
"true" :
"false" );
954 catElem.setAttribute( QStringLiteral(
"uuid" ), cat.
uuid() );
955 catsElem.appendChild( catElem );
958 rendererElem.appendChild( catsElem );
962 rendererElem.appendChild( symbolsElem );
969 sourceSymbols.insert( QStringLiteral(
"0" ),
mSourceSymbol.get() );
971 rendererElem.appendChild( sourceSymbolElem );
978 rendererElem.appendChild( colorRampElem );
981 QDomElement rotationElem = doc.createElement( QStringLiteral(
"rotation" ) );
982 rendererElem.appendChild( rotationElem );
984 QDomElement sizeScaleElem = doc.createElement( QStringLiteral(
"sizescale" ) );
985 rendererElem.appendChild( sizeScaleElem );
989 QDomElement ddsLegendElem = doc.createElement( QStringLiteral(
"data-defined-size-legend" ) );
991 rendererElem.appendChild( ddsLegendElem );
1013 auto _displayString = [ ](
const QVariant & v,
int precision ) -> QString
1021 const bool isNumeric {v.userType() == QMetaType::Type::Double || v.userType() == QMetaType::Type::Int || v.userType() == QMetaType::Type::UInt || v.userType() == QMetaType::Type::LongLong || v.userType() == QMetaType::Type::ULongLong};
1024 if ( v.userType() == QMetaType::Type::Double )
1031 return v.toString();
1034 if ( QLocale().decimalPoint() !=
'.' ||
1035 !( QLocale().numberOptions() & QLocale::NumberOption::OmitGroupSeparator ) )
1039 if ( -1 < v.toDouble() && v.toDouble() < 1 )
1041 return QLocale().toString( v.toDouble(),
'g',
precision );
1045 return QLocale().toString( v.toDouble(),
'f',
precision );
1052 const QString s( v.toString() );
1053 const int dotPosition( s.indexOf(
'.' ) );
1055 if ( dotPosition < 0 && s.indexOf(
'e' ) < 0 )
1058 return QLocale().toString( v.toDouble(),
'f',
precision );
1063 else precision = s.length() - dotPosition - 1;
1065 if ( -1 < v.toDouble() && v.toDouble() < 1 )
1067 return QLocale().toString( v.toDouble(),
'g',
precision );
1071 return QLocale().toString( v.toDouble(),
'f',
precision );
1079 if ( -1 < v.toDouble() && v.toDouble() < 1 )
1081 return QString::number( v.toDouble(),
'g',
precision );
1085 return QString::number( v.toDouble(),
'f',
precision );
1090 else if ( isNumeric &&
1091 !( QLocale().numberOptions() & QLocale::NumberOption::OmitGroupSeparator ) )
1094 const qlonglong converted( v.toLongLong( &ok ) );
1096 return QLocale().toString( converted );
1098 else if ( v.userType() == QMetaType::Type::QByteArray )
1100 return QObject::tr(
"BLOB" );
1104 return v.toString();
1107 if ( v.userType() == QMetaType::Type::QStringList || v.userType() == QMetaType::Type::QVariantList )
1113 const QVariantList list = v.toList();
1114 for (
const QVariant &var : list )
1116 if ( !result.isEmpty() )
1118 result.append(
';' );
1120 result.append( _displayString( var,
precision ) );
1142 if ( sSize != ddSize )
1145 return baseLegendSymbolItems();
1162 lst += baseLegendSymbolItems();
1167 return baseLegendSymbolItems();
1172 const QVariant value = valueForFeature( feature, context );
1177 if ( cat.value().userType() == QMetaType::Type::QVariantList )
1179 const QVariantList list = cat.value().toList();
1180 for (
const QVariant &v : list )
1192 if (
QgsVariantUtils::isNull( value ) && ( value.userType() == QMetaType::Type::Double || value.userType() == QMetaType::Type::Int ||
1193 value.userType() == QMetaType::Type::UInt || value.userType() == QMetaType::Type::LongLong ||
1194 value.userType() == QMetaType::Type::ULongLong || value.userType() == QMetaType::Type::Bool ) )
1196 match = cat.value().toString().isEmpty();
1200 match = value == cat.value();
1207 return QSet< QString >() << cat.uuid();
1209 return QSet< QString >();
1213 return QSet< QString >();
1236 const bool isNumeric = layer && fieldIndex >= 0 ? layer->
fields().
at( fieldIndex ).
isNumeric() :
false;
1237 const QMetaType::Type fieldType = layer && fieldIndex >= 0 ? layer->
fields().
at( fieldIndex ).
type() : QMetaType::Type::UnknownType;
1242 if ( cat.
value().userType() == QMetaType::Type::QVariantList )
1244 const QVariantList list = cat.
value().toList();
1246 parts.reserve( list.size() );
1247 for (
const QVariant &v : list )
1252 return QStringLiteral(
"%1 IN (%2)" ).arg( attributeComponent, parts.join( QLatin1String(
", " ) ) );
1257 QVariant value = cat.
value();
1258 if ( isNumeric && value.toString().isEmpty() )
1264 return QStringLiteral(
"%1 IS NULL" ).arg( attributeComponent );
1265 else if ( fieldType == QMetaType::Type::UnknownType )
1318 double value = count / num;
1330 symbol->
setColor( cat.symbol()->color() );
1346 if ( category.uuid() == key )
1348 return category.renderState();
1388 std::unique_ptr< QgsCategorizedSymbolRenderer > r;
1389 if ( renderer->
type() == QLatin1String(
"categorizedSymbol" ) )
1393 else if ( renderer->
type() == QLatin1String(
"graduatedSymbol" ) )
1396 if ( graduatedSymbolRenderer )
1405 r->setClassAttribute( graduatedSymbolRenderer->
classAttribute() );
1408 else if ( renderer->
type() == QLatin1String(
"pointDisplacement" ) || renderer->
type() == QLatin1String(
"pointCluster" ) )
1411 if ( pointDistanceRenderer )
1414 else if ( renderer->
type() == QLatin1String(
"invertedPolygonRenderer" ) )
1417 if ( invertedPolygonRenderer )
1420 else if ( renderer->
type() == QLatin1String(
"embeddedSymbol" ) && layer )
1443 r = std::make_unique< QgsCategorizedSymbolRenderer >( QString(),
QgsCategoryList() );
1448 r->setSourceSymbol(
symbols.at( 0 )->clone() );
1474 const QSet< QString > allSymbolNames( unmatchedSymbols.begin(), unmatchedSymbols.end() );
1476 const thread_local QRegularExpression tolerantMatchRe( QStringLiteral(
"[^\\w\\d ]" ), QRegularExpression::UseUnicodePropertiesOption );
1478 for (
int catIdx = 0; catIdx <
mCategories.count(); ++catIdx )
1480 const QVariant value =
mCategories.at( catIdx ).value();
1481 const QString val = value.toString().trimmed();
1482 std::unique_ptr< QgsSymbol > symbol( style->
symbol( val ) );
1484 if ( symbol && symbol->type() ==
type )
1487 unmatchedSymbols.removeAll( val );
1492 if ( !caseSensitive || useTolerantMatch )
1494 QString testVal = val;
1495 if ( useTolerantMatch )
1496 testVal.replace( tolerantMatchRe, QString() );
1498 bool foundMatch =
false;
1499 for (
const QString &name : allSymbolNames )
1501 QString testName = name.trimmed();
1502 if ( useTolerantMatch )
1503 testName.replace( tolerantMatchRe, QString() );
1505 if ( testName == testVal || ( !caseSensitive && testName.trimmed().compare( testVal, Qt::CaseInsensitive ) == 0 ) )
1508 std::unique_ptr< QgsSymbol > symbol( style->
symbol( name ) );
1509 if ( symbol && symbol->type() ==
type )
1512 unmatchedSymbols.removeAll( name );
1523 unmatchedCategories << value;
1532 QVariantList vals = values;
1536 if ( layer && !attributeName.isNull() )
1539 for (
const QVariant &value : vals )
1544 const int fieldIdx = fields.
lookupField( attributeName );
1546 if ( fieldIdx != -1 )
1548 const QgsField field = fields.
at( fieldIdx );
1551 categoryName =
formatter->representValue( layer, fieldIdx, setup.
config(), QVariant(), value );
@ NoGeometry
Geometry is not required. It may still be returned if e.g. required for a filter condition.
@ EmbeddedSymbols
Retrieve any embedded feature symbology.
QFlags< FeatureRendererFlag > FeatureRendererFlags
Flags controlling behavior of vector feature renderers.
@ AffectsLabeling
If present, indicates that the renderer will participate in the map labeling problem.
@ AffectsLabeling
If present, indicates that the symbol will participate in the map labeling problem.
static QString nullRepresentation()
Returns the string used to represent the value NULL throughout QGIS.
static QgsFieldFormatterRegistry * fieldFormatterRegistry()
Gets the registry of available field formatters.
void sortByValue(Qt::SortOrder order=Qt::AscendingOrder)
Sorts the existing categories by their value.
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...
QgsSymbol * symbolForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
To be overridden.
void updateSymbols(QgsSymbol *sym)
Update all the symbols but leave categories and colors.
bool updateCategoryRenderState(int catIndex, bool render)
Changes the render state for the category with the specified index.
void setSourceColorRamp(QgsColorRamp *ramp)
Sets the source color ramp.
void stopRender(QgsRenderContext &context) override
Must be called when a render cycle has finished, to allow the renderer to clean up.
QgsSymbol * sourceSymbol()
Returns the renderer's source symbol, which is the base symbol used for the each categories' symbol b...
const QgsCategoryList & categories() const
Returns a list of all categories recognized by the renderer.
QString legendKeyToExpression(const QString &key, QgsVectorLayer *layer, bool &ok) const override
Attempts to convert the specified legend rule key to a QGIS expression matching the features displaye...
int matchToSymbols(QgsStyle *style, Qgis::SymbolType type, QVariantList &unmatchedCategories, QStringList &unmatchedSymbols, bool caseSensitive=true, bool useTolerantMatch=false)
Replaces category symbols with the symbols from a style that have a matching name and symbol type.
std::unique_ptr< QgsColorRamp > mSourceColorRamp
Q_DECL_DEPRECATED QgsSymbol * symbolForValue(const QVariant &value) const
Returns the matching symbol corresponding to an attribute value.
std::unique_ptr< QgsSymbol > mSourceSymbol
static QgsCategorizedSymbolRenderer * convertFromRenderer(const QgsFeatureRenderer *renderer, QgsVectorLayer *layer=nullptr)
Creates a new QgsCategorizedSymbolRenderer from an existing renderer.
void updateColorRamp(QgsColorRamp *ramp)
Update the color ramp used and all symbols colors.
QgsDataDefinedSizeLegend * dataDefinedSizeLegend() const
Returns configuration of appearance of legend when using data-defined size for marker symbols.
static QgsCategoryList createCategories(const QVariantList &values, const QgsSymbol *symbol, QgsVectorLayer *layer=nullptr, const QString &fieldName=QString())
Create categories for a list of values.
QHash< QString, QgsSymbol * > mSymbolHash
hashtable for faster access to symbols
bool filterNeedsGeometry() const override
Returns true if this renderer requires the geometry to apply the filter.
QSet< QString > usedAttributes(const QgsRenderContext &context) const override
Returns a list of attributes required by this renderer.
void setSourceSymbol(QgsSymbol *sym)
Sets the source symbol for the renderer, which is the base symbol used for the each categories' symbo...
void startRender(QgsRenderContext &context, const QgsFields &fields) override
Must be called when a new render cycle is started.
QgsSymbolList symbols(QgsRenderContext &context) const override
Returns list of symbols used by the renderer.
int categoryIndexForValue(const QVariant &val)
Returns the index for the category with the specified value (or -1 if not found).
static QgsFeatureRenderer * create(QDomElement &element, const QgsReadWriteContext &context)
Creates a categorized renderer from an XML element.
bool updateCategorySymbol(int catIndex, QgsSymbol *symbol)
Changes the symbol for the category with the specified index.
QgsCategoryList mCategories
bool accept(QgsStyleEntityVisitorInterface *visitor) const override
Accepts the specified symbology visitor, causing it to visit all symbols associated with the renderer...
void setLegendSymbolItem(const QString &key, QgsSymbol *symbol) override
Sets the symbol to be used for a legend symbol item.
std::unique_ptr< QgsExpression > mExpression
std::unique_ptr< QgsDataDefinedSizeLegend > mDataDefinedSizeLegend
bool legendSymbolItemChecked(const QString &key) override
Returns true if the legend symbology item with the specified key is checked.
bool legendSymbolItemsCheckable() const override
Returns true if symbology items in legend are checkable.
void addCategory(const QgsRendererCategory &category)
Adds a new category to the renderer.
QgsCategorizedSymbolRenderer(const QString &attrName=QString(), const QgsCategoryList &categories=QgsCategoryList())
Constructor for QgsCategorizedSymbolRenderer.
void sortByLabel(Qt::SortOrder order=Qt::AscendingOrder)
Sorts the existing categories by their label.
QgsSymbol * originalSymbolForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Returns symbol for feature.
int mAttrNum
attribute index (derived from attribute name in startRender)
QgsLegendSymbolList legendSymbolItems() const override
Returns a list of symbology items for the legend.
void moveCategory(int from, int to)
Moves an existing category at index position from to index position to.
QDomElement save(QDomDocument &doc, const QgsReadWriteContext &context) override
Stores renderer properties to an XML element.
bool deleteCategory(int catIndex)
Deletes the category with the specified index from the renderer.
Qgis::FeatureRendererFlags flags() const override
Returns flags associated with the renderer.
Q_DECL_DEPRECATED QgsSymbol * skipRender()
void checkLegendSymbolItem(const QString &key, bool state=true) override
Sets whether the legend symbology item with the specified ley should be checked.
QString dump() const override
Returns debug information about this renderer.
QSet< QString > legendKeysForFeature(const QgsFeature &feature, QgsRenderContext &context) const override
Returns legend keys matching a specified feature.
QgsColorRamp * sourceColorRamp()
Returns the source color ramp, from which each categories' color is derived.
bool updateCategoryValue(int catIndex, const QVariant &value)
Changes the value for the category with the specified index.
void toSld(QDomDocument &doc, QDomElement &element, const QVariantMap &props=QVariantMap()) const override
used from subclasses to create SLD Rule elements following SLD v1.1 specs
QgsCategorizedSymbolRenderer * clone() const override
Create a deep copy of this renderer.
void deleteAllCategories()
Deletes all existing categories from the renderer.
void setDataDefinedSizeLegend(QgsDataDefinedSizeLegend *settings)
Configures appearance of legend when renderer is configured to use data-defined size for marker symbo...
bool updateCategoryLabel(int catIndex, const QString &label)
Changes the label for the category with the specified index.
static QString displayString(const QVariant &value, int precision=-1)
Returns a localized representation of value with the given precision, if precision is -1 then precisi...
~QgsCategorizedSymbolRenderer() override
int categoryIndexForLabel(const QString &val)
Returns the index of the category with the specified label (or -1 if the label was not found,...
Abstract base class for color ramps.
virtual QgsColorRamp * clone() const =0
Creates a clone of the color ramp.
Object that keeps configuration of appearance of marker symbol's data-defined size in legend.
static QgsDataDefinedSizeLegend * readXml(const QDomElement &elem, const QgsReadWriteContext &context) SIP_FACTORY
Creates instance from given element and returns it (caller takes ownership). Returns nullptr on error...
void updateFromSymbolAndProperty(const QgsMarkerSymbol *symbol, const QgsProperty &ddSize)
Updates the list of classes, source symbol and title label from given symbol and property.
QgsLegendSymbolList legendSymbolList() const
Generates legend symbol items according to the configuration.
A vector feature renderer which uses embedded feature symbology to render per-feature symbols.
static QList< QgsExpressionContextScope * > globalProjectLayerScopes(const QgsMapLayer *layer)
Creates a list of three scopes: global, layer's project and layer.
Expression contexts are used to encapsulate the parameters around which a QgsExpression should be eva...
void appendScopes(const QList< QgsExpressionContextScope * > &scopes)
Appends a list of scopes to the end of the context.
Class for parsing and evaluation of expressions (formerly called "search strings").
bool prepare(const QgsExpressionContext *context)
Gets the expression ready for evaluation - find out column indexes.
static QString quotedValue(const QVariant &value)
Returns a string representation of a literal value, including appropriate quotations where required.
static QString quoteFieldExpression(const QString &expression, const QgsVectorLayer *layer)
Validate if the expression is a field in the layer and ensure it is quoted.
bool hasParserError() const
Returns true if an error occurred when parsing the input expression.
bool isField() const
Checks whether an expression consists only of a single field reference.
QSet< QString > referencedColumns() const
Gets list of columns referenced by the expression.
static QString quotedColumnRef(QString name)
Returns a quoted column reference (in double quotes)
const QgsExpressionNode * rootNode() const
Returns the root node of the expression.
bool needsGeometry() const
Returns true if the expression uses feature geometry for some computation.
Wrapper for iterator of features from vector data provider or vector layer.
bool nextFeature(QgsFeature &f)
Fetch next feature and stores in f, returns true on success.
Abstract base class for all 2D vector feature renderers.
virtual void stopRender(QgsRenderContext &context)
Must be called when a render cycle has finished, to allow the renderer to clean up.
void copyRendererData(QgsFeatureRenderer *destRenderer) const
Clones generic renderer data to another renderer.
static void convertSymbolRotation(QgsSymbol *symbol, const QString &field)
void saveRendererData(QDomDocument &doc, QDomElement &element, const QgsReadWriteContext &context)
Saves generic renderer data into the specified element.
virtual const QgsFeatureRenderer * embeddedRenderer() const
Returns the current embedded renderer (subrenderer) for this feature renderer.
virtual void startRender(QgsRenderContext &context, const QgsFields &fields)
Must be called when a new render cycle is started.
static void convertSymbolSizeScale(QgsSymbol *symbol, Qgis::ScaleMethod method, const QString &field)
virtual QgsFeatureRenderer * clone() const =0
Create a deep copy of this renderer.
This class wraps a request for features to a vector layer (or directly its vector data provider).
QgsFeatureRequest & setFlags(Qgis::FeatureRequestFlags flags)
Sets flags that affect how features will be fetched.
QgsFeatureRequest & setNoAttributes()
Set that no attributes will be fetched.
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
const QgsSymbol * embeddedSymbol() const
Returns the feature's embedded symbology, or nullptr if the feature has no embedded symbol.
Encapsulate a field in an attribute table or data source.
QgsEditorWidgetSetup editorWidgetSetup() const
Gets the editor widget setup for the field.
Container of fields for a vector layer.
QgsField at(int i) const
Returns the field at particular index (must be in range 0..N-1).
Q_INVOKABLE int lookupField(const QString &fieldName) const
Looks up field's index from the field name.
A vector feature renderer which uses numeric attributes to classify features into different ranges.
QgsSymbol * sourceSymbol()
Returns the renderer's source symbol, which is the base symbol used for the each classes' symbol befo...
QgsColorRamp * sourceColorRamp()
Returns the source color ramp, from which each classes' color is derived.
QString classAttribute() const
Returns the attribute name (or expression) used for the classification.
void setSourceSymbol(QgsSymbol *sym)
Sets the source symbol for the renderer, which is the base symbol used for the each classes' symbol b...
QgsInvertedPolygonRenderer is a polygon-only feature renderer used to display features inverted,...
The class stores information about one class/rule of a vector layer renderer in a unified way that ca...
A marker symbol type, for rendering Point and MultiPoint geometries.
QgsProperty dataDefinedSize() const
Returns data defined size for whole symbol (including all symbol layers).
const QgsFeatureRenderer * embeddedRenderer() const override
Returns the current embedded renderer (subrenderer) for this feature renderer.
An abstract base class for distance based point renderers (e.g., clusterer and displacement renderers...
const QgsFeatureRenderer * embeddedRenderer() const override
Returns the current embedded renderer (subrenderer) for this feature renderer.
A store for object properties.
bool isActive() const
Returns whether the property is currently active.
Totally random color ramp.
virtual void setTotalColorCount(int colorCount)
Sets the desired total number of unique colors for the resultant ramp.
The class is used as a container of context for various read/write operations on other objects.
Contains information about the context of a rendering operation.
double rendererScale() const
Returns the renderer map scale.
QgsExpressionContext & expressionContext()
Gets the expression context.
Represents an individual category (class) from a QgsCategorizedSymbolRenderer.
void setRenderState(bool render)
Sets whether the category is currently enabled and should be rendered.
std::unique_ptr< QgsSymbol > mSymbol
QgsSymbol * symbol() const
Returns the symbol which will be used to render this category.
void setSymbol(QgsSymbol *s)
Sets the symbol which will be used to render this category.
QString uuid() const
Returns the unique identifier for this category.
QgsRendererCategory()=default
bool renderState() const
Returns true if the category is currently enabled and should be rendered.
QString dump() const
Returns a string representing the categories settings, used for debugging purposes only.
void setLabel(const QString &label)
Sets the label for this category, which is used to represent the category within legends and the laye...
void toSld(QDomDocument &doc, QDomElement &element, QVariantMap props) const
Converts the category to a matching SLD rule, within the specified DOM document and element.
void setValue(const QVariant &value)
Sets the value corresponding to this category.
QVariant value() const
Returns the value corresponding to this category.
QString label() const
Returns the label for this category, which is used to represent the category within legends and the l...
QgsRendererCategory & operator=(QgsRendererCategory cat)
A color ramp entity for QgsStyle databases.
An interface for classes which can visit style entity (e.g.
virtual bool visit(const QgsStyleEntityVisitorInterface::StyleLeaf &entity)
Called when the visitor will visit a style entity.
A symbol entity for QgsStyle databases.
QgsSymbol * symbol(const QString &name)
Returns a NEW copy of symbol.
QStringList symbolNames() const
Returns a list of names of symbols.
static void sortVariantList(QList< QVariant > &list, Qt::SortOrder order)
Sorts the passed list in requested order.
static void applyScaleDependency(QDomDocument &doc, QDomElement &ruleElem, QVariantMap &props)
Checks if the properties contain scaleMinDenom and scaleMaxDenom, if available, they are added into t...
static bool createFunctionElement(QDomDocument &doc, QDomElement &element, const QString &function)
static QgsColorRamp * loadColorRamp(QDomElement &element)
Creates a color ramp from the settings encoded in an XML element.
static bool hasSldSymbolizer(const QDomElement &element)
Returns true if a DOM element contains an SLD Symbolizer element.
static Qgis::ScaleMethod decodeScaleMethod(const QString &str)
Decodes a symbol scale method from a string.
static QDomElement saveColorRamp(const QString &name, QgsColorRamp *ramp, QDomDocument &doc)
Encodes a color ramp's settings to an XML element.
static void clearSymbolMap(QgsSymbolMap &symbols)
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 ...
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.
Abstract base class for all rendered symbols.
void setColor(const QColor &color) const
Sets the color for the symbol.
QSet< QString > usedAttributes(const QgsRenderContext &context) const
Returns a list of attributes required to render this feature.
virtual QgsSymbol * clone() const =0
Returns a deep copy of this symbol.
static bool isNull(const QVariant &variant, bool silenceNullWarnings=false)
Returns true if the specified variant should be considered a NULL value.
Represents a vector layer which manages a vector based data sets.
QgsFeatureIterator getFeatures(const QgsFeatureRequest &request=QgsFeatureRequest()) const FINAL
Queries the layer for features specified in request.
bool qgsVariantLessThan(const QVariant &lhs, const QVariant &rhs)
Compares two QVariant values and returns whether the first is less than the second.
bool qgsVariantGreaterThan(const QVariant &lhs, const QVariant &rhs)
Compares two QVariant values and returns whether the first is greater than the second.
bool labelGreaterThan(const QgsRendererCategory &c1, const QgsRendererCategory &c2)
bool valueLessThan(const QgsRendererCategory &c1, const QgsRendererCategory &c2)
bool valueGreaterThan(const QgsRendererCategory &c1, const QgsRendererCategory &c2)
bool labelLessThan(const QgsRendererCategory &c1, const QgsRendererCategory &c2)
QList< QgsRendererCategory > QgsCategoryList
QList< QgsLegendSymbolItem > QgsLegendSymbolList
#define QgsDebugMsgLevel(str, level)
#define QgsDebugError(str)
#define RENDERER_TAG_NAME
QMap< QString, QgsSymbol * > QgsSymbolMap
QList< QgsSymbol * > QgsSymbolList
Contains information relating to the style entity currently being visited.