File indexing completed on 2024-05-05 04:38:04

0001 /*
0002     SPDX-FileCopyrightText: 2007-2008 Hamish Rodda <rodda@kde.org>
0003 
0004     SPDX-License-Identifier: LGPL-2.0-or-later
0005 */
0006 
0007 #include "outputjob.h"
0008 
0009 #include <QStandardItemModel>
0010 #include <QItemDelegate>
0011 #include <QIcon>
0012 #include <QPointer>
0013 
0014 #include "interfaces/icore.h"
0015 #include "interfaces/iplugincontroller.h"
0016 #include "outputview/ioutputview.h"
0017 
0018 using namespace KDevelop;
0019 
0020 class KDevelop::OutputJobPrivate
0021 {
0022 public:
0023     explicit OutputJobPrivate(OutputJob::OutputJobVerbosity verbosity) : verbosity(verbosity) {}
0024 
0025     int standardToolView = -1;
0026     QString title;
0027     QString toolTitle;
0028     QIcon toolIcon;
0029     IOutputView::ViewType type = IOutputView::OneView;
0030     IOutputView::Behaviours behaviours = IOutputView::AllowUserClose;
0031     bool killJobOnOutputClose = true;
0032     OutputJob::OutputJobVerbosity verbosity;
0033     int outputId = -1;
0034     QPointer<QAbstractItemModel> outputModel;
0035     QAbstractItemDelegate* outputDelegate = nullptr;
0036 };
0037 
0038 OutputJob::OutputJob(QObject* parent, OutputJobVerbosity verbosity)
0039     : KJob(parent)
0040     , d_ptr(new OutputJobPrivate(verbosity))
0041 {
0042 }
0043 
0044 OutputJob::~OutputJob() = default;
0045 
0046 void OutputJob::startOutput()
0047 {
0048     Q_D(OutputJob);
0049 
0050     IPlugin* i = ICore::self()->pluginController()->pluginForExtension(QStringLiteral("org.kdevelop.IOutputView"));
0051     if( i )
0052     {
0053         auto* view = i->extension<KDevelop::IOutputView>();
0054         if( view )
0055         {
0056             int tvid;
0057             if (d->standardToolView != -1) {
0058                 tvid = view->standardToolView(static_cast<IOutputView::StandardToolView>(d->standardToolView));
0059             } else {
0060                 tvid = view->registerToolView(QByteArray(), d->toolTitle, d->type, d->toolIcon);
0061             }
0062 
0063             if (d->title.isEmpty())
0064                 d->title = objectName();
0065 
0066             d->outputId = view->registerOutputInToolView(tvid, d->title, d->behaviours);
0067 
0068             if (!d->outputModel) {
0069                 d->outputModel = new QStandardItemModel(nullptr);
0070             }
0071 
0072             // Keep the item model around after the job is gone
0073             view->setModel(d->outputId, d->outputModel);
0074 
0075             if (!d->outputDelegate) {
0076                 d->outputDelegate = new QItemDelegate(nullptr);
0077             }
0078 
0079             view->setDelegate(d->outputId, d->outputDelegate);
0080 
0081             if (d->killJobOnOutputClose) {
0082                 // can't use qt5 signal slot syntax here, IOutputView is no a QObject
0083                 connect(i, SIGNAL(outputRemoved(int,int)), this, SLOT(outputViewRemoved(int,int)));
0084             }
0085 
0086             if (d->verbosity == OutputJob::Verbose)
0087                 view->raiseOutput(d->outputId);
0088         }
0089     }
0090 }
0091 
0092 void OutputJob::outputViewRemoved(int toolViewId, int id)
0093 {
0094     Q_D(OutputJob);
0095 
0096     Q_UNUSED(toolViewId);
0097     if (id == d->outputId && d->killJobOnOutputClose) {
0098         // Make sure that the job emits result signal as the job
0099         // might be used in composite jobs and that one depends
0100         // on result being emitted to know whether a subjob
0101         // is done.
0102         // NOTE: ExecuteCompositeJob no longer needs the result signal, but this class is widely used.
0103         // After more than ten years of emitting result here, other code may now rely on this behavior.
0104         kill( KJob::EmitResult );
0105     }
0106 }
0107 
0108 void KDevelop::OutputJob::setTitle(const QString & title)
0109 {
0110     Q_D(OutputJob);
0111 
0112     d->title = title;
0113     if (d->outputId >= 0 && d->standardToolView >= 0) {
0114         IPlugin* i = ICore::self()->pluginController()->pluginForExtension(QStringLiteral("org.kdevelop.IOutputView"));
0115         if( i )
0116         {
0117             auto* view = i->extension<KDevelop::IOutputView>();
0118             if( view )
0119             {
0120                 view->setTitle(d->outputId, title);
0121             }
0122         }
0123     }
0124 }
0125 
0126 void KDevelop::OutputJob::setViewType(IOutputView::ViewType type)
0127 {
0128     Q_D(OutputJob);
0129 
0130     d->type = type;
0131 }
0132 
0133 void KDevelop::OutputJob::setBehaviours(IOutputView::Behaviours behaviours)
0134 {
0135     Q_D(OutputJob);
0136 
0137     d->behaviours = behaviours;
0138 }
0139 
0140 void KDevelop::OutputJob::setKillJobOnOutputClose(bool killJobOnOutputClose)
0141 {
0142     Q_D(OutputJob);
0143 
0144     d->killJobOnOutputClose = killJobOnOutputClose;
0145 }
0146 
0147 void KDevelop::OutputJob::setModel(QAbstractItemModel * model)
0148 {
0149     Q_D(OutputJob);
0150 
0151     if (d->outputModel) {
0152         delete d->outputModel;
0153     }
0154 
0155     d->outputModel = model;
0156 
0157     if (d->outputModel) {
0158         d->outputModel->setParent(this);
0159     }
0160 }
0161 
0162 void KDevelop::OutputJob::setDelegate(QAbstractItemDelegate * delegate)
0163 {
0164     Q_D(OutputJob);
0165 
0166     d->outputDelegate = delegate;
0167 }
0168 
0169 QAbstractItemModel * KDevelop::OutputJob::model() const
0170 {
0171     Q_D(const OutputJob);
0172 
0173     return d->outputModel;
0174 }
0175 
0176 void KDevelop::OutputJob::setStandardToolView(IOutputView::StandardToolView standard)
0177 {
0178     Q_D(OutputJob);
0179 
0180     d->standardToolView = standard;
0181 }
0182 
0183 void OutputJob::setToolTitle(const QString& title)
0184 {
0185     Q_D(OutputJob);
0186 
0187     d->toolTitle = title;
0188 }
0189 
0190 void OutputJob::setToolIcon(const QIcon& icon)
0191 {
0192     Q_D(OutputJob);
0193 
0194     d->toolIcon = icon;
0195 }
0196 
0197 int OutputJob::outputId() const
0198 {
0199     Q_D(const OutputJob);
0200 
0201     return d->outputId;
0202 }
0203 
0204 OutputJob::OutputJobVerbosity OutputJob::verbosity() const
0205 {
0206     Q_D(const OutputJob);
0207 
0208     return d->verbosity;
0209 }
0210 
0211 void OutputJob::setVerbosity(OutputJob::OutputJobVerbosity verbosity)
0212 {
0213     Q_D(OutputJob);
0214 
0215     d->verbosity = verbosity;
0216 }
0217 
0218 #include "moc_outputjob.cpp"