QMetaTypeId2::IsBuiltIn: (new) template meta-function to check for built-in types

This allows to check whether QMetaTypeId2::MetaType exists, and can help
turn run-time into compile-time expressions, even without constexpr support,
or in situations where constexpr can't be used (because you can't overload
on it). This was designed for the QMetaType::registerConversion feature,
but it's much more widely applicable.

Change-Id: Iafa04add04bcb531b3f7fe3e751c7e91ee6a3bc0
Reviewed-by: Olivier Goffart <ogoffart@woboq.com>
Reviewed-by: Stephen Kelly <stephen.kelly@kdab.com>
Reviewed-by: Jędrzej Nowacki <jedrzej.nowacki@nokia.com>
This commit is contained in:
Marc Mutz 2012-07-20 15:46:40 +02:00 committed by Qt by Nokia
parent f694b9c83f
commit e083d25395
4 changed files with 41 additions and 2 deletions

View File

@ -539,7 +539,7 @@ struct QMetaTypeId : public QMetaTypeIdQObject<T>
template <typename T>
struct QMetaTypeId2
{
enum { Defined = QMetaTypeId<T>::Defined };
enum { Defined = QMetaTypeId<T>::Defined, IsBuiltIn=false };
static inline Q_DECL_CONSTEXPR int qt_metatype_id() { return QMetaTypeId<T>::qt_metatype_id(); }
};
@ -717,7 +717,7 @@ inline int qRegisterMetaTypeStreamOperators()
QT_BEGIN_NAMESPACE \
template<> struct QMetaTypeId2<NAME> \
{ \
enum { Defined = 1, MetaType = METATYPEID }; \
enum { Defined = 1, IsBuiltIn = true, MetaType = METATYPEID }; \
static inline Q_DECL_CONSTEXPR int qt_metatype_id() { return METATYPEID; } \
}; \
QT_END_NAMESPACE

View File

@ -383,6 +383,25 @@ void tst_QMetaType::typeName()
FOR_EACH_PRIMITIVE_METATYPE(F) \
FOR_EACH_COMPLEX_CORE_METATYPE(F) \
namespace {
template <typename T>
struct static_assert_trigger {
Q_STATIC_ASSERT(( QMetaTypeId2<T>::IsBuiltIn ));
enum { value = true };
};
}
#define CHECK_BUILTIN(MetaTypeName, MetaTypeId, RealType) static_assert_trigger< RealType >::value &&
Q_STATIC_ASSERT(( FOR_EACH_CORE_METATYPE(CHECK_BUILTIN) true ));
#undef CHECK_BUILTIN
Q_STATIC_ASSERT(( QMetaTypeId2<QList<QVariant> >::IsBuiltIn));
Q_STATIC_ASSERT(( QMetaTypeId2<QMap<QString,QVariant> >::IsBuiltIn));
Q_STATIC_ASSERT(( QMetaTypeId2<QObject*>::IsBuiltIn));
Q_STATIC_ASSERT((!QMetaTypeId2<tst_QMetaType*>::IsBuiltIn)); // QObject subclass
Q_STATIC_ASSERT((!QMetaTypeId2<QList<int> >::IsBuiltIn));
Q_STATIC_ASSERT((!QMetaTypeId2<QMap<int,int> >::IsBuiltIn));
Q_STATIC_ASSERT((!QMetaTypeId2<QMetaType::Type>::IsBuiltIn));
template <int ID>
struct MetaEnumToType {};

View File

@ -87,6 +87,20 @@ private slots:
F(QVector4D, QVector4D) \
F(QQuaternion, QQuaternion)
namespace {
template <typename T>
struct static_assert_trigger {
Q_STATIC_ASSERT(( QMetaTypeId2<T>::IsBuiltIn ));
enum { value = true };
};
}
#define CHECK_BUILTIN(TYPE, ID) static_assert_trigger< TYPE >::value &&
Q_STATIC_ASSERT(( FOR_EACH_GUI_METATYPE(CHECK_BUILTIN) true ));
#undef CHECK_BUILTIN
Q_STATIC_ASSERT((!QMetaTypeId2<QList<QPen> >::IsBuiltIn));
Q_STATIC_ASSERT((!QMetaTypeId2<QMap<QString,QPen> >::IsBuiltIn));
template <int ID>
struct MetaEnumToType {};

View File

@ -67,6 +67,12 @@ public:
}
};
Q_STATIC_ASSERT(( QMetaTypeId2<QSizePolicy>::IsBuiltIn));
Q_STATIC_ASSERT(( QMetaTypeId2<QWidget*>::IsBuiltIn));
Q_STATIC_ASSERT((!QMetaTypeId2<QList<QSizePolicy> >::IsBuiltIn));
Q_STATIC_ASSERT((!QMetaTypeId2<QMap<QString,QSizePolicy> >::IsBuiltIn));
void tst_QWidgetMetaType::metaObject()
{
QCOMPARE(QMetaType::metaObjectForType(QMetaType::QWidgetStar), &QWidget::staticMetaObject);