aboutsummaryrefslogtreecommitdiffstats
path: root/src/qml/qml/qqmlmetatype.cpp
diff options
context:
space:
mode:
authorUlf Hermann <ulf.hermann@qt.io>2022-01-07 11:01:56 +0100
committerUlf Hermann <ulf.hermann@qt.io>2022-01-28 15:03:00 +0100
commitb0fc028cb5a5dfa9e95640a32e9b38ca6df0734d (patch)
tree7a446acca0f5bcbe4e62a1ac22bdb0185913bc5a /src/qml/qml/qqmlmetatype.cpp
parent8c4c0605b077d63e3d73d34ad6dcc4a2cf607b4c (diff)
QML: Allow named lists of value types
We register QList<T> as sequential container type for any value type T we get. This way we can always find a type to use for list<t> with t being a value type. The metatypes are shuffled around so that we have an easier time associating a type with its list and vice versa. As QQmlPropertyData's isQList flag denotes both QQmlListProperty<T> and QList<T> now, we need to use QMetaType::IsQmlList more often. Conversely, any name given to extra sequential containers registered via QML_SEQUENTIAL_CONTAINER is explicitly ignored now. As you can do list<foo> for any type foo now, there is not much of a point in having further named container registrations for the same type. It would just make things more complicated. Mind that the name had already been ignored before, just not explicitly. [ChangeLog][QtQml] You can now use lists of value types in QML. For example a property of type list<int> will hold a list of integers. Task-number: QTBUG-82443 Change-Id: I7bee61cee3963dae5d231bf59f70b8012984371d Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Diffstat (limited to 'src/qml/qml/qqmlmetatype.cpp')
-rw-r--r--src/qml/qml/qqmlmetatype.cpp45
1 files changed, 29 insertions, 16 deletions
diff --git a/src/qml/qml/qqmlmetatype.cpp b/src/qml/qml/qqmlmetatype.cpp
index f8cf142f5e..fb0e2af578 100644
--- a/src/qml/qml/qqmlmetatype.cpp
+++ b/src/qml/qml/qqmlmetatype.cpp
@@ -475,12 +475,15 @@ static void addTypeToData(QQmlTypePrivate *type, QQmlMetaTypeData *data)
if (type->baseMetaObject)
data->metaObjectToType.insert(type->baseMetaObject, type);
- if (type->typeId.isValid()) {
- data->idToType.insert(type->typeId.id(), type);
- }
+ if (type->regType == QQmlType::SequentialContainerType) {
+ if (type->listId.isValid())
+ data->idToType.insert(type->listId.id(), type);
+ } else {
+ if (type->typeId.isValid())
+ data->idToType.insert(type->typeId.id(), type);
- if (type->listId.isValid()) {
- data->idToType.insert(type->listId.id(), type);
+ if (type->listId.flags().testFlag(QMetaType::IsQmlList))
+ data->idToType.insert(type->listId.id(), type);
}
if (!type->module.isEmpty()) {
@@ -637,8 +640,7 @@ QQmlType QQmlMetaType::registerSequentialContainer(
QQmlMetaTypeDataPtr data;
- const QString typeName = QString::fromUtf8(container.typeName);
- if (!checkRegistration(QQmlType::SequentialContainerType, data, container.uri, typeName,
+ if (!checkRegistration(QQmlType::SequentialContainerType, data, container.uri, QString(),
container.version, {})) {
return QQmlType();
}
@@ -646,10 +648,11 @@ QQmlType QQmlMetaType::registerSequentialContainer(
QQmlTypePrivate *priv = new QQmlTypePrivate(QQmlType::SequentialContainerType);
data->registerType(priv);
- priv->setName(QString::fromUtf8(container.uri), typeName);
+ priv->setName(QString::fromUtf8(container.uri), QString());
priv->version = container.version;
priv->revision = container.revision;
- priv->typeId = container.typeId;
+ priv->typeId = container.metaSequence.valueMetaType();
+ priv->listId = container.typeId;
*priv->extraData.ld = container.metaSequence;
addTypeToData(priv, data);
@@ -1067,13 +1070,16 @@ QObject *QQmlMetaType::toQObject(const QVariant &v, bool *ok)
/*
Returns the item type for a list of type \a id.
*/
-QMetaType QQmlMetaType::listType(QMetaType metaType)
-{
- if (!isList(metaType))
- return QMetaType {};
- const auto iface = metaType.iface();
- if (iface->metaObjectFn == &dynamicQmlListMarker)
- return QMetaType(static_cast<const QQmlListMetaTypeInterface *>(iface)->valueType);
+QMetaType QQmlMetaType::listValueType(QMetaType metaType)
+{
+ if (isList(metaType)) {
+ const auto iface = metaType.iface();
+ if (iface->metaObjectFn == &dynamicQmlListMarker)
+ return QMetaType(static_cast<const QQmlListMetaTypeInterface *>(iface)->valueType);
+ } else if (metaType.flags() & QMetaType::PointerToQObject) {
+ return QMetaType();
+ }
+
QQmlMetaTypeDataPtr data;
QQmlTypePrivate *type = data->idToType.value(metaType.id());
if (type && type->listId == metaType)
@@ -1258,6 +1264,13 @@ QQmlType QQmlMetaType::qmlType(QMetaType metaType)
return (type && type->typeId == metaType) ? QQmlType(type) : QQmlType();
}
+QQmlType QQmlMetaType::qmlListType(QMetaType metaType)
+{
+ const QQmlMetaTypeDataPtr data;
+ QQmlTypePrivate *type = data->idToType.value(metaType.id());
+ return (type && type->listId == metaType) ? QQmlType(type) : QQmlType();
+}
+
/*!
Returns the type (if any) that corresponds to the given \a url in the set of
composite types added through file imports.