1 /****************************************************************************
3 ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: Nokia Corporation (qt-info@nokia.com)
7 ** This file is part of the QtCore module of the Qt Toolkit.
9 ** $QT_BEGIN_LICENSE:LGPL$
10 ** GNU Lesser General Public License Usage
11 ** This file may be used under the terms of the GNU Lesser General Public
12 ** License version 2.1 as published by the Free Software Foundation and
13 ** appearing in the file LICENSE.LGPL included in the packaging of this
14 ** file. Please review the following information to ensure the GNU Lesser
15 ** General Public License version 2.1 requirements will be met:
16 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
18 ** In addition, as a special exception, Nokia gives you certain additional
19 ** rights. These rights are described in the Nokia Qt LGPL Exception
20 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
22 ** GNU General Public License Usage
23 ** Alternatively, this file may be used under the terms of the GNU General
24 ** Public License version 3.0 as published by the Free Software Foundation
25 ** and appearing in the file LICENSE.GPL included in the packaging of this
26 ** file. Please review the following information to ensure the GNU General
27 ** Public License version 3.0 requirements will be met:
28 ** http://www.gnu.org/copyleft/gpl.html.
31 ** Alternatively, this file may be used in accordance with the terms and
32 ** conditions contained in a signed written agreement between you and Nokia.
40 ****************************************************************************/
43 #include "qbitarray.h"
44 #include "qbytearray.h"
45 #include "qdatastream.h"
48 #include "qdatetime.h"
49 #include "qeasingcurve.h"
52 #include "qstringlist.h"
56 #include "private/qvariant_p.h"
57 #include "qmetatype_p.h"
59 #ifndef QT_NO_GEOM_VARIANT
80 static const QVariant::Handler *Handlers[QModulesPrivate::ModulesCount];
82 const QVariant::Handler *operator[] (const int typeId) const
84 return Handlers[QModulesPrivate::moduleForType(typeId)];
87 void registerHandler(const QModulesPrivate::Names name, const QVariant::Handler *handler)
89 Handlers[name] = handler;
92 inline void unregisterHandler(const QModulesPrivate::Names name);
98 struct TypeDefiniton {
99 static const bool IsAvailable = true;
102 // Ignore these types, as incomplete
103 #ifdef QT_BOOTSTRAPPED
104 template<> struct TypeDefiniton<QEasingCurve> { static const bool IsAvailable = false; };
106 #ifdef QT_NO_GEOM_VARIANT
107 template<> struct TypeDefiniton<QRect> { static const bool IsAvailable = false; };
108 template<> struct TypeDefiniton<QRectF> { static const bool IsAvailable = false; };
109 template<> struct TypeDefiniton<QSize> { static const bool IsAvailable = false; };
110 template<> struct TypeDefiniton<QSizeF> { static const bool IsAvailable = false; };
111 template<> struct TypeDefiniton<QLine> { static const bool IsAvailable = false; };
112 template<> struct TypeDefiniton<QLineF> { static const bool IsAvailable = false; };
113 template<> struct TypeDefiniton<QPoint> { static const bool IsAvailable = false; };
114 template<> struct TypeDefiniton<QPointF> { static const bool IsAvailable = false; };
117 struct CoreTypesFilter {
120 static const bool IsAccepted = QTypeModuleInfo<T>::IsCore && TypeDefiniton<T>::IsAvailable;
123 } // annonymous used to hide TypeDefiniton
125 namespace { // annonymous used to hide QVariant handlers
127 static void construct(QVariant::Private *x, const void *copy)
129 QVariantConstructor<CoreTypesFilter> constructor(x, copy);
130 QMetaTypeSwitcher::switcher<void>(constructor, x->type, 0);
133 static void clear(QVariant::Private *d)
135 QVariantDestructor<CoreTypesFilter> cleaner(d);
136 QMetaTypeSwitcher::switcher<void>(cleaner, d->type, 0);
139 static bool isNull(const QVariant::Private *d)
141 QVariantIsNull<CoreTypesFilter> isNull(d);
142 return QMetaTypeSwitcher::switcher<bool>(isNull, d->type, 0);
148 Compares \a a to \a b. The caller guarantees that \a a and \a b
149 are of the same type.
151 static bool compare(const QVariant::Private *a, const QVariant::Private *b)
153 QVariantComparator<CoreTypesFilter> comparator(a, b);
154 return QMetaTypeSwitcher::switcher<bool>(comparator, a->type, 0);
160 static qlonglong qMetaTypeNumber(const QVariant::Private *d)
165 case QMetaType::LongLong:
167 case QMetaType::Char:
168 return qlonglong(d->data.c);
169 case QMetaType::Short:
170 return qlonglong(d->data.s);
171 case QMetaType::Long:
172 return qlonglong(d->data.l);
173 case QMetaType::Float:
174 return qRound64(d->data.f);
175 case QVariant::Double:
176 return qRound64(d->data.d);
182 static qulonglong qMetaTypeUNumber(const QVariant::Private *d)
187 case QVariant::ULongLong:
189 case QMetaType::UChar:
191 case QMetaType::UShort:
193 case QMetaType::ULong:
200 static qlonglong qConvertToNumber(const QVariant::Private *d, bool *ok)
204 switch (uint(d->type)) {
205 case QVariant::String:
206 return v_cast<QString>(d)->toLongLong(ok);
208 return v_cast<QChar>(d)->unicode();
209 case QVariant::ByteArray:
210 return v_cast<QByteArray>(d)->toLongLong(ok);
212 return qlonglong(d->data.b);
213 case QVariant::Double:
215 case QMetaType::Char:
216 case QMetaType::Short:
217 case QMetaType::Long:
218 case QMetaType::Float:
219 case QMetaType::LongLong:
220 return qMetaTypeNumber(d);
221 case QVariant::ULongLong:
223 case QMetaType::UChar:
224 case QMetaType::UShort:
225 case QMetaType::ULong:
226 return qlonglong(qMetaTypeUNumber(d));
233 static qulonglong qConvertToUnsignedNumber(const QVariant::Private *d, bool *ok)
237 switch (uint(d->type)) {
238 case QVariant::String:
239 return v_cast<QString>(d)->toULongLong(ok);
241 return v_cast<QChar>(d)->unicode();
242 case QVariant::ByteArray:
243 return v_cast<QByteArray>(d)->toULongLong(ok);
245 return qulonglong(d->data.b);
246 case QVariant::Double:
248 case QMetaType::Char:
249 case QMetaType::Short:
250 case QMetaType::Long:
251 case QMetaType::Float:
252 case QMetaType::LongLong:
253 return qulonglong(qMetaTypeNumber(d));
254 case QVariant::ULongLong:
256 case QMetaType::UChar:
257 case QMetaType::UShort:
258 case QMetaType::ULong:
259 return qMetaTypeUNumber(d);
263 return Q_UINT64_C(0);
266 template<typename TInput, typename LiteralWrapper>
267 inline bool qt_convertToBool(const QVariant::Private *const d)
269 TInput str = v_cast<TInput>(d)->toLower();
270 return !(str == LiteralWrapper("0") || str == LiteralWrapper("false") || str.isEmpty());
276 Converts \a d to type \a t, which is placed in \a result.
278 static bool convert(const QVariant::Private *d, QVariant::Type t, void *result, bool *ok)
280 Q_ASSERT(d->type != uint(t));
290 case QVariant::String:
291 *static_cast<QUrl *>(result) = QUrl(*v_cast<QString>(d));
297 case QVariant::String: {
298 QString *str = static_cast<QString *>(result);
301 *str = QString(*v_cast<QChar>(d));
303 case QMetaType::Char:
304 case QMetaType::UChar:
305 *str = QChar::fromAscii(d->data.c);
307 case QMetaType::Short:
308 case QMetaType::Long:
310 case QVariant::LongLong:
311 *str = QString::number(qMetaTypeNumber(d));
314 case QVariant::ULongLong:
315 case QMetaType::UShort:
316 case QMetaType::ULong:
317 *str = QString::number(qMetaTypeUNumber(d));
319 case QMetaType::Float:
320 *str = QString::number(d->data.f, 'g', FLT_DIG);
322 case QVariant::Double:
323 *str = QString::number(d->data.d, 'g', DBL_DIG);
325 #if !defined(QT_NO_DATESTRING)
327 *str = v_cast<QDate>(d)->toString(Qt::ISODate);
330 *str = v_cast<QTime>(d)->toString(Qt::ISODate);
332 case QVariant::DateTime:
333 *str = v_cast<QDateTime>(d)->toString(Qt::ISODate);
337 *str = QLatin1String(d->data.b ? "true" : "false");
339 case QVariant::ByteArray:
340 *str = QString::fromAscii(v_cast<QByteArray>(d)->constData());
342 case QVariant::StringList:
343 if (v_cast<QStringList>(d)->count() == 1)
344 *str = v_cast<QStringList>(d)->at(0);
347 *str = v_cast<QUrl>(d)->toString();
350 *str = v_cast<QUuid>(d)->toString();
357 case QVariant::Char: {
358 QChar *c = static_cast<QChar *>(result);
361 case QVariant::LongLong:
362 case QMetaType::Char:
363 case QMetaType::Short:
364 case QMetaType::Long:
365 case QMetaType::Float:
366 *c = QChar(ushort(qMetaTypeNumber(d)));
369 case QVariant::ULongLong:
370 case QMetaType::UChar:
371 case QMetaType::UShort:
372 case QMetaType::ULong:
373 *c = QChar(ushort(qMetaTypeUNumber(d)));
380 #ifndef QT_NO_GEOM_VARIANT
381 case QVariant::Size: {
382 QSize *s = static_cast<QSize *>(result);
384 case QVariant::SizeF:
385 *s = v_cast<QSizeF>(d)->toSize();
393 case QVariant::SizeF: {
394 QSizeF *s = static_cast<QSizeF *>(result);
397 *s = QSizeF(*(v_cast<QSize>(d)));
405 case QVariant::Line: {
406 QLine *s = static_cast<QLine *>(result);
408 case QVariant::LineF:
409 *s = v_cast<QLineF>(d)->toLine();
417 case QVariant::LineF: {
418 QLineF *s = static_cast<QLineF *>(result);
421 *s = QLineF(*(v_cast<QLine>(d)));
429 case QVariant::StringList:
430 if (d->type == QVariant::List) {
431 QStringList *slst = static_cast<QStringList *>(result);
432 const QVariantList *list = v_cast<QVariantList >(d);
433 for (int i = 0; i < list->size(); ++i)
434 slst->append(list->at(i).toString());
435 } else if (d->type == QVariant::String) {
436 QStringList *slst = static_cast<QStringList *>(result);
437 *slst = QStringList(*v_cast<QString>(d));
442 case QVariant::Date: {
443 QDate *dt = static_cast<QDate *>(result);
444 if (d->type == QVariant::DateTime)
445 *dt = v_cast<QDateTime>(d)->date();
446 #ifndef QT_NO_DATESTRING
447 else if (d->type == QVariant::String)
448 *dt = QDate::fromString(*v_cast<QString>(d), Qt::ISODate);
453 return dt->isValid();
455 case QVariant::Time: {
456 QTime *t = static_cast<QTime *>(result);
458 case QVariant::DateTime:
459 *t = v_cast<QDateTime>(d)->time();
461 #ifndef QT_NO_DATESTRING
462 case QVariant::String:
463 *t = QTime::fromString(*v_cast<QString>(d), Qt::ISODate);
471 case QVariant::DateTime: {
472 QDateTime *dt = static_cast<QDateTime *>(result);
474 #ifndef QT_NO_DATESTRING
475 case QVariant::String:
476 *dt = QDateTime::fromString(*v_cast<QString>(d), Qt::ISODate);
480 *dt = QDateTime(*v_cast<QDate>(d));
485 return dt->isValid();
487 case QVariant::ByteArray: {
488 QByteArray *ba = static_cast<QByteArray *>(result);
490 case QVariant::String:
491 *ba = v_cast<QString>(d)->toAscii();
493 case QVariant::Double:
494 *ba = QByteArray::number(d->data.d, 'g', DBL_DIG);
496 case QMetaType::Float:
497 *ba = QByteArray::number(d->data.f, 'g', FLT_DIG);
499 case QMetaType::Char:
500 case QMetaType::UChar:
501 *ba = QByteArray(1, d->data.c);
504 case QVariant::LongLong:
505 case QMetaType::Short:
506 case QMetaType::Long:
507 *ba = QByteArray::number(qMetaTypeNumber(d));
510 case QVariant::ULongLong:
511 case QMetaType::UShort:
512 case QMetaType::ULong:
513 *ba = QByteArray::number(qMetaTypeUNumber(d));
516 *ba = QByteArray(d->data.b ? "true" : "false");
523 case QMetaType::Short:
524 *static_cast<short *>(result) = short(qConvertToNumber(d, ok));
526 case QMetaType::Long:
527 *static_cast<long *>(result) = long(qConvertToNumber(d, ok));
529 case QMetaType::UShort:
530 *static_cast<ushort *>(result) = ushort(qConvertToUnsignedNumber(d, ok));
532 case QMetaType::ULong:
533 *static_cast<ulong *>(result) = ulong(qConvertToUnsignedNumber(d, ok));
536 *static_cast<int *>(result) = int(qConvertToNumber(d, ok));
539 *static_cast<uint *>(result) = uint(qConvertToUnsignedNumber(d, ok));
541 case QVariant::LongLong:
542 *static_cast<qlonglong *>(result) = qConvertToNumber(d, ok);
544 case QVariant::ULongLong: {
545 *static_cast<qulonglong *>(result) = qConvertToUnsignedNumber(d, ok);
548 case QMetaType::UChar: {
549 *static_cast<uchar *>(result) = qConvertToUnsignedNumber(d, ok);
552 case QVariant::Bool: {
553 bool *b = static_cast<bool *>(result);
555 case QVariant::ByteArray:
556 *b = qt_convertToBool<QByteArray, QByteArray>(d);
558 case QVariant::String:
559 *b = qt_convertToBool<QString, QLatin1String>(d);
562 *b = !v_cast<QChar>(d)->isNull();
564 case QVariant::Double:
566 case QVariant::LongLong:
567 case QMetaType::Char:
568 case QMetaType::Short:
569 case QMetaType::Long:
570 case QMetaType::Float:
571 *b = qMetaTypeNumber(d) != Q_INT64_C(0);
574 case QVariant::ULongLong:
575 case QMetaType::UChar:
576 case QMetaType::UShort:
577 case QMetaType::ULong:
578 *b = qMetaTypeUNumber(d) != Q_UINT64_C(0);
586 case QVariant::Double: {
587 double *f = static_cast<double *>(result);
589 case QVariant::String:
590 *f = v_cast<QString>(d)->toDouble(ok);
592 case QVariant::ByteArray:
593 *f = v_cast<QByteArray>(d)->toDouble(ok);
596 *f = double(d->data.b);
598 case QMetaType::Float:
599 *f = double(d->data.f);
601 case QVariant::LongLong:
603 case QMetaType::Char:
604 case QMetaType::Short:
605 case QMetaType::Long:
606 *f = double(qMetaTypeNumber(d));
609 case QVariant::ULongLong:
610 case QMetaType::UChar:
611 case QMetaType::UShort:
612 case QMetaType::ULong:
613 *f = double(qMetaTypeUNumber(d));
621 case QMetaType::Float: {
622 float *f = static_cast<float *>(result);
624 case QVariant::String:
625 *f = v_cast<QString>(d)->toFloat(ok);
627 case QVariant::ByteArray:
628 *f = v_cast<QByteArray>(d)->toFloat(ok);
631 *f = float(d->data.b);
633 case QVariant::Double:
634 *f = float(d->data.d);
636 case QVariant::LongLong:
638 case QMetaType::Char:
639 case QMetaType::Short:
640 case QMetaType::Long:
641 *f = float(qMetaTypeNumber(d));
644 case QVariant::ULongLong:
645 case QMetaType::UChar:
646 case QMetaType::UShort:
647 case QMetaType::ULong:
648 *f = float(qMetaTypeUNumber(d));
657 if (d->type == QVariant::StringList) {
658 QVariantList *lst = static_cast<QVariantList *>(result);
659 const QStringList *slist = v_cast<QStringList>(d);
660 for (int i = 0; i < slist->size(); ++i)
661 lst->append(QVariant(slist->at(i)));
662 } else if (qstrcmp(QMetaType::typeName(d->type), "QList<QVariant>") == 0) {
663 *static_cast<QVariantList *>(result) =
664 *static_cast<QList<QVariant> *>(d->data.shared->ptr);
670 if (qstrcmp(QMetaType::typeName(d->type), "QMap<QString, QVariant>") == 0) {
671 *static_cast<QVariantMap *>(result) =
672 *static_cast<QMap<QString, QVariant> *>(d->data.shared->ptr);
678 if (qstrcmp(QMetaType::typeName(d->type), "QHash<QString, QVariant>") == 0) {
679 *static_cast<QVariantHash *>(result) =
680 *static_cast<QHash<QString, QVariant> *>(d->data.shared->ptr);
685 #ifndef QT_NO_GEOM_VARIANT
687 if (d->type == QVariant::RectF)
688 *static_cast<QRect *>(result) = (v_cast<QRectF>(d))->toRect();
692 case QVariant::RectF:
693 if (d->type == QVariant::Rect)
694 *static_cast<QRectF *>(result) = *v_cast<QRect>(d);
698 case QVariant::PointF:
699 if (d->type == QVariant::Point)
700 *static_cast<QPointF *>(result) = *v_cast<QPoint>(d);
704 case QVariant::Point:
705 if (d->type == QVariant::PointF)
706 *static_cast<QPoint *>(result) = (v_cast<QPointF>(d))->toPoint();
710 case QMetaType::Char:
712 *static_cast<qint8 *>(result) = qint8(qConvertToNumber(d, ok));
718 case QVariant::String:
719 *static_cast<QUuid *>(result) = QUuid(*v_cast<QString>(d));
731 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
732 static void streamDebug(QDebug dbg, const QVariant &v)
734 QVariant::Private *d = const_cast<QVariant::Private *>(&v.data_ptr());
735 QVariantDebugStream<CoreTypesFilter> stream(dbg, d);
736 QMetaTypeSwitcher::switcher<void>(stream, d->type, 0);
740 const QVariant::Handler qt_kernel_variant_handler = {
744 #ifndef QT_NO_DATASTREAM
751 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
758 static void dummyConstruct(QVariant::Private *, const void *) { Q_ASSERT_X(false, "QVariant", "Trying to construct an unknown type"); }
759 static void dummyClear(QVariant::Private *) { Q_ASSERT_X(false, "QVariant", "Trying to clear an unknown type"); }
760 static bool dummyIsNull(const QVariant::Private *d) { Q_ASSERT_X(false, "QVariant::isNull", "Trying to call isNull on an unknown type"); return d->is_null; }
761 static bool dummyCompare(const QVariant::Private *, const QVariant::Private *) { Q_ASSERT_X(false, "QVariant", "Trying to compare an unknown types"); return false; }
762 static bool dummyConvert(const QVariant::Private *, QVariant::Type , void *, bool *) { Q_ASSERT_X(false, "QVariant", "Trying to convert an unknown type"); return false; }
763 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
764 static void dummyStreamDebug(QDebug, const QVariant &) { Q_ASSERT_X(false, "QVariant", "Trying to convert an unknown type"); }
766 const QVariant::Handler qt_dummy_variant_handler = {
770 #ifndef QT_NO_DATASTREAM
777 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
784 static void customConstruct(QVariant::Private *d, const void *copy)
786 const uint size = QMetaType::sizeOf(d->type);
788 d->type = QVariant::Invalid;
792 // this logic should match with QVariantIntegrator::CanUseInternalSpace
793 if (size <= sizeof(QVariant::Private::Data)
794 && (QMetaType::typeFlags(d->type) & QMetaType::MovableType)) {
795 QMetaType::construct(d->type, &d->data.ptr, copy);
796 d->is_shared = false;
798 void *ptr = QMetaType::create(d->type, copy);
800 d->data.shared = new QVariant::PrivateShared(ptr);
804 static void customClear(QVariant::Private *d)
807 QMetaType::destruct(d->type, &d->data.ptr);
809 QMetaType::destroy(d->type, d->data.shared->ptr);
810 delete d->data.shared;
814 static bool customIsNull(const QVariant::Private *d)
819 static bool customCompare(const QVariant::Private *a, const QVariant::Private *b)
821 const char *const typeName = QMetaType::typeName(a->type);
822 if (Q_UNLIKELY(!typeName) && Q_LIKELY(!QMetaType::isRegistered(a->type)))
823 qFatal("QVariant::compare: type %d unknown to QVariant.", a->type);
825 const void *a_ptr = a->is_shared ? a->data.shared->ptr : &(a->data.ptr);
826 const void *b_ptr = b->is_shared ? b->data.shared->ptr : &(b->data.ptr);
828 uint typeNameLen = qstrlen(typeName);
829 if (typeNameLen > 0 && typeName[typeNameLen - 1] == '*')
830 return *static_cast<void *const *>(a_ptr) == *static_cast<void *const *>(b_ptr);
832 if (a->is_null && b->is_null)
835 return !memcmp(a_ptr, b_ptr, QMetaType::sizeOf(a->type));
838 static bool customConvert(const QVariant::Private *, QVariant::Type, void *, bool *ok)
845 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
846 static void customStreamDebug(QDebug, const QVariant &) {}
849 const QVariant::Handler qt_custom_variant_handler = {
853 #ifndef QT_NO_DATASTREAM
860 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
867 } // annonymous used to hide QVariant handlers
869 static HandlersManager handlerManager;
870 Q_STATIC_ASSERT_X(!QModulesPrivate::Core, "Initialization assumes that ModulesNames::Core is 0");
871 const QVariant::Handler *HandlersManager::Handlers[QModulesPrivate::ModulesCount]
872 = { &qt_kernel_variant_handler, &qt_dummy_variant_handler,
873 &qt_dummy_variant_handler, &qt_custom_variant_handler };
875 Q_CORE_EXPORT const QVariant::Handler *qcoreVariantHandler()
877 return &qt_kernel_variant_handler;
880 inline void HandlersManager::unregisterHandler(const QModulesPrivate::Names name)
882 Handlers[name] = &qt_dummy_variant_handler;
885 Q_CORE_EXPORT void QVariantPrivate::registerHandler(const int /* Modules::Names */name, const QVariant::Handler *handler)
887 handlerManager.registerHandler(static_cast<QModulesPrivate::Names>(name), handler);
890 Q_CORE_EXPORT void QVariantPrivate::unregisterHandler(const int /* Modules::Names */ name)
892 handlerManager.unregisterHandler(static_cast<QModulesPrivate::Names>(name));
897 \brief The QVariant class acts like a union for the most common Qt data types.
903 Because C++ forbids unions from including types that have
904 non-default constructors or destructors, most interesting Qt
905 classes cannot be used in unions. Without QVariant, this would be
906 a problem for QObject::property() and for database work, etc.
908 A QVariant object holds a single value of a single type() at a
909 time. (Some type()s are multi-valued, for example a string list.)
910 You can find out what type, T, the variant holds, convert it to a
911 different type using convert(), get its value using one of the
912 toT() functions (e.g., toSize()) and check whether the type can
913 be converted to a particular type using canConvert().
915 The methods named toT() (e.g., toInt(), toString()) are const. If
916 you ask for the stored type, they return a copy of the stored
917 object. If you ask for a type that can be generated from the
918 stored type, toT() copies and converts and leaves the object
919 itself unchanged. If you ask for a type that cannot be generated
920 from the stored type, the result depends on the type; see the
921 function documentation for details.
923 Here is some example code to demonstrate the use of QVariant:
925 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 0
927 You can even store QList<QVariant> and QMap<QString, QVariant>
928 values in a variant, so you can easily construct arbitrarily
929 complex data structures of arbitrary types. This is very powerful
930 and versatile, but may prove less memory and speed efficient than
931 storing specific types in standard data structures.
933 QVariant also supports the notion of null values, where you can
934 have a defined type with no value set. However, note that QVariant
935 types can only be cast when they have had a value set.
937 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 1
939 QVariant can be extended to support other types than those
940 mentioned in the \l Type enum. See the \l QMetaType documentation
943 \section1 A Note on GUI Types
945 Because QVariant is part of the QtCore library, it cannot provide
946 conversion functions to data types defined in QtGui, such as
947 QColor, QImage, and QPixmap. In other words, there is no \c
948 toColor() function. Instead, you can use the QVariant::value() or
949 the qvariant_cast() template function. For example:
951 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 2
953 The inverse conversion (e.g., from QColor to QVariant) is
954 automatic for all data types supported by QVariant, including
957 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 3
959 \section1 Using canConvert() and convert() Consecutively
961 When using canConvert() and convert() consecutively, it is possible for
962 canConvert() to return true, but convert() to return false. This
963 is typically because canConvert() only reports the general ability of
964 QVariant to convert between types given suitable data; it is still
965 possible to supply data which cannot actually be converted.
967 For example, canConvert() would return true when called on a variant
968 containing a string because, in principle, QVariant is able to convert
969 strings of numbers to integers.
970 However, if the string contains non-numeric characters, it cannot be
971 converted to an integer, and any attempt to convert it will fail.
972 Hence, it is important to have both functions return true for a
973 successful conversion.
981 This enum type defines the types of variable that a QVariant can
984 \value Invalid no type
985 \value BitArray a QBitArray
986 \value Bitmap a QBitmap
988 \value Brush a QBrush
989 \value ByteArray a QByteArray
991 \value Color a QColor
992 \value Cursor a QCursor
994 \value DateTime a QDateTime
995 \value Double a double
996 \value EasingCurve a QEasingCurve
999 \value Hash a QVariantHash
1001 \value Image a QImage
1003 \value KeySequence a QKeySequence
1005 \value LineF a QLineF
1006 \value List a QVariantList
1007 \value Locale a QLocale
1008 \value LongLong a \l qlonglong
1009 \value Map a QVariantMap
1010 \value Matrix a QMatrix
1011 \value Transform a QTransform
1012 \value Matrix4x4 a QMatrix4x4
1013 \value Palette a QPalette
1015 \value Pixmap a QPixmap
1016 \value Point a QPoint
1017 \value PointF a QPointF
1018 \value Polygon a QPolygon
1019 \value PolygonF a QPolygonF
1020 \value Quaternion a QQuaternion
1022 \value RectF a QRectF
1023 \value RegExp a QRegExp
1024 \value Region a QRegion
1026 \value SizeF a QSizeF
1027 \value SizePolicy a QSizePolicy
1028 \value String a QString
1029 \value StringList a QStringList
1030 \value TextFormat a QTextFormat
1031 \value TextLength a QTextLength
1033 \value UInt a \l uint
1034 \value ULongLong a \l qulonglong
1036 \value Vector2D a QVector2D
1037 \value Vector3D a QVector3D
1038 \value Vector4D a QVector4D
1040 \value UserType Base value for user-defined types.
1043 \omitvalue ColorGroup
1045 \omitvalue LastGuiType
1046 \omitvalue LastCoreType
1051 \fn QVariant::QVariant()
1053 Constructs an invalid variant.
1058 \fn QVariant::QVariant(int typeOrUserType, const void *copy)
1060 Constructs variant of type \a typeOrUserType, and initializes with
1061 \a copy if \a copy is not 0.
1063 Note that you have to pass the address of the variable you want stored.
1065 Usually, you never have to use this constructor, use QVariant::fromValue()
1066 instead to construct variants from the pointer types represented by
1067 \c QMetaType::VoidStar, \c QMetaType::QObjectStar and
1068 \c QMetaType::QWidgetStar.
1070 \sa QVariant::fromValue(), Type
1074 \fn QVariant::QVariant(Type type)
1076 Constructs a null variant of type \a type.
1082 \fn QVariant::create(int type, const void *copy)
1086 Constructs a variant private of type \a type, and initializes with \a copy if
1090 void QVariant::create(int type, const void *copy)
1093 handlerManager[type]->construct(&d, copy);
1097 \fn QVariant::~QVariant()
1099 Destroys the QVariant and the contained object.
1101 Note that subclasses that reimplement clear() should reimplement
1102 the destructor to call clear(). This destructor calls clear(), but
1103 because it is the destructor, QVariant::clear() is called rather
1104 than a subclass's clear().
1107 QVariant::~QVariant()
1109 if ((d.is_shared && !d.data.shared->ref.deref()) || (!d.is_shared && d.type > Char))
1110 handlerManager[d.type]->clear(&d);
1114 \fn QVariant::QVariant(const QVariant &p)
1116 Constructs a copy of the variant, \a p, passed as the argument to
1120 QVariant::QVariant(const QVariant &p)
1124 d.data.shared->ref.ref();
1125 } else if (p.d.type > Char) {
1126 handlerManager[d.type]->construct(&d, p.constData());
1127 d.is_null = p.d.is_null;
1131 #ifndef QT_NO_DATASTREAM
1133 Reads the variant from the data stream, \a s.
1135 QVariant::QVariant(QDataStream &s)
1140 #endif //QT_NO_DATASTREAM
1143 \fn QVariant::QVariant(const QString &val)
1145 Constructs a new variant with a string value, \a val.
1149 \fn QVariant::QVariant(const QLatin1String &val)
1151 Constructs a new variant with a string value, \a val.
1155 \fn QVariant::QVariant(const char *val)
1157 Constructs a new variant with a string value of \a val.
1158 The variant creates a deep copy of \a val, using the encoding
1159 set by QTextCodec::setCodecForCStrings().
1161 Note that \a val is converted to a QString for storing in the
1162 variant and QVariant::type() will return QMetaType::QString for
1165 You can disable this operator by defining \c
1166 QT_NO_CAST_FROM_ASCII when you compile your applications.
1168 \sa QTextCodec::setCodecForCStrings()
1171 #ifndef QT_NO_CAST_FROM_ASCII
1172 QVariant::QVariant(const char *val)
1174 QString s = QString::fromAscii(val);
1180 \fn QVariant::QVariant(const QStringList &val)
1182 Constructs a new variant with a string list value, \a val.
1186 \fn QVariant::QVariant(const QMap<QString, QVariant> &val)
1188 Constructs a new variant with a map of QVariants, \a val.
1192 \fn QVariant::QVariant(const QHash<QString, QVariant> &val)
1194 Constructs a new variant with a hash of QVariants, \a val.
1198 \fn QVariant::QVariant(const QDate &val)
1200 Constructs a new variant with a date value, \a val.
1204 \fn QVariant::QVariant(const QTime &val)
1206 Constructs a new variant with a time value, \a val.
1210 \fn QVariant::QVariant(const QDateTime &val)
1212 Constructs a new variant with a date/time value, \a val.
1217 \fn QVariant::QVariant(const QEasingCurve &val)
1219 Constructs a new variant with an easing curve value, \a val.
1223 \fn QVariant::QVariant(const QByteArray &val)
1225 Constructs a new variant with a bytearray value, \a val.
1229 \fn QVariant::QVariant(const QBitArray &val)
1231 Constructs a new variant with a bitarray value, \a val.
1235 \fn QVariant::QVariant(const QPoint &val)
1237 Constructs a new variant with a point value of \a val.
1241 \fn QVariant::QVariant(const QPointF &val)
1243 Constructs a new variant with a point value of \a val.
1247 \fn QVariant::QVariant(const QRectF &val)
1249 Constructs a new variant with a rect value of \a val.
1253 \fn QVariant::QVariant(const QLineF &val)
1255 Constructs a new variant with a line value of \a val.
1259 \fn QVariant::QVariant(const QLine &val)
1261 Constructs a new variant with a line value of \a val.
1265 \fn QVariant::QVariant(const QRect &val)
1267 Constructs a new variant with a rect value of \a val.
1271 \fn QVariant::QVariant(const QSize &val)
1273 Constructs a new variant with a size value of \a val.
1277 \fn QVariant::QVariant(const QSizeF &val)
1279 Constructs a new variant with a size value of \a val.
1283 \fn QVariant::QVariant(const QUrl &val)
1285 Constructs a new variant with a url value of \a val.
1289 \fn QVariant::QVariant(int val)
1291 Constructs a new variant with an integer value, \a val.
1295 \fn QVariant::QVariant(uint val)
1297 Constructs a new variant with an unsigned integer value, \a val.
1301 \fn QVariant::QVariant(qlonglong val)
1303 Constructs a new variant with a long long integer value, \a val.
1307 \fn QVariant::QVariant(qulonglong val)
1309 Constructs a new variant with an unsigned long long integer value, \a val.
1314 \fn QVariant::QVariant(bool val)
1316 Constructs a new variant with a boolean value, \a val.
1320 \fn QVariant::QVariant(double val)
1322 Constructs a new variant with a floating point value, \a val.
1326 \fn QVariant::QVariant(float val)
1328 Constructs a new variant with a floating point value, \a val.
1333 \fn QVariant::QVariant(const QList<QVariant> &val)
1335 Constructs a new variant with a list value, \a val.
1339 \fn QVariant::QVariant(const QChar &c)
1341 Constructs a new variant with a char value, \a c.
1345 \fn QVariant::QVariant(const QLocale &l)
1347 Constructs a new variant with a locale value, \a l.
1351 \fn QVariant::QVariant(const QRegExp ®Exp)
1353 Constructs a new variant with the regexp value \a regExp.
1357 \fn QVariant::QVariant(Qt::GlobalColor color)
1359 Constructs a new variant of type QVariant::Color and initializes
1362 This is a convenience constructor that allows \c{QVariant(Qt::blue);}
1363 to create a valid QVariant storing a QColor.
1365 Note: This constructor will assert if the application does not link
1366 to the Qt GUI library.
1369 QVariant::QVariant(Type type)
1370 { create(type, 0); }
1371 QVariant::QVariant(int typeOrUserType, const void *copy)
1372 { create(typeOrUserType, copy); d.is_null = false; }
1375 flags is true if it is a pointer type
1377 QVariant::QVariant(int typeOrUserType, const void *copy, uint flags)
1379 if (flags) { //type is a pointer type
1380 d.type = typeOrUserType;
1381 d.data.ptr = *reinterpret_cast<void *const*>(copy);
1383 create(typeOrUserType, copy);
1388 QVariant::QVariant(int val)
1389 { d.is_null = false; d.type = Int; d.data.i = val; }
1390 QVariant::QVariant(uint val)
1391 { d.is_null = false; d.type = UInt; d.data.u = val; }
1392 QVariant::QVariant(qlonglong val)
1393 { d.is_null = false; d.type = LongLong; d.data.ll = val; }
1394 QVariant::QVariant(qulonglong val)
1395 { d.is_null = false; d.type = ULongLong; d.data.ull = val; }
1396 QVariant::QVariant(bool val)
1397 { d.is_null = false; d.type = Bool; d.data.b = val; }
1398 QVariant::QVariant(double val)
1399 { d.is_null = false; d.type = Double; d.data.d = val; }
1401 QVariant::QVariant(const QByteArray &val)
1402 { d.is_null = false; d.type = ByteArray; v_construct<QByteArray>(&d, val); }
1403 QVariant::QVariant(const QBitArray &val)
1404 { d.is_null = false; d.type = BitArray; v_construct<QBitArray>(&d, val); }
1405 QVariant::QVariant(const QString &val)
1406 { d.is_null = false; d.type = String; v_construct<QString>(&d, val); }
1407 QVariant::QVariant(const QChar &val)
1408 { d.is_null = false; d.type = Char; v_construct<QChar>(&d, val); }
1409 QVariant::QVariant(const QLatin1String &val)
1410 { QString str(val); d.is_null = false; d.type = String; v_construct<QString>(&d, str); }
1411 QVariant::QVariant(const QStringList &val)
1412 { d.is_null = false; d.type = StringList; v_construct<QStringList>(&d, val); }
1414 QVariant::QVariant(const QDate &val)
1415 { d.is_null = false; d.type = Date; v_construct<QDate>(&d, val); }
1416 QVariant::QVariant(const QTime &val)
1417 { d.is_null = false; d.type = Time; v_construct<QTime>(&d, val); }
1418 QVariant::QVariant(const QDateTime &val)
1419 { d.is_null = false; d.type = DateTime; v_construct<QDateTime>(&d, val); }
1420 #ifndef QT_BOOTSTRAPPED
1421 QVariant::QVariant(const QEasingCurve &val)
1422 { d.is_null = false; d.type = EasingCurve; v_construct<QEasingCurve>(&d, val); }
1424 QVariant::QVariant(const QList<QVariant> &list)
1425 { d.is_null = false; d.type = List; v_construct<QVariantList>(&d, list); }
1426 QVariant::QVariant(const QMap<QString, QVariant> &map)
1427 { d.is_null = false; d.type = Map; v_construct<QVariantMap>(&d, map); }
1428 QVariant::QVariant(const QHash<QString, QVariant> &hash)
1429 { d.is_null = false; d.type = Hash; v_construct<QVariantHash>(&d, hash); }
1430 #ifndef QT_NO_GEOM_VARIANT
1431 QVariant::QVariant(const QPoint &pt) { d.is_null = false; d.type = Point; v_construct<QPoint>(&d, pt); }
1432 QVariant::QVariant(const QPointF &pt) { d.is_null = false; d.type = PointF; v_construct<QPointF>(&d, pt); }
1433 QVariant::QVariant(const QRectF &r) { d.is_null = false; d.type = RectF; v_construct<QRectF>(&d, r); }
1434 QVariant::QVariant(const QLineF &l) { d.is_null = false; d.type = LineF; v_construct<QLineF>(&d, l); }
1435 QVariant::QVariant(const QLine &l) { d.is_null = false; d.type = Line; v_construct<QLine>(&d, l); }
1436 QVariant::QVariant(const QRect &r) { d.is_null = false; d.type = Rect; v_construct<QRect>(&d, r); }
1437 QVariant::QVariant(const QSize &s) { d.is_null = false; d.type = Size; v_construct<QSize>(&d, s); }
1438 QVariant::QVariant(const QSizeF &s) { d.is_null = false; d.type = SizeF; v_construct<QSizeF>(&d, s); }
1440 QVariant::QVariant(const QUrl &u) { d.is_null = false; d.type = Url; v_construct<QUrl>(&d, u); }
1441 QVariant::QVariant(const QLocale &l) { d.is_null = false; d.type = Locale; v_construct<QLocale>(&d, l); }
1442 #ifndef QT_NO_REGEXP
1443 QVariant::QVariant(const QRegExp ®Exp) { d.is_null = false; d.type = RegExp; v_construct<QRegExp>(&d, regExp); }
1445 QVariant::QVariant(Qt::GlobalColor color) { create(62, &color); }
1448 Returns the storage type of the value stored in the variant.
1449 Although this function is declared as returning QVariant::Type,
1450 the return value should be interpreted as QMetaType::Type. In
1451 particular, QVariant::UserType is returned here only if the value
1452 is equal or greater than QMetaType::User.
1454 Note that return values in the ranges QVariant::Char through
1455 QVariant::RegExp and QVariant::Font through QVariant::Transform
1456 correspond to the values in the ranges QMetaType::QChar through
1457 QMetaType::QRegExp and QMetaType::QFont through QMetaType::QQuaternion.
1459 Pay particular attention when working with char and QChar
1460 variants. Note that there is no QVariant constructor specifically
1461 for type char, but there is one for QChar. For a variant of type
1462 QChar, this function returns QVariant::Char, which is the same as
1463 QMetaType::QChar, but for a variant of type \c char, this function
1464 returns QMetaType::Char, which is \e not the same as
1467 Also note that the types \c void*, \c long, \c short, \c unsigned
1468 \c long, \c unsigned \c short, \c unsigned \c char, \c float, \c
1469 QObject*, and \c QWidget* are represented in QMetaType::Type but
1470 not in QVariant::Type, and they can be returned by this function.
1471 However, they are considered to be user defined types when tested
1472 against QVariant::Type.
1474 To test whether an instance of QVariant contains a data type that
1475 is compatible with the data type you are interested in, use
1479 QVariant::Type QVariant::type() const
1481 return d.type >= QMetaType::User ? UserType : static_cast<Type>(d.type);
1485 Returns the storage type of the value stored in the variant. For
1486 non-user types, this is the same as type().
1491 int QVariant::userType() const
1497 Assigns the value of the variant \a variant to this variant.
1499 QVariant& QVariant::operator=(const QVariant &variant)
1501 if (this == &variant)
1505 if (variant.d.is_shared) {
1506 variant.d.data.shared->ref.ref();
1508 } else if (variant.d.type > Char) {
1509 d.type = variant.d.type;
1510 handlerManager[d.type]->construct(&d, variant.constData());
1511 d.is_null = variant.d.is_null;
1520 \fn void QVariant::swap(QVariant &other)
1523 Swaps variant \a other with this variant. This operation is very
1524 fast and never fails.
1528 \fn void QVariant::detach()
1533 void QVariant::detach()
1535 if (!d.is_shared || d.data.shared->ref.load() == 1)
1540 handlerManager[d.type]->construct(&dd, constData());
1541 if (!d.data.shared->ref.deref())
1542 handlerManager[d.type]->clear(&d);
1543 d.data.shared = dd.data.shared;
1547 \fn bool QVariant::isDetached() const
1552 // ### Qt 5: change typeName()(and froends= to return a QString. Suggestion from Harald.
1554 Returns the name of the type stored in the variant. The returned
1555 strings describe the C++ datatype used to store the data: for
1556 example, "QFont", "QString", or "QVariantList". An Invalid
1559 const char *QVariant::typeName() const
1561 return typeToName(Type(d.type));
1565 Convert this variant to type Invalid and free up any resources
1568 void QVariant::clear()
1570 if ((d.is_shared && !d.data.shared->ref.deref()) || (!d.is_shared && d.type > Char))
1571 handlerManager[d.type]->clear(&d);
1574 d.is_shared = false;
1578 Converts the enum representation of the storage type, \a typ, to
1579 its string representation.
1581 Returns a null pointer if the type is QVariant::Invalid or doesn't exist.
1583 const char *QVariant::typeToName(Type typ)
1587 if (typ == UserType)
1590 return QMetaType::typeName(typ);
1595 Converts the string representation of the storage type given in \a
1596 name, to its enum representation.
1598 If the string representation cannot be converted to any enum
1599 representation, the variant is set to \c Invalid.
1601 QVariant::Type QVariant::nameToType(const char *name)
1603 if (!name || !*name)
1605 if (strcmp(name, "Q3CString") == 0)
1607 if (strcmp(name, "Q_LLONG") == 0)
1609 if (strcmp(name, "Q_ULLONG") == 0)
1611 if (strcmp(name, "QIconSet") == 0)
1613 if (strcmp(name, "UserType") == 0)
1616 int metaType = QMetaType::type(name);
1617 return metaType <= int(LastGuiType) ? QVariant::Type(metaType) : UserType;
1620 #ifndef QT_NO_DATASTREAM
1621 enum { MapFromThreeCount = 36 };
1622 static const ushort map_from_three[MapFromThreeCount] =
1628 QVariant::StringList,
1644 QVariant::ByteArray,
1649 QVariant::SizePolicy,
1653 QVariant::ByteArray,
1655 QVariant::KeySequence,
1658 QVariant::ULongLong,
1659 QVariant::EasingCurve
1663 Internal function for loading a variant from stream \a s. Use the
1664 stream operators instead.
1668 void QVariant::load(QDataStream &s)
1674 if (s.version() < QDataStream::Qt_4_0) {
1675 if (u >= MapFromThreeCount)
1677 u = map_from_three[u];
1679 qint8 is_null = false;
1680 if (s.version() >= QDataStream::Qt_4_2)
1682 if (u == QVariant::UserType) {
1685 u = QMetaType::type(name);
1687 s.setStatus(QDataStream::ReadCorruptData);
1691 create(static_cast<int>(u), 0);
1692 d.is_null = is_null;
1695 // Since we wrote something, we should read something
1702 // const cast is safe since we operate on a newly constructed variant
1703 if (!QMetaType::load(s, d.type, const_cast<void *>(constData()))) {
1704 s.setStatus(QDataStream::ReadCorruptData);
1705 qWarning("QVariant::load: unable to load type %d.", d.type);
1710 Internal function for saving a variant to the stream \a s. Use the
1711 stream operators instead.
1715 void QVariant::save(QDataStream &s) const
1717 quint32 tp = type();
1718 if (s.version() < QDataStream::Qt_4_0) {
1720 for (i = MapFromThreeCount - 1; i >= 0; i--) {
1721 if (map_from_three[i] == tp) {
1732 if (s.version() >= QDataStream::Qt_4_2)
1733 s << qint8(d.is_null);
1734 if (tp == QVariant::UserType) {
1735 s << QMetaType::typeName(userType());
1743 if (!QMetaType::save(s, d.type, constData())) {
1744 Q_ASSERT_X(false, "QVariant::save", "Invalid type to save");
1745 qWarning("QVariant::save: unable to save type %d.", d.type);
1752 Reads a variant \a p from the stream \a s.
1754 \sa \link datastreamformat.html Format of the QDataStream
1757 QDataStream& operator>>(QDataStream &s, QVariant &p)
1764 Writes a variant \a p to the stream \a s.
1766 \sa \link datastreamformat.html Format of the QDataStream
1769 QDataStream& operator<<(QDataStream &s, const QVariant &p)
1776 Reads a variant type \a p in enum representation from the stream \a s.
1778 QDataStream& operator>>(QDataStream &s, QVariant::Type &p)
1782 p = (QVariant::Type)u;
1788 Writes a variant type \a p to the stream \a s.
1790 QDataStream& operator<<(QDataStream &s, const QVariant::Type p)
1792 s << static_cast<quint32>(p);
1797 #endif //QT_NO_DATASTREAM
1800 \fn bool QVariant::isValid() const
1802 Returns true if the storage type of this variant is not
1803 QVariant::Invalid; otherwise returns false.
1806 template <typename T>
1807 inline T qVariantToHelper(const QVariant::Private &d, QVariant::Type t, const HandlersManager &handlerManager)
1810 return *v_cast<T>(&d);
1813 handlerManager[d.type]->convert(&d, t, &ret, 0);
1818 \fn QStringList QVariant::toStringList() const
1820 Returns the variant as a QStringList if the variant has type()
1821 StringList, \l String, or \l List of a type that can be converted
1822 to QString; otherwise returns an empty list.
1824 \sa canConvert(), convert()
1826 QStringList QVariant::toStringList() const
1828 return qVariantToHelper<QStringList>(d, StringList, handlerManager);
1832 Returns the variant as a QString if the variant has type() \l
1833 String, \l Bool, \l ByteArray, \l Char, \l Date, \l DateTime, \l
1834 Double, \l Int, \l LongLong, \l StringList, \l Time, \l UInt, or
1835 \l ULongLong; otherwise returns an empty string.
1837 \sa canConvert(), convert()
1839 QString QVariant::toString() const
1841 return qVariantToHelper<QString>(d, String, handlerManager);
1845 Returns the variant as a QMap<QString, QVariant> if the variant
1846 has type() \l Map; otherwise returns an empty map.
1848 \sa canConvert(), convert()
1850 QVariantMap QVariant::toMap() const
1852 return qVariantToHelper<QVariantMap>(d, Map, handlerManager);
1856 Returns the variant as a QHash<QString, QVariant> if the variant
1857 has type() \l Hash; otherwise returns an empty map.
1859 \sa canConvert(), convert()
1861 QVariantHash QVariant::toHash() const
1863 return qVariantToHelper<QVariantHash>(d, Hash, handlerManager);
1867 \fn QDate QVariant::toDate() const
1869 Returns the variant as a QDate if the variant has type() \l Date,
1870 \l DateTime, or \l String; otherwise returns an invalid date.
1872 If the type() is \l String, an invalid date will be returned if the
1873 string cannot be parsed as a Qt::ISODate format date.
1875 \sa canConvert(), convert()
1877 QDate QVariant::toDate() const
1879 return qVariantToHelper<QDate>(d, Date, handlerManager);
1883 \fn QTime QVariant::toTime() const
1885 Returns the variant as a QTime if the variant has type() \l Time,
1886 \l DateTime, or \l String; otherwise returns an invalid time.
1888 If the type() is \l String, an invalid time will be returned if
1889 the string cannot be parsed as a Qt::ISODate format time.
1891 \sa canConvert(), convert()
1893 QTime QVariant::toTime() const
1895 return qVariantToHelper<QTime>(d, Time, handlerManager);
1899 \fn QDateTime QVariant::toDateTime() const
1901 Returns the variant as a QDateTime if the variant has type() \l
1902 DateTime, \l Date, or \l String; otherwise returns an invalid
1905 If the type() is \l String, an invalid date/time will be returned
1906 if the string cannot be parsed as a Qt::ISODate format date/time.
1908 \sa canConvert(), convert()
1910 QDateTime QVariant::toDateTime() const
1912 return qVariantToHelper<QDateTime>(d, DateTime, handlerManager);
1917 \fn QEasingCurve QVariant::toEasingCurve() const
1919 Returns the variant as a QEasingCurve if the variant has type() \l
1920 EasingCurve; otherwise returns a default easing curve.
1922 \sa canConvert(), convert()
1924 #ifndef QT_BOOTSTRAPPED
1925 QEasingCurve QVariant::toEasingCurve() const
1927 return qVariantToHelper<QEasingCurve>(d, EasingCurve, handlerManager);
1932 \fn QByteArray QVariant::toByteArray() const
1934 Returns the variant as a QByteArray if the variant has type() \l
1935 ByteArray or \l String (converted using QString::fromAscii());
1936 otherwise returns an empty byte array.
1938 \sa canConvert(), convert()
1940 QByteArray QVariant::toByteArray() const
1942 return qVariantToHelper<QByteArray>(d, ByteArray, handlerManager);
1945 #ifndef QT_NO_GEOM_VARIANT
1947 \fn QPoint QVariant::toPoint() const
1949 Returns the variant as a QPoint if the variant has type()
1950 \l Point or \l PointF; otherwise returns a null QPoint.
1952 \sa canConvert(), convert()
1954 QPoint QVariant::toPoint() const
1956 return qVariantToHelper<QPoint>(d, Point, handlerManager);
1960 \fn QRect QVariant::toRect() const
1962 Returns the variant as a QRect if the variant has type() \l Rect;
1963 otherwise returns an invalid QRect.
1965 \sa canConvert(), convert()
1967 QRect QVariant::toRect() const
1969 return qVariantToHelper<QRect>(d, Rect, handlerManager);
1973 \fn QSize QVariant::toSize() const
1975 Returns the variant as a QSize if the variant has type() \l Size;
1976 otherwise returns an invalid QSize.
1978 \sa canConvert(), convert()
1980 QSize QVariant::toSize() const
1982 return qVariantToHelper<QSize>(d, Size, handlerManager);
1986 \fn QSizeF QVariant::toSizeF() const
1988 Returns the variant as a QSizeF if the variant has type() \l
1989 SizeF; otherwise returns an invalid QSizeF.
1991 \sa canConvert(), convert()
1993 QSizeF QVariant::toSizeF() const
1995 return qVariantToHelper<QSizeF>(d, SizeF, handlerManager);
1999 \fn QRectF QVariant::toRectF() const
2001 Returns the variant as a QRectF if the variant has type() \l Rect
2002 or \l RectF; otherwise returns an invalid QRectF.
2004 \sa canConvert(), convert()
2006 QRectF QVariant::toRectF() const
2008 return qVariantToHelper<QRectF>(d, RectF, handlerManager);
2012 \fn QLineF QVariant::toLineF() const
2014 Returns the variant as a QLineF if the variant has type() \l
2015 LineF; otherwise returns an invalid QLineF.
2017 \sa canConvert(), convert()
2019 QLineF QVariant::toLineF() const
2021 return qVariantToHelper<QLineF>(d, LineF, handlerManager);
2025 \fn QLine QVariant::toLine() const
2027 Returns the variant as a QLine if the variant has type() \l Line;
2028 otherwise returns an invalid QLine.
2030 \sa canConvert(), convert()
2032 QLine QVariant::toLine() const
2034 return qVariantToHelper<QLine>(d, Line, handlerManager);
2038 \fn QPointF QVariant::toPointF() const
2040 Returns the variant as a QPointF if the variant has type() \l
2041 Point or \l PointF; otherwise returns a null QPointF.
2043 \sa canConvert(), convert()
2045 QPointF QVariant::toPointF() const
2047 return qVariantToHelper<QPointF>(d, PointF, handlerManager);
2050 #endif // QT_NO_GEOM_VARIANT
2053 \fn QUrl QVariant::toUrl() const
2055 Returns the variant as a QUrl if the variant has type()
2056 \l Url; otherwise returns an invalid QUrl.
2058 \sa canConvert(), convert()
2060 QUrl QVariant::toUrl() const
2062 return qVariantToHelper<QUrl>(d, Url, handlerManager);
2066 \fn QLocale QVariant::toLocale() const
2068 Returns the variant as a QLocale if the variant has type()
2069 \l Locale; otherwise returns an invalid QLocale.
2071 \sa canConvert(), convert()
2073 QLocale QVariant::toLocale() const
2075 return qVariantToHelper<QLocale>(d, Locale, handlerManager);
2079 \fn QRegExp QVariant::toRegExp() const
2082 Returns the variant as a QRegExp if the variant has type() \l
2083 RegExp; otherwise returns an empty QRegExp.
2085 \sa canConvert(), convert()
2087 #ifndef QT_NO_REGEXP
2088 QRegExp QVariant::toRegExp() const
2090 return qVariantToHelper<QRegExp>(d, RegExp, handlerManager);
2095 \fn QChar QVariant::toChar() const
2097 Returns the variant as a QChar if the variant has type() \l Char,
2098 \l Int, or \l UInt; otherwise returns an invalid QChar.
2100 \sa canConvert(), convert()
2102 QChar QVariant::toChar() const
2104 return qVariantToHelper<QChar>(d, Char, handlerManager);
2108 Returns the variant as a QBitArray if the variant has type()
2109 \l BitArray; otherwise returns an empty bit array.
2111 \sa canConvert(), convert()
2113 QBitArray QVariant::toBitArray() const
2115 return qVariantToHelper<QBitArray>(d, BitArray, handlerManager);
2118 template <typename T>
2119 inline T qNumVariantToHelper(const QVariant::Private &d,
2120 const HandlersManager &handlerManager, bool *ok, const T& val)
2122 uint t = qMetaTypeId<T>();
2129 if (!handlerManager[d.type]->convert(&d, QVariant::Type(t), &ret, ok) && ok)
2135 Returns the variant as an int if the variant has type() \l Int,
2136 \l Bool, \l ByteArray, \l Char, \l Double, \l LongLong, \l
2137 String, \l UInt, or \l ULongLong; otherwise returns 0.
2139 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2140 converted to an int; otherwise \c{*}\a{ok} is set to false.
2142 \bold{Warning:} If the value is convertible to a \l LongLong but is too
2143 large to be represented in an int, the resulting arithmetic overflow will
2144 not be reflected in \a ok. A simple workaround is to use QString::toInt().
2145 Fixing this bug has been postponed to Qt 5 in order to avoid breaking existing code.
2147 \sa canConvert(), convert()
2149 int QVariant::toInt(bool *ok) const
2151 return qNumVariantToHelper<int>(d, handlerManager, ok, d.data.i);
2155 Returns the variant as an unsigned int if the variant has type()
2156 \l UInt, \l Bool, \l ByteArray, \l Char, \l Double, \l Int, \l
2157 LongLong, \l String, or \l ULongLong; otherwise returns 0.
2159 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2160 converted to an unsigned int; otherwise \c{*}\a{ok} is set to false.
2162 \bold{Warning:} If the value is convertible to a \l ULongLong but is too
2163 large to be represented in an unsigned int, the resulting arithmetic overflow will
2164 not be reflected in \a ok. A simple workaround is to use QString::toUInt().
2165 Fixing this bug has been postponed to Qt 5 in order to avoid breaking existing code.
2167 \sa canConvert(), convert()
2169 uint QVariant::toUInt(bool *ok) const
2171 return qNumVariantToHelper<uint>(d, handlerManager, ok, d.data.u);
2175 Returns the variant as a long long int if the variant has type()
2176 \l LongLong, \l Bool, \l ByteArray, \l Char, \l Double, \l Int,
2177 \l String, \l UInt, or \l ULongLong; otherwise returns 0.
2179 If \a ok is non-null: \c{*}\c{ok} is set to true if the value could be
2180 converted to an int; otherwise \c{*}\c{ok} is set to false.
2182 \sa canConvert(), convert()
2184 qlonglong QVariant::toLongLong(bool *ok) const
2186 return qNumVariantToHelper<qlonglong>(d, handlerManager, ok, d.data.ll);
2190 Returns the variant as as an unsigned long long int if the
2191 variant has type() \l ULongLong, \l Bool, \l ByteArray, \l Char,
2192 \l Double, \l Int, \l LongLong, \l String, or \l UInt; otherwise
2195 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2196 converted to an int; otherwise \c{*}\a{ok} is set to false.
2198 \sa canConvert(), convert()
2200 qulonglong QVariant::toULongLong(bool *ok) const
2202 return qNumVariantToHelper<qulonglong>(d, handlerManager, ok, d.data.ull);
2206 Returns the variant as a bool if the variant has type() Bool.
2208 Returns true if the variant has type() \l Bool, \l Char, \l Double,
2209 \l Int, \l LongLong, \l UInt, or \l ULongLong and the value is
2210 non-zero, or if the variant has type \l String or \l ByteArray and
2211 its lower-case content is not empty, "0" or "false"; otherwise
2214 \sa canConvert(), convert()
2216 bool QVariant::toBool() const
2222 handlerManager[d.type]->convert(&d, Bool, &res, 0);
2228 Returns the variant as a double if the variant has type() \l
2229 Double, \l QMetaType::Float, \l Bool, \l ByteArray, \l Int, \l LongLong, \l String, \l
2230 UInt, or \l ULongLong; otherwise returns 0.0.
2232 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2233 converted to a double; otherwise \c{*}\a{ok} is set to false.
2235 \sa canConvert(), convert()
2237 double QVariant::toDouble(bool *ok) const
2239 return qNumVariantToHelper<double>(d, handlerManager, ok, d.data.d);
2243 Returns the variant as a float if the variant has type() \l
2244 Double, \l QMetaType::Float, \l Bool, \l ByteArray, \l Int, \l LongLong, \l String, \l
2245 UInt, or \l ULongLong; otherwise returns 0.0.
2249 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2250 converted to a double; otherwise \c{*}\a{ok} is set to false.
2252 \sa canConvert(), convert()
2254 float QVariant::toFloat(bool *ok) const
2256 return qNumVariantToHelper<float>(d, handlerManager, ok, d.data.f);
2260 Returns the variant as a qreal if the variant has type() \l
2261 Double, \l QMetaType::Float, \l Bool, \l ByteArray, \l Int, \l LongLong, \l String, \l
2262 UInt, or \l ULongLong; otherwise returns 0.0.
2266 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2267 converted to a double; otherwise \c{*}\a{ok} is set to false.
2269 \sa canConvert(), convert()
2271 qreal QVariant::toReal(bool *ok) const
2273 return qNumVariantToHelper<qreal>(d, handlerManager, ok, d.data.real);
2277 Returns the variant as a QVariantList if the variant has type()
2278 \l List or \l StringList; otherwise returns an empty list.
2280 \sa canConvert(), convert()
2282 QVariantList QVariant::toList() const
2284 return qVariantToHelper<QVariantList>(d, List, handlerManager);
2288 static const quint32 qCanConvertMatrix[QVariant::LastCoreType + 1] =
2292 /*Bool*/ 1 << QVariant::Double | 1 << QVariant::Int | 1 << QVariant::UInt
2293 | 1 << QVariant::LongLong | 1 << QVariant::ULongLong | 1 << QVariant::ByteArray
2294 | 1 << QVariant::String | 1 << QVariant::Char,
2296 /*Int*/ 1 << QVariant::UInt | 1 << QVariant::String | 1 << QVariant::Double
2297 | 1 << QVariant::Bool | 1 << QVariant::LongLong | 1 << QVariant::ULongLong
2298 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2300 /*UInt*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::Double
2301 | 1 << QVariant::Bool | 1 << QVariant::LongLong | 1 << QVariant::ULongLong
2302 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2304 /*LLong*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::Double
2305 | 1 << QVariant::Bool | 1 << QVariant::UInt | 1 << QVariant::ULongLong
2306 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2308 /*ULlong*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::Double
2309 | 1 << QVariant::Bool | 1 << QVariant::UInt | 1 << QVariant::LongLong
2310 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2312 /*double*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::ULongLong
2313 | 1 << QVariant::Bool | 1 << QVariant::UInt | 1 << QVariant::LongLong
2314 | 1 << QVariant::ByteArray,
2316 /*QChar*/ 1 << QVariant::Int | 1 << QVariant::UInt | 1 << QVariant::LongLong
2317 | 1 << QVariant::ULongLong,
2321 /*QList*/ 1 << QVariant::StringList,
2323 /*QString*/ 1 << QVariant::StringList | 1 << QVariant::ByteArray | 1 << QVariant::Int
2324 | 1 << QVariant::UInt | 1 << QVariant::Bool | 1 << QVariant::Double
2325 | 1 << QVariant::Date | 1 << QVariant::Time | 1 << QVariant::DateTime
2326 | 1 << QVariant::LongLong | 1 << QVariant::ULongLong | 1 << QVariant::Char
2327 | 1 << QVariant::Url | 1 << QVariant::Uuid,
2329 /*QStringList*/ 1 << QVariant::List | 1 << QVariant::String,
2331 /*QByteArray*/ 1 << QVariant::String | 1 << QVariant::Int | 1 << QVariant::UInt | 1 << QVariant::Bool
2332 | 1 << QVariant::Double | 1 << QVariant::LongLong | 1 << QVariant::ULongLong,
2336 /*QDate*/ 1 << QVariant::String | 1 << QVariant::DateTime,
2338 /*QTime*/ 1 << QVariant::String | 1 << QVariant::DateTime,
2340 /*QDateTime*/ 1 << QVariant::String | 1 << QVariant::Date,
2342 /*QUrl*/ 1 << QVariant::String,
2346 /*QRect*/ 1 << QVariant::RectF,
2348 /*QRectF*/ 1 << QVariant::Rect,
2350 /*QSize*/ 1 << QVariant::SizeF,
2352 /*QSizeF*/ 1 << QVariant::Size,
2354 /*QLine*/ 1 << QVariant::LineF,
2356 /*QLineF*/ 1 << QVariant::Line,
2358 /*QPoint*/ 1 << QVariant::PointF,
2360 /*QPointF*/ 1 << QVariant::Point,
2368 /*QUuid*/ 1 << QVariant::String
2372 Returns true if the variant's type can be cast to the requested
2373 type, \a t. Such casting is done automatically when calling the
2374 toInt(), toBool(), ... methods.
2376 The following casts are done automatically:
2379 \header \o Type \o Automatically Cast To
2380 \row \o \l Bool \o \l Char, \l Double, \l Int, \l LongLong, \l String, \l UInt, \l ULongLong
2381 \row \o \l ByteArray \o \l Double, \l Int, \l LongLong, \l String, \l UInt, \l ULongLong
2382 \row \o \l Char \o \l Bool, \l Int, \l UInt, \l LongLong, \l ULongLong
2383 \row \o \l Color \o \l String
2384 \row \o \l Date \o \l DateTime, \l String
2385 \row \o \l DateTime \o \l Date, \l String, \l Time
2386 \row \o \l Double \o \l Bool, \l Int, \l LongLong, \l String, \l UInt, \l ULongLong
2387 \row \o \l Font \o \l String
2388 \row \o \l Int \o \l Bool, \l Char, \l Double, \l LongLong, \l String, \l UInt, \l ULongLong
2389 \row \o \l KeySequence \o \l Int, \l String
2390 \row \o \l List \o \l StringList (if the list's items can be converted to strings)
2391 \row \o \l LongLong \o \l Bool, \l ByteArray, \l Char, \l Double, \l Int, \l String, \l UInt, \l ULongLong
2392 \row \o \l Point \o PointF
2393 \row \o \l Rect \o RectF
2394 \row \o \l String \o \l Bool, \l ByteArray, \l Char, \l Color, \l Date, \l DateTime, \l Double,
2395 \l Font, \l Int, \l KeySequence, \l LongLong, \l StringList, \l Time, \l UInt,
2397 \row \o \l StringList \o \l List, \l String (if the list contains exactly one item)
2398 \row \o \l Time \o \l String
2399 \row \o \l UInt \o \l Bool, \l Char, \l Double, \l Int, \l LongLong, \l String, \l ULongLong
2400 \row \o \l ULongLong \o \l Bool, \l Char, \l Double, \l Int, \l LongLong, \l String, \l UInt
2405 bool QVariant::canConvert(Type t) const
2407 //we can treat floats as double
2408 //the reason for not doing it the "proper" way is that QMetaType::Float's value is 135,
2409 //which can't be handled by qCanConvertMatrix
2410 //In addition QVariant::Type doesn't have a Float value, so we're using QMetaType::Float
2411 const uint currentType = ((d.type == QMetaType::Float) ? QVariant::Double : d.type);
2412 if (uint(t) == uint(QMetaType::Float)) t = QVariant::Double;
2414 if (currentType == uint(t))
2417 if (currentType > QVariant::LastCoreType || t > QVariant::LastCoreType) {
2420 return currentType == QVariant::KeySequence
2421 || currentType == QMetaType::ULong
2422 || currentType == QMetaType::Long
2423 || currentType == QMetaType::UShort
2424 || currentType == QMetaType::UChar
2425 || currentType == QMetaType::Char
2426 || currentType == QMetaType::Short;
2427 case QVariant::Image:
2428 return currentType == QVariant::Pixmap || currentType == QVariant::Bitmap;
2429 case QVariant::Pixmap:
2430 return currentType == QVariant::Image || currentType == QVariant::Bitmap
2431 || currentType == QVariant::Brush;
2432 case QVariant::Bitmap:
2433 return currentType == QVariant::Pixmap || currentType == QVariant::Image;
2434 case QVariant::ByteArray:
2435 return currentType == QVariant::Color;
2436 case QVariant::String:
2437 return currentType == QVariant::KeySequence || currentType == QVariant::Font
2438 || currentType == QVariant::Color;
2439 case QVariant::KeySequence:
2440 return currentType == QVariant::String || currentType == QVariant::Int;
2441 case QVariant::Font:
2442 return currentType == QVariant::String;
2443 case QVariant::Color:
2444 return currentType == QVariant::String || currentType == QVariant::ByteArray
2445 || currentType == QVariant::Brush;
2446 case QVariant::Brush:
2447 return currentType == QVariant::Color || currentType == QVariant::Pixmap;
2448 case QMetaType::Long:
2449 case QMetaType::Char:
2450 case QMetaType::UChar:
2451 case QMetaType::ULong:
2452 case QMetaType::Short:
2453 case QMetaType::UShort:
2454 return qCanConvertMatrix[QVariant::Int] & (1 << currentType) || currentType == QVariant::Int;
2460 if(t == String && currentType == StringList)
2461 return v_cast<QStringList>(&d)->count() == 1;
2463 return qCanConvertMatrix[t] & (1 << currentType);
2467 Casts the variant to the requested type, \a t. If the cast cannot be
2468 done, the variant is cleared. Returns true if the current type of
2469 the variant was successfully cast; otherwise returns false.
2471 \warning For historical reasons, converting a null QVariant results
2472 in a null value of the desired type (e.g., an empty string for
2473 QString) and a result of false.
2475 \sa canConvert(), clear()
2478 bool QVariant::convert(Type t)
2480 if (d.type == uint(t))
2483 QVariant oldValue = *this;
2486 if (!oldValue.canConvert(t))
2490 if (oldValue.isNull())
2494 if (!handlerManager[d.type]->convert(&oldValue.d, t, data(), &isOk))
2501 \fn convert(const int type, void *ptr) const
2503 Created for qvariant_cast() usage
2505 bool QVariant::convert(const int type, void *ptr) const
2507 Q_ASSERT(type < int(QMetaType::User));
2508 return handlerManager[type]->convert(&d, QVariant::Type(type), ptr, 0);
2513 \fn bool operator==(const QVariant &v1, const QVariant &v2)
2517 Returns true if \a v1 and \a v2 are equal; otherwise returns false.
2519 \warning This function doesn't support custom types registered
2520 with qRegisterMetaType().
2523 \fn bool operator!=(const QVariant &v1, const QVariant &v2)
2527 Returns false if \a v1 and \a v2 are equal; otherwise returns true.
2529 \warning This function doesn't support custom types registered
2530 with qRegisterMetaType().
2533 /*! \fn bool QVariant::operator==(const QVariant &v) const
2535 Compares this QVariant with \a v and returns true if they are
2536 equal; otherwise returns false.
2538 In the case of custom types, their equalness operators are not called.
2539 Instead the values' addresses are compared.
2543 \fn bool QVariant::operator!=(const QVariant &v) const
2545 Compares this QVariant with \a v and returns true if they are not
2546 equal; otherwise returns false.
2548 \warning This function doesn't support custom types registered
2549 with qRegisterMetaType().
2552 static bool qIsNumericType(uint tp)
2554 return (tp >= QVariant::Bool && tp <= QVariant::Double)
2555 || (tp >= QMetaType::Long && tp <= QMetaType::Float);
2558 static bool qIsFloatingPoint(uint tp)
2560 return tp == QVariant::Double || tp == QMetaType::Float;
2565 bool QVariant::cmp(const QVariant &v) const
2568 if (d.type != v2.d.type) {
2569 if (qIsNumericType(d.type) && qIsNumericType(v.d.type)) {
2570 if (qIsFloatingPoint(d.type) || qIsFloatingPoint(v.d.type))
2571 return qFuzzyCompare(toReal(), v.toReal());
2573 return toLongLong() == v.toLongLong();
2575 if (!v2.canConvert(Type(d.type)) || !v2.convert(Type(d.type)))
2578 return handlerManager[d.type]->compare(&d, &v2.d);
2584 const void *QVariant::constData() const
2586 return d.is_shared ? d.data.shared->ptr : reinterpret_cast<const void *>(&d.data.ptr);
2590 \fn const void* QVariant::data() const
2596 void* QVariant::data()
2599 return const_cast<void *>(constData());
2604 Returns true if this is a NULL variant, false otherwise.
2606 bool QVariant::isNull() const
2608 return handlerManager[d.type]->isNull(&d);
2611 #ifndef QT_NO_DEBUG_STREAM
2612 QDebug operator<<(QDebug dbg, const QVariant &v)
2614 #ifndef Q_BROKEN_DEBUG_STREAM
2615 dbg.nospace() << "QVariant(" << QMetaType::typeName(v.userType()) << ", ";
2616 handlerManager[v.d.type]->debugStream(dbg, v);
2617 dbg.nospace() << ')';
2620 qWarning("This compiler doesn't support streaming QVariant to QDebug");
2626 QDebug operator<<(QDebug dbg, const QVariant::Type p)
2628 #ifndef Q_BROKEN_DEBUG_STREAM
2629 dbg.nospace() << "QVariant::" << QMetaType::typeName(p);
2632 qWarning("This compiler doesn't support streaming QVariant::Type to QDebug");
2640 /*! \fn void QVariant::setValue(const T &value)
2642 Stores a copy of \a value. If \c{T} is a type that QVariant
2643 doesn't support, QMetaType is used to store the value. A compile
2644 error will occur if QMetaType doesn't handle the type.
2648 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 4
2650 \sa value(), fromValue(), canConvert()
2653 /*! \fn T QVariant::value() const
2655 Returns the stored value converted to the template type \c{T}.
2656 Call canConvert() to find out whether a type can be converted.
2657 If the value cannot be converted, \l{default-constructed value}
2660 If the type \c{T} is supported by QVariant, this function behaves
2661 exactly as toString(), toInt() etc.
2665 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 5
2667 \sa setValue(), fromValue(), canConvert()
2670 /*! \fn bool QVariant::canConvert() const
2672 Returns true if the variant can be converted to the template type \c{T},
2677 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 6
2682 /*! \fn static QVariant QVariant::fromValue(const T &value)
2684 Returns a QVariant containing a copy of \a value. Behaves
2685 exactly like setValue() otherwise.
2689 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 7
2691 \note If you are working with custom types, you should use
2692 the Q_DECLARE_METATYPE() macro to register your custom type.
2694 \sa setValue(), value()
2698 \fn QVariant qVariantFromValue(const T &value)
2702 Returns a variant containing a copy of the given \a value
2703 with template type \c{T}.
2705 This function is equivalent to QVariant::fromValue(\a value).
2707 \note This function was provided as a workaround for MSVC 6
2708 which did not support member template functions. It is advised
2709 to use the other form in new code.
2711 For example, a QObject pointer can be stored in a variant with the
2714 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 8
2716 \sa QVariant::fromValue()
2719 /*! \fn void qVariantSetValue(QVariant &variant, const T &value)
2723 Sets the contents of the given \a variant to a copy of the
2724 \a value with the specified template type \c{T}.
2726 This function is equivalent to QVariant::setValue(\a value).
2728 \note This function was provided as a workaround for MSVC 6
2729 which did not support member template functions. It is advised
2730 to use the other form in new code.
2732 \sa QVariant::setValue()
2736 \fn T qvariant_cast(const QVariant &value)
2739 Returns the given \a value converted to the template type \c{T}.
2741 This function is equivalent to QVariant::value().
2743 \sa QVariant::value()
2746 /*! \fn T qVariantValue(const QVariant &value)
2750 Returns the given \a value converted to the template type \c{T}.
2752 This function is equivalent to
2753 \l{QVariant::value()}{QVariant::value}<T>(\a value).
2755 \note This function was provided as a workaround for MSVC 6
2756 which did not support member template functions. It is advised
2757 to use the other form in new code.
2759 \sa QVariant::value(), qvariant_cast()
2762 /*! \fn bool qVariantCanConvert(const QVariant &value)
2766 Returns true if the given \a value can be converted to the
2767 template type specified; otherwise returns false.
2769 This function is equivalent to QVariant::canConvert(\a value).
2771 \note This function was provided as a workaround for MSVC 6
2772 which did not support member template functions. It is advised
2773 to use the other form in new code.
2775 \sa QVariant::canConvert()
2779 \typedef QVariantList
2782 Synonym for QList<QVariant>.
2786 \typedef QVariantMap
2789 Synonym for QMap<QString, QVariant>.
2793 \typedef QVariantHash
2797 Synonym for QHash<QString, QVariant>.
2801 \typedef QVariant::DataPtr
2806 \fn DataPtr &QVariant::data_ptr()