2012-10-02 09:12:39 +02:00
|
|
|
/****************************************************************************
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
2016-01-15 14:57:40 +01:00
|
|
|
** Copyright (C) 2016 The Qt Company Ltd.
|
|
|
|
|
** Contact: https://www.qt.io/licensing/
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
2012-10-02 09:12:39 +02:00
|
|
|
** This file is part of Qt Creator.
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
2012-10-02 09:12:39 +02:00
|
|
|
** 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
|
2016-01-15 14:57:40 +01:00
|
|
|
** 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.
|
2008-12-02 14:17:16 +01:00
|
|
|
**
|
2016-01-15 14:57:40 +01:00
|
|
|
** 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.
|
2010-12-17 16:01:08 +01:00
|
|
|
**
|
2012-10-02 09:12:39 +02:00
|
|
|
****************************************************************************/
|
2008-12-02 16:19:05 +01:00
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
#include "taskwindow.h"
|
|
|
|
|
|
2010-06-18 11:18:48 +02:00
|
|
|
#include "itaskhandler.h"
|
|
|
|
|
#include "projectexplorerconstants.h"
|
2015-11-23 16:41:54 +01:00
|
|
|
#include "projectexplorericons.h"
|
2014-11-20 16:47:00 +01:00
|
|
|
#include "session.h"
|
2010-06-16 14:12:30 +02:00
|
|
|
#include "task.h"
|
2010-07-06 12:11:15 +02:00
|
|
|
#include "taskhub.h"
|
2011-09-20 09:42:10 +00:00
|
|
|
#include "taskmodel.h"
|
2010-06-16 14:12:30 +02:00
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
#include <coreplugin/actionmanager/actionmanager.h>
|
2015-02-26 13:38:54 +01:00
|
|
|
#include <coreplugin/actionmanager/command.h>
|
2015-11-23 16:41:54 +01:00
|
|
|
#include <coreplugin/coreicons.h>
|
2009-01-23 13:03:36 +01:00
|
|
|
#include <coreplugin/icore.h>
|
2013-03-27 08:29:38 +01:00
|
|
|
#include <coreplugin/icontext.h>
|
2010-06-18 11:18:48 +02:00
|
|
|
#include <extensionsystem/pluginmanager.h>
|
2014-11-20 16:47:00 +01:00
|
|
|
#include <utils/algorithm.h>
|
2012-01-26 13:38:25 +01:00
|
|
|
#include <utils/qtcassert.h>
|
2014-04-09 18:08:02 +02:00
|
|
|
#include <utils/itemviews.h>
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2012-02-15 10:42:41 +01:00
|
|
|
#include <QDir>
|
|
|
|
|
#include <QPainter>
|
|
|
|
|
#include <QStyledItemDelegate>
|
|
|
|
|
#include <QMenu>
|
|
|
|
|
#include <QToolButton>
|
2013-10-24 16:54:24 +02:00
|
|
|
#include <QScrollBar>
|
2009-11-11 09:54:13 +01:00
|
|
|
|
2010-02-19 13:06:28 +01:00
|
|
|
namespace {
|
2010-10-20 11:33:23 +02:00
|
|
|
const int ELLIPSIS_GRADIENT_WIDTH = 16;
|
2014-11-20 16:47:00 +01:00
|
|
|
const char SESSION_FILTER_CATEGORIES[] = "TaskWindow.Categories";
|
|
|
|
|
const char SESSION_FILTER_WARNINGS[] = "TaskWindow.IncludeWarnings";
|
2010-02-19 13:06:28 +01:00
|
|
|
}
|
|
|
|
|
|
2009-11-11 09:54:13 +01:00
|
|
|
namespace ProjectExplorer {
|
|
|
|
|
namespace Internal {
|
|
|
|
|
|
2014-04-09 18:08:02 +02:00
|
|
|
class TaskView : public Utils::ListView
|
2009-11-11 09:54:13 +01:00
|
|
|
{
|
|
|
|
|
public:
|
|
|
|
|
TaskView(QWidget *parent = 0);
|
|
|
|
|
~TaskView();
|
|
|
|
|
void resizeEvent(QResizeEvent *e);
|
|
|
|
|
};
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2009-11-11 09:54:13 +01:00
|
|
|
class TaskWindowContext : public Core::IContext
|
|
|
|
|
{
|
|
|
|
|
public:
|
|
|
|
|
TaskWindowContext(QWidget *widget);
|
|
|
|
|
};
|
|
|
|
|
|
2010-10-20 11:33:23 +02:00
|
|
|
class TaskDelegate : public QStyledItemDelegate
|
|
|
|
|
{
|
|
|
|
|
Q_OBJECT
|
|
|
|
|
|
2013-10-24 16:54:24 +02:00
|
|
|
friend class TaskView; // for using Positions::minimumSize()
|
|
|
|
|
|
2010-10-20 11:33:23 +02:00
|
|
|
public:
|
|
|
|
|
TaskDelegate(QObject * parent = 0);
|
|
|
|
|
~TaskDelegate();
|
|
|
|
|
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const;
|
|
|
|
|
QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const;
|
|
|
|
|
|
|
|
|
|
// TaskView uses this method if the size of the taskview changes
|
|
|
|
|
void emitSizeHintChanged(const QModelIndex &index);
|
|
|
|
|
|
|
|
|
|
public slots:
|
|
|
|
|
void currentChanged(const QModelIndex ¤t, const QModelIndex &previous);
|
|
|
|
|
|
|
|
|
|
private:
|
|
|
|
|
void generateGradientPixmap(int width, int height, QColor color, bool selected) const;
|
|
|
|
|
|
2011-09-20 09:42:10 +00:00
|
|
|
mutable int m_cachedHeight;
|
|
|
|
|
mutable QFont m_cachedFont;
|
|
|
|
|
|
2010-10-20 11:33:23 +02:00
|
|
|
/*
|
|
|
|
|
Collapsed:
|
|
|
|
|
+----------------------------------------------------------------------------------------------------+
|
|
|
|
|
| TASKICONAREA TEXTAREA FILEAREA LINEAREA |
|
|
|
|
|
+----------------------------------------------------------------------------------------------------+
|
|
|
|
|
|
|
|
|
|
Expanded:
|
|
|
|
|
+----------------------------------------------------------------------------------------------------+
|
|
|
|
|
| TASKICONICON TEXTAREA FILEAREA LINEAREA |
|
|
|
|
|
| more text -------------------------------------------------------------------------> |
|
|
|
|
|
+----------------------------------------------------------------------------------------------------+
|
|
|
|
|
*/
|
|
|
|
|
class Positions
|
|
|
|
|
{
|
|
|
|
|
public:
|
|
|
|
|
Positions(const QStyleOptionViewItemV4 &options, TaskModel *model) :
|
|
|
|
|
m_totalWidth(options.rect.width()),
|
|
|
|
|
m_maxFileLength(model->sizeOfFile(options.font)),
|
|
|
|
|
m_maxLineLength(model->sizeOfLineNumber(options.font)),
|
|
|
|
|
m_realFileLength(m_maxFileLength),
|
|
|
|
|
m_top(options.rect.top()),
|
|
|
|
|
m_bottom(options.rect.bottom())
|
|
|
|
|
{
|
|
|
|
|
int flexibleArea = lineAreaLeft() - textAreaLeft() - ITEM_SPACING;
|
|
|
|
|
if (m_maxFileLength > flexibleArea / 2)
|
|
|
|
|
m_realFileLength = flexibleArea / 2;
|
|
|
|
|
m_fontHeight = QFontMetrics(options.font).height();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
int top() const { return m_top + ITEM_MARGIN; }
|
|
|
|
|
int left() const { return ITEM_MARGIN; }
|
|
|
|
|
int right() const { return m_totalWidth - ITEM_MARGIN; }
|
|
|
|
|
int bottom() const { return m_bottom; }
|
|
|
|
|
int firstLineHeight() const { return m_fontHeight + 1; }
|
2013-10-24 16:54:24 +02:00
|
|
|
static int minimumHeight() { return taskIconHeight() + 2 * ITEM_MARGIN; }
|
2010-10-20 11:33:23 +02:00
|
|
|
|
|
|
|
|
int taskIconLeft() const { return left(); }
|
2013-10-24 16:54:24 +02:00
|
|
|
static int taskIconWidth() { return TASK_ICON_SIZE; }
|
|
|
|
|
static int taskIconHeight() { return TASK_ICON_SIZE; }
|
2010-10-20 11:33:23 +02:00
|
|
|
int taskIconRight() const { return taskIconLeft() + taskIconWidth(); }
|
|
|
|
|
QRect taskIcon() const { return QRect(taskIconLeft(), top(), taskIconWidth(), taskIconHeight()); }
|
|
|
|
|
|
|
|
|
|
int textAreaLeft() const { return taskIconRight() + ITEM_SPACING; }
|
|
|
|
|
int textAreaWidth() const { return textAreaRight() - textAreaLeft(); }
|
|
|
|
|
int textAreaRight() const { return fileAreaLeft() - ITEM_SPACING; }
|
|
|
|
|
QRect textArea() const { return QRect(textAreaLeft(), top(), textAreaWidth(), firstLineHeight()); }
|
|
|
|
|
|
|
|
|
|
int fileAreaLeft() const { return fileAreaRight() - fileAreaWidth(); }
|
|
|
|
|
int fileAreaWidth() const { return m_realFileLength; }
|
|
|
|
|
int fileAreaRight() const { return lineAreaLeft() - ITEM_SPACING; }
|
|
|
|
|
QRect fileArea() const { return QRect(fileAreaLeft(), top(), fileAreaWidth(), firstLineHeight()); }
|
|
|
|
|
|
|
|
|
|
int lineAreaLeft() const { return lineAreaRight() - lineAreaWidth(); }
|
|
|
|
|
int lineAreaWidth() const { return m_maxLineLength; }
|
|
|
|
|
int lineAreaRight() const { return right(); }
|
|
|
|
|
QRect lineArea() const { return QRect(lineAreaLeft(), top(), lineAreaWidth(), firstLineHeight()); }
|
|
|
|
|
|
|
|
|
|
private:
|
|
|
|
|
int m_totalWidth;
|
|
|
|
|
int m_maxFileLength;
|
|
|
|
|
int m_maxLineLength;
|
|
|
|
|
int m_realFileLength;
|
|
|
|
|
int m_top;
|
|
|
|
|
int m_bottom;
|
|
|
|
|
int m_fontHeight;
|
|
|
|
|
|
|
|
|
|
static const int TASK_ICON_SIZE = 16;
|
|
|
|
|
static const int ITEM_MARGIN = 2;
|
|
|
|
|
static const int ITEM_SPACING = 2 * ITEM_MARGIN;
|
|
|
|
|
};
|
|
|
|
|
};
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
TaskView::TaskView(QWidget *parent)
|
2014-04-09 18:08:02 +02:00
|
|
|
: Utils::ListView(parent)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
|
|
|
|
setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
|
2011-01-24 13:51:26 +01:00
|
|
|
setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
|
2013-10-24 16:54:24 +02:00
|
|
|
|
|
|
|
|
QFontMetrics fm(font());
|
|
|
|
|
int vStepSize = fm.height() + 3;
|
|
|
|
|
if (vStepSize < TaskDelegate::Positions::minimumHeight())
|
|
|
|
|
vStepSize = TaskDelegate::Positions::minimumHeight();
|
|
|
|
|
|
|
|
|
|
verticalScrollBar()->setSingleStep(vStepSize);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
TaskView::~TaskView()
|
2014-10-23 16:32:26 +02:00
|
|
|
{ }
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
void TaskView::resizeEvent(QResizeEvent *e)
|
|
|
|
|
{
|
2009-07-13 17:35:17 +02:00
|
|
|
Q_UNUSED(e)
|
2008-12-02 12:01:29 +01:00
|
|
|
static_cast<TaskDelegate *>(itemDelegate())->emitSizeHintChanged(selectionModel()->currentIndex());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/////
|
|
|
|
|
// TaskWindow
|
|
|
|
|
/////
|
|
|
|
|
|
2010-06-16 14:24:22 +02:00
|
|
|
class TaskWindowPrivate
|
|
|
|
|
{
|
|
|
|
|
public:
|
2010-05-27 13:28:07 +02:00
|
|
|
Internal::TaskModel *m_model;
|
|
|
|
|
Internal::TaskFilterModel *m_filter;
|
|
|
|
|
Internal::TaskView *m_listview;
|
|
|
|
|
Internal::TaskWindowContext *m_taskWindowContext;
|
2010-06-18 11:18:48 +02:00
|
|
|
QMenu *m_contextMenu;
|
|
|
|
|
ITaskHandler *m_defaultHandler;
|
2010-09-14 17:15:11 +02:00
|
|
|
QToolButton *m_filterWarningsButton;
|
|
|
|
|
QToolButton *m_categoriesButton;
|
|
|
|
|
QMenu *m_categoriesMenu;
|
2012-10-05 14:35:34 +02:00
|
|
|
QList<QAction *> m_actions;
|
2010-05-27 13:28:07 +02:00
|
|
|
};
|
|
|
|
|
|
2010-09-14 17:15:11 +02:00
|
|
|
static QToolButton *createFilterButton(QIcon icon, const QString &toolTip,
|
2015-11-10 15:56:44 +01:00
|
|
|
QObject *receiver, std::function<void(bool)> lambda)
|
2010-09-14 17:15:11 +02:00
|
|
|
{
|
|
|
|
|
QToolButton *button = new QToolButton;
|
|
|
|
|
button->setIcon(icon);
|
|
|
|
|
button->setToolTip(toolTip);
|
|
|
|
|
button->setCheckable(true);
|
|
|
|
|
button->setChecked(true);
|
|
|
|
|
button->setAutoRaise(true);
|
|
|
|
|
button->setEnabled(true);
|
2015-11-10 15:56:44 +01:00
|
|
|
QObject::connect(button, &QToolButton::toggled, receiver, lambda);
|
2010-09-14 17:15:11 +02:00
|
|
|
return button;
|
|
|
|
|
}
|
|
|
|
|
|
2013-08-15 12:14:46 +02:00
|
|
|
TaskWindow::TaskWindow() : d(new TaskWindowPrivate)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2010-06-18 11:18:48 +02:00
|
|
|
d->m_defaultHandler = 0;
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2011-09-20 09:42:10 +00:00
|
|
|
d->m_model = new Internal::TaskModel(this);
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_filter = new Internal::TaskFilterModel(d->m_model);
|
|
|
|
|
d->m_listview = new Internal::TaskView;
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_listview->setModel(d->m_filter);
|
|
|
|
|
d->m_listview->setFrameStyle(QFrame::NoFrame);
|
2011-10-04 12:25:13 +02:00
|
|
|
d->m_listview->setWindowTitle(tr("Issues"));
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_listview->setSelectionMode(QAbstractItemView::SingleSelection);
|
|
|
|
|
Internal::TaskDelegate *tld = new Internal::TaskDelegate(this);
|
|
|
|
|
d->m_listview->setItemDelegate(tld);
|
2015-11-23 16:41:54 +01:00
|
|
|
d->m_listview->setWindowIcon(Icons::WINDOW.icon());
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_listview->setContextMenuPolicy(Qt::ActionsContextMenu);
|
|
|
|
|
d->m_listview->setAttribute(Qt::WA_MacShowFocusRect, false);
|
2008-12-03 21:50:31 +01:00
|
|
|
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_taskWindowContext = new Internal::TaskWindowContext(d->m_listview);
|
2010-07-06 12:11:15 +02:00
|
|
|
|
2012-01-24 15:36:40 +01:00
|
|
|
Core::ICore::addContextObject(d->m_taskWindowContext);
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2010-05-27 13:28:07 +02:00
|
|
|
connect(d->m_listview->selectionModel(), SIGNAL(currentChanged(QModelIndex,QModelIndex)),
|
2010-03-19 17:22:18 +01:00
|
|
|
tld, SLOT(currentChanged(QModelIndex,QModelIndex)));
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
connect(d->m_listview->selectionModel(), SIGNAL(currentChanged(QModelIndex,QModelIndex)),
|
|
|
|
|
this, SLOT(currentChanged(QModelIndex)));
|
2010-05-27 13:28:07 +02:00
|
|
|
connect(d->m_listview, SIGNAL(activated(QModelIndex)),
|
2010-06-18 11:18:48 +02:00
|
|
|
this, SLOT(triggerDefaultHandler(QModelIndex)));
|
|
|
|
|
|
|
|
|
|
d->m_contextMenu = new QMenu(d->m_listview);
|
|
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
d->m_listview->setContextMenuPolicy(Qt::ActionsContextMenu);
|
2008-12-03 21:50:31 +01:00
|
|
|
|
2013-11-12 21:59:43 +01:00
|
|
|
d->m_filterWarningsButton = createFilterButton(
|
2015-12-04 19:21:05 +01:00
|
|
|
Core::Icons::WARNING_TOOLBAR.icon(),
|
2015-11-10 15:56:44 +01:00
|
|
|
tr("Show Warnings"), this, [this](bool show) { setShowWarnings(show); });
|
2010-09-14 17:15:11 +02:00
|
|
|
|
|
|
|
|
d->m_categoriesButton = new QToolButton;
|
2015-11-23 16:41:54 +01:00
|
|
|
d->m_categoriesButton->setIcon(Core::Icons::FILTER.icon());
|
2010-09-14 17:15:11 +02:00
|
|
|
d->m_categoriesButton->setToolTip(tr("Filter by categories"));
|
2012-03-16 11:34:20 +01:00
|
|
|
d->m_categoriesButton->setProperty("noArrow", true);
|
2010-09-14 17:15:11 +02:00
|
|
|
d->m_categoriesButton->setAutoRaise(true);
|
|
|
|
|
d->m_categoriesButton->setPopupMode(QToolButton::InstantPopup);
|
2010-09-14 15:42:15 +02:00
|
|
|
|
|
|
|
|
d->m_categoriesMenu = new QMenu(d->m_categoriesButton);
|
2015-11-10 15:56:44 +01:00
|
|
|
connect(d->m_categoriesMenu, &QMenu::aboutToShow, this, &TaskWindow::updateCategoriesMenu);
|
2010-09-14 15:42:15 +02:00
|
|
|
|
2010-09-14 17:15:11 +02:00
|
|
|
d->m_categoriesButton->setMenu(d->m_categoriesMenu);
|
2009-11-11 12:36:44 +01:00
|
|
|
|
2015-11-10 15:56:44 +01:00
|
|
|
TaskHub *hub = TaskHub::instance();
|
|
|
|
|
connect(hub, &TaskHub::categoryAdded, this, &TaskWindow::addCategory);
|
|
|
|
|
connect(hub, &TaskHub::taskAdded, this, &TaskWindow::addTask);
|
|
|
|
|
connect(hub, &TaskHub::taskRemoved, this, &TaskWindow::removeTask);
|
|
|
|
|
connect(hub, &TaskHub::taskLineNumberUpdated, this, &TaskWindow::updatedTaskLineNumber);
|
|
|
|
|
connect(hub, &TaskHub::taskFileNameUpdated, this, &TaskWindow::updatedTaskFileName);
|
|
|
|
|
connect(hub, &TaskHub::tasksCleared, this, &TaskWindow::clearTasks);
|
|
|
|
|
connect(hub, &TaskHub::categoryVisibilityChanged, this, &TaskWindow::setCategoryVisibility);
|
|
|
|
|
connect(hub, &TaskHub::popupRequested, this, &TaskWindow::popup);
|
|
|
|
|
connect(hub, &TaskHub::showTask, this, &TaskWindow::showTask);
|
|
|
|
|
connect(hub, &TaskHub::openTask, this, &TaskWindow::openTask);
|
2014-10-23 16:32:26 +02:00
|
|
|
|
|
|
|
|
connect(d->m_filter, &TaskFilterModel::rowsRemoved,
|
|
|
|
|
[this]() { emit setBadgeNumber(d->m_filter->rowCount()); });
|
|
|
|
|
connect(d->m_filter, &TaskFilterModel::rowsInserted,
|
|
|
|
|
[this]() { emit setBadgeNumber(d->m_filter->rowCount()); });
|
|
|
|
|
connect(d->m_filter, &TaskFilterModel::modelReset,
|
|
|
|
|
[this]() { emit setBadgeNumber(d->m_filter->rowCount()); });
|
2014-11-20 16:47:00 +01:00
|
|
|
|
|
|
|
|
SessionManager *session = SessionManager::instance();
|
|
|
|
|
connect(session, &SessionManager::aboutToSaveSession, this, &TaskWindow::saveSettings);
|
|
|
|
|
connect(session, &SessionManager::sessionLoaded, this, &TaskWindow::loadSettings);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
TaskWindow::~TaskWindow()
|
|
|
|
|
{
|
2012-01-24 15:36:40 +01:00
|
|
|
Core::ICore::removeContextObject(d->m_taskWindowContext);
|
2010-09-14 17:15:11 +02:00
|
|
|
delete d->m_filterWarningsButton;
|
2010-05-27 13:28:07 +02:00
|
|
|
delete d->m_listview;
|
|
|
|
|
delete d->m_filter;
|
|
|
|
|
delete d->m_model;
|
|
|
|
|
delete d;
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
static ITaskHandler *handler(QAction *action)
|
|
|
|
|
{
|
2013-02-06 11:41:15 +01:00
|
|
|
QVariant prop = action->property("ITaskHandler");
|
|
|
|
|
ITaskHandler *handler = qobject_cast<ITaskHandler *>(prop.value<QObject *>());
|
|
|
|
|
QTC_CHECK(handler);
|
|
|
|
|
return handler;
|
2012-10-05 14:35:34 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskWindow::delayedInitialization()
|
|
|
|
|
{
|
|
|
|
|
static bool alreadyDone = false;
|
|
|
|
|
if (alreadyDone)
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
alreadyDone = true;
|
|
|
|
|
|
|
|
|
|
QList<ITaskHandler *> handlers = ExtensionSystem::PluginManager::getObjects<ITaskHandler>();
|
|
|
|
|
foreach (ITaskHandler *h, handlers) {
|
|
|
|
|
if (h->isDefaultHandler() && !d->m_defaultHandler)
|
|
|
|
|
d->m_defaultHandler = h;
|
|
|
|
|
|
|
|
|
|
QAction *action = h->createAction(this);
|
|
|
|
|
QTC_ASSERT(action, continue);
|
2013-02-06 11:41:15 +01:00
|
|
|
action->setProperty("ITaskHandler", qVariantFromValue(qobject_cast<QObject*>(h)));
|
2015-11-10 15:56:44 +01:00
|
|
|
connect(action, &QAction::triggered, this, &TaskWindow::actionTriggered);
|
2012-10-05 14:35:34 +02:00
|
|
|
d->m_actions << action;
|
|
|
|
|
|
|
|
|
|
Core::Id id = h->actionManagerId();
|
|
|
|
|
if (id.isValid()) {
|
|
|
|
|
Core::Command *cmd = Core::ActionManager::instance()
|
|
|
|
|
->registerAction(action, id, d->m_taskWindowContext->context(), true);
|
|
|
|
|
action = cmd->action();
|
|
|
|
|
}
|
|
|
|
|
d->m_listview->addAction(action);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Disable everything for now:
|
|
|
|
|
currentChanged(QModelIndex());
|
|
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
QList<QWidget*> TaskWindow::toolBarWidgets() const
|
|
|
|
|
{
|
2010-09-14 17:15:11 +02:00
|
|
|
return QList<QWidget*>() << d->m_filterWarningsButton << d->m_categoriesButton;
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
QWidget *TaskWindow::outputWidget(QWidget *)
|
|
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
return d->m_listview;
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2014-07-01 11:08:26 +02:00
|
|
|
void TaskWindow::clearTasks(Core::Id categoryId)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_model->clearTasks(categoryId);
|
2009-11-11 09:54:13 +01:00
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
emit tasksChanged();
|
2010-07-02 14:19:13 +02:00
|
|
|
emit tasksCleared();
|
2009-04-30 12:50:52 +02:00
|
|
|
navigateStateChanged();
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2014-07-01 11:08:26 +02:00
|
|
|
void TaskWindow::setCategoryVisibility(Core::Id categoryId, bool visible)
|
2011-08-09 14:40:04 +02:00
|
|
|
{
|
2015-06-23 13:15:17 +02:00
|
|
|
if (!categoryId.isValid())
|
2011-08-09 14:40:04 +02:00
|
|
|
return;
|
|
|
|
|
|
2012-01-26 13:38:25 +01:00
|
|
|
QList<Core::Id> categories = d->m_filter->filteredCategories();
|
2011-08-09 14:40:04 +02:00
|
|
|
|
Remove braces for single lines of conditions
#!/usr/bin/env ruby
Dir.glob('**/*.cpp') { |file|
# skip ast (excluding paste, astpath, and canv'ast'imer)
next if file =~ /ast[^eip]|keywords\.|qualifiers|preprocessor|names.cpp/i
s = File.read(file)
next if s.include?('qlalr')
orig = s.dup
s.gsub!(/\n *if [^\n]*{\n[^\n]*\n\s+}(\s+else if [^\n]* {\n[^\n]*\n\s+})*(\s+else {\n[^\n]*\n\s+})?\n/m) { |m|
res = $&
if res =~ /^\s*(\/\/|[A-Z_]{3,})/ # C++ comment or macro (Q_UNUSED, SDEBUG), do not touch braces
res
else
res.gsub!('} else', 'else')
res.gsub!(/\n +} *\n/m, "\n")
res.gsub(/ *{$/, '')
end
}
s.gsub!(/ *$/, '')
File.open(file, 'wb').write(s) if s != orig
}
Change-Id: I3b30ee60df0986f66c02132c65fc38a3fbb6bbdc
Reviewed-by: hjk <qthjk@ovi.com>
2013-01-08 03:32:53 +02:00
|
|
|
if (visible)
|
2011-08-09 14:40:04 +02:00
|
|
|
categories.removeOne(categoryId);
|
Remove braces for single lines of conditions
#!/usr/bin/env ruby
Dir.glob('**/*.cpp') { |file|
# skip ast (excluding paste, astpath, and canv'ast'imer)
next if file =~ /ast[^eip]|keywords\.|qualifiers|preprocessor|names.cpp/i
s = File.read(file)
next if s.include?('qlalr')
orig = s.dup
s.gsub!(/\n *if [^\n]*{\n[^\n]*\n\s+}(\s+else if [^\n]* {\n[^\n]*\n\s+})*(\s+else {\n[^\n]*\n\s+})?\n/m) { |m|
res = $&
if res =~ /^\s*(\/\/|[A-Z_]{3,})/ # C++ comment or macro (Q_UNUSED, SDEBUG), do not touch braces
res
else
res.gsub!('} else', 'else')
res.gsub!(/\n +} *\n/m, "\n")
res.gsub(/ *{$/, '')
end
}
s.gsub!(/ *$/, '')
File.open(file, 'wb').write(s) if s != orig
}
Change-Id: I3b30ee60df0986f66c02132c65fc38a3fbb6bbdc
Reviewed-by: hjk <qthjk@ovi.com>
2013-01-08 03:32:53 +02:00
|
|
|
else
|
2011-08-09 14:40:04 +02:00
|
|
|
categories.append(categoryId);
|
|
|
|
|
|
|
|
|
|
d->m_filter->setFilteredCategories(categories);
|
|
|
|
|
}
|
|
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
void TaskWindow::currentChanged(const QModelIndex &index)
|
|
|
|
|
{
|
|
|
|
|
const Task task = index.isValid() ? d->m_filter->task(index) : Task();
|
|
|
|
|
foreach (QAction *action, d->m_actions) {
|
|
|
|
|
ITaskHandler *h = handler(action);
|
|
|
|
|
action->setEnabled((task.isNull() || !h) ? false : h->canHandle(task));
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2014-11-20 16:47:00 +01:00
|
|
|
void TaskWindow::saveSettings()
|
|
|
|
|
{
|
|
|
|
|
QStringList categories = Utils::transform(d->m_filter->filteredCategories(), &Core::Id::toString);
|
|
|
|
|
SessionManager::setValue(QLatin1String(SESSION_FILTER_CATEGORIES), categories);
|
|
|
|
|
SessionManager::setValue(QLatin1String(SESSION_FILTER_WARNINGS), d->m_filter->filterIncludesWarnings());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskWindow::loadSettings()
|
|
|
|
|
{
|
|
|
|
|
QVariant value = SessionManager::value(QLatin1String(SESSION_FILTER_CATEGORIES));
|
|
|
|
|
if (value.isValid()) {
|
|
|
|
|
QList<Core::Id> categories
|
|
|
|
|
= Utils::transform(value.toStringList(), &Core::Id::fromString);
|
|
|
|
|
d->m_filter->setFilteredCategories(categories);
|
|
|
|
|
}
|
|
|
|
|
value = SessionManager::value(QLatin1String(SESSION_FILTER_WARNINGS));
|
|
|
|
|
if (value.isValid()) {
|
|
|
|
|
bool includeWarnings = value.toBool();
|
|
|
|
|
d->m_filter->setFilterIncludesWarnings(includeWarnings);
|
|
|
|
|
d->m_filter->setFilterIncludesUnknowns(includeWarnings);
|
|
|
|
|
d->m_filterWarningsButton->setDown(d->m_filter->filterIncludesWarnings());
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
void TaskWindow::visibilityChanged(bool visible)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2012-10-05 14:35:34 +02:00
|
|
|
if (visible)
|
|
|
|
|
delayedInitialization();
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2014-07-01 11:08:26 +02:00
|
|
|
void TaskWindow::addCategory(Core::Id categoryId, const QString &displayName, bool visible)
|
2009-11-11 09:54:13 +01:00
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_model->addCategory(categoryId, displayName);
|
2011-08-09 14:40:04 +02:00
|
|
|
if (!visible) {
|
2012-01-26 13:38:25 +01:00
|
|
|
QList<Core::Id> filters = d->m_filter->filteredCategories();
|
2011-08-09 14:40:04 +02:00
|
|
|
filters += categoryId;
|
|
|
|
|
d->m_filter->setFilteredCategories(filters);
|
|
|
|
|
}
|
2009-11-11 09:54:13 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskWindow::addTask(const Task &task)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_model->addTask(task);
|
2009-11-11 09:54:13 +01:00
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
emit tasksChanged();
|
2009-11-11 09:54:13 +01:00
|
|
|
navigateStateChanged();
|
2012-06-11 10:32:16 +02:00
|
|
|
|
2012-09-11 16:18:45 +02:00
|
|
|
if (task.type == Task::Error && d->m_filter->filterIncludesErrors()
|
2014-10-23 16:32:26 +02:00
|
|
|
&& !d->m_filter->filteredCategories().contains(task.category))
|
2012-06-11 10:32:16 +02:00
|
|
|
flash();
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2010-04-16 12:41:26 +02:00
|
|
|
void TaskWindow::removeTask(const Task &task)
|
|
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_model->removeTask(task);
|
2010-04-16 12:41:26 +02:00
|
|
|
|
|
|
|
|
emit tasksChanged();
|
|
|
|
|
navigateStateChanged();
|
|
|
|
|
}
|
|
|
|
|
|
2012-03-12 16:56:25 +01:00
|
|
|
void TaskWindow::updatedTaskFileName(unsigned int id, const QString &fileName)
|
|
|
|
|
{
|
|
|
|
|
d->m_model->updateTaskFileName(id, fileName);
|
|
|
|
|
emit tasksChanged();
|
|
|
|
|
}
|
|
|
|
|
|
2012-02-03 16:07:13 +01:00
|
|
|
void TaskWindow::updatedTaskLineNumber(unsigned int id, int line)
|
|
|
|
|
{
|
|
|
|
|
d->m_model->updateTaskLineNumber(id, line);
|
|
|
|
|
emit tasksChanged();
|
|
|
|
|
}
|
|
|
|
|
|
2012-02-29 16:15:25 +01:00
|
|
|
void TaskWindow::showTask(unsigned int id)
|
|
|
|
|
{
|
|
|
|
|
int sourceRow = d->m_model->rowForId(id);
|
|
|
|
|
QModelIndex sourceIdx = d->m_model->index(sourceRow, 0);
|
|
|
|
|
QModelIndex filterIdx = d->m_filter->mapFromSource(sourceIdx);
|
|
|
|
|
d->m_listview->setCurrentIndex(filterIdx);
|
2012-09-13 15:50:06 +02:00
|
|
|
popup(Core::IOutputPane::ModeSwitch);
|
2012-02-29 16:15:25 +01:00
|
|
|
}
|
|
|
|
|
|
2010-06-25 10:41:49 +02:00
|
|
|
void TaskWindow::openTask(unsigned int id)
|
|
|
|
|
{
|
|
|
|
|
int sourceRow = d->m_model->rowForId(id);
|
|
|
|
|
QModelIndex sourceIdx = d->m_model->index(sourceRow, 0);
|
|
|
|
|
QModelIndex filterIdx = d->m_filter->mapFromSource(sourceIdx);
|
|
|
|
|
triggerDefaultHandler(filterIdx);
|
|
|
|
|
}
|
|
|
|
|
|
2010-06-18 11:18:48 +02:00
|
|
|
void TaskWindow::triggerDefaultHandler(const QModelIndex &index)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2012-10-05 14:35:34 +02:00
|
|
|
if (!index.isValid() || !d->m_defaultHandler)
|
2008-12-02 12:01:29 +01:00
|
|
|
return;
|
|
|
|
|
|
2010-08-04 14:57:36 +02:00
|
|
|
Task task(d->m_filter->task(index));
|
|
|
|
|
if (task.isNull())
|
|
|
|
|
return;
|
|
|
|
|
|
2010-06-18 11:18:48 +02:00
|
|
|
if (d->m_defaultHandler->canHandle(task)) {
|
|
|
|
|
d->m_defaultHandler->handle(task);
|
|
|
|
|
} else {
|
2014-10-24 13:15:54 +02:00
|
|
|
if (!task.file.exists())
|
2010-06-18 11:18:48 +02:00
|
|
|
d->m_model->setFileNotFound(index, true);
|
2008-12-02 17:57:50 +01:00
|
|
|
}
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
void TaskWindow::actionTriggered()
|
2010-03-19 17:22:18 +01:00
|
|
|
{
|
2012-10-05 14:35:34 +02:00
|
|
|
QAction *action = qobject_cast<QAction *>(sender());
|
|
|
|
|
if (!action || !action->isEnabled())
|
|
|
|
|
return;
|
|
|
|
|
ITaskHandler *h = handler(action);
|
|
|
|
|
if (!h)
|
2010-03-19 17:22:18 +01:00
|
|
|
return;
|
2010-06-18 11:18:48 +02:00
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
QModelIndex index = d->m_listview->selectionModel()->currentIndex();
|
2010-08-04 14:57:36 +02:00
|
|
|
Task task = d->m_filter->task(index);
|
|
|
|
|
if (task.isNull())
|
|
|
|
|
return;
|
2010-06-18 11:18:48 +02:00
|
|
|
|
2012-10-05 14:35:34 +02:00
|
|
|
h->handle(task);
|
2008-12-03 21:50:31 +01:00
|
|
|
}
|
|
|
|
|
|
2009-07-16 12:11:32 +02:00
|
|
|
void TaskWindow::setShowWarnings(bool show)
|
|
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_filter->setFilterIncludesWarnings(show);
|
|
|
|
|
d->m_filter->setFilterIncludesUnknowns(show); // "Unknowns" are often associated with warnings
|
2009-07-16 12:11:32 +02:00
|
|
|
}
|
|
|
|
|
|
2009-11-11 12:36:44 +01:00
|
|
|
void TaskWindow::updateCategoriesMenu()
|
|
|
|
|
{
|
2013-03-19 18:27:04 +01:00
|
|
|
typedef QMap<QString, Core::Id>::ConstIterator NameToIdsConstIt;
|
2013-03-14 14:14:48 +01:00
|
|
|
|
2010-09-14 17:15:11 +02:00
|
|
|
d->m_categoriesMenu->clear();
|
2009-11-11 12:36:44 +01:00
|
|
|
|
2012-01-26 13:38:25 +01:00
|
|
|
const QList<Core::Id> filteredCategories = d->m_filter->filteredCategories();
|
2009-11-11 12:36:44 +01:00
|
|
|
|
2013-03-19 18:27:04 +01:00
|
|
|
QMap<QString, Core::Id> nameToIds;
|
2014-07-01 11:08:26 +02:00
|
|
|
foreach (Core::Id categoryId, d->m_model->categoryIds())
|
2013-03-19 18:27:04 +01:00
|
|
|
nameToIds.insert(d->m_model->categoryDisplayName(categoryId), categoryId);
|
2009-11-11 12:36:44 +01:00
|
|
|
|
2013-03-14 14:14:48 +01:00
|
|
|
const NameToIdsConstIt cend = nameToIds.constEnd();
|
|
|
|
|
for (NameToIdsConstIt it = nameToIds.constBegin(); it != cend; ++it) {
|
|
|
|
|
const QString &displayName = it.key();
|
2013-03-19 18:27:04 +01:00
|
|
|
const Core::Id categoryId = it.value();
|
2010-09-14 17:15:11 +02:00
|
|
|
QAction *action = new QAction(d->m_categoriesMenu);
|
2009-11-11 12:36:44 +01:00
|
|
|
action->setCheckable(true);
|
2011-10-12 15:48:59 +02:00
|
|
|
action->setText(displayName);
|
2013-03-19 18:27:04 +01:00
|
|
|
action->setChecked(!filteredCategories.contains(categoryId));
|
2015-03-03 23:43:37 +01:00
|
|
|
connect(action, &QAction::triggered, this, [this, action, categoryId] {
|
|
|
|
|
setCategoryVisibility(categoryId, action->isChecked());
|
|
|
|
|
});
|
2010-09-14 17:15:11 +02:00
|
|
|
d->m_categoriesMenu->addAction(action);
|
2009-11-11 12:36:44 +01:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2014-07-01 11:08:26 +02:00
|
|
|
int TaskWindow::taskCount(Core::Id category) const
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2011-09-20 09:42:10 +00:00
|
|
|
return d->m_model->taskCount(category);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2014-07-01 11:08:26 +02:00
|
|
|
int TaskWindow::errorTaskCount(Core::Id category) const
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2011-09-20 09:42:10 +00:00
|
|
|
return d->m_model->errorTaskCount(category);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2014-07-01 11:08:26 +02:00
|
|
|
int TaskWindow::warningTaskCount(Core::Id category) const
|
2011-06-07 17:53:46 +02:00
|
|
|
{
|
2011-09-20 09:42:10 +00:00
|
|
|
return d->m_model->warningTaskCount(category);
|
2011-06-07 17:53:46 +02:00
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
int TaskWindow::priorityInStatusBar() const
|
|
|
|
|
{
|
|
|
|
|
return 90;
|
|
|
|
|
}
|
|
|
|
|
|
2009-11-11 09:54:13 +01:00
|
|
|
void TaskWindow::clearContents()
|
|
|
|
|
{
|
2010-07-06 12:11:15 +02:00
|
|
|
// clear all tasks in all displays
|
|
|
|
|
// Yeah we are that special
|
2013-08-15 12:14:46 +02:00
|
|
|
TaskHub::clearTasks();
|
2009-11-11 09:54:13 +01:00
|
|
|
}
|
|
|
|
|
|
2011-09-27 13:47:06 +02:00
|
|
|
bool TaskWindow::hasFocus() const
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2014-11-07 15:48:36 +01:00
|
|
|
return d->m_listview->window()->focusWidget() == d->m_listview;
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2011-09-27 13:47:06 +02:00
|
|
|
bool TaskWindow::canFocus() const
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
return d->m_filter->rowCount();
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskWindow::setFocus()
|
|
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
if (d->m_filter->rowCount()) {
|
|
|
|
|
d->m_listview->setFocus();
|
Remove braces for single lines of conditions
#!/usr/bin/env ruby
Dir.glob('**/*.cpp') { |file|
# skip ast (excluding paste, astpath, and canv'ast'imer)
next if file =~ /ast[^eip]|keywords\.|qualifiers|preprocessor|names.cpp/i
s = File.read(file)
next if s.include?('qlalr')
orig = s.dup
s.gsub!(/\n *if [^\n]*{\n[^\n]*\n\s+}(\s+else if [^\n]* {\n[^\n]*\n\s+})*(\s+else {\n[^\n]*\n\s+})?\n/m) { |m|
res = $&
if res =~ /^\s*(\/\/|[A-Z_]{3,})/ # C++ comment or macro (Q_UNUSED, SDEBUG), do not touch braces
res
else
res.gsub!('} else', 'else')
res.gsub!(/\n +} *\n/m, "\n")
res.gsub(/ *{$/, '')
end
}
s.gsub!(/ *$/, '')
File.open(file, 'wb').write(s) if s != orig
}
Change-Id: I3b30ee60df0986f66c02132c65fc38a3fbb6bbdc
Reviewed-by: hjk <qthjk@ovi.com>
2013-01-08 03:32:53 +02:00
|
|
|
if (d->m_listview->currentIndex() == QModelIndex())
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_listview->setCurrentIndex(d->m_filter->index(0,0, QModelIndex()));
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2011-09-27 13:47:06 +02:00
|
|
|
bool TaskWindow::canNext() const
|
2009-04-30 12:50:52 +02:00
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
return d->m_filter->rowCount();
|
2009-04-30 12:50:52 +02:00
|
|
|
}
|
|
|
|
|
|
2011-09-27 13:47:06 +02:00
|
|
|
bool TaskWindow::canPrevious() const
|
2009-04-30 12:50:52 +02:00
|
|
|
{
|
2010-05-27 13:28:07 +02:00
|
|
|
return d->m_filter->rowCount();
|
2009-04-30 12:50:52 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskWindow::goToNext()
|
|
|
|
|
{
|
2010-08-25 18:07:53 +02:00
|
|
|
if (!canNext())
|
2009-04-30 12:50:52 +02:00
|
|
|
return;
|
2010-08-25 18:07:53 +02:00
|
|
|
QModelIndex startIndex = d->m_listview->currentIndex();
|
|
|
|
|
QModelIndex currentIndex = startIndex;
|
|
|
|
|
|
|
|
|
|
if (startIndex.isValid()) {
|
|
|
|
|
do {
|
|
|
|
|
int row = currentIndex.row() + 1;
|
|
|
|
|
if (row == d->m_filter->rowCount())
|
|
|
|
|
row = 0;
|
|
|
|
|
currentIndex = d->m_filter->index(row, 0);
|
|
|
|
|
if (d->m_filter->hasFile(currentIndex))
|
|
|
|
|
break;
|
|
|
|
|
} while (startIndex != currentIndex);
|
2009-04-30 12:50:52 +02:00
|
|
|
} else {
|
2010-05-27 13:28:07 +02:00
|
|
|
currentIndex = d->m_filter->index(0, 0);
|
2009-04-30 12:50:52 +02:00
|
|
|
}
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_listview->setCurrentIndex(currentIndex);
|
2010-06-18 11:18:48 +02:00
|
|
|
triggerDefaultHandler(currentIndex);
|
2009-04-30 12:50:52 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskWindow::goToPrev()
|
|
|
|
|
{
|
2010-08-25 18:07:53 +02:00
|
|
|
if (!canPrevious())
|
2009-04-30 12:50:52 +02:00
|
|
|
return;
|
2010-08-25 18:07:53 +02:00
|
|
|
QModelIndex startIndex = d->m_listview->currentIndex();
|
|
|
|
|
QModelIndex currentIndex = startIndex;
|
|
|
|
|
|
|
|
|
|
if (startIndex.isValid()) {
|
|
|
|
|
do {
|
|
|
|
|
int row = currentIndex.row() - 1;
|
|
|
|
|
if (row < 0)
|
|
|
|
|
row = d->m_filter->rowCount() - 1;
|
|
|
|
|
currentIndex = d->m_filter->index(row, 0);
|
|
|
|
|
if (d->m_filter->hasFile(currentIndex))
|
|
|
|
|
break;
|
|
|
|
|
} while (startIndex != currentIndex);
|
2009-04-30 12:50:52 +02:00
|
|
|
} else {
|
2010-08-25 18:07:53 +02:00
|
|
|
currentIndex = d->m_filter->index(0, 0);
|
2009-04-30 12:50:52 +02:00
|
|
|
}
|
2010-05-27 13:28:07 +02:00
|
|
|
d->m_listview->setCurrentIndex(currentIndex);
|
2010-06-18 11:18:48 +02:00
|
|
|
triggerDefaultHandler(currentIndex);
|
2009-04-30 12:50:52 +02:00
|
|
|
}
|
|
|
|
|
|
2011-09-27 13:47:06 +02:00
|
|
|
bool TaskWindow::canNavigate() const
|
2009-04-30 12:50:52 +02:00
|
|
|
{
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
/////
|
|
|
|
|
// Delegate
|
|
|
|
|
/////
|
|
|
|
|
|
2011-09-20 09:42:10 +00:00
|
|
|
TaskDelegate::TaskDelegate(QObject *parent) :
|
|
|
|
|
QStyledItemDelegate(parent),
|
|
|
|
|
m_cachedHeight(0)
|
|
|
|
|
{ }
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
TaskDelegate::~TaskDelegate()
|
|
|
|
|
{
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
QSize TaskDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
|
QStyleOptionViewItemV4 opt = option;
|
|
|
|
|
initStyleOption(&opt, index);
|
|
|
|
|
|
2011-09-20 09:42:10 +00:00
|
|
|
const QAbstractItemView * view = qobject_cast<const QAbstractItemView *>(opt.widget);
|
|
|
|
|
const bool selected = (view->selectionModel()->currentIndex() == index);
|
|
|
|
|
QSize s;
|
|
|
|
|
s.setWidth(option.rect.width());
|
|
|
|
|
|
|
|
|
|
if (!selected && option.font == m_cachedFont && m_cachedHeight > 0) {
|
|
|
|
|
s.setHeight(m_cachedHeight);
|
|
|
|
|
return s;
|
|
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
QFontMetrics fm(option.font);
|
2009-03-27 13:37:24 +01:00
|
|
|
int fontHeight = fm.height();
|
|
|
|
|
int fontLeading = fm.leading();
|
|
|
|
|
|
2009-07-16 12:11:32 +02:00
|
|
|
TaskModel *model = static_cast<TaskFilterModel *>(view->model())->taskModel();
|
2010-10-20 11:33:23 +02:00
|
|
|
Positions positions(option, model);
|
|
|
|
|
|
2011-09-20 09:42:10 +00:00
|
|
|
if (selected) {
|
2008-12-02 12:01:29 +01:00
|
|
|
QString description = index.data(TaskModel::Description).toString();
|
|
|
|
|
// Layout the description
|
2009-03-27 13:37:24 +01:00
|
|
|
int leading = fontLeading;
|
2008-12-02 12:01:29 +01:00
|
|
|
int height = 0;
|
2012-01-09 16:30:33 +01:00
|
|
|
description.replace(QLatin1Char('\n'), QChar::LineSeparator);
|
2008-12-02 12:01:29 +01:00
|
|
|
QTextLayout tl(description);
|
2014-10-13 22:37:28 +03:00
|
|
|
tl.setAdditionalFormats(index.data(TaskModel::Task_t).value<Task>().formats);
|
2008-12-02 12:01:29 +01:00
|
|
|
tl.beginLayout();
|
2008-12-09 11:07:24 +01:00
|
|
|
while (true) {
|
2008-12-02 12:01:29 +01:00
|
|
|
QTextLine line = tl.createLine();
|
|
|
|
|
if (!line.isValid())
|
|
|
|
|
break;
|
2010-10-20 11:33:23 +02:00
|
|
|
line.setLineWidth(positions.textAreaWidth());
|
2008-12-02 12:01:29 +01:00
|
|
|
height += leading;
|
|
|
|
|
line.setPosition(QPoint(0, height));
|
|
|
|
|
height += static_cast<int>(line.height());
|
|
|
|
|
}
|
|
|
|
|
tl.endLayout();
|
|
|
|
|
|
2009-03-27 13:37:24 +01:00
|
|
|
s.setHeight(height + leading + fontHeight + 3);
|
2008-12-02 12:01:29 +01:00
|
|
|
} else {
|
2009-03-27 13:37:24 +01:00
|
|
|
s.setHeight(fontHeight + 3);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
2010-10-20 11:33:23 +02:00
|
|
|
if (s.height() < positions.minimumHeight())
|
|
|
|
|
s.setHeight(positions.minimumHeight());
|
2011-09-20 09:42:10 +00:00
|
|
|
|
|
|
|
|
if (!selected) {
|
|
|
|
|
m_cachedHeight = s.height();
|
|
|
|
|
m_cachedFont = option.font;
|
|
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
return s;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskDelegate::emitSizeHintChanged(const QModelIndex &index)
|
|
|
|
|
{
|
|
|
|
|
emit sizeHintChanged(index);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskDelegate::currentChanged(const QModelIndex ¤t, const QModelIndex &previous)
|
|
|
|
|
{
|
|
|
|
|
emit sizeHintChanged(current);
|
|
|
|
|
emit sizeHintChanged(previous);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void TaskDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
|
QStyleOptionViewItemV4 opt = option;
|
|
|
|
|
initStyleOption(&opt, index);
|
|
|
|
|
painter->save();
|
|
|
|
|
|
|
|
|
|
QFontMetrics fm(opt.font);
|
|
|
|
|
QColor backgroundColor;
|
|
|
|
|
QColor textColor;
|
|
|
|
|
|
|
|
|
|
const QAbstractItemView * view = qobject_cast<const QAbstractItemView *>(opt.widget);
|
|
|
|
|
bool selected = view->selectionModel()->currentIndex() == index;
|
|
|
|
|
|
|
|
|
|
if (selected) {
|
|
|
|
|
painter->setBrush(opt.palette.highlight().color());
|
|
|
|
|
backgroundColor = opt.palette.highlight().color();
|
|
|
|
|
} else {
|
|
|
|
|
painter->setBrush(opt.palette.background().color());
|
|
|
|
|
backgroundColor = opt.palette.background().color();
|
|
|
|
|
}
|
|
|
|
|
painter->setPen(Qt::NoPen);
|
|
|
|
|
painter->drawRect(opt.rect);
|
|
|
|
|
|
|
|
|
|
// Set Text Color
|
|
|
|
|
if (selected)
|
|
|
|
|
textColor = opt.palette.highlightedText().color();
|
|
|
|
|
else
|
|
|
|
|
textColor = opt.palette.text().color();
|
|
|
|
|
|
|
|
|
|
painter->setPen(textColor);
|
|
|
|
|
|
2011-11-03 17:33:11 -04:00
|
|
|
TaskModel *model = static_cast<TaskFilterModel *>(view->model())->taskModel();
|
2010-10-20 11:33:23 +02:00
|
|
|
Positions positions(opt, model);
|
|
|
|
|
|
|
|
|
|
// Paint TaskIconArea:
|
2010-04-19 16:03:28 +02:00
|
|
|
QIcon icon = index.data(TaskModel::Icon).value<QIcon>();
|
2010-10-20 11:33:23 +02:00
|
|
|
painter->drawPixmap(positions.left(), positions.top(),
|
|
|
|
|
icon.pixmap(positions.taskIconWidth(), positions.taskIconHeight()));
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2010-10-20 11:33:23 +02:00
|
|
|
// Paint TextArea:
|
2010-01-29 21:33:57 +01:00
|
|
|
if (!selected) {
|
2008-12-02 12:01:29 +01:00
|
|
|
// in small mode we lay out differently
|
2012-01-09 16:30:33 +01:00
|
|
|
QString bottom = index.data(TaskModel::Description).toString().split(QLatin1Char('\n')).first();
|
2010-10-20 11:33:23 +02:00
|
|
|
painter->setClipRect(positions.textArea());
|
|
|
|
|
painter->drawText(positions.textAreaLeft(), positions.top() + fm.ascent(), bottom);
|
|
|
|
|
if (fm.width(bottom) > positions.textAreaWidth()) {
|
2008-12-02 12:01:29 +01:00
|
|
|
// draw a gradient to mask the text
|
2010-10-20 11:33:23 +02:00
|
|
|
int gradientStart = positions.textAreaRight() - ELLIPSIS_GRADIENT_WIDTH + 1;
|
|
|
|
|
QLinearGradient lg(gradientStart, 0, gradientStart + ELLIPSIS_GRADIENT_WIDTH, 0);
|
|
|
|
|
lg.setColorAt(0, Qt::transparent);
|
|
|
|
|
lg.setColorAt(1, backgroundColor);
|
|
|
|
|
painter->fillRect(gradientStart, positions.top(), ELLIPSIS_GRADIENT_WIDTH, positions.firstLineHeight(), lg);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
} else {
|
2008-12-03 21:50:31 +01:00
|
|
|
// Description
|
2008-12-02 12:01:29 +01:00
|
|
|
QString description = index.data(TaskModel::Description).toString();
|
|
|
|
|
// Layout the description
|
|
|
|
|
int leading = fm.leading();
|
|
|
|
|
int height = 0;
|
2012-01-09 16:30:33 +01:00
|
|
|
description.replace(QLatin1Char('\n'), QChar::LineSeparator);
|
2008-12-02 12:01:29 +01:00
|
|
|
QTextLayout tl(description);
|
2014-10-13 22:37:28 +03:00
|
|
|
tl.setAdditionalFormats(index.data(TaskModel::Task_t).value<Task>().formats);
|
2008-12-02 12:01:29 +01:00
|
|
|
tl.beginLayout();
|
2008-12-09 11:07:24 +01:00
|
|
|
while (true) {
|
2008-12-02 12:01:29 +01:00
|
|
|
QTextLine line = tl.createLine();
|
|
|
|
|
if (!line.isValid())
|
|
|
|
|
break;
|
2010-10-20 11:33:23 +02:00
|
|
|
line.setLineWidth(positions.textAreaWidth());
|
2008-12-02 12:01:29 +01:00
|
|
|
height += leading;
|
|
|
|
|
line.setPosition(QPoint(0, height));
|
|
|
|
|
height += static_cast<int>(line.height());
|
|
|
|
|
}
|
|
|
|
|
tl.endLayout();
|
2010-10-20 11:33:23 +02:00
|
|
|
tl.draw(painter, QPoint(positions.textAreaLeft(), positions.top()));
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
QColor mix;
|
|
|
|
|
mix.setRgb( static_cast<int>(0.7 * textColor.red() + 0.3 * backgroundColor.red()),
|
|
|
|
|
static_cast<int>(0.7 * textColor.green() + 0.3 * backgroundColor.green()),
|
|
|
|
|
static_cast<int>(0.7 * textColor.blue() + 0.3 * backgroundColor.blue()));
|
|
|
|
|
painter->setPen(mix);
|
|
|
|
|
|
2009-04-15 16:34:37 +02:00
|
|
|
const QString directory = QDir::toNativeSeparators(index.data(TaskModel::File).toString());
|
2010-10-20 11:33:23 +02:00
|
|
|
int secondBaseLine = positions.top() + fm.ascent() + height + leading;
|
2013-01-17 15:45:04 +01:00
|
|
|
if (index.data(TaskModel::FileNotFound).toBool()
|
|
|
|
|
&& !directory.isEmpty()) {
|
2008-12-02 12:01:29 +01:00
|
|
|
QString fileNotFound = tr("File not found: %1").arg(directory);
|
|
|
|
|
painter->setPen(Qt::red);
|
2010-10-20 11:33:23 +02:00
|
|
|
painter->drawText(positions.textAreaLeft(), secondBaseLine, fileNotFound);
|
2008-12-02 12:01:29 +01:00
|
|
|
} else {
|
2010-10-20 11:33:23 +02:00
|
|
|
painter->drawText(positions.textAreaLeft(), secondBaseLine, directory);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
painter->setPen(textColor);
|
2010-10-20 11:33:23 +02:00
|
|
|
|
|
|
|
|
// Paint FileArea
|
2008-12-02 12:01:29 +01:00
|
|
|
QString file = index.data(TaskModel::File).toString();
|
2010-02-01 12:43:56 +01:00
|
|
|
const int pos = file.lastIndexOf(QLatin1Char('/'));
|
2008-12-02 12:01:29 +01:00
|
|
|
if (pos != -1)
|
|
|
|
|
file = file.mid(pos +1);
|
2010-10-20 11:33:23 +02:00
|
|
|
const int realFileWidth = fm.width(file);
|
|
|
|
|
painter->setClipRect(positions.fileArea());
|
|
|
|
|
painter->drawText(qMin(positions.fileAreaLeft(), positions.fileAreaRight() - realFileWidth),
|
|
|
|
|
positions.top() + fm.ascent(), file);
|
|
|
|
|
if (realFileWidth > positions.fileAreaWidth()) {
|
|
|
|
|
// draw a gradient to mask the text
|
|
|
|
|
int gradientStart = positions.fileAreaLeft() - 1;
|
|
|
|
|
QLinearGradient lg(gradientStart + ELLIPSIS_GRADIENT_WIDTH, 0, gradientStart, 0);
|
|
|
|
|
lg.setColorAt(0, Qt::transparent);
|
|
|
|
|
lg.setColorAt(1, backgroundColor);
|
|
|
|
|
painter->fillRect(gradientStart, positions.top(), ELLIPSIS_GRADIENT_WIDTH, positions.firstLineHeight(), lg);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Paint LineArea
|
2012-02-03 16:07:13 +01:00
|
|
|
int line = index.data(TaskModel::Line).toInt();
|
|
|
|
|
int movedLine = index.data(TaskModel::MovedLine).toInt();
|
|
|
|
|
QString lineText;
|
|
|
|
|
|
|
|
|
|
if (line == -1) {
|
|
|
|
|
// No line information at all
|
|
|
|
|
} else if (movedLine == -1) {
|
|
|
|
|
// removed the line, but we had line information, show the line in ()
|
|
|
|
|
QFont f = painter->font();
|
|
|
|
|
f.setItalic(true);
|
|
|
|
|
painter->setFont(f);
|
2012-03-06 19:27:49 +01:00
|
|
|
lineText = QLatin1Char('(') + QString::number(line) + QLatin1Char(')');
|
2012-02-03 16:07:13 +01:00
|
|
|
} else if (movedLine != line) {
|
|
|
|
|
// The line was moved
|
|
|
|
|
QFont f = painter->font();
|
|
|
|
|
f.setItalic(true);
|
|
|
|
|
painter->setFont(f);
|
|
|
|
|
lineText = QString::number(movedLine);
|
|
|
|
|
} else {
|
|
|
|
|
lineText = QString::number(line);
|
|
|
|
|
}
|
|
|
|
|
|
2010-10-20 11:33:23 +02:00
|
|
|
painter->setClipRect(positions.lineArea());
|
|
|
|
|
const int realLineWidth = fm.width(lineText);
|
|
|
|
|
painter->drawText(positions.lineAreaRight() - realLineWidth, positions.top() + fm.ascent(), lineText);
|
|
|
|
|
painter->setClipRect(opt.rect);
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
// Separator lines
|
|
|
|
|
painter->setPen(QColor::fromRgb(150,150,150));
|
|
|
|
|
painter->drawLine(0, opt.rect.bottom(), opt.rect.right(), opt.rect.bottom());
|
|
|
|
|
painter->restore();
|
|
|
|
|
}
|
2008-12-03 21:50:31 +01:00
|
|
|
|
|
|
|
|
TaskWindowContext::TaskWindowContext(QWidget *widget)
|
2011-04-13 13:00:30 +02:00
|
|
|
: Core::IContext(widget)
|
2008-12-03 21:50:31 +01:00
|
|
|
{
|
2011-04-13 13:00:30 +02:00
|
|
|
setWidget(widget);
|
|
|
|
|
setContext(Core::Context(Core::Constants::C_PROBLEM_PANE));
|
2008-12-03 21:50:31 +01:00
|
|
|
}
|
|
|
|
|
|
2010-05-27 13:28:07 +02:00
|
|
|
} // namespace Internal
|
|
|
|
|
} // namespace ProjectExplorer
|
|
|
|
|
|
2009-11-11 09:54:13 +01:00
|
|
|
#include "taskwindow.moc"
|