QGIS API Documentation 3.99.0-Master (09f76ad7019)
Loading...
Searching...
No Matches
qgsmaplayersavestyledialog.cpp
Go to the documentation of this file.
1/***************************************************************************
2 qgsmaplayersavestyledialog.h
3 --------------------------------------
4 Date : September 2018
5 Copyright : (C) 2018 by Denis Rouzaud
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 "qgsgui.h"
19#include "qgshelp.h"
22#include "qgssettings.h"
23#include "qgsvectorlayer.h"
24
25#include <QListWidgetItem>
26#include <QMessageBox>
27#include <QPushButton>
28#include <QString>
29
30#include "moc_qgsmaplayersavestyledialog.cpp"
31
32using namespace Qt::StringLiterals;
33
35 : QDialog( parent )
36 , mLayer( layer )
37{
38 setupUi( this );
40
41 QgsSettings settings;
42
43 const QString myLastUsedDir = settings.value( u"style/lastStyleDir"_s, QDir::homePath() ).toString();
44
45 // save style type combobox
46 connect( mStyleTypeComboBox, qOverload<int>( &QComboBox::currentIndexChanged ), this, [this, layer]( int ) {
50 mSaveToDbWidget->setVisible( type == QgsLayerPropertiesDialog::DatasourceDatabase );
51 mSaveToSldWidget->setVisible( type == QgsLayerPropertiesDialog::SLD && layer->type() == Qgis::LayerType::Vector && static_cast<QgsVectorLayer *>( layer )->geometryType() == Qgis::GeometryType::Polygon );
52 mStyleCategoriesListView->setEnabled( type != QgsLayerPropertiesDialog::SLD );
53 mFileWidget->setFilter( type == QgsLayerPropertiesDialog::QML ? tr( "QGIS Layer Style File (*.qml)" ) : tr( "SLD File (*.sld)" ) );
54 updateSaveButtonState();
55 } );
56
57 // Save to DB setup
58 connect( mDbStyleNameEdit, &QLineEdit::textChanged, this, &QgsMapLayerSaveStyleDialog::updateSaveButtonState );
59 mDbStyleDescriptionEdit->setTabChangesFocus( true );
60 setTabOrder( mDbStyleNameEdit, mDbStyleDescriptionEdit );
61 setTabOrder( mDbStyleDescriptionEdit, mDbStyleUseAsDefault );
62 mDbStyleUIFileWidget->setDefaultRoot( myLastUsedDir );
63 mDbStyleUIFileWidget->setFilter( tr( "Qt Designer UI file (*.ui)" ) );
64 connect( mDbStyleUIFileWidget, &QgsFileWidget::fileChanged, this, &QgsMapLayerSaveStyleDialog::readUiFileContent );
65 connect( buttonBox, &QDialogButtonBox::helpRequested, this, &QgsMapLayerSaveStyleDialog::showHelp );
66
67 // save to file setup
68 connect( mFileWidget, &QgsFileWidget::fileChanged, this, &QgsMapLayerSaveStyleDialog::updateSaveButtonState );
69 mFileWidget->setStorageMode( QgsFileWidget::SaveFile );
70 mFileWidget->setDefaultRoot( myLastUsedDir );
71 connect( mFileWidget, &QgsFileWidget::fileChanged, this, []( const QString &path ) {
72 QgsSettings settings;
73 const QFileInfo tmplFileInfo( path );
74 settings.setValue( u"style/lastStyleDir"_s, tmplFileInfo.absolutePath() );
75 } );
76
77 // fill style categories
78 mModel = new QgsMapLayerStyleCategoriesModel( mLayer->type(), this );
79 const QgsMapLayer::StyleCategories lastStyleCategories = settings.flagValue( u"style/lastStyleCategories"_s, QgsMapLayer::AllStyleCategories );
80 mModel->setCategories( lastStyleCategories );
81 mStyleCategoriesListView->setModel( mModel );
82 mStyleCategoriesListView->setWordWrap( true );
83 mStyleCategoriesListView->setItemDelegate( new QgsCategoryDisplayLabelDelegate( this ) );
84
85 // select and deselect all categories
86 connect( mSelectAllButton, &QPushButton::clicked, this, &QgsMapLayerSaveStyleDialog::selectAll );
87 connect( mDeselectAllButton, &QPushButton::clicked, this, &QgsMapLayerSaveStyleDialog::deselectAll );
88 connect( mInvertSelectionButton, &QPushButton::clicked, this, &QgsMapLayerSaveStyleDialog::invertSelection );
89
90 mStyleCategoriesListView->adjustSize();
91
92 setupMultipleStyles();
93}
94
95void QgsMapLayerSaveStyleDialog::invertSelection()
96{
97 for ( int i = 0; i < mModel->rowCount( QModelIndex() ); i++ )
98 {
99 QModelIndex index = mModel->index( i, 0 );
100 Qt::CheckState currentState = Qt::CheckState( mModel->data( index, Qt::CheckStateRole ).toInt() );
101 Qt::CheckState newState = ( currentState == Qt::Checked ) ? Qt::Unchecked : Qt::Checked;
102 mModel->setData( index, newState, Qt::CheckStateRole );
103 }
104}
105
106void QgsMapLayerSaveStyleDialog::selectAll()
107{
108 for ( int i = 0; i < mModel->rowCount( QModelIndex() ); i++ )
109 {
110 QModelIndex index = mModel->index( i, 0 );
111 mModel->setData( index, Qt::Checked, Qt::CheckStateRole );
112 }
113}
114
115void QgsMapLayerSaveStyleDialog::deselectAll()
116{
117 for ( int i = 0; i < mModel->rowCount( QModelIndex() ); i++ )
118 {
119 QModelIndex index = mModel->index( i, 0 );
120 mModel->setData( index, Qt::Unchecked, Qt::CheckStateRole );
121 }
122}
123
124void QgsMapLayerSaveStyleDialog::populateStyleComboBox()
125{
126 mStyleTypeComboBox->clear();
127 mStyleTypeComboBox->addItem( tr( "As QGIS QML style file" ), QgsLayerPropertiesDialog::QML );
128 mStyleTypeComboBox->addItem( tr( "As SLD style file" ), QgsLayerPropertiesDialog::SLD );
129
130 if ( mLayer->dataProvider()->styleStorageCapabilities().testFlag( Qgis::ProviderStyleStorageCapability::SaveToDatabase ) )
131 mStyleTypeComboBox->addItem( tr( "In datasource database" ), QgsLayerPropertiesDialog::DatasourceDatabase );
132
133 if ( mSaveOnlyCurrentStyle )
134 mStyleTypeComboBox->addItem( tr( "As default in local user database" ), QgsLayerPropertiesDialog::UserDatabase );
135}
136
138{
139 QgsSettings().setFlagValue( u"style/lastStyleCategories"_s, styleCategories() );
140 QDialog::accept();
141}
142
143void QgsMapLayerSaveStyleDialog::updateSaveButtonState()
144{
146 bool enabled { false };
147 switch ( type )
148 {
150 if ( saveOnlyCurrentStyle() )
151 {
152 enabled = !mDbStyleNameEdit->text().isEmpty();
153 }
154 else
155 {
156 enabled = true;
157 }
158 break;
161 enabled = !mFileWidget->filePath().isEmpty();
162 break;
164 enabled = true;
165 break;
166 }
167 buttonBox->button( QDialogButtonBox::Ok )->setEnabled( enabled );
168}
169
171{
172 SaveToDbSettings settings;
173 settings.name = mDbStyleNameEdit->text();
174 settings.description = mDbStyleDescriptionEdit->toPlainText();
175 settings.isDefault = mDbStyleUseAsDefault->isChecked();
176 settings.uiFileContent = mUiFileContent;
177 return settings;
178}
179
181{
182 return mFileWidget->filePath();
183}
184
186{
187 return mModel->categories();
188}
189
194
195void QgsMapLayerSaveStyleDialog::readUiFileContent( const QString &filePath )
196{
197 QgsSettings myQSettings; // where we keep last used filter in persistent state
198 mUiFileContent = QString();
199
200 if ( filePath.isNull() )
201 {
202 return;
203 }
204
205 const QFileInfo myFI( filePath );
206 QFile uiFile( myFI.filePath() );
207
208 const QString myPath = myFI.path();
209 myQSettings.setValue( u"style/lastStyleDir"_s, myPath );
210
211 if ( uiFile.open( QIODevice::ReadOnly ) )
212 {
213 const QString content( uiFile.readAll() );
214 QDomDocument doc;
215
216 if ( !doc.setContent( content ) || doc.documentElement().tagName().compare( "ui"_L1 ) )
217 {
218 QMessageBox::warning( this, tr( "Attach UI File" ), tr( "The selected file does not appear to be a valid Qt Designer UI file." ) );
219 return;
220 }
221 mUiFileContent = content;
222 }
223}
224
225void QgsMapLayerSaveStyleDialog::setupMultipleStyles()
226{
227 // Show/hide part of the UI according to multiple style support
228 if ( !mSaveOnlyCurrentStyle )
229 {
230 const QgsMapLayerStyleManager *styleManager { mLayer->styleManager() };
231 const QStringList constStyles = styleManager->styles();
232 for ( const QString &name : constStyles )
233 {
234 QListWidgetItem *item = new QListWidgetItem( name, mStylesWidget );
235 item->setCheckState( Qt::CheckState::Checked );
236 // Highlight the current style
237 if ( name == styleManager->currentStyle() )
238 {
239 item->setToolTip( tr( "Current style" ) );
240 QFont font { item->font() };
241 font.setItalic( true );
242 item->setFont( font );
243 }
244 mStylesWidget->addItem( item );
245 }
246 mDbStyleNameEdit->setToolTip( tr( "Leave blank to use style names or set the base name (an incremental number will be automatically appended)" ) );
247 }
248 else
249 {
250 mDbStyleNameEdit->setToolTip( QString() );
251 }
252
253 mStylesWidget->setVisible( !mSaveOnlyCurrentStyle );
254 mStylesWidgetLabel->setVisible( !mSaveOnlyCurrentStyle );
255
256 mDbStyleDescriptionEdit->setVisible( mSaveOnlyCurrentStyle );
257 descriptionLabel->setVisible( mSaveOnlyCurrentStyle );
258 mDbStyleUseAsDefault->setVisible( mSaveOnlyCurrentStyle );
259
260 populateStyleComboBox();
261}
262
264{
265 return mSaveOnlyCurrentStyle;
266}
267
269{
270 if ( mSaveOnlyCurrentStyle != saveOnlyCurrentStyle )
271 {
272 mSaveOnlyCurrentStyle = saveOnlyCurrentStyle;
273 setupMultipleStyles();
274 }
275}
276
278{
279 return mStylesWidget;
280}
281
283{
285
286 if ( mStyleTypeComboBox->currentData() == QgsLayerPropertiesDialog::SLD && mSldExportPng->isChecked() )
287 {
288 options.setFlag( Qgis::SldExportOption::Png );
289 }
290 return options;
291}
292
293void QgsMapLayerSaveStyleDialog::showHelp()
294{
295 QgsHelp::openHelp( u"introduction/general_tools.html#save-and-share-layer-properties"_s );
296}
@ Png
Export complex styles to separate PNG files for better compatibility with OGC servers.
Definition qgis.h:718
@ Polygon
Polygons.
Definition qgis.h:368
@ Vector
Vector layer.
Definition qgis.h:194
QFlags< SldExportOption > SldExportOptions
Definition qgis.h:721
A label delegate able to display HTML encoded content.
@ SaveFile
Select a single new or pre-existing file.
void fileChanged(const QString &path)
Emitted whenever the current file or directory path is changed.
static void enableAutoGeometryRestore(QWidget *widget, const QString &key=QString())
Register the widget to allow its position to be automatically saved and restored when open and closed...
Definition qgsgui.cpp:224
static void openHelp(const QString &key)
Opens help topic for the given help key using default system web browser.
Definition qgshelp.cpp:41
QString outputFilePath() const
Returns the selected file output path.
Qgis::SldExportOptions sldExportOptions() const
Returns the SLD export options.
SaveToDbSettings saveToDbSettings() const
Returns the database settings for saving the style in the DB.
void setSaveOnlyCurrentStyle(bool saveCurrentStyle)
Sets whether the user only allowed to save the current style.
bool saveOnlyCurrentStyle() const
Returns whether the user only allowed to save the current style.
QgsMapLayer::StyleCategories styleCategories() const
Returns the available style categories.
QgsLayerPropertiesDialog::StyleType currentStyleType() const
Returns the selected style storage type.
QgsMapLayerSaveStyleDialog(QgsMapLayer *layer, QWidget *parent=nullptr)
Constructor.
const QListWidget * stylesWidget()
Returns the styles list widget.
QVariant data(const QModelIndex &index, int role) const override
bool setData(const QModelIndex &index, const QVariant &value, int role) override
int rowCount(const QModelIndex &=QModelIndex()) const override
QString currentStyle() const
Returns name of the current style.
QStringList styles() const
Returns list of all defined style names.
Base class for all map layer types.
Definition qgsmaplayer.h:83
Qgis::LayerType type
Definition qgsmaplayer.h:93
QFlags< StyleCategory > StyleCategories
Stores settings for use within QGIS.
Definition qgssettings.h:68
T flagValue(const QString &key, const T &defaultValue, const Section section=NoSection)
Returns the setting value for a setting based on a flag.
void setFlagValue(const QString &key, const T &value, const Section section=NoSection)
Set the value of a setting based on a flag.
QVariant value(const QString &key, const QVariant &defaultValue=QVariant(), Section section=NoSection) const
Returns the value for setting key.
void setValue(const QString &key, const QVariant &value, QgsSettings::Section section=QgsSettings::NoSection)
Sets the value of setting key to value.
Represents a vector layer which manages a vector based dataset.
Q_INVOKABLE Qgis::GeometryType geometryType() const
Returns point, line or polygon.