77#define TVL_True QVariant( 1 )
78#define TVL_False QVariant( 0 )
79#define TVL_Unknown QVariant()
81 static QVariant tvl2variant( TVL v )
96 static TVL getTVLValue(
const QVariant &value,
QgsExpression *parent )
103 int userType = value.userType();
104 if ( value.type() == QVariant::UserType )
106 if ( userType == qMetaTypeId< QgsGeometry>() || userType == qMetaTypeId<QgsReferencedGeometry>() )
109 const QgsGeometry geom = getGeometry( value,
nullptr );
110 return geom.
isNull() ? False : True;
112 else if ( userType == qMetaTypeId<QgsFeature>() )
116 return feat.
isValid() ? True : False;
120 if ( userType == QMetaType::Type::Int )
121 return value.toInt() != 0 ? True : False;
124 const double x = value.toDouble( &ok );
128 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to boolean" ).arg( value.toString() ) );
135 static inline bool isIntSafe(
const QVariant &v )
137 if ( v.userType() == QMetaType::Type::Int )
139 if ( v.userType() == QMetaType::Type::UInt )
141 if ( v.userType() == QMetaType::Type::LongLong )
143 if ( v.userType() == QMetaType::Type::ULongLong )
145 if ( v.userType() == QMetaType::Type::Double )
147 if ( v.userType() == QMetaType::Type::QString )
150 v.toString().toInt( &ok );
156 static inline bool isDoubleSafe(
const QVariant &v )
158 if ( v.userType() == QMetaType::Type::Double )
160 if ( v.userType() == QMetaType::Type::Int )
162 if ( v.userType() == QMetaType::Type::UInt )
164 if ( v.userType() == QMetaType::Type::LongLong )
166 if ( v.userType() == QMetaType::Type::ULongLong )
168 if ( v.userType() == QMetaType::Type::QString )
171 const double val = v.toString().toDouble( &ok );
172 ok = ok && std::isfinite( val ) && !std::isnan( val );
178 static inline bool isDateTimeSafe(
const QVariant &v )
180 return v.userType() == QMetaType::Type::QDateTime
181 || v.userType() == QMetaType::Type::QDate
182 || v.userType() == QMetaType::Type::QTime;
185 static inline bool isIntervalSafe(
const QVariant &v )
187 if ( v.userType() == qMetaTypeId<QgsInterval>() )
192 if ( v.userType() == QMetaType::Type::QString )
199 static inline bool isNull(
const QVariant &v )
204 static inline bool isList(
const QVariant &v )
206 return v.userType() == QMetaType::Type::QVariantList || v.userType() == QMetaType::Type::QStringList;
210 static QString getStringValue(
const QVariant &value,
QgsExpression * )
212 return value.toString();
222 static QByteArray getBinaryValue(
const QVariant &value,
QgsExpression *parent )
224 if ( value.userType() != QMetaType::Type::QByteArray )
230 return value.toByteArray();
233 static double getDoubleValue(
const QVariant &value,
QgsExpression *parent )
236 const double x = value.toDouble( &ok );
237 if ( !ok || std::isnan( x ) || !std::isfinite( x ) )
240 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to double" ).arg( value.toString() ) );
246 static qlonglong getIntValue(
const QVariant &value,
QgsExpression *parent )
249 const qlonglong x = value.toLongLong( &ok );
257 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to int" ).arg( value.toString() ) );
262 static int getNativeIntValue(
const QVariant &value,
QgsExpression *parent )
265 const qlonglong x = value.toLongLong( &ok );
266 if ( ok && x >= std::numeric_limits<int>::min() && x <= std::numeric_limits<int>::max() )
268 return static_cast<int>( x );
273 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to native int" ).arg( value.toString() ) );
278 static QDateTime getDateTimeValue(
const QVariant &value,
QgsExpression *parent )
280 QDateTime d = value.toDateTime();
287 const QTime t = value.toTime();
290 return QDateTime( QDate( 1, 1, 1 ), t );
294 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to DateTime" ).arg( value.toString() ) );
299 static QDate getDateValue(
const QVariant &value,
QgsExpression *parent )
301 QDate d = value.toDate();
309 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to Date" ).arg( value.toString() ) );
314 static QTime getTimeValue(
const QVariant &value,
QgsExpression *parent )
316 QTime t = value.toTime();
324 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to Time" ).arg( value.toString() ) );
329 static QColor getColorValue(
const QVariant &value,
QgsExpression *parent,
bool &isQColor );
333 if ( value.userType() == qMetaTypeId<QgsInterval>() )
337 if ( inter.isValid() )
342 if ( report_error && parent )
343 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to interval" ).arg( value.toString() ) );
352 if ( value.userType() == qMetaTypeId< QgsReferencedGeometry>() )
355 if ( value.userType() == qMetaTypeId< QgsGeometry>() )
358 if ( !tolerant && parent )
365 if ( value.userType() == qMetaTypeId<QgsFeature>() )
385 static QTimeZone getTimeZoneValue(
const QVariant &value,
QgsExpression *parent );
419 static std::unique_ptr<QgsVectorLayerFeatureSource> getFeatureSource(
const QVariant &value,
const QgsExpressionContext *context,
QgsExpression *e,
bool &foundLayer );
433 static QVariantList getListValue(
const QVariant &value,
QgsExpression *parent )
435 if ( value.userType() == QMetaType::Type::QVariantList || value.userType() == QMetaType::Type::QStringList )
437 return value.toList();
442 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to array" ).arg( value.toString() ) );
443 return QVariantList();
447 static QVariantMap getMapValue(
const QVariant &value,
QgsExpression *parent )
449 if ( value.userType() == QMetaType::Type::QVariantMap )
451 return value.toMap();
456 parent->
setEvalErrorString( QObject::tr(
"Cannot convert '%1' to map" ).arg( value.toString() ) );
457 return QVariantMap();
467 static QString toLocalizedString(
const QVariant &value )
469 if ( value.userType() == QMetaType::Type::Int || value.userType() == QMetaType::Type::UInt || value.userType() == QMetaType::Type::LongLong || value.userType() == QMetaType::Type::ULongLong )
474 if ( value.userType() == QMetaType::Type::ULongLong )
476 res = QLocale().toString( value.toULongLong( &ok ) );
480 res = QLocale().toString( value.toLongLong( &ok ) );
489 return value.toString();
493 else if ( value.userType() == QMetaType::Type::Double || value.userType() ==
static_cast<QMetaType::Type
>( QMetaType::Float ) )
496 const QString strVal = value.toString();
497 const int dotPosition = strVal.indexOf(
'.' );
498 const int precision = dotPosition > 0 ? strVal.length() - dotPosition - 1 : 0;
499 const QString res = QLocale().toString( value.toDouble( &ok ),
'f', precision );
507 return value.toString();
512 return value.toString();
Expression contexts are used to encapsulate the parameters around which a QgsExpression should be eva...