QGIS API Documentation  3.8.0-Zanzibar (11aff65)
qgsmaplayerproxymodel.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsmaplayerproxymodel.cpp
3  --------------------------------------
4  Date : 01.04.2014
5  Copyright : (C) 2014 Denis Rouzaud
6  Email : denis.rouzaud@gmail.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 
16 #include "qgsmaplayerproxymodel.h"
17 #include "qgsmaplayermodel.h"
18 #include "qgsmaplayer.h"
19 #include "qgsproject.h"
20 #include "qgsvectorlayer.h"
21 #include "qgsrasterlayer.h"
22 #include "qgsmeshlayer.h"
23 #include "qgsvectordataprovider.h"
24 #include "qgsrasterdataprovider.h"
25 #include "qgsmeshdataprovider.h"
26 
28  : QSortFilterProxyModel( parent )
29  , mFilters( All )
30  , mModel( new QgsMapLayerModel( parent ) )
31 {
32  setSourceModel( mModel );
33  setDynamicSortFilter( true );
34  setSortLocaleAware( true );
35  setFilterCaseSensitivity( Qt::CaseInsensitive );
36  sort( 0 );
37 }
38 
40 {
41  mFilters = filters;
42  invalidateFilter();
43  return this;
44 }
45 
46 void QgsMapLayerProxyModel::setLayerWhitelist( const QList<QgsMapLayer *> &layers )
47 {
48  if ( mLayerWhitelist == layers )
49  return;
50 
51  mLayerWhitelist = layers;
52  invalidateFilter();
53 }
54 
55 void QgsMapLayerProxyModel::setExceptedLayerList( const QList<QgsMapLayer *> &exceptList )
56 {
57  if ( mExceptList == exceptList )
58  return;
59 
60  mExceptList = exceptList;
61  invalidateFilter();
62 }
63 
64 void QgsMapLayerProxyModel::setExceptedLayerIds( const QStringList &ids )
65 {
66  mExceptList.clear();
67 
68  const auto constIds = ids;
69  for ( const QString &id : constIds )
70  {
72  if ( l )
73  mExceptList << l;
74  }
75  invalidateFilter();
76 }
77 
79 {
80  QStringList lst;
81 
82  const auto constMExceptList = mExceptList;
83  for ( QgsMapLayer *l : constMExceptList )
84  lst << l->id();
85 
86  return lst;
87 }
88 
89 void QgsMapLayerProxyModel::setExcludedProviders( const QStringList &providers )
90 {
91  mExcludedProviders = providers;
92  invalidateFilter();
93 }
94 
96 {
97  if ( !layer )
98  return false;
99 
100  if ( !mLayerWhitelist.isEmpty() && !mLayerWhitelist.contains( layer ) )
101  return false;
102 
103  if ( mExceptList.contains( layer ) )
104  return false;
105 
106  if ( layer->dataProvider() && mExcludedProviders.contains( layer->dataProvider()->name() ) )
107  return false;
108 
109  if ( mFilters.testFlag( WritableLayer ) && layer->readOnly() )
110  return false;
111 
112  if ( !layer->name().contains( mFilterString, Qt::CaseInsensitive ) )
113  return false;
114 
115  // layer type
116  if ( ( mFilters.testFlag( RasterLayer ) && layer->type() == QgsMapLayerType::RasterLayer ) ||
117  ( mFilters.testFlag( VectorLayer ) && layer->type() == QgsMapLayerType::VectorLayer ) ||
118  ( mFilters.testFlag( MeshLayer ) && layer->type() == QgsMapLayerType::MeshLayer ) ||
119  ( mFilters.testFlag( PluginLayer ) && layer->type() == QgsMapLayerType::PluginLayer ) )
120  return true;
121 
122  // geometry type
123  bool detectGeometry = mFilters.testFlag( NoGeometry ) ||
124  mFilters.testFlag( PointLayer ) ||
125  mFilters.testFlag( LineLayer ) ||
126  mFilters.testFlag( PolygonLayer ) ||
127  mFilters.testFlag( HasGeometry );
128  if ( detectGeometry && layer->type() == QgsMapLayerType::VectorLayer )
129  {
130  if ( QgsVectorLayer *vl = qobject_cast< QgsVectorLayer *>( layer ) )
131  {
132  if ( mFilters.testFlag( HasGeometry ) && vl->isSpatial() )
133  return true;
134  if ( mFilters.testFlag( NoGeometry ) && vl->geometryType() == QgsWkbTypes::NullGeometry )
135  return true;
136  if ( mFilters.testFlag( PointLayer ) && vl->geometryType() == QgsWkbTypes::PointGeometry )
137  return true;
138  if ( mFilters.testFlag( LineLayer ) && vl->geometryType() == QgsWkbTypes::LineGeometry )
139  return true;
140  if ( mFilters.testFlag( PolygonLayer ) && vl->geometryType() == QgsWkbTypes::PolygonGeometry )
141  return true;
142  }
143  }
144 
145  return false;
146 }
147 
148 void QgsMapLayerProxyModel::setFilterString( const QString &filter )
149 {
150  mFilterString = filter;
151  invalidateFilter();
152 }
153 
154 bool QgsMapLayerProxyModel::filterAcceptsRow( int source_row, const QModelIndex &source_parent ) const
155 {
156  if ( mFilters.testFlag( All ) && mExceptList.isEmpty() && mLayerWhitelist.isEmpty() && mExcludedProviders.isEmpty() && mFilterString.isEmpty() )
157  return true;
158 
159  QModelIndex index = sourceModel()->index( source_row, 0, source_parent );
160 
161  if ( sourceModel()->data( index, QgsMapLayerModel::EmptyRole ).toBool()
162  || sourceModel()->data( index, QgsMapLayerModel::AdditionalRole ).toBool() )
163  return true;
164 
165  return acceptsLayer( static_cast<QgsMapLayer *>( index.internalPointer() ) );
166 }
167 
168 bool QgsMapLayerProxyModel::lessThan( const QModelIndex &left, const QModelIndex &right ) const
169 {
170  // empty row is always first
171  if ( sourceModel()->data( left, QgsMapLayerModel::EmptyRole ).toBool() )
172  return true;
173  else if ( sourceModel()->data( right, QgsMapLayerModel::EmptyRole ).toBool() )
174  return false;
175 
176  // additional rows are always last
177  bool leftAdditional = sourceModel()->data( left, QgsMapLayerModel::AdditionalRole ).toBool();
178  bool rightAdditional = sourceModel()->data( right, QgsMapLayerModel::AdditionalRole ).toBool();
179 
180  if ( leftAdditional && !rightAdditional )
181  return false;
182  else if ( rightAdditional && !leftAdditional )
183  return true;
184 
185  // default mode is alphabetical order
186  QString leftStr = sourceModel()->data( left ).toString();
187  QString rightStr = sourceModel()->data( right ).toString();
188  return QString::localeAwareCompare( leftStr, rightStr ) < 0;
189 }
QgsMapLayerProxyModel(QObject *parent=nullptr)
QgsMapLayerProxModel creates a proxy model with a QgsMapLayerModel as source model.
Base class for all map layer types.
Definition: qgsmaplayer.h:78
QgsMapLayerType type() const
Returns the type of the layer.
virtual QgsDataProvider * dataProvider()
Returns the layer&#39;s data provider, it may be nullptr.
QStringList exceptedLayerIds() const
Returns the blacklist of layer IDs which are excluded from the model.
void setExceptedLayerIds(const QStringList &ids)
Sets a blacklist of layers (by layer ID) to exclude from the model.
virtual QString name() const =0
Returns a provider name.
bool filterAcceptsRow(int source_row, const QModelIndex &source_parent) const override
True if index corresponds to an additional (non map layer) item.
bool acceptsLayer(QgsMapLayer *layer) const
Returns true if the proxy model accepts the specified map layer.
void setExceptedLayerList(const QList< QgsMapLayer *> &exceptList)
Sets a blacklist of layers to exclude from the model.
The QgsMapLayerModel class is a model to display layers in widgets.
The QgsMapLayerProxyModel class provides an easy to use model to display the list of layers in widget...
bool lessThan(const QModelIndex &left, const QModelIndex &right) const override
void setLayerWhitelist(const QList< QgsMapLayer *> &layers)
Sets a whitelist of layers to include within the model.
void setExcludedProviders(const QStringList &providers)
Sets a blacklist of data providers which should be excluded from the model.
static QgsProject * instance()
Returns the QgsProject singleton instance.
Definition: qgsproject.cpp:438
QgsMapLayerProxyModel * setFilters(QgsMapLayerProxyModel::Filters filters)
Sets filter flags which affect how layers are filtered within the model.
const Filters & filters() const
Returns the filter flags which affect how layers are filtered within the model.
QgsMapLayer * mapLayer(const QString &layerId) const
Retrieve a pointer to a registered layer by layer ID.
bool readOnly() const
Returns if this layer is read only.
Definition: qgsmaplayer.h:458
QString name
Definition: qgsmaplayer.h:82
Represents a vector layer which manages a vector based data sets.
void setFilterString(const QString &filter)
Sets a filter string, such that only layers with names matching the specified string will be shown...
True if index corresponds to the empty (not set) value.