QGIS API Documentation 3.99.0-Master (2fe06baccd8)
Loading...
Searching...
No Matches
qgspointclusterrendererwidget.cpp
Go to the documentation of this file.
1/***************************************************************************
2 qgspointclusterrendererwidget.cpp
3 ---------------------------------
4 begin : February 2016
5 copyright : (C) 2016 by Nyall Dawson
6 email : nyall dot dawson at gmail dot com
7 ***************************************************************************/
8
9/***************************************************************************
10 * *
11 * This program is free software; you can redistribute it and/or modify *
12 * it under the terms of the GNU General Public License as published by *
13 * the Free Software Foundation; either version 2 of the License, or *
14 * (at your option) any later version. *
15 * *
16 ***************************************************************************/
17
19
20#include "qgsapplication.h"
21#include "qgsmarkersymbol.h"
23#include "qgsrendererregistry.h"
24#include "qgsstyle.h"
26#include "qgsvectorlayer.h"
27
28#include "moc_qgspointclusterrendererwidget.cpp"
29
34
36 : QgsRendererWidget( layer, style )
37
38{
39 if ( !layer )
40 {
41 return;
42 }
43
44 //the renderer only applies to point vector layers
46 {
47 //setup blank dialog
48 mRenderer = nullptr;
49 setupBlankUi( layer->name() );
50 return;
51 }
52 setupUi( this );
53 connect( mRendererComboBox, static_cast<void ( QComboBox::* )( int )>( &QComboBox::currentIndexChanged ), this, &QgsPointClusterRendererWidget::mRendererComboBox_currentIndexChanged );
54 connect( mDistanceSpinBox, static_cast<void ( QDoubleSpinBox::* )( double )>( &QDoubleSpinBox::valueChanged ), this, &QgsPointClusterRendererWidget::mDistanceSpinBox_valueChanged );
55 connect( mDistanceUnitWidget, &QgsUnitSelectionWidget::changed, this, &QgsPointClusterRendererWidget::mDistanceUnitWidget_changed );
56 connect( mRendererSettingsButton, &QPushButton::clicked, this, &QgsPointClusterRendererWidget::mRendererSettingsButton_clicked );
57 this->layout()->setContentsMargins( 0, 0, 0, 0 );
58
60
61 mCenterSymbolToolButton->setSymbolType( Qgis::SymbolType::Marker );
62
63 if ( renderer )
64 {
66 }
67 if ( !mRenderer )
68 {
69 mRenderer = std::make_unique<QgsPointClusterRenderer>();
70 if ( renderer )
71 renderer->copyRendererData( mRenderer.get() );
72 }
73
74 blockAllSignals( true );
75
76 //insert possible renderer types
78 QStringList::const_iterator it = rendererList.constBegin();
79 for ( ; it != rendererList.constEnd(); ++it )
80 {
81 if ( *it != QLatin1String( "pointDisplacement" ) && *it != QLatin1String( "pointCluster" ) && *it != QLatin1String( "heatmapRenderer" ) )
82 {
84 mRendererComboBox->addItem( m->icon(), m->visibleName(), *it );
85 }
86 }
87
88 mDistanceSpinBox->setValue( mRenderer->tolerance() );
89 mDistanceUnitWidget->setUnit( mRenderer->toleranceUnit() );
90 mDistanceUnitWidget->setMapUnitScale( mRenderer->toleranceMapUnitScale() );
91 mCenterSymbolToolButton->setSymbol( mRenderer->clusterSymbol()->clone() );
92
93 blockAllSignals( false );
94
95 //set the appropriate renderer dialog
96 if ( mRenderer->embeddedRenderer() )
97 {
98 const QString rendererName = mRenderer->embeddedRenderer()->type();
99 const int rendererIndex = mRendererComboBox->findData( rendererName );
100 if ( rendererIndex != -1 )
101 {
102 mRendererComboBox->setCurrentIndex( rendererIndex );
103 mRendererComboBox_currentIndexChanged( rendererIndex );
104 }
105 }
106
107 connect( mCenterSymbolToolButton, &QgsSymbolButton::changed, this, &QgsPointClusterRendererWidget::centerSymbolChanged );
108 mCenterSymbolToolButton->setDialogTitle( tr( "Cluster symbol" ) );
109 mCenterSymbolToolButton->setLayer( mLayer );
110 mCenterSymbolToolButton->registerExpressionContextGenerator( this );
111}
112
114
116{
117 return mRenderer.get();
118}
119
121{
123 if ( mDistanceUnitWidget )
124 mDistanceUnitWidget->setMapCanvas( context.mapCanvas() );
125 if ( mCenterSymbolToolButton )
126 {
127 mCenterSymbolToolButton->setMapCanvas( context.mapCanvas() );
128 mCenterSymbolToolButton->setMessageBar( context.messageBar() );
129 }
130}
131
132void QgsPointClusterRendererWidget::mRendererComboBox_currentIndexChanged( int index )
133{
134 const QString rendererId = mRendererComboBox->itemData( index ).toString();
136 if ( m )
137 {
138 // unfortunately renderer conversion is only available through the creation of a widget...
139 const std::unique_ptr<QgsFeatureRenderer> oldRenderer( mRenderer->embeddedRenderer()->clone() );
140 QgsRendererWidget *tempRenderWidget = m->createRendererWidget( mLayer, mStyle, oldRenderer.get() );
141 mRenderer->setEmbeddedRenderer( tempRenderWidget->renderer()->clone() );
142 delete tempRenderWidget;
143 }
144 emit widgetChanged();
145}
146
147void QgsPointClusterRendererWidget::mRendererSettingsButton_clicked()
148{
149 if ( !mRenderer )
150 return;
151
152 QgsRendererAbstractMetadata *m = QgsApplication::rendererRegistry()->rendererMetadata( mRenderer->embeddedRenderer()->type() );
153 if ( m )
154 {
155 QgsRendererWidget *w = m->createRendererWidget( mLayer, mStyle, mRenderer->embeddedRenderer()->clone() );
156 w->setPanelTitle( tr( "Renderer Settings" ) );
157
158 QgsExpressionContextScope scope;
159 scope.addVariable( QgsExpressionContextScope::StaticVariable( QgsExpressionContext::EXPR_CLUSTER_COLOR, "", true ) );
160 scope.addVariable( QgsExpressionContextScope::StaticVariable( QgsExpressionContext::EXPR_CLUSTER_SIZE, 0, true ) );
161 QList<QgsExpressionContextScope> scopes = mContext.additionalExpressionContextScopes();
162 scopes << scope;
163 QgsSymbolWidgetContext context = mContext;
164 context.setAdditionalExpressionContextScopes( scopes );
165 w->setContext( context );
167 connect( w, &QgsPanelWidget::widgetChanged, this, &QgsPointClusterRendererWidget::updateRendererFromWidget );
168 w->setDockMode( this->dockMode() );
169 openPanel( w );
170 }
171}
172
173void QgsPointClusterRendererWidget::mDistanceSpinBox_valueChanged( double d )
174{
175 if ( mRenderer )
176 {
177 mRenderer->setTolerance( d );
178 }
179 emit widgetChanged();
180}
181
182void QgsPointClusterRendererWidget::mDistanceUnitWidget_changed()
183{
184 if ( mRenderer )
185 {
186 mRenderer->setToleranceUnit( mDistanceUnitWidget->unit() );
187 mRenderer->setToleranceMapUnitScale( mDistanceUnitWidget->getMapUnitScale() );
188 }
189 emit widgetChanged();
190}
191
192void QgsPointClusterRendererWidget::blockAllSignals( bool block )
193{
194 mRendererComboBox->blockSignals( block );
195 mCenterSymbolToolButton->blockSignals( block );
196 mDistanceSpinBox->blockSignals( block );
197 mDistanceUnitWidget->blockSignals( block );
198}
199
201{
203 if ( auto *lExpressionContext = mContext.expressionContext() )
204 context = *lExpressionContext;
205 else
206 context.appendScopes( mContext.globalProjectAtlasMapLayerScopes( mLayer ) );
210 QList<QgsExpressionContextScope> scopes = mContext.additionalExpressionContextScopes();
211 scopes << scope;
212 const auto constScopes = scopes;
213 for ( const QgsExpressionContextScope &s : constScopes )
214 {
216 }
218 return context;
219}
220
221void QgsPointClusterRendererWidget::centerSymbolChanged()
222{
223 mRenderer->setClusterSymbol( mCenterSymbolToolButton->clonedSymbol<QgsMarkerSymbol>() );
224 emit widgetChanged();
225}
226
227void QgsPointClusterRendererWidget::updateRendererFromWidget()
228{
229 QgsRendererWidget *w = qobject_cast<QgsRendererWidget *>( sender() );
230 if ( !w )
231 return;
232
233 mRenderer->setEmbeddedRenderer( w->renderer()->clone() );
234 emit widgetChanged();
235}
236
237void QgsPointClusterRendererWidget::setupBlankUi( const QString &layerName )
238{
239 QGridLayout *layout = new QGridLayout( this );
240 QLabel *label = new QLabel( tr( "The point cluster renderer only applies to (single) point layers. \n'%1' is not a (single) point layer and cannot be displayed by the point cluster renderer." ).arg( layerName ), this );
241 layout->addWidget( label );
242}
@ Point
Points.
Definition qgis.h:359
@ Millimeters
Millimeters.
Definition qgis.h:5184
@ Points
Points (e.g., for font sizes).
Definition qgis.h:5188
@ MapUnits
Map units.
Definition qgis.h:5185
@ Pixels
Pixels.
Definition qgis.h:5186
@ Inches
Inches.
Definition qgis.h:5189
@ MetersInMapUnits
Meters value as Map units.
Definition qgis.h:5191
@ Marker
Marker symbol.
Definition qgis.h:611
static QgsRendererRegistry * rendererRegistry()
Returns the application's renderer registry, used for managing vector layer renderers.
Single scope for storing variables and functions for use within a QgsExpressionContext.
void addVariable(const QgsExpressionContextScope::StaticVariable &variable)
Adds a variable into the context scope.
Expression contexts are used to encapsulate the parameters around which a QgsExpression should be eva...
static const QString EXPR_CLUSTER_SIZE
Inbuilt variable name for cluster size variable.
static const QString EXPR_CLUSTER_COLOR
Inbuilt variable name for cluster color variable.
Abstract base class for all 2D vector feature renderers.
virtual QgsFeatureRenderer * clone() const =0
Create a deep copy of this renderer.
A marker symbol type, for rendering Point and MultiPoint geometries.
void openPanel(QgsPanelWidget *panel)
Open a panel or dialog depending on dock mode setting If dock mode is true this method will emit the ...
bool dockMode() const
Returns the dock mode state.
void widgetChanged()
Emitted when the widget state changes.
void setPanelTitle(const QString &panelTitle)
Set the title of the panel when shown in the interface.
QgsPointClusterRendererWidget(QgsVectorLayer *layer, QgsStyle *style, QgsFeatureRenderer *renderer)
Constructor for QgsPointClusterRendererWidget.
~QgsPointClusterRendererWidget() override
QgsExpressionContext createExpressionContext() const override
This method needs to be reimplemented in all classes which implement this interface and return an exp...
void setContext(const QgsSymbolWidgetContext &context) override
Sets the context in which the renderer widget is shown, e.g., the associated map canvas and expressio...
QgsFeatureRenderer * renderer() override
Returns pointer to the renderer (no transfer of ownership).
static QgsRendererWidget * create(QgsVectorLayer *layer, QgsStyle *style, QgsFeatureRenderer *renderer)
Returns a new QgsPointClusterRendererWidget.
static QgsPointClusterRenderer * convertFromRenderer(const QgsFeatureRenderer *renderer)
Creates a QgsPointClusterRenderer from an existing renderer.
Stores metadata about one renderer class.
@ PointLayer
Compatible with point layers.
QIcon icon() const
Returns an icon representing the renderer.
QString visibleName() const
Returns a friendly display name of the renderer.
virtual QgsRendererWidget * createRendererWidget(QgsVectorLayer *layer, QgsStyle *style, QgsFeatureRenderer *oldRenderer)
Returns new instance of settings widget for the renderer.
QStringList renderersList(QgsRendererAbstractMetadata::LayerTypes layerTypes=QgsRendererAbstractMetadata::All) const
Returns a list of available renderers.
QgsRendererAbstractMetadata * rendererMetadata(const QString &rendererName)
Returns the metadata for a specified renderer.
Base class for renderer settings widgets.
QgsRendererWidget(QgsVectorLayer *layer, QgsStyle *style)
void setDockMode(bool dockMode) override
Set the widget in dock mode which tells the widget to emit panel widgets and not open dialogs.
QgsSymbolWidgetContext mContext
Context in which widget is shown.
virtual void setContext(const QgsSymbolWidgetContext &context)
Sets the context in which the renderer widget is shown, e.g., the associated map canvas and expressio...
virtual QgsFeatureRenderer * renderer()=0
Returns pointer to the renderer (no transfer of ownership).
virtual void disableSymbolLevels()
Disables symbol level modification on the widget.
QgsSymbolWidgetContext context() const
Returns the context in which the renderer widget is shown, e.g., the associated map canvas and expres...
QgsVectorLayer * mLayer
A database of saved style entities, including symbols, color ramps, text formats and others.
Definition qgsstyle.h:88
void changed()
Emitted when the symbol's settings are changed.
Contains settings which reflect the context in which a symbol (or renderer) widget is shown,...
void changed()
Emitted when the selected unit is changed, or the definition of the map unit scale is changed.
Represents a vector layer which manages a vector based dataset.
Q_INVOKABLE Qgis::WkbType wkbType() const final
Returns the WKBType or WKBUnknown in case of error.
static Qgis::GeometryType geometryType(Qgis::WkbType type)
Returns the geometry type for a WKB type, e.g., both MultiPolygon and CurvePolygon would have a Polyg...
Single variable definition for use within a QgsExpressionContextScope.