aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/imports/builtins/builtins.qmltypes101
-rw-r--r--src/labs/sharedimage/CMakeLists.txt1
-rw-r--r--src/qml/CMakeLists.txt1
-rw-r--r--src/qml/Qt6QmlBuildInternals.cmake2
-rw-r--r--src/qml/Qt6QmlMacros.cmake17
-rw-r--r--src/qml/qml/qqmlcomponent.h1
-rw-r--r--src/qml/qml/qqmlengine_p.h2
-rw-r--r--src/qml/qmldirparser/qqmldirparser.cpp10
-rw-r--r--src/qml/qmldirparser/qqmldirparser_p.h4
-rw-r--r--src/qmlcompiler/qqmljsimporter.cpp32
-rw-r--r--src/qmlcompiler/qqmljsimporter_p.h16
-rw-r--r--src/qmlcompiler/qqmljsimportvisitor.cpp18
-rw-r--r--src/qmlcompiler/qqmljsimportvisitor_p.h2
-rw-r--r--src/qmltyperegistrar/qmltypesclassdescription.cpp5
-rw-r--r--src/qmltyperegistrar/qmltypesclassdescription.h2
-rw-r--r--src/qmltyperegistrar/qmltypescreator.cpp83
-rw-r--r--tests/auto/qml/qmllint/data/qobjectHasOwnProperty.qml7
-rw-r--r--tests/auto/qml/qmllint/data/unused_static.qml4
-rw-r--r--tests/auto/qml/qmllint/tst_qmllint.cpp2
19 files changed, 202 insertions, 108 deletions
diff --git a/src/imports/builtins/builtins.qmltypes b/src/imports/builtins/builtins.qmltypes
index 23defaa55b..0bc89d8c9c 100644
--- a/src/imports/builtins/builtins.qmltypes
+++ b/src/imports/builtins/builtins.qmltypes
@@ -23,61 +23,118 @@ Module {
}
Component {
+ file: "private/qqmlengine_p.h"
name: "QObject"
+ extension: "Object"
accessSemantics: "reference"
exports: ["QML/QtObject 1.0"]
exportMetaObjectRevisions: [256]
-
- Method {
- name: "toString"
+ Property {
+ name: "objectName"
type: "QString"
+ bindable: "bindableObjectName"
+ read: "objectName"
+ write: "setObjectName"
+ notify: "objectNameChanged"
+ index: 0
+ }
+ Signal {
+ name: "objectNameChanged"
+ Parameter { name: "objectName"; type: "QString" }
}
-
Method {
- name: "destroy"
+ name: "_q_reregisterTimers"
+ Parameter { type: "void"; isPointer: true }
}
-
+ Method { name: "toString"; type: "string" }
+ Method { name: "destroy" }
Method {
name: "destroy"
-
- Parameter {
- name: "delay"
- type: "int"
- }
+ Parameter { name: "delay"; type: "int" }
}
}
Component {
+ file: "qqmlcomponent.h"
name: "QQmlComponent"
accessSemantics: "reference"
prototype: "QObject"
exports: ["QML/Component 1.0"]
exportMetaObjectRevisions: [256]
-
+ attachedType: "QQmlComponentAttached"
+ Enum {
+ name: "CompilationMode"
+ values: ["PreferSynchronous", "Asynchronous"]
+ }
Enum {
name: "Status"
values: ["Null", "Ready", "Loading", "Error"]
}
-
+ Property {
+ name: "progress"
+ type: "double"
+ read: "progress"
+ notify: "progressChanged"
+ index: 0
+ isReadonly: true
+ }
Property {
name: "status"
type: "Status"
+ read: "status"
+ notify: "statusChanged"
+ index: 1
isReadonly: true
}
-
+ Property { name: "url"; type: "QUrl"; read: "url"; index: 2; isReadonly: true }
Signal {
name: "statusChanged"
-
- Parameter {
- type: "QQmlComponent::Status"
- }
-
+ Parameter { type: "QQmlComponent::Status" }
+ }
+ Signal {
+ name: "progressChanged"
+ Parameter { type: "double" }
}
-
Method {
- name: "errorString"
- type: "QString"
+ name: "loadUrl"
+ Parameter { name: "url"; type: "QUrl" }
+ }
+ Method {
+ name: "loadUrl"
+ Parameter { name: "url"; type: "QUrl" }
+ Parameter { name: "mode"; type: "CompilationMode" }
+ }
+ Method {
+ name: "setData"
+ Parameter { type: "QByteArray" }
+ Parameter { name: "baseUrl"; type: "QUrl" }
}
+ Method { name: "errorString"; type: "QString" }
+ Method { name: "createObject"; isJavaScriptFunction: true }
+ Method {
+ name: "createObject"
+ type: "QObject"
+ isPointer: true
+ Parameter { name: "parent"; type: "QObject"; isPointer: true }
+ Parameter { name: "properties"; type: "QVariantMap" }
+ }
+ Method {
+ name: "createObject"
+ type: "QObject"
+ isPointer: true
+ Parameter { name: "parent"; type: "QObject"; isPointer: true }
+ }
+ Method { name: "createObject"; type: "QObject"; isPointer: true }
+ Method { name: "incubateObject"; isJavaScriptFunction: true }
+ }
+
+ Component {
+ file: "private/qqmlcomponentattached_p.h"
+ name: "QQmlComponentAttached"
+ accessSemantics: "reference"
+ prototype: "QObject"
+ Signal { name: "completed" }
+ Signal { name: "destruction" }
}
Component {
diff --git a/src/labs/sharedimage/CMakeLists.txt b/src/labs/sharedimage/CMakeLists.txt
index 0dec607ac2..5acfb3dddf 100644
--- a/src/labs/sharedimage/CMakeLists.txt
+++ b/src/labs/sharedimage/CMakeLists.txt
@@ -1,6 +1,7 @@
qt_internal_add_qml_module(LabsSharedImage
URI "Qt.labs.sharedimage"
VERSION "${PROJECT_VERSION}"
+ __QT_INTERNAL_STATIC_MODULE
PLUGIN_TARGET sharedimageplugin
NO_PLUGIN_OPTIONAL
NO_GENERATE_PLUGIN_SOURCE
diff --git a/src/qml/CMakeLists.txt b/src/qml/CMakeLists.txt
index 046e29fdcd..3c08c6f9c5 100644
--- a/src/qml/CMakeLists.txt
+++ b/src/qml/CMakeLists.txt
@@ -32,6 +32,7 @@ qt_internal_add_qml_module(Qml
URI "QtQml"
VERSION "${PROJECT_VERSION}"
DESIGNER_SUPPORTED
+ __QT_INTERNAL_SYSTEM_MODULE
PLUGIN_TARGET qmlplugin
CLASS_NAME QtQmlPlugin
IMPORTS ${module_dynamic_qml_imports}
diff --git a/src/qml/Qt6QmlBuildInternals.cmake b/src/qml/Qt6QmlBuildInternals.cmake
index 4b6a144b0e..13cc64cad7 100644
--- a/src/qml/Qt6QmlBuildInternals.cmake
+++ b/src/qml/Qt6QmlBuildInternals.cmake
@@ -18,6 +18,8 @@ macro(qt_internal_get_internal_add_qml_module_keywords
NO_GENERATE_QMLDIR
NO_LINT
NO_CACHEGEN
+ __QT_INTERNAL_STATIC_MODULE
+ __QT_INTERNAL_SYSTEM_MODULE
)
set(${single_args}
URI
diff --git a/src/qml/Qt6QmlMacros.cmake b/src/qml/Qt6QmlMacros.cmake
index e2bef207d3..d3e9ac0e03 100644
--- a/src/qml/Qt6QmlMacros.cmake
+++ b/src/qml/Qt6QmlMacros.cmake
@@ -32,6 +32,11 @@ function(qt6_add_qml_module target)
# Used only by _qt_internal_qml_type_registration()
# TODO: Remove this once qt6_extract_metatypes does not install by default.
__QT_INTERNAL_INSTALL_METATYPES_JSON
+
+ # Used to mark modules as having static side effects (i.e. if they install an image provider)
+ __QT_INTERNAL_STATIC_MODULE
+ # Used to mark modules as being a system module that provides all builtins
+ __QT_INTERNAL_SYSTEM_MODULE
)
set(args_single
@@ -453,6 +458,8 @@ function(qt6_add_qml_module target)
_qt_qml_module_installed_plugin_target "${arg_INSTALLED_PLUGIN_TARGET}"
QT_QML_MODULE_DESIGNER_SUPPORTED "${arg_DESIGNER_SUPPORTED}"
+ QT_QML_MODULE_IS_STATIC "${arg___QT_INTERNAL_STATIC_MODULE}"
+ QT_QML_MODULE_IS_SYSTEM "${arg___QT_INTERNAL_SYSTEM_MODULE}"
QT_QML_MODULE_OUTPUT_DIRECTORY "${arg_OUTPUT_DIRECTORY}"
QT_QML_MODULE_RESOURCE_PREFIX "${qt_qml_module_resource_prefix}"
QT_QML_MODULE_PAST_MAJOR_VERSIONS "${arg_PAST_MAJOR_VERSIONS}"
@@ -954,6 +961,16 @@ function(_qt_internal_target_generate_qmldir target)
string(APPEND content "designersupported\n")
endif()
+ get_target_property(static_module ${target} QT_QML_MODULE_IS_STATIC)
+ if (static_module)
+ string(APPEND content "static\n")
+ endif()
+
+ get_target_property(system_module ${target} QT_QML_MODULE_IS_SYSTEM)
+ if (system_module)
+ string(APPEND content "system\n")
+ endif()
+
_qt_internal_qmldir_item(typeinfo QT_QML_MODULE_TYPEINFO)
_qt_internal_qmldir_item_list(import QT_QML_MODULE_IMPORTS)
diff --git a/src/qml/qml/qqmlcomponent.h b/src/qml/qml/qqmlcomponent.h
index d60c2cdc9f..e70dae5de8 100644
--- a/src/qml/qml/qqmlcomponent.h
+++ b/src/qml/qml/qqmlcomponent.h
@@ -73,6 +73,7 @@ class Q_QML_EXPORT QQmlComponent : public QObject
QML_NAMED_ELEMENT(Component)
QML_ADDED_IN_VERSION(2, 0)
QML_ATTACHED(QQmlComponentAttached)
+ Q_CLASSINFO("QML.OmitFromQmlTypes", "true")
public:
enum CompilationMode { PreferSynchronous, Asynchronous };
diff --git a/src/qml/qml/qqmlengine_p.h b/src/qml/qml/qqmlengine_p.h
index 630d32736b..58bc61dcf0 100644
--- a/src/qml/qml/qqmlengine_p.h
+++ b/src/qml/qml/qqmlengine_p.h
@@ -96,7 +96,7 @@ struct QObjectForeign {
QML_FOREIGN(QObject)
QML_NAMED_ELEMENT(QtObject)
QML_ADDED_IN_VERSION(2, 0)
- Q_CLASSINFO("QML.Root", "QML")
+ Q_CLASSINFO("QML.OmitFromQmlTypes", "true")
};
// This needs to be declared here so that the pool for it can live in QQmlEnginePrivate.
diff --git a/src/qml/qmldirparser/qqmldirparser.cpp b/src/qml/qmldirparser/qqmldirparser.cpp
index 183fa918d2..bb9036582e 100644
--- a/src/qml/qmldirparser/qqmldirparser.cpp
+++ b/src/qml/qmldirparser/qqmldirparser.cpp
@@ -296,6 +296,16 @@ bool QQmlDirParser::parse(const QString &source)
reportError(lineNumber, 0, QStringLiteral("designersupported does not expect any argument"));
else
_designerSupported = true;
+ } else if (sections[0] == QLatin1String("static")) {
+ if (sectionCount != 1)
+ reportError(lineNumber, 0, QStringLiteral("static does not expect any argument"));
+ else
+ _isStaticModule = true;
+ } else if (sections[0] == QLatin1String("system")) {
+ if (sectionCount != 1)
+ reportError(lineNumber, 0, QStringLiteral("system does not expect any argument"));
+ else
+ _isSystemModule = true;
} else if (sections[0] == QLatin1String("import")
|| sections[0] == QLatin1String("depends")) {
if (!readImport(sections, sectionCount, Import::Default))
diff --git a/src/qml/qmldirparser/qqmldirparser_p.h b/src/qml/qmldirparser/qqmldirparser_p.h
index fe371e6b4f..51d4d75323 100644
--- a/src/qml/qmldirparser/qqmldirparser_p.h
+++ b/src/qml/qmldirparser/qqmldirparser_p.h
@@ -157,6 +157,8 @@ public:
QList<Script> scripts() const { return _scripts; }
QList<Plugin> plugins() const { return _plugins; }
bool designerSupported() const { return _designerSupported; }
+ bool isStaticModule() const { return _isStaticModule; }
+ bool isSystemModule() const { return _isSystemModule; }
QStringList typeInfos() const { return _typeInfos; }
QStringList classNames() const { return _classNames; }
@@ -177,6 +179,8 @@ private:
QList<Script> _scripts;
QList<Plugin> _plugins;
bool _designerSupported = false;
+ bool _isStaticModule = false;
+ bool _isSystemModule = false;
QStringList _typeInfos;
QStringList _classNames;
QString _linkTarget;
diff --git a/src/qmlcompiler/qqmljsimporter.cpp b/src/qmlcompiler/qqmljsimporter.cpp
index e14fa7a52d..757830448e 100644
--- a/src/qmlcompiler/qqmljsimporter.cpp
+++ b/src/qmlcompiler/qqmljsimporter.cpp
@@ -146,6 +146,9 @@ QQmlJSImporter::Import QQmlJSImporter::readQmldir(const QString &path)
{
Import result;
auto reader = createQmldirParserForFile(path + SlashQmldir);
+ result.name = reader.typeNamespace();
+ result.isStaticModule = reader.isStaticModule();
+ result.isSystemModule = reader.isSystemModule();
result.imports.append(reader.imports());
result.dependencies.append(reader.dependencies());
@@ -354,6 +357,14 @@ void QQmlJSImporter::processImport(const QQmlJSScope::Import &importDescription,
if (!importDescription.prefix().isEmpty())
types->qmlNames.insert(importDescription.prefix(), {}); // Empty type means "this is the prefix"
+ if (!importDescription.isDependency()) {
+ if (import.isStaticModule)
+ types->staticModules << import.name;
+
+ if (import.isSystemModule)
+ types->hasSystemModule = true;
+ }
+
for (auto it = import.scripts.begin(); it != import.scripts.end(); ++it) {
types->cppNames.insert(prefixedName(anonPrefix, internalName(it->scope)), it->scope);
// You cannot have a script without an export
@@ -520,10 +531,13 @@ void QQmlJSImporter::importQmldirs(const QStringList &qmldirFiles)
}
}
-QQmlJSImporter::ImportedTypes QQmlJSImporter::importModule(
- const QString &module, const QString &prefix, QTypeRevision version)
+QQmlJSImporter::ImportedTypes QQmlJSImporter::importModule(const QString &module,
+ const QString &prefix,
+ QTypeRevision version,
+ QStringList *staticModuleList)
{
- AvailableTypes result(builtinImportHelper().cppNames);
+ const AvailableTypes builtins = builtinImportHelper();
+ AvailableTypes result(builtins.cppNames);
if (!importHelper(module, &result, prefix, version)) {
m_warnings.append({
QStringLiteral("Failed to import %1. Are your include paths set up properly?").arg(module),
@@ -531,6 +545,16 @@ QQmlJSImporter::ImportedTypes QQmlJSImporter::importModule(
QQmlJS::SourceLocation()
});
}
+
+ // If we imported a system module add all builtin QML types
+ if (result.hasSystemModule) {
+ for (const QString &name : builtins.qmlNames.keys())
+ result.qmlNames.insert(prefixedName(prefix, name), builtins.qmlNames[name]);
+ }
+
+ if (staticModuleList)
+ *staticModuleList << result.staticModules;
+
return result.qmlNames;
}
@@ -558,6 +582,8 @@ bool QQmlJSImporter::importHelper(const QString &module, AvailableTypes *types,
const auto &cacheEntry = m_cachedImportTypes[cacheKey];
types->cppNames.insert(cacheEntry->cppNames);
+ types->staticModules << cacheEntry->staticModules;
+ types->hasSystemModule = cacheEntry->hasSystemModule;
// No need to import qml names for dependencies
if (!isDependency)
diff --git a/src/qmlcompiler/qqmljsimporter_p.h b/src/qmlcompiler/qqmljsimporter_p.h
index fdadcf6c3b..4cc22f4cfe 100644
--- a/src/qmlcompiler/qqmljsimporter_p.h
+++ b/src/qmlcompiler/qqmljsimporter_p.h
@@ -65,9 +65,9 @@ public:
QQmlJSScope::Ptr importFile(const QString &file);
ImportedTypes importDirectory(const QString &directory, const QString &prefix = QString());
- ImportedTypes importModule(
- const QString &module, const QString &prefix = QString(),
- QTypeRevision version = QTypeRevision());
+ ImportedTypes importModule(const QString &module, const QString &prefix = QString(),
+ QTypeRevision version = QTypeRevision(),
+ QStringList *staticModuleList = nullptr);
ImportedTypes builtinInternalNames();
@@ -97,9 +97,19 @@ private:
// Names the importing component sees, including any prefixes
QHash<QString, QQmlJSScope::ConstPtr> qmlNames;
+
+ // Static modules included here
+ QStringList staticModules;
+
+ // Whether a system module has been imported
+ bool hasSystemModule = false;
};
struct Import {
+ QString name;
+ bool isStaticModule;
+ bool isSystemModule;
+
QHash<QString, QQmlJSExportedScope> objects;
QHash<QString, QQmlJSExportedScope> scripts;
QList<QQmlDirParser::Import> imports;
diff --git a/src/qmlcompiler/qqmljsimportvisitor.cpp b/src/qmlcompiler/qqmljsimportvisitor.cpp
index 6d7fe4807c..4efc722d5e 100644
--- a/src/qmlcompiler/qqmljsimportvisitor.cpp
+++ b/src/qmlcompiler/qqmljsimportvisitor.cpp
@@ -398,6 +398,9 @@ void QQmlJSImportVisitor::endVisit(UiProgram *)
break;
}
+ for (const QQmlJS::SourceLocation &import : m_importStaticModuleLocationMap.values())
+ unusedImports.remove(import);
+
for (const auto &import : unusedImports) {
m_logger->logInfo(QString::fromLatin1("Unused import at %1:%2:%3")
.arg(m_logger->fileName())
@@ -1715,13 +1718,26 @@ bool QQmlJSImportVisitor::visit(QQmlJS::AST::UiImport *import)
}
path.chop(1);
+ QStringList staticModulesProvided;
+
const auto imported = m_importer->importModule(
- path, prefix, import->version ? import->version->version : QTypeRevision());
+ path, prefix, import->version ? import->version->version : QTypeRevision(),
+ &staticModulesProvided);
m_rootScopeImports.insert(imported);
for (const QString &key : imported.keys())
addImportLocation(key);
+ if (prefix.isEmpty()) {
+ for (const QString &staticModule : staticModulesProvided) {
+ // Always prefer a direct import of static module to it being imported as a dependency
+ if (path != staticModule && m_importStaticModuleLocationMap.contains(staticModule))
+ continue;
+
+ m_importStaticModuleLocationMap[staticModule] = import->firstSourceLocation();
+ }
+ }
+
processImportWarnings(QStringLiteral("module \"%1\"").arg(path), import->firstSourceLocation());
return true;
}
diff --git a/src/qmlcompiler/qqmljsimportvisitor_p.h b/src/qmlcompiler/qqmljsimportvisitor_p.h
index c5175fac2a..5a5256a98c 100644
--- a/src/qmlcompiler/qqmljsimportvisitor_p.h
+++ b/src/qmlcompiler/qqmljsimportvisitor_p.h
@@ -167,6 +167,8 @@ protected:
// Maps all qmlNames to the source location of their import
QMultiHash<QString, QQmlJS::SourceLocation> m_importTypeLocationMap;
+ // Maps all static modules to the source location of their import
+ QMultiHash<QString, QQmlJS::SourceLocation> m_importStaticModuleLocationMap;
// Contains all import source locations (could be extracted from above but that is expensive)
QSet<QQmlJS::SourceLocation> m_importLocations;
// A set of all types that have been used during type resolution
diff --git a/src/qmltyperegistrar/qmltypesclassdescription.cpp b/src/qmltyperegistrar/qmltypesclassdescription.cpp
index 369b42fbd9..fb01a48013 100644
--- a/src/qmltyperegistrar/qmltypesclassdescription.cpp
+++ b/src/qmltyperegistrar/qmltypesclassdescription.cpp
@@ -180,8 +180,9 @@ void QmlTypesClassDescription::collect(
isSingleton = true;
} else if (name == QLatin1String("QML.Foreign")) {
foreignTypeName = value;
- } else if (name == QLatin1String("QML.Root")) {
- isRootClass = true;
+ } else if (name == QLatin1String("QML.OmitFromQmlTypes")) {
+ if (value == QLatin1String("true"))
+ omitFromQmlTypes = true;
} else if (name == QLatin1String("QML.HasCustomParser")) {
if (value == QLatin1String("true"))
hasCustomParser = true;
diff --git a/src/qmltyperegistrar/qmltypesclassdescription.h b/src/qmltyperegistrar/qmltypesclassdescription.h
index 10470a1644..000ff2b0da 100644
--- a/src/qmltyperegistrar/qmltypesclassdescription.h
+++ b/src/qmltyperegistrar/qmltypesclassdescription.h
@@ -53,8 +53,8 @@ struct QmlTypesClassDescription
QTypeRevision removedInRevision;
bool isCreatable = true;
bool isSingleton = false;
- bool isRootClass = false;
bool hasCustomParser = false;
+ bool omitFromQmlTypes = false;
QStringList implementsInterfaces;
QStringList deferredNames;
QStringList immediateNames;
diff --git a/src/qmltyperegistrar/qmltypescreator.cpp b/src/qmltyperegistrar/qmltypescreator.cpp
index d7eef3421c..bf74fa9ca2 100644
--- a/src/qmltyperegistrar/qmltypescreator.cpp
+++ b/src/qmltyperegistrar/qmltypescreator.cpp
@@ -336,89 +336,26 @@ static QJsonArray members(const QJsonObject *classDef,
void QmlTypesCreator::writeComponents()
{
- const QLatin1String nameKey("name");
const QLatin1String signalsKey("signals");
const QLatin1String enumsKey("enums");
const QLatin1String propertiesKey("properties");
const QLatin1String slotsKey("slots");
const QLatin1String methodsKey("methods");
- const QLatin1String accessKey("access");
- const QLatin1String typeKey("type");
- const QLatin1String returnTypeKey("returnType");
- const QLatin1String argumentsKey("arguments");
-
- const QLatin1String destroyedName("destroyed");
- const QLatin1String deleteLaterName("deleteLater");
- const QLatin1String toStringName("toString");
- const QLatin1String destroyName("destroy");
- const QLatin1String delayName("delay");
const QLatin1String signalElement("Signal");
const QLatin1String componentElement("Component");
const QLatin1String methodElement("Method");
- const QLatin1String publicAccess("public");
- const QLatin1String intType("int");
- const QLatin1String stringType("string");
-
- auto writeRootClass = [&](const QJsonObject *classDef) {
- // Hide destroyed() signals
- QJsonArray componentSignals = members(classDef, signalsKey, m_version);
- for (auto it = componentSignals.begin(); it != componentSignals.end();) {
- if (it->toObject().value(nameKey).toString() == destroyedName)
- it = componentSignals.erase(it);
- else
- ++it;
- }
- writeMethods(componentSignals, signalElement);
-
- // Hide deleteLater() methods
- QJsonArray componentMethods = members(classDef, methodsKey, m_version);
- const QJsonArray componentSlots = members(classDef, slotsKey, m_version);
- for (const QJsonValue componentSlot : componentSlots)
- componentMethods.append(componentSlot);
- for (auto it = componentMethods.begin(); it != componentMethods.end();) {
- if (it->toObject().value(nameKey).toString() == deleteLaterName)
- it = componentMethods.erase(it);
- else
- ++it;
- }
-
- // Add toString()
- QJsonObject toStringMethod;
- toStringMethod.insert(nameKey, toStringName);
- toStringMethod.insert(accessKey, publicAccess);
- toStringMethod.insert(returnTypeKey, stringType);
- componentMethods.append(toStringMethod);
-
- // Add destroy()
- QJsonObject destroyMethod;
- destroyMethod.insert(nameKey, destroyName);
- destroyMethod.insert(accessKey, publicAccess);
- componentMethods.append(destroyMethod);
-
- // Add destroy(int)
- QJsonObject destroyMethodWithArgument;
- destroyMethodWithArgument.insert(nameKey, destroyName);
- destroyMethodWithArgument.insert(accessKey, publicAccess);
- QJsonObject delayArgument;
- delayArgument.insert(nameKey, delayName);
- delayArgument.insert(typeKey, intType);
- QJsonArray destroyArguments;
- destroyArguments.append(delayArgument);
- destroyMethodWithArgument.insert(argumentsKey, destroyArguments);
- componentMethods.append(destroyMethodWithArgument);
-
- writeMethods(componentMethods, methodElement);
- };
-
for (const QJsonObject &component : m_ownTypes) {
- m_qml.writeStartObject(componentElement);
-
QmlTypesClassDescription collector;
collector.collect(&component, m_ownTypes, m_foreignTypes,
QmlTypesClassDescription::TopLevel, m_version);
+ if (collector.omitFromQmlTypes)
+ continue;
+
+ m_qml.writeStartObject(componentElement);
+
writeClassProperties(collector);
if (const QJsonObject *classDef = collector.resolvedClass) {
@@ -426,13 +363,9 @@ void QmlTypesCreator::writeComponents()
writeProperties(members(classDef, propertiesKey, m_version));
- if (collector.isRootClass) {
- writeRootClass(classDef);
- } else {
- writeMethods(members(classDef, signalsKey, m_version), signalElement);
- writeMethods(members(classDef, slotsKey, m_version), methodElement);
- writeMethods(members(classDef, methodsKey, m_version), methodElement);
- }
+ writeMethods(members(classDef, signalsKey, m_version), signalElement);
+ writeMethods(members(classDef, slotsKey, m_version), methodElement);
+ writeMethods(members(classDef, methodsKey, m_version), methodElement);
}
m_qml.writeEndObject();
diff --git a/tests/auto/qml/qmllint/data/qobjectHasOwnProperty.qml b/tests/auto/qml/qmllint/data/qobjectHasOwnProperty.qml
new file mode 100644
index 0000000000..b985c1354f
--- /dev/null
+++ b/tests/auto/qml/qmllint/data/qobjectHasOwnProperty.qml
@@ -0,0 +1,7 @@
+import QtQml
+
+QtObject {
+ id: root
+
+ property bool hasFooProperty: root.hasOwnProperty('foo')
+}
diff --git a/tests/auto/qml/qmllint/data/unused_static.qml b/tests/auto/qml/qmllint/data/unused_static.qml
new file mode 100644
index 0000000000..57c4bcba2e
--- /dev/null
+++ b/tests/auto/qml/qmllint/data/unused_static.qml
@@ -0,0 +1,4 @@
+import QtQuick
+import Qt.labs.sharedimage
+
+Item {}
diff --git a/tests/auto/qml/qmllint/tst_qmllint.cpp b/tests/auto/qml/qmllint/tst_qmllint.cpp
index 0e166b81f3..8963f3a5f1 100644
--- a/tests/auto/qml/qmllint/tst_qmllint.cpp
+++ b/tests/auto/qml/qmllint/tst_qmllint.cpp
@@ -895,6 +895,7 @@ void TestQmllint::cleanQmlCode_data()
QTest::newRow("duplicateQmldirImport") << QStringLiteral("qmldirImport/duplicate.qml");
QTest::newRow("Used imports") << QStringLiteral("used.qml");
QTest::newRow("Unused imports (multi)") << QStringLiteral("unused_multi.qml");
+ QTest::newRow("Unused static module") << QStringLiteral("unused_static.qml");
QTest::newRow("compositeSingleton") << QStringLiteral("compositesingleton.qml");
QTest::newRow("stringLength") << QStringLiteral("stringLength.qml");
QTest::newRow("stringLength2") << QStringLiteral("stringLength2.qml");
@@ -947,6 +948,7 @@ void TestQmllint::cleanQmlCode_data()
QTest::newRow("declared property of JS object") << QStringLiteral("bareQt.qml");
QTest::newRow("ID overrides property") << QStringLiteral("accessibleId.qml");
QTest::newRow("matchByName") << QStringLiteral("matchByName.qml");
+ QTest::newRow("QObject.hasOwnProperty") << QStringLiteral("qobjectHasOwnProperty.qml");
}
void TestQmllint::cleanQmlCode()