diff --git a/src/plugins/projectexplorer/abstractprocessstep.cpp b/src/plugins/projectexplorer/abstractprocessstep.cpp index 13e5d00d33a..550ecff2812 100644 --- a/src/plugins/projectexplorer/abstractprocessstep.cpp +++ b/src/plugins/projectexplorer/abstractprocessstep.cpp @@ -72,7 +72,6 @@ public: Private(AbstractProcessStep *q) : q(q) {} AbstractProcessStep *q; - std::unique_ptr m_taskTree; ProcessParameters m_param; ProcessParameters *m_displayedParams = &m_param; std::function m_commandLineProvider; @@ -144,7 +143,7 @@ void AbstractProcessStep::setWorkingDirectoryProvider(const std::functionm_taskTree) + if (!BuildStep::init()) return false; if (!setupProcessParameters(processParameters())) @@ -163,30 +162,6 @@ void AbstractProcessStep::setupOutputFormatter(OutputFormatter *formatter) BuildStep::setupOutputFormatter(formatter); } -/*! - Reimplemented from BuildStep::init(). You need to call this from - YourBuildStep::run(). -*/ - -void AbstractProcessStep::doRun() -{ - QTC_ASSERT(!d->m_taskTree, return); - - d->m_taskTree.reset(new TaskTree({runRecipe()})); - connect(d->m_taskTree.get(), &TaskTree::progressValueChanged, this, [this](int value) { - emit progress(qRound(double(value) * 100 / std::max(d->m_taskTree->progressMaximum(), 1)), {}); - }); - connect(d->m_taskTree.get(), &TaskTree::done, this, [this] { - d->m_taskTree.release()->deleteLater(); - emit finished(true); - }); - connect(d->m_taskTree.get(), &TaskTree::errorOccurred, this, [this] { - d->m_taskTree.release()->deleteLater(); - emit finished(false); - }); - d->m_taskTree->start(); -} - GroupItem AbstractProcessStep::defaultProcessTask() { const auto onSetup = [this](Process &process) { @@ -269,16 +244,6 @@ void AbstractProcessStep::setLowPriority() d->m_lowPriority = true; } -void AbstractProcessStep::doCancel() -{ - if (!d->m_taskTree) - return; - - d->m_taskTree.reset(); - emit addOutput(Tr::tr("The build step was ended forcefully."), OutputFormat::ErrorMessage); - emit finished(false); -} - ProcessParameters *AbstractProcessStep::processParameters() { return &d->m_param; diff --git a/src/plugins/projectexplorer/abstractprocessstep.h b/src/plugins/projectexplorer/abstractprocessstep.h index 7b5209a0234..ef52e648c00 100644 --- a/src/plugins/projectexplorer/abstractprocessstep.h +++ b/src/plugins/projectexplorer/abstractprocessstep.h @@ -10,8 +10,6 @@ class CommandLine; class Process; } -namespace Tasking { class GroupItem; } - namespace ProjectExplorer { class ProcessParameters; @@ -39,8 +37,6 @@ protected: bool init() override; void setupOutputFormatter(Utils::OutputFormatter *formatter) override; - void doRun() final; - void doCancel() final; void setLowPriority(); void setDisplayedParameters(ProcessParameters *params); @@ -49,7 +45,7 @@ protected: void handleProcessDone(const Utils::Process &process); private: - virtual Tasking::GroupItem runRecipe(); + Tasking::GroupItem runRecipe() override; class Private; Private *d; diff --git a/src/plugins/projectexplorer/buildstep.cpp b/src/plugins/projectexplorer/buildstep.cpp index d9017ce4a06..20747bf0cb2 100644 --- a/src/plugins/projectexplorer/buildstep.cpp +++ b/src/plugins/projectexplorer/buildstep.cpp @@ -10,9 +10,12 @@ #include "kitinformation.h" #include "project.h" #include "projectexplorerconstants.h" +#include "projectexplorertr.h" #include "sanitizerparser.h" #include "target.h" +#include + #include #include #include @@ -103,6 +106,7 @@ immutable steps are run. The default implementation returns \c false. */ +using namespace Tasking; using namespace Utils; static const char buildStepEnabledKey[] = "ProjectExplorer.BuildStep.Enabled"; @@ -114,6 +118,7 @@ static QList g_buildStepFactories; BuildStep::BuildStep(BuildStepList *bsl, Id id) : ProjectConfiguration(bsl, bsl->target(), id) , m_stepList(bsl) + , m_cancelMessage(Tr::tr("The build step was ended forcefully.")) { connect(this, &ProjectConfiguration::displayNameChanged, this, &BuildStep::updateSummary); @@ -126,6 +131,11 @@ BuildStep::~BuildStep() emit finished(false); } +bool BuildStep::init() +{ + return !m_taskTree; +} + void BuildStep::run() { m_cancelFlag = false; @@ -297,10 +307,44 @@ bool BuildStep::isCanceled() const return m_cancelFlag; } +void BuildStep::setCancelMessage(const QString &message) +{ + m_cancelMessage = message; +} + +Tasking::GroupItem BuildStep::runRecipe() +{ + return Group {}; +} + +void BuildStep::doRun() +{ + QTC_ASSERT(!m_taskTree, return); + + m_taskTree.reset(new TaskTree({runRecipe()})); + connect(m_taskTree.get(), &TaskTree::progressValueChanged, this, [this](int value) { + emit progress(qRound(double(value) * 100 / std::max(m_taskTree->progressMaximum(), 1)), {}); + }); + connect(m_taskTree.get(), &TaskTree::done, this, [this] { + emit finished(true); + m_taskTree.release()->deleteLater(); + }); + connect(m_taskTree.get(), &TaskTree::errorOccurred, this, [this] { + emit finished(false); + m_taskTree.release()->deleteLater(); + }); + m_taskTree->start(); +} + void BuildStep::doCancel() { - QTC_ASSERT(false, qWarning() << "Build step" << displayName() - << "neeeds to implement the doCancel() function"); + if (!m_taskTree) + return; + + m_taskTree.reset(); + if (!m_cancelMessage.isEmpty()) + emit addOutput(m_cancelMessage, OutputFormat::ErrorMessage); + emit finished(false); } void BuildStep::addMacroExpander() diff --git a/src/plugins/projectexplorer/buildstep.h b/src/plugins/projectexplorer/buildstep.h index 8520f851def..ef483f60796 100644 --- a/src/plugins/projectexplorer/buildstep.h +++ b/src/plugins/projectexplorer/buildstep.h @@ -24,6 +24,11 @@ class MacroExpander; class OutputFormatter; } // Utils +namespace Tasking { +class GroupItem; +class TaskTree; +} + namespace ProjectExplorer { class BuildConfiguration; @@ -44,7 +49,7 @@ protected: public: ~BuildStep() override; - virtual bool init() = 0; + virtual bool init(); void run(); void cancel(); @@ -122,13 +127,14 @@ signals: protected: virtual QWidget *createConfigWidget(); - bool isCanceled() const; + void setCancelMessage(const QString &message); private: using ProjectConfiguration::parent; - virtual void doRun() = 0; + virtual Tasking::GroupItem runRecipe(); // TODO: Make pure virtual when all subclasses implement it. + virtual void doRun(); virtual void doCancel(); BuildStepList * const m_stepList; @@ -139,8 +145,10 @@ private: bool m_addMacroExpander = false; std::optional m_wasExpanded; std::function m_summaryUpdater; + std::unique_ptr m_taskTree; QString m_summaryText; + QString m_cancelMessage; }; class PROJECTEXPLORER_EXPORT BuildStepFactory diff --git a/src/plugins/remotelinux/abstractremotelinuxdeploystep.cpp b/src/plugins/remotelinux/abstractremotelinuxdeploystep.cpp index 894f91f49c3..16745f77f08 100644 --- a/src/plugins/remotelinux/abstractremotelinuxdeploystep.cpp +++ b/src/plugins/remotelinux/abstractremotelinuxdeploystep.cpp @@ -29,7 +29,6 @@ public: std::function()> internalInit; DeploymentTimeInfo deployTimes; - std::unique_ptr m_taskTree; }; } // Internal @@ -38,7 +37,9 @@ using namespace Internal; AbstractRemoteLinuxDeployStep::AbstractRemoteLinuxDeployStep(BuildStepList *bsl, Id id) : BuildStep(bsl, id), d(new AbstractRemoteLinuxDeployStepPrivate) -{} +{ + setCancelMessage(Tr::tr("User requests deployment to stop; cleaning up.")); +} AbstractRemoteLinuxDeployStep::~AbstractRemoteLinuxDeployStep() { @@ -99,6 +100,8 @@ QVariantMap AbstractRemoteLinuxDeployStep::toMap() const bool AbstractRemoteLinuxDeployStep::init() { QTC_ASSERT(d->internalInit, return false); + if (!BuildStep::init()) + return false; const auto canDeploy = d->internalInit(); if (!canDeploy) { emit addOutput(Tr::tr("Cannot deploy: %1").arg(canDeploy.error()), @@ -107,35 +110,6 @@ bool AbstractRemoteLinuxDeployStep::init() return bool(canDeploy); } -void AbstractRemoteLinuxDeployStep::doRun() -{ - QTC_ASSERT(!d->m_taskTree, return); - - d->m_taskTree.reset(new TaskTree({runRecipe()})); - const auto onDone = [this] { - d->m_taskTree.release()->deleteLater(); - emit finished(true); - }; - const auto onError = [this] { - d->m_taskTree.release()->deleteLater(); - emit finished(false); - }; - connect(d->m_taskTree.get(), &TaskTree::done, this, onDone); - connect(d->m_taskTree.get(), &TaskTree::errorOccurred, this, onError); - d->m_taskTree->start(); -} - -void AbstractRemoteLinuxDeployStep::doCancel() -{ - if (!d->m_taskTree) - return; - - d->m_taskTree.reset(); - emit addOutput(Tr::tr("User requests deployment to stop; cleaning up."), - OutputFormat::NormalMessage); - emit finished(false); -} - void AbstractRemoteLinuxDeployStep::addProgressMessage(const QString &message) { emit addOutput(message, OutputFormat::NormalMessage); diff --git a/src/plugins/remotelinux/abstractremotelinuxdeploystep.h b/src/plugins/remotelinux/abstractremotelinuxdeploystep.h index 299a3ca736a..0bfc44edfab 100644 --- a/src/plugins/remotelinux/abstractremotelinuxdeploystep.h +++ b/src/plugins/remotelinux/abstractremotelinuxdeploystep.h @@ -9,7 +9,6 @@ #include namespace ProjectExplorer { class DeployableFile; } -namespace Tasking { class GroupItem; } namespace RemoteLinux { @@ -30,8 +29,6 @@ protected: bool fromMap(const QVariantMap &map) final; QVariantMap toMap() const final; bool init() final; - void doRun() final; - void doCancel() final; void setInternalInitializer(const std::function()> &init); @@ -45,12 +42,10 @@ protected: void addErrorMessage(const QString &message); void addWarningMessage(const QString &message); - void handleFinished(); - private: virtual bool isDeploymentNecessary() const; virtual Tasking::GroupItem deployRecipe() = 0; - Tasking::GroupItem runRecipe(); + Tasking::GroupItem runRecipe() final; Internal::AbstractRemoteLinuxDeployStepPrivate *d; };