forked from qt-creator/qt-creator
Utils: Allow BaseTreeView users to hide columns manually
... using a context menu on the header views. Use the feature in the debugger views where it was previously un-intuitively available as part of the main context menu of the view, but not in the header. Task-number: QTCREATORBUG-24384 Change-Id: I3f030c3dd8ce35dc91bad921e37d2273bfe548b5 Reviewed-by: Eike Ziller <eike.ziller@qt.io> Reviewed-by: Christian Stenger <christian.stenger@qt.io>
This commit is contained in:
@@ -552,6 +552,33 @@ void BaseTreeView::setSpanColumn(int column)
|
|||||||
d->setSpanColumn(column);
|
d->setSpanColumn(column);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void BaseTreeView::enableColumnHiding()
|
||||||
|
{
|
||||||
|
header()->setContextMenuPolicy(Qt::CustomContextMenu);
|
||||||
|
connect(header(), &QWidget::customContextMenuRequested, this, [this](const QPoint &pos) {
|
||||||
|
QTC_ASSERT(model(), return);
|
||||||
|
const int columns = model()->columnCount();
|
||||||
|
QMenu menu;
|
||||||
|
int shown = 0;
|
||||||
|
for (int i = 0; i < columns; ++i)
|
||||||
|
shown += !isColumnHidden(i);
|
||||||
|
for (int i = 0; i < columns; ++i) {
|
||||||
|
QString columnName = model()->headerData(i, Qt::Horizontal).toString();
|
||||||
|
QAction *act = menu.addAction(tr("Show %1 Column").arg(columnName));
|
||||||
|
act->setCheckable(true);
|
||||||
|
act->setChecked(!isColumnHidden(i));
|
||||||
|
// Prevent disabling the last visible column as there's no way back.
|
||||||
|
if (shown == 1 && !isColumnHidden(i))
|
||||||
|
act->setEnabled(false);
|
||||||
|
QObject::connect(act, &QAction::toggled, &menu, [this, i](bool on) {
|
||||||
|
setColumnHidden(i, !on);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
menu.addSeparator();
|
||||||
|
menu.exec(mapToGlobal(pos));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
void BaseTreeView::refreshSpanColumn()
|
void BaseTreeView::refreshSpanColumn()
|
||||||
{
|
{
|
||||||
d->rebalanceColumns();
|
d->rebalanceColumns();
|
||||||
|
@@ -78,6 +78,8 @@ public:
|
|||||||
int spanColumn() const;
|
int spanColumn() const;
|
||||||
void setSpanColumn(int column);
|
void setSpanColumn(int column);
|
||||||
|
|
||||||
|
void enableColumnHiding();
|
||||||
|
|
||||||
// In some situations this needs to be called when manually resizing columns when the span
|
// In some situations this needs to be called when manually resizing columns when the span
|
||||||
// column is set.
|
// column is set.
|
||||||
void refreshSpanColumn();
|
void refreshSpanColumn();
|
||||||
|
@@ -1671,7 +1671,6 @@ bool BreakHandler::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
menu->addSeparator();
|
menu->addSeparator();
|
||||||
|
|
||||||
menu->addAction(action(UseToolTipsInBreakpointsView)->action());
|
menu->addAction(action(UseToolTipsInBreakpointsView)->action());
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
|
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
@@ -2632,7 +2631,6 @@ bool BreakpointManager::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
menu->addSeparator();
|
menu->addSeparator();
|
||||||
|
|
||||||
menu->addAction(action(UseToolTipsInBreakpointsView)->action());
|
menu->addAction(action(UseToolTipsInBreakpointsView)->action());
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
|
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
|
@@ -73,9 +73,6 @@ QAction *addAction(QMenu *menu, const QString &d1, const QString &d2, bool on,
|
|||||||
QAction *addCheckableAction(QMenu *menu, const QString &display, bool on, bool checked,
|
QAction *addCheckableAction(QMenu *menu, const QString &display, bool on, bool checked,
|
||||||
const std::function<void()> &onTriggered);
|
const std::function<void()> &onTriggered);
|
||||||
|
|
||||||
void addHideColumnActions(QMenu *menu, QWidget *widget);
|
|
||||||
|
|
||||||
|
|
||||||
// Qt's various build paths for unpatched versions
|
// Qt's various build paths for unpatched versions
|
||||||
QStringList qtBuildPaths();
|
QStringList qtBuildPaths();
|
||||||
|
|
||||||
|
@@ -635,6 +635,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_modulesView->setModel(m_modulesHandler.model());
|
m_modulesView->setModel(m_modulesHandler.model());
|
||||||
m_modulesView->setSortingEnabled(true);
|
m_modulesView->setSortingEnabled(true);
|
||||||
m_modulesView->setSettings(settings, "Debugger.ModulesView");
|
m_modulesView->setSettings(settings, "Debugger.ModulesView");
|
||||||
|
m_modulesView->enableColumnHiding();
|
||||||
connect(m_modulesView, &BaseTreeView::aboutToShow,
|
connect(m_modulesView, &BaseTreeView::aboutToShow,
|
||||||
m_engine, &DebuggerEngine::reloadModules,
|
m_engine, &DebuggerEngine::reloadModules,
|
||||||
Qt::QueuedConnection);
|
Qt::QueuedConnection);
|
||||||
@@ -646,6 +647,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_registerView->setModel(m_registerHandler.model());
|
m_registerView->setModel(m_registerHandler.model());
|
||||||
m_registerView->setRootIsDecorated(true);
|
m_registerView->setRootIsDecorated(true);
|
||||||
m_registerView->setSettings(settings, "Debugger.RegisterView");
|
m_registerView->setSettings(settings, "Debugger.RegisterView");
|
||||||
|
m_registerView->enableColumnHiding();
|
||||||
connect(m_registerView, &BaseTreeView::aboutToShow,
|
connect(m_registerView, &BaseTreeView::aboutToShow,
|
||||||
m_engine, &DebuggerEngine::reloadRegisters,
|
m_engine, &DebuggerEngine::reloadRegisters,
|
||||||
Qt::QueuedConnection);
|
Qt::QueuedConnection);
|
||||||
@@ -657,6 +659,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_peripheralRegisterView->setModel(m_peripheralRegisterHandler.model());
|
m_peripheralRegisterView->setModel(m_peripheralRegisterHandler.model());
|
||||||
m_peripheralRegisterView->setRootIsDecorated(true);
|
m_peripheralRegisterView->setRootIsDecorated(true);
|
||||||
m_peripheralRegisterView->setSettings(settings, "Debugger.PeripheralRegisterView");
|
m_peripheralRegisterView->setSettings(settings, "Debugger.PeripheralRegisterView");
|
||||||
|
m_peripheralRegisterView->enableColumnHiding();
|
||||||
connect(m_peripheralRegisterView, &BaseTreeView::aboutToShow,
|
connect(m_peripheralRegisterView, &BaseTreeView::aboutToShow,
|
||||||
m_engine, &DebuggerEngine::reloadPeripheralRegisters,
|
m_engine, &DebuggerEngine::reloadPeripheralRegisters,
|
||||||
Qt::QueuedConnection);
|
Qt::QueuedConnection);
|
||||||
@@ -668,6 +671,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_stackView->setModel(m_stackHandler.model());
|
m_stackView->setModel(m_stackHandler.model());
|
||||||
m_stackView->setSettings(settings, "Debugger.StackView");
|
m_stackView->setSettings(settings, "Debugger.StackView");
|
||||||
m_stackView->setIconSize(QSize(10, 10));
|
m_stackView->setIconSize(QSize(10, 10));
|
||||||
|
m_stackView->enableColumnHiding();
|
||||||
m_stackWindow = addSearch(m_stackView);
|
m_stackWindow = addSearch(m_stackView);
|
||||||
m_stackWindow->setObjectName("Debugger.Dock.Stack." + engineId);
|
m_stackWindow->setObjectName("Debugger.Dock.Stack." + engineId);
|
||||||
m_stackWindow->setWindowTitle(tr("&Stack"));
|
m_stackWindow->setWindowTitle(tr("&Stack"));
|
||||||
@@ -676,6 +680,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_sourceFilesView->setModel(m_sourceFilesHandler.model());
|
m_sourceFilesView->setModel(m_sourceFilesHandler.model());
|
||||||
m_sourceFilesView->setSortingEnabled(true);
|
m_sourceFilesView->setSortingEnabled(true);
|
||||||
m_sourceFilesView->setSettings(settings, "Debugger.SourceFilesView");
|
m_sourceFilesView->setSettings(settings, "Debugger.SourceFilesView");
|
||||||
|
m_sourceFilesView->enableColumnHiding();
|
||||||
connect(m_sourceFilesView, &BaseTreeView::aboutToShow,
|
connect(m_sourceFilesView, &BaseTreeView::aboutToShow,
|
||||||
m_engine, &DebuggerEngine::reloadSourceFiles,
|
m_engine, &DebuggerEngine::reloadSourceFiles,
|
||||||
Qt::QueuedConnection);
|
Qt::QueuedConnection);
|
||||||
@@ -689,6 +694,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_threadsView->setSettings(settings, "Debugger.ThreadsView");
|
m_threadsView->setSettings(settings, "Debugger.ThreadsView");
|
||||||
m_threadsView->setIconSize(QSize(10, 10));
|
m_threadsView->setIconSize(QSize(10, 10));
|
||||||
m_threadsView->setSpanColumn(ThreadData::FunctionColumn);
|
m_threadsView->setSpanColumn(ThreadData::FunctionColumn);
|
||||||
|
m_threadsView->enableColumnHiding();
|
||||||
m_threadsWindow = addSearch(m_threadsView);
|
m_threadsWindow = addSearch(m_threadsView);
|
||||||
m_threadsWindow->setObjectName("Debugger.Dock.Threads." + engineId);
|
m_threadsWindow->setObjectName("Debugger.Dock.Threads." + engineId);
|
||||||
m_threadsWindow->setWindowTitle(tr("&Threads"));
|
m_threadsWindow->setWindowTitle(tr("&Threads"));
|
||||||
@@ -738,6 +744,7 @@ void DebuggerEnginePrivate::setupViews()
|
|||||||
m_breakView->setSettings(settings, "Debugger.BreakWindow");
|
m_breakView->setSettings(settings, "Debugger.BreakWindow");
|
||||||
m_breakView->setModel(m_breakHandler.model());
|
m_breakView->setModel(m_breakHandler.model());
|
||||||
m_breakView->setRootIsDecorated(true);
|
m_breakView->setRootIsDecorated(true);
|
||||||
|
m_breakView->enableColumnHiding();
|
||||||
m_breakWindow = addSearch(m_breakView);
|
m_breakWindow = addSearch(m_breakView);
|
||||||
m_breakWindow->setObjectName("Debugger.Dock.Break." + engineId);
|
m_breakWindow->setObjectName("Debugger.Dock.Break." + engineId);
|
||||||
m_breakWindow->setWindowTitle(tr("&Breakpoints"));
|
m_breakWindow->setWindowTitle(tr("&Breakpoints"));
|
||||||
|
@@ -459,26 +459,6 @@ QAction *addCheckableAction(QMenu *menu, const QString &display, bool on, bool c
|
|||||||
return act;
|
return act;
|
||||||
}
|
}
|
||||||
|
|
||||||
void addHideColumnActions(QMenu *menu, QWidget *widget)
|
|
||||||
{
|
|
||||||
QTreeView *view = qobject_cast<QTreeView *>(widget);
|
|
||||||
QTC_ASSERT(view, return);
|
|
||||||
QAbstractItemModel *model = view->model();
|
|
||||||
QTC_ASSERT(model, return);
|
|
||||||
const int columns = model->columnCount();
|
|
||||||
menu->addSeparator();
|
|
||||||
for (int i = 0; i < columns; ++i) {
|
|
||||||
QString columnName = model->headerData(i, Qt::Horizontal).toString();
|
|
||||||
QAction *act = menu->addAction(DebuggerPlugin::tr("Show %1 Column").arg(columnName));
|
|
||||||
act->setCheckable(true);
|
|
||||||
act->setChecked(!view->isColumnHidden(i));
|
|
||||||
QObject::connect(act, &QAction::toggled, menu, [view, i](bool on) {
|
|
||||||
view->setColumnHidden(i, !on);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
menu->addSeparator();
|
|
||||||
}
|
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// DebugMode
|
// DebugMode
|
||||||
@@ -840,6 +820,7 @@ DebuggerPluginPrivate::DebuggerPluginPrivate(const QStringList &arguments)
|
|||||||
breakpointManagerView->setRootIsDecorated(true);
|
breakpointManagerView->setRootIsDecorated(true);
|
||||||
breakpointManagerView->setModel(BreakpointManager::model());
|
breakpointManagerView->setModel(BreakpointManager::model());
|
||||||
breakpointManagerView->setSpanColumn(BreakpointFunctionColumn);
|
breakpointManagerView->setSpanColumn(BreakpointFunctionColumn);
|
||||||
|
breakpointManagerView->enableColumnHiding();
|
||||||
|
|
||||||
auto breakpointManagerWindow = addSearch(breakpointManagerView);
|
auto breakpointManagerWindow = addSearch(breakpointManagerView);
|
||||||
breakpointManagerWindow->setWindowTitle(tr("Breakpoint Preset"));
|
breakpointManagerWindow->setWindowTitle(tr("Breakpoint Preset"));
|
||||||
@@ -854,6 +835,7 @@ DebuggerPluginPrivate::DebuggerPluginPrivate(const QStringList &arguments)
|
|||||||
engineManagerView->setIconSize(QSize(10, 10));
|
engineManagerView->setIconSize(QSize(10, 10));
|
||||||
engineManagerView->setModel(m_engineManager.model());
|
engineManagerView->setModel(m_engineManager.model());
|
||||||
engineManagerView->setSelectionMode(QAbstractItemView::SingleSelection);
|
engineManagerView->setSelectionMode(QAbstractItemView::SingleSelection);
|
||||||
|
engineManagerView->enableColumnHiding();
|
||||||
|
|
||||||
auto engineManagerWindow = addSearch(engineManagerView);
|
auto engineManagerWindow = addSearch(engineManagerView);
|
||||||
engineManagerWindow->setWindowTitle(tr("Debugger Perspectives"));
|
engineManagerWindow->setWindowTitle(tr("Debugger Perspectives"));
|
||||||
|
@@ -223,7 +223,6 @@ bool ModulesModel::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
canShowSymbols && moduleNameValid,
|
canShowSymbols && moduleNameValid,
|
||||||
[this, modulePath] { engine->requestModuleSections(modulePath); });
|
[this, modulePath] { engine->requestModuleSections(modulePath); });
|
||||||
|
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
|
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
|
@@ -786,7 +786,6 @@ bool PeripheralRegisterHandler::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
menu->addMenu(fmtMenu);
|
menu->addMenu(fmtMenu);
|
||||||
}
|
}
|
||||||
|
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
return true;
|
return true;
|
||||||
|
@@ -756,7 +756,6 @@ bool RegisterHandler::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
addFormatAction(tr("Octal"), OctalFormat);
|
addFormatAction(tr("Octal"), OctalFormat);
|
||||||
addFormatAction(tr("Binary"), BinaryFormat);
|
addFormatAction(tr("Binary"), BinaryFormat);
|
||||||
|
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
return true;
|
return true;
|
||||||
|
@@ -137,7 +137,6 @@ bool SourceFilesHandler::setData(const QModelIndex &idx, const QVariant &data, i
|
|||||||
addAction(tr("Open File \"%1\"").arg(name), true,
|
addAction(tr("Open File \"%1\"").arg(name), true,
|
||||||
[this, name] { m_engine->gotoLocation(FilePath::fromString(name)); });
|
[this, name] { m_engine->gotoLocation(FilePath::fromString(name)); });
|
||||||
|
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
return true;
|
return true;
|
||||||
|
@@ -517,7 +517,6 @@ bool StackHandler::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
|
|
||||||
menu->addSeparator();
|
menu->addSeparator();
|
||||||
menu->addAction(action(UseToolTipsInStackView)->action());
|
menu->addAction(action(UseToolTipsInStackView)->action());
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
return true;
|
return true;
|
||||||
|
@@ -258,7 +258,6 @@ bool ThreadsHandler::setData(const QModelIndex &idx, const QVariant &data, int r
|
|||||||
|
|
||||||
if (ev.as<QContextMenuEvent>()) {
|
if (ev.as<QContextMenuEvent>()) {
|
||||||
auto menu = new QMenu;
|
auto menu = new QMenu;
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
return true;
|
return true;
|
||||||
|
@@ -1745,8 +1745,6 @@ bool WatchModel::contextMenuEvent(const ItemViewEvent &ev)
|
|||||||
menu->addAction(action(UseDynamicType)->action());
|
menu->addAction(action(UseDynamicType)->action());
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
menu->addAction(action(SettingsDialog)->action());
|
||||||
|
|
||||||
Internal::addHideColumnActions(menu, ev.view());
|
|
||||||
menu->addAction(action(SettingsDialog)->action());
|
|
||||||
connect(menu, &QMenu::aboutToHide, menu, &QObject::deleteLater);
|
connect(menu, &QMenu::aboutToHide, menu, &QObject::deleteLater);
|
||||||
menu->popup(ev.globalPos());
|
menu->popup(ev.globalPos());
|
||||||
return true;
|
return true;
|
||||||
|
Reference in New Issue
Block a user