aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/qml/qml/qqml.cpp80
-rw-r--r--src/qml/qml/qqml.h21
-rw-r--r--src/qml/qml/qqmlengine.cpp105
-rw-r--r--src/qml/qml/qqmlengine_p.h4
-rw-r--r--src/qml/qml/qqmlimport.cpp8
-rw-r--r--src/qml/qml/qqmlmetatype.cpp25
-rw-r--r--src/qml/qml/qqmlmetatype_p.h7
-rw-r--r--src/qml/qml/qqmlmetatypedata.cpp22
-rw-r--r--src/qml/qml/qqmlmetatypedata_p.h4
-rw-r--r--src/qml/qml/qqmlmoduleregistration.cpp21
-rw-r--r--src/qml/qml/qqmlmoduleregistration.h7
-rw-r--r--src/qml/qml/qqmlpropertycachecreator.cpp11
-rw-r--r--src/qml/qml/qqmlpropertyvalidator.cpp5
-rw-r--r--src/qml/qml/qqmltypecompiler.cpp8
-rw-r--r--src/qml/qml/qqmltypeloader.cpp2
-rw-r--r--src/qmltyperegistrar/qmltyperegistrar.cpp4
-rw-r--r--src/qmltyperegistrar/qmltypesclassdescription.cpp20
-rw-r--r--src/qmltyperegistrar/qmltypesclassdescription.h2
-rw-r--r--src/qmltyperegistrar/qmltypescreator.cpp18
-rw-r--r--tests/auto/qml/qmlplugindump/data/dumper/Versions/plugins.qmltypes6
-rw-r--r--tests/auto/qml/qqmlpropertycache/tst_qqmlpropertycache.cpp2
21 files changed, 232 insertions, 150 deletions
diff --git a/src/qml/qml/qqml.cpp b/src/qml/qml/qqml.cpp
index 3f327e4821..c732818bd9 100644
--- a/src/qml/qml/qqml.cpp
+++ b/src/qml/qml/qqml.cpp
@@ -144,6 +144,54 @@ static QVector<QTypeRevision> availableRevisions(const QMetaObject *metaObject)
return revisions;
}
+template<typename Registration>
+void assignVersions(Registration *registration, QTypeRevision revision,
+ QTypeRevision defaultVersion)
+{
+ const quint8 majorVersion = revision.hasMajorVersion() ? revision.majorVersion()
+ : defaultVersion.majorVersion();
+ registration->version = revision.hasMinorVersion()
+ ? QTypeRevision::fromVersion(majorVersion, revision.minorVersion())
+ : QTypeRevision::fromMajorVersion(majorVersion);
+ registration->revision = revision;
+}
+
+static QVector<QTypeRevision> prepareRevisions(const QMetaObject *metaObject, QTypeRevision added)
+{
+ auto revisions = availableRevisions(metaObject);
+ revisions.append(added);
+ return revisions;
+}
+
+static void uniqueRevisions(QVector<QTypeRevision> *revisions, QTypeRevision defaultVersion,
+ QTypeRevision added)
+{
+ bool revisionsHaveMajorVersions = false;
+ for (QTypeRevision revision : QVector<QTypeRevision>(*revisions)) { // yes, copy
+ // allow any minor version for each explicitly specified past major one
+ if (revision.hasMajorVersion()) {
+ revisionsHaveMajorVersions = true;
+ if (revision.majorVersion() < defaultVersion.majorVersion())
+ revisions->append(QTypeRevision::fromVersion(revision.majorVersion(), 254));
+ }
+ }
+
+ if (revisionsHaveMajorVersions) {
+ if (!added.hasMajorVersion()) {
+ // If added in unspecified major version, assume default one.
+ revisions->append(QTypeRevision::fromVersion(defaultVersion.majorVersion(),
+ added.minorVersion()));
+ } else if (added.majorVersion() < defaultVersion.majorVersion()) {
+ // If added in past major version, add .0 of default version.
+ revisions->append(QTypeRevision::fromVersion(defaultVersion.majorVersion(), 0));
+ }
+ }
+
+ std::sort(revisions->begin(), revisions->end());
+ const auto it = std::unique(revisions->begin(), revisions->end());
+ revisions->erase(it, revisions->end());
+}
+
/*
This method is "over generalized" to allow us to (potentially) register more types of things in
the future without adding exported symbols.
@@ -191,18 +239,14 @@ int QQmlPrivate::qmlregister(RegistrationType type, void *data)
const QTypeRevision added = revisionClassInfo(
type.classInfoMetaObject, "QML.AddedInVersion",
- QTypeRevision::zero());
+ QTypeRevision::fromMinorVersion(0));
const QTypeRevision removed = revisionClassInfo(
type.classInfoMetaObject, "QML.RemovedInVersion");
- auto revisions = availableRevisions(type.metaObject);
- revisions.append(qMax(added, QTypeRevision::zero()));
+ auto revisions = prepareRevisions(type.metaObject, added);
if (type.attachedPropertiesMetaObject)
revisions += availableRevisions(type.attachedPropertiesMetaObject);
-
- std::sort(revisions.begin(), revisions.end());
- const auto it = std::unique(revisions.begin(), revisions.end());
- revisions.erase(it, revisions.end());
+ uniqueRevisions(&revisions, type.version, added);
for (QTypeRevision revision : revisions) {
if (revision < added)
@@ -217,12 +261,8 @@ int QQmlPrivate::qmlregister(RegistrationType type, void *data)
revisionRegistration.create = creatable ? type.create : nullptr;
}
- // Equivalent of qmlRegisterRevision<T, revision>(...)
- revisionRegistration.version = QTypeRevision::fromVersion(type.version.majorVersion(),
- revision.minorVersion());
- revisionRegistration.revision = revision;
+ assignVersions(&revisionRegistration, revision, type.version);
revisionRegistration.customParser = type.customParserFactory();
-
qmlregister(TypeRegistration, &revisionRegistration);
}
break;
@@ -248,16 +288,12 @@ int QQmlPrivate::qmlregister(RegistrationType type, void *data)
const QTypeRevision added = revisionClassInfo(
type.classInfoMetaObject, "QML.AddedInVersion",
- QTypeRevision::zero());
+ QTypeRevision::fromMinorVersion(0));
const QTypeRevision removed = revisionClassInfo(
type.classInfoMetaObject, "QML.RemovedInVersion");
- auto revisions = availableRevisions(type.instanceMetaObject);
- revisions.append(qMax(added, QTypeRevision::zero()));
-
- std::sort(revisions.begin(), revisions.end());
- const auto it = std::unique(revisions.begin(), revisions.end());
- revisions.erase(it, revisions.end());
+ auto revisions = prepareRevisions(type.instanceMetaObject, added);
+ uniqueRevisions(&revisions, type.version, added);
for (QTypeRevision revision : qAsConst(revisions)) {
if (revision < added)
@@ -274,11 +310,7 @@ int QQmlPrivate::qmlregister(RegistrationType type, void *data)
revisionRegistration.generalizedQobjectApi = type.generalizedQobjectApi;
}
- // Equivalent of qmlRegisterRevision<T, revision>(...)
- revisionRegistration.version = QTypeRevision::fromVersion(type.version.majorVersion(),
- revision.minorVersion());
- revisionRegistration.revision = revision;
-
+ assignVersions(&revisionRegistration, revision, type.version);
qmlregister(SingletonRegistration, &revisionRegistration);
}
break;
diff --git a/src/qml/qml/qqml.h b/src/qml/qml/qqml.h
index 2711d184aa..096bef7e4b 100644
--- a/src/qml/qml/qqml.h
+++ b/src/qml/qml/qqml.h
@@ -44,6 +44,7 @@
#include <QtCore/qbytearray.h>
#include <QtCore/qmetaobject.h>
+#include <QtCore/qversionnumber.h>
#define QML_VERSION 0x020000
#define QML_VERSION_STR "2.0"
@@ -88,10 +89,16 @@
friend void QML_REGISTER_TYPES_AND_REVISIONS(const char *uri, int versionMajor);
#define QML_ADDED_IN_MINOR_VERSION(VERSION) \
- Q_CLASSINFO("QML.AddedInMinorVersion", #VERSION)
+ Q_CLASSINFO("QML.AddedInVersion", Q_REVISION(VERSION))
+
+#define QML_ADDED_IN_VERSION(MAJOR, MINOR) \
+ Q_CLASSINFO("QML.AddedInVersion", Q_REVISION(MAJOR, MINOR))
#define QML_REMOVED_IN_MINOR_VERSION(VERSION) \
- Q_CLASSINFO("QML.RemovedInMinorVersion", #VERSION)
+ Q_CLASSINFO("QML.RemovedInVersion", Q_REVISION(VERSION))
+
+#define QML_REMOVED_IN_VERSION(MAJOR, MINOR) \
+ Q_CLASSINFO("QML.RemovedInVersion", Q_REVISION(MAJOR, MINOR))
#define QML_ATTACHED(ATTACHED_TYPE) \
Q_CLASSINFO("QML.Attached", #ATTACHED_TYPE) \
@@ -236,7 +243,7 @@ int qmlRegisterUncreatableType(const char *uri, int versionMajor, int versionMin
nullptr, nullptr,
nullptr,
- QTypeRevision::fromEncodedVersion(metaObjectRevision)
+ QTypeRevision::fromMinorVersion(metaObjectRevision)
};
return QQmlPrivate::qmlregister(QQmlPrivate::TypeRegistration, &type);
@@ -314,7 +321,7 @@ int qmlRegisterExtendedUncreatableType(const char *uri, int versionMajor, int ve
QQmlPrivate::createParent<E>, &E::staticMetaObject,
nullptr,
- QTypeRevision::fromEncodedVersion(metaObjectRevision)
+ QTypeRevision::fromMinorVersion(metaObjectRevision)
};
return QQmlPrivate::qmlregister(QQmlPrivate::TypeRegistration, &type);
@@ -378,7 +385,7 @@ int qmlRegisterType(const char *uri, int versionMajor, int versionMinor, const c
nullptr, nullptr,
nullptr,
- QTypeRevision::fromEncodedVersion(metaObjectRevision)
+ QTypeRevision::fromMinorVersion(metaObjectRevision)
};
return QQmlPrivate::qmlregister(QQmlPrivate::TypeRegistration, &type);
@@ -409,7 +416,7 @@ int qmlRegisterRevision(const char *uri, int versionMajor, int versionMinor)
nullptr, nullptr,
nullptr,
- QTypeRevision::fromEncodedVersion(metaObjectRevision)
+ QTypeRevision::fromMinorVersion(metaObjectRevision)
};
return QQmlPrivate::qmlregister(QQmlPrivate::TypeRegistration, &type);
@@ -565,7 +572,7 @@ int qmlRegisterCustomType(const char *uri, int versionMajor, int versionMinor,
nullptr, nullptr,
parser,
- QTypeRevision::fromEncodedVersion(metaObjectRevision)
+ QTypeRevision::fromMinorVersion(metaObjectRevision)
};
return QQmlPrivate::qmlregister(QQmlPrivate::TypeRegistration, &type);
diff --git a/src/qml/qml/qqmlengine.cpp b/src/qml/qml/qqmlengine.cpp
index c67e091518..7f30c4d713 100644
--- a/src/qml/qml/qqmlengine.cpp
+++ b/src/qml/qml/qqmlengine.cpp
@@ -2354,58 +2354,91 @@ static QQmlPropertyCache *propertyCacheForPotentialInlineComponentType(int t, co
return (*iter)->rootPropertyCache().data();
}
+/*!
+ * \internal
+ *
+ * Look up by type's baseMetaObject.
+ */
QQmlMetaObject QQmlEnginePrivate::rawMetaObjectForType(int t) const
{
- Locker locker(this);
- auto iter = m_compositeTypes.constFind(t);
- if (iter != m_compositeTypes.cend()) {
- return propertyCacheForPotentialInlineComponentType(t, iter);
- } else {
- QQmlType type = QQmlMetaType::qmlType(t);
- return QQmlMetaObject(type.baseMetaObject());
- }
+ if (QQmlPropertyCache *composite = findPropertyCacheInCompositeTypes(t))
+ return QQmlMetaObject(composite);
+
+ QQmlType type = QQmlMetaType::qmlType(t);
+ return QQmlMetaObject(type.baseMetaObject());
}
+/*!
+ * \internal
+ *
+ * Look up by type's metaObject.
+ */
QQmlMetaObject QQmlEnginePrivate::metaObjectForType(int t) const
{
- Locker locker(this);
- auto iter = m_compositeTypes.constFind(t);
- if (iter != m_compositeTypes.cend()) {
- return propertyCacheForPotentialInlineComponentType(t, iter);
- } else {
- QQmlType type = QQmlMetaType::qmlType(t);
- return QQmlMetaObject(type.metaObject());
- }
+ if (QQmlPropertyCache *composite = findPropertyCacheInCompositeTypes(t))
+ return QQmlMetaObject(composite);
+
+ QQmlType type = QQmlMetaType::qmlType(t);
+ return QQmlMetaObject(type.metaObject());
}
+/*!
+ * \internal
+ *
+ * Look up by type's metaObject and version.
+ */
QQmlPropertyCache *QQmlEnginePrivate::propertyCacheForType(int t)
{
- Locker locker(this);
- auto iter = m_compositeTypes.constFind(t);
- if (iter != m_compositeTypes.cend()) {
- return propertyCacheForPotentialInlineComponentType(t, iter);
- } else {
- QQmlType type = QQmlMetaType::qmlType(t);
- locker.unlock();
- return type.isValid() ? cache(type.metaObject()) : nullptr;
- }
+ if (QQmlPropertyCache *composite = findPropertyCacheInCompositeTypes(t))
+ return composite;
+
+ QQmlType type = QQmlMetaType::qmlType(t);
+ return type.isValid() ? cache(type.metaObject(), type.version()) : nullptr;
+}
+
+/*!
+ * \internal
+ *
+ * Look up by type's baseMetaObject and unspecified/any version.
+ * TODO: Is this correct? Passing a plain QTypeRevision() rather than QTypeRevision::zero() or
+ * the actual type's version seems strange. The behavior has been in place for a while.
+ */
+QQmlPropertyCache *QQmlEnginePrivate::rawPropertyCacheForType(int t)
+{
+ if (QQmlPropertyCache *composite = findPropertyCacheInCompositeTypes(t))
+ return composite;
+
+ QQmlType type = QQmlMetaType::qmlType(t);
+ return type.isValid() ? cache(type.baseMetaObject(), QTypeRevision()) : nullptr;
}
+/*!
+ * \internal
+ *
+ * Look up by QQmlType and version. We only fall back to lookup by metaobject if the type
+ * has no revisiononed attributes here. Unspecified versions are interpreted as "any".
+ */
QQmlPropertyCache *QQmlEnginePrivate::rawPropertyCacheForType(int t, QTypeRevision version)
{
+ if (QQmlPropertyCache *composite = findPropertyCacheInCompositeTypes(t))
+ return composite;
+
+ QQmlType type = QQmlMetaType::qmlType(t);
+ if (!type.isValid())
+ return nullptr;
+
+ return type.containsRevisionedAttributes()
+ ? QQmlMetaType::propertyCache(type, version)
+ : cache(type.metaObject(), version);
+}
+
+QQmlPropertyCache *QQmlEnginePrivate::findPropertyCacheInCompositeTypes(int t) const
+{
Locker locker(this);
auto iter = m_compositeTypes.constFind(t);
- if (iter != m_compositeTypes.cend()) {
- return propertyCacheForPotentialInlineComponentType(t, iter);
- } else {
- QQmlType type = QQmlMetaType::qmlType(t);
- locker.unlock();
-
- if (version.hasMinorVersion())
- return type.isValid() ? cache(type, version) : nullptr;
- else
- return type.isValid() ? cache(type.baseMetaObject()) : nullptr;
- }
+ return (iter == m_compositeTypes.constEnd())
+ ? nullptr
+ : propertyCacheForPotentialInlineComponentType(t, iter);
}
void QQmlEnginePrivate::registerInternalCompositeType(QV4::ExecutableCompilationUnit *compilationUnit)
diff --git a/src/qml/qml/qqmlengine_p.h b/src/qml/qml/qqmlengine_p.h
index 23c8d9e07a..2c702367a4 100644
--- a/src/qml/qml/qqmlengine_p.h
+++ b/src/qml/qml/qqmlengine_p.h
@@ -228,7 +228,8 @@ public:
QQmlMetaObject rawMetaObjectForType(int) const;
QQmlMetaObject metaObjectForType(int) const;
QQmlPropertyCache *propertyCacheForType(int);
- QQmlPropertyCache *rawPropertyCacheForType(int, QTypeRevision version = QTypeRevision());
+ QQmlPropertyCache *rawPropertyCacheForType(int);
+ QQmlPropertyCache *rawPropertyCacheForType(int, QTypeRevision version);
void registerInternalCompositeType(QV4::ExecutableCompilationUnit *compilationUnit);
void unregisterInternalCompositeType(QV4::ExecutableCompilationUnit *compilationUnit);
QV4::ExecutableCompilationUnit *obtainExecutableCompilationUnit(int typeId);
@@ -282,6 +283,7 @@ private:
void doDeleteInEngineThread();
void cleanupScarceResources();
+ QQmlPropertyCache *findPropertyCacheInCompositeTypes(int t) const;
};
/*
diff --git a/src/qml/qml/qqmlimport.cpp b/src/qml/qml/qqmlimport.cpp
index c053b14237..5ee27d4457 100644
--- a/src/qml/qml/qqmlimport.cpp
+++ b/src/qml/qml/qqmlimport.cpp
@@ -1174,13 +1174,7 @@ bool QQmlImportsPrivate::importExtension(const QString &qmldirFilePath,
if (qmldirPluginCount == 0)
return true;
- if (database->qmlDirFilesForWhichPluginsHaveBeenLoaded.contains(qmldirFilePath)) {
- if ((version.hasMajorVersion() && version.hasMinorVersion())
- ? !QQmlMetaType::isModule(uri, version)
- : !QQmlMetaType::isAnyModule(uri)) {
- QQmlMetaType::qmlRegisterModuleTypes(uri, version);
- }
- } else {
+ if (!database->qmlDirFilesForWhichPluginsHaveBeenLoaded.contains(qmldirFilePath)) {
// First search for listed qmldir plugins dynamically. If we cannot resolve them all, we continue
// searching static plugins that has correct metadata uri. Note that since we only know the uri
// for a static plugin, and not the filename, we cannot know which static plugin belongs to which
diff --git a/src/qml/qml/qqmlmetatype.cpp b/src/qml/qml/qqmlmetatype.cpp
index 429f9c5b09..c5c767df43 100644
--- a/src/qml/qml/qqmlmetatype.cpp
+++ b/src/qml/qml/qqmlmetatype.cpp
@@ -265,35 +265,32 @@ void QQmlMetaType::clone(QMetaObjectBuilder &builder, const QMetaObject *mo,
}
}
-void QQmlMetaType::qmlInsertModuleRegistration(const QString &uri, QTypeRevision version,
- void (*registerFunction)())
+void QQmlMetaType::qmlInsertModuleRegistration(const QString &uri, void (*registerFunction)())
{
- const QQmlMetaTypeData::VersionedUri versionedUri(uri, version);
QQmlMetaTypeDataPtr data;
- if (data->moduleTypeRegistrationFunctions.contains(versionedUri))
- qFatal("Cannot add multiple registrations for %s %d", qPrintable(uri), version.majorVersion());
+ if (data->moduleTypeRegistrationFunctions.contains(uri))
+ qFatal("Cannot add multiple registrations for %s", qPrintable(uri));
else
- data->moduleTypeRegistrationFunctions.insert(versionedUri, registerFunction);
+ data->moduleTypeRegistrationFunctions.insert(uri, registerFunction);
}
-void QQmlMetaType::qmlRemoveModuleRegistration(const QString &uri, QTypeRevision version)
+void QQmlMetaType::qmlRemoveModuleRegistration(const QString &uri)
{
- const QQmlMetaTypeData::VersionedUri versionedUri(uri, version);
QQmlMetaTypeDataPtr data;
if (!data.isValid())
return; // shutdown/deletion race. Not a problem.
- if (!data->moduleTypeRegistrationFunctions.contains(versionedUri))
- qFatal("Cannot remove multiple registrations for %s %d", qPrintable(uri), version.majorVersion());
+ if (!data->moduleTypeRegistrationFunctions.contains(uri))
+ qFatal("Cannot remove multiple registrations for %s", qPrintable(uri));
else
- data->moduleTypeRegistrationFunctions.remove(versionedUri);
+ data->moduleTypeRegistrationFunctions.remove(uri);
}
-bool QQmlMetaType::qmlRegisterModuleTypes(const QString &uri, QTypeRevision version)
+bool QQmlMetaType::qmlRegisterModuleTypes(const QString &uri)
{
QQmlMetaTypeDataPtr data;
- return data->registerModuleTypes(QQmlMetaTypeData::VersionedUri(uri, version));
+ return data->registerModuleTypes(uri);
}
void QQmlMetaType::clearTypeRegistrations()
@@ -713,7 +710,7 @@ bool QQmlMetaType::registerPluginTypes(QObject *instance, const QString &basePat
iface->registerTypes(moduleId);
}
- data->registerModuleTypes(QQmlMetaTypeData::VersionedUri(uri, version));
+ data->registerModuleTypes(uri);
if (!failures.isEmpty()) {
if (errors) {
diff --git a/src/qml/qml/qqmlmetatype_p.h b/src/qml/qml/qqmlmetatype_p.h
index e98a87e6a9..c68bf0c551 100644
--- a/src/qml/qml/qqmlmetatype_p.h
+++ b/src/qml/qml/qqmlmetatype_p.h
@@ -198,11 +198,10 @@ public:
static void clone(QMetaObjectBuilder &builder, const QMetaObject *mo,
const QMetaObject *ignoreStart, const QMetaObject *ignoreEnd);
- static void qmlInsertModuleRegistration(const QString &uri, QTypeRevision version,
- void (*registerFunction)());
- static void qmlRemoveModuleRegistration(const QString &uri, QTypeRevision version);
+ static void qmlInsertModuleRegistration(const QString &uri, void (*registerFunction)());
+ static void qmlRemoveModuleRegistration(const QString &uri);
- static bool qmlRegisterModuleTypes(const QString &uri, QTypeRevision version);
+ static bool qmlRegisterModuleTypes(const QString &uri);
};
Q_DECLARE_TYPEINFO(QQmlMetaType, Q_MOVABLE_TYPE);
diff --git a/src/qml/qml/qqmlmetatypedata.cpp b/src/qml/qml/qqmlmetatypedata.cpp
index 51d944e771..a34a0c1ae4 100644
--- a/src/qml/qml/qqmlmetatypedata.cpp
+++ b/src/qml/qml/qqmlmetatypedata.cpp
@@ -78,9 +78,9 @@ void QQmlMetaTypeData::registerType(QQmlTypePrivate *priv)
priv->release();
}
-bool QQmlMetaTypeData::registerModuleTypes(const QQmlMetaTypeData::VersionedUri &versionedUri)
+bool QQmlMetaTypeData::registerModuleTypes(const QString &uri)
{
- auto function = moduleTypeRegistrationFunctions.constFind(versionedUri);
+ auto function = moduleTypeRegistrationFunctions.constFind(uri);
if (function != moduleTypeRegistrationFunctions.constEnd()) {
(*function)();
return true;
@@ -138,10 +138,15 @@ QQmlPropertyCache *QQmlMetaTypeData::propertyCache(const QQmlType &type, QTypeRe
const QMetaObject *metaObject = type.metaObject();
+ const QTypeRevision combinedVersion = version.hasMajorVersion()
+ ? version
+ : (version.hasMinorVersion()
+ ? QTypeRevision::fromVersion(type.version().majorVersion(),
+ version.minorVersion())
+ : type.version());
+
while (metaObject) {
- QQmlType t = QQmlMetaType::qmlType(metaObject, type.module(),
- QTypeRevision::fromVersion(type.version().majorVersion(),
- version.minorVersion()));
+ QQmlType t = QQmlMetaType::qmlType(metaObject, type.module(), combinedVersion);
if (t.isValid()) {
maxMinorVersion = qMax(maxMinorVersion, t.version().minorVersion());
types << t;
@@ -152,13 +157,14 @@ QQmlPropertyCache *QQmlMetaTypeData::propertyCache(const QQmlType &type, QTypeRe
metaObject = metaObject->superClass();
}
- const QTypeRevision maxVersion = QTypeRevision::fromVersion(version.majorVersion(), maxMinorVersion);
+ const QTypeRevision maxVersion = QTypeRevision::fromVersion(combinedVersion.majorVersion(),
+ maxMinorVersion);
if (QQmlPropertyCache *pc = propertyCacheForVersion(type.index(), maxVersion)) {
setPropertyCacheForVersion(type.index(), maxVersion, pc);
return pc;
}
- QQmlPropertyCache *raw = propertyCache(type.metaObject(), version);
+ QQmlPropertyCache *raw = propertyCache(type.metaObject(), combinedVersion);
bool hasCopied = false;
@@ -230,7 +236,7 @@ QQmlPropertyCache *QQmlMetaTypeData::propertyCache(const QQmlType &type, QTypeRe
if (hasCopied)
raw->release();
- if (version.minorVersion() != maxMinorVersion)
+ if (version != maxVersion)
setPropertyCacheForVersion(type.index(), maxVersion, raw);
return raw;
diff --git a/src/qml/qml/qqmlmetatypedata_p.h b/src/qml/qml/qqmlmetatypedata_p.h
index 7392b8573d..26fc566653 100644
--- a/src/qml/qml/qqmlmetatypedata_p.h
+++ b/src/qml/qml/qqmlmetatypedata_p.h
@@ -99,8 +99,8 @@ struct QQmlMetaTypeData
typedef QHash<VersionedUri, QQmlTypeModule *> TypeModules;
TypeModules uriToModule;
- QHash<VersionedUri, void (*)()> moduleTypeRegistrationFunctions;
- bool registerModuleTypes(const VersionedUri &versionedUri);
+ QHash<QString, void (*)()> moduleTypeRegistrationFunctions;
+ bool registerModuleTypes(const QString &uri);
QBitArray objects;
QBitArray interfaces;
diff --git a/src/qml/qml/qqmlmoduleregistration.cpp b/src/qml/qml/qqmlmoduleregistration.cpp
index 01f93b85fe..422a5c0551 100644
--- a/src/qml/qml/qqmlmoduleregistration.cpp
+++ b/src/qml/qml/qqmlmoduleregistration.cpp
@@ -46,23 +46,26 @@ QT_BEGIN_NAMESPACE
struct QQmlModuleRegistrationPrivate
{
const QString uri;
- const QTypeRevision version;
};
+QQmlModuleRegistration::QQmlModuleRegistration(const char *uri, void (*registerFunction)()) :
+ d(new QQmlModuleRegistrationPrivate { QString::fromUtf8(uri) })
+{
+ QQmlMetaType::qmlInsertModuleRegistration(d->uri, registerFunction);
+}
+
+#if QT_DEPRECATED_SINCE(6, 0)
QQmlModuleRegistration::QQmlModuleRegistration(
- const char *uri, int majorVersion,
- void (*registerFunction)()) :
- d(new QQmlModuleRegistrationPrivate {
- QString::fromUtf8(uri),
- QTypeRevision::fromMajorVersion(majorVersion)
- })
+ const char *uri, int majorVersion, void (*registerFunction)()) :
+ QQmlModuleRegistration(uri, registerFunction)
{
- QQmlMetaType::qmlInsertModuleRegistration(d->uri, d->version, registerFunction);
+ Q_UNUSED(majorVersion);
}
+#endif
QQmlModuleRegistration::~QQmlModuleRegistration()
{
- QQmlMetaType::qmlRemoveModuleRegistration(d->uri, d->version);
+ QQmlMetaType::qmlRemoveModuleRegistration(d->uri);
delete d;
}
diff --git a/src/qml/qml/qqmlmoduleregistration.h b/src/qml/qml/qqmlmoduleregistration.h
index 6f553a2823..3db535faa0 100644
--- a/src/qml/qml/qqmlmoduleregistration.h
+++ b/src/qml/qml/qqmlmoduleregistration.h
@@ -49,9 +49,14 @@ class Q_QML_EXPORT QQmlModuleRegistration
{
Q_DISABLE_COPY_MOVE(QQmlModuleRegistration)
public:
- QQmlModuleRegistration(const char *uri, int majorVersion, void (*registerFunction)());
+ QQmlModuleRegistration(const char *uri, void (*registerFunction)());
~QQmlModuleRegistration();
+#if QT_DEPRECATED_SINCE(6, 0)
+ QT_DEPRECATED_X("Use registration without major version")
+ QQmlModuleRegistration(const char *uri, int majorVersion, void (*registerFunction)());
+#endif
+
private:
QQmlModuleRegistrationPrivate *d = nullptr;
};
diff --git a/src/qml/qml/qqmlpropertycachecreator.cpp b/src/qml/qml/qqmlpropertycachecreator.cpp
index 5e83deff18..f132fb2d78 100644
--- a/src/qml/qml/qqmlpropertycachecreator.cpp
+++ b/src/qml/qml/qqmlpropertycachecreator.cpp
@@ -119,13 +119,10 @@ QQmlRefPointer<QQmlPropertyCache> QQmlBindingInstantiationContext::instantiating
{
if (instantiatingProperty) {
if (instantiatingProperty->isQObject()) {
- // If the typeVersion is invalid here, we want to match any version we can find.
- // 254.254 is the largest version QTypeRevision can hold.
- return enginePrivate->rawPropertyCacheForType(
- instantiatingProperty->propType(),
- instantiatingProperty->typeVersion().isValid()
- ? instantiatingProperty->typeVersion()
- : QTypeRevision::fromVersion(254, 254));
+ // rawPropertyCacheForType assumes a given unspecified version means "any version".
+ // There is another overload that takes no version, which we shall not use here.
+ return enginePrivate->rawPropertyCacheForType(instantiatingProperty->propType(),
+ instantiatingProperty->typeVersion());
} else if (const QMetaObject *vtmo = QQmlValueTypeFactory::metaObjectForMetaType(instantiatingProperty->propType())) {
return enginePrivate->cache(vtmo, instantiatingProperty->typeVersion());
}
diff --git a/src/qml/qml/qqmlpropertyvalidator.cpp b/src/qml/qml/qqmlpropertyvalidator.cpp
index 01bf1bede7..001b19a8e5 100644
--- a/src/qml/qml/qqmlpropertyvalidator.cpp
+++ b/src/qml/qml/qqmlpropertyvalidator.cpp
@@ -747,9 +747,8 @@ QQmlJS::DiagnosticMessage QQmlPropertyValidator::validateObjectBinding(QQmlPrope
// We want to use the raw metaObject here as the raw metaobject is the
// actual property type before we applied any extensions that might
// effect the properties on the type, but don't effect assignability
- // Using -1 for the minor version ensures that we get the raw metaObject.
- QQmlPropertyCache *propertyMetaObject = enginePrivate->rawPropertyCacheForType(propType,
- QTypeRevision());
+ // Not passing a version ensures that we get the raw metaObject.
+ QQmlPropertyCache *propertyMetaObject = enginePrivate->rawPropertyCacheForType(propType);
if (propertyMetaObject) {
// Will be true if the assigned type inherits propertyMetaObject
diff --git a/src/qml/qml/qqmltypecompiler.cpp b/src/qml/qml/qqmltypecompiler.cpp
index 06d5c47b53..d7a549e380 100644
--- a/src/qml/qml/qqmltypecompiler.cpp
+++ b/src/qml/qml/qqmltypecompiler.cpp
@@ -818,8 +818,12 @@ void QQmlComponentAndAliasResolver::findAndRegisterImplicitComponents(const QmlI
if (!pd || !pd->isQObject())
continue;
- QQmlPropertyCache *pc = enginePrivate->rawPropertyCacheForType(
- pd->propType(), pd->typeVersion());
+ // If the version is given, use it and look up by QQmlType.
+ // Otherwise, make sure we look up by metaobject.
+ // TODO: Is this correct?
+ QQmlPropertyCache *pc = pd->typeVersion().hasMinorVersion()
+ ? enginePrivate->rawPropertyCacheForType(pd->propType(), pd->typeVersion())
+ : enginePrivate->rawPropertyCacheForType(pd->propType());
const QMetaObject *mo = pc ? pc->firstCppMetaObject() : nullptr;
while (mo) {
if (mo == &QQmlComponent::staticMetaObject)
diff --git a/src/qml/qml/qqmltypeloader.cpp b/src/qml/qml/qqmltypeloader.cpp
index 01f70b1703..afad15331c 100644
--- a/src/qml/qml/qqmltypeloader.cpp
+++ b/src/qml/qml/qqmltypeloader.cpp
@@ -606,7 +606,7 @@ bool QQmlTypeLoader::Blob::addImport(QQmlTypeLoader::Blob::PendingImportPtr impo
// Is this a module?
if (QQmlMetaType::isAnyModule(import->uri)
|| (qmldirResult != QQmlImports::QmldirInterceptedToRemote
- && QQmlMetaType::qmlRegisterModuleTypes(import->uri, import->version))) {
+ && QQmlMetaType::qmlRegisterModuleTypes(import->uri))) {
if (!m_importCache.addLibraryImport(
importDatabase, import->uri, import->qualifier, import->version,
QString(), QString(), false, errors))
diff --git a/src/qmltyperegistrar/qmltyperegistrar.cpp b/src/qmltyperegistrar/qmltyperegistrar.cpp
index c22f349ea0..697f96959f 100644
--- a/src/qmltyperegistrar/qmltyperegistrar.cpp
+++ b/src/qmltyperegistrar/qmltyperegistrar.cpp
@@ -368,8 +368,8 @@ int main(int argc, char **argv)
qPrintable(module), qPrintable(majorVersion),
qPrintable(parser.value(minorVersionOption)));
fprintf(output, "\n}\n");
- fprintf(output, "\nstatic const QQmlModuleRegistration registration(\"%s\", %s, %s);\n",
- qPrintable(module), qPrintable(majorVersion), qPrintable(functionName));
+ fprintf(output, "\nstatic const QQmlModuleRegistration registration(\"%s\", %s);\n",
+ qPrintable(module), qPrintable(functionName));
if (!parser.isSet(pluginTypesOption))
return EXIT_SUCCESS;
diff --git a/src/qmltyperegistrar/qmltypesclassdescription.cpp b/src/qmltyperegistrar/qmltypesclassdescription.cpp
index aceab7c2b1..f1ec700c50 100644
--- a/src/qmltyperegistrar/qmltypesclassdescription.cpp
+++ b/src/qmltyperegistrar/qmltypesclassdescription.cpp
@@ -61,7 +61,7 @@ const QJsonObject *QmlTypesClassDescription::findType(const QVector<QJsonObject>
void QmlTypesClassDescription::collect(const QJsonObject *classDef,
const QVector<QJsonObject> &types,
const QVector<QJsonObject> &foreign,
- bool topLevel)
+ bool topLevel, QTypeRevision defaultRevision)
{
const auto classInfos = classDef->value(QLatin1String("classInfos")).toArray();
for (const QJsonValue &classInfo : classInfos) {
@@ -72,7 +72,7 @@ void QmlTypesClassDescription::collect(const QJsonObject *classDef,
if (name == QLatin1String("DefaultProperty")) {
if (defaultProp.isEmpty())
defaultProp = value;
- } else if (name == QLatin1String("QML.AddedInMinorVersion")) {
+ } else if (name == QLatin1String("QML.AddedInVersion")) {
const QTypeRevision revision = QTypeRevision::fromEncodedVersion(value.toInt());
if (topLevel) {
addedInRevision = revision;
@@ -91,16 +91,16 @@ void QmlTypesClassDescription::collect(const QJsonObject *classDef,
elementName = classDef->value(QLatin1String("className")).toString();
else if (value != QLatin1String("anonymous"))
elementName = value;
- } else if (name == QLatin1String("QML.RemovedInMinorVersion")) {
+ } else if (name == QLatin1String("QML.RemovedInVersion")) {
removedInRevision = QTypeRevision::fromEncodedVersion(value.toInt());
} else if (name == QLatin1String("QML.Creatable")) {
isCreatable = (value != QLatin1String("false"));
} else if (name == QLatin1String("QML.Attached")) {
attachedType = value;
if (const QJsonObject *other = findType(types, attachedType))
- collect(other, types, foreign, false);
+ collect(other, types, foreign, false, defaultRevision);
else if (const QJsonObject *other = findType(foreign, attachedType))
- collect(other, types, foreign, false);
+ collect(other, types, foreign, false, defaultRevision);
} else if (name == QLatin1String("QML.Singleton")) {
if (value == QLatin1String("true"))
isSingleton = true;
@@ -143,15 +143,17 @@ void QmlTypesClassDescription::collect(const QJsonObject *classDef,
superClass = superName;
if (const QJsonObject *other = findType(types, superName))
- collect(other, types, foreign, false);
+ collect(other, types, foreign, false, defaultRevision);
else if (const QJsonObject *other = findType(foreign, superName))
- collect(other, types, foreign, false);
+ collect(other, types, foreign, false, defaultRevision);
}
}
if (!addedInRevision.isValid()) {
- revisions.append(QTypeRevision::zero());
- addedInRevision = QTypeRevision::zero();
+ revisions.append(defaultRevision);
+ addedInRevision = defaultRevision;
+ } else if (addedInRevision < defaultRevision) {
+ revisions.append(defaultRevision);
}
std::sort(revisions.begin(), revisions.end());
diff --git a/src/qmltyperegistrar/qmltypesclassdescription.h b/src/qmltyperegistrar/qmltypesclassdescription.h
index 8222016faf..6f391ba45c 100644
--- a/src/qmltyperegistrar/qmltypesclassdescription.h
+++ b/src/qmltyperegistrar/qmltypesclassdescription.h
@@ -51,7 +51,7 @@ struct QmlTypesClassDescription
bool isBuiltin = false;
void collect(const QJsonObject *classDef, const QVector<QJsonObject> &types,
- const QVector<QJsonObject> &foreign, bool topLevel);
+ const QVector<QJsonObject> &foreign, bool topLevel, QTypeRevision defaultRevision);
static const QJsonObject *findType(const QVector<QJsonObject> &types, const QString &name);
};
diff --git a/src/qmltyperegistrar/qmltypescreator.cpp b/src/qmltyperegistrar/qmltypescreator.cpp
index 8991ee42b6..d34740eaa0 100644
--- a/src/qmltyperegistrar/qmltypescreator.cpp
+++ b/src/qmltyperegistrar/qmltypescreator.cpp
@@ -63,6 +63,11 @@ void QmlTypesCreator::writeClassProperties(const QmlTypesClassDescription &colle
QStringList exports;
QStringList metaObjects;
+ if (collector.isBuiltin) {
+ exports.append(enquote(QString::fromLatin1("QML/%1 1.0").arg(collector.elementName)));
+ metaObjects.append(QString::number(QTypeRevision::fromVersion(1, 0).toEncodedVersion<quint16>()));
+ }
+
for (auto it = collector.revisions.begin(), end = collector.revisions.end(); it != end; ++it) {
const QTypeRevision revision = *it;
if (revision < collector.addedInRevision)
@@ -70,14 +75,11 @@ void QmlTypesCreator::writeClassProperties(const QmlTypesClassDescription &colle
if (collector.removedInRevision.isValid() && !(revision < collector.removedInRevision))
break;
- if (collector.isBuiltin) {
- exports.append(enquote(QString::fromLatin1("QML/%1 1.0").arg(collector.elementName)));
- metaObjects.append(QLatin1String("0"));
- }
-
exports.append(enquote(QString::fromLatin1("%1/%2 %3.%4")
- .arg(m_module).arg(collector.elementName)
- .arg(m_version.majorVersion()).arg(revision.minorVersion())));
+ .arg(m_module).arg(collector.elementName)
+ .arg(revision.hasMajorVersion() ? revision.majorVersion()
+ : m_version.majorVersion())
+ .arg(revision.minorVersion())));
metaObjects.append(QString::number(revision.toEncodedVersion<quint16>()));
}
@@ -244,7 +246,7 @@ void QmlTypesCreator::writeComponents()
m_qml.writeStartObject(componentElement);
QmlTypesClassDescription collector;
- collector.collect(&component, m_ownTypes, m_foreignTypes, true);
+ collector.collect(&component, m_ownTypes, m_foreignTypes, true, m_version);
writeClassProperties(collector);
diff --git a/tests/auto/qml/qmlplugindump/data/dumper/Versions/plugins.qmltypes b/tests/auto/qml/qmlplugindump/data/dumper/Versions/plugins.qmltypes
index 3a33590139..ce003fc535 100644
--- a/tests/auto/qml/qmlplugindump/data/dumper/Versions/plugins.qmltypes
+++ b/tests/auto/qml/qmlplugindump/data/dumper/Versions/plugins.qmltypes
@@ -15,9 +15,9 @@ Module {
"dumper.Versions/Versions 1.0",
"dumper.Versions/Versions 1.1"
]
- exportMetaObjectRevisions: [0, 1]
+ exportMetaObjectRevisions: [0, 65281]
Property { name: "foo"; type: "int" }
- Property { name: "bar"; revision: 1; type: "int" }
- Property { name: "baz"; revision: 2; type: "int" }
+ Property { name: "bar"; revision: 65281; type: "int" }
+ Property { name: "baz"; revision: 65282; type: "int" }
}
}
diff --git a/tests/auto/qml/qqmlpropertycache/tst_qqmlpropertycache.cpp b/tests/auto/qml/qqmlpropertycache/tst_qqmlpropertycache.cpp
index 25a448a97f..2e040eec18 100644
--- a/tests/auto/qml/qqmlpropertycache/tst_qqmlpropertycache.cpp
+++ b/tests/auto/qml/qqmlpropertycache/tst_qqmlpropertycache.cpp
@@ -168,7 +168,7 @@ void tst_qqmlpropertycache::revisionedProperties()
QQmlRefPointer<QQmlPropertyCache> cacheWithoutVersion(new QQmlPropertyCache(metaObject),
QQmlRefPointer<QQmlPropertyCache>::Adopt);
QQmlRefPointer<QQmlPropertyCache> cacheWithVersion(
- new QQmlPropertyCache(metaObject, QTypeRevision::fromEncodedVersion(1)),
+ new QQmlPropertyCache(metaObject, QTypeRevision::fromMinorVersion(1)),
QQmlRefPointer<QQmlPropertyCache>::Adopt);
QQmlPropertyData *data;