我有以下(简化的)代码将QStandardItem
's 添加到 a QStandardItemModel
,将模型附加到 a QListView
,并将我选择的信号从模型连接到我选择的函数:
// MyUIContainer derives from QWidget
MyUIContainer::SetItems()
{
// Inside a member function where model/items are added to a QListView...
// This code does not show deletion of existing ItemSelectionModel
QStandardItemModel * model = new QStandardItemModel(ui->listView);
// In the real code, data is set in each QStandardItem
model->setItem( 0, new QStandardItem() );
model->setItem( 1, new QStandardItem() );
model->setItem( 2, new QStandardItem() );
connect(model,
SIGNAL(itemChanged(QStandardItem*)),
this,
SLOT(ReceiveChange(QStandardItem*)));
// I have also tried connecting to this signal - same problem described below
//connect(model, SIGNAL(dataChanged(const QModelIndex &, const QModelIndex &, const QVector<int>)), this, SLOT(ReceiveChange(const QModelIndex &, const QModelIndex &, const QVector<int>)));
ui->listView->setModel(model);
}
MyUIContainer::ReceiveChange(QStandardItem * item)
{
// Problem! This slot is called *three times*
// whenever the check state of an item changes
}
正如代码注释所示,有一个问题:每当一个复选框的检查状态更改一次itemChanged()
时, \ ReceiveChange()
signal\slot 组合就会被调用3次。QListView
我知道我可以创建自己的模型类,该类QAbstractItemModel
从itemChanged
复选框状态的更改只能处理一次。
但是,后一种方法需要我小心处理所有可能导致复选框状态更改的鼠标单击和键盘事件的情况。我希望并假设该逻辑已在 Qt 库本身内部处理,因此我不必这样做 - 这样我就可以在复选框的检查状态更改时简单地接收信号(或其他消息) .
请注意,似乎QListWidget
( 而不是QListView
) 也有完全相同的问题。
所以,我的问题是:如果不编写我自己的模型类派生自QAbstractItemModel
- 要求我自己编写代码来处理检查状态可以改变的所有可能方式 - 我如何捕获更改的检查状态(通过信号或其他方式)这样我就可以明确地捕获每次检查状态更改一次且每次检查状态更改仅一次?
附录
道歉 - 因为我非常小心地排除了其他一切 - Riacheche 的评论向我清楚地表明,这种行为不应该以这个问题突出的方式起作用。最后,我确实将问题归结为我connect()
多次调用的事实。