QGIS API Documentation  3.26.3-Buenos Aires (65e4edfdad)
qgsvectorlayersavestyledialog.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsvectorlayersavestyledialog.h
3  --------------------------------------
4  Date : September 2018
5  Copyright : (C) 2018 by Denis Rouzaud
6  Email : [email protected]
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 <QListWidgetItem>
17 #include <QMessageBox>
18 
20 #include "qgsvectorlayer.h"
21 #include "qgssettings.h"
22 #include "qgshelp.h"
23 #include "qgsgui.h"
25 
27  : QDialog( parent )
28  , mLayer( layer )
29 {
30  setupUi( this );
32 
33  QgsSettings settings;
34 
35  const QString myLastUsedDir = settings.value( QStringLiteral( "style/lastStyleDir" ), QDir::homePath() ).toString();
36 
37  // save style type combobox
38  connect( mStyleTypeComboBox, qOverload<int>( &QComboBox::currentIndexChanged ), this, [ = ]( int )
39  {
41  mFileLabel->setVisible( type != QgsVectorLayerProperties::DB && type != QgsVectorLayerProperties::Local );
42  mFileWidget->setVisible( type != QgsVectorLayerProperties::DB && type != QgsVectorLayerProperties::Local );
43  mSaveToDbWidget->setVisible( type == QgsVectorLayerProperties::DB );
44  mStyleCategoriesListView->setEnabled( type != QgsVectorLayerProperties::SLD );
45  mFileWidget->setFilter( type == QgsVectorLayerProperties::QML ? tr( "QGIS Layer Style File (*.qml)" ) : tr( "SLD File (*.sld)" ) );
46  updateSaveButtonState();
47  } );
48 
49  // Save to DB setup
50  connect( mDbStyleNameEdit, &QLineEdit::textChanged, this, &QgsVectorLayerSaveStyleDialog::updateSaveButtonState );
51  mDbStyleDescriptionEdit->setTabChangesFocus( true );
52  setTabOrder( mDbStyleNameEdit, mDbStyleDescriptionEdit );
53  setTabOrder( mDbStyleDescriptionEdit, mDbStyleUseAsDefault );
54  mDbStyleUIFileWidget->setDefaultRoot( myLastUsedDir );
55  mDbStyleUIFileWidget->setFilter( tr( "Qt Designer UI file (*.ui)" ) );
56  connect( mDbStyleUIFileWidget, &QgsFileWidget::fileChanged, this, &QgsVectorLayerSaveStyleDialog::readUiFileContent );
57  connect( buttonBox, &QDialogButtonBox::helpRequested, this, &QgsVectorLayerSaveStyleDialog::showHelp );
58 
59  // save to file setup
60  connect( mFileWidget, &QgsFileWidget::fileChanged, this, &QgsVectorLayerSaveStyleDialog::updateSaveButtonState );
61  mFileWidget->setStorageMode( QgsFileWidget::SaveFile );
62  mFileWidget->setDefaultRoot( myLastUsedDir );
63  connect( mFileWidget, &QgsFileWidget::fileChanged, this, [ = ]( const QString & path )
64  {
65  QgsSettings settings;
66  const QFileInfo tmplFileInfo( path );
67  settings.setValue( QStringLiteral( "style/lastStyleDir" ), tmplFileInfo.absolutePath() );
68  } );
69 
70  // fill style categories
71  mModel = new QgsMapLayerStyleCategoriesModel( mLayer->type(), this );
72  const QgsMapLayer::StyleCategories lastStyleCategories = settings.flagValue( QStringLiteral( "style/lastStyleCategories" ), QgsMapLayer::AllStyleCategories );
73  mModel->setCategories( lastStyleCategories );
74  mStyleCategoriesListView->setModel( mModel );
75 
76  mStyleCategoriesListView->adjustSize();
77 
78  setupMultipleStyles();
79 
80 }
81 
82 void QgsVectorLayerSaveStyleDialog::populateStyleComboBox()
83 {
84  QString providerName = mLayer->providerType();
85  if ( providerName == QLatin1String( "ogr" ) )
86  {
87  providerName = mLayer->dataProvider()->storageType();
88  if ( providerName == QLatin1String( "GPKG" ) )
89  providerName = QStringLiteral( "GeoPackage" );
90  }
91 
92  mStyleTypeComboBox->clear();
93  mStyleTypeComboBox->addItem( tr( "As QGIS QML Style File" ), QgsVectorLayerProperties::QML );
94  mStyleTypeComboBox->addItem( tr( "As SLD Style File" ), QgsVectorLayerProperties::SLD );
95 
96  if ( mLayer->dataProvider()->isSaveAndLoadStyleToDatabaseSupported() )
97  mStyleTypeComboBox->addItem( tr( "In Database (%1)" ).arg( providerName ), QgsVectorLayerProperties::DB );
98 
99  if ( mSaveOnlyCurrentStyle )
100  mStyleTypeComboBox->addItem( tr( "As Default In Local Database" ), QgsVectorLayerProperties::Local );
101 }
102 
104 {
105  QgsSettings().setFlagValue( QStringLiteral( "style/lastStyleCategories" ), styleCategories() );
106  QDialog::accept();
107 }
108 
109 void QgsVectorLayerSaveStyleDialog::updateSaveButtonState()
110 {
111  const QgsVectorLayerProperties::StyleType type = currentStyleType();
112  bool enabled { false };
113  switch ( type )
114  {
116  if ( saveOnlyCurrentStyle( ) )
117  {
118  enabled = ! mDbStyleNameEdit->text().isEmpty();
119  }
120  else
121  {
122  enabled = true;
123  }
124  break;
127  enabled = ! mFileWidget->filePath().isEmpty();
128  break;
130  enabled = true;
131  break;
132  }
133  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( enabled );
134 }
135 
137 {
138  SaveToDbSettings settings;
139  settings.name = mDbStyleNameEdit->text();
140  settings.description = mDbStyleDescriptionEdit->toPlainText();
141  settings.isDefault = mDbStyleUseAsDefault->isChecked();
142  settings.uiFileContent = mUiFileContent;
143  return settings;
144 }
145 
147 {
148  return mFileWidget->filePath();
149 }
150 
151 QgsMapLayer::StyleCategories QgsVectorLayerSaveStyleDialog::styleCategories() const
152 {
153  return mModel->categories();
154 }
155 
157 {
158  return mStyleTypeComboBox->currentData().value<QgsVectorLayerProperties::StyleType>();
159 }
160 
161 void QgsVectorLayerSaveStyleDialog::readUiFileContent( const QString &filePath )
162 {
163  QgsSettings myQSettings; // where we keep last used filter in persistent state
164  mUiFileContent = QString();
165 
166  if ( filePath.isNull() )
167  {
168  return;
169  }
170 
171  const QFileInfo myFI( filePath );
172  QFile uiFile( myFI.filePath() );
173 
174  const QString myPath = myFI.path();
175  myQSettings.setValue( QStringLiteral( "style/lastStyleDir" ), myPath );
176 
177  if ( uiFile.open( QIODevice::ReadOnly ) )
178  {
179  const QString content( uiFile.readAll() );
180  QDomDocument doc;
181 
182  if ( !doc.setContent( content ) || doc.documentElement().tagName().compare( QLatin1String( "ui" ) ) )
183  {
184  QMessageBox::warning( this, tr( "Attach UI File" ),
185  tr( "The selected file does not appear to be a valid Qt Designer UI file." ) );
186  return;
187  }
188  mUiFileContent = content;
189  }
190 }
191 
192 void QgsVectorLayerSaveStyleDialog::setupMultipleStyles()
193 {
194  // Show/hide part of the UI according to multiple style support
195  if ( ! mSaveOnlyCurrentStyle )
196  {
197  const QgsMapLayerStyleManager *styleManager { mLayer->styleManager() };
198  const QStringList constStyles = styleManager->styles();
199  for ( const QString &name : constStyles )
200  {
201  QListWidgetItem *item = new QListWidgetItem( name, mStylesWidget );
202  item->setCheckState( Qt::CheckState::Checked );
203  // Highlight the current style
204  if ( name == styleManager->currentStyle() )
205  {
206  item->setToolTip( tr( "Current style" ) );
207  QFont font { item->font() };
208  font.setItalic( true );
209  item->setFont( font );
210  }
211  mStylesWidget->addItem( item );
212  }
213  mDbStyleNameEdit->setToolTip( tr( "Leave blank to use style names or set the base name (an incremental number will be automatically appended)" ) );
214  }
215  else
216  {
217  mDbStyleNameEdit->setToolTip( QString() );
218  }
219 
220  mStylesWidget->setVisible( ! mSaveOnlyCurrentStyle );
221  mStylesWidgetLabel->setVisible( ! mSaveOnlyCurrentStyle );
222 
223  mDbStyleDescriptionEdit->setVisible( mSaveOnlyCurrentStyle );
224  descriptionLabel->setVisible( mSaveOnlyCurrentStyle );
225  mDbStyleUseAsDefault->setVisible( mSaveOnlyCurrentStyle );
226 
227  populateStyleComboBox();
228 }
229 
231 {
232  return mSaveOnlyCurrentStyle;
233 }
234 
236 {
237  if ( mSaveOnlyCurrentStyle != saveOnlyCurrentStyle )
238  {
239  mSaveOnlyCurrentStyle = saveOnlyCurrentStyle;
240  setupMultipleStyles();
241  }
242 }
243 
245 {
246  return mStylesWidget;
247 }
248 
249 
250 void QgsVectorLayerSaveStyleDialog::showHelp()
251 {
252  QgsHelp::openHelp( QStringLiteral( "introduction/general_tools.html#save-and-share-layer-properties" ) );
253 }
QgsMapLayerStyleManager::styles
QStringList styles() const
Returns list of all defined style names.
Definition: qgsmaplayerstylemanager.cpp:86
QgsVectorLayerSaveStyleDialog::currentStyleType
QgsVectorLayerProperties::StyleType currentStyleType() const
Definition: qgsvectorlayersavestyledialog.cpp:156
QgsFileWidget::fileChanged
void fileChanged(const QString &path)
Emitted whenever the current file or directory path is changed.
QgsVectorLayerSaveStyleDialog::stylesWidget
const QListWidget * stylesWidget()
Definition: qgsvectorlayersavestyledialog.cpp:244
QgsSettings::setFlagValue
void setFlagValue(const QString &key, const T &value, const Section section=NoSection)
Set the value of a setting based on a flag.
Definition: qgssettings.h:424
QgsSettings::value
QVariant value(const QString &key, const QVariant &defaultValue=QVariant(), Section section=NoSection) const
Returns the value for setting key.
Definition: qgssettings.cpp:161
qgsgui.h
QgsVectorLayerSaveStyleDialog::SaveToDbSettings::isDefault
bool isDefault
Definition: qgsvectorlayersavestyledialog.h:50
QgsSettings
This class is a composition of two QSettings instances:
Definition: qgssettings.h:61
QgsVectorLayerSaveStyleDialog::SaveToDbSettings
Definition: qgsvectorlayersavestyledialog.h:44
QgsVectorLayerProperties::StyleType
StyleType
Definition: qgsvectorlayerproperties.h:66
QgsFileWidget::SaveFile
@ SaveFile
Select a single new or pre-existing file.
Definition: qgsfilewidget.h:71
QgsMapLayerStyleCategoriesModel
Model for layer style categories.
Definition: qgsmaplayerstylecategoriesmodel.h:35
QgsGui::enableAutoGeometryRestore
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:180
QgsMapLayerStyleManager
Management of styles for use with one map layer.
Definition: qgsmaplayerstylemanager.h:57
QgsVectorLayerProperties::DB
@ DB
Definition: qgsvectorlayerproperties.h:70
QgsVectorLayerProperties::Local
@ Local
Definition: qgsvectorlayerproperties.h:71
QgsVectorLayerSaveStyleDialog::accept
void accept() override
Definition: qgsvectorlayersavestyledialog.cpp:103
QgsSettings::flagValue
T flagValue(const QString &key, const T &defaultValue, const Section section=NoSection)
Returns the setting value for a setting based on a flag.
Definition: qgssettings.h:360
qgsmaplayerstylecategoriesmodel.h
QgsVectorLayerProperties::QML
@ QML
Definition: qgsvectorlayerproperties.h:68
QgsVectorLayerProperties::SLD
@ SLD
Definition: qgsvectorlayerproperties.h:69
QgsSettings::setValue
void setValue(const QString &key, const QVariant &value, QgsSettings::Section section=QgsSettings::NoSection)
Sets the value of setting key to value.
Definition: qgssettings.cpp:279
qgsvectorlayer.h
QgsVectorLayerSaveStyleDialog::saveOnlyCurrentStyle
bool saveOnlyCurrentStyle() const
Definition: qgsvectorlayersavestyledialog.cpp:230
QgsVectorLayerSaveStyleDialog::saveToDbSettings
SaveToDbSettings saveToDbSettings() const
Definition: qgsvectorlayersavestyledialog.cpp:136
QgsHelp::openHelp
static void openHelp(const QString &key)
Opens help topic for the given help key using default system web browser.
Definition: qgshelp.cpp:36
QgsVectorLayer
Represents a vector layer which manages a vector based data sets.
Definition: qgsvectorlayer.h:391
qgssettings.h
QgsVectorLayerSaveStyleDialog::SaveToDbSettings::description
QString description
Definition: qgsvectorlayersavestyledialog.h:49
QgsVectorLayerSaveStyleDialog::SaveToDbSettings::name
QString name
Definition: qgsvectorlayersavestyledialog.h:48
QgsMapLayer::AllStyleCategories
@ AllStyleCategories
Definition: qgsmaplayer.h:178
QgsVectorLayerSaveStyleDialog::QgsVectorLayerSaveStyleDialog
QgsVectorLayerSaveStyleDialog(QgsVectorLayer *layer, QWidget *parent=nullptr)
Definition: qgsvectorlayersavestyledialog.cpp:26
QgsVectorLayerSaveStyleDialog::styleCategories
QgsMapLayer::StyleCategories styleCategories() const
Definition: qgsvectorlayersavestyledialog.cpp:151
QgsVectorLayerSaveStyleDialog::SaveToDbSettings::uiFileContent
QString uiFileContent
Definition: qgsvectorlayersavestyledialog.h:47
QgsVectorLayerSaveStyleDialog::outputFilePath
QString outputFilePath() const
Definition: qgsvectorlayersavestyledialog.cpp:146
qgshelp.h
qgsvectorlayersavestyledialog.h
QgsVectorLayerSaveStyleDialog::setSaveOnlyCurrentStyle
void setSaveOnlyCurrentStyle(bool saveCurrentStyle)
Definition: qgsvectorlayersavestyledialog.cpp:235
QgsMapLayer::type
QgsMapLayerType type
Definition: qgsmaplayer.h:80