1 /****************************************************************************
3 ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: http://www.qt-project.org/
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 #ifndef QT_BOOTSTRAPPED
57 #include "qabstractitemmodel.h"
59 #include "private/qvariant_p.h"
60 #include "qmetatype_p.h"
62 #ifndef QT_NO_GEOM_VARIANT
83 static const QVariant::Handler *Handlers[QModulesPrivate::ModulesCount];
85 const QVariant::Handler *operator[] (const int typeId) const
87 return Handlers[QModulesPrivate::moduleForType(typeId)];
90 void registerHandler(const QModulesPrivate::Names name, const QVariant::Handler *handler)
92 Handlers[name] = handler;
95 inline void unregisterHandler(const QModulesPrivate::Names name);
101 struct TypeDefiniton {
102 static const bool IsAvailable = true;
105 // Ignore these types, as incomplete
106 #ifdef QT_BOOTSTRAPPED
107 template<> struct TypeDefiniton<QEasingCurve> { static const bool IsAvailable = false; };
108 template<> struct TypeDefiniton<QModelIndex> { static const bool IsAvailable = false; };
110 #ifdef QT_NO_GEOM_VARIANT
111 template<> struct TypeDefiniton<QRect> { static const bool IsAvailable = false; };
112 template<> struct TypeDefiniton<QRectF> { static const bool IsAvailable = false; };
113 template<> struct TypeDefiniton<QSize> { static const bool IsAvailable = false; };
114 template<> struct TypeDefiniton<QSizeF> { static const bool IsAvailable = false; };
115 template<> struct TypeDefiniton<QLine> { static const bool IsAvailable = false; };
116 template<> struct TypeDefiniton<QLineF> { static const bool IsAvailable = false; };
117 template<> struct TypeDefiniton<QPoint> { static const bool IsAvailable = false; };
118 template<> struct TypeDefiniton<QPointF> { static const bool IsAvailable = false; };
121 struct CoreTypesFilter {
124 static const bool IsAccepted = QTypeModuleInfo<T>::IsCore && TypeDefiniton<T>::IsAvailable;
127 } // annonymous used to hide TypeDefiniton
129 namespace { // annonymous used to hide QVariant handlers
131 static void construct(QVariant::Private *x, const void *copy)
133 QVariantConstructor<CoreTypesFilter> constructor(x, copy);
134 QMetaTypeSwitcher::switcher<void>(constructor, x->type, 0);
137 static void clear(QVariant::Private *d)
139 QVariantDestructor<CoreTypesFilter> cleaner(d);
140 QMetaTypeSwitcher::switcher<void>(cleaner, d->type, 0);
143 static bool isNull(const QVariant::Private *d)
145 QVariantIsNull<CoreTypesFilter> isNull(d);
146 return QMetaTypeSwitcher::switcher<bool>(isNull, d->type, 0);
152 Compares \a a to \a b. The caller guarantees that \a a and \a b
153 are of the same type.
155 static bool compare(const QVariant::Private *a, const QVariant::Private *b)
157 QVariantComparator<CoreTypesFilter> comparator(a, b);
158 return QMetaTypeSwitcher::switcher<bool>(comparator, a->type, 0);
164 static qlonglong qMetaTypeNumber(const QVariant::Private *d)
169 case QMetaType::LongLong:
171 case QMetaType::Char:
172 return qlonglong(d->data.c);
173 case QMetaType::Short:
174 return qlonglong(d->data.s);
175 case QMetaType::Long:
176 return qlonglong(d->data.l);
177 case QMetaType::Float:
178 return qRound64(d->data.f);
179 case QVariant::Double:
180 return qRound64(d->data.d);
186 static qulonglong qMetaTypeUNumber(const QVariant::Private *d)
191 case QVariant::ULongLong:
193 case QMetaType::UChar:
195 case QMetaType::UShort:
197 case QMetaType::ULong:
204 static qlonglong qConvertToNumber(const QVariant::Private *d, bool *ok)
208 switch (uint(d->type)) {
209 case QVariant::String:
210 return v_cast<QString>(d)->toLongLong(ok);
212 return v_cast<QChar>(d)->unicode();
213 case QVariant::ByteArray:
214 return v_cast<QByteArray>(d)->toLongLong(ok);
216 return qlonglong(d->data.b);
217 case QVariant::Double:
219 case QMetaType::Char:
220 case QMetaType::Short:
221 case QMetaType::Long:
222 case QMetaType::Float:
223 case QMetaType::LongLong:
224 return qMetaTypeNumber(d);
225 case QVariant::ULongLong:
227 case QMetaType::UChar:
228 case QMetaType::UShort:
229 case QMetaType::ULong:
230 return qlonglong(qMetaTypeUNumber(d));
237 static qulonglong qConvertToUnsignedNumber(const QVariant::Private *d, bool *ok)
241 switch (uint(d->type)) {
242 case QVariant::String:
243 return v_cast<QString>(d)->toULongLong(ok);
245 return v_cast<QChar>(d)->unicode();
246 case QVariant::ByteArray:
247 return v_cast<QByteArray>(d)->toULongLong(ok);
249 return qulonglong(d->data.b);
250 case QVariant::Double:
252 case QMetaType::Char:
253 case QMetaType::Short:
254 case QMetaType::Long:
255 case QMetaType::Float:
256 case QMetaType::LongLong:
257 return qulonglong(qMetaTypeNumber(d));
258 case QVariant::ULongLong:
260 case QMetaType::UChar:
261 case QMetaType::UShort:
262 case QMetaType::ULong:
263 return qMetaTypeUNumber(d);
267 return Q_UINT64_C(0);
270 template<typename TInput, typename LiteralWrapper>
271 inline bool qt_convertToBool(const QVariant::Private *const d)
273 TInput str = v_cast<TInput>(d)->toLower();
274 return !(str == LiteralWrapper("0") || str == LiteralWrapper("false") || str.isEmpty());
280 Converts \a d to type \a t, which is placed in \a result.
282 static bool convert(const QVariant::Private *d, QVariant::Type t, void *result, bool *ok)
284 Q_ASSERT(d->type != uint(t));
294 case QVariant::String:
295 *static_cast<QUrl *>(result) = QUrl(*v_cast<QString>(d));
301 case QVariant::String: {
302 QString *str = static_cast<QString *>(result);
305 *str = QString(*v_cast<QChar>(d));
307 case QMetaType::Char:
308 case QMetaType::UChar:
309 *str = QChar::fromAscii(d->data.c);
311 case QMetaType::Short:
312 case QMetaType::Long:
314 case QVariant::LongLong:
315 *str = QString::number(qMetaTypeNumber(d));
318 case QVariant::ULongLong:
319 case QMetaType::UShort:
320 case QMetaType::ULong:
321 *str = QString::number(qMetaTypeUNumber(d));
323 case QMetaType::Float:
324 *str = QString::number(d->data.f, 'g', FLT_DIG);
326 case QVariant::Double:
327 *str = QString::number(d->data.d, 'g', DBL_DIG);
329 #if !defined(QT_NO_DATESTRING)
331 *str = v_cast<QDate>(d)->toString(Qt::ISODate);
334 *str = v_cast<QTime>(d)->toString(Qt::ISODate);
336 case QVariant::DateTime:
337 *str = v_cast<QDateTime>(d)->toString(Qt::ISODate);
341 *str = QLatin1String(d->data.b ? "true" : "false");
343 case QVariant::ByteArray:
344 *str = QString::fromAscii(v_cast<QByteArray>(d)->constData());
346 case QVariant::StringList:
347 if (v_cast<QStringList>(d)->count() == 1)
348 *str = v_cast<QStringList>(d)->at(0);
351 *str = v_cast<QUrl>(d)->toString();
354 *str = v_cast<QUuid>(d)->toString();
361 case QVariant::Char: {
362 QChar *c = static_cast<QChar *>(result);
365 case QVariant::LongLong:
366 case QMetaType::Char:
367 case QMetaType::Short:
368 case QMetaType::Long:
369 case QMetaType::Float:
370 *c = QChar(ushort(qMetaTypeNumber(d)));
373 case QVariant::ULongLong:
374 case QMetaType::UChar:
375 case QMetaType::UShort:
376 case QMetaType::ULong:
377 *c = QChar(ushort(qMetaTypeUNumber(d)));
384 #ifndef QT_NO_GEOM_VARIANT
385 case QVariant::Size: {
386 QSize *s = static_cast<QSize *>(result);
388 case QVariant::SizeF:
389 *s = v_cast<QSizeF>(d)->toSize();
397 case QVariant::SizeF: {
398 QSizeF *s = static_cast<QSizeF *>(result);
401 *s = QSizeF(*(v_cast<QSize>(d)));
409 case QVariant::Line: {
410 QLine *s = static_cast<QLine *>(result);
412 case QVariant::LineF:
413 *s = v_cast<QLineF>(d)->toLine();
421 case QVariant::LineF: {
422 QLineF *s = static_cast<QLineF *>(result);
425 *s = QLineF(*(v_cast<QLine>(d)));
433 case QVariant::StringList:
434 if (d->type == QVariant::List) {
435 QStringList *slst = static_cast<QStringList *>(result);
436 const QVariantList *list = v_cast<QVariantList >(d);
437 for (int i = 0; i < list->size(); ++i)
438 slst->append(list->at(i).toString());
439 } else if (d->type == QVariant::String) {
440 QStringList *slst = static_cast<QStringList *>(result);
441 *slst = QStringList(*v_cast<QString>(d));
446 case QVariant::Date: {
447 QDate *dt = static_cast<QDate *>(result);
448 if (d->type == QVariant::DateTime)
449 *dt = v_cast<QDateTime>(d)->date();
450 #ifndef QT_NO_DATESTRING
451 else if (d->type == QVariant::String)
452 *dt = QDate::fromString(*v_cast<QString>(d), Qt::ISODate);
457 return dt->isValid();
459 case QVariant::Time: {
460 QTime *t = static_cast<QTime *>(result);
462 case QVariant::DateTime:
463 *t = v_cast<QDateTime>(d)->time();
465 #ifndef QT_NO_DATESTRING
466 case QVariant::String:
467 *t = QTime::fromString(*v_cast<QString>(d), Qt::ISODate);
475 case QVariant::DateTime: {
476 QDateTime *dt = static_cast<QDateTime *>(result);
478 #ifndef QT_NO_DATESTRING
479 case QVariant::String:
480 *dt = QDateTime::fromString(*v_cast<QString>(d), Qt::ISODate);
484 *dt = QDateTime(*v_cast<QDate>(d));
489 return dt->isValid();
491 case QVariant::ByteArray: {
492 QByteArray *ba = static_cast<QByteArray *>(result);
494 case QVariant::String:
495 *ba = v_cast<QString>(d)->toAscii();
497 case QVariant::Double:
498 *ba = QByteArray::number(d->data.d, 'g', DBL_DIG);
500 case QMetaType::Float:
501 *ba = QByteArray::number(d->data.f, 'g', FLT_DIG);
503 case QMetaType::Char:
504 case QMetaType::UChar:
505 *ba = QByteArray(1, d->data.c);
508 case QVariant::LongLong:
509 case QMetaType::Short:
510 case QMetaType::Long:
511 *ba = QByteArray::number(qMetaTypeNumber(d));
514 case QVariant::ULongLong:
515 case QMetaType::UShort:
516 case QMetaType::ULong:
517 *ba = QByteArray::number(qMetaTypeUNumber(d));
520 *ba = QByteArray(d->data.b ? "true" : "false");
527 case QMetaType::Short:
528 *static_cast<short *>(result) = short(qConvertToNumber(d, ok));
530 case QMetaType::Long:
531 *static_cast<long *>(result) = long(qConvertToNumber(d, ok));
533 case QMetaType::UShort:
534 *static_cast<ushort *>(result) = ushort(qConvertToUnsignedNumber(d, ok));
536 case QMetaType::ULong:
537 *static_cast<ulong *>(result) = ulong(qConvertToUnsignedNumber(d, ok));
540 *static_cast<int *>(result) = int(qConvertToNumber(d, ok));
543 *static_cast<uint *>(result) = uint(qConvertToUnsignedNumber(d, ok));
545 case QVariant::LongLong:
546 *static_cast<qlonglong *>(result) = qConvertToNumber(d, ok);
548 case QVariant::ULongLong: {
549 *static_cast<qulonglong *>(result) = qConvertToUnsignedNumber(d, ok);
552 case QMetaType::UChar: {
553 *static_cast<uchar *>(result) = qConvertToUnsignedNumber(d, ok);
556 case QVariant::Bool: {
557 bool *b = static_cast<bool *>(result);
559 case QVariant::ByteArray:
560 *b = qt_convertToBool<QByteArray, QByteArray>(d);
562 case QVariant::String:
563 *b = qt_convertToBool<QString, QLatin1String>(d);
566 *b = !v_cast<QChar>(d)->isNull();
568 case QVariant::Double:
570 case QVariant::LongLong:
571 case QMetaType::Char:
572 case QMetaType::Short:
573 case QMetaType::Long:
574 case QMetaType::Float:
575 *b = qMetaTypeNumber(d) != Q_INT64_C(0);
578 case QVariant::ULongLong:
579 case QMetaType::UChar:
580 case QMetaType::UShort:
581 case QMetaType::ULong:
582 *b = qMetaTypeUNumber(d) != Q_UINT64_C(0);
590 case QVariant::Double: {
591 double *f = static_cast<double *>(result);
593 case QVariant::String:
594 *f = v_cast<QString>(d)->toDouble(ok);
596 case QVariant::ByteArray:
597 *f = v_cast<QByteArray>(d)->toDouble(ok);
600 *f = double(d->data.b);
602 case QMetaType::Float:
603 *f = double(d->data.f);
605 case QVariant::LongLong:
607 case QMetaType::Char:
608 case QMetaType::Short:
609 case QMetaType::Long:
610 *f = double(qMetaTypeNumber(d));
613 case QVariant::ULongLong:
614 case QMetaType::UChar:
615 case QMetaType::UShort:
616 case QMetaType::ULong:
617 *f = double(qMetaTypeUNumber(d));
625 case QMetaType::Float: {
626 float *f = static_cast<float *>(result);
628 case QVariant::String:
629 *f = v_cast<QString>(d)->toFloat(ok);
631 case QVariant::ByteArray:
632 *f = v_cast<QByteArray>(d)->toFloat(ok);
635 *f = float(d->data.b);
637 case QVariant::Double:
638 *f = float(d->data.d);
640 case QVariant::LongLong:
642 case QMetaType::Char:
643 case QMetaType::Short:
644 case QMetaType::Long:
645 *f = float(qMetaTypeNumber(d));
648 case QVariant::ULongLong:
649 case QMetaType::UChar:
650 case QMetaType::UShort:
651 case QMetaType::ULong:
652 *f = float(qMetaTypeUNumber(d));
661 if (d->type == QVariant::StringList) {
662 QVariantList *lst = static_cast<QVariantList *>(result);
663 const QStringList *slist = v_cast<QStringList>(d);
664 for (int i = 0; i < slist->size(); ++i)
665 lst->append(QVariant(slist->at(i)));
666 } else if (qstrcmp(QMetaType::typeName(d->type), "QList<QVariant>") == 0) {
667 *static_cast<QVariantList *>(result) =
668 *static_cast<QList<QVariant> *>(d->data.shared->ptr);
674 if (qstrcmp(QMetaType::typeName(d->type), "QMap<QString, QVariant>") == 0) {
675 *static_cast<QVariantMap *>(result) =
676 *static_cast<QMap<QString, QVariant> *>(d->data.shared->ptr);
682 if (qstrcmp(QMetaType::typeName(d->type), "QHash<QString, QVariant>") == 0) {
683 *static_cast<QVariantHash *>(result) =
684 *static_cast<QHash<QString, QVariant> *>(d->data.shared->ptr);
689 #ifndef QT_NO_GEOM_VARIANT
691 if (d->type == QVariant::RectF)
692 *static_cast<QRect *>(result) = (v_cast<QRectF>(d))->toRect();
696 case QVariant::RectF:
697 if (d->type == QVariant::Rect)
698 *static_cast<QRectF *>(result) = *v_cast<QRect>(d);
702 case QVariant::PointF:
703 if (d->type == QVariant::Point)
704 *static_cast<QPointF *>(result) = *v_cast<QPoint>(d);
708 case QVariant::Point:
709 if (d->type == QVariant::PointF)
710 *static_cast<QPoint *>(result) = (v_cast<QPointF>(d))->toPoint();
714 case QMetaType::Char:
716 *static_cast<qint8 *>(result) = qint8(qConvertToNumber(d, ok));
722 case QVariant::String:
723 *static_cast<QUuid *>(result) = QUuid(*v_cast<QString>(d));
735 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
736 static void streamDebug(QDebug dbg, const QVariant &v)
738 QVariant::Private *d = const_cast<QVariant::Private *>(&v.data_ptr());
739 QVariantDebugStream<CoreTypesFilter> stream(dbg, d);
740 QMetaTypeSwitcher::switcher<void>(stream, d->type, 0);
744 const QVariant::Handler qt_kernel_variant_handler = {
748 #ifndef QT_NO_DATASTREAM
755 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
762 static void dummyConstruct(QVariant::Private *, const void *) { Q_ASSERT_X(false, "QVariant", "Trying to construct an unknown type"); }
763 static void dummyClear(QVariant::Private *) { Q_ASSERT_X(false, "QVariant", "Trying to clear an unknown type"); }
764 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; }
765 static bool dummyCompare(const QVariant::Private *, const QVariant::Private *) { Q_ASSERT_X(false, "QVariant", "Trying to compare an unknown types"); return false; }
766 static bool dummyConvert(const QVariant::Private *, QVariant::Type , void *, bool *) { Q_ASSERT_X(false, "QVariant", "Trying to convert an unknown type"); return false; }
767 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
768 static void dummyStreamDebug(QDebug, const QVariant &) { Q_ASSERT_X(false, "QVariant", "Trying to convert an unknown type"); }
770 const QVariant::Handler qt_dummy_variant_handler = {
774 #ifndef QT_NO_DATASTREAM
781 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
788 static void customConstruct(QVariant::Private *d, const void *copy)
790 const uint size = QMetaType::sizeOf(d->type);
792 d->type = QVariant::Invalid;
796 // this logic should match with QVariantIntegrator::CanUseInternalSpace
797 if (size <= sizeof(QVariant::Private::Data)
798 && (QMetaType::typeFlags(d->type) & QMetaType::MovableType)) {
799 QMetaType::construct(d->type, &d->data.ptr, copy);
800 d->is_shared = false;
802 void *ptr = QMetaType::create(d->type, copy);
804 d->data.shared = new QVariant::PrivateShared(ptr);
808 static void customClear(QVariant::Private *d)
811 QMetaType::destruct(d->type, &d->data.ptr);
813 QMetaType::destroy(d->type, d->data.shared->ptr);
814 delete d->data.shared;
818 static bool customIsNull(const QVariant::Private *d)
823 static bool customCompare(const QVariant::Private *a, const QVariant::Private *b)
825 const char *const typeName = QMetaType::typeName(a->type);
826 if (Q_UNLIKELY(!typeName) && Q_LIKELY(!QMetaType::isRegistered(a->type)))
827 qFatal("QVariant::compare: type %d unknown to QVariant.", a->type);
829 const void *a_ptr = a->is_shared ? a->data.shared->ptr : &(a->data.ptr);
830 const void *b_ptr = b->is_shared ? b->data.shared->ptr : &(b->data.ptr);
832 uint typeNameLen = qstrlen(typeName);
833 if (typeNameLen > 0 && typeName[typeNameLen - 1] == '*')
834 return *static_cast<void *const *>(a_ptr) == *static_cast<void *const *>(b_ptr);
836 if (a->is_null && b->is_null)
839 return !memcmp(a_ptr, b_ptr, QMetaType::sizeOf(a->type));
842 static bool customConvert(const QVariant::Private *, QVariant::Type, void *, bool *ok)
849 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
850 static void customStreamDebug(QDebug, const QVariant &) {}
853 const QVariant::Handler qt_custom_variant_handler = {
857 #ifndef QT_NO_DATASTREAM
864 #if !defined(QT_NO_DEBUG_STREAM) && !defined(Q_BROKEN_DEBUG_STREAM)
871 } // annonymous used to hide QVariant handlers
873 static HandlersManager handlerManager;
874 Q_STATIC_ASSERT_X(!QModulesPrivate::Core, "Initialization assumes that ModulesNames::Core is 0");
875 const QVariant::Handler *HandlersManager::Handlers[QModulesPrivate::ModulesCount]
876 = { &qt_kernel_variant_handler, &qt_dummy_variant_handler,
877 &qt_dummy_variant_handler, &qt_custom_variant_handler };
879 Q_CORE_EXPORT const QVariant::Handler *qcoreVariantHandler()
881 return &qt_kernel_variant_handler;
884 inline void HandlersManager::unregisterHandler(const QModulesPrivate::Names name)
886 Handlers[name] = &qt_dummy_variant_handler;
889 Q_CORE_EXPORT void QVariantPrivate::registerHandler(const int /* Modules::Names */name, const QVariant::Handler *handler)
891 handlerManager.registerHandler(static_cast<QModulesPrivate::Names>(name), handler);
894 Q_CORE_EXPORT void QVariantPrivate::unregisterHandler(const int /* Modules::Names */ name)
896 handlerManager.unregisterHandler(static_cast<QModulesPrivate::Names>(name));
901 \brief The QVariant class acts like a union for the most common Qt data types.
907 Because C++ forbids unions from including types that have
908 non-default constructors or destructors, most interesting Qt
909 classes cannot be used in unions. Without QVariant, this would be
910 a problem for QObject::property() and for database work, etc.
912 A QVariant object holds a single value of a single type() at a
913 time. (Some type()s are multi-valued, for example a string list.)
914 You can find out what type, T, the variant holds, convert it to a
915 different type using convert(), get its value using one of the
916 toT() functions (e.g., toSize()) and check whether the type can
917 be converted to a particular type using canConvert().
919 The methods named toT() (e.g., toInt(), toString()) are const. If
920 you ask for the stored type, they return a copy of the stored
921 object. If you ask for a type that can be generated from the
922 stored type, toT() copies and converts and leaves the object
923 itself unchanged. If you ask for a type that cannot be generated
924 from the stored type, the result depends on the type; see the
925 function documentation for details.
927 Here is some example code to demonstrate the use of QVariant:
929 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 0
931 You can even store QList<QVariant> and QMap<QString, QVariant>
932 values in a variant, so you can easily construct arbitrarily
933 complex data structures of arbitrary types. This is very powerful
934 and versatile, but may prove less memory and speed efficient than
935 storing specific types in standard data structures.
937 QVariant also supports the notion of null values, where you can
938 have a defined type with no value set. However, note that QVariant
939 types can only be cast when they have had a value set.
941 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 1
943 QVariant can be extended to support other types than those
944 mentioned in the \l Type enum. See the \l QMetaType documentation
947 \section1 A Note on GUI Types
949 Because QVariant is part of the QtCore library, it cannot provide
950 conversion functions to data types defined in QtGui, such as
951 QColor, QImage, and QPixmap. In other words, there is no \c
952 toColor() function. Instead, you can use the QVariant::value() or
953 the qvariant_cast() template function. For example:
955 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 2
957 The inverse conversion (e.g., from QColor to QVariant) is
958 automatic for all data types supported by QVariant, including
961 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 3
963 \section1 Using canConvert() and convert() Consecutively
965 When using canConvert() and convert() consecutively, it is possible for
966 canConvert() to return true, but convert() to return false. This
967 is typically because canConvert() only reports the general ability of
968 QVariant to convert between types given suitable data; it is still
969 possible to supply data which cannot actually be converted.
971 For example, canConvert() would return true when called on a variant
972 containing a string because, in principle, QVariant is able to convert
973 strings of numbers to integers.
974 However, if the string contains non-numeric characters, it cannot be
975 converted to an integer, and any attempt to convert it will fail.
976 Hence, it is important to have both functions return true for a
977 successful conversion.
983 \obsolete Use QMetaType::Type instead
986 This enum type defines the types of variable that a QVariant can
989 \value Invalid no type
990 \value BitArray a QBitArray
991 \value Bitmap a QBitmap
993 \value Brush a QBrush
994 \value ByteArray a QByteArray
996 \value Color a QColor
997 \value Cursor a QCursor
999 \value DateTime a QDateTime
1000 \value Double a double
1001 \value EasingCurve a QEasingCurve
1003 \value ModelIndex a QModelIndex
1005 \value Hash a QVariantHash
1007 \value Image a QImage
1009 \value KeySequence a QKeySequence
1011 \value LineF a QLineF
1012 \value List a QVariantList
1013 \value Locale a QLocale
1014 \value LongLong a \l qlonglong
1015 \value Map a QVariantMap
1016 \value Matrix a QMatrix
1017 \value Transform a QTransform
1018 \value Matrix4x4 a QMatrix4x4
1019 \value Palette a QPalette
1021 \value Pixmap a QPixmap
1022 \value Point a QPoint
1023 \value PointF a QPointF
1024 \value Polygon a QPolygon
1025 \value PolygonF a QPolygonF
1026 \value Quaternion a QQuaternion
1028 \value RectF a QRectF
1029 \value RegExp a QRegExp
1030 \value Region a QRegion
1032 \value SizeF a QSizeF
1033 \value SizePolicy a QSizePolicy
1034 \value String a QString
1035 \value StringList a QStringList
1036 \value TextFormat a QTextFormat
1037 \value TextLength a QTextLength
1039 \value UInt a \l uint
1040 \value ULongLong a \l qulonglong
1042 \value Vector2D a QVector2D
1043 \value Vector3D a QVector3D
1044 \value Vector4D a QVector4D
1046 \value UserType Base value for user-defined types.
1049 \omitvalue ColorGroup
1051 \omitvalue LastGuiType
1052 \omitvalue LastCoreType
1057 \fn QVariant::QVariant()
1059 Constructs an invalid variant.
1064 \fn QVariant::QVariant(int typeOrUserType, const void *copy)
1066 Constructs variant of type \a typeOrUserType, and initializes with
1067 \a copy if \a copy is not 0.
1069 Note that you have to pass the address of the variable you want stored.
1071 Usually, you never have to use this constructor, use QVariant::fromValue()
1072 instead to construct variants from the pointer types represented by
1073 \c QMetaType::VoidStar, \c QMetaType::QObjectStar and
1074 \c QMetaType::QWidgetStar.
1076 \sa QVariant::fromValue(), Type
1080 \fn QVariant::QVariant(Type type)
1082 Constructs a null variant of type \a type.
1088 \fn QVariant::create(int type, const void *copy)
1092 Constructs a variant private of type \a type, and initializes with \a copy if
1096 void QVariant::create(int type, const void *copy)
1099 handlerManager[type]->construct(&d, copy);
1103 \fn QVariant::~QVariant()
1105 Destroys the QVariant and the contained object.
1107 Note that subclasses that reimplement clear() should reimplement
1108 the destructor to call clear(). This destructor calls clear(), but
1109 because it is the destructor, QVariant::clear() is called rather
1110 than a subclass's clear().
1113 QVariant::~QVariant()
1115 if ((d.is_shared && !d.data.shared->ref.deref()) || (!d.is_shared && d.type > Char))
1116 handlerManager[d.type]->clear(&d);
1120 \fn QVariant::QVariant(const QVariant &p)
1122 Constructs a copy of the variant, \a p, passed as the argument to
1126 QVariant::QVariant(const QVariant &p)
1130 d.data.shared->ref.ref();
1131 } else if (p.d.type > Char) {
1132 handlerManager[d.type]->construct(&d, p.constData());
1133 d.is_null = p.d.is_null;
1137 #ifndef QT_NO_DATASTREAM
1139 Reads the variant from the data stream, \a s.
1141 QVariant::QVariant(QDataStream &s)
1146 #endif //QT_NO_DATASTREAM
1149 \fn QVariant::QVariant(const QString &val)
1151 Constructs a new variant with a string value, \a val.
1155 \fn QVariant::QVariant(const QLatin1String &val)
1157 Constructs a new variant with a string value, \a val.
1161 \fn QVariant::QVariant(const char *val)
1163 Constructs a new variant with a string value of \a val.
1164 The variant creates a deep copy of \a val, using the encoding
1165 set by QTextCodec::setCodecForCStrings().
1167 Note that \a val is converted to a QString for storing in the
1168 variant and QVariant::type() will return QMetaType::QString for
1171 You can disable this operator by defining \c
1172 QT_NO_CAST_FROM_ASCII when you compile your applications.
1174 \sa QTextCodec::setCodecForCStrings()
1177 #ifndef QT_NO_CAST_FROM_ASCII
1178 QVariant::QVariant(const char *val)
1180 QString s = QString::fromAscii(val);
1186 \fn QVariant::QVariant(const QStringList &val)
1188 Constructs a new variant with a string list value, \a val.
1192 \fn QVariant::QVariant(const QMap<QString, QVariant> &val)
1194 Constructs a new variant with a map of QVariants, \a val.
1198 \fn QVariant::QVariant(const QHash<QString, QVariant> &val)
1200 Constructs a new variant with a hash of QVariants, \a val.
1204 \fn QVariant::QVariant(const QDate &val)
1206 Constructs a new variant with a date value, \a val.
1210 \fn QVariant::QVariant(const QTime &val)
1212 Constructs a new variant with a time value, \a val.
1216 \fn QVariant::QVariant(const QDateTime &val)
1218 Constructs a new variant with a date/time value, \a val.
1223 \fn QVariant::QVariant(const QEasingCurve &val)
1225 Constructs a new variant with an easing curve value, \a val.
1229 \fn QVariant::QVariant(const QByteArray &val)
1231 Constructs a new variant with a bytearray value, \a val.
1235 \fn QVariant::QVariant(const QBitArray &val)
1237 Constructs a new variant with a bitarray value, \a val.
1241 \fn QVariant::QVariant(const QPoint &val)
1243 Constructs a new variant with a point value of \a val.
1247 \fn QVariant::QVariant(const QPointF &val)
1249 Constructs a new variant with a point value of \a val.
1253 \fn QVariant::QVariant(const QRectF &val)
1255 Constructs a new variant with a rect value of \a val.
1259 \fn QVariant::QVariant(const QLineF &val)
1261 Constructs a new variant with a line value of \a val.
1265 \fn QVariant::QVariant(const QLine &val)
1267 Constructs a new variant with a line value of \a val.
1271 \fn QVariant::QVariant(const QRect &val)
1273 Constructs a new variant with a rect value of \a val.
1277 \fn QVariant::QVariant(const QSize &val)
1279 Constructs a new variant with a size value of \a val.
1283 \fn QVariant::QVariant(const QSizeF &val)
1285 Constructs a new variant with a size value of \a val.
1289 \fn QVariant::QVariant(const QUrl &val)
1291 Constructs a new variant with a url value of \a val.
1295 \fn QVariant::QVariant(int val)
1297 Constructs a new variant with an integer value, \a val.
1301 \fn QVariant::QVariant(uint val)
1303 Constructs a new variant with an unsigned integer value, \a val.
1307 \fn QVariant::QVariant(qlonglong val)
1309 Constructs a new variant with a long long integer value, \a val.
1313 \fn QVariant::QVariant(qulonglong val)
1315 Constructs a new variant with an unsigned long long integer value, \a val.
1320 \fn QVariant::QVariant(bool val)
1322 Constructs a new variant with a boolean value, \a val.
1326 \fn QVariant::QVariant(double val)
1328 Constructs a new variant with a floating point value, \a val.
1332 \fn QVariant::QVariant(float val)
1334 Constructs a new variant with a floating point value, \a val.
1339 \fn QVariant::QVariant(const QList<QVariant> &val)
1341 Constructs a new variant with a list value, \a val.
1345 \fn QVariant::QVariant(const QChar &c)
1347 Constructs a new variant with a char value, \a c.
1351 \fn QVariant::QVariant(const QLocale &l)
1353 Constructs a new variant with a locale value, \a l.
1357 \fn QVariant::QVariant(const QRegExp ®Exp)
1359 Constructs a new variant with the regexp value \a regExp.
1363 \fn QVariant::QVariant(Qt::GlobalColor color)
1365 Constructs a new variant of type QVariant::Color and initializes
1368 This is a convenience constructor that allows \c{QVariant(Qt::blue);}
1369 to create a valid QVariant storing a QColor.
1371 Note: This constructor will assert if the application does not link
1372 to the Qt GUI library.
1375 QVariant::QVariant(Type type)
1376 { create(type, 0); }
1377 QVariant::QVariant(int typeOrUserType, const void *copy)
1378 { create(typeOrUserType, copy); d.is_null = false; }
1381 flags is true if it is a pointer type
1383 QVariant::QVariant(int typeOrUserType, const void *copy, uint flags)
1385 if (flags) { //type is a pointer type
1386 d.type = typeOrUserType;
1387 d.data.ptr = *reinterpret_cast<void *const*>(copy);
1389 create(typeOrUserType, copy);
1394 QVariant::QVariant(int val)
1395 { d.is_null = false; d.type = Int; d.data.i = val; }
1396 QVariant::QVariant(uint val)
1397 { d.is_null = false; d.type = UInt; d.data.u = val; }
1398 QVariant::QVariant(qlonglong val)
1399 { d.is_null = false; d.type = LongLong; d.data.ll = val; }
1400 QVariant::QVariant(qulonglong val)
1401 { d.is_null = false; d.type = ULongLong; d.data.ull = val; }
1402 QVariant::QVariant(bool val)
1403 { d.is_null = false; d.type = Bool; d.data.b = val; }
1404 QVariant::QVariant(double val)
1405 { d.is_null = false; d.type = Double; d.data.d = val; }
1407 QVariant::QVariant(const QByteArray &val)
1408 { d.is_null = false; d.type = ByteArray; v_construct<QByteArray>(&d, val); }
1409 QVariant::QVariant(const QBitArray &val)
1410 { d.is_null = false; d.type = BitArray; v_construct<QBitArray>(&d, val); }
1411 QVariant::QVariant(const QString &val)
1412 { d.is_null = false; d.type = String; v_construct<QString>(&d, val); }
1413 QVariant::QVariant(const QChar &val)
1414 { d.is_null = false; d.type = Char; v_construct<QChar>(&d, val); }
1415 QVariant::QVariant(const QLatin1String &val)
1416 { QString str(val); d.is_null = false; d.type = String; v_construct<QString>(&d, str); }
1417 QVariant::QVariant(const QStringList &val)
1418 { d.is_null = false; d.type = StringList; v_construct<QStringList>(&d, val); }
1420 QVariant::QVariant(const QDate &val)
1421 { d.is_null = false; d.type = Date; v_construct<QDate>(&d, val); }
1422 QVariant::QVariant(const QTime &val)
1423 { d.is_null = false; d.type = Time; v_construct<QTime>(&d, val); }
1424 QVariant::QVariant(const QDateTime &val)
1425 { d.is_null = false; d.type = DateTime; v_construct<QDateTime>(&d, val); }
1426 #ifndef QT_BOOTSTRAPPED
1427 QVariant::QVariant(const QEasingCurve &val)
1428 { d.is_null = false; d.type = EasingCurve; v_construct<QEasingCurve>(&d, val); }
1430 QVariant::QVariant(const QList<QVariant> &list)
1431 { d.is_null = false; d.type = List; v_construct<QVariantList>(&d, list); }
1432 QVariant::QVariant(const QMap<QString, QVariant> &map)
1433 { d.is_null = false; d.type = Map; v_construct<QVariantMap>(&d, map); }
1434 QVariant::QVariant(const QHash<QString, QVariant> &hash)
1435 { d.is_null = false; d.type = Hash; v_construct<QVariantHash>(&d, hash); }
1436 #ifndef QT_NO_GEOM_VARIANT
1437 QVariant::QVariant(const QPoint &pt) { d.is_null = false; d.type = Point; v_construct<QPoint>(&d, pt); }
1438 QVariant::QVariant(const QPointF &pt) { d.is_null = false; d.type = PointF; v_construct<QPointF>(&d, pt); }
1439 QVariant::QVariant(const QRectF &r) { d.is_null = false; d.type = RectF; v_construct<QRectF>(&d, r); }
1440 QVariant::QVariant(const QLineF &l) { d.is_null = false; d.type = LineF; v_construct<QLineF>(&d, l); }
1441 QVariant::QVariant(const QLine &l) { d.is_null = false; d.type = Line; v_construct<QLine>(&d, l); }
1442 QVariant::QVariant(const QRect &r) { d.is_null = false; d.type = Rect; v_construct<QRect>(&d, r); }
1443 QVariant::QVariant(const QSize &s) { d.is_null = false; d.type = Size; v_construct<QSize>(&d, s); }
1444 QVariant::QVariant(const QSizeF &s) { d.is_null = false; d.type = SizeF; v_construct<QSizeF>(&d, s); }
1446 QVariant::QVariant(const QUrl &u) { d.is_null = false; d.type = Url; v_construct<QUrl>(&d, u); }
1447 QVariant::QVariant(const QLocale &l) { d.is_null = false; d.type = Locale; v_construct<QLocale>(&d, l); }
1448 #ifndef QT_NO_REGEXP
1449 QVariant::QVariant(const QRegExp ®Exp) { d.is_null = false; d.type = RegExp; v_construct<QRegExp>(&d, regExp); }
1451 QVariant::QVariant(Qt::GlobalColor color) { create(62, &color); }
1454 Returns the storage type of the value stored in the variant.
1455 Although this function is declared as returning QVariant::Type,
1456 the return value should be interpreted as QMetaType::Type. In
1457 particular, QVariant::UserType is returned here only if the value
1458 is equal or greater than QMetaType::User.
1460 Note that return values in the ranges QVariant::Char through
1461 QVariant::RegExp and QVariant::Font through QVariant::Transform
1462 correspond to the values in the ranges QMetaType::QChar through
1463 QMetaType::QRegExp and QMetaType::QFont through QMetaType::QQuaternion.
1465 Pay particular attention when working with char and QChar
1466 variants. Note that there is no QVariant constructor specifically
1467 for type char, but there is one for QChar. For a variant of type
1468 QChar, this function returns QVariant::Char, which is the same as
1469 QMetaType::QChar, but for a variant of type \c char, this function
1470 returns QMetaType::Char, which is \e not the same as
1473 Also note that the types \c void*, \c long, \c short, \c unsigned
1474 \c long, \c unsigned \c short, \c unsigned \c char, \c float, \c
1475 QObject*, and \c QWidget* are represented in QMetaType::Type but
1476 not in QVariant::Type, and they can be returned by this function.
1477 However, they are considered to be user defined types when tested
1478 against QVariant::Type.
1480 To test whether an instance of QVariant contains a data type that
1481 is compatible with the data type you are interested in, use
1485 QVariant::Type QVariant::type() const
1487 return d.type >= QMetaType::User ? UserType : static_cast<Type>(d.type);
1491 Returns the storage type of the value stored in the variant. For
1492 non-user types, this is the same as type().
1497 int QVariant::userType() const
1503 Assigns the value of the variant \a variant to this variant.
1505 QVariant& QVariant::operator=(const QVariant &variant)
1507 if (this == &variant)
1511 if (variant.d.is_shared) {
1512 variant.d.data.shared->ref.ref();
1514 } else if (variant.d.type > Char) {
1515 d.type = variant.d.type;
1516 handlerManager[d.type]->construct(&d, variant.constData());
1517 d.is_null = variant.d.is_null;
1526 \fn void QVariant::swap(QVariant &other)
1529 Swaps variant \a other with this variant. This operation is very
1530 fast and never fails.
1534 \fn void QVariant::detach()
1539 void QVariant::detach()
1541 if (!d.is_shared || d.data.shared->ref.load() == 1)
1546 handlerManager[d.type]->construct(&dd, constData());
1547 if (!d.data.shared->ref.deref())
1548 handlerManager[d.type]->clear(&d);
1549 d.data.shared = dd.data.shared;
1553 \fn bool QVariant::isDetached() const
1558 // ### Qt 5: change typeName()(and froends= to return a QString. Suggestion from Harald.
1560 Returns the name of the type stored in the variant. The returned
1561 strings describe the C++ datatype used to store the data: for
1562 example, "QFont", "QString", or "QVariantList". An Invalid
1565 const char *QVariant::typeName() const
1567 return typeToName(Type(d.type));
1571 Convert this variant to type Invalid and free up any resources
1574 void QVariant::clear()
1576 if ((d.is_shared && !d.data.shared->ref.deref()) || (!d.is_shared && d.type > Char))
1577 handlerManager[d.type]->clear(&d);
1580 d.is_shared = false;
1584 Converts the enum representation of the storage type, \a typ, to
1585 its string representation.
1587 Returns a null pointer if the type is QVariant::Invalid or doesn't exist.
1589 const char *QVariant::typeToName(Type typ)
1593 if (typ == UserType)
1596 return QMetaType::typeName(typ);
1601 Converts the string representation of the storage type given in \a
1602 name, to its enum representation.
1604 If the string representation cannot be converted to any enum
1605 representation, the variant is set to \c Invalid.
1607 QVariant::Type QVariant::nameToType(const char *name)
1609 if (!name || !*name)
1611 if (strcmp(name, "Q3CString") == 0)
1613 if (strcmp(name, "Q_LLONG") == 0)
1615 if (strcmp(name, "Q_ULLONG") == 0)
1617 if (strcmp(name, "QIconSet") == 0)
1619 if (strcmp(name, "UserType") == 0)
1622 int metaType = QMetaType::type(name);
1623 return metaType <= int(LastGuiType) ? QVariant::Type(metaType) : UserType;
1626 #ifndef QT_NO_DATASTREAM
1627 enum { MapFromThreeCount = 36 };
1628 static const ushort mapIdFromQt3ToCurrent[MapFromThreeCount] =
1634 QVariant::StringList,
1650 QVariant::ByteArray,
1655 QVariant::SizePolicy,
1659 QVariant::ByteArray,
1661 QVariant::KeySequence,
1664 QVariant::ULongLong,
1665 QVariant::EasingCurve
1669 Internal function for loading a variant from stream \a s. Use the
1670 stream operators instead.
1674 void QVariant::load(QDataStream &s)
1680 if (s.version() < QDataStream::Qt_4_0) {
1681 if (typeId >= MapFromThreeCount)
1683 typeId = mapIdFromQt3ToCurrent[typeId];
1684 } else if (s.version() < QDataStream::Qt_5_0) {
1685 if (typeId >= 128 && typeId != QVariant::UserType) {
1686 // In Qt4 id == 128 was FirstExtCoreType. In Qt5 ExtCoreTypes set was merged to CoreTypes
1687 // by moving all ids down by 97.
1689 } else if (typeId == 69 /* QIcon */) {
1690 // In Qt5 after modularization project this types where moved to a separate module (and ids were downgraded)
1691 typeId = QMetaType::QIcon;
1692 } else if (typeId == 75 /* QSizePolicy */) {
1693 typeId = QMetaType::QSizePolicy;
1694 } else if (typeId >= 70) {
1695 // and as a result this types recieved lower ids too
1696 if (typeId <= 74) { // QImage QPolygon QRegion QBitmap QCursor
1698 } else if (typeId <= 86) { // QKeySequence QPen QTextLength QTextFormat QMatrix QTransform QMatrix4x4 QVector2D QVector3D QVector4D QQuaternion
1704 qint8 is_null = false;
1705 if (s.version() >= QDataStream::Qt_4_2)
1707 if (typeId == QVariant::UserType) {
1710 typeId = QMetaType::type(name);
1712 s.setStatus(QDataStream::ReadCorruptData);
1716 create(static_cast<int>(typeId), 0);
1717 d.is_null = is_null;
1720 // Since we wrote something, we should read something
1727 // const cast is safe since we operate on a newly constructed variant
1728 if (!QMetaType::load(s, d.type, const_cast<void *>(constData()))) {
1729 s.setStatus(QDataStream::ReadCorruptData);
1730 qWarning("QVariant::load: unable to load type %d.", d.type);
1735 Internal function for saving a variant to the stream \a s. Use the
1736 stream operators instead.
1740 void QVariant::save(QDataStream &s) const
1742 quint32 typeId = type();
1743 if (s.version() < QDataStream::Qt_4_0) {
1745 for (i = MapFromThreeCount - 1; i >= 0; i--) {
1746 if (mapIdFromQt3ToCurrent[i] == typeId) {
1755 } else if (s.version() < QDataStream::Qt_5_0) {
1756 if (typeId >= 128 - 97 && typeId <= LastCoreType) {
1757 // In Qt4 id == 128 was FirstExtCoreType. In Qt5 ExtCoreTypes set was merged to CoreTypes
1758 // by moving all ids down by 97.
1760 } else if (typeId == QMetaType::QIcon) {
1761 // In Qt5 after modularization project this types where moved to a separate module (and ids were downgraded)
1763 } else if (typeId == QMetaType::QSizePolicy) {
1765 } else if (typeId >= QMetaType::QImage) {
1766 // and as a result this types recieved lower ids too
1767 if (typeId <= QMetaType::QCursor) {
1769 } else if (typeId <= QMetaType::QQuaternion) {
1775 if (s.version() >= QDataStream::Qt_4_2)
1776 s << qint8(d.is_null);
1777 if (typeId == QVariant::UserType) {
1778 s << QMetaType::typeName(userType());
1786 if (!QMetaType::save(s, d.type, constData())) {
1787 Q_ASSERT_X(false, "QVariant::save", "Invalid type to save");
1788 qWarning("QVariant::save: unable to save type %d.", d.type);
1795 Reads a variant \a p from the stream \a s.
1797 \sa \link datastreamformat.html Format of the QDataStream
1800 QDataStream& operator>>(QDataStream &s, QVariant &p)
1807 Writes a variant \a p to the stream \a s.
1809 \sa \link datastreamformat.html Format of the QDataStream
1812 QDataStream& operator<<(QDataStream &s, const QVariant &p)
1819 Reads a variant type \a p in enum representation from the stream \a s.
1821 QDataStream& operator>>(QDataStream &s, QVariant::Type &p)
1825 p = (QVariant::Type)u;
1831 Writes a variant type \a p to the stream \a s.
1833 QDataStream& operator<<(QDataStream &s, const QVariant::Type p)
1835 s << static_cast<quint32>(p);
1840 #endif //QT_NO_DATASTREAM
1843 \fn bool QVariant::isValid() const
1845 Returns true if the storage type of this variant is not
1846 QVariant::Invalid; otherwise returns false.
1849 template <typename T>
1850 inline T qVariantToHelper(const QVariant::Private &d, const HandlersManager &handlerManager)
1852 const QVariant::Type targetType = static_cast<const QVariant::Type>(qMetaTypeId<T>());
1853 if (d.type == targetType)
1854 return *v_cast<T>(&d);
1857 handlerManager[d.type]->convert(&d, targetType, &ret, 0);
1862 \fn QStringList QVariant::toStringList() const
1864 Returns the variant as a QStringList if the variant has type()
1865 StringList, \l String, or \l List of a type that can be converted
1866 to QString; otherwise returns an empty list.
1868 \sa canConvert(), convert()
1870 QStringList QVariant::toStringList() const
1872 return qVariantToHelper<QStringList>(d, handlerManager);
1876 Returns the variant as a QString if the variant has type() \l
1877 String, \l Bool, \l ByteArray, \l Char, \l Date, \l DateTime, \l
1878 Double, \l Int, \l LongLong, \l StringList, \l Time, \l UInt, or
1879 \l ULongLong; otherwise returns an empty string.
1881 \sa canConvert(), convert()
1883 QString QVariant::toString() const
1885 return qVariantToHelper<QString>(d, handlerManager);
1889 Returns the variant as a QMap<QString, QVariant> if the variant
1890 has type() \l Map; otherwise returns an empty map.
1892 \sa canConvert(), convert()
1894 QVariantMap QVariant::toMap() const
1896 return qVariantToHelper<QVariantMap>(d, handlerManager);
1900 Returns the variant as a QHash<QString, QVariant> if the variant
1901 has type() \l Hash; otherwise returns an empty map.
1903 \sa canConvert(), convert()
1905 QVariantHash QVariant::toHash() const
1907 return qVariantToHelper<QVariantHash>(d, handlerManager);
1911 \fn QDate QVariant::toDate() const
1913 Returns the variant as a QDate if the variant has type() \l Date,
1914 \l DateTime, or \l String; otherwise returns an invalid date.
1916 If the type() is \l String, an invalid date will be returned if the
1917 string cannot be parsed as a Qt::ISODate format date.
1919 \sa canConvert(), convert()
1921 QDate QVariant::toDate() const
1923 return qVariantToHelper<QDate>(d, handlerManager);
1927 \fn QTime QVariant::toTime() const
1929 Returns the variant as a QTime if the variant has type() \l Time,
1930 \l DateTime, or \l String; otherwise returns an invalid time.
1932 If the type() is \l String, an invalid time will be returned if
1933 the string cannot be parsed as a Qt::ISODate format time.
1935 \sa canConvert(), convert()
1937 QTime QVariant::toTime() const
1939 return qVariantToHelper<QTime>(d, handlerManager);
1943 \fn QDateTime QVariant::toDateTime() const
1945 Returns the variant as a QDateTime if the variant has type() \l
1946 DateTime, \l Date, or \l String; otherwise returns an invalid
1949 If the type() is \l String, an invalid date/time will be returned
1950 if the string cannot be parsed as a Qt::ISODate format date/time.
1952 \sa canConvert(), convert()
1954 QDateTime QVariant::toDateTime() const
1956 return qVariantToHelper<QDateTime>(d, handlerManager);
1961 \fn QEasingCurve QVariant::toEasingCurve() const
1963 Returns the variant as a QEasingCurve if the variant has type() \l
1964 EasingCurve; otherwise returns a default easing curve.
1966 \sa canConvert(), convert()
1968 #ifndef QT_BOOTSTRAPPED
1969 QEasingCurve QVariant::toEasingCurve() const
1971 return qVariantToHelper<QEasingCurve>(d, handlerManager);
1976 \fn QByteArray QVariant::toByteArray() const
1978 Returns the variant as a QByteArray if the variant has type() \l
1979 ByteArray or \l String (converted using QString::fromAscii());
1980 otherwise returns an empty byte array.
1982 \sa canConvert(), convert()
1984 QByteArray QVariant::toByteArray() const
1986 return qVariantToHelper<QByteArray>(d, handlerManager);
1989 #ifndef QT_NO_GEOM_VARIANT
1991 \fn QPoint QVariant::toPoint() const
1993 Returns the variant as a QPoint if the variant has type()
1994 \l Point or \l PointF; otherwise returns a null QPoint.
1996 \sa canConvert(), convert()
1998 QPoint QVariant::toPoint() const
2000 return qVariantToHelper<QPoint>(d, handlerManager);
2004 \fn QRect QVariant::toRect() const
2006 Returns the variant as a QRect if the variant has type() \l Rect;
2007 otherwise returns an invalid QRect.
2009 \sa canConvert(), convert()
2011 QRect QVariant::toRect() const
2013 return qVariantToHelper<QRect>(d, handlerManager);
2017 \fn QSize QVariant::toSize() const
2019 Returns the variant as a QSize if the variant has type() \l Size;
2020 otherwise returns an invalid QSize.
2022 \sa canConvert(), convert()
2024 QSize QVariant::toSize() const
2026 return qVariantToHelper<QSize>(d, handlerManager);
2030 \fn QSizeF QVariant::toSizeF() const
2032 Returns the variant as a QSizeF if the variant has type() \l
2033 SizeF; otherwise returns an invalid QSizeF.
2035 \sa canConvert(), convert()
2037 QSizeF QVariant::toSizeF() const
2039 return qVariantToHelper<QSizeF>(d, handlerManager);
2043 \fn QRectF QVariant::toRectF() const
2045 Returns the variant as a QRectF if the variant has type() \l Rect
2046 or \l RectF; otherwise returns an invalid QRectF.
2048 \sa canConvert(), convert()
2050 QRectF QVariant::toRectF() const
2052 return qVariantToHelper<QRectF>(d, handlerManager);
2056 \fn QLineF QVariant::toLineF() const
2058 Returns the variant as a QLineF if the variant has type() \l
2059 LineF; otherwise returns an invalid QLineF.
2061 \sa canConvert(), convert()
2063 QLineF QVariant::toLineF() const
2065 return qVariantToHelper<QLineF>(d, handlerManager);
2069 \fn QLine QVariant::toLine() const
2071 Returns the variant as a QLine if the variant has type() \l Line;
2072 otherwise returns an invalid QLine.
2074 \sa canConvert(), convert()
2076 QLine QVariant::toLine() const
2078 return qVariantToHelper<QLine>(d, handlerManager);
2082 \fn QPointF QVariant::toPointF() const
2084 Returns the variant as a QPointF if the variant has type() \l
2085 Point or \l PointF; otherwise returns a null QPointF.
2087 \sa canConvert(), convert()
2089 QPointF QVariant::toPointF() const
2091 return qVariantToHelper<QPointF>(d, handlerManager);
2094 #endif // QT_NO_GEOM_VARIANT
2097 \fn QUrl QVariant::toUrl() const
2099 Returns the variant as a QUrl if the variant has type()
2100 \l Url; otherwise returns an invalid QUrl.
2102 \sa canConvert(), convert()
2104 QUrl QVariant::toUrl() const
2106 return qVariantToHelper<QUrl>(d, handlerManager);
2110 \fn QLocale QVariant::toLocale() const
2112 Returns the variant as a QLocale if the variant has type()
2113 \l Locale; otherwise returns an invalid QLocale.
2115 \sa canConvert(), convert()
2117 QLocale QVariant::toLocale() const
2119 return qVariantToHelper<QLocale>(d, handlerManager);
2123 \fn QRegExp QVariant::toRegExp() const
2126 Returns the variant as a QRegExp if the variant has type() \l
2127 RegExp; otherwise returns an empty QRegExp.
2129 \sa canConvert(), convert()
2131 #ifndef QT_NO_REGEXP
2132 QRegExp QVariant::toRegExp() const
2134 return qVariantToHelper<QRegExp>(d, handlerManager);
2139 \fn QChar QVariant::toChar() const
2141 Returns the variant as a QChar if the variant has type() \l Char,
2142 \l Int, or \l UInt; otherwise returns an invalid QChar.
2144 \sa canConvert(), convert()
2146 QChar QVariant::toChar() const
2148 return qVariantToHelper<QChar>(d, handlerManager);
2152 Returns the variant as a QBitArray if the variant has type()
2153 \l BitArray; otherwise returns an empty bit array.
2155 \sa canConvert(), convert()
2157 QBitArray QVariant::toBitArray() const
2159 return qVariantToHelper<QBitArray>(d, handlerManager);
2162 template <typename T>
2163 inline T qNumVariantToHelper(const QVariant::Private &d,
2164 const HandlersManager &handlerManager, bool *ok, const T& val)
2166 uint t = qMetaTypeId<T>();
2173 if (!handlerManager[d.type]->convert(&d, QVariant::Type(t), &ret, ok) && ok)
2179 Returns the variant as an int if the variant has type() \l Int,
2180 \l Bool, \l ByteArray, \l Char, \l Double, \l LongLong, \l
2181 String, \l UInt, or \l ULongLong; otherwise returns 0.
2183 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2184 converted to an int; otherwise \c{*}\a{ok} is set to false.
2186 \bold{Warning:} If the value is convertible to a \l LongLong but is too
2187 large to be represented in an int, the resulting arithmetic overflow will
2188 not be reflected in \a ok. A simple workaround is to use QString::toInt().
2189 Fixing this bug has been postponed to Qt 5 in order to avoid breaking existing code.
2191 \sa canConvert(), convert()
2193 int QVariant::toInt(bool *ok) const
2195 return qNumVariantToHelper<int>(d, handlerManager, ok, d.data.i);
2199 Returns the variant as an unsigned int if the variant has type()
2200 \l UInt, \l Bool, \l ByteArray, \l Char, \l Double, \l Int, \l
2201 LongLong, \l String, or \l ULongLong; otherwise returns 0.
2203 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2204 converted to an unsigned int; otherwise \c{*}\a{ok} is set to false.
2206 \bold{Warning:} If the value is convertible to a \l ULongLong but is too
2207 large to be represented in an unsigned int, the resulting arithmetic overflow will
2208 not be reflected in \a ok. A simple workaround is to use QString::toUInt().
2209 Fixing this bug has been postponed to Qt 5 in order to avoid breaking existing code.
2211 \sa canConvert(), convert()
2213 uint QVariant::toUInt(bool *ok) const
2215 return qNumVariantToHelper<uint>(d, handlerManager, ok, d.data.u);
2219 Returns the variant as a long long int if the variant has type()
2220 \l LongLong, \l Bool, \l ByteArray, \l Char, \l Double, \l Int,
2221 \l String, \l UInt, or \l ULongLong; otherwise returns 0.
2223 If \a ok is non-null: \c{*}\c{ok} is set to true if the value could be
2224 converted to an int; otherwise \c{*}\c{ok} is set to false.
2226 \sa canConvert(), convert()
2228 qlonglong QVariant::toLongLong(bool *ok) const
2230 return qNumVariantToHelper<qlonglong>(d, handlerManager, ok, d.data.ll);
2234 Returns the variant as as an unsigned long long int if the
2235 variant has type() \l ULongLong, \l Bool, \l ByteArray, \l Char,
2236 \l Double, \l Int, \l LongLong, \l String, or \l UInt; otherwise
2239 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2240 converted to an int; otherwise \c{*}\a{ok} is set to false.
2242 \sa canConvert(), convert()
2244 qulonglong QVariant::toULongLong(bool *ok) const
2246 return qNumVariantToHelper<qulonglong>(d, handlerManager, ok, d.data.ull);
2250 Returns the variant as a bool if the variant has type() Bool.
2252 Returns true if the variant has type() \l Bool, \l Char, \l Double,
2253 \l Int, \l LongLong, \l UInt, or \l ULongLong and the value is
2254 non-zero, or if the variant has type \l String or \l ByteArray and
2255 its lower-case content is not empty, "0" or "false"; otherwise
2258 \sa canConvert(), convert()
2260 bool QVariant::toBool() const
2266 handlerManager[d.type]->convert(&d, Bool, &res, 0);
2272 Returns the variant as a double if the variant has type() \l
2273 Double, \l QMetaType::Float, \l Bool, \l ByteArray, \l Int, \l LongLong, \l String, \l
2274 UInt, or \l ULongLong; otherwise returns 0.0.
2276 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2277 converted to a double; otherwise \c{*}\a{ok} is set to false.
2279 \sa canConvert(), convert()
2281 double QVariant::toDouble(bool *ok) const
2283 return qNumVariantToHelper<double>(d, handlerManager, ok, d.data.d);
2287 Returns the variant as a float if the variant has type() \l
2288 Double, \l QMetaType::Float, \l Bool, \l ByteArray, \l Int, \l LongLong, \l String, \l
2289 UInt, or \l ULongLong; otherwise returns 0.0.
2293 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2294 converted to a double; otherwise \c{*}\a{ok} is set to false.
2296 \sa canConvert(), convert()
2298 float QVariant::toFloat(bool *ok) const
2300 return qNumVariantToHelper<float>(d, handlerManager, ok, d.data.f);
2304 Returns the variant as a qreal if the variant has type() \l
2305 Double, \l QMetaType::Float, \l Bool, \l ByteArray, \l Int, \l LongLong, \l String, \l
2306 UInt, or \l ULongLong; otherwise returns 0.0.
2310 If \a ok is non-null: \c{*}\a{ok} is set to true if the value could be
2311 converted to a double; otherwise \c{*}\a{ok} is set to false.
2313 \sa canConvert(), convert()
2315 qreal QVariant::toReal(bool *ok) const
2317 return qNumVariantToHelper<qreal>(d, handlerManager, ok, d.data.real);
2321 Returns the variant as a QVariantList if the variant has type()
2322 \l List or \l StringList; otherwise returns an empty list.
2324 \sa canConvert(), convert()
2326 QVariantList QVariant::toList() const
2328 return qVariantToHelper<QVariantList>(d, handlerManager);
2332 static const quint32 qCanConvertMatrix[QVariant::LastCoreType + 1] =
2336 /*Bool*/ 1 << QVariant::Double | 1 << QVariant::Int | 1 << QVariant::UInt
2337 | 1 << QVariant::LongLong | 1 << QVariant::ULongLong | 1 << QVariant::ByteArray
2338 | 1 << QVariant::String | 1 << QVariant::Char,
2340 /*Int*/ 1 << QVariant::UInt | 1 << QVariant::String | 1 << QVariant::Double
2341 | 1 << QVariant::Bool | 1 << QVariant::LongLong | 1 << QVariant::ULongLong
2342 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2344 /*UInt*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::Double
2345 | 1 << QVariant::Bool | 1 << QVariant::LongLong | 1 << QVariant::ULongLong
2346 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2348 /*LLong*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::Double
2349 | 1 << QVariant::Bool | 1 << QVariant::UInt | 1 << QVariant::ULongLong
2350 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2352 /*ULlong*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::Double
2353 | 1 << QVariant::Bool | 1 << QVariant::UInt | 1 << QVariant::LongLong
2354 | 1 << QVariant::Char | 1 << QVariant::ByteArray,
2356 /*double*/ 1 << QVariant::Int | 1 << QVariant::String | 1 << QVariant::ULongLong
2357 | 1 << QVariant::Bool | 1 << QVariant::UInt | 1 << QVariant::LongLong
2358 | 1 << QVariant::ByteArray,
2360 /*QChar*/ 1 << QVariant::Int | 1 << QVariant::UInt | 1 << QVariant::LongLong
2361 | 1 << QVariant::ULongLong,
2365 /*QList*/ 1 << QVariant::StringList,
2367 /*QString*/ 1 << QVariant::StringList | 1 << QVariant::ByteArray | 1 << QVariant::Int
2368 | 1 << QVariant::UInt | 1 << QVariant::Bool | 1 << QVariant::Double
2369 | 1 << QVariant::Date | 1 << QVariant::Time | 1 << QVariant::DateTime
2370 | 1 << QVariant::LongLong | 1 << QVariant::ULongLong | 1 << QVariant::Char
2371 | 1 << QVariant::Url | 1 << QVariant::Uuid,
2373 /*QStringList*/ 1 << QVariant::List | 1 << QVariant::String,
2375 /*QByteArray*/ 1 << QVariant::String | 1 << QVariant::Int | 1 << QVariant::UInt | 1 << QVariant::Bool
2376 | 1 << QVariant::Double | 1 << QVariant::LongLong | 1 << QVariant::ULongLong,
2380 /*QDate*/ 1 << QVariant::String | 1 << QVariant::DateTime,
2382 /*QTime*/ 1 << QVariant::String | 1 << QVariant::DateTime,
2384 /*QDateTime*/ 1 << QVariant::String | 1 << QVariant::Date,
2386 /*QUrl*/ 1 << QVariant::String,
2390 /*QRect*/ 1 << QVariant::RectF,
2392 /*QRectF*/ 1 << QVariant::Rect,
2394 /*QSize*/ 1 << QVariant::SizeF,
2396 /*QSizeF*/ 1 << QVariant::Size,
2398 /*QLine*/ 1 << QVariant::LineF,
2400 /*QLineF*/ 1 << QVariant::Line,
2402 /*QPoint*/ 1 << QVariant::PointF,
2404 /*QPointF*/ 1 << QVariant::Point,
2412 /*QUuid*/ 1 << QVariant::String
2416 Returns true if the variant's type can be cast to the requested
2417 type, \a t. Such casting is done automatically when calling the
2418 toInt(), toBool(), ... methods.
2420 The following casts are done automatically:
2423 \header \o Type \o Automatically Cast To
2424 \row \o \l Bool \o \l Char, \l Double, \l Int, \l LongLong, \l String, \l UInt, \l ULongLong
2425 \row \o \l ByteArray \o \l Double, \l Int, \l LongLong, \l String, \l UInt, \l ULongLong
2426 \row \o \l Char \o \l Bool, \l Int, \l UInt, \l LongLong, \l ULongLong
2427 \row \o \l Color \o \l String
2428 \row \o \l Date \o \l DateTime, \l String
2429 \row \o \l DateTime \o \l Date, \l String, \l Time
2430 \row \o \l Double \o \l Bool, \l Int, \l LongLong, \l String, \l UInt, \l ULongLong
2431 \row \o \l Font \o \l String
2432 \row \o \l Int \o \l Bool, \l Char, \l Double, \l LongLong, \l String, \l UInt, \l ULongLong
2433 \row \o \l KeySequence \o \l Int, \l String
2434 \row \o \l List \o \l StringList (if the list's items can be converted to strings)
2435 \row \o \l LongLong \o \l Bool, \l ByteArray, \l Char, \l Double, \l Int, \l String, \l UInt, \l ULongLong
2436 \row \o \l Point \o PointF
2437 \row \o \l Rect \o RectF
2438 \row \o \l String \o \l Bool, \l ByteArray, \l Char, \l Color, \l Date, \l DateTime, \l Double,
2439 \l Font, \l Int, \l KeySequence, \l LongLong, \l StringList, \l Time, \l UInt,
2441 \row \o \l StringList \o \l List, \l String (if the list contains exactly one item)
2442 \row \o \l Time \o \l String
2443 \row \o \l UInt \o \l Bool, \l Char, \l Double, \l Int, \l LongLong, \l String, \l ULongLong
2444 \row \o \l ULongLong \o \l Bool, \l Char, \l Double, \l Int, \l LongLong, \l String, \l UInt
2449 bool QVariant::canConvert(Type t) const
2451 // TODO Reimplement this function, currently it works but it is a historical mess.
2452 const uint currentType = ((d.type == QMetaType::Float) ? QVariant::Double : d.type);
2453 if (uint(t) == uint(QMetaType::Float)) t = QVariant::Double;
2455 if (currentType == uint(t))
2458 // FIXME It should be LastCoreType intead of Uuid
2459 if (currentType > QVariant::Uuid || t > QVariant::Uuid) {
2462 return currentType == QVariant::KeySequence
2463 || currentType == QMetaType::ULong
2464 || currentType == QMetaType::Long
2465 || currentType == QMetaType::UShort
2466 || currentType == QMetaType::UChar
2467 || currentType == QMetaType::Char
2468 || currentType == QMetaType::Short;
2469 case QVariant::Image:
2470 return currentType == QVariant::Pixmap || currentType == QVariant::Bitmap;
2471 case QVariant::Pixmap:
2472 return currentType == QVariant::Image || currentType == QVariant::Bitmap
2473 || currentType == QVariant::Brush;
2474 case QVariant::Bitmap:
2475 return currentType == QVariant::Pixmap || currentType == QVariant::Image;
2476 case QVariant::ByteArray:
2477 return currentType == QVariant::Color;
2478 case QVariant::String:
2479 return currentType == QVariant::KeySequence || currentType == QVariant::Font
2480 || currentType == QVariant::Color;
2481 case QVariant::KeySequence:
2482 return currentType == QVariant::String || currentType == QVariant::Int;
2483 case QVariant::Font:
2484 return currentType == QVariant::String;
2485 case QVariant::Color:
2486 return currentType == QVariant::String || currentType == QVariant::ByteArray
2487 || currentType == QVariant::Brush;
2488 case QVariant::Brush:
2489 return currentType == QVariant::Color || currentType == QVariant::Pixmap;
2490 case QMetaType::Long:
2491 case QMetaType::Char:
2492 case QMetaType::UChar:
2493 case QMetaType::ULong:
2494 case QMetaType::Short:
2495 case QMetaType::UShort:
2496 return qCanConvertMatrix[QVariant::Int] & (1 << currentType) || currentType == QVariant::Int;
2502 if(t == String && currentType == StringList)
2503 return v_cast<QStringList>(&d)->count() == 1;
2505 return qCanConvertMatrix[t] & (1 << currentType);
2509 Casts the variant to the requested type, \a t. If the cast cannot be
2510 done, the variant is cleared. Returns true if the current type of
2511 the variant was successfully cast; otherwise returns false.
2513 \warning For historical reasons, converting a null QVariant results
2514 in a null value of the desired type (e.g., an empty string for
2515 QString) and a result of false.
2517 \sa canConvert(), clear()
2520 bool QVariant::convert(Type t)
2522 if (d.type == uint(t))
2525 QVariant oldValue = *this;
2528 if (!oldValue.canConvert(t))
2532 if (oldValue.isNull())
2536 if (!handlerManager[d.type]->convert(&oldValue.d, t, data(), &isOk))
2543 \fn convert(const int type, void *ptr) const
2545 Created for qvariant_cast() usage
2547 bool QVariant::convert(const int type, void *ptr) const
2549 Q_ASSERT(type < int(QMetaType::User));
2550 return handlerManager[type]->convert(&d, QVariant::Type(type), ptr, 0);
2555 \fn bool operator==(const QVariant &v1, const QVariant &v2)
2559 Returns true if \a v1 and \a v2 are equal; otherwise returns false.
2561 \warning This function doesn't support custom types registered
2562 with qRegisterMetaType().
2565 \fn bool operator!=(const QVariant &v1, const QVariant &v2)
2569 Returns false if \a v1 and \a v2 are equal; otherwise returns true.
2571 \warning This function doesn't support custom types registered
2572 with qRegisterMetaType().
2575 /*! \fn bool QVariant::operator==(const QVariant &v) const
2577 Compares this QVariant with \a v and returns true if they are
2578 equal; otherwise returns false.
2580 In the case of custom types, their equalness operators are not called.
2581 Instead the values' addresses are compared.
2585 \fn bool QVariant::operator!=(const QVariant &v) const
2587 Compares this QVariant with \a v and returns true if they are not
2588 equal; otherwise returns false.
2590 \warning This function doesn't support custom types registered
2591 with qRegisterMetaType().
2594 static bool qIsNumericType(uint tp)
2596 return (tp >= QVariant::Bool && tp <= QVariant::Double)
2597 || (tp >= QMetaType::Long && tp <= QMetaType::Float);
2600 static bool qIsFloatingPoint(uint tp)
2602 return tp == QVariant::Double || tp == QMetaType::Float;
2607 bool QVariant::cmp(const QVariant &v) const
2610 if (d.type != v2.d.type) {
2611 if (qIsNumericType(d.type) && qIsNumericType(v.d.type)) {
2612 if (qIsFloatingPoint(d.type) || qIsFloatingPoint(v.d.type))
2613 return qFuzzyCompare(toReal(), v.toReal());
2615 return toLongLong() == v.toLongLong();
2617 if (!v2.canConvert(Type(d.type)) || !v2.convert(Type(d.type)))
2620 return handlerManager[d.type]->compare(&d, &v2.d);
2626 const void *QVariant::constData() const
2628 return d.is_shared ? d.data.shared->ptr : reinterpret_cast<const void *>(&d.data.ptr);
2632 \fn const void* QVariant::data() const
2638 void* QVariant::data()
2641 return const_cast<void *>(constData());
2646 Returns true if this is a NULL variant, false otherwise.
2648 bool QVariant::isNull() const
2650 return handlerManager[d.type]->isNull(&d);
2653 #ifndef QT_NO_DEBUG_STREAM
2654 QDebug operator<<(QDebug dbg, const QVariant &v)
2656 #ifndef Q_BROKEN_DEBUG_STREAM
2657 dbg.nospace() << "QVariant(" << QMetaType::typeName(v.userType()) << ", ";
2658 handlerManager[v.d.type]->debugStream(dbg, v);
2659 dbg.nospace() << ')';
2662 qWarning("This compiler doesn't support streaming QVariant to QDebug");
2668 QDebug operator<<(QDebug dbg, const QVariant::Type p)
2670 #ifndef Q_BROKEN_DEBUG_STREAM
2671 dbg.nospace() << "QVariant::" << QMetaType::typeName(p);
2674 qWarning("This compiler doesn't support streaming QVariant::Type to QDebug");
2682 /*! \fn void QVariant::setValue(const T &value)
2684 Stores a copy of \a value. If \c{T} is a type that QVariant
2685 doesn't support, QMetaType is used to store the value. A compile
2686 error will occur if QMetaType doesn't handle the type.
2690 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 4
2692 \sa value(), fromValue(), canConvert()
2695 /*! \fn T QVariant::value() const
2697 Returns the stored value converted to the template type \c{T}.
2698 Call canConvert() to find out whether a type can be converted.
2699 If the value cannot be converted, \l{default-constructed value}
2702 If the type \c{T} is supported by QVariant, this function behaves
2703 exactly as toString(), toInt() etc.
2707 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 5
2709 \sa setValue(), fromValue(), canConvert()
2712 /*! \fn bool QVariant::canConvert() const
2714 Returns true if the variant can be converted to the template type \c{T},
2719 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 6
2724 /*! \fn static QVariant QVariant::fromValue(const T &value)
2726 Returns a QVariant containing a copy of \a value. Behaves
2727 exactly like setValue() otherwise.
2731 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 7
2733 \note If you are working with custom types, you should use
2734 the Q_DECLARE_METATYPE() macro to register your custom type.
2736 \sa setValue(), value()
2740 \fn QVariant qVariantFromValue(const T &value)
2744 Returns a variant containing a copy of the given \a value
2745 with template type \c{T}.
2747 This function is equivalent to QVariant::fromValue(\a value).
2749 \note This function was provided as a workaround for MSVC 6
2750 which did not support member template functions. It is advised
2751 to use the other form in new code.
2753 For example, a QObject pointer can be stored in a variant with the
2756 \snippet doc/src/snippets/code/src_corelib_kernel_qvariant.cpp 8
2758 \sa QVariant::fromValue()
2761 /*! \fn void qVariantSetValue(QVariant &variant, const T &value)
2765 Sets the contents of the given \a variant to a copy of the
2766 \a value with the specified template type \c{T}.
2768 This function is equivalent to QVariant::setValue(\a value).
2770 \note This function was provided as a workaround for MSVC 6
2771 which did not support member template functions. It is advised
2772 to use the other form in new code.
2774 \sa QVariant::setValue()
2778 \fn T qvariant_cast(const QVariant &value)
2781 Returns the given \a value converted to the template type \c{T}.
2783 This function is equivalent to QVariant::value().
2785 \sa QVariant::value()
2788 /*! \fn T qVariantValue(const QVariant &value)
2792 Returns the given \a value converted to the template type \c{T}.
2794 This function is equivalent to
2795 \l{QVariant::value()}{QVariant::value}<T>(\a value).
2797 \note This function was provided as a workaround for MSVC 6
2798 which did not support member template functions. It is advised
2799 to use the other form in new code.
2801 \sa QVariant::value(), qvariant_cast()
2804 /*! \fn bool qVariantCanConvert(const QVariant &value)
2808 Returns true if the given \a value can be converted to the
2809 template type specified; otherwise returns false.
2811 This function is equivalent to QVariant::canConvert(\a value).
2813 \note This function was provided as a workaround for MSVC 6
2814 which did not support member template functions. It is advised
2815 to use the other form in new code.
2817 \sa QVariant::canConvert()
2821 \typedef QVariantList
2824 Synonym for QList<QVariant>.
2828 \typedef QVariantMap
2831 Synonym for QMap<QString, QVariant>.
2835 \typedef QVariantHash
2839 Synonym for QHash<QString, QVariant>.
2843 \typedef QVariant::DataPtr
2848 \fn DataPtr &QVariant::data_ptr()