26 : QAbstractItemModel( parent )
54 if ( index.row() < 0 || index.row() >=
rowCount( QModelIndex() ) )
58 const bool isColorRamp = index.row() >= mStyle->
symbolCount();
59 const QString name = !isColorRamp
60 ? mSymbolNames.value( index.row() )
61 : mRampNames.value( index.row() - mSymbolNames.size() );
69 switch ( index.column() )
75 if ( role == Qt::ToolTipRole )
77 QString tooltip = QStringLiteral(
"<h3>%1</h3><p><i>%2</i>" ).arg( name,
78 tags.count() > 0 ? tags.join( QStringLiteral(
", " ) ) : tr(
"Not tagged" ) );
81 std::unique_ptr< QgsSymbol > symbol( mStyle->
symbol( name ) );
84 int width =
static_cast< int >(
Qgis::UI_SCALE_FACTOR * QFontMetrics(
data( index, Qt::FontRole ).value< QFont >() ).width(
'X' ) * 23 );
85 int height =
static_cast< int >( width / 1.61803398875 );
88 QBuffer buffer( &data );
89 pm.save( &buffer,
"PNG", 100 );
90 tooltip += QStringLiteral(
"<p><img src='data:image/png;base64, %3'>" ).arg( QString( data.toBase64() ) );
105 case Qt::DecorationRole:
109 switch ( index.column() )
115 QIcon icon = mSymbolIconCache.value( name );
116 if ( !icon.isNull() )
119 std::unique_ptr< QgsSymbol > symbol( mStyle->
symbol( name ) );
122 if ( mAdditionalSizes.isEmpty() )
125 for (
const QVariant &size : mAdditionalSizes )
127 QSize s = size.toSize();
132 mSymbolIconCache.insert( name, icon );
138 QIcon icon = mColorRampIconCache.value( name );
139 if ( !icon.isNull() )
142 std::unique_ptr< QgsColorRamp > ramp( mStyle->
colorRamp( name ) );
145 if ( mAdditionalSizes.isEmpty() )
147 for (
const QVariant &size : mAdditionalSizes )
149 QSize s = size.toSize();
154 mColorRampIconCache.insert( name, icon );
175 return symbol ? symbol->
type() : QVariant();
187 if ( index.row() < 0 || index.row() >=
rowCount( QModelIndex() ) || role != Qt::EditRole )
190 switch ( index.column() )
194 const bool isColorRamp = index.row() >= mStyle->
symbolCount();
195 const QString name = !isColorRamp
196 ? mSymbolNames.value( index.row() )
197 : mRampNames.value( index.row() - mSymbolNames.size() );
198 const QString newName = value.toString();
214 Qt::ItemFlags
flags = QAbstractItemModel::flags( index );
215 if ( index.isValid() && index.column() ==
Name )
217 return flags | Qt::ItemIsEditable;
227 if ( role == Qt::DisplayRole )
229 if ( orientation == Qt::Vertical )
231 return QVariant( section );
238 return QVariant( tr(
"Name" ) );
241 return QVariant( tr(
"Tags" ) );
256 if ( !hasIndex( row, column, parent ) )
257 return QModelIndex();
259 if ( !parent.isValid() )
261 return createIndex( row, column );
264 return QModelIndex();
270 return QModelIndex();
275 if ( !parent.isValid() )
277 return mSymbolNames.count() + mRampNames.count();
289 mAdditionalSizes << size;
290 mSymbolIconCache.clear();
291 mColorRampIconCache.clear();
294 void QgsStyleModel::onSymbolAdded(
const QString &name,
QgsSymbol * )
296 mSymbolIconCache.remove( name );
297 const QStringList oldSymbolNames = mSymbolNames;
298 const QStringList newSymbolNames = mStyle->
symbolNames();
301 const int newNameIndex = newSymbolNames.indexOf( name );
302 if ( newNameIndex < 0 )
305 beginInsertRows( QModelIndex(), newNameIndex, newNameIndex );
306 mSymbolNames = newSymbolNames;
310 void QgsStyleModel::onSymbolRemoved(
const QString &name )
312 mSymbolIconCache.remove( name );
313 const QStringList oldSymbolNames = mSymbolNames;
314 const QStringList newSymbolNames = mStyle->
symbolNames();
317 const int oldNameIndex = oldSymbolNames.indexOf( name );
318 if ( oldNameIndex < 0 )
321 beginRemoveRows( QModelIndex(), oldNameIndex, oldNameIndex );
322 mSymbolNames = newSymbolNames;
326 void QgsStyleModel::onSymbolChanged(
const QString &name )
328 mSymbolIconCache.remove( name );
330 QModelIndex i =
index( mSymbolNames.indexOf( name ),
Tags );
331 emit dataChanged( i, i, QVector< int >() << Qt::DecorationRole );
334 void QgsStyleModel::onSymbolRename(
const QString &oldName,
const QString &newName )
336 mSymbolIconCache.remove( oldName );
337 const QStringList oldSymbolNames = mSymbolNames;
338 const QStringList newSymbolNames = mStyle->
symbolNames();
341 const int oldNameIndex = oldSymbolNames.indexOf( oldName );
342 if ( oldNameIndex < 0 )
346 const int newNameIndex = newSymbolNames.indexOf( newName );
347 if ( newNameIndex < 0 )
350 if ( newNameIndex == oldNameIndex )
352 mSymbolNames = newSymbolNames;
356 beginMoveRows( QModelIndex(), oldNameIndex, oldNameIndex, QModelIndex(), newNameIndex > oldNameIndex ? newNameIndex + 1 : newNameIndex );
357 mSymbolNames = newSymbolNames;
361 void QgsStyleModel::onRampAdded(
const QString &name )
363 mColorRampIconCache.remove( name );
364 const QStringList oldRampNames = mRampNames;
368 const int newNameIndex = newRampNames.indexOf( name );
369 if ( newNameIndex < 0 )
372 beginInsertRows( QModelIndex(), newNameIndex + mSymbolNames.count(), newNameIndex + mSymbolNames.count() );
373 mRampNames = newRampNames;
377 void QgsStyleModel::onRampRemoved(
const QString &name )
379 mColorRampIconCache.remove( name );
380 const QStringList oldRampNames = mRampNames;
384 const int oldNameIndex = oldRampNames.indexOf( name );
385 if ( oldNameIndex < 0 )
388 beginRemoveRows( QModelIndex(), oldNameIndex + mSymbolNames.count(), oldNameIndex + mSymbolNames.count() );
389 mRampNames = newRampNames;
393 void QgsStyleModel::onRampChanged(
const QString &name )
395 mColorRampIconCache.remove( name );
397 QModelIndex i =
index( mSymbolNames.count() + mRampNames.indexOf( name ),
Tags );
398 emit dataChanged( i, i, QVector< int >() << Qt::DecorationRole );
401 void QgsStyleModel::onRampRename(
const QString &oldName,
const QString &newName )
403 mColorRampIconCache.remove( oldName );
404 const QStringList oldRampNames = mRampNames;
408 const int oldNameIndex = oldRampNames.indexOf( oldName );
409 if ( oldNameIndex < 0 )
413 const int newNameIndex = newRampNames.indexOf( newName );
414 if ( newNameIndex < 0 )
417 if ( newNameIndex == oldNameIndex )
419 mRampNames = newRampNames;
423 beginMoveRows( QModelIndex(), oldNameIndex + mSymbolNames.count(), oldNameIndex + mSymbolNames.count(),
424 QModelIndex(), ( newNameIndex > oldNameIndex ? newNameIndex + 1 : newNameIndex ) + mSymbolNames.count() );
425 mRampNames = newRampNames;
429 void QgsStyleModel::onTagsChanged(
int entity,
const QString &name,
const QStringList & )
434 i =
index( mSymbolNames.indexOf( name ),
Tags );
438 i =
index( mSymbolNames.count() + mRampNames.indexOf( name ),
Tags );
440 emit dataChanged( i, i );
443 void QgsStyleModel::rebuildSymbolIcons()
445 mSymbolIconCache.clear();
446 emit dataChanged(
index( 0, 0 ),
index( mSymbolNames.count() - 1, 0 ), QVector<int>() << Qt::DecorationRole );
454 : QSortFilterProxyModel( parent )
458 setSortCaseSensitivity( Qt::CaseInsensitive );
460 setSourceModel( mModel );
461 setDynamicSortFilter(
true );
469 if ( mSmartGroupId >= 0 )
476 if ( mFavoritesOnly )
482 if ( mSmartGroupId >= 0 )
487 if ( mSmartGroupId >= 0 )
494 if ( mFilterString.isEmpty() && !mEntityFilterEnabled && !mSymbolTypeFilterEnabled && mTagId < 0 && mSmartGroupId < 0 && !mFavoritesOnly )
497 QModelIndex index = sourceModel()->index( source_row, 0, source_parent );
498 const QString name = sourceModel()->data( index ).toString();
502 if ( mEntityFilterEnabled && styleEntityType != mEntityFilter )
506 if ( mSymbolTypeFilterEnabled && symbolType != mSymbolType )
509 if ( mTagId >= 0 && !mTaggedSymbolNames.contains( name ) )
512 if ( mSmartGroupId >= 0 && !mSmartGroupSymbolNames.contains( name ) )
515 if ( mFavoritesOnly && !mFavoritedSymbolNames.contains( name ) )
518 if ( !mFilterString.isEmpty() )
522 const QStringList partsToMatch = mFilterString.trimmed().split(
' ' );
524 QStringList partsToSearch = name.split(
' ' );
525 for (
const QString &tag : tags )
527 partsToSearch.append( tag.split(
' ' ) );
530 for (
const QString &part : partsToMatch )
533 for (
const QString &partToSearch : qgis::as_const( partsToSearch ) )
535 if ( partToSearch.contains( part, Qt::CaseInsensitive ) )
551 mFilterString = filter;
557 return mFavoritesOnly;
564 if ( mFavoritesOnly )
571 mFavoritedSymbolNames.clear();
583 return mSymbolTypeFilterEnabled;
603 mTaggedSymbolNames.clear();
618 if ( mSmartGroupId >= 0 )
625 mSmartGroupSymbolNames.clear();
633 return mSmartGroupId;
649 return mEntityFilterEnabled;
660 return mEntityFilter;
A QAbstractItemModel subclass for showing symbol and color ramp entities contained within a QgsStyle ...
static QgsSvgCache * svgCache()
Returns the application's SVG cache, used for caching SVG images and handling parameter replacement w...
static QPixmap symbolPreviewPixmap(QgsSymbol *symbol, QSize size, int padding=0, QgsRenderContext *customContext=nullptr)
Returns a pixmap preview for a color ramp.
int rowCount(const QModelIndex &parent=QModelIndex()) const override
void setFilterString(const QString &filter)
Sets a filter string, such that only symbol entities with names matching the specified string will be...
void symbolSaved(const QString &name, QgsSymbol *symbol)
Emitted every time a new symbol has been added to the database.
void setSmartGroupId(int id)
Sets a smart group id to filter style entities by.
Abstract base class for all rendered symbols.
QgsSymbol::SymbolType symbolType() const
Returns the symbol type filter.
static const double UI_SCALE_FACTOR
UI scaling factor.
void entityTagsChanged(QgsStyle::StyleEntity entity, const QString &name, const QStringList &newTags)
Emitted whenever an entity's tags are changed.
QgsColorRamp * colorRamp(const QString &name) const
Returns a new copy of the specified color ramp.
QgsStyleModel(QgsStyle *style, QObject *parent=nullptr)
Constructor for QgsStyleModel, for the specified style and parent object.
void setTagId(int id)
Sets a tag id to filter style entities by.
QStringList tagsOfSymbol(StyleEntity type, const QString &symbol)
Returns the tags associated with the symbol.
int columnCount(const QModelIndex &parent=QModelIndex()) const override
const QgsSymbol * symbolRef(const QString &name) const
Returns a const pointer to a symbol (doesn't create new instance)
void setSymbolType(QgsSymbol::SymbolType type)
Sets the symbol type filter.
void rampChanged(const QString &name)
Emitted whenever a color ramp's definition is changed.
QStringList symbolsWithTag(StyleEntity type, int tagid) const
Returns the symbol names with which have the given tag.
void setFavoritesOnly(bool favoritesOnly)
Sets whether the model should show only favorited entities.
void rampAdded(const QString &name)
Emitted whenever a color ramp has been added to the style and the database has been updated as a resu...
bool filterAcceptsRow(int source_row, const QModelIndex &source_parent) const override
QModelIndex parent(const QModelIndex &index) const override
StyleEntity
Enum for Entities involved in a style.
void setSymbolTypeFilterEnabled(bool enabled)
Sets whether filtering by symbol type is enabled.
SymbolType
Type of the symbol.
int symbolCount()
Returns count of symbols in style.
QgsStyle::StyleEntity entityFilter() const
Returns the style entity type filter.
void setEntityFilterEnabled(bool enabled)
Sets whether filtering by entity type is enabled.
bool renameSymbol(const QString &oldName, const QString &newName)
Renames a symbol from oldName to newName.
const double ICON_PADDING_FACTOR
void addDesiredIconSize(QSize size)
Adds an additional icon size to generate for Qt::DecorationRole data.
void rampRemoved(const QString &name)
Emitted whenever a color ramp has been removed from the style and the database has been updated as a ...
bool setData(const QModelIndex &index, const QVariant &value, int role=Qt::EditRole) override
QStringList symbolNames()
Returns a list of names of symbols.
QModelIndex index(int row, int column, const QModelIndex &parent=QModelIndex()) const override
bool symbolTypeFilterEnabled() const
Returns true if filtering by symbol type is enabled.
QStringList symbolsOfFavorite(StyleEntity type) const
Returns the symbol names which are flagged as favorite.
void symbolRenamed(const QString &oldName, const QString &newName)
Emitted whenever a symbol has been renamed from oldName to newName.
void favoritedChanged(QgsStyle::StyleEntity entity, const QString &name, bool isFavorite)
Emitted whenever an entity is either favorited or un-favorited.
static QPixmap colorRampPreviewPixmap(QgsColorRamp *ramp, QSize size, int padding=0)
Returns a pixmap preview for a color ramp.
QStringList colorRampNames()
Returns a list of names of color ramps.
void symbolRemoved(const QString &name)
Emitted whenever a symbol has been removed from the style and the database has been updated as a resu...
QStringList symbolsOfSmartgroup(StyleEntity type, int id)
Returns the symbols for the smartgroup.
QVariant headerData(int section, Qt::Orientation orientation, int role=Qt::DisplayRole) const override
void addDesiredIconSize(QSize size)
Adds an additional icon size to generate for Qt::DecorationRole data.
void rampRenamed(const QString &oldName, const QString &newName)
Emitted whenever a color ramp has been renamed from oldName to newName.
QgsStyleProxyModel(QgsStyle *style, QObject *parent=nullptr)
Constructor for QgsStyleProxyModel, for the specified style and parent object.
void symbolChanged(const QString &name)
Emitted whenever a symbol's definition is changed.
int tagId() const
Returns the tag id used to filter style entities by.
bool favoritesOnly() const
Returns true if the model is showing only favorited entities.
bool entityFilterEnabled() const
Returns true if filtering by entity type is enabled.
SymbolType type() const
Returns the symbol's type.
bool renameColorRamp(const QString &oldName, const QString &newName)
Changes ramp's name.
void remoteSvgFetched(const QString &url)
Emitted when the cache has finished retrieving an SVG file from a remote url.
QgsSymbol * symbol(const QString &name)
Returns a NEW copy of symbol.
QVariant data(const QModelIndex &index, int role) const override
void setEntityFilter(QgsStyle::StyleEntity filter)
Sets the style entity type filter.
Style entity type, see QgsStyle::StyleEntity.
int smartGroupId() const
Returns the smart group id used to filter style entities by.
Qt::ItemFlags flags(const QModelIndex &index) const override
Symbol type (for symbol entities)