18#include <QImageWriter>
21#include "moc_qgslayoutatlaswidget.cpp"
33 , mAtlas( layout->atlas() )
36 connect( mUseAtlasCheckBox, &QCheckBox::stateChanged,
this, &QgsLayoutAtlasWidget::mUseAtlasCheckBox_stateChanged );
37 connect( mAtlasFilenamePatternEdit, &QLineEdit::editingFinished,
this, &QgsLayoutAtlasWidget::mAtlasFilenamePatternEdit_editingFinished );
38 connect( mAtlasFilenameExpressionButton, &QToolButton::clicked,
this, &QgsLayoutAtlasWidget::mAtlasFilenameExpressionButton_clicked );
39 connect( mAtlasHideCoverageCheckBox, &QCheckBox::stateChanged,
this, &QgsLayoutAtlasWidget::mAtlasHideCoverageCheckBox_stateChanged );
40 connect( mAtlasSingleFileCheckBox, &QCheckBox::stateChanged,
this, &QgsLayoutAtlasWidget::mAtlasSingleFileCheckBox_stateChanged );
41 connect( mAtlasSortFeatureCheckBox, &QCheckBox::stateChanged,
this, &QgsLayoutAtlasWidget::mAtlasSortFeatureCheckBox_stateChanged );
42 connect( mAtlasSortFeatureDirectionButton, &QToolButton::clicked,
this, &QgsLayoutAtlasWidget::mAtlasSortFeatureDirectionButton_clicked );
43 connect( mAtlasFeatureFilterEdit, &QLineEdit::editingFinished,
this, &QgsLayoutAtlasWidget::mAtlasFeatureFilterEdit_editingFinished );
44 connect( mAtlasFeatureFilterButton, &QToolButton::clicked,
this, &QgsLayoutAtlasWidget::mAtlasFeatureFilterButton_clicked );
45 connect( mAtlasFeatureFilterCheckBox, &QCheckBox::stateChanged,
this, &QgsLayoutAtlasWidget::mAtlasFeatureFilterCheckBox_stateChanged );
56 mAtlasSortFeatureDirectionButton->setEnabled(
false );
57 mAtlasSortExpressionWidget->setEnabled(
false );
62 mPageNameWidget->registerExpressionContextGenerator( mLayout );
64 const QList<QByteArray> formats = QImageWriter::supportedImageFormats();
65 for (
int i = 0; i < formats.size(); ++i )
67 mAtlasFileFormat->addItem( QString( formats.at( i ) ) );
69 connect( mAtlasFileFormat, qOverload<int>( &QComboBox::currentIndexChanged ),
this, [ = ](
int ) { changeFileFormat(); } );
79void QgsLayoutAtlasWidget::mUseAtlasCheckBox_stateChanged(
int state )
81 if ( state == Qt::Checked )
84 mConfigurationGroup->setEnabled(
true );
85 mOutputGroup->setEnabled(
true );
90 mConfigurationGroup->setEnabled(
false );
91 mOutputGroup->setEnabled(
false );
95void QgsLayoutAtlasWidget::changeCoverageLayer(
QgsMapLayer *layer )
103 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Layer" ) );
104 mLayout->reportContext().setLayer( vl );
112 updateAtlasFeatures();
118 if ( exp.prepare( &context ) && !exp.hasParserError() )
127 mLayout->undoStack()->endCommand();
130void QgsLayoutAtlasWidget::mAtlasFilenamePatternEdit_editingFinished()
136 mBlockUpdates =
true;
137 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Filename" ) );
142 tr(
"Could not set filename expression to '%1'.\nParser error:\n%2" )
143 .arg( mAtlasFilenamePatternEdit->text(),
146 mLayout->undoStack()->endCommand();
147 mBlockUpdates =
false;
150void QgsLayoutAtlasWidget::mAtlasFilenameExpressionButton_clicked()
159 exprDlg.setWindowTitle( tr(
"Expression Based Filename" ) );
161 if ( exprDlg.exec() == QDialog::Accepted )
163 const QString expression = exprDlg.expressionText();
164 if ( !expression.isEmpty() )
167 mAtlasFilenamePatternEdit->setText( expression );
169 mBlockUpdates =
true;
170 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Filename" ) );
174 mMessageBar->
pushWarning( tr(
"Atlas" ), tr(
"Could not set filename expression to '%1'.\nParser error:\n%2" )
178 mBlockUpdates =
false;
179 mLayout->undoStack()->endCommand();
184void QgsLayoutAtlasWidget::mAtlasHideCoverageCheckBox_stateChanged(
int state )
189 mBlockUpdates =
true;
190 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Toggle Atlas Layer" ) );
192 mLayout->undoStack()->endCommand();
193 mBlockUpdates =
false;
196void QgsLayoutAtlasWidget::mAtlasSingleFileCheckBox_stateChanged(
int state )
201 if ( state == Qt::Checked )
203 mAtlasFilenamePatternEdit->setEnabled(
false );
204 mAtlasFilenameExpressionButton->setEnabled(
false );
208 mAtlasFilenamePatternEdit->setEnabled(
true );
209 mAtlasFilenameExpressionButton->setEnabled(
true );
212 mLayout->setCustomProperty( QStringLiteral(
"singleFile" ), state == Qt::Checked );
215void QgsLayoutAtlasWidget::mAtlasSortFeatureCheckBox_stateChanged(
int state )
220 if ( state == Qt::Checked )
222 mAtlasSortFeatureDirectionButton->setEnabled(
true );
223 mAtlasSortExpressionWidget->setEnabled(
true );
227 mAtlasSortFeatureDirectionButton->setEnabled(
false );
228 mAtlasSortExpressionWidget->setEnabled(
false );
230 mBlockUpdates =
true;
231 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Toggle Atlas Sorting" ) );
233 mLayout->undoStack()->endCommand();
234 mBlockUpdates =
false;
235 updateAtlasFeatures();
238void QgsLayoutAtlasWidget::changesSortFeatureExpression(
const QString &expression,
bool )
243 mBlockUpdates =
true;
244 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Sort" ) );
245 QgsVectorLayer *vlayer = qobject_cast<QgsVectorLayer *>( mAtlasCoverageLayerComboBox->currentLayer() );
247 mLayout->undoStack()->endCommand();
248 mBlockUpdates =
false;
249 updateAtlasFeatures();
252void QgsLayoutAtlasWidget::updateAtlasFeatures()
257 mMessageBar->
pushInfo( tr(
"Atlas" ),
258 tr(
"No matching atlas features found!" ) );
265void QgsLayoutAtlasWidget::mAtlasFeatureFilterCheckBox_stateChanged(
int state )
270 if ( state == Qt::Checked )
272 mAtlasFeatureFilterEdit->setEnabled(
true );
273 mAtlasFeatureFilterButton->setEnabled(
true );
277 mAtlasFeatureFilterEdit->setEnabled(
false );
278 mAtlasFeatureFilterButton->setEnabled(
false );
280 mBlockUpdates =
true;
281 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Filter" ) );
283 mLayout->undoStack()->endCommand();
284 mBlockUpdates =
false;
285 updateAtlasFeatures();
288void QgsLayoutAtlasWidget::pageNameExpressionChanged(
const QString &,
bool valid )
293 const QString expression = mPageNameWidget->asExpression();
294 if ( !valid && !expression.isEmpty() )
299 mBlockUpdates =
true;
300 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Name" ) );
302 mLayout->undoStack()->endCommand();
303 mBlockUpdates =
false;
306void QgsLayoutAtlasWidget::mAtlasFeatureFilterEdit_editingFinished()
312 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Filter" ) );
314 mBlockUpdates =
true;
318 mMessageBar->
pushWarning( tr(
"Atlas" ), tr(
"Could not set filter expression to '%1'.\nParser error:\n%2" )
319 .arg( mAtlasFeatureFilterEdit->text(),
322 mBlockUpdates =
false;
323 mLayout->undoStack()->endCommand();
324 updateAtlasFeatures();
327void QgsLayoutAtlasWidget::mAtlasFeatureFilterButton_clicked()
332 QgsVectorLayer *vl = qobject_cast<QgsVectorLayer *>( mAtlasCoverageLayerComboBox->currentLayer() );
341 exprDlg.setWindowTitle( tr(
"Expression Based Filter" ) );
343 if ( exprDlg.exec() == QDialog::Accepted )
345 const QString expression = exprDlg.expressionText();
346 if ( !expression.isEmpty() )
348 mAtlasFeatureFilterEdit->setText( expression );
350 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Filter" ) );
351 mBlockUpdates =
true;
356 tr(
"Could not set filter expression to '%1'.\nParser error:\n%2" )
357 .arg( mAtlasFeatureFilterEdit->text(),
361 mBlockUpdates =
false;
362 mLayout->undoStack()->endCommand();
363 updateAtlasFeatures();
368void QgsLayoutAtlasWidget::mAtlasSortFeatureDirectionButton_clicked()
373 Qt::ArrowType at = mAtlasSortFeatureDirectionButton->arrowType();
374 at = ( at == Qt::UpArrow ) ? Qt::DownArrow : Qt::UpArrow;
375 mAtlasSortFeatureDirectionButton->setArrowType( at );
377 mBlockUpdates =
true;
378 mLayout->undoStack()->beginCommand( mAtlas, tr(
"Change Atlas Sort" ) );
380 mLayout->undoStack()->endCommand();
381 mBlockUpdates =
false;
382 updateAtlasFeatures();
385void QgsLayoutAtlasWidget::changeFileFormat()
390 mLayout->setCustomProperty( QStringLiteral(
"atlasRasterFormat" ), mAtlasFileFormat->currentText() );
393void QgsLayoutAtlasWidget::updateGuiElements()
398 blockAllSignals(
true );
399 mUseAtlasCheckBox->setCheckState( mAtlas->
enabled() ? Qt::Checked : Qt::Unchecked );
400 mConfigurationGroup->setEnabled( mAtlas->
enabled() );
401 mOutputGroup->setEnabled( mAtlas->
enabled() );
403 mAtlasCoverageLayerComboBox->setLayer( mAtlas->
coverageLayer() );
407 mAtlasSortExpressionWidget->setLayer( mAtlas->
coverageLayer() );
411 mAtlasHideCoverageCheckBox->setCheckState( mAtlas->
hideCoverage() ? Qt::Checked : Qt::Unchecked );
413 const bool singleFile = mLayout->customProperty( QStringLiteral(
"singleFile" ) ).toBool();
414 mAtlasSingleFileCheckBox->setCheckState( singleFile ? Qt::Checked : Qt::Unchecked );
415 mAtlasFilenamePatternEdit->setEnabled( !singleFile );
416 mAtlasFilenameExpressionButton->setEnabled( !singleFile );
418 mAtlasSortFeatureCheckBox->setCheckState( mAtlas->
sortFeatures() ? Qt::Checked : Qt::Unchecked );
419 mAtlasSortFeatureDirectionButton->setEnabled( mAtlas->
sortFeatures() );
420 mAtlasSortExpressionWidget->setEnabled( mAtlas->
sortFeatures() );
422 mAtlasSortFeatureDirectionButton->setArrowType( mAtlas->
sortAscending() ? Qt::UpArrow : Qt::DownArrow );
425 mAtlasFeatureFilterCheckBox->setCheckState( mAtlas->
filterFeatures() ? Qt::Checked : Qt::Unchecked );
427 mAtlasFeatureFilterButton->setEnabled( mAtlas->
filterFeatures() );
429 mAtlasFileFormat->setCurrentIndex( mAtlasFileFormat->findText( mLayout->customProperty( QStringLiteral(
"atlasRasterFormat" ), QStringLiteral(
"png" ) ).toString() ) );
431 blockAllSignals(
false );
434void QgsLayoutAtlasWidget::blockAllSignals(
bool b )
436 mUseAtlasCheckBox->blockSignals( b );
437 mConfigurationGroup->blockSignals( b );
438 mOutputGroup->blockSignals( b );
439 mAtlasCoverageLayerComboBox->blockSignals( b );
440 mPageNameWidget->blockSignals( b );
441 mAtlasSortExpressionWidget->blockSignals( b );
442 mAtlasFilenamePatternEdit->blockSignals( b );
443 mAtlasHideCoverageCheckBox->blockSignals( b );
444 mAtlasSingleFileCheckBox->blockSignals( b );
445 mAtlasSortFeatureCheckBox->blockSignals( b );
446 mAtlasSortFeatureDirectionButton->blockSignals( b );
447 mAtlasFeatureFilterEdit->blockSignals( b );
448 mAtlasFeatureFilterCheckBox->blockSignals( b );
A generic dialog for building expression strings.
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...
Class for parsing and evaluation of expressions (formerly called "search strings").
static QString quoteFieldExpression(const QString &expression, const QgsVectorLayer *layer)
Validate if the expression is a field in the layer and ensure it is quoted.
QString sortExpression() const
Returns the expression (or field name) to use for sorting features.
bool filterFeatures() const
Returns true if features should be filtered in the coverage layer.
QString filenameExpression() const
Returns the filename expression used for generating output filenames for each atlas page.
bool sortAscending() const
Returns true if features should be sorted in an ascending order.
void setCoverageLayer(QgsVectorLayer *layer)
Sets the coverage layer to use for the atlas features.
bool setFilterExpression(const QString &expression, QString &errorString)
Sets the expression used for filtering features in the coverage layer.
void setSortAscending(bool ascending)
Sets whether features should be sorted in an ascending order.
bool hideCoverage() const
Returns true if the atlas is set to hide the coverage layer.
void setEnabled(bool enabled)
Sets whether the atlas is enabled.
void setPageNameExpression(const QString &expression)
Sets the expression (or field name) used for calculating the page name.
QString filterExpression() const
Returns the expression used for filtering features in the coverage layer.
bool enabled() const
Returns whether the atlas generation is enabled.
bool setFilenameExpression(const QString &expression, QString &errorString)
Sets the filename expression used for generating output filenames for each atlas page.
void setSortFeatures(bool enabled)
Sets whether features should be sorted in the atlas.
QString pageNameExpression() const
Returns the expression (or field name) used for calculating the page name.
void setSortExpression(const QString &expression)
Sets the expression (or field name) to use for sorting features.
void setFilterFeatures(bool filtered)
Sets whether features should be filtered in the coverage layer.
QgsVectorLayer * coverageLayer() const
Returns the coverage layer used for the atlas features.
void changed()
Emitted when one of the atlas parameters changes.
int updateFeatures()
Requeries the current atlas coverage layer and applies filtering and sorting.
bool sortFeatures() const
Returns true if features should be sorted in the atlas.
void setHideCoverage(bool hide)
Sets whether the coverage layer should be hidden in map items in the layouts.
void layerChanged(QgsMapLayer *layer)
Emitted whenever the currently selected layer changes.
Base class for all map layer types.
A bar for displaying non-blocking messages to the user.
void pushInfo(const QString &title, const QString &message)
Pushes a information message with default timeout to the message bar.
void pushWarning(const QString &title, const QString &message)
Pushes a warning message that must be manually dismissed by the user.
Print layout, a QgsLayout subclass for static or atlas-based layouts.
Represents a vector layer which manages a vector based data sets.
QString displayExpression