/**************************************************************************** ** ** Copyright (C) 2016 The Qt Company Ltd. ** Contact: https://www.qt.io/licensing/ ** ** This file is part of Qt Creator. ** ** Commercial License Usage ** Licensees holding valid commercial Qt licenses may use this file in ** accordance with the commercial license agreement provided with the ** Software or, alternatively, in accordance with the terms contained in ** a written agreement between you and The Qt Company. For licensing terms ** and conditions see https://www.qt.io/terms-conditions. For further ** information use the contact form at https://www.qt.io/contact-us. ** ** GNU General Public License Usage ** Alternatively, this file may be used under the terms of the GNU ** General Public License version 3 as published by the Free Software ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT ** included in the packaging of this file. Please review the following ** information to ensure the GNU General Public License requirements will ** be met: https://www.gnu.org/licenses/gpl-3.0.html. ** ****************************************************************************/ #pragma once #include "projectexplorer_export.h" #include "kit.h" #include "subscription.h" #include #include #include #include #include #include namespace Core { class Context; } namespace Utils { class MacroExpander; } namespace ProjectExplorer { class BuildInfo; class ContainerNode; class EditorConfiguration; class FolderNode; class NamedWidget; class Node; class ProjectConfiguration; class ProjectImporter; class ProjectNode; class ProjectPrivate; class Target; // Auto-registers with the DocumentManager if a callback is set! class PROJECTEXPLORER_EXPORT ProjectDocument : public Core::IDocument { public: using ProjectCallback = std::function; ProjectDocument(const QString &mimeType, const Utils::FileName &fileName, const ProjectCallback &callback = {}); Core::IDocument::ReloadBehavior reloadBehavior(Core::IDocument::ChangeTrigger state, Core::IDocument::ChangeType type) const final; bool reload(QString *errorString, Core::IDocument::ReloadFlag flag, Core::IDocument::ChangeType type) final; private: ProjectCallback m_callback; }; // Documentation inside. class PROJECTEXPLORER_EXPORT Project : public QObject { friend class SessionManager; // for setActiveTarget friend class ProjectExplorerPlugin; // for projectLoaded Q_OBJECT public: // Roles to be implemented by all models that are exported via model() enum ModelRoles { // Absolute file path FilePathRole = QFileSystemModel::FilePathRole, isParsingRole }; Project(const QString &mimeType, const Utils::FileName &fileName, const ProjectDocument::ProjectCallback &callback = {}); ~Project() override; QString displayName() const; Core::Id id() const; QString mimeType() const; Core::IDocument *document() const; Utils::FileName projectFilePath() const; Utils::FileName projectDirectory() const; Utils::FileName rootProjectDirectory() const; static Utils::FileName projectDirectory(const Utils::FileName &top); virtual ProjectNode *rootProjectNode() const; ContainerNode *containerNode() const; bool hasActiveBuildSettings() const; // EditorConfiguration: EditorConfiguration *editorConfiguration() const; // Target: void addTarget(std::unique_ptr &&target); bool removeTarget(Target *target); QList targets() const; // Note: activeTarget can be 0 (if no targets are defined). Target *activeTarget() const; Target *target(Core::Id id) const; Target *target(Kit *k) const; virtual QList projectIssues(const Kit *k) const; std::unique_ptr createTarget(Kit *k); static bool copySteps(Target *sourceTarget, Target *newTarget); std::unique_ptr restoreTarget(const QVariantMap &data); void saveSettings(); enum class RestoreResult { Ok, Error, UserAbort }; RestoreResult restoreSettings(QString *errorMessage); using NodeMatcher = std::function; static const NodeMatcher AllFiles; static const NodeMatcher SourceFiles; static const NodeMatcher GeneratedFiles; Utils::FileNameList files(const NodeMatcher &matcher) const; virtual QStringList filesGeneratedFrom(const QString &sourceFile) const; bool isKnownFile(const Utils::FileName &filename) const; virtual QVariantMap toMap() const; Core::Context projectContext() const; Core::Context projectLanguages() const; QVariant namedSettings(const QString &name) const; void setNamedSettings(const QString &name, const QVariant &value); virtual bool needsConfiguration() const; virtual bool needsBuildConfigurations() const; virtual void configureAsExampleProject(const QSet &platforms); virtual ProjectImporter *projectImporter() const; Kit::Predicate requiredKitPredicate() const; Kit::Predicate preferredKitPredicate() const; virtual bool needsSpecialDeployment() const; // The build system is able to report all executables that can be built, independent // of configuration. virtual bool knowsAllBuildExecutables() const; void setup(const QList &infoList); Utils::MacroExpander *macroExpander() const; virtual QVariant additionalData(Core::Id id, const Target *target) const; bool isParsing() const; bool hasParsingData() const; const ProjectNode *findNodeForBuildKey(const QString &buildKey) const; template void subscribeSignal(void (S::*sig)(Args1...), R*recv, T (R::*sl)(Args2...)) { new Internal::ProjectSubscription([sig, recv, sl, this](ProjectConfiguration *pc) { if (S* sender = qobject_cast(pc)) return connect(sender, sig, recv, sl); return QMetaObject::Connection(); }, recv, this); } template void subscribeSignal(void (S::*sig)(Args1...), R*recv, T sl) { new Internal::ProjectSubscription([sig, recv, sl, this](ProjectConfiguration *pc) { if (S* sender = qobject_cast(pc)) return connect(sender, sig, recv, sl); return QMetaObject::Connection(); }, recv, this); } signals: void displayNameChanged(); void fileListChanged(); // Note: activeTarget can be 0 (if no targets are defined). void activeTargetChanged(ProjectExplorer::Target *target); void aboutToRemoveProjectConfiguration(ProjectExplorer::ProjectConfiguration *pc); void removedProjectConfiguration(ProjectExplorer::ProjectConfiguration *pc); void addedProjectConfiguration(ProjectExplorer::ProjectConfiguration *pc); // *ANY* active project configuration changed somewhere in the tree. This might not be // the one that would get started right now, since some part of the tree in between might // not be active. void activeProjectConfigurationChanged(ProjectExplorer::ProjectConfiguration *pc); void aboutToRemoveTarget(ProjectExplorer::Target *target); void removedTarget(ProjectExplorer::Target *target); void addedTarget(ProjectExplorer::Target *target); void settingsLoaded(); void aboutToSaveSettings(); void projectLanguagesUpdated(); void parsingStarted(); void parsingFinished(bool success); protected: virtual RestoreResult fromMap(const QVariantMap &map, QString *errorMessage); void createTargetFromMap(const QVariantMap &map, int index); virtual bool setupTarget(Target *t); // Helper methods to manage parsing state and signalling // Call in GUI thread before the actual parsing starts void emitParsingStarted(); // Call in GUI thread right after the actual parsing is done void emitParsingFinished(bool success); void setDisplayName(const QString &name); // Used to pre-check kits in the TargetSetupPage. RequiredKitPredicate // is used to select kits available in the TargetSetupPage void setPreferredKitPredicate(const Kit::Predicate &predicate); // The predicate used to select kits available in TargetSetupPage. void setRequiredKitPredicate(const Kit::Predicate &predicate); void setId(Core::Id id); void setRootProjectNode(std::unique_ptr &&root); // takes ownership! void setProjectLanguages(Core::Context language); void addProjectLanguage(Core::Id id); void removeProjectLanguage(Core::Id id); void setProjectLanguage(Core::Id id, bool enabled); virtual void projectLoaded(); // Called when the project is fully loaded. static ProjectExplorer::Task createProjectTask(ProjectExplorer::Task::TaskType type, const QString &description); private: void handleSubTreeChanged(FolderNode *node); void setActiveTarget(Target *target); ProjectPrivate *d; friend class ContainerNode; }; } // namespace ProjectExplorer Q_DECLARE_METATYPE(ProjectExplorer::Project *)