runconfiguration.h 10.9 KB
Newer Older
hjk's avatar
hjk committed
1
/****************************************************************************
con's avatar
con committed
2
**
Eike Ziller's avatar
Eike Ziller committed
3
4
** Copyright (C) 2015 The Qt Company Ltd.
** Contact: http://www.qt.io/licensing
con's avatar
con committed
5
**
hjk's avatar
hjk committed
6
** This file is part of Qt Creator.
con's avatar
con committed
7
**
hjk's avatar
hjk committed
8
9
10
11
** 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
Eike Ziller's avatar
Eike Ziller committed
12
13
** a written agreement between you and The Qt Company.  For licensing terms and
** conditions see http://www.qt.io/terms-conditions.  For further information
Eike Ziller's avatar
Eike Ziller committed
14
** use the contact form at http://www.qt.io/contact-us.
15
**
16
** GNU Lesser General Public License Usage
hjk's avatar
hjk committed
17
** Alternatively, this file may be used under the terms of the GNU Lesser
Eike Ziller's avatar
Eike Ziller committed
18
19
20
21
22
23
** General Public License version 2.1 or version 3 as published by the Free
** Software Foundation and appearing in the file LICENSE.LGPLv21 and
** LICENSE.LGPLv3 included in the packaging of this file.  Please review the
** following information to ensure the GNU Lesser General Public License
** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
hjk's avatar
hjk committed
24
**
Eike Ziller's avatar
Eike Ziller committed
25
26
** In addition, as a special exception, The Qt Company gives you certain additional
** rights.  These rights are described in The Qt Company LGPL Exception
con's avatar
con committed
27
28
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
hjk's avatar
hjk committed
29
****************************************************************************/
hjk's avatar
hjk committed
30

con's avatar
con committed
31
32
33
#ifndef RUNCONFIGURATION_H
#define RUNCONFIGURATION_H

34
#include "projectconfiguration.h"
con's avatar
con committed
35
#include "projectexplorer_export.h"
36
#include "projectexplorerconstants.h"
con's avatar
con committed
37

38
#include <utils/outputformat.h>
39
#include <utils/qtcassert.h>
con's avatar
con committed
40

41
#include <QPointer>
42
#include <QWidget>
con's avatar
con committed
43

44
45
46
47
QT_BEGIN_NAMESPACE
class QFormLayout;
QT_END_NAMESPACE

48
namespace Utils { class OutputFormatter; }
con's avatar
con committed
49

50
51
namespace ProjectExplorer {
class Abi;
52
class BuildConfiguration;
53
class IRunConfigurationAspect;
54
class RunConfiguration;
55
class RunConfigWidget;
56
57
class RunControl;
class Target;
con's avatar
con committed
58

59
60
61
62
// FIXME: This should also contain a handle to an remote device if used.
class PROJECTEXPLORER_EXPORT ProcessHandle
{
public:
63
    explicit ProcessHandle(quint64 pid = 0);
64

65
66
67
68
69
70
    bool isValid() const;
    void setPid(quint64 pid);
    quint64 pid() const;
    QString toString() const;

    bool equals(const ProcessHandle &) const;
71
72
73
74
75

private:
    quint64 m_pid;
};

76
77
78
inline bool operator==(const ProcessHandle &p1, const ProcessHandle &p2) { return p1.equals(p2); }
inline bool operator!=(const ProcessHandle &p1, const ProcessHandle &p2) { return !p1.equals(p2); }

79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
/**
 * An interface for a hunk of global or per-project
 * configuration data.
 *
 */

class PROJECTEXPLORER_EXPORT ISettingsAspect : public QObject
{
    Q_OBJECT

public:
    ISettingsAspect() {}

    /// Create a configuration widget for this settings aspect.
    virtual QWidget *createConfigWidget(QWidget *parent) = 0;
    /// "Virtual default constructor"
    virtual ISettingsAspect *create() const = 0;
    /// "Virtual copy constructor"
    ISettingsAspect *clone() const;

protected:
    ///
    friend class IRunConfigurationAspect;
    /// Converts current object into map for storage.
    virtual void toMap(QVariantMap &map) const = 0;
    /// Read object state from @p map.
    virtual void fromMap(const QVariantMap &map) = 0;
};


/**
 * An interface to facilitate switching between hunks of
 * global and per-project configuration data.
 *
 */

hjk's avatar
hjk committed
115
class PROJECTEXPLORER_EXPORT IRunConfigurationAspect : public QObject
116
{
hjk's avatar
hjk committed
117
118
    Q_OBJECT

119
public:
120
    explicit IRunConfigurationAspect(RunConfiguration *runConfig);
121
122
    ~IRunConfigurationAspect();

123
124
    virtual IRunConfigurationAspect *create(RunConfiguration *runConfig) const = 0;
    virtual IRunConfigurationAspect *clone(RunConfiguration *runConfig) const;
125
    virtual RunConfigWidget *createConfigurationWidget();
126

127
    void setId(Core::Id id) { m_id = id; }
hjk's avatar
hjk committed
128
    void setDisplayName(const QString &displayName) { m_displayName = displayName; }
129
130
    void setProjectSettings(ISettingsAspect *settings);
    void setGlobalSettings(ISettingsAspect *settings);
hjk's avatar
hjk committed
131

132
    QString displayName() const { return m_displayName; }
hjk's avatar
hjk committed
133
    Core::Id id() const { return m_id; }
134
135
136
137
138
139
140
141
142
    bool isUsingGlobalSettings() const { return m_useGlobalSettings; }
    void setUsingGlobalSettings(bool value);
    void resetProjectToGlobalSettings();

    ISettingsAspect *projectSettings() const { return m_projectSettings; }
    ISettingsAspect *globalSettings() const { return m_globalSettings; }
    ISettingsAspect *currentSettings() const;
    RunConfiguration *runConfiguration() const { return m_runConfiguration; }

143
144
protected:
    friend class RunConfiguration;
145
146
    virtual void fromMap(const QVariantMap &map);
    virtual void toMap(QVariantMap &data) const;
hjk's avatar
hjk committed
147
148
149

private:
    Core::Id m_id;
150
151
152
153
154
    QString m_displayName;
    bool m_useGlobalSettings;
    RunConfiguration *m_runConfiguration;
    ISettingsAspect *m_projectSettings; // Owned if present.
    ISettingsAspect *m_globalSettings;  // Not owned.
155
156
};

157
// Documentation inside.
158
class PROJECTEXPLORER_EXPORT RunConfiguration : public ProjectConfiguration
con's avatar
con committed
159
160
{
    Q_OBJECT
161

con's avatar
con committed
162
public:
Tobias Hunger's avatar
Tobias Hunger committed
163
    ~RunConfiguration();
con's avatar
con committed
164

165
    virtual bool isEnabled() const;
dt_'s avatar
dt_ committed
166
    virtual QString disabledReason() const;
167
    virtual QWidget *createConfigurationWidget() = 0;
168

Tobias Hunger's avatar
Tobias Hunger committed
169
    virtual bool isConfigured() const;
170
    // Pop up configuration dialog in case for example the executable is missing.
171
172
173
    enum ConfigurationState { Configured, UnConfigured, Waiting };
    // TODO rename function
    virtual ConfigurationState ensureConfigured(QString *errorMessage = 0);
con's avatar
con committed
174

Tobias Hunger's avatar
Tobias Hunger committed
175
    Target *target() const;
176

con's avatar
con committed
177
    virtual Utils::OutputFormatter *createOutputFormatter() const;
dt's avatar
dt committed
178

Tobias Hunger's avatar
Tobias Hunger committed
179
180
    bool fromMap(const QVariantMap &map);
    QVariantMap toMap() const;
181

182
    QList<IRunConfigurationAspect *> extraAspects() const;
183
    IRunConfigurationAspect *extraAspect(Core::Id id) const;
hjk's avatar
hjk committed
184

185
186
    template <typename T> T *extraAspect() const
    {
187
        QTC_ASSERT(m_aspectsInitialized, return 0);
hjk's avatar
hjk committed
188
189
190
191
192
193
        foreach (IRunConfigurationAspect *aspect, m_aspects)
            if (T *result = qobject_cast<T *>(aspect))
                return result;
        return 0;
    }

194
    virtual Abi abi() const;
195

196
    void addExtraAspects();
197
    void addExtraAspect(IRunConfigurationAspect *aspect);
198

199
signals:
200
    void enabledChanged();
201
    void requestRunActionsUpdate();
202
    void configurationFinished();
203

204
protected:
205
    RunConfiguration(Target *parent, Core::Id id);
Tobias Hunger's avatar
Tobias Hunger committed
206
    RunConfiguration(Target *parent, RunConfiguration *source);
207

208
    /// convenience function to get current build configuration.
209
    BuildConfiguration *activeBuildConfiguration() const;
210
211

private:
212
213
    void ctor();

214
    QList<IRunConfigurationAspect *> m_aspects;
215
    bool m_aspectsInitialized;
con's avatar
con committed
216
217
};

218
class PROJECTEXPLORER_EXPORT IRunConfigurationFactory : public QObject
con's avatar
con committed
219
220
{
    Q_OBJECT
221

con's avatar
con committed
222
public:
223
    explicit IRunConfigurationFactory(QObject *parent = 0);
con's avatar
con committed
224
    virtual ~IRunConfigurationFactory();
225

226
227
    enum CreationMode {UserCreate, AutoCreate};
    virtual QList<Core::Id> availableCreationIds(Target *parent, CreationMode mode = UserCreate) const = 0;
228
    virtual QString displayNameForId(Core::Id id) const = 0;
229

230
231
    virtual bool canCreate(Target *parent, Core::Id id) const = 0;
    RunConfiguration *create(Target *parent, Core::Id id);
Tobias Hunger's avatar
Tobias Hunger committed
232
    virtual bool canRestore(Target *parent, const QVariantMap &map) const = 0;
233
    RunConfiguration *restore(Target *parent, const QVariantMap &map);
Tobias Hunger's avatar
Tobias Hunger committed
234
235
236
    virtual bool canClone(Target *parent, RunConfiguration *product) const = 0;
    virtual RunConfiguration *clone(Target *parent, RunConfiguration *product) = 0;

Tobias Hunger's avatar
Tobias Hunger committed
237
    static IRunConfigurationFactory *find(Target *parent, const QVariantMap &map);
238
    static IRunConfigurationFactory *find(Target *parent, RunConfiguration *rc);
Tobias Hunger's avatar
Tobias Hunger committed
239
    static QList<IRunConfigurationFactory *> find(Target *parent);
240
241
242

signals:
    void availableCreationIdsChanged();
243
244

private:
245
    virtual RunConfiguration *doCreate(Target *parent, Core::Id id) = 0;
246
    virtual RunConfiguration *doRestore(Target *parent, const QVariantMap &map) = 0;
con's avatar
con committed
247
248
};

249
class PROJECTEXPLORER_EXPORT IRunControlFactory : public QObject
con's avatar
con committed
250
251
252
{
    Q_OBJECT
public:
253
254
255
    explicit IRunControlFactory(QObject *parent = 0);
    virtual ~IRunControlFactory();

256
    virtual bool canRun(RunConfiguration *runConfiguration, RunMode mode) const = 0;
257
    virtual RunControl *create(RunConfiguration *runConfiguration, RunMode mode, QString *errorMessage) = 0;
con's avatar
con committed
258

259
    virtual IRunConfigurationAspect *createRunConfigurationAspect(RunConfiguration *rc);
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
};

class PROJECTEXPLORER_EXPORT RunConfigWidget
    : public QWidget
{
    Q_OBJECT
public:
    RunConfigWidget()
        : QWidget(0)
    {}

    virtual QString displayName() const = 0;

signals:
    void displayNameChanged(const QString &);
con's avatar
con committed
275
276
};

277
278
class PROJECTEXPLORER_EXPORT RunControl : public QObject
{
con's avatar
con committed
279
280
    Q_OBJECT
public:
281
282
    enum StopResult {
        StoppedSynchronously, // Stopped.
283
        AsynchronousStop     // Stop sequence has been started
284
285
    };

286
    RunControl(RunConfiguration *runConfiguration, RunMode mode);
con's avatar
con committed
287
288
    virtual ~RunControl();
    virtual void start() = 0;
289
290

    virtual bool promptToStop(bool *optionalPrompt = 0) const;
291
    virtual StopResult stop() = 0;
con's avatar
con committed
292
    virtual bool isRunning() const = 0;
293
    virtual QString displayName() const;
294
    virtual bool supportsReRunning() const { return true; }
295
296
297

    void setIcon(const QString &icon) { m_icon = icon; }
    QString icon() const { return m_icon; }
298

299
300
    ProcessHandle applicationProcessHandle() const;
    void setApplicationProcessHandle(const ProcessHandle &handle);
301
    Abi abi() const;
302

303
    RunConfiguration *runConfiguration() const;
304
    bool sameRunConfiguration(const RunControl *other) const;
305

con's avatar
con committed
306
    Utils::OutputFormatter *outputFormatter();
307
    RunMode runMode() const;
308

309
310
public slots:
    void bringApplicationToForeground(qint64 pid);
con's avatar
con committed
311
    void appendMessage(const QString &msg, Utils::OutputFormat format);
312

con's avatar
con committed
313
signals:
314
    void appendMessage(ProjectExplorer::RunControl *runControl,
con's avatar
con committed
315
        const QString &msg, Utils::OutputFormat format);
con's avatar
con committed
316
317
    void started();
    void finished();
318
    void applicationProcessHandleChanged();
Thorbjørn Lindeijer's avatar
Thorbjørn Lindeijer committed
319

con's avatar
con committed
320
321
322
private slots:
    void bringApplicationToForegroundInternal();

323
324
325
326
327
328
protected:
    bool showPromptToStopDialog(const QString &title, const QString &text,
                                const QString &stopButtonText = QString(),
                                const QString &cancelButtonText = QString(),
                                bool *prompt = 0) const;

con's avatar
con committed
329
private:
330
    QString m_displayName;
331
    RunMode m_runMode;
332
    QString m_icon;
333
    const QPointer<RunConfiguration> m_runConfiguration;
con's avatar
con committed
334
    Utils::OutputFormatter *m_outputFormatter;
con's avatar
con committed
335

336
337
338
    // A handle to the actual application process.
    ProcessHandle m_applicationProcessHandle;

con's avatar
con committed
339
340
341
342
343
344
345
346
347
348
349
#ifdef Q_OS_MAC
    //these two are used to bring apps in the foreground on Mac
    qint64 m_internalPid;
    int m_foregroundCount;
#endif
};

} // namespace ProjectExplorer

// Allow a RunConfiguration to be stored in a QVariant
Q_DECLARE_METATYPE(ProjectExplorer::RunConfiguration*)
350
Q_DECLARE_METATYPE(ProjectExplorer::RunControl*)
con's avatar
con committed
351
352

#endif // RUNCONFIGURATION_H