1#include "moc_qgsfield.cpp"
28#include <QJsonDocument>
39 : mName( nam ), mType( typ ), mLength( len ), mPrecision( prec ), mNumeric( num )
50 const QString &
typeName,
int len,
int prec,
const QString &comment, QMetaType::Type subType )
56 const QString &
typeName,
int len,
int prec,
const QString &comment, QVariant::Type subType )
83 return *( other.d ) == *d;
88 return !( *
this == other );
98 if ( !d->alias.isEmpty() )
106 if (
alias().isEmpty() )
110 return QStringLiteral(
"%1 (%2)" ).arg(
name(),
alias() );
116 if ( typeStr.isEmpty() )
122 typeStr += QStringLiteral(
"(%1, %2)" ).arg(
length() ).arg(
precision() );
124 typeStr += QStringLiteral(
"(%1)" ).arg(
length() );
126 if ( showConstraints )
129 ? QStringLiteral(
" NOT NULL" )
130 : QStringLiteral(
" NULL" );
133 ? QStringLiteral(
" UNIQUE" )
142 if ( d->type == QMetaType::Type::User )
144 if ( d->typeName.compare( QLatin1String(
"geometry" ), Qt::CaseInsensitive ) == 0 )
146 return QObject::tr(
"Geometry" );
184 return d->metadata.value( property );
194 return d->metadata.value(
static_cast< int >( property ) );
204 d->metadata[
static_cast< int >( property )] = value;
209 d->metadata[ property ] = value;
214 return d->type == QMetaType::Type::Double || d->type == QMetaType::Type::Int || d->type == QMetaType::Type::UInt || d->type == QMetaType::Type::LongLong || d->type == QMetaType::Type::ULongLong;
219 return d->type == QMetaType::Type::QDate || d->type == QMetaType::Type::QTime || d->type == QMetaType::Type::QDateTime;
274 return d->defaultValueDefinition;
289 return d->constraints;
325 if ( v.userType() == qMetaTypeId<QgsReferencedGeometry>() )
332 QString wkt = geom.
asWkt();
333 if ( wkt.length() >= 1050 )
338 return formattedText;
343 if ( d->type == QMetaType::Type::Double )
353 if ( QLocale().decimalPoint() !=
'.' ||
354 !( QLocale().numberOptions() & QLocale::NumberOption::OmitGroupSeparator ) )
356 if ( d->precision > 0 )
358 if ( -1 < v.toDouble() && v.toDouble() < 1 )
360 return QLocale().toString( v.toDouble(),
'g', d->precision );
364 return QLocale().toString( v.toDouble(),
'f', d->precision );
371 const QString s( v.toString() );
372 const int dotPosition( s.indexOf(
'.' ) );
374 if ( dotPosition < 0 && s.indexOf(
'e' ) < 0 )
377 return QLocale().toString( v.toDouble(),
'f',
precision );
382 else precision = s.length() - dotPosition - 1;
384 if ( -1 < v.toDouble() && v.toDouble() < 1 )
386 return QLocale().toString( v.toDouble(),
'g',
precision );
390 return QLocale().toString( v.toDouble(),
'f',
precision );
396 else if ( d->precision > 0 )
398 if ( -1 < v.toDouble() && v.toDouble() < 1 )
400 return QString::number( v.toDouble(),
'g', d->precision );
404 return QString::number( v.toDouble(),
'f', d->precision );
409 const double vDouble = v.toDouble();
411 if ( std::fabs( vDouble ) < 1e-04 )
412 return QString::number( vDouble,
'g', QLocale::FloatingPointShortest );
414 return QString::number( vDouble,
'f', QLocale::FloatingPointShortest );
419 !( QLocale().numberOptions() & QLocale::NumberOption::OmitGroupSeparator ) )
422 const qlonglong converted( v.toLongLong( &ok ) );
424 return QLocale().toString( converted );
426 else if ( d->typeName.compare( QLatin1String(
"json" ), Qt::CaseInsensitive ) == 0 || d->typeName == QLatin1String(
"jsonb" ) )
428 const QJsonDocument doc = QJsonDocument::fromVariant( v );
429 return QString::fromUtf8( doc.toJson().constData() );
431 else if ( d->type == QMetaType::Type::QByteArray )
433 return QObject::tr(
"BLOB" );
435 else if ( d->type == QMetaType::Type::QStringList || d->type == QMetaType::Type::QVariantList )
438 const QVariantList list = v.toList();
439 for (
const QVariant &var : list )
441 if ( !result.isEmpty() )
442 result.append( QStringLiteral(
", " ) );
443 result.append( var.toString() );
457 return QObject::tr(
"None" );
459 return QObject::tr(
"Not searchable" );
461 return QObject::tr(
"Do not expose via WMS" );
463 return QObject::tr(
"Do not expose via WFS" );
476 const QVariant original = v;
478 errorMessage->clear();
482 v.convert( d->type );
486 if ( v.userType() == qMetaTypeId< QgsUnsetAttributeValue >() )
491 if ( d->type == QMetaType::Type::Int && v.toInt() != v.toLongLong() )
495 *errorMessage = QObject::tr(
"Value \"%1\" is too large for integer field" ).arg( original.toLongLong() );
501 if ( d->type == QMetaType::Type::Double && v.userType() == QMetaType::Type::QString )
504 if ( !tmp.convert( d->type ) )
515 if ( QLocale().decimalPoint() !=
'.' )
517 d = QLocale( QLocale::C ).toDouble( v.toString(), &ok );
528 if ( d->type == QMetaType::Type::Int && v.userType() == QMetaType::Type::QString )
531 if ( !tmp.convert( d->type ) )
545 if ( d->type == QMetaType::Type::LongLong && v.userType() == QMetaType::Type::QString )
548 if ( !tmp.convert( d->type ) )
563 if ( d->type == QMetaType::Type::Int && v.canConvert( QMetaType::Type::Double ) )
566 const double dbl = v.toDouble( &ok );
573 *errorMessage = QObject::tr(
"Value \"%1\" is not a number" ).arg( original.toString() );
578 const double round = std::round( dbl );
579 if ( round > std::numeric_limits<int>::max() || round < -std::numeric_limits<int>::max() )
585 *errorMessage = QObject::tr(
"Value \"%1\" is too large for integer field" ).arg( original.toDouble() );
589 v = QVariant(
static_cast< int >( std::round( dbl ) ) );
595 if ( d->type == QMetaType::Type::LongLong && v.canConvert( QMetaType::Type::Double ) )
599 if ( !tmp.convert( d->type ) )
602 const double dbl = v.toDouble( &ok );
609 *errorMessage = QObject::tr(
"Value \"%1\" is not a number" ).arg( original.toString() );
614 const double round = std::round( dbl );
615 if ( round >
static_cast<double>( std::numeric_limits<long long>::max() ) || round <
static_cast<double>( -std::numeric_limits<long long>::max() ) )
621 *errorMessage = QObject::tr(
"Value \"%1\" is too large for long long field" ).arg( original.toDouble() );
625 v = QVariant(
static_cast< long long >( std::round( dbl ) ) );
630 if ( d->typeName.compare( QLatin1String(
"json" ), Qt::CaseInsensitive ) == 0 || d->typeName.compare( QLatin1String(
"jsonb" ), Qt::CaseInsensitive ) == 0 )
632 if ( d->type == QMetaType::Type::QString )
634 const QJsonDocument doc = QJsonDocument::fromVariant( v );
637 v = QString::fromUtf8( doc.toJson( QJsonDocument::Compact ).constData() );
643 else if ( d->type == QMetaType::Type::QVariantMap )
645 if ( v.userType() == QMetaType::Type::QStringList || v.userType() == QMetaType::Type::QVariantList || v.userType() == QMetaType::Type::QVariantMap )
654 if ( ( d->type == QMetaType::Type::QStringList || ( d->type == QMetaType::Type::QVariantList && d->subType == QMetaType::Type::QString ) )
655 && ( v.userType() == QMetaType::Type::QString ) )
657 v = QStringList( { v.toString() } );
661 if ( ( d->type == QMetaType::Type::QStringList || d->type == QMetaType::Type::QVariantList ) && !( v.userType() == QMetaType::Type::QStringList || v.userType() == QMetaType::Type::QVariantList ) )
666 *errorMessage = QObject::tr(
"Could not convert value \"%1\" to target list type" ).arg( original.toString() );
672 if ( d->type == QMetaType::Type::QString && v.userType() == qMetaTypeId<QgsReferencedGeometry>() )
681 v = QVariant( geom.asWkt() );
685 else if ( d->type == QMetaType::Type::User && d->typeName.compare( QLatin1String(
"geometry" ), Qt::CaseInsensitive ) == 0 )
687 if ( v.userType() == qMetaTypeId<QgsReferencedGeometry>() || v.userType() == qMetaTypeId< QgsGeometry>() )
691 else if ( v.userType() == QMetaType::Type::QString )
696 v = QVariant::fromValue( geom );
702 else if ( !v.convert( d->type ) )
707 *errorMessage = QObject::tr(
"Could not convert value \"%1\" to target type \"%2\"" )
708 .arg( original.toString(),
714 if ( d->type == QMetaType::Type::Double && d->precision > 0 )
716 const double s = std::pow( 10, d->precision );
717 const double d = v.toDouble() * s;
718 v = QVariant( ( d < 0 ? std::ceil( d - 0.5 ) : std::floor( d + 0.5 ) ) / s );
722 if ( d->type == QMetaType::Type::QString && d->length > 0 && v.toString().length() > d->length )
724 const int length = v.toString().length();
725 v = v.toString().left( d->length );
728 *errorMessage = QObject::tr(
"String of length %1 exceeds maximum field length (%2)" ).arg(
length ).arg( d->length );
736QgsField::operator QVariant()
const
738 return QVariant::fromValue( *
this );
736QgsField::operator QVariant()
const {
…}
743 d->editorWidgetSetup = v;
748 return d->editorWidgetSetup;
753 d->isReadOnly = readOnly;
758 return d->isReadOnly;
763 return d->splitPolicy;
768 d->splitPolicy = policy;
773 return d->duplicatePolicy;
778 d->duplicatePolicy = policy;
783 return d->mergePolicy;
788 d->mergePolicy = policy;
800 out << static_cast< quint32 >( field.
type() );
805 out << field.
alias();
817 out << static_cast< quint32 >( field.
subType() );
831 quint32 originNotNull;
832 quint32 originUnique;
833 quint32 originExpression;
834 quint32 strengthNotNull;
835 quint32 strengthUnique;
836 quint32 strengthExpression;
846 QString defaultValueExpression;
847 QString constraintExpression;
848 QString constraintDescription;
849 QMap< int, QVariant > metadata;
852 >> defaultValueExpression >> applyOnUpdate >> constraints >> originNotNull >> originUnique >> originExpression >> strengthNotNull >> strengthUnique >> strengthExpression >>
853 constraintExpression >> constraintDescription >> subType >> splitPolicy >> duplicatePolicy >> metadata;
855 field.
setType(
static_cast< QMetaType::Type
>( type ) );
857 field.
setLength(
static_cast< int >( length ) );
888 field.
setSubType(
static_cast< QMetaType::Type
>( subType ) );
FieldDomainMergePolicy
Merge policy for field domains.
FieldDomainSplitPolicy
Split policy for field domains.
FieldDuplicatePolicy
Duplicate policy for fields.
FieldMetadataProperty
Standard field metadata values.
FieldConfigurationFlag
Configuration flags for fields These flags are meant to be user-configurable and are not describing a...
@ HideFromWfs
Field is not available if layer is served as WFS from QGIS server.
@ NoFlag
No flag is defined.
@ NotSearchable
Defines if the field is searchable (used in the locator search for instance)
@ HideFromWms
Field is not available if layer is served as WMS from QGIS server.
QFlags< FieldConfigurationFlag > FieldConfigurationFlags
Configuration flags for fields These flags are meant to be user-configurable and are not describing a...
static QString nullRepresentation()
Returns the string used to represent the value NULL throughout QGIS.
QString userFriendlyIdentifier(Qgis::CrsIdentifierType type=Qgis::CrsIdentifierType::MediumString) const
Returns a user friendly identifier for the CRS.
Provides a container for managing client side default values for fields.
Stores information about constraints which may be present on a field.
ConstraintStrength
Strength of constraints.
void setConstraintStrength(Constraint constraint, ConstraintStrength strength)
Sets the strength of a constraint.
void setConstraintExpression(const QString &expression, const QString &description=QString())
Set the constraint expression for the field.
ConstraintOrigin
Origin of constraints.
ConstraintStrength constraintStrength(Constraint constraint) const
Returns the strength of a field constraint, or ConstraintStrengthNotSet if the constraint is not pres...
ConstraintOrigin constraintOrigin(Constraint constraint) const
Returns the origin of a field constraint, or ConstraintOriginNotSet if the constraint is not present ...
QString constraintExpression() const
Returns the constraint expression for the field, if set.
@ ConstraintNotNull
Field may not be null.
@ ConstraintUnique
Field must have a unique value.
@ ConstraintExpression
Field has an expression constraint set. See constraintExpression().
void removeConstraint(Constraint constraint)
Removes a constraint from the field.
QString constraintDescription() const
Returns the descriptive name for the constraint expression.
void setConstraint(Constraint constraint, ConstraintOrigin origin=ConstraintOriginLayer)
Sets a constraint on the field.
Encapsulate a field in an attribute table or data source.
void setSplitPolicy(Qgis::FieldDomainSplitPolicy policy)
Sets the field's split policy, which indicates how field values should be handled during a split oper...
void setEditorWidgetSetup(const QgsEditorWidgetSetup &v)
Set the editor widget setup for the field.
QString typeName() const
Gets the field type.
void setConstraints(const QgsFieldConstraints &constraints)
Sets constraints which are present for the field.
void setAlias(const QString &alias)
Sets the alias for the field (the friendly displayed name of the field ).
bool operator!=(const QgsField &other) const
bool operator==(const QgsField &other) const
QgsField & operator=(const QgsField &other)
QString displayString(const QVariant &v) const
Formats string for display.
void setPrecision(int precision)
Set the field precision.
void setDuplicatePolicy(Qgis::FieldDuplicatePolicy policy)
Sets the field's duplicate policy, which indicates how field values should be handled during a duplic...
QString displayNameWithAlias() const
Returns the name to use when displaying this field and adds the alias in parenthesis if it is defined...
QgsField(const QString &name=QString(), QMetaType::Type type=QMetaType::Type::UnknownType, const QString &typeName=QString(), int len=0, int prec=0, const QString &comment=QString(), QMetaType::Type subType=QMetaType::Type::UnknownType)
Constructor.
bool convertCompatible(QVariant &v, QString *errorMessage=nullptr) const
Converts the provided variant to a compatible format.
void setMergePolicy(Qgis::FieldDomainMergePolicy policy)
Sets the field's merge policy, which indicates how field values should be handled during a merge oper...
void setSubType(QMetaType::Type subType)
If the field is a collection, set its element's type.
void setName(const QString &name)
Set the field name.
void setComment(const QString &comment)
Set the field comment.
void setType(QMetaType::Type type)
Set variant type.
QString displayType(bool showConstraints=false) const
Returns the type to use when displaying this field, including the length and precision of the datatyp...
void setConfigurationFlags(Qgis::FieldConfigurationFlags flags)
Sets the Flags for the field (searchable, …).
Qgis::FieldDomainSplitPolicy splitPolicy() const
Returns the field's split policy, which indicates how field values should be handled during a split o...
void setLength(int len)
Set the field length.
QString displayName() const
Returns the name to use when displaying this field.
void setDefaultValueDefinition(const QgsDefaultValue &defaultValueDefinition)
Sets an expression to use when calculating the default value for the field.
QString friendlyTypeString() const
Returns a user friendly, translated representation of the field type.
void setReadOnly(bool readOnly)
Make field read-only if readOnly is set to true.
QMap< int, QVariant > metadata() const
Returns the map of field metadata.
static QString readableConfigurationFlag(Qgis::FieldConfigurationFlag flag)
Returns the readable and translated value of the configuration flag.
Qgis::FieldConfigurationFlags configurationFlags
QMetaType::Type subType() const
If the field is a collection, gets its element's type.
Qgis::FieldDuplicatePolicy duplicatePolicy() const
Returns the field's duplicate policy, which indicates how field values should be handled during a dup...
static constexpr int MAX_WKT_LENGTH
QgsDefaultValue defaultValueDefinition
Qgis::FieldDomainMergePolicy mergePolicy() const
Returns the field's merge policy, which indicates how field values should be handled during a merge o...
void setMetadata(const QMap< int, QVariant > metadata)
Sets the map of field metadata.
QgsFieldConstraints constraints
QgsEditorWidgetSetup editorWidgetSetup() const
Gets the editor widget setup for the field.
void setTypeName(const QString &typeName)
Set the field type.
A geometry is the spatial representation of a feature.
static Q_INVOKABLE QgsGeometry fromWkt(const QString &wkt)
Creates a new geometry from a WKT string.
Q_INVOKABLE QString asWkt(int precision=17) const
Exports the geometry to WKT.
QgsCoordinateReferenceSystem crs() const
Returns the associated coordinate reference system, or an invalid CRS if no reference system is set.
A QgsGeometry with associated coordinate reference system.
Contains utility functions for working with QVariants and QVariant types.
static QMetaType::Type variantTypeToMetaType(QVariant::Type variantType)
Converts a QVariant::Type to a QMetaType::Type.
static bool isNull(const QVariant &variant, bool silenceNullWarnings=false)
Returns true if the specified variant should be considered a NULL value.
static QString typeToDisplayString(QMetaType::Type type, QMetaType::Type subType=QMetaType::Type::UnknownType)
Returns a user-friendly translated string representing a QVariant type.
static QVariant createNullVariant(QMetaType::Type metaType)
Helper method to properly create a null QVariant from a metaType Returns the created QVariant.
qlonglong qgsPermissiveToLongLong(QString string, bool &ok)
Converts a string to an qlonglong in a permissive way, e.g., allowing for incorrect numbers of digits...
double qgsPermissiveToDouble(QString string, bool &ok)
Converts a string to a double in a permissive way, e.g., allowing for incorrect numbers of digits bet...
int qgsPermissiveToInt(QString string, bool &ok)
Converts a string to an integer in a permissive way, e.g., allowing for incorrect numbers of digits b...
QDataStream & operator>>(QDataStream &in, QgsField &field)
Reads a field from stream in into field. QGIS version compatibility is not guaranteed.
QDataStream & operator<<(QDataStream &out, const QgsField &field)
Writes the field to stream out. QGIS version compatibility is not guaranteed.