QGIS API Documentation 4.1.0-Master (5bf3c20f3c9)
Loading...
Searching...
No Matches
qgsaddattrdialog.cpp
Go to the documentation of this file.
1/***************************************************************************
2 qgsaddattrdialog.h - description
3 -------------------
4 begin : January 2005
5 copyright : (C) 2005 by Marco Hugentobler
7 ***************************************************************************/
8
9/***************************************************************************
10 * *
11 * This program is free software; you can redistribute it and/or modify *
12 * it under the terms of the GNU General Public License as published by *
13 * the Free Software Foundation; either version 2 of the License, or *
14 * (at your option) any later version. *
15 * *
16 ***************************************************************************/
17
18#include "qgsaddattrdialog.h"
19
20#include "qgsfields.h"
21#include "qgslogger.h"
23#include "qgsvectorlayer.h"
24
25#include <QMessageBox>
26#include <QString>
27
28#include "moc_qgsaddattrdialog.cpp"
29
30using namespace Qt::StringLiterals;
31
32QgsAddAttrDialog::QgsAddAttrDialog( QgsVectorLayer *vlayer, QWidget *parent, Qt::WindowFlags fl )
33 : QDialog( parent, fl )
34 , mIsShapeFile( vlayer && vlayer->providerType() == "ogr"_L1 && vlayer->storageType() == "ESRI Shapefile"_L1 )
35{
36 setupUi( this );
37 connect( mTypeBox, static_cast<void ( QComboBox::* )( int )>( &QComboBox::currentIndexChanged ), this, &QgsAddAttrDialog::mTypeBox_currentIndexChanged );
38 connect( mLength, &QSpinBox::editingFinished, this, &QgsAddAttrDialog::mLength_editingFinished );
39
40 if ( !vlayer || !vlayer->dataProvider() )
41 return;
42
44
45 //fill data types into the combo box
46 const QList<QgsVectorDataProvider::NativeType> &typelist = vlayer->dataProvider()->nativeTypes();
47 for ( int i = 0; i < typelist.size(); i++ )
48 {
50 u"name:%1 type:%2 typeName:%3 length:%4-%5 prec:%6-%7"_s.arg( typelist[i].mTypeDesc )
51 .arg( typelist[i].mType )
52 .arg( typelist[i].mTypeName )
53 .arg( typelist[i].mMinLen )
54 .arg( typelist[i].mMaxLen )
55 .arg( typelist[i].mMinPrec )
56 .arg( typelist[i].mMaxPrec ),
57 2
58 );
59
60 whileBlocking( mTypeBox )->addItem( QgsFields::iconForFieldType( typelist[i].mType, typelist[i].mSubType, typelist[i].mTypeName ), typelist[i].mTypeDesc );
61 mTypeBox->setItemData( i, static_cast<int>( typelist[i].mType ), Qt::UserRole );
62 mTypeBox->setItemData( i, typelist[i].mTypeName, Qt::UserRole + 1 );
63 mTypeBox->setItemData( i, typelist[i].mMinLen, Qt::UserRole + 2 );
64 mTypeBox->setItemData( i, typelist[i].mMaxLen, Qt::UserRole + 3 );
65 mTypeBox->setItemData( i, typelist[i].mMinPrec, Qt::UserRole + 4 );
66 mTypeBox->setItemData( i, typelist[i].mMaxPrec, Qt::UserRole + 5 );
67 }
68
69 //default values for field width and precision
70 mLength->setValue( 10 );
71 mLength->setClearValue( 10 );
72 mPrec->setValue( 3 );
73 mPrec->setClearValue( 3 );
74 mTypeBox_currentIndexChanged( 0 );
75
76 if ( mIsShapeFile )
77 mNameEdit->setMaxLength( 10 );
78
79 mNameEdit->setFocus();
80
81 if ( !( attributeEditCapabilities & Qgis::VectorDataProviderAttributeEditCapability::EditAlias ) )
82 {
83 mLabelAlias->hide();
84 mAliasEdit->hide();
85 }
86 if ( !( attributeEditCapabilities & Qgis::VectorDataProviderAttributeEditCapability::EditComment ) )
87 {
88 mLabelComment->hide();
89 mCommentEdit->hide();
90 }
91}
92
93void QgsAddAttrDialog::setIllegalFieldNames( const QSet<QString> &names )
94{
95 mIllegalFieldNames = names;
96}
97
98void QgsAddAttrDialog::mTypeBox_currentIndexChanged( int idx )
99{
100 mTypeName->setText( mTypeBox->itemData( idx, Qt::UserRole + 1 ).toString() );
101
102 mLength->setMinimum( mTypeBox->itemData( idx, Qt::UserRole + 2 ).toInt() );
103 mLength->setMaximum( mTypeBox->itemData( idx, Qt::UserRole + 3 ).toInt() );
104 mLength->setVisible( mLength->minimum() < mLength->maximum() );
105 mLengthLabel->setVisible( mLength->minimum() < mLength->maximum() );
106 if ( mLength->value() < mLength->minimum() )
107 mLength->setValue( mLength->minimum() );
108 if ( mLength->value() > mLength->maximum() )
109 mLength->setValue( mLength->maximum() );
110 setPrecisionMinMax();
111}
112
113void QgsAddAttrDialog::mLength_editingFinished()
114{
115 setPrecisionMinMax();
116}
117
118void QgsAddAttrDialog::setPrecisionMinMax()
119{
120 const int idx = mTypeBox->currentIndex();
121 const int minPrecType = mTypeBox->itemData( idx, Qt::UserRole + 4 ).toInt();
122 const int maxPrecType = mTypeBox->itemData( idx, Qt::UserRole + 5 ).toInt();
123 const bool precisionIsEnabled = minPrecType < maxPrecType;
124 mPrec->setEnabled( precisionIsEnabled );
125 mPrec->setVisible( precisionIsEnabled );
126 mPrecLabel->setVisible( precisionIsEnabled );
127
128 // Do not set min/max if it's disabled or we'll loose the default value,
129 // see https://github.com/qgis/QGIS/issues/26880 - QGIS saves integer field when
130 // I create a new real field through field calculator (Update field works as intended)
131 if ( precisionIsEnabled )
132 {
133 mPrec->setMinimum( minPrecType );
134 mPrec->setMaximum( std::max( minPrecType, std::min( maxPrecType, mLength->value() ) ) );
135 }
136}
137
138void QgsAddAttrDialog::accept()
139{
140 const QString newName = mNameEdit->text().trimmed();
141 if ( mIsShapeFile && newName.compare( "shape"_L1, Qt::CaseInsensitive ) == 0 )
142 {
143 QMessageBox::warning( this, tr( "Add Field" ), tr( "Invalid field name. This field name is reserved and cannot be used." ) );
144 return;
145 }
146
147
148 for ( const QString &illegalName : std::as_const( mIllegalFieldNames ) )
149 {
150 if ( newName.compare( illegalName, Qt::CaseInsensitive ) == 0 )
151 {
152 QMessageBox::warning( this, tr( "Add Field" ), tr( "%1 is an illegal field name for this format and cannot be used." ).arg( newName ) );
153 return;
154 }
155 }
156
157 if ( mNameEdit->text().isEmpty() )
158 {
159 QMessageBox::warning( this, tr( "Add Field" ), tr( "No name specified. Please specify a name to create a new field." ) );
160 return;
161 }
162
163 QDialog::accept();
164}
165
167{
169 u"idx:%1 name:%2 type:%3 typeName:%4 length:%5 prec:%6 comment:%7"_s.arg( mTypeBox->currentIndex() )
170 .arg( mNameEdit->text() )
171 .arg( mTypeBox->currentData( Qt::UserRole ).toInt() )
172 .arg( mTypeBox->currentData( Qt::UserRole + 1 ).toString() )
173 .arg( mLength->value() )
174 .arg( mPrec->value() )
175 .arg( mCommentEdit->text() ),
176 2
177 );
178
179 QgsField res = QgsField(
180 mNameEdit->text(),
181 ( QMetaType::Type ) mTypeBox->currentData( Qt::UserRole ).toInt(),
182 mTypeBox->currentData( Qt::UserRole + 1 ).toString(),
183 mLength->value(),
184 mPrec->isEnabled() ? mPrec->value() : 0,
185 mCommentEdit->text(),
186 static_cast<QMetaType::Type>( mTypeBox->currentData( Qt::UserRole ).toInt() ) == QMetaType::Type::QVariantMap ? QMetaType::Type::QString : QMetaType::Type::UnknownType
187 );
188
189 if ( !mAliasEdit->text().isEmpty() )
190 res.setAlias( mAliasEdit->text() );
191
192 return res;
193}
@ EditComment
Allows editing comments.
Definition qgis.h:618
QFlags< VectorDataProviderAttributeEditCapability > VectorDataProviderAttributeEditCapabilities
Attribute editing capabilities which may be supported by vector data providers.
Definition qgis.h:628
QgsField field() const
Returns a field for the configured attribute.
void setIllegalFieldNames(const QSet< QString > &names)
Sets a list of field names which are considered illegal and should not be accepted by the dialog.
QgsAddAttrDialog(QgsVectorLayer *vlayer, QWidget *parent=nullptr, Qt::WindowFlags fl=QgsGuiUtils::ModalDialogFlags)
constructor
Encapsulate a field in an attribute table or data source.
Definition qgsfield.h:56
void setAlias(const QString &alias)
Sets the alias for the field (the friendly displayed name of the field ).
Definition qgsfield.cpp:293
static QIcon iconForFieldType(QMetaType::Type type, QMetaType::Type subType=QMetaType::Type::UnknownType, const QString &typeString=QString())
Returns an icon corresponding to a field type.
QList< QgsVectorDataProvider::NativeType > nativeTypes() const
Returns the names of the supported types.
virtual Qgis::VectorDataProviderAttributeEditCapabilities attributeEditCapabilities() const
Returns the provider's supported attribute editing capabilities.
Represents a vector layer which manages a vector based dataset.
QgsVectorDataProvider * dataProvider() final
Returns the layer's data provider, it may be nullptr.
QgsSignalBlocker< Object > whileBlocking(Object *object)
Temporarily blocks signals from a QObject while calling a single method from the object.
Definition qgis.h:6880
#define QgsDebugMsgLevel(str, level)
Definition qgslogger.h:63