From 8ffd3d20a59a9b8d45963bb5fe2ed11063e0032e Mon Sep 17 00:00:00 2001 From: Miikka Heikkinen Date: Mon, 2 Nov 2020 16:14:32 +0200 Subject: [PATCH] QmlDesigner: Add support for specifying extra files to library entry Extra files specified in the ItemLibraryEntry will be copied to the same directory as the qml doc. Change-Id: I6f10e7ba8114355cbf68bc4b306f0500a81dbad2 Fixes: QDS-2635 Reviewed-by: Mahmoud Badri Reviewed-by: Thomas Hartmann --- .../navigator/navigatortreemodel.cpp | 16 ++++++++++++++ .../designercore/include/itemlibraryinfo.h | 2 ++ .../designercore/include/metainforeader.h | 5 ++++- .../designercore/metainfo/itemlibraryinfo.cpp | 14 ++++++++++++ .../designercore/metainfo/metainforeader.cpp | 22 +++++++++++++++++++ 5 files changed, 58 insertions(+), 1 deletion(-) diff --git a/src/plugins/qmldesigner/components/navigator/navigatortreemodel.cpp b/src/plugins/qmldesigner/components/navigator/navigatortreemodel.cpp index 16cb7e50ea7..1e8cbfa7630 100644 --- a/src/plugins/qmldesigner/components/navigator/navigatortreemodel.cpp +++ b/src/plugins/qmldesigner/components/navigator/navigatortreemodel.cpp @@ -54,6 +54,7 @@ #include #include #include +#include #include #include @@ -681,6 +682,21 @@ void NavigatorTreeModel::handleItemLibraryItemDrop(const QMimeData *mimeData, in if (newQmlObjectNode.isValid()) m_view->setSelectedModelNode(newQmlObjectNode.modelNode()); } + + const QStringList copyFiles = itemLibraryEntry.extraFilePaths(); + if (!copyFiles.isEmpty()) { + // Files are copied into the same directory as the current qml document + for (const auto ©File : copyFiles) { + QFileInfo fi(copyFile); + const QString targetFile = QmlDesignerPlugin::instance()->documentManager() + .currentFilePath().toFileInfo().dir().absoluteFilePath(fi.fileName()); + // We don't want to overwrite existing default files + if (!QFileInfo::exists(targetFile)) { + if (!QFile::copy(copyFile, targetFile)) + qWarning() << QStringLiteral("Copying extra file '%1' failed.").arg(copyFile); + } + } + } } } diff --git a/src/plugins/qmldesigner/designercore/include/itemlibraryinfo.h b/src/plugins/qmldesigner/designercore/include/itemlibraryinfo.h index b7f67259782..9e26d8a3c22 100644 --- a/src/plugins/qmldesigner/designercore/include/itemlibraryinfo.h +++ b/src/plugins/qmldesigner/designercore/include/itemlibraryinfo.h @@ -69,6 +69,7 @@ public: QString qmlSource() const; QString requiredImport() const; QString customComponentSource() const; + QStringList extraFilePaths() const; using Property = QmlDesigner::PropertyContainer; @@ -86,6 +87,7 @@ public: void setRequiredImport(const QString &requiredImport); void addHints(const QHash &hints); void setCustomComponentSource(const QString &source); + void addExtraFilePath(const QString &extraFile); private: std::shared_ptr m_data; diff --git a/src/plugins/qmldesigner/designercore/include/metainforeader.h b/src/plugins/qmldesigner/designercore/include/metainforeader.h index eb725b5f863..f14336b4a17 100644 --- a/src/plugins/qmldesigner/designercore/include/metainforeader.h +++ b/src/plugins/qmldesigner/designercore/include/metainforeader.h @@ -69,7 +69,8 @@ private: ParsingItemLibrary, ParsingHints, ParsingProperty, - ParsingQmlSource + ParsingQmlSource, + ParsingExtraFile }; ParserSate readDocument(const QString &name); @@ -79,12 +80,14 @@ private: ParserSate readItemLibraryEntryElement(const QString &name); ParserSate readPropertyElement(const QString &name); ParserSate readQmlSourceElement(const QString &name); + ParserSate readExtraFileElement(const QString &name); void readTypeProperty(const QString &name, const QVariant &value); void readImportsProperty(const QString &name, const QVariant &value); void readItemLibraryEntryProperty(const QString &name, const QVariant &value); void readPropertyProperty(const QString &name, const QVariant &value); void readQmlSourceProperty(const QString &name, const QVariant &value); + void readExtraFileProperty(const QString &name, const QVariant &value); void readHint(const QString &name, const QVariant &value); void setVersion(const QString &versionNumber); diff --git a/src/plugins/qmldesigner/designercore/metainfo/itemlibraryinfo.cpp b/src/plugins/qmldesigner/designercore/metainfo/itemlibraryinfo.cpp index 2c60f694a0c..ccda886fdba 100644 --- a/src/plugins/qmldesigner/designercore/metainfo/itemlibraryinfo.cpp +++ b/src/plugins/qmldesigner/designercore/metainfo/itemlibraryinfo.cpp @@ -51,6 +51,7 @@ public: QString requiredImport; QHash hints; QString customComponentSource; + QStringList extraFilePaths; }; } // namespace Internal @@ -110,6 +111,11 @@ QString ItemLibraryEntry::customComponentSource() const return m_data->customComponentSource; } +QStringList ItemLibraryEntry::extraFilePaths() const +{ + return m_data->extraFilePaths; +} + int ItemLibraryEntry::majorVersion() const { return m_data->majorVersion; @@ -189,6 +195,11 @@ void ItemLibraryEntry::setCustomComponentSource(const QString &source) m_data->customComponentSource = source; } +void ItemLibraryEntry::addExtraFilePath(const QString &extraFile) +{ + m_data->extraFilePaths.append(extraFile); +} + void ItemLibraryEntry::addProperty(PropertyName &name, QString &type, QVariant &value) { Property property; @@ -212,6 +223,7 @@ QDataStream& operator<<(QDataStream& stream, const ItemLibraryEntry &itemLibrary stream << itemLibraryEntry.m_data->qml; stream << itemLibraryEntry.m_data->qmlSource; stream << itemLibraryEntry.m_data->customComponentSource; + stream << itemLibraryEntry.m_data->extraFilePaths; return stream; } @@ -236,6 +248,7 @@ QDataStream& operator>>(QDataStream& stream, ItemLibraryEntry &itemLibraryEntry) stream >> itemLibraryEntry.m_data->qml; stream >> itemLibraryEntry.m_data->qmlSource; stream >> itemLibraryEntry.m_data->customComponentSource; + stream >> itemLibraryEntry.m_data->extraFilePaths; return stream; } @@ -256,6 +269,7 @@ QDebug operator<<(QDebug debug, const ItemLibraryEntry &itemLibraryEntry) debug << itemLibraryEntry.m_data->qml; debug << itemLibraryEntry.m_data->qmlSource; debug << itemLibraryEntry.m_data->customComponentSource; + debug << itemLibraryEntry.m_data->extraFilePaths; return debug.space(); } diff --git a/src/plugins/qmldesigner/designercore/metainfo/metainforeader.cpp b/src/plugins/qmldesigner/designercore/metainfo/metainforeader.cpp index be4953de0d1..cfb35aac772 100644 --- a/src/plugins/qmldesigner/designercore/metainfo/metainforeader.cpp +++ b/src/plugins/qmldesigner/designercore/metainfo/metainforeader.cpp @@ -45,6 +45,7 @@ const QString ItemLibraryEntryElementName = QStringLiteral("ItemLibraryEntry"); const QString HintsElementName = QStringLiteral("Hints"); const QString QmlSourceElementName = QStringLiteral("QmlSource"); const QString PropertyElementName = QStringLiteral("Property"); +const QString ExtraFileElementName = QStringLiteral("ExtraFile"); MetaInfoReader::MetaInfoReader(const MetaInfo &metaInfo) : m_parserState(Undefined), @@ -93,6 +94,7 @@ void MetaInfoReader::elementStart(const QString &name) case ParsingItemLibrary: setParserState(readItemLibraryEntryElement(name)); break; case ParsingProperty: setParserState(readPropertyElement(name)); break; case ParsingQmlSource: setParserState(readQmlSourceElement(name)); break; + case ParsingExtraFile: setParserState(readExtraFileElement(name)); break; case ParsingHints: case Finished: case Undefined: setParserState(Error); @@ -112,6 +114,7 @@ void MetaInfoReader::elementEnd() case ParsingHints: setParserState(ParsingType); break; case ParsingProperty: insertProperty(); setParserState(ParsingItemLibrary); break; case ParsingQmlSource: setParserState(ParsingItemLibrary); break; + case ParsingExtraFile: setParserState(ParsingItemLibrary); break; case ParsingDocument: case Finished: case Undefined: setParserState(Error); @@ -129,6 +132,7 @@ void MetaInfoReader::propertyDefinition(const QString &name, const QVariant &val case ParsingItemLibrary: readItemLibraryEntryProperty(name, value); break; case ParsingProperty: readPropertyProperty(name, value); break; case ParsingQmlSource: readQmlSourceProperty(name, value); break; + case ParsingExtraFile: readExtraFileProperty(name, value); break; case ParsingMetaInfo: addError(tr("No property definition allowed."), currentSourceLocation()); break; case ParsingDocument: case ParsingHints: readHint(name, value); break; @@ -194,6 +198,8 @@ MetaInfoReader::ParserSate MetaInfoReader::readItemLibraryEntryElement(const QSt m_currentPropertyType.clear(); m_currentPropertyValue = QVariant(); return ParsingProperty; + } else if (name == ExtraFileElementName) { + return ParsingExtraFile; } else { addError(tr("Invalid type %1").arg(name), currentSourceLocation()); return Error; @@ -212,6 +218,12 @@ MetaInfoReader::ParserSate MetaInfoReader::readQmlSourceElement(const QString &n return Error; } +MetaInfoReader::ParserSate MetaInfoReader::readExtraFileElement(const QString &name) +{ + addError(tr("Invalid type %1").arg(name), currentSourceLocation()); + return Error; +} + void MetaInfoReader::readImportsProperty(const QString &name, const QVariant &value) { const auto values = value.toStringList(); @@ -298,6 +310,16 @@ void MetaInfoReader::readQmlSourceProperty(const QString &name, const QVariant & } } +void MetaInfoReader::readExtraFileProperty(const QString &name, const QVariant &value) +{ + if (name == QLatin1String("source")) { + m_currentEntry.addExtraFilePath(absoluteFilePathForDocument(value.toString())); + } else { + addError(tr("Unknown property for ExtraFile %1").arg(name), currentSourceLocation()); + setParserState(Error); + } +} + void MetaInfoReader::readHint(const QString &name, const QVariant &value) { m_currentHints.insert(name, value.toString());