QGIS API Documentation  3.24.2-Tisler (13c1a02865)
qgsmeshrendererscalarsettingswidget.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsmeshrendererscalarsettingswidget.cpp
3  ---------------------------------------
4  begin : June 2018
5  copyright : (C) 2018 by Peter Petrik
6  email : zilolv at gmail dot 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 
17 
18 #include "QDialogButtonBox"
19 
20 #include "qgis.h"
21 #include "qgsmeshlayer.h"
22 #include "qgsmeshlayerutils.h"
23 #include "qgsmessagelog.h"
25 #include "qgssettings.h"
26 #include <QPointer>
27 
29  : QWidget( parent )
30 
31 {
32  setupUi( this );
33 
34  mScalarMinSpinBox->setClearValueMode( QgsDoubleSpinBox::ClearValueMode::MinimumValue );
35  mScalarMinSpinBox->setSpecialValueText( QString( ) );
36  mScalarMaxSpinBox->setClearValueMode( QgsDoubleSpinBox::ClearValueMode::MinimumValue );
37  mScalarMaxSpinBox->setSpecialValueText( QString( ) );
38 
39  // add items to data interpolation combo box
40  mScalarInterpolationTypeComboBox->addItem( tr( "None" ), QgsMeshRendererScalarSettings::None );
41  mScalarInterpolationTypeComboBox->addItem( tr( "Neighbour Average" ), QgsMeshRendererScalarSettings::NeighbourAverage );
42  mScalarInterpolationTypeComboBox->setCurrentIndex( 0 );
43 
44  mScalarEdgeStrokeWidthUnitSelectionWidget->setUnits( QgsUnitTypes::RenderUnitList()
49 
50  // connect
51  connect( mScalarRecalculateMinMaxButton, &QPushButton::clicked, this, &QgsMeshRendererScalarSettingsWidget::recalculateMinMaxButtonClicked );
52  connect( mScalarMinSpinBox, qOverload<double>( &QgsDoubleSpinBox::valueChanged ), this, [ = ]( double ) { minMaxChanged(); } );
53  connect( mScalarMaxSpinBox, qOverload<double>( &QgsDoubleSpinBox::valueChanged ), this, [ = ]( double ) { minMaxChanged(); } );
54  connect( mScalarEdgeStrokeWidthVariableRadioButton, &QRadioButton::toggled, this, &QgsMeshRendererScalarSettingsWidget::onEdgeStrokeWidthMethodChanged );
55 
58  connect( mScalarInterpolationTypeComboBox, qOverload<int>( &QComboBox::currentIndexChanged ), this, &QgsMeshRendererScalarSettingsWidget::widgetChanged );
59 
60  connect( mScalarEdgeStrokeWidthUnitSelectionWidget, &QgsUnitSelectionWidget::changed,
62  connect( mScalarEdgeStrokeWidthSpinBox, qOverload<double>( &QgsDoubleSpinBox::valueChanged ),
64  connect( mScalarEdgeStrokeWidthVariableRadioButton, &QCheckBox::toggled, this, &QgsMeshRendererScalarSettingsWidget::widgetChanged );
65  connect( mScalarEdgeStrokeWidthFixedRadioButton, &QCheckBox::toggled, this, &QgsMeshRendererScalarSettingsWidget::widgetChanged );
66  connect( mScalarEdgeStrokeWidthVariablePushButton, &QgsMeshVariableStrokeWidthButton::widgetChanged, this, &QgsMeshRendererScalarSettingsWidget::widgetChanged );
67 
68 }
69 
71 {
72  mMeshLayer = layer;
73  mScalarInterpolationTypeComboBox->setEnabled( !dataIsDefinedOnEdges() );
74 }
75 
77 {
78  mActiveDatasetGroup = groupIndex;
79  mScalarInterpolationTypeComboBox->setEnabled( !dataIsDefinedOnEdges() );
80 }
81 
83 {
85  settings.setColorRampShader( mScalarColorRampShaderWidget->shader() );
86  settings.setClassificationMinimumMaximum( spinBoxValue( mScalarMinSpinBox ), spinBoxValue( mScalarMaxSpinBox ) );
87  settings.setOpacity( mOpacityWidget->opacity() );
88  settings.setDataResamplingMethod( dataIntepolationMethod() );
89 
90  const bool hasEdges = ( mMeshLayer->contains( QgsMesh::ElementType::Edge ) );
91  if ( hasEdges )
92  {
93 
94  QgsInterpolatedLineWidth edgeStrokeWidth = mScalarEdgeStrokeWidthVariablePushButton->variableStrokeWidth();
95  edgeStrokeWidth.setIsVariableWidth( mScalarEdgeStrokeWidthVariableRadioButton->isChecked() );
96  edgeStrokeWidth.setFixedStrokeWidth( mScalarEdgeStrokeWidthSpinBox->value() );
97  settings.setEdgeStrokeWidth( edgeStrokeWidth );
98  settings.setEdgeStrokeWidthUnit( mScalarEdgeStrokeWidthUnitSelectionWidget->unit() );
99  }
100 
101  return settings;
102 }
103 
105 {
106  if ( !mMeshLayer )
107  return;
108 
109  if ( mActiveDatasetGroup < 0 )
110  return;
111 
112  const QgsMeshRendererSettings rendererSettings = mMeshLayer->rendererSettings();
113  const QgsMeshRendererScalarSettings settings = rendererSettings.scalarSettings( mActiveDatasetGroup );
115  const double min = settings.classificationMinimum();
116  const double max = settings.classificationMaximum();
117 
118  whileBlocking( mScalarMinSpinBox )->setValue( min );
119  whileBlocking( mScalarMaxSpinBox )->setValue( max );
120  whileBlocking( mScalarColorRampShaderWidget )->setFromShader( shader );
121  whileBlocking( mScalarColorRampShaderWidget )->setMinimumMaximum( min, max );
122  whileBlocking( mOpacityWidget )->setOpacity( settings.opacity() );
123  const int index = mScalarInterpolationTypeComboBox->findData( settings.dataResamplingMethod() );
124  whileBlocking( mScalarInterpolationTypeComboBox )->setCurrentIndex( index );
125 
126  const bool hasEdges = ( mMeshLayer->contains( QgsMesh::ElementType::Edge ) );
127  const bool hasFaces = ( mMeshLayer->contains( QgsMesh::ElementType::Face ) );
128 
129  mScalarResamplingWidget->setVisible( hasFaces );
130 
131  mEdgeWidthGroupBox->setVisible( hasEdges );
132 
133  if ( hasEdges )
134  {
135  const QgsInterpolatedLineWidth edgeStrokeWidth = settings.edgeStrokeWidth();
136  whileBlocking( mScalarEdgeStrokeWidthVariablePushButton )->setVariableStrokeWidth( edgeStrokeWidth );
137  whileBlocking( mScalarEdgeStrokeWidthSpinBox )->setValue( edgeStrokeWidth.fixedStrokeWidth() );
138  whileBlocking( mScalarEdgeStrokeWidthVariableRadioButton )->setChecked( edgeStrokeWidth.isVariableWidth() );
139  whileBlocking( mScalarEdgeStrokeWidthUnitSelectionWidget )->setUnit( settings.edgeStrokeWidthUnit() );
140  if ( !hasFaces )
141  mOpacityContainerWidget->setVisible( false );
142 
143  const QgsMeshDatasetGroupMetadata metadata = mMeshLayer->datasetGroupMetadata( mActiveDatasetGroup );
144  const double min = metadata.minimum();
145  const double max = metadata.maximum();
146  mScalarEdgeStrokeWidthVariablePushButton->setDefaultMinMaxValue( min, max );
147  }
148 
149  onEdgeStrokeWidthMethodChanged();
150 }
151 
152 double QgsMeshRendererScalarSettingsWidget::spinBoxValue( const QgsDoubleSpinBox *spinBox ) const
153 {
154  if ( spinBox->value() == spinBox->clearValue() )
155  {
156  return std::numeric_limits<double>::quiet_NaN();
157  }
158 
159  return spinBox->value();
160 }
161 
162 void QgsMeshRendererScalarSettingsWidget::minMaxChanged()
163 {
164  const double min = spinBoxValue( mScalarMinSpinBox );
165  const double max = spinBoxValue( mScalarMaxSpinBox );
166  mScalarColorRampShaderWidget->setMinimumMaximumAndClassify( min, max );
167 }
168 
169 void QgsMeshRendererScalarSettingsWidget::recalculateMinMaxButtonClicked()
170 {
171  const QgsMeshDatasetGroupMetadata metadata = mMeshLayer->datasetGroupMetadata( mActiveDatasetGroup );
172  const double min = metadata.minimum();
173  const double max = metadata.maximum();
174  whileBlocking( mScalarMinSpinBox )->setValue( min );
175  whileBlocking( mScalarMaxSpinBox )->setValue( max );
176  mScalarColorRampShaderWidget->setMinimumMaximumAndClassify( min, max );
177 }
178 
179 void QgsMeshRendererScalarSettingsWidget::onEdgeStrokeWidthMethodChanged()
180 {
181  const bool variableWidth = mScalarEdgeStrokeWidthVariableRadioButton->isChecked();
182  mScalarEdgeStrokeWidthVariablePushButton->setVisible( variableWidth );
183  mScalarEdgeStrokeWidthSpinBox->setVisible( !variableWidth );
184 }
185 
186 QgsMeshRendererScalarSettings::DataResamplingMethod QgsMeshRendererScalarSettingsWidget::dataIntepolationMethod() const
187 {
188  const int data = mScalarInterpolationTypeComboBox->currentData().toInt();
190  return method;
191 }
192 
193 bool QgsMeshRendererScalarSettingsWidget::dataIsDefinedOnFaces() const
194 {
195  if ( !mMeshLayer )
196  return false;
197 
198  if ( mActiveDatasetGroup < 0 )
199  return false;
200 
201  const QgsMeshDatasetGroupMetadata meta = mMeshLayer->datasetGroupMetadata( mActiveDatasetGroup );
202  const bool onFaces = ( meta.dataType() == QgsMeshDatasetGroupMetadata::DataOnFaces );
203  return onFaces;
204 }
205 
206 bool QgsMeshRendererScalarSettingsWidget::dataIsDefinedOnEdges() const
207 {
208  if ( !mMeshLayer )
209  return false;
210 
211  if ( mActiveDatasetGroup < 0 )
212  return false;
213 
214  const QgsMeshDatasetGroupMetadata meta = mMeshLayer->datasetGroupMetadata( mActiveDatasetGroup );
215  const bool onEdges = ( meta.dataType() == QgsMeshDatasetGroupMetadata::DataOnEdges );
216  return onEdges;
217 }
218 
219 
void widgetChanged()
Widget changed.
A ramp shader will color a raster pixel based on a list of values ranges in a ramp.
The QgsSpinBox is a spin box with a clear button that will set the value to the defined clear value.
Represents a width than can vary depending on values.
void setFixedStrokeWidth(double fixedWidth)
Sets the fixed width.
void setIsVariableWidth(bool isVariableWidth)
Returns whether the width is variable.
double fixedStrokeWidth() const
Returns the fixed width.
bool isVariableWidth() const
Returns whether the width is variable.
QgsMeshDatasetGroupMetadata is a collection of dataset group metadata such as whether the data is vec...
DataType dataType() const
Returns whether dataset group data is defined on vertices or faces or volumes.
double minimum() const
Returns minimum scalar value/vector magnitude present for whole dataset group.
double maximum() const
Returns maximum scalar value/vector magnitude present for whole dataset group.
@ DataOnEdges
Data is defined on edges.
@ DataOnFaces
Data is defined on faces.
Represents a mesh layer supporting display of data on structured or unstructured meshes.
Definition: qgsmeshlayer.h:97
bool contains(const QgsMesh::ElementType &type) const
Returns whether the mesh contains at mesh elements of given type.
QgsMeshRendererSettings rendererSettings() const
Returns renderer settings.
QgsMeshDatasetGroupMetadata datasetGroupMetadata(const QgsMeshDatasetIndex &index) const
Returns the dataset groups metadata.
void syncToLayer()
Synchronizes widgets state with associated mesh layer.
void setLayer(QgsMeshLayer *layer)
Associates mesh layer with the widget.
void widgetChanged()
Mesh rendering settings changed.
QgsMeshRendererScalarSettings settings() const
Returns scalar settings.
QgsMeshRendererScalarSettingsWidget(QWidget *parent=nullptr)
A widget to hold the renderer scalar settings for a mesh layer.
void setActiveDatasetGroup(int groupIndex)
Associates a dataset group with the widget (should be set before syncToLayer())
Represents a mesh renderer settings for scalar datasets.
void setClassificationMinimumMaximum(double minimum, double maximum)
Sets min/max values used for creation of the color ramp shader.
double opacity() const
Returns opacity.
void setColorRampShader(const QgsColorRampShader &shader)
Sets color ramp shader function.
QgsColorRampShader colorRampShader() const
Returns color ramp shader function.
double classificationMinimum() const
Returns min value used for creation of the color ramp shader.
void setOpacity(double opacity)
Sets opacity.
DataResamplingMethod
Resampling of value from dataset.
@ NeighbourAverage
Does a simple average of values defined for all surrounding faces/vertices.
DataResamplingMethod dataResamplingMethod() const
Returns the type of interpolation to use to convert face defined datasets to values on vertices.
void setEdgeStrokeWidthUnit(const QgsUnitTypes::RenderUnit &edgeStrokeWidthUnit)
Sets the stroke width unit used to render edges scalar dataset.
void setEdgeStrokeWidth(const QgsInterpolatedLineWidth &strokeWidth)
Sets the stroke width used to render edges scalar dataset.
double classificationMaximum() const
Returns max value used for creation of the color ramp shader.
QgsUnitTypes::RenderUnit edgeStrokeWidthUnit() const
Returns the stroke width unit used to render edges scalar dataset.
QgsInterpolatedLineWidth edgeStrokeWidth() const
Returns the stroke width used to render edges scalar dataset.
void setDataResamplingMethod(const DataResamplingMethod &dataResamplingMethod)
Sets data interpolation method.
Represents all mesh renderer settings.
QgsMeshRendererScalarSettings scalarSettings(int groupIndex) const
Returns renderer settings.
void opacityChanged(double opacity)
Emitted when the opacity is changed in the widget, where opacity ranges from 0.0 (transparent) to 1....
QList< QgsUnitTypes::RenderUnit > RenderUnitList
List of render units.
Definition: qgsunittypes.h:240
@ RenderMetersInMapUnits
Meters value as Map units.
Definition: qgsunittypes.h:176
@ RenderPoints
Points (e.g., for font sizes)
Definition: qgsunittypes.h:173
@ RenderPixels
Pixels.
Definition: qgsunittypes.h:171
@ RenderMillimeters
Millimeters.
Definition: qgsunittypes.h:169
QgsSignalBlocker< Object > whileBlocking(Object *object)
Temporarily blocks signals from a QObject while calling a single method from the object.
Definition: qgis.h:1517