Custom context menu in QTreeView
Hi all,
I have a QTreeView and QStandardItemModel and want to add a context menu so that new child node(s) can be added to the current node.
At construction, I'd like to have three empty tree nodes
<checkbox><icon>Rectangles
<checkbox><icon>Circles
<checkbox><icon>Squares
and to enable a right click on each of those nodes to add/delete/modify. I started with an ActionsContextMenu but then I need the node's index, so I successfully created a custom context menu.
Code:
...
// set context menu policy
projectTreeView->setContextMenuPolicy(Qt::CustomContextMenu);
...
// initialize the model with three empty nodes
for (int i=0; i<3; ++i) {
model->appendRow(m_dm[i]);
}
m_ui.projectTreeView->setModel(model);
...
// create an add action and connect it to a signal
m_addAction
= new QAction(tr
("Add new"), m_ui.
projectTreeView);
connect(m_addAction, SIGNAL(triggered()), this, SLOT(addObject()));
// connect custom context menu
connect(m_ui.
projectTreeView,
SIGNAL(customContextMenuRequested
( const QPoint
& )),
this,
SLOT(showContextMenu
(const QPoint &)));
...
void showContextMenu(const QPoint& pnt)
{
QList<QAction *> actions;
if (m_ui.projectTreeView->indexAt(pnt).isValid()) {
actions.append(m_addAction);
}
if (actions.count() > 0)
QMenu::exec(actions, m_ui.
projectTreeView->mapToGlobal
(pnt
));
}
...
void MainWindow::addObject()
{
// HOW am I going to get access to the node's index to insert a new child row???
}
I got the code to compile and the addObject() method is invoked properly. My question is how am I going to get access to the corresponding node index to insert a child node appropriately?
Thanks in advance.
Re: Custom context menu in QTreeView
try to use QAbstractItemView::currentIndex.
Re: Custom context menu in QTreeView
Thanks. Follow-up questions,
1) I want to setCheckable on the tree top level nodes to true when it has children + when check/uncheck a parent's checkbox, all children will be checked/unchecked accordingly. Do I have to subclass QStandardItem?
2) Children node always has a checkbox or radiobox, and toggling child node checkbox/radiobox won't change its parent checked state. Do I have to subclass QStandardItem?
3) when create a child node, I want to use a different default icon and/or naming convention by the parent's type (i.e. Squares, Circles, ...). I don't want to just rely on the name of the parent's node if I don't have to. If so, can I use QStandardItem then somehow utilizing Qt role/type OR do I need to subclass QStandardItem?
In general, I want to avoid subclassing QStandardItem, QStandardItemModel, and QTreeView unless I have to.
Re: Custom context menu in QTreeView
Quote:
Originally Posted by
ttvo
Thanks. Follow-up questions,
1) I want to setCheckable on the tree top level nodes to true when it has children + when check/uncheck a parent's checkbox, all children will be checked/unchecked accordingly. Do I have to subclass QStandardItem?
try this code
Code:
...
tree->setColumnCount(1);
root->setCheckState(0, Qt::Unchecked);
tree->insertTopLevelItem(0, root);
for (int i = 0; i < 10; ++i) {
item->setCheckState(0, Qt::Unchecked);
for (int j = 0; j < 10; ++j) {
itm->setCheckState(0, Qt::Unchecked);
}
}
....
{
changeItemState(item);
}
{
if (!item)
return;
for (int i = 0; i < item->childCount(); ++i) {
child->setCheckState(0, item->checkState(0));
changeItemState(child);
}
}
I don't test it, but hope you got idea.
PS. I don't see any reason to subclass QStandardItem in second and third points.
Re: Custom context menu in QTreeView
I added
Code:
// where QStandardItemModel *model = new QStandardItemModel();
from my MainWindow (inherits from QMainWindow) and
Code:
{
changeItemState(item);
}
{
if (!item)
return;
for (int i=0; i<item->rowCount(); ++i) {
child->setCheckable(item->checkState());
changeItemState(child);
}
}
similar to your example but the two methods weren't invoked at all when I toggle the checkbox.
(Fixed) Custom context menu in QTreeView
Quote:
Originally Posted by
ttvo
I added
Code:
// where QStandardItemModel *model = new QStandardItemModel();
The correct code is: