QGIS API Documentation  3.22.4-Białowieża (ce8e65e95e)
qgsvectorlayersaveasdialog.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsvectorlayersaveasdialog.h
3  Dialog to select destination, type and crs for ogr layers
4  -------------------
5  begin : Mon Mar 22 2010
6  copyright : (C) 2010 by Juergen E. Fischer
7  email : jef at norbit dot de
8  ***************************************************************************/
9 
10 /***************************************************************************
11  * *
12  * This program is free software; you can redistribute it and/or modify *
13  * it under the terms of the GNU General Public License as published by *
14  * the Free Software Foundation; either version 2 of the License, or *
15  * (at your option) any later version. *
16  * *
17  ***************************************************************************/
18 #include "qgslogger.h"
21 #include "qgsvectordataprovider.h"
23 #include "qgseditorwidgetfactory.h"
25 #include "qgssettings.h"
26 #include "qgsmapcanvas.h"
27 #include "qgsgui.h"
28 #include "qgsapplication.h"
29 #include <QMessageBox>
30 #include <QFileDialog>
31 #include <QTextCodec>
32 #include <QSpinBox>
33 #include <QRegularExpression>
34 #include "gdal.h"
35 #include "qgsdatums.h"
36 #include "qgsiconutils.h"
37 #include "qgsproviderregistry.h"
39 
40 static const int COLUMN_IDX_NAME = 0;
41 static const int COLUMN_IDX_TYPE = 1;
42 static const int COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE = 2;
43 
44 QgsVectorLayerSaveAsDialog::QgsVectorLayerSaveAsDialog( long srsid, QWidget *parent, Qt::WindowFlags fl )
45  : QDialog( parent, fl )
46  , mSelectedCrs( QgsCoordinateReferenceSystem::fromSrsId( srsid ) )
47  , mAttributeTableItemChangedSlotEnabled( true )
48  , mReplaceRawFieldValuesStateChangedSlotEnabled( true )
49  , mActionOnExistingFile( QgsVectorFileWriter::CreateOrOverwriteFile )
50 {
51  setup();
52 }
53 
54 QgsVectorLayerSaveAsDialog::QgsVectorLayerSaveAsDialog( QgsVectorLayer *layer, Options options, QWidget *parent, Qt::WindowFlags fl )
55  : QDialog( parent, fl )
56  , mLayer( layer )
57  , mAttributeTableItemChangedSlotEnabled( true )
58  , mReplaceRawFieldValuesStateChangedSlotEnabled( true )
59  , mActionOnExistingFile( QgsVectorFileWriter::CreateOrOverwriteFile )
60  , mOptions( options )
61 {
62  if ( layer )
63  {
64  mSelectedCrs = layer->crs();
65  mLayerExtent = layer->extent();
66  }
67  setup();
68 
69  if ( !( mOptions & Symbology ) )
70  {
71  mSymbologyExportLabel->hide();
72  mSymbologyExportComboBox->hide();
73  mScaleLabel->hide();
74  mScaleWidget->hide();
75  }
76 
77  if ( !( mOptions & DestinationCrs ) )
78  {
79  mCrsLabel->hide();
80  mCrsSelector->hide();
81  }
82  if ( !( mOptions & Fields ) )
83  mAttributesSelection->hide();
84 
85  if ( !( mOptions & SelectedOnly ) )
86  mSelectedOnly->hide();
87 
88  if ( !( mOptions & AddToCanvas ) )
89  mAddToCanvas->hide();
90 
91  if ( !( mOptions & GeometryType ) )
92  mGeometryGroupBox->hide();
93 
94  if ( !( mOptions & Extent ) )
95  mExtentGroupBox->hide();
96 
97  if ( !( mOptions & Metadata ) )
98  {
99  mCheckPersistMetadata->setChecked( false );
100  mCheckPersistMetadata->hide();
101  }
102 
103  mSelectedOnly->setEnabled( layer && layer->selectedFeatureCount() != 0 );
104  mButtonBox->button( QDialogButtonBox::Ok )->setDisabled( true );
105 }
106 
107 void QgsVectorLayerSaveAsDialog::setup()
108 {
109  setupUi( this );
111 
112  connect( mFormatComboBox, static_cast<void ( QComboBox::* )( int )>( &QComboBox::currentIndexChanged ), this, &QgsVectorLayerSaveAsDialog::mFormatComboBox_currentIndexChanged );
113  connect( mCrsSelector, &QgsProjectionSelectionWidget::crsChanged, this, &QgsVectorLayerSaveAsDialog::mCrsSelector_crsChanged );
114  connect( mSymbologyExportComboBox, &QComboBox::currentTextChanged, this, &QgsVectorLayerSaveAsDialog::mSymbologyExportComboBox_currentIndexChanged );
115  connect( mGeometryTypeComboBox, static_cast<void ( QComboBox::* )( int )>( &QComboBox::currentIndexChanged ), this, &QgsVectorLayerSaveAsDialog::mGeometryTypeComboBox_currentIndexChanged );
116  connect( mSelectAllAttributes, &QPushButton::clicked, this, &QgsVectorLayerSaveAsDialog::mSelectAllAttributes_clicked );
117  connect( mDeselectAllAttributes, &QPushButton::clicked, this, &QgsVectorLayerSaveAsDialog::mDeselectAllAttributes_clicked );
118  connect( mReplaceRawFieldValues, &QCheckBox::stateChanged, this, &QgsVectorLayerSaveAsDialog::mReplaceRawFieldValues_stateChanged );
119  connect( mAttributeTable, &QTableWidget::itemChanged, this, &QgsVectorLayerSaveAsDialog::mAttributeTable_itemChanged );
120 
121 #ifdef Q_OS_WIN
122  mHelpButtonBox->setVisible( false );
123  mButtonBox->addButton( QDialogButtonBox::Help );
124  connect( mButtonBox, &QDialogButtonBox::helpRequested, this, &QgsVectorLayerSaveAsDialog::showHelp );
125 #else
126  connect( mHelpButtonBox, &QDialogButtonBox::helpRequested, this, &QgsVectorLayerSaveAsDialog::showHelp );
127 #endif
128  connect( mButtonBox, &QDialogButtonBox::accepted, this, &QgsVectorLayerSaveAsDialog::accept );
129  connect( mButtonBox, &QDialogButtonBox::rejected, this, &QgsVectorLayerSaveAsDialog::reject );
130 
131  const QList< QgsVectorFileWriter::DriverDetails > drivers = QgsVectorFileWriter::ogrDriverList();
132  mFormatComboBox->blockSignals( true );
133  for ( const QgsVectorFileWriter::DriverDetails &driver : drivers )
134  {
135  mFormatComboBox->addItem( driver.longName, driver.driverName );
136  }
137 
138  QgsSettings settings;
139  QString format = settings.value( QStringLiteral( "UI/lastVectorFormat" ), "GPKG" ).toString();
140  mFormatComboBox->setCurrentIndex( mFormatComboBox->findData( format ) );
141  mFormatComboBox->blockSignals( false );
142 
143  const auto addGeomItem = [this]( QgsWkbTypes::Type type )
144  {
145  mGeometryTypeComboBox->addItem( QgsIconUtils::iconForWkbType( type ), QgsWkbTypes::translatedDisplayString( type ), type );
146  };
147 
148  //add geometry types to combobox
149  mGeometryTypeComboBox->addItem( tr( "Automatic" ), -1 );
150  addGeomItem( QgsWkbTypes::Point );
151  addGeomItem( QgsWkbTypes::LineString );
152  addGeomItem( QgsWkbTypes::Polygon );
154  addGeomItem( QgsWkbTypes::NoGeometry );
155  mGeometryTypeComboBox->setCurrentIndex( mGeometryTypeComboBox->findData( -1 ) );
156 
157  mEncodingComboBox->addItems( QgsVectorDataProvider::availableEncodings() );
158 
159  QString enc = settings.value( QStringLiteral( "UI/encoding" ), "System" ).toString();
160  int idx = mEncodingComboBox->findText( enc );
161  if ( idx < 0 )
162  {
163  mEncodingComboBox->insertItem( 0, enc );
164  idx = 0;
165  }
166 
167  mCrsSelector->setCrs( mSelectedCrs );
168  mCrsSelector->setLayerCrs( mSelectedCrs );
169  mCrsSelector->setMessage( tr( "Select the coordinate reference system for the vector file. "
170  "The data points will be transformed from the layer coordinate reference system." ) );
171 
172  mEncodingComboBox->setCurrentIndex( idx );
173  mFormatComboBox_currentIndexChanged( mFormatComboBox->currentIndex() );
174 
175  //symbology export combo box
176  mSymbologyExportComboBox->addItem( tr( "No Symbology" ), QgsVectorFileWriter::NoSymbology );
177  mSymbologyExportComboBox->addItem( tr( "Feature Symbology" ), QgsVectorFileWriter::FeatureSymbology );
178  mSymbologyExportComboBox->addItem( tr( "Symbol Layer Symbology" ), QgsVectorFileWriter::SymbolLayerSymbology );
179  mSymbologyExportComboBox_currentIndexChanged( mSymbologyExportComboBox->currentText() );
180 
181  // extent group box
182  mExtentGroupBox->setOutputCrs( mSelectedCrs );
183  mExtentGroupBox->setOriginalExtent( mLayerExtent, mSelectedCrs );
184  mExtentGroupBox->setOutputExtentFromOriginal();
185  mExtentGroupBox->setCheckable( true );
186  mExtentGroupBox->setChecked( false );
187  mExtentGroupBox->setCollapsed( true );
188 
189  mFilename->setStorageMode( QgsFileWidget::SaveFile );
190  mFilename->setDialogTitle( tr( "Save Layer As" ) );
191  mFilename->setDefaultRoot( settings.value( QStringLiteral( "UI/lastVectorFileFilterDir" ), QDir::homePath() ).toString() );
192  mFilename->setConfirmOverwrite( false );
193  connect( mFilename, &QgsFileWidget::fileChanged, this, [ = ]( const QString & filePath )
194  {
195  QgsSettings settings;
196  QFileInfo tmplFileInfo( filePath );
197  settings.setValue( QStringLiteral( "UI/lastVectorFileFilterDir" ), tmplFileInfo.absolutePath() );
198  if ( !filePath.isEmpty() && leLayername->isEnabled() )
199  {
200  QFileInfo fileInfo( filePath );
201  leLayername->setText( fileInfo.completeBaseName() );
202  }
203  mButtonBox->button( QDialogButtonBox::Ok )->setEnabled( !filePath.isEmpty() );
204  } );
205 
206  try
207  {
208  const QgsDatumEnsemble ensemble = mSelectedCrs.datumEnsemble();
209  if ( ensemble.isValid() )
210  {
211  mCrsSelector->setSourceEnsemble( ensemble.name() );
212  }
213  }
214  catch ( QgsNotSupportedException & )
215  {
216  }
217 
218  mCrsSelector->setShowAccuracyWarnings( true );
219 }
220 
221 QList<QPair<QLabel *, QWidget *> > QgsVectorLayerSaveAsDialog::createControls( const QMap<QString, QgsVectorFileWriter::Option *> &options )
222 {
223  QList<QPair<QLabel *, QWidget *> > controls;
224  QMap<QString, QgsVectorFileWriter::Option *>::ConstIterator it;
225 
226  for ( it = options.constBegin(); it != options.constEnd(); ++it )
227  {
228  QgsVectorFileWriter::Option *option = it.value();
229  QLabel *label = new QLabel( it.key() );
230  QWidget *control = nullptr;
231  switch ( option->type )
232  {
234  {
235  QgsVectorFileWriter::IntOption *opt = dynamic_cast<QgsVectorFileWriter::IntOption *>( option );
236  if ( opt )
237  {
238  QSpinBox *sb = new QSpinBox();
239  sb->setObjectName( it.key() );
240  sb->setValue( opt->defaultValue );
241  control = sb;
242  }
243  break;
244  }
245 
247  {
248  QgsVectorFileWriter::SetOption *opt = dynamic_cast<QgsVectorFileWriter::SetOption *>( option );
249  if ( opt )
250  {
251  QComboBox *cb = new QComboBox();
252  cb->setObjectName( it.key() );
253  for ( const QString &val : std::as_const( opt->values ) )
254  {
255  cb->addItem( val, val );
256  }
257  if ( opt->allowNone )
258  cb->addItem( tr( "<Default>" ), QVariant( QVariant::String ) );
259  int idx = cb->findText( opt->defaultValue );
260  if ( idx == -1 )
261  idx = cb->findData( QVariant( QVariant::String ) );
262  cb->setCurrentIndex( idx );
263  control = cb;
264  }
265  break;
266  }
267 
269  {
271  if ( opt )
272  {
273  QLineEdit *le = new QLineEdit( opt->defaultValue );
274  le->setObjectName( it.key() );
275  control = le;
276  }
277  break;
278  }
279 
281  control = nullptr;
282  break;
283  }
284 
285  if ( control )
286  {
287  // Pack the tooltip in some html element, so it gets linebreaks.
288  label->setToolTip( QStringLiteral( "<p>%1</p>" ).arg( option->docString.toHtmlEscaped() ) );
289  control->setToolTip( QStringLiteral( "<p>%1</p>" ).arg( option->docString.toHtmlEscaped() ) );
290 
291  controls << QPair<QLabel *, QWidget *>( label, control );
292  }
293  }
294 
295  return controls;
296 }
297 
298 void QgsVectorLayerSaveAsDialog::accept()
299 {
300  if ( QFile::exists( filename() ) )
301  {
302  QgsVectorFileWriter::EditionCapabilities caps =
304  bool layerExists = QgsVectorFileWriter::targetLayerExists( filename(),
305  layername() );
306  QMessageBox msgBox;
307  msgBox.setIcon( QMessageBox::Question );
308  msgBox.setWindowTitle( tr( "Save Vector Layer As" ) );
309  QPushButton *overwriteFileButton = msgBox.addButton( tr( "Overwrite File" ), QMessageBox::ActionRole );
310  QPushButton *overwriteLayerButton = msgBox.addButton( tr( "Overwrite Layer" ), QMessageBox::ActionRole );
311  QPushButton *appendToLayerButton = msgBox.addButton( tr( "Append to Layer" ), QMessageBox::ActionRole );
312  msgBox.setStandardButtons( QMessageBox::Cancel );
313  msgBox.setDefaultButton( QMessageBox::Cancel );
314  overwriteFileButton->hide();
315  overwriteLayerButton->hide();
316  appendToLayerButton->hide();
317  if ( layerExists )
318  {
322  {
323  msgBox.setText( tr( "The layer already exists. Do you want to overwrite the whole file or overwrite the layer?" ) );
324  overwriteFileButton->setVisible( true );
325  overwriteLayerButton->setVisible( true );
326  }
327  else if ( !( caps & QgsVectorFileWriter::CanAppendToExistingLayer ) )
328  {
329  msgBox.setText( tr( "The file already exists. Do you want to overwrite it?" ) );
330  overwriteFileButton->setVisible( true );
331  }
332  else if ( ( caps & QgsVectorFileWriter::CanDeleteLayer ) &&
334  {
335  msgBox.setText( tr( "The layer already exists. Do you want to overwrite the whole file, overwrite the layer or append features to the layer?" ) );
336  appendToLayerButton->setVisible( true );
337  overwriteFileButton->setVisible( true );
338  overwriteLayerButton->setVisible( true );
339  }
340  else
341  {
342  msgBox.setText( tr( "The layer already exists. Do you want to overwrite the whole file or append features to the layer?" ) );
343  appendToLayerButton->setVisible( true );
344  overwriteFileButton->setVisible( true );
345  }
346 
347  int ret = msgBox.exec();
348  if ( ret == QMessageBox::Cancel )
349  return;
350  if ( msgBox.clickedButton() == overwriteFileButton )
351  mActionOnExistingFile = QgsVectorFileWriter::CreateOrOverwriteFile;
352  else if ( msgBox.clickedButton() == overwriteLayerButton )
353  mActionOnExistingFile = QgsVectorFileWriter::CreateOrOverwriteLayer;
354  else if ( msgBox.clickedButton() == appendToLayerButton )
355  mActionOnExistingFile = QgsVectorFileWriter::AppendToLayerNoNewFields;
356  }
357  else // !layerExists
358  {
359  if ( ( caps & QgsVectorFileWriter::CanAddNewLayer ) )
360  {
361  mActionOnExistingFile = QgsVectorFileWriter::CreateOrOverwriteLayer;
362  }
363  else
364  {
365  // should not reach here, layer does not exist and cannot add new layer
366  if ( QMessageBox::question( this,
367  tr( "Save Vector Layer As" ),
368  tr( "The file already exists. Do you want to overwrite it?" ) ) == QMessageBox::NoButton )
369  {
370  return;
371  }
372  mActionOnExistingFile = QgsVectorFileWriter::CreateOrOverwriteFile;
373  }
374  }
375  }
376 
377  if ( mActionOnExistingFile == QgsVectorFileWriter::AppendToLayerNoNewFields )
378  {
380  {
381  if ( QMessageBox::question( this,
382  tr( "Save Vector Layer As" ),
383  tr( "The existing layer has additional fields. Do you want to add the missing fields to the layer?" ) ) == QMessageBox::Yes )
384  {
385  mActionOnExistingFile = QgsVectorFileWriter::AppendToLayerAddFields;
386  }
387  }
388  }
389  else if ( mActionOnExistingFile == QgsVectorFileWriter::CreateOrOverwriteFile && QFile::exists( filename() ) )
390  {
391  const QList<QgsProviderSublayerDetails> sublayers = QgsProviderRegistry::instance()->querySublayers( filename() );
392  QStringList layerList;
393  layerList.reserve( sublayers.size() );
394  for ( const QgsProviderSublayerDetails &sublayer : sublayers )
395  {
396  layerList.append( sublayer.name() );
397  }
398  if ( layerList.length() > 1 )
399  {
400  layerList.sort( Qt::CaseInsensitive );
401  QMessageBox msgBox;
402  msgBox.setIcon( QMessageBox::Warning );
403  msgBox.setWindowTitle( tr( "Overwrite File" ) );
404  msgBox.setText( tr( "This file contains %1 layers that will be lost!\n" ).arg( QLocale().toString( layerList.length() ) ) );
405  msgBox.setDetailedText( tr( "The following layers will be permanently lost:\n\n%1" ).arg( layerList.join( "\n" ) ) );
406  msgBox.setStandardButtons( QMessageBox::Ok | QMessageBox::Cancel );
407  if ( msgBox.exec() == QMessageBox::Cancel )
408  return;
409  }
410  }
411 
412  QgsSettings settings;
413  settings.setValue( QStringLiteral( "UI/lastVectorFileFilterDir" ), QFileInfo( filename() ).absolutePath() );
414  settings.setValue( QStringLiteral( "UI/lastVectorFormat" ), format() );
415  settings.setValue( QStringLiteral( "UI/encoding" ), encoding() );
416  QDialog::accept();
417 }
418 
419 void QgsVectorLayerSaveAsDialog::mFormatComboBox_currentIndexChanged( int idx )
420 {
421  Q_UNUSED( idx )
422 
423  mFilename->setEnabled( true );
424  mFilename->setFilter( QgsVectorFileWriter::filterForDriver( format() ) );
425 
426  // if output filename already defined we need to replace old suffix
427  // to avoid double extensions like .gpkg.shp
428  if ( !mFilename->filePath().isEmpty() )
429  {
430  QRegularExpression rx( "\\.(.*?)[\\s]" );
431  QString ext;
432  ext = rx.match( QgsVectorFileWriter::filterForDriver( format() ) ).captured( 1 );
433  if ( !ext.isEmpty() )
434  {
435  QFileInfo fi( mFilename->filePath() );
436  mFilename->setFilePath( QStringLiteral( "%1/%2.%3" ).arg( fi.path() ).arg( fi.baseName() ).arg( ext ) );
437  }
438  }
439 
440  bool selectAllFields = true;
441 
442  // Is it a format for which fields that have attached widgets of types
443  // ValueMap, ValueRelation, etc. should be by default exported with their displayed
444  // values
445  bool isFormatForFieldsAsDisplayedValues = false;
446 
447  const QString sFormat( format() );
448  if ( sFormat == QLatin1String( "DXF" ) || sFormat == QLatin1String( "DGN" ) )
449  {
450  mAttributesSelection->setVisible( false );
451  selectAllFields = false;
452  }
453  else
454  {
455  if ( mOptions & Fields )
456  {
457  mAttributesSelection->setVisible( true );
458  isFormatForFieldsAsDisplayedValues = ( sFormat == QLatin1String( "CSV" ) ||
459  sFormat == QLatin1String( "XLS" ) ||
460  sFormat == QLatin1String( "XLSX" ) ||
461  sFormat == QLatin1String( "ODS" ) );
462  }
463  }
464 
465  // Show symbology options only for some formats
466  if ( QgsVectorFileWriter::supportsFeatureStyles( sFormat ) && ( mOptions & Symbology ) )
467  {
468  mSymbologyExportLabel->setVisible( true );
469  mSymbologyExportComboBox->setVisible( true );
470  mScaleLabel->setVisible( true );
471  mScaleWidget->setVisible( true );
472  }
473  else
474  {
475  mSymbologyExportLabel->hide();
476  mSymbologyExportComboBox->hide();
477  mScaleLabel->hide();
478  mScaleWidget->hide();
479  }
480 
481  leLayername->setEnabled( sFormat == QLatin1String( "KML" ) ||
482  sFormat == QLatin1String( "GPKG" ) ||
483  sFormat == QLatin1String( "XLSX" ) ||
484  sFormat == QLatin1String( "ODS" ) ||
485  sFormat == QLatin1String( "FileGDB" ) ||
486  sFormat == QLatin1String( "SQLite" ) ||
487  sFormat == QLatin1String( "SpatiaLite" ) );
488 
489  if ( sFormat == QLatin1String( "XLSX" ) )
490  leLayername->setMaxLength( 31 );
491  else if ( leLayername->isEnabled() )
492  leLayername->setMaxLength( 32767 ); // default length
493 
494  if ( !leLayername->isEnabled() )
495  leLayername->setText( QString() );
496  else if ( leLayername->text().isEmpty() &&
497  !mFilename->filePath().isEmpty() )
498  {
499  QString layerName = QFileInfo( mFilename->filePath() ).baseName();
500  leLayername->setText( layerName );
501  }
502 
503  if ( mLayer )
504  {
505  mAttributeTable->setRowCount( mLayer->fields().count() );
506 
507  bool foundFieldThatCanBeExportedAsDisplayedValue = false;
508  for ( int i = 0; i < mLayer->fields().size(); ++i )
509  {
510  const QgsEditorWidgetSetup setup = QgsGui::editorWidgetRegistry()->findBest( mLayer, mLayer->fields()[i].name() );
511  if ( setup.type() != QLatin1String( "TextEdit" ) &&
512  QgsGui::editorWidgetRegistry()->factory( setup.type() ) )
513  {
514  foundFieldThatCanBeExportedAsDisplayedValue = true;
515  break;
516  }
517  }
518  if ( foundFieldThatCanBeExportedAsDisplayedValue )
519  {
520  mAttributeTable->setColumnCount( 3 );
521  mAttributeTable->setHorizontalHeaderLabels( QStringList() << tr( "Name" ) << tr( "Type" ) << tr( "Replace with displayed values" ) );
522  }
523  else
524  {
525  mAttributeTable->setColumnCount( 2 );
526  mAttributeTable->setHorizontalHeaderLabels( QStringList() << tr( "Name" ) << tr( "Type" ) );
527  }
528 
529  mAttributeTableItemChangedSlotEnabled = false;
530 
531  bool checkReplaceRawFieldValues = selectAllFields && isFormatForFieldsAsDisplayedValues;
532  for ( int i = 0; i < mLayer->fields().size(); ++i )
533  {
534  QgsField fld = mLayer->fields().at( i );
535  Qt::ItemFlags flags = mLayer->providerType() != QLatin1String( "oracle" ) || !fld.typeName().contains( QLatin1String( "SDO_GEOMETRY" ) ) ? Qt::ItemIsEnabled : Qt::NoItemFlags;
536  QTableWidgetItem *item = nullptr;
537  item = new QTableWidgetItem( fld.name() );
538  item->setFlags( flags | Qt::ItemIsUserCheckable );
539  item->setCheckState( ( selectAllFields ) ? Qt::Checked : Qt::Unchecked );
540  mAttributeTable->setItem( i, COLUMN_IDX_NAME, item );
541 
542  item = new QTableWidgetItem( fld.typeName() );
543  item->setFlags( flags );
544  mAttributeTable->setItem( i, COLUMN_IDX_TYPE, item );
545 
546  if ( foundFieldThatCanBeExportedAsDisplayedValue )
547  {
548  const QgsEditorWidgetSetup setup = QgsGui::editorWidgetRegistry()->findBest( mLayer, mLayer->fields()[i].name() );
549  QgsEditorWidgetFactory *factory = nullptr;
550  const QString widgetId( setup.type() );
551  if ( flags == Qt::ItemIsEnabled &&
552  widgetId != QLatin1String( "TextEdit" ) &&
553  ( factory = QgsGui::editorWidgetRegistry()->factory( widgetId ) ) )
554  {
555  item = new QTableWidgetItem( tr( "Use %1" ).arg( factory->name() ) );
556  item->setFlags( ( selectAllFields ) ? ( Qt::ItemIsEnabled | Qt::ItemIsUserCheckable ) : Qt::ItemIsUserCheckable );
557  const bool checkItem = ( selectAllFields && isFormatForFieldsAsDisplayedValues &&
558  ( widgetId == QLatin1String( "ValueMap" ) ||
559  widgetId == QLatin1String( "ValueRelation" ) ||
560  widgetId == QLatin1String( "CheckBox" ) ||
561  widgetId == QLatin1String( "RelationReference" ) ) );
562  checkReplaceRawFieldValues &= checkItem;
563  item->setCheckState( checkItem ?
564  Qt::Checked : Qt::Unchecked );
565  mAttributeTable->setItem( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE, item );
566  }
567  else
568  {
569  item = new QTableWidgetItem();
570  item->setFlags( Qt::NoItemFlags );
571  mAttributeTable->setItem( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE, item );
572  }
573  }
574  }
575 
576  mAttributeTableItemChangedSlotEnabled = true;
577 
578  mReplaceRawFieldValuesStateChangedSlotEnabled = false;
579  mReplaceRawFieldValues->setChecked( checkReplaceRawFieldValues );
580  mReplaceRawFieldValuesStateChangedSlotEnabled = true;
581  mReplaceRawFieldValues->setEnabled( selectAllFields );
582  mReplaceRawFieldValues->setVisible( foundFieldThatCanBeExportedAsDisplayedValue );
583 
584  mAttributeTable->resizeColumnsToContents();
585  }
586 
587  QgsVectorFileWriter::MetaData driverMetaData;
588 
589  while ( mDatasourceOptionsGroupBox->layout()->count() )
590  {
591  QLayoutItem *item = mDatasourceOptionsGroupBox->layout()->takeAt( 0 );
592  delete item->widget();
593  delete item;
594  }
595 
596  while ( mLayerOptionsGroupBox->layout()->count() )
597  {
598  QLayoutItem *item = mLayerOptionsGroupBox->layout()->takeAt( 0 );
599  delete item->widget();
600  delete item;
601  }
602 
603  typedef QPair<QLabel *, QWidget *> LabelControlPair;
604 
605  if ( QgsVectorFileWriter::driverMetadata( format(), driverMetaData ) )
606  {
607  if ( !driverMetaData.driverOptions.empty() )
608  {
609  mDatasourceOptionsGroupBox->setVisible( true );
610  QList<QPair<QLabel *, QWidget *> > controls = createControls( driverMetaData.driverOptions );
611 
612  QFormLayout *datasourceLayout = dynamic_cast<QFormLayout *>( mDatasourceOptionsGroupBox->layout() );
613 
614  const auto constControls = controls;
615  for ( LabelControlPair control : constControls )
616  {
617  datasourceLayout->addRow( control.first, control.second );
618  }
619  }
620  else
621  {
622  mDatasourceOptionsGroupBox->setVisible( false );
623  }
624 
625  if ( !driverMetaData.layerOptions.empty() )
626  {
627  mLayerOptionsGroupBox->setVisible( true );
628  QList<QPair<QLabel *, QWidget *> > controls = createControls( driverMetaData.layerOptions );
629 
630  QFormLayout *layerOptionsLayout = dynamic_cast<QFormLayout *>( mLayerOptionsGroupBox->layout() );
631 
632  const auto constControls = controls;
633  for ( LabelControlPair control : constControls )
634  {
635  layerOptionsLayout->addRow( control.first, control.second );
636  }
637  }
638  else
639  {
640  mLayerOptionsGroupBox->setVisible( false );
641  }
642 
643  if ( driverMetaData.compulsoryEncoding.isEmpty() )
644  {
645  mEncodingComboBox->setEnabled( true );
646  }
647  else
648  {
649  int idx = mEncodingComboBox->findText( driverMetaData.compulsoryEncoding );
650  if ( idx >= 0 )
651  {
652  mEncodingComboBox->setCurrentIndex( idx );
653  mEncodingComboBox->setDisabled( true );
654  }
655  else
656  {
657  mEncodingComboBox->setEnabled( true );
658  }
659  }
660 
661  }
662  else
663  {
664  mEncodingComboBox->setEnabled( true );
665  }
666 
667  GDALDriverH hDriver = GDALGetDriverByName( format().toUtf8().constData() );
668  if ( hDriver )
669  {
670  mAddToCanvas->setEnabled( GDALGetMetadataItem( hDriver, GDAL_DCAP_OPEN, nullptr ) != nullptr );
671  }
672 }
673 
674 void QgsVectorLayerSaveAsDialog::mReplaceRawFieldValues_stateChanged( int )
675 {
676  if ( !mReplaceRawFieldValuesStateChangedSlotEnabled )
677  return;
678  if ( mAttributeTable->columnCount() != 3 )
679  return;
680  mReplaceRawFieldValuesStateChangedSlotEnabled = false;
681  mAttributeTableItemChangedSlotEnabled = false;
682  if ( mReplaceRawFieldValues->checkState() != Qt::PartiallyChecked )
683  {
684  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
685  {
686  if ( mAttributeTable->item( i, COLUMN_IDX_NAME )->checkState() == Qt::Checked &&
687  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE ) &&
688  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsEnabled )
689  {
690  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setCheckState( mReplaceRawFieldValues->checkState() );
691  }
692  }
693  }
694  mReplaceRawFieldValues->setTristate( false );
695  mAttributeTableItemChangedSlotEnabled = true;
696  mReplaceRawFieldValuesStateChangedSlotEnabled = true;
697 }
698 
699 void QgsVectorLayerSaveAsDialog::mAttributeTable_itemChanged( QTableWidgetItem *item )
700 {
701  if ( !mAttributeTableItemChangedSlotEnabled )
702  return;
703  mReplaceRawFieldValuesStateChangedSlotEnabled = false;
704  mAttributeTableItemChangedSlotEnabled = false;
705  int row = item->row();
706  int column = item->column();
707  if ( column == COLUMN_IDX_NAME &&
708  mAttributeTable->item( row, column )->checkState() == Qt::Unchecked &&
709  mAttributeTable->columnCount() == 3 &&
710  mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE ) &&
711  ( mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsUserCheckable ) )
712  {
713  mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setCheckState( Qt::Unchecked );
714  mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setFlags( Qt::ItemIsUserCheckable );
715  bool checkBoxEnabled = false;
716  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
717  {
718  if ( mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE ) &&
719  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsEnabled )
720  {
721  checkBoxEnabled = true;
722  break;
723  }
724  }
725  mReplaceRawFieldValues->setEnabled( checkBoxEnabled );
726  if ( !checkBoxEnabled )
727  mReplaceRawFieldValues->setCheckState( Qt::Unchecked );
728  }
729  else if ( column == COLUMN_IDX_NAME &&
730  mAttributeTable->item( row, column )->checkState() == Qt::Checked &&
731  mAttributeTable->columnCount() == 3 &&
732  mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE ) &&
733  ( mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsUserCheckable ) )
734  {
735  mAttributeTable->item( row, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setFlags( Qt::ItemIsUserCheckable | Qt::ItemIsEnabled );
736  mReplaceRawFieldValues->setEnabled( true );
737  }
738  else if ( column == COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE &&
739  ( mAttributeTable->item( row, column )->flags() & Qt::ItemIsUserCheckable ) )
740  {
741  bool allChecked = true;
742  bool allUnchecked = true;
743  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
744  {
745  if ( mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE ) &&
746  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsEnabled )
747  {
748  if ( mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->checkState() == Qt::Unchecked )
749  allChecked = false;
750  else
751  allUnchecked = false;
752  }
753  }
754  mReplaceRawFieldValues->setCheckState( ( !allChecked && !allUnchecked ) ? Qt::PartiallyChecked : ( allChecked ) ? Qt::Checked : Qt::Unchecked );
755  }
756  mAttributeTableItemChangedSlotEnabled = true;
757  mReplaceRawFieldValuesStateChangedSlotEnabled = true;
758 }
759 
760 void QgsVectorLayerSaveAsDialog::mCrsSelector_crsChanged( const QgsCoordinateReferenceSystem &crs )
761 {
762  mSelectedCrs = crs;
763  mExtentGroupBox->setOutputCrs( mSelectedCrs );
764 }
765 
767 {
768  return mFilename->filePath();
769 }
770 
772 {
773  return leLayername->text();
774 }
775 
777 {
778  return mEncodingComboBox->currentText();
779 }
780 
782 {
783  return mFormatComboBox->currentData().toString();
784 }
785 
787 {
788  return mSelectedCrs.srsid();
789 }
790 
792 {
793  return mSelectedCrs;
794 }
795 
797 {
798  QStringList options;
799 
800  QgsVectorFileWriter::MetaData driverMetaData;
801 
802  if ( QgsVectorFileWriter::driverMetadata( format(), driverMetaData ) )
803  {
804  QMap<QString, QgsVectorFileWriter::Option *>::ConstIterator it;
805 
806  for ( it = driverMetaData.driverOptions.constBegin(); it != driverMetaData.driverOptions.constEnd(); ++it )
807  {
808  switch ( it.value()->type )
809  {
811  {
813  QSpinBox *sb = mDatasourceOptionsGroupBox->findChild<QSpinBox *>( it.key() );
814  if ( opt && sb && sb->value() != opt->defaultValue )
815  options << QStringLiteral( "%1=%2" ).arg( it.key() ).arg( sb->value() );
816  break;
817  }
818 
820  {
822  QComboBox *cb = mDatasourceOptionsGroupBox->findChild<QComboBox *>( it.key() );
823  if ( opt && cb && cb->itemData( cb->currentIndex() ) != opt->defaultValue )
824  options << QStringLiteral( "%1=%2" ).arg( it.key(), cb->currentText() );
825  break;
826  }
827 
829  {
831  QLineEdit *le = mDatasourceOptionsGroupBox->findChild<QLineEdit *>( it.key() );
832  if ( opt && le && le->text() != opt->defaultValue )
833  options << QStringLiteral( "%1=%2" ).arg( it.key(), le->text() );
834  break;
835  }
836 
838  {
840  dynamic_cast<QgsVectorFileWriter::HiddenOption *>( it.value() );
841  options << QStringLiteral( "%1=%2" ).arg( it.key(), opt->mValue );
842  break;
843  }
844  }
845  }
846  }
847 
848  QString plainText = mOgrDatasourceOptions->toPlainText().trimmed();
849  if ( !plainText.isEmpty() )
850  options += plainText.split( '\n' );
851 
852  return options;
853 }
854 
856 {
857  QStringList options;
858 
859  QgsVectorFileWriter::MetaData driverMetaData;
860 
861  if ( QgsVectorFileWriter::driverMetadata( format(), driverMetaData ) )
862  {
863  QMap<QString, QgsVectorFileWriter::Option *>::ConstIterator it;
864 
865  for ( it = driverMetaData.layerOptions.constBegin(); it != driverMetaData.layerOptions.constEnd(); ++it )
866  {
867  switch ( it.value()->type )
868  {
870  {
872  QSpinBox *sb = mLayerOptionsGroupBox->findChild<QSpinBox *>( it.key() );
873  if ( opt && sb && sb->value() != opt->defaultValue )
874  options << QStringLiteral( "%1=%2" ).arg( it.key() ).arg( sb->value() );
875  break;
876  }
877 
879  {
881  QComboBox *cb = mLayerOptionsGroupBox->findChild<QComboBox *>( it.key() );
882  if ( opt && cb && cb->itemData( cb->currentIndex() ) != opt->defaultValue )
883  options << QStringLiteral( "%1=%2" ).arg( it.key(), cb->currentText() );
884  break;
885  }
886 
888  {
890  QLineEdit *le = mLayerOptionsGroupBox->findChild<QLineEdit *>( it.key() );
891  if ( opt && le && le->text() != opt->defaultValue )
892  options << QStringLiteral( "%1=%2" ).arg( it.key(), le->text() );
893  break;
894  }
895 
897  {
899  dynamic_cast<QgsVectorFileWriter::HiddenOption *>( it.value() );
900  options << QStringLiteral( "%1=%2" ).arg( it.key(), opt->mValue );
901  break;
902  }
903  }
904  }
905  }
906 
907  QString plainText = mOgrLayerOptions->toPlainText().trimmed();
908  if ( !plainText.isEmpty() )
909  options += plainText.split( '\n' );
910 
911  return options;
912 }
913 
915 {
916  QgsAttributeList attributes;
917 
918  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
919  {
920  if ( mAttributeTable->item( i, COLUMN_IDX_NAME )->checkState() == Qt::Checked )
921  {
922  attributes.append( i );
923  }
924  }
925 
926  return attributes;
927 }
928 
930 {
931  QgsAttributeList attributes;
932 
933  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
934  {
935  if ( mAttributeTable->item( i, COLUMN_IDX_NAME )->checkState() == Qt::Checked &&
936  mAttributeTable->columnCount() == 3 &&
937  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->checkState() == Qt::Checked )
938  {
939  attributes.append( i );
940  }
941  }
942 
943  return attributes;
944 }
945 
947 {
948  return mAddToCanvas->isChecked() && mAddToCanvas->isEnabled();
949 }
950 
952 {
953  mAddToCanvas->setChecked( enabled );
954 }
955 
957 {
958  return mSymbologyExportComboBox->currentData().toInt();
959 }
960 
962 {
963  return mScaleWidget->scale();
964 }
965 
967 {
968  mMapCanvas = canvas;
969  mScaleWidget->setMapCanvas( canvas );
970  mScaleWidget->setShowCurrentScaleButton( true );
971  mExtentGroupBox->setCurrentExtent( canvas->mapSettings().visibleExtent(), canvas->mapSettings().destinationCrs() );
972 }
973 
975 {
976  return mExtentGroupBox->isChecked();
977 }
978 
980 {
981  return mExtentGroupBox->outputExtent();
982 }
983 
985 {
986  mSelectedOnly->setChecked( onlySelected );
987 }
988 
990 {
991  return mSelectedOnly->isChecked();
992 }
993 
995 {
996  return mCheckPersistMetadata->isChecked();
997 }
998 
1000 {
1001  int currentIndexData = mGeometryTypeComboBox->currentData().toInt();
1002  if ( currentIndexData == -1 )
1003  {
1004  //automatic
1005  return QgsWkbTypes::Unknown;
1006  }
1007 
1008  return static_cast< QgsWkbTypes::Type >( currentIndexData );
1009 }
1010 
1012 {
1013  int currentIndexData = mGeometryTypeComboBox->currentData().toInt();
1014  return currentIndexData == -1;
1015 }
1016 
1018 {
1019  return mForceMultiCheckBox->isChecked();
1020 }
1021 
1023 {
1024  mForceMultiCheckBox->setChecked( checked );
1025 }
1026 
1028 {
1029  return mIncludeZCheckBox->isChecked();
1030 }
1031 
1033 {
1034  return mActionOnExistingFile;
1035 }
1036 
1038 {
1039  mIncludeZCheckBox->setChecked( checked );
1040 }
1041 
1042 void QgsVectorLayerSaveAsDialog::mSymbologyExportComboBox_currentIndexChanged( const QString &text )
1043 {
1044  bool scaleEnabled = true;
1045  if ( text == tr( "No symbology" ) )
1046  {
1047  scaleEnabled = false;
1048  }
1049  mScaleWidget->setEnabled( scaleEnabled );
1050  mScaleLabel->setEnabled( scaleEnabled );
1051 }
1052 
1053 void QgsVectorLayerSaveAsDialog::mGeometryTypeComboBox_currentIndexChanged( int index )
1054 {
1055  int currentIndexData = mGeometryTypeComboBox->itemData( index ).toInt();
1056 
1057  if ( currentIndexData != -1 && currentIndexData != QgsWkbTypes::NoGeometry )
1058  {
1059  mForceMultiCheckBox->setEnabled( true );
1060  mIncludeZCheckBox->setEnabled( true );
1061  }
1062  else
1063  {
1064  mForceMultiCheckBox->setEnabled( false );
1065  mForceMultiCheckBox->setChecked( false );
1066  mIncludeZCheckBox->setEnabled( false );
1067  mIncludeZCheckBox->setChecked( false );
1068  }
1069 }
1070 
1071 void QgsVectorLayerSaveAsDialog::mSelectAllAttributes_clicked()
1072 {
1073  mAttributeTableItemChangedSlotEnabled = false;
1074  mReplaceRawFieldValuesStateChangedSlotEnabled = false;
1075  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
1076  {
1077  if ( mAttributeTable->item( i, COLUMN_IDX_NAME )->flags() & Qt::ItemIsEnabled )
1078  {
1079  if ( mAttributeTable->columnCount() == 3 &&
1080  ( mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsUserCheckable ) )
1081  {
1082  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setFlags( Qt::ItemIsUserCheckable | Qt::ItemIsEnabled );
1083  }
1084  mAttributeTable->item( i, COLUMN_IDX_NAME )->setCheckState( Qt::Checked );
1085  }
1086  }
1087  if ( mAttributeTable->columnCount() == 3 )
1088  {
1089  mReplaceRawFieldValues->setEnabled( true );
1090  }
1091  mAttributeTableItemChangedSlotEnabled = true;
1092  mReplaceRawFieldValuesStateChangedSlotEnabled = true;
1093 }
1094 
1095 void QgsVectorLayerSaveAsDialog::mDeselectAllAttributes_clicked()
1096 {
1097  mAttributeTableItemChangedSlotEnabled = false;
1098  mReplaceRawFieldValuesStateChangedSlotEnabled = false;
1099  for ( int i = 0; i < mAttributeTable->rowCount(); i++ )
1100  {
1101  mAttributeTable->item( i, COLUMN_IDX_NAME )->setCheckState( Qt::Unchecked );
1102  if ( mAttributeTable->columnCount() == 3 &&
1103  ( mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->flags() & Qt::ItemIsUserCheckable ) )
1104  {
1105  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setFlags( Qt::ItemIsUserCheckable );
1106  mAttributeTable->item( i, COLUMN_IDX_EXPORT_AS_DISPLAYED_VALUE )->setCheckState( Qt::Unchecked );
1107  }
1108  }
1109  if ( mAttributeTable->columnCount() == 3 )
1110  {
1111  mReplaceRawFieldValues->setCheckState( Qt::Unchecked );
1112  mReplaceRawFieldValues->setEnabled( false );
1113  }
1114  mAttributeTableItemChangedSlotEnabled = true;
1115  mReplaceRawFieldValuesStateChangedSlotEnabled = true;
1116 }
1117 
1118 void QgsVectorLayerSaveAsDialog::showHelp()
1119 {
1120  QgsHelp::openHelp( QStringLiteral( "managing_data_source/create_layers.html#creating-new-layers-from-an-existing-layer" ) );
1121 }
This class represents a coordinate reference system (CRS).
QgsDatumEnsemble datumEnsemble() const SIP_THROW(QgsNotSupportedException)
Attempts to retrieve datum ensemble details from the CRS.
long srsid() const
Returns the internal CRS ID, if available.
Contains information about a datum ensemble.
Definition: qgsdatums.h:95
bool isValid() const
Returns true if the datum ensemble is a valid object, or false if it is a null/invalid object.
Definition: qgsdatums.h:102
QString name() const
Display name of datum ensemble.
Definition: qgsdatums.h:107
Every attribute editor widget needs a factory, which inherits this class.
QString name()
Returns The human readable identifier name of this widget type.
QgsEditorWidgetSetup findBest(const QgsVectorLayer *vl, const QString &fieldName) const
Find the best editor widget and its configuration for a given field.
Holder for the widget type and its configuration for a field.
Encapsulate a field in an attribute table or data source.
Definition: qgsfield.h:51
QString typeName() const
Gets the field type.
Definition: qgsfield.cpp:138
QString name
Definition: qgsfield.h:60
int count() const
Returns number of items.
Definition: qgsfields.cpp:133
QgsField at(int i) const
Returns the field at particular index (must be in range 0..N-1).
Definition: qgsfields.cpp:163
@ SaveFile
Select a single new or pre-existing file.
Definition: qgsfilewidget.h:71
void fileChanged(const QString &path)
Emitted whenever the current file or directory path is changed.
static QgsEditorWidgetRegistry * editorWidgetRegistry()
Returns the global editor widget registry, used for managing all known edit widget factories.
Definition: qgsgui.cpp:83
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:168
static void openHelp(const QString &key)
Opens help topic for the given help key using default system web browser.
Definition: qgshelp.cpp:36
static QIcon iconForWkbType(QgsWkbTypes::Type type)
Returns the icon for a vector layer whose geometry type is provided.
Map canvas is a class for displaying all GIS data types on a canvas.
Definition: qgsmapcanvas.h:89
const QgsMapSettings & mapSettings() const
Gets access to properties used for map rendering.
QString providerType() const
Returns the provider type (provider key) for this layer.
QgsCoordinateReferenceSystem crs
Definition: qgsmaplayer.h:79
QgsRectangle visibleExtent() const
Returns the actual extent derived from requested extent that takes output image size into account.
QgsCoordinateReferenceSystem destinationCrs() const
Returns the destination coordinate reference system for the map render.
Custom exception class which is raised when an operation is not supported.
Definition: qgsexception.h:118
void crsChanged(const QgsCoordinateReferenceSystem &)
Emitted when the selected CRS is changed.
QList< QgsProviderSublayerDetails > querySublayers(const QString &uri, Qgis::SublayerQueryFlags flags=Qgis::SublayerQueryFlags(), QgsFeedback *feedback=nullptr) const
Queries the specified uri and returns a list of any valid sublayers found in the dataset which can be...
static QgsProviderRegistry * instance(const QString &pluginPath=QString())
Means of accessing canonical single instance.
Contains details about a sub layer available from a dataset.
A rectangle specified with double values.
Definition: qgsrectangle.h:42
This class is a composition of two QSettings instances:
Definition: qgssettings.h:62
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.
static QStringList availableEncodings()
Returns a list of available encodings.
QgsVectorFileWriter::OptionType type
A convenience class for writing vector layers to disk based formats (e.g.
@ CanAppendToExistingLayer
Flag to indicate that new features can be added to an existing layer.
@ CanAddNewLayer
Flag to indicate that a new layer can be added to the dataset.
@ CanDeleteLayer
Flag to indicate that an existing layer can be deleted.
static QgsVectorFileWriter::EditionCapabilities editionCapabilities(const QString &datasetName)
Returns edition capabilities for an existing dataset name.
static bool supportsFeatureStyles(const QString &driverName)
Returns true if the specified driverName supports feature styles.
static bool targetLayerExists(const QString &datasetName, const QString &layerName)
Returns whether the target layer already exists.
static bool driverMetadata(const QString &driverName, MetaData &driverMetadata)
static QString filterForDriver(const QString &driverName)
Creates a filter for an OGR driver key.
static bool areThereNewFieldsToCreate(const QString &datasetName, const QString &layerName, QgsVectorLayer *layer, const QgsAttributeList &attributes)
Returns whether there are among the attributes specified some that do not exist yet in the layer.
static QList< QgsVectorFileWriter::DriverDetails > ogrDriverList(VectorFormatOptions options=SortRecommended)
Returns the driver list that can be used for dialogs.
ActionOnExistingFile
Combination of CanAddNewLayer, CanAppendToExistingLayer, CanAddNewFieldsToExistingLayer or CanDeleteL...
@ CreateOrOverwriteLayer
Create or overwrite layer.
@ CreateOrOverwriteFile
Create or overwrite file.
@ AppendToLayerNoNewFields
Append features to existing layer, but do not create new fields.
@ AppendToLayerAddFields
Append features to existing layer, and create new fields if needed.
bool onlySelected() const
Returns whether only selected features will be saved.
bool forceMulti() const
Returns true if force multi geometry type is checked.
QString filename() const
Returns the target filename.
QgsAttributeList selectedAttributes() const
Returns a list of attributes which are selected for saving.
QgsRectangle filterExtent() const
Determines the extent to be exported.
Q_DECL_DEPRECATED long crs() const
Returns the internal CRS ID.
QString format() const
The format in which the export should be written.
QStringList datasourceOptions() const
Returns a list of additional data source options which are passed to OGR.
bool persistMetadata() const
Returns true if the persist metadata (copy source metadata to destination layer) option is checked.
QString encoding() const
The encoding of the target file.
void setIncludeZ(bool checked)
Sets whether the include z dimension checkbox should be checked.
void setOnlySelected(bool onlySelected)
Sets whether only selected features will be saved.
@ DestinationCrs
Show destination CRS (reprojection) option.
@ AddToCanvas
Show add to map option.
@ Symbology
Show symbology options.
@ SelectedOnly
Show selected features only option.
@ Fields
Show field customization group.
bool automaticGeometryType() const
Returns true if geometry type is set to automatic.
QString layername() const
Returns the target layer name.
QgsWkbTypes::Type geometryType() const
Returns the selected flat geometry type for the export.
Q_DECL_DEPRECATED QgsVectorLayerSaveAsDialog(long srsid, QWidget *parent=nullptr, Qt::WindowFlags fl=Qt::WindowFlags())
Construct a new QgsVectorLayerSaveAsDialog.
bool includeZ() const
Returns true if include z dimension is checked.
QgsCoordinateReferenceSystem crsObject() const
Returns the CRS chosen for export.
QStringList layerOptions() const
Returns a list of additional layer options which are passed to OGR.
void setForceMulti(bool checked)
Sets whether the force multi geometry checkbox should be checked.
bool addToCanvas() const
Returns true if the "add to canvas" checkbox is checked.
void setMapCanvas(QgsMapCanvas *canvas)
Sets a map canvas to associate with the dialog.
QgsVectorFileWriter::ActionOnExistingFile creationActionOnExistingFile() const
Returns creation action.
int symbologyExport() const
Returns type of symbology export.
QgsAttributeList attributesAsDisplayedValues() const
Returns selected attributes that must be exported with their displayed values instead of their raw va...
double scale() const
Returns the specified map scale.
bool hasFilterExtent() const
Determines if filtering the export by an extent is activated.
void setAddToCanvas(bool checked)
Sets whether the "add to canvas" checkbox should be checked.
Represents a vector layer which manages a vector based data sets.
QgsFields fields() const FINAL
Returns the list of fields of this layer.
int selectedFeatureCount() const
Returns the number of features that are selected in this layer.
QgsRectangle extent() const FINAL
Returns the extent of the layer.
static QString translatedDisplayString(Type type) SIP_HOLDGIL
Returns a translated display string type for a WKB type, e.g., the geometry name used in WKT geometry...
Type
The WKB type describes the number of dimensions a geometry has.
Definition: qgswkbtypes.h:70
@ GeometryCollection
Definition: qgswkbtypes.h:79
QList< int > QgsAttributeList
Definition: qgsfield.h:26
const QgsCoordinateReferenceSystem & crs
Details of available driver formats.
QMap< QString, QgsVectorFileWriter::Option * > driverOptions
QMap< QString, QgsVectorFileWriter::Option * > layerOptions
QString compulsoryEncoding
Some formats require a compulsory encoding, typically UTF-8. If no compulsory encoding,...