From c17bce14cffbb230a98f0ae724b13da5d9d0e1df Mon Sep 17 00:00:00 2001 From: Daniel Teske <daniel.teske@digia.com> Date: Mon, 3 Feb 2014 14:45:28 +0100 Subject: [PATCH] ProjectNodes: Move supportedActions to Node By default this simply calls the parent's supportedActions. Most changes are due to the enum moving. Change-Id: I25bf21b712cca48450014dbb0f748ac0c461e029 Reviewed-by: Tobias Hunger <tobias.hunger@digia.com> Reviewed-by: Daniel Teske <daniel.teske@digia.com> --- .../autotoolsprojectnode.cpp | 4 +- .../autotoolsprojectnode.h | 2 +- .../cmakeprojectmanager/cmakeprojectnodes.cpp | 4 +- .../cmakeprojectmanager/cmakeprojectnodes.h | 2 +- .../genericprojectnodes.cpp | 2 +- .../genericprojectnodes.h | 2 +- .../projectexplorer/projectexplorer.cpp | 24 +++++----- .../projectfilewizardextension.cpp | 22 ++++----- src/plugins/projectexplorer/projectmodels.cpp | 2 +- src/plugins/projectexplorer/projectnodes.cpp | 11 +++++ src/plugins/projectexplorer/projectnodes.h | 48 ++++++++++--------- src/plugins/qbsprojectmanager/qbsnodes.cpp | 4 +- src/plugins/qbsprojectmanager/qbsnodes.h | 2 +- .../qmakeprojectmanager/qmakenodes.cpp | 18 +++---- src/plugins/qmakeprojectmanager/qmakenodes.h | 2 +- .../qmlprojectmanager/qmlprojectnodes.cpp | 10 ++-- .../qmlprojectmanager/qmlprojectnodes.h | 2 +- 17 files changed, 87 insertions(+), 74 deletions(-) diff --git a/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.cpp b/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.cpp index c646dbad784..355720d1693 100644 --- a/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.cpp +++ b/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.cpp @@ -50,10 +50,10 @@ bool AutotoolsProjectNode::hasBuildTargets() const return true; } -QList<ProjectNode::ProjectAction> AutotoolsProjectNode::supportedActions(Node *node) const +QList<ProjectExplorer::ProjectAction> AutotoolsProjectNode::supportedActions(Node *node) const { Q_UNUSED(node); - return QList<ProjectNode::ProjectAction>(); + return QList<ProjectExplorer::ProjectAction>(); } bool AutotoolsProjectNode::canAddSubProject(const QString &proFilePath) const diff --git a/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.h b/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.h index 82564ec115d..a96e1485a27 100644 --- a/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.h +++ b/src/plugins/autotoolsprojectmanager/autotoolsprojectnode.h @@ -58,7 +58,7 @@ public: AutotoolsProjectNode(AutotoolsProject *project, Core::IDocument *projectFile); bool hasBuildTargets() const; - QList<ProjectExplorer::ProjectNode::ProjectAction> supportedActions(Node *node) const; + QList<ProjectExplorer::ProjectAction> supportedActions(Node *node) const; bool canAddSubProject(const QString &proFilePath) const; bool addSubProjects(const QStringList &proFilePaths); bool removeSubProjects(const QStringList &proFilePaths); diff --git a/src/plugins/cmakeprojectmanager/cmakeprojectnodes.cpp b/src/plugins/cmakeprojectmanager/cmakeprojectnodes.cpp index 1d7ccdabed1..405b598990f 100644 --- a/src/plugins/cmakeprojectmanager/cmakeprojectnodes.cpp +++ b/src/plugins/cmakeprojectmanager/cmakeprojectnodes.cpp @@ -43,10 +43,10 @@ bool CMakeProjectNode::hasBuildTargets() const return true; } -QList<ProjectExplorer::ProjectNode::ProjectAction> CMakeProjectNode::supportedActions(Node *node) const +QList<ProjectExplorer::ProjectAction> CMakeProjectNode::supportedActions(Node *node) const { Q_UNUSED(node); - return QList<ProjectAction>(); + return QList<ProjectExplorer::ProjectAction>(); } bool CMakeProjectNode::canAddSubProject(const QString &proFilePath) const diff --git a/src/plugins/cmakeprojectmanager/cmakeprojectnodes.h b/src/plugins/cmakeprojectmanager/cmakeprojectnodes.h index adac01ec8af..d34989ef223 100644 --- a/src/plugins/cmakeprojectmanager/cmakeprojectnodes.h +++ b/src/plugins/cmakeprojectmanager/cmakeprojectnodes.h @@ -42,7 +42,7 @@ class CMakeProjectNode : public ProjectExplorer::ProjectNode public: CMakeProjectNode(const QString &fileName); virtual bool hasBuildTargets() const; - virtual QList<ProjectExplorer::ProjectNode::ProjectAction> supportedActions(Node *node) const; + virtual QList<ProjectExplorer::ProjectAction> supportedActions(Node *node) const; virtual bool canAddSubProject(const QString &proFilePath) const; diff --git a/src/plugins/genericprojectmanager/genericprojectnodes.cpp b/src/plugins/genericprojectmanager/genericprojectnodes.cpp index 6e7c1dde763..66a80f90400 100644 --- a/src/plugins/genericprojectmanager/genericprojectnodes.cpp +++ b/src/plugins/genericprojectmanager/genericprojectnodes.cpp @@ -231,7 +231,7 @@ bool GenericProjectNode::hasBuildTargets() const return true; } -QList<ProjectNode::ProjectAction> GenericProjectNode::supportedActions(Node *node) const +QList<ProjectExplorer::ProjectAction> GenericProjectNode::supportedActions(Node *node) const { Q_UNUSED(node); return QList<ProjectAction>() diff --git a/src/plugins/genericprojectmanager/genericprojectnodes.h b/src/plugins/genericprojectmanager/genericprojectnodes.h index 9dc6c32bf87..a7c25c0b304 100644 --- a/src/plugins/genericprojectmanager/genericprojectnodes.h +++ b/src/plugins/genericprojectmanager/genericprojectnodes.h @@ -53,7 +53,7 @@ public: bool hasBuildTargets() const; - QList<ProjectExplorer::ProjectNode::ProjectAction> supportedActions(Node *node) const; + QList<ProjectExplorer::ProjectAction> supportedActions(Node *node) const; bool canAddSubProject(const QString &proFilePath) const; diff --git a/src/plugins/projectexplorer/projectexplorer.cpp b/src/plugins/projectexplorer/projectexplorer.cpp index 32f0f2aeaad..3c0f05368fa 100644 --- a/src/plugins/projectexplorer/projectexplorer.cpp +++ b/src/plugins/projectexplorer/projectexplorer.cpp @@ -2680,8 +2680,8 @@ void ProjectExplorerPlugin::updateContextMenuActions() runMenu->menu()->clear(); if (d->m_currentNode && d->m_currentNode->projectNode()) { - QList<ProjectNode::ProjectAction> actions = - d->m_currentNode->projectNode()->supportedActions(d->m_currentNode); + QList<ProjectExplorer::ProjectAction> actions = + d->m_currentNode->supportedActions(d->m_currentNode); if (ProjectNode *pn = qobject_cast<ProjectNode *>(d->m_currentNode)) { if (pn == d->m_currentProject->rootProjectNode()) { @@ -2705,26 +2705,26 @@ void ProjectExplorerPlugin::updateContextMenuActions() } if (qobject_cast<FolderNode*>(d->m_currentNode)) { // Also handles ProjectNode - d->m_addNewFileAction->setEnabled(actions.contains(ProjectNode::AddNewFile)); + d->m_addNewFileAction->setEnabled(actions.contains(ProjectExplorer::AddNewFile)); d->m_addNewSubprojectAction->setEnabled(d->m_currentNode->nodeType() == ProjectNodeType - && actions.contains(ProjectNode::AddSubProject)); - d->m_addExistingFilesAction->setEnabled(actions.contains(ProjectNode::AddExistingFile)); - d->m_addExistingDirectoryAction->setEnabled(actions.contains(ProjectNode::AddExistingDirectory)); - d->m_renameFileAction->setEnabled(actions.contains(ProjectNode::Rename)); + && actions.contains(ProjectExplorer::AddSubProject)); + d->m_addExistingFilesAction->setEnabled(actions.contains(ProjectExplorer::AddExistingFile)); + d->m_addExistingDirectoryAction->setEnabled(actions.contains(ProjectExplorer::AddExistingDirectory)); + d->m_renameFileAction->setEnabled(actions.contains(ProjectExplorer::Rename)); } else if (qobject_cast<FileNode*>(d->m_currentNode)) { // Enable and show remove / delete in magic ways: // If both are disabled show Remove // If both are enabled show both (can't happen atm) // If only removeFile is enabled only show it // If only deleteFile is enable only show it - bool enableRemove = actions.contains(ProjectNode::RemoveFile); + bool enableRemove = actions.contains(ProjectExplorer::RemoveFile); d->m_removeFileAction->setEnabled(enableRemove); - bool enableDelete = actions.contains(ProjectNode::EraseFile); + bool enableDelete = actions.contains(ProjectExplorer::EraseFile); d->m_deleteFileAction->setEnabled(enableDelete); d->m_deleteFileAction->setVisible(enableDelete); d->m_removeFileAction->setVisible(!enableDelete || enableRemove); - d->m_renameFileAction->setEnabled(actions.contains(ProjectNode::Rename)); + d->m_renameFileAction->setEnabled(actions.contains(ProjectExplorer::Rename)); } } } @@ -2791,8 +2791,8 @@ void ProjectExplorerPlugin::addNewSubproject() QString location = directoryFor(d->m_currentNode); if (d->m_currentNode->nodeType() == ProjectNodeType - && d->m_currentNode->projectNode()->supportedActions( - d->m_currentNode->projectNode()).contains(ProjectNode::AddSubProject)) { + && d->m_currentNode->supportedActions( + d->m_currentNode).contains(ProjectExplorer::AddSubProject)) { QVariantMap map; map.insert(QLatin1String(Constants::PREFERED_PROJECT_NODE), d->m_currentNode->projectNode()->path()); if (d->m_currentProject) { diff --git a/src/plugins/projectexplorer/projectfilewizardextension.cpp b/src/plugins/projectexplorer/projectfilewizardextension.cpp index a67a87fe47f..1e843ae7281 100644 --- a/src/plugins/projectexplorer/projectfilewizardextension.cpp +++ b/src/plugins/projectexplorer/projectfilewizardextension.cpp @@ -94,20 +94,20 @@ namespace Internal { class AllProjectNodesVisitor : public NodesVisitor { public: - AllProjectNodesVisitor(ProjectNode::ProjectAction action) + AllProjectNodesVisitor(ProjectExplorer::ProjectAction action) : m_action(action) {} - static ProjectNodeList allProjects(ProjectNode::ProjectAction action); + static ProjectNodeList allProjects(ProjectExplorer::ProjectAction action); virtual void visitProjectNode(ProjectNode *node); private: ProjectNodeList m_projectNodes; - ProjectNode::ProjectAction m_action; + ProjectExplorer::ProjectAction m_action; }; -ProjectNodeList AllProjectNodesVisitor::allProjects(ProjectNode::ProjectAction action) +ProjectNodeList AllProjectNodesVisitor::allProjects(ProjectExplorer::ProjectAction action) { AllProjectNodesVisitor visitor(action); SessionManager::sessionNode()->accept(&visitor); @@ -397,7 +397,7 @@ QList<QWizardPage *> ProjectFileWizardExtension::extensionPages(const IWizard *w static inline void getProjectChoicesAndToolTips(QStringList *projectChoicesParam, QStringList *projectToolTipsParam, - ProjectNode::ProjectAction *projectActionParam, + ProjectExplorer::ProjectAction *projectActionParam, const QString &generatedProjectFilePath, ProjectWizardContext *context) { @@ -413,12 +413,12 @@ static inline void getProjectChoicesAndToolTips(QStringList *projectChoicesParam // via Map. ProjectEntryMap entryMap; - ProjectNode::ProjectAction projectAction = + ProjectExplorer::ProjectAction projectAction = context->wizard->kind() == IWizard::ProjectWizard - ? ProjectNode::AddSubProject : ProjectNode::AddNewFile; + ? ProjectExplorer::AddSubProject : ProjectExplorer::AddNewFile; foreach (ProjectNode *n, AllProjectNodesVisitor::allProjects(projectAction)) { - if (projectAction == ProjectNode::AddNewFile - || (projectAction == ProjectNode::AddSubProject + if (projectAction == ProjectExplorer::AddNewFile + || (projectAction == ProjectExplorer::AddSubProject && (generatedProjectFilePath.isEmpty() ? true : n->canAddSubProject(generatedProjectFilePath)))) entryMap.insert(ProjectEntry(n), true); } @@ -441,14 +441,14 @@ void ProjectFileWizardExtension::initProjectChoices(const QString &generatedProj { QStringList projectChoices; QStringList projectToolTips; - ProjectNode::ProjectAction projectAction; + ProjectExplorer::ProjectAction projectAction; getProjectChoicesAndToolTips(&projectChoices, &projectToolTips, &projectAction, generatedProjectFilePath, m_context); m_context->page->setProjects(projectChoices); m_context->page->setProjectToolTips(projectToolTips); - m_context->page->setAddingSubProject(projectAction == ProjectNode::AddSubProject); + m_context->page->setAddingSubProject(projectAction == ProjectExplorer::AddSubProject); } bool ProjectFileWizardExtension::processFiles( diff --git a/src/plugins/projectexplorer/projectmodels.cpp b/src/plugins/projectexplorer/projectmodels.cpp index e899054ec62..e0ba8a81c1b 100644 --- a/src/plugins/projectexplorer/projectmodels.cpp +++ b/src/plugins/projectexplorer/projectmodels.cpp @@ -326,7 +326,7 @@ Qt::ItemFlags FlatModel::flags(const QModelIndex &index) const return 0; // no flags for session node... if (!qobject_cast<ProjectNode *>(node)) { // either folder or file node - if (node->projectNode()->supportedActions(node).contains(ProjectNode::Rename)) + if (node->supportedActions(node).contains(ProjectExplorer::Rename)) f = f | Qt::ItemIsEditable; } } diff --git a/src/plugins/projectexplorer/projectnodes.cpp b/src/plugins/projectexplorer/projectnodes.cpp index a7fdd142314..942f3e814b3 100644 --- a/src/plugins/projectexplorer/projectnodes.cpp +++ b/src/plugins/projectexplorer/projectnodes.cpp @@ -178,6 +178,11 @@ bool Node::isEnabled() const return parentFolderNode()->isEnabled(); } +QList<ProjectAction> Node::supportedActions(Node *node) const +{ + return parentFolderNode()->supportedActions(node); +} + void Node::setNodeType(NodeType type) { m_nodeType = type; @@ -730,6 +735,12 @@ SessionNode::SessionNode(QObject *parentObject) setNodeType(SessionNodeType); } +QList<ProjectAction> SessionNode::supportedActions(Node *node) const +{ + Q_UNUSED(node) + return QList<ProjectAction>(); +} + QList<NodesWatcher*> SessionNode::watchers() const { return m_watchers; diff --git a/src/plugins/projectexplorer/projectnodes.h b/src/plugins/projectexplorer/projectnodes.h index 0b54d56c06d..464f8d37da7 100644 --- a/src/plugins/projectexplorer/projectnodes.h +++ b/src/plugins/projectexplorer/projectnodes.h @@ -66,6 +66,27 @@ enum FileType { FileTypeSize }; +enum ProjectAction { + AddSubProject, + RemoveSubProject, + // Let's the user select to which project file + // the file is added + AddNewFile, + AddExistingFile, + // Add files, which match user defined filters, + // from an existing directory and its subdirectories + AddExistingDirectory, + // Removes a file from the project, optionally also + // delete it on disc + RemoveFile, + // Deletes a file from the file system, informs the project + // that a file was deleted + // DeleteFile is a define on windows... + EraseFile, + Rename, + HasSubProjectRunConfigurations +}; + class Node; class FileNode; class FileContainerNode; @@ -88,6 +109,8 @@ public: virtual QString tooltip() const; virtual bool isEnabled() const; + virtual QList<ProjectAction> supportedActions(Node *node) const; + void setPath(const QString &path); void setLine(int line); void setPathAndLine(const QString &path, int line); @@ -177,27 +200,6 @@ class PROJECTEXPLORER_EXPORT ProjectNode : public FolderNode Q_OBJECT public: - enum ProjectAction { - AddSubProject, - RemoveSubProject, - // Let's the user select to which project file - // the file is added - AddNewFile, - AddExistingFile, - // Add files, which match user defined filters, - // from an existing directory and its subdirectories - AddExistingDirectory, - // Removes a file from the project, optionally also - // delete it on disc - RemoveFile, - // Deletes a file from the file system, informs the project - // that a file was deleted - // DeleteFile is a define on windows... - EraseFile, - Rename, - HasSubProjectRunConfigurations - }; - QString vcsTopic() const; // all subFolders that are projects @@ -209,8 +211,6 @@ public: void hasBuildTargetsChanged(); virtual bool hasBuildTargets() const = 0; - virtual QList<ProjectAction> supportedActions(Node *node) const = 0; - virtual bool canAddSubProject(const QString &proFilePath) const = 0; virtual bool addSubProjects(const QStringList &proFilePaths) = 0; @@ -270,6 +270,8 @@ class PROJECTEXPLORER_EXPORT SessionNode : public FolderNode { public: SessionNode(QObject *parentObject); + QList<ProjectAction> supportedActions(Node *node) const; + QList<ProjectNode*> projectNodes() const; QList<NodesWatcher*> watchers() const; diff --git a/src/plugins/qbsprojectmanager/qbsnodes.cpp b/src/plugins/qbsprojectmanager/qbsnodes.cpp index 6da2dea773d..8a26cd47adf 100644 --- a/src/plugins/qbsprojectmanager/qbsnodes.cpp +++ b/src/plugins/qbsprojectmanager/qbsnodes.cpp @@ -252,10 +252,10 @@ bool QbsBaseProjectNode::hasBuildTargets() const return false; } -QList<ProjectExplorer::ProjectNode::ProjectAction> QbsBaseProjectNode::supportedActions(ProjectExplorer::Node *node) const +QList<ProjectExplorer::ProjectAction> QbsBaseProjectNode::supportedActions(ProjectExplorer::Node *node) const { Q_UNUSED(node); - return QList<ProjectExplorer::ProjectNode::ProjectAction>(); + return QList<ProjectExplorer::ProjectAction>(); } bool QbsBaseProjectNode::canAddSubProject(const QString &proFilePath) const diff --git a/src/plugins/qbsprojectmanager/qbsnodes.h b/src/plugins/qbsprojectmanager/qbsnodes.h index 49502f59f4c..fe8ed9a65da 100644 --- a/src/plugins/qbsprojectmanager/qbsnodes.h +++ b/src/plugins/qbsprojectmanager/qbsnodes.h @@ -76,7 +76,7 @@ public: bool hasBuildTargets() const; - QList<ProjectAction> supportedActions(Node *node) const; + QList<ProjectExplorer::ProjectAction> supportedActions(Node *node) const; bool canAddSubProject(const QString &proFilePath) const; diff --git a/src/plugins/qmakeprojectmanager/qmakenodes.cpp b/src/plugins/qmakeprojectmanager/qmakenodes.cpp index 00d3b2548f0..c8929967035 100644 --- a/src/plugins/qmakeprojectmanager/qmakenodes.cpp +++ b/src/plugins/qmakeprojectmanager/qmakenodes.cpp @@ -825,9 +825,9 @@ void QmakePriFileNode::setIncludedInExactParse(bool b) m_includedInExactParse = b; } -QList<ProjectNode::ProjectAction> QmakePriFileNode::supportedActions(Node *node) const +QList<ProjectExplorer::ProjectAction> QmakePriFileNode::supportedActions(Node *node) const { - QList<ProjectAction> actions; + QList<ProjectExplorer::ProjectAction> actions; const FolderNode *folderNode = this; const QmakeProFileNode *proFileNode; @@ -843,11 +843,11 @@ QList<ProjectNode::ProjectAction> QmakePriFileNode::supportedActions(Node *node) // projects (e.g. cpp). It'd be nice if the "add" action could // work on a subset of the file types according to project type. - actions << AddNewFile; + actions << ProjectExplorer::AddNewFile; if (m_recursiveEnumerateFiles.contains(Utils::FileName::fromString(node->path()))) - actions << EraseFile; + actions << ProjectExplorer::EraseFile; else - actions << RemoveFile; + actions << ProjectExplorer::RemoveFile; bool addExistingFiles = true; if (node->nodeType() == ProjectExplorer::VirtualFolderNodeType) { @@ -865,12 +865,12 @@ QList<ProjectNode::ProjectAction> QmakePriFileNode::supportedActions(Node *node) addExistingFiles = addExistingFiles && !deploysFolder(node->path()); if (addExistingFiles) - actions << AddExistingFile << AddExistingDirectory; + actions << ProjectExplorer::AddExistingFile << ProjectExplorer::AddExistingDirectory; break; } case SubDirsTemplate: - actions << AddSubProject << RemoveSubProject; + actions << ProjectExplorer::AddSubProject << ProjectExplorer::RemoveSubProject; break; default: break; @@ -878,13 +878,13 @@ QList<ProjectNode::ProjectAction> QmakePriFileNode::supportedActions(Node *node) ProjectExplorer::FileNode *fileNode = qobject_cast<FileNode *>(node); if (fileNode && fileNode->fileType() != ProjectExplorer::ProjectFileType) - actions << Rename; + actions << ProjectExplorer::Rename; ProjectExplorer::Target *target = m_project->activeTarget(); QmakeRunConfigurationFactory *factory = QmakeRunConfigurationFactory::find(target); if (factory && !factory->runConfigurationsForNode(target, node).isEmpty()) - actions << HasSubProjectRunConfigurations; + actions << ProjectExplorer::HasSubProjectRunConfigurations; return actions; } diff --git a/src/plugins/qmakeprojectmanager/qmakenodes.h b/src/plugins/qmakeprojectmanager/qmakenodes.h index 6856d7d60a4..8775a1d7d16 100644 --- a/src/plugins/qmakeprojectmanager/qmakenodes.h +++ b/src/plugins/qmakeprojectmanager/qmakenodes.h @@ -145,7 +145,7 @@ public: // ProjectNode interface - QList<ProjectAction> supportedActions(Node *node) const; + QList<ProjectExplorer::ProjectAction> supportedActions(Node *node) const; bool hasBuildTargets() const { return false; } diff --git a/src/plugins/qmlprojectmanager/qmlprojectnodes.cpp b/src/plugins/qmlprojectmanager/qmlprojectnodes.cpp index 3e20f653e73..55462b5e157 100644 --- a/src/plugins/qmlprojectmanager/qmlprojectnodes.cpp +++ b/src/plugins/qmlprojectmanager/qmlprojectnodes.cpp @@ -170,16 +170,16 @@ bool QmlProjectNode::hasBuildTargets() const return true; } -QList<ProjectExplorer::ProjectNode::ProjectAction> QmlProjectNode::supportedActions(Node *node) const +QList<ProjectExplorer::ProjectAction> QmlProjectNode::supportedActions(Node *node) const { Q_UNUSED(node); - QList<ProjectAction> actions; - actions.append(AddNewFile); - actions.append(EraseFile); + QList<ProjectExplorer::ProjectAction> actions; + actions.append(ProjectExplorer::AddNewFile); + actions.append(ProjectExplorer::EraseFile); if (node->nodeType() == ProjectExplorer::FileNodeType) { ProjectExplorer::FileNode *fileNode = static_cast<ProjectExplorer::FileNode *>(node); if (fileNode->fileType() != ProjectExplorer::ProjectFileType) - actions.append(Rename); + actions.append(ProjectExplorer::Rename); } return actions; } diff --git a/src/plugins/qmlprojectmanager/qmlprojectnodes.h b/src/plugins/qmlprojectmanager/qmlprojectnodes.h index 6dedae8a96f..d47f7fb6d7f 100644 --- a/src/plugins/qmlprojectmanager/qmlprojectnodes.h +++ b/src/plugins/qmlprojectmanager/qmlprojectnodes.h @@ -54,7 +54,7 @@ public: virtual bool hasBuildTargets() const; - virtual QList<ProjectExplorer::ProjectNode::ProjectAction> supportedActions(Node *node) const; + virtual QList<ProjectExplorer::ProjectAction> supportedActions(Node *node) const; virtual bool canAddSubProject(const QString &proFilePath) const; -- GitLab