summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/corelib/kernel/qmetatype.cpp142
-rw-r--r--src/corelib/kernel/qmetatype.h1
-rw-r--r--src/corelib/kernel/qvariant.cpp396
-rw-r--r--tests/auto/corelib/io/qsettings/tst_qsettings.cpp3
-rw-r--r--tests/auto/corelib/kernel/qvariant/CMakeLists.txt1
-rw-r--r--tests/auto/corelib/kernel/qvariant/qvariant.pro2
-rw-r--r--tests/auto/corelib/kernel/qvariant/tst_qvariant.cpp16
7 files changed, 159 insertions, 402 deletions
diff --git a/src/corelib/kernel/qmetatype.cpp b/src/corelib/kernel/qmetatype.cpp
index 446511c14d..e8f359a366 100644
--- a/src/corelib/kernel/qmetatype.cpp
+++ b/src/corelib/kernel/qmetatype.cpp
@@ -1829,6 +1829,18 @@ static bool convertToEnum(const void *from, int fromTypeId, void *to, const QMet
}
}
+#ifndef QT_BOOTSTRAPPED
+static bool canConvertMetaObject(const QMetaType &fromType, const QMetaType &toType)
+{
+ if ((fromType.flags() & QMetaType::PointerToQObject) && (toType.flags() & QMetaType::PointerToQObject)) {
+ return fromType.metaObject()->inherits(toType.metaObject()) ||
+ toType.metaObject()->inherits(fromType.metaObject());
+ }
+ return false;
+}
+#endif
+
+
/*!
Converts the object at \a from from \a fromTypeId to the preallocated space at \a to
typed \a toTypeId. Returns \c true, if the conversion succeeded, otherwise false.
@@ -1836,6 +1848,16 @@ static bool convertToEnum(const void *from, int fromTypeId, void *to, const QMet
*/
bool QMetaType::convert(const void *from, int fromTypeId, void *to, int toTypeId)
{
+ if (fromTypeId == UnknownType || toTypeId == UnknownType)
+ return false;
+
+ if (fromTypeId == toTypeId) {
+ // just make a copy
+ QMetaType(fromTypeId).destruct(to);
+ QMetaType(fromTypeId).construct(to, from);
+ return true;
+ }
+
if (auto moduleHelper = qModuleHelperForType(qMax(fromTypeId, toTypeId))) {
if (moduleHelper->convert(from, fromTypeId, to, toTypeId))
return true;
@@ -1862,6 +1884,126 @@ bool QMetaType::convert(const void *from, int fromTypeId, void *to, int toTypeId
}
/*!
+ Returns \c true if QMetaType::convert can convert from \a fromType to
+ \a toType.
+
+ The following conversions are supported by Qt:
+
+ \table
+ \header \li Type \li Automatically Cast To
+ \row \li \l QMetaType::Bool \li \l QMetaType::QChar, \l QMetaType::Double,
+ \l QMetaType::Int, \l QMetaType::LongLong, \l QMetaType::QString,
+ \l QMetaType::UInt, \l QMetaType::ULongLong
+ \row \li \l QMetaType::QByteArray \li \l QMetaType::Double,
+ \l QMetaType::Int, \l QMetaType::LongLong, \l QMetaType::QString,
+ \l QMetaType::UInt, \l QMetaType::ULongLong, \l QMetaType::QUuid
+ \row \li \l QMetaType::QChar \li \l QMetaType::Bool, \l QMetaType::Int,
+ \l QMetaType::UInt, \l QMetaType::LongLong, \l QMetaType::ULongLong
+ \row \li \l QMetaType::QColor \li \l QMetaType::QString
+ \row \li \l QMetaType::QDate \li \l QMetaType::QDateTime,
+ \l QMetaType::QString
+ \row \li \l QMetaType::QDateTime \li \l QMetaType::QDate,
+ \l QMetaType::QString, \l QMetaType::QTime
+ \row \li \l QMetaType::Double \li \l QMetaType::Bool, \l QMetaType::Int,
+ \l QMetaType::LongLong, \l QMetaType::QString, \l QMetaType::UInt,
+ \l QMetaType::ULongLong
+ \row \li \l QMetaType::QFont \li \l QMetaType::QString
+ \row \li \l QMetaType::Int \li \l QMetaType::Bool, \l QMetaType::QChar,
+ \l QMetaType::Double, \l QMetaType::LongLong, \l QMetaType::QString,
+ \l QMetaType::UInt, \l QMetaType::ULongLong
+ \row \li \l QMetaType::QKeySequence \li \l QMetaType::Int,
+ \l QMetaType::QString
+ \row \li \l QMetaType::QVariantList \li \l QMetaType::QStringList (if the
+ list's items can be converted to QStrings)
+ \row \li \l QMetaType::LongLong \li \l QMetaType::Bool,
+ \l QMetaType::QByteArray, \l QMetaType::QChar, \l QMetaType::Double,
+ \l QMetaType::Int, \l QMetaType::QString, \l QMetaType::UInt,
+ \l QMetaType::ULongLong
+ \row \li \l QMetaType::QPoint \li QMetaType::QPointF
+ \row \li \l QMetaType::QRect \li QMetaType::QRectF
+ \row \li \l QMetaType::QString \li \l QMetaType::Bool,
+ \l QMetaType::QByteArray, \l QMetaType::QChar, \l QMetaType::QColor,
+ \l QMetaType::QDate, \l QMetaType::QDateTime, \l QMetaType::Double,
+ \l QMetaType::QFont, \l QMetaType::Int, \l QMetaType::QKeySequence,
+ \l QMetaType::LongLong, \l QMetaType::QStringList, \l QMetaType::QTime,
+ \l QMetaType::UInt, \l QMetaType::ULongLong, \l QMetaType::QUuid
+ \row \li \l QMetaType::QStringList \li \l QMetaType::QVariantList,
+ \l QMetaType::QString (if the list contains exactly one item)
+ \row \li \l QMetaType::QTime \li \l QMetaType::QString
+ \row \li \l QMetaType::UInt \li \l QMetaType::Bool, \l QMetaType::QChar,
+ \l QMetaType::Double, \l QMetaType::Int, \l QMetaType::LongLong,
+ \l QMetaType::QString, \l QMetaType::ULongLong
+ \row \li \l QMetaType::ULongLong \li \l QMetaType::Bool,
+ \l QMetaType::QChar, \l QMetaType::Double, \l QMetaType::Int,
+ \l QMetaType::LongLong, \l QMetaType::QString, \l QMetaType::UInt
+ \row \li \l QMetaType::QUuid \li \l QMetaType::QByteArray, \l QMetaType::QString
+ \endtable
+
+ Casting between primitive type (int, float, bool etc.) is supported.
+
+ Converting between pointers of types derived from QObject will also return true for this
+ function if a qobject_cast from the type described by \a fromType to the type described
+ by \a toType would succeed.
+
+ A cast from a sequential container will also return true for this
+ function if the \a toType is QVariantList.
+
+ Similarly, a cast from an associative container will also return true for this
+ function the \a toType is QVariantHash or QVariantMap.
+
+ \sa convert(), QSequentialIterable, Q_DECLARE_SEQUENTIAL_CONTAINER_METATYPE(), QAssociativeIterable,
+ Q_DECLARE_ASSOCIATIVE_CONTAINER_METATYPE()
+*/
+bool QMetaType::canConvert(const QMetaType &fromType, const QMetaType &toType)
+{
+ int fromTypeId = fromType.id();
+ int toTypeId = toType.id();
+
+ if (fromTypeId == UnknownType || toTypeId == UnknownType)
+ return false;
+
+ if (fromTypeId == toTypeId)
+ return true;
+
+ if (auto moduleHelper = qModuleHelperForType(qMax(fromTypeId, toTypeId))) {
+ if (moduleHelper->convert(nullptr, fromTypeId, nullptr, toTypeId))
+ return true;
+ }
+ const QMetaType::ConverterFunction * const f =
+ customTypesConversionRegistry()->function(qMakePair(fromTypeId, toTypeId));
+ if (f)
+ return true;
+
+ if (fromType.flags() & QMetaType::IsEnumeration) {
+ if (toTypeId == QMetaType::QString || toTypeId == QMetaType::QByteArray)
+ return true;
+ return QMetaType::canConvert(QMetaType(LongLong), toType);
+ }
+ if (toType.flags() & QMetaType::IsEnumeration) {
+ if (fromTypeId == QMetaType::QString || fromTypeId == QMetaType::QByteArray)
+ return true;
+ return QMetaType::canConvert(fromType, QMetaType(LongLong));
+ }
+ if (toTypeId == Nullptr && fromType.flags() & QMetaType::IsPointer)
+ return true;
+#ifndef QT_BOOTSTRAPPED
+ if (canConvertMetaObject(fromType, toType))
+ return true;
+#endif
+
+ return false;
+}
+
+/*!
+ bool QMetaType::compare(const void *lhs, const void *rhs, int typeId, int* result)
+ \deprecated Use the non-static compare method instead
+
+ Compares the objects at \a lhs and \a rhs. Both objects need to be of type \a typeId.
+ \a result is set to less than, equal to or greater than zero, if \a lhs is less than, equal to
+ or greater than \a rhs. Returns \c true, if the comparison succeeded, otherwise \c false.
+*/
+
+/*!
\fn bool QMetaType::hasRegisteredConverterFunction()
Returns \c true, if the meta type system has a registered conversion from type From to type To.
\since 5.2
diff --git a/src/corelib/kernel/qmetatype.h b/src/corelib/kernel/qmetatype.h
index b4217bc3a1..4a3ed1affc 100644
--- a/src/corelib/kernel/qmetatype.h
+++ b/src/corelib/kernel/qmetatype.h
@@ -524,6 +524,7 @@ public:
#endif
static bool convert(const void *from, int fromTypeId, void *to, int toTypeId);
+ static bool canConvert(const QMetaType &fromType, const QMetaType &toType);
#if QT_DEPRECATED_SINCE(6, 0)
QT_DEPRECATED_VERSION_6_0
static bool compare(const void *lhs, const void *rhs, int typeId, int *result)
diff --git a/src/corelib/kernel/qvariant.cpp b/src/corelib/kernel/qvariant.cpp
index 4f0664dc28..c16e4a0e06 100644
--- a/src/corelib/kernel/qvariant.cpp
+++ b/src/corelib/kernel/qvariant.cpp
@@ -1962,219 +1962,17 @@ QVariantList QVariant::toList() const
return qVariantToHelper<QVariantList>(d);
}
-
-static const quint32 qCanConvertMatrix[QMetaType::LastCoreType + 1] =
-{
-/*Invalid*/ 0,
-
-/*Bool*/ 1 << QMetaType::Double | 1 << QMetaType::Int | 1 << QMetaType::UInt
- | 1 << QMetaType::LongLong | 1 << QMetaType::ULongLong | 1 << QMetaType::QByteArray
- | 1 << QMetaType::QString | 1 << QMetaType::QChar,
-
-/*Int*/ 1 << QMetaType::UInt | 1 << QMetaType::QString | 1 << QMetaType::Double
- | 1 << QMetaType::Bool | 1 << QMetaType::LongLong | 1 << QMetaType::ULongLong
- | 1 << QMetaType::QChar | 1 << QMetaType::QByteArray | 1 << QMetaType::Int,
-
-/*UInt*/ 1 << QMetaType::Int | 1 << QMetaType::QString | 1 << QMetaType::Double
- | 1 << QMetaType::Bool | 1 << QMetaType::LongLong | 1 << QMetaType::ULongLong
- | 1 << QMetaType::QChar | 1 << QMetaType::QByteArray,
-
-/*LLong*/ 1 << QMetaType::Int | 1 << QMetaType::QString | 1 << QMetaType::Double
- | 1 << QMetaType::Bool | 1 << QMetaType::UInt | 1 << QMetaType::ULongLong
- | 1 << QMetaType::QChar | 1 << QMetaType::QByteArray,
-
-/*ULlong*/ 1 << QMetaType::Int | 1 << QMetaType::QString | 1 << QMetaType::Double
- | 1 << QMetaType::Bool | 1 << QMetaType::UInt | 1 << QMetaType::LongLong
- | 1 << QMetaType::QChar | 1 << QMetaType::QByteArray,
-
-/*double*/ 1 << QMetaType::Int | 1 << QMetaType::QString | 1 << QMetaType::ULongLong
- | 1 << QMetaType::Bool | 1 << QMetaType::UInt | 1 << QMetaType::LongLong
- | 1 << QMetaType::QByteArray,
-
-/*QChar*/ 1 << QMetaType::Int | 1 << QMetaType::UInt | 1 << QMetaType::LongLong
- | 1 << QMetaType::ULongLong,
-
-/*QMap*/ 0,
-
-/*QList*/ 1 << QMetaType::QStringList,
-
-/*QString*/ 1 << QMetaType::QStringList | 1 << QMetaType::QByteArray | 1 << QMetaType::Int
- | 1 << QMetaType::UInt | 1 << QMetaType::Bool | 1 << QMetaType::Double
- | 1 << QMetaType::QDate | 1 << QMetaType::QTime | 1 << QMetaType::QDateTime
- | 1 << QMetaType::LongLong | 1 << QMetaType::ULongLong | 1 << QMetaType::QChar
- | 1 << QMetaType::QUrl | 1 << QMetaType::QUuid,
-
-/*QStringList*/ 1 << QMetaType::QVariantList | 1 << QMetaType::QString,
-
-/*QByteArray*/ 1 << QMetaType::QString | 1 << QMetaType::Int | 1 << QMetaType::UInt | 1 << QMetaType::Bool
- | 1 << QMetaType::Double | 1 << QMetaType::LongLong | 1 << QMetaType::ULongLong
- | 1 << QMetaType::QUuid,
-
-/*QBitArray*/ 0,
-
-/*QDate*/ 1 << QMetaType::QString | 1 << QMetaType::QDateTime,
-
-/*QTime*/ 1 << QMetaType::QString | 1 << QMetaType::QDateTime,
-
-/*QDateTime*/ 1 << QMetaType::QString | 1 << QMetaType::QDate,
-
-/*QUrl*/ 1 << QMetaType::QString,
-
-/*QLocale*/ 0,
-
-/*QRect*/ 1 << QMetaType::QRectF,
-
-/*QRectF*/ 1 << QMetaType::QRect,
-
-/*QSize*/ 1 << QMetaType::QSizeF,
-
-/*QSizeF*/ 1 << QMetaType::QSize,
-
-/*QLine*/ 1 << QMetaType::QLineF,
-
-/*QLineF*/ 1 << QMetaType::QLine,
-
-/*QPoint*/ 1 << QMetaType::QPointF,
-
-/*QPointF*/ 1 << QMetaType::QPoint,
-
-/*unused, was: QRegExp*/ 0,
-
-/*QHash*/ 0,
-
-/*QEasingCurve*/ 0,
-
-/*QUuid*/ 1 << QMetaType::QString | 1 << QMetaType::QByteArray,
-};
-static const size_t qCanConvertMatrixMaximumTargetType = 8 * sizeof(*qCanConvertMatrix);
-
-#ifndef QT_BOOTSTRAPPED
-/*
- Returns \c true if from inherits to.
-*/
-static bool canConvertMetaObject(const QMetaObject *from, const QMetaObject *to)
-{
- if (from && to == &QObject::staticMetaObject)
- return true;
-
- while (from) {
- if (from == to)
- return true;
- from = from->superClass();
- }
-
- return false;
-}
-#endif
-
-static bool canConvertMetaObject(int fromId, int toId, QObject *fromObject)
-{
-#ifndef QT_BOOTSTRAPPED
- QMetaType toType(toId);
- if ((QMetaType::typeFlags(fromId) & QMetaType::PointerToQObject) && (toType.flags() & QMetaType::PointerToQObject)) {
- if (!fromObject)
- return true;
- return canConvertMetaObject(fromObject->metaObject(), toType.metaObject());
- }
-#else
- Q_UNUSED(fromId);
- Q_UNUSED(toId);
- Q_UNUSED(fromObject);
-#endif
- return false;
-}
-
-
/*!
Returns \c true if the variant's type can be cast to the requested
type, \a targetTypeId. Such casting is done automatically when calling the
toInt(), toBool(), ... methods.
- The following casts are done automatically:
-
- \table
- \header \li Type \li Automatically Cast To
- \row \li \l QMetaType::Bool \li \l QMetaType::QChar, \l QMetaType::Double,
- \l QMetaType::Int, \l QMetaType::LongLong, \l QMetaType::QString,
- \l QMetaType::UInt, \l QMetaType::ULongLong
- \row \li \l QMetaType::QByteArray \li \l QMetaType::Double,
- \l QMetaType::Int, \l QMetaType::LongLong, \l QMetaType::QString,
- \l QMetaType::UInt, \l QMetaType::ULongLong, \l QMetaType::QUuid
- \row \li \l QMetaType::QChar \li \l QMetaType::Bool, \l QMetaType::Int,
- \l QMetaType::UInt, \l QMetaType::LongLong, \l QMetaType::ULongLong
- \row \li \l QMetaType::QColor \li \l QMetaType::QString
- \row \li \l QMetaType::QDate \li \l QMetaType::QDateTime,
- \l QMetaType::QString
- \row \li \l QMetaType::QDateTime \li \l QMetaType::QDate,
- \l QMetaType::QString, \l QMetaType::QTime
- \row \li \l QMetaType::Double \li \l QMetaType::Bool, \l QMetaType::Int,
- \l QMetaType::LongLong, \l QMetaType::QString, \l QMetaType::UInt,
- \l QMetaType::ULongLong
- \row \li \l QMetaType::QFont \li \l QMetaType::QString
- \row \li \l QMetaType::Int \li \l QMetaType::Bool, \l QMetaType::QChar,
- \l QMetaType::Double, \l QMetaType::LongLong, \l QMetaType::QString,
- \l QMetaType::UInt, \l QMetaType::ULongLong
- \row \li \l QMetaType::QKeySequence \li \l QMetaType::Int,
- \l QMetaType::QString
- \row \li \l QMetaType::QVariantList \li \l QMetaType::QStringList (if the
- list's items can be converted to QStrings)
- \row \li \l QMetaType::LongLong \li \l QMetaType::Bool,
- \l QMetaType::QByteArray, \l QMetaType::QChar, \l QMetaType::Double,
- \l QMetaType::Int, \l QMetaType::QString, \l QMetaType::UInt,
- \l QMetaType::ULongLong
- \row \li \l QMetaType::QPoint \li QMetaType::QPointF
- \row \li \l QMetaType::QRect \li QMetaType::QRectF
- \row \li \l QMetaType::QString \li \l QMetaType::Bool,
- \l QMetaType::QByteArray, \l QMetaType::QChar, \l QMetaType::QColor,
- \l QMetaType::QDate, \l QMetaType::QDateTime, \l QMetaType::Double,
- \l QMetaType::QFont, \l QMetaType::Int, \l QMetaType::QKeySequence,
- \l QMetaType::LongLong, \l QMetaType::QStringList, \l QMetaType::QTime,
- \l QMetaType::UInt, \l QMetaType::ULongLong, \l QMetaType::QUuid
- \row \li \l QMetaType::QStringList \li \l QMetaType::QVariantList,
- \l QMetaType::QString (if the list contains exactly one item)
- \row \li \l QMetaType::QTime \li \l QMetaType::QString
- \row \li \l QMetaType::UInt \li \l QMetaType::Bool, \l QMetaType::QChar,
- \l QMetaType::Double, \l QMetaType::Int, \l QMetaType::LongLong,
- \l QMetaType::QString, \l QMetaType::ULongLong
- \row \li \l QMetaType::ULongLong \li \l QMetaType::Bool,
- \l QMetaType::QChar, \l QMetaType::Double, \l QMetaType::Int,
- \l QMetaType::LongLong, \l QMetaType::QString, \l QMetaType::UInt
- \row \li \l QMetaType::QUuid \li \l QMetaType::QByteArray, \l QMetaType::QString
- \endtable
-
- A QVariant containing a pointer to a type derived from QObject will also return true for this
- function if a qobject_cast to the type described by \a targetTypeId would succeed. Note that
- this only works for QObject subclasses which use the Q_OBJECT macro.
-
- A QVariant containing a sequential container will also return true for this
- function if the \a targetTypeId is QVariantList. It is possible to iterate over
- the contents of the container without extracting it as a (copied) QVariantList:
-
- \snippet code/src_corelib_kernel_qvariant.cpp 9
-
- This requires that the value_type of the container is itself a metatype.
-
- Similarly, a QVariant containing a sequential container will also return true for this
- function the \a targetTypeId is QVariantHash or QVariantMap. It is possible to iterate over
- the contents of the container without extracting it as a (copied) QVariantHash or QVariantMap:
-
- \snippet code/src_corelib_kernel_qvariant.cpp 10
-
- \sa convert(), QSequentialIterable, Q_DECLARE_SEQUENTIAL_CONTAINER_METATYPE(), QAssociativeIterable,
- Q_DECLARE_ASSOCIATIVE_CONTAINER_METATYPE()
+ \sa QMetaType::canConvert()
*/
bool QVariant::canConvert(int targetTypeId) const
{
- if (d.typeId() == targetTypeId)
- return true;
-
-#if QT_CONFIG(itemmodel)
- if ((targetTypeId == QMetaType::QModelIndex
- && d.typeId() == QMetaType::QPersistentModelIndex)
- || (targetTypeId == QMetaType::QPersistentModelIndex
- && d.typeId() == QMetaType::QModelIndex))
+ if (d.typeId() == targetTypeId && targetTypeId != QMetaType::UnknownType)
return true;
-#endif
if (targetTypeId == QMetaType::QVariantList
&& (d.typeId() == QMetaType::QVariantList || d.typeId() == QMetaType::QStringList
@@ -2197,193 +1995,7 @@ bool QVariant::canConvert(int targetTypeId) const
return true;
}
- if ((d.typeId() >= QMetaType::LastCoreType|| targetTypeId >= QMetaType::LastCoreType)
- && QMetaType::hasRegisteredConverterFunction(d.typeId(), targetTypeId)) {
- return true;
- }
-
- // TODO Reimplement this function, currently it works but it is a historical mess.
- uint currentType = d.typeId();
- if (currentType == QMetaType::SChar || currentType == QMetaType::Char)
- currentType = QMetaType::UInt;
- if (targetTypeId == QMetaType::SChar || currentType == QMetaType::Char)
- targetTypeId = QMetaType::UInt;
- if (currentType == QMetaType::Short || currentType == QMetaType::UShort)
- currentType = QMetaType::Int;
- if (targetTypeId == QMetaType::Short || currentType == QMetaType::UShort)
- targetTypeId = QMetaType::Int;
- if (currentType == QMetaType::Float)
- currentType = QMetaType::Double;
- if (targetTypeId == QMetaType::Float)
- targetTypeId = QMetaType::Double;
-
- if (currentType == uint(targetTypeId))
- return true;
-
- if (targetTypeId < 0)
- return false;
- if (targetTypeId >= QMetaType::User) {
- if (QMetaType::typeFlags(targetTypeId) & QMetaType::IsEnumeration) {
- targetTypeId = QMetaType::Int;
- } else {
- return canConvertMetaObject(currentType, targetTypeId, d.get<QObject *>());
- }
- }
-
- if (currentType == QMetaType::QJsonValue || targetTypeId == QMetaType::QJsonValue) {
- switch (currentType == QMetaType::QJsonValue ? targetTypeId : currentType) {
- case QMetaType::Nullptr:
- case QMetaType::QString:
- case QMetaType::Bool:
- case QMetaType::Int:
- case QMetaType::UInt:
- case QMetaType::Double:
- case QMetaType::Float:
- case QMetaType::ULong:
- case QMetaType::Long:
- case QMetaType::LongLong:
- case QMetaType::ULongLong:
- case QMetaType::UShort:
- case QMetaType::UChar:
- case QMetaType::Char:
- case QMetaType::SChar:
- case QMetaType::Short:
- case QMetaType::QVariantList:
- case QMetaType::QVariantMap:
- case QMetaType::QVariantHash:
- case QMetaType::QCborValue:
- case QMetaType::QCborArray:
- case QMetaType::QCborMap:
- return true;
- default:
- return false;
- }
- }
- if (currentType == QMetaType::QJsonArray)
- return targetTypeId == QMetaType::QVariantList || targetTypeId == QMetaType::QCborValue
- || targetTypeId == QMetaType::QCborArray;
- if (currentType == QMetaType::QJsonObject)
- return targetTypeId == QMetaType::QVariantMap || targetTypeId == QMetaType::QVariantHash
- || targetTypeId == QMetaType::QCborValue || targetTypeId == QMetaType::QCborMap;
-
- if (currentType == QMetaType::QCborValue || targetTypeId == QMetaType::QCborValue) {
- switch (currentType == QMetaType::QCborValue ? targetTypeId : currentType) {
- case QMetaType::UnknownType:
- case QMetaType::Nullptr:
- case QMetaType::Bool:
- case QMetaType::Int:
- case QMetaType::UInt:
- case QMetaType::Double:
- case QMetaType::Float:
- case QMetaType::ULong:
- case QMetaType::Long:
- case QMetaType::LongLong:
- case QMetaType::ULongLong:
- case QMetaType::UShort:
- case QMetaType::UChar:
- case QMetaType::Char:
- case QMetaType::SChar:
- case QMetaType::Short:
- case QMetaType::QString:
- case QMetaType::QByteArray:
- case QMetaType::QDateTime:
- case QMetaType::QUrl:
-#if QT_CONFIG(regularexpression)
- case QMetaType::QRegularExpression:
-#endif
- case QMetaType::QUuid:
- case QMetaType::QVariantList:
- case QMetaType::QVariantMap:
- case QMetaType::QVariantHash:
- case QMetaType::QJsonValue:
- case QMetaType::QJsonArray:
- case QMetaType::QJsonObject:
- case QMetaType::QJsonDocument:
- case QMetaType::QCborArray:
- case QMetaType::QCborMap:
- case QMetaType::QCborSimpleType:
- return true;
- default:
- return false;
- }
- }
- if (currentType == QMetaType::QCborArray)
- return targetTypeId == QMetaType::QVariantList || targetTypeId == QMetaType::QCborValue
- || targetTypeId == QMetaType::QJsonArray;
- if (currentType == QMetaType::QCborMap)
- return targetTypeId == QMetaType::QVariantMap || targetTypeId == QMetaType::QVariantHash
- || targetTypeId == QMetaType::QCborValue || targetTypeId == QMetaType::QJsonObject;
-
- // FIXME It should be LastCoreType intead of Uuid
- if (currentType > int(QMetaType::QUuid) || targetTypeId > int(QMetaType::QUuid)) {
- switch (uint(targetTypeId)) {
- case QVariant::Int:
-#if QT_CONFIG(shortcut)
- if (currentType == QVariant::KeySequence)
- return true;
- Q_FALLTHROUGH();
-#endif
- case QVariant::UInt:
- case QVariant::LongLong:
- case QVariant::ULongLong:
- return currentType == QMetaType::ULong
- || currentType == QMetaType::Long
- || currentType == QMetaType::UShort
- || currentType == QMetaType::UChar
- || currentType == QMetaType::Char
- || currentType == QMetaType::SChar
- || currentType == QMetaType::Short
- || QMetaType::typeFlags(currentType) & QMetaType::IsEnumeration;
- case QVariant::Image:
- return currentType == QVariant::Pixmap || currentType == QVariant::Bitmap;
- case QVariant::Pixmap:
- return currentType == QVariant::Image || currentType == QVariant::Bitmap
- || currentType == QVariant::Brush;
- case QVariant::Bitmap:
- return currentType == QVariant::Pixmap || currentType == QVariant::Image;
- case QVariant::ByteArray:
- return currentType == QVariant::Color || currentType == QMetaType::Nullptr
- || ((QMetaType::typeFlags(currentType) & QMetaType::IsEnumeration) && QMetaType::metaObjectForType(currentType));
- case QVariant::String:
- return currentType == QVariant::Font
- || currentType == QVariant::Color || currentType == QMetaType::Nullptr
-#if QT_CONFIG(shortcut)
- || currentType == QVariant::KeySequence
-#endif
- || ((QMetaType::typeFlags(currentType) & QMetaType::IsEnumeration) && QMetaType::metaObjectForType(currentType));
-#if QT_CONFIG(shortcut)
- case QVariant::KeySequence:
- return currentType == QVariant::String || currentType == QVariant::Int;
-#endif
- case QVariant::Font:
- return currentType == QVariant::String;
- case QVariant::Color:
- return currentType == QVariant::String || currentType == QVariant::ByteArray
- || currentType == QVariant::Brush;
- case QVariant::Brush:
- return currentType == QVariant::Color || currentType == QVariant::Pixmap;
- case QMetaType::Long:
- case QMetaType::Char:
- case QMetaType::SChar:
- case QMetaType::UChar:
- case QMetaType::ULong:
- case QMetaType::Short:
- case QMetaType::UShort:
- return currentType == QVariant::Int
- || (currentType < qCanConvertMatrixMaximumTargetType
- && qCanConvertMatrix[QVariant::Int] & (1U << currentType))
- || QMetaType::typeFlags(currentType) & QMetaType::IsEnumeration;
- case QMetaType::QObjectStar:
- return canConvertMetaObject(currentType, targetTypeId, d.get<QObject *>());
- default:
- return false;
- }
- }
-
- if (targetTypeId == String && currentType == StringList)
- return d.get<QStringList>().count() == 1;
- return currentType < qCanConvertMatrixMaximumTargetType
- && qCanConvertMatrix[targetTypeId] & (1U << currentType);
+ return QMetaType::canConvert(d.type(), QMetaType(targetTypeId));
}
/*!
@@ -2409,7 +2021,7 @@ bool QVariant::canConvert(int targetTypeId) const
bool QVariant::convert(int targetTypeId)
{
if (d.typeId() == targetTypeId)
- return true;
+ return (targetTypeId != QMetaType::UnknownType);
QVariant oldValue = *this;
diff --git a/tests/auto/corelib/io/qsettings/tst_qsettings.cpp b/tests/auto/corelib/io/qsettings/tst_qsettings.cpp
index aa893309e8..a84825d1e6 100644
--- a/tests/auto/corelib/io/qsettings/tst_qsettings.cpp
+++ b/tests/auto/corelib/io/qsettings/tst_qsettings.cpp
@@ -929,7 +929,8 @@ void tst_QSettings::testIniParsing()
if ( settings.status() == QSettings::NoError ) { // else no point proceeding
QVariant v = settings.value(key);
- QVERIFY(v.canConvert(expect.type()));
+ if (expect.isValid())
+ QVERIFY(v.canConvert(expect.type()));
// check some types so as to give prettier error messages
if ( v.type() == QVariant::String ) {
QCOMPARE(v.toString(), expect.toString());
diff --git a/tests/auto/corelib/kernel/qvariant/CMakeLists.txt b/tests/auto/corelib/kernel/qvariant/CMakeLists.txt
index f1baaefe43..8b122a48e2 100644
--- a/tests/auto/corelib/kernel/qvariant/CMakeLists.txt
+++ b/tests/auto/corelib/kernel/qvariant/CMakeLists.txt
@@ -13,6 +13,7 @@ qt_add_test(tst_qvariant
../../../other/qvariant_common
PUBLIC_LIBRARIES
Qt::CorePrivate
+ Qt::Gui
)
# Resources:
diff --git a/tests/auto/corelib/kernel/qvariant/qvariant.pro b/tests/auto/corelib/kernel/qvariant/qvariant.pro
index a620be0091..7416023808 100644
--- a/tests/auto/corelib/kernel/qvariant/qvariant.pro
+++ b/tests/auto/corelib/kernel/qvariant/qvariant.pro
@@ -1,6 +1,6 @@
CONFIG += testcase
TARGET = tst_qvariant
-QT = core-private testlib
+QT = core-private gui testlib
INCLUDEPATH += $$PWD/../../../other/qvariant_common
SOURCES = tst_qvariant.cpp
RESOURCES += qvariant.qrc
diff --git a/tests/auto/corelib/kernel/qvariant/tst_qvariant.cpp b/tests/auto/corelib/kernel/qvariant/tst_qvariant.cpp
index a722e53f48..d4af02baf1 100644
--- a/tests/auto/corelib/kernel/qvariant/tst_qvariant.cpp
+++ b/tests/auto/corelib/kernel/qvariant/tst_qvariant.cpp
@@ -477,7 +477,7 @@ void tst_QVariant::canConvert_data()
<< var << N << N << Y << N << Y << N << N << N << N << Y << N << N << Y << N << Y << N << Y << N << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
var = QVariant();
QTest::newRow("Invalid")
- << var << N << N << N << N << N << N << N << N << N << N << N << N << N << Y << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N;
+ << var << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N;
var = QVariant(QList<QVariant>());
QTest::newRow("List")
<< var << N << N << N << N << N << N << N << N << N << N << N << N << N << N << N << Y << N << N << N << N << N << N << N << N << N << N << N << Y << N << N << N;
@@ -520,12 +520,12 @@ void tst_QVariant::canConvert_data()
var = QVariant::fromValue<signed char>(-1);
QTest::newRow("SChar")
<< var << N << N << Y << N << Y << N << N << N << N << Y << N << N << Y << N << N << N << Y << N << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
- var = QVariant((short)-3);
+ var = QVariant::fromValue((short)-3);
QTest::newRow("Short")
- << var << N << N << Y << N << Y << N << N << N << N << Y << N << N << Y << N << Y << N << Y << N << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
- var = QVariant((ushort)7);
+ << var << N << N << Y << N << Y << N << N << N << N << Y << N << N << Y << N << N << N << Y << N << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
+ var = QVariant::fromValue((ushort)7);
QTest::newRow("UShort")
- << var << N << N << Y << N << Y << N << N << N << N << Y << N << N << Y << N << Y << N << Y << N << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
+ << var << N << N << Y << N << Y << N << N << N << N << Y << N << N << Y << N << N << N << Y << N << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
var = QVariant::fromValue<QJsonValue>(QJsonValue(QStringLiteral("hello")));
QTest::newRow("JsonValue")
<< var << N << N << Y << N << N << N << N << N << N << Y << N << N << Y << N << N << Y << Y << Y << N << N << N << N << N << N << N << N << Y << N << N << Y << Y;
@@ -2705,17 +2705,17 @@ void tst_QVariant::canConvertQStringList_data() const
QTest::addColumn<QStringList>("input");
QTest::addColumn<QString>("result");
- QTest::newRow("An empty list") << false << QStringList() << QString();
+ QTest::newRow("An empty list") << true << QStringList() << QString();
QTest::newRow("A single item") << true << QStringList(QLatin1String("foo")) << QString::fromLatin1("foo");
QTest::newRow("A single, but empty item") << true << QStringList(QString()) << QString();
QStringList l;
l << "a" << "b";
- QTest::newRow("Two items") << false << l << QString();
+ QTest::newRow("Two items") << true << l << QString();
l << "c";
- QTest::newRow("Three items") << false << l << QString();
+ QTest::newRow("Three items") << true << l << QString();
}
template<typename T> void convertMetaType()