我有一个 QTreeWidgetItem 有两列的数据,是否有任何方式使只有第二列中的可编辑?当我做到以下几点:

QTreeWidgetItem* item = new QTreeWidgetItem();
item->setFlags(item->flags() | Qt::ItemIsEditable);

所有列成为编辑。

有帮助吗?

解决方案

看起来你有使用QTreeWidgetQTreeWidgetItem放弃与QTreeViewQAbstractItemModel去。 “微件”类是便利类是更抽象的,但更灵活的版本的具体实现。 QAbstractItemModel具有呼叫flags(QModelIndex index),你将返回相应值的列。

其他提示

可以使用一种变通方法使只有某些列在QTreeWidget编辑:

1)将QTreeWidget到NoEditTriggers的editTriggers属性

2)在插入项目中,设置了Qt:所述QTreeWidgetItem对象的ItemIsEditable标志

3)连接的下一个槽的 “itemDoubleClicked” 的QTreeWidget对象的信号:

void MainWindow::onTreeWidgetItemDoubleClicked(QTreeWidgetItem * item, int column)
{
    if (isEditable(column)) {
        ui.treeWidget->editItem(item, column);
    }
}

,其中“isEditable”是你写的,则返回true为可编辑的列和假非可编辑栏的功能。

我最近有同样的问题,并发现其与所有EditTriggers工作的解决方案,不仅DoubleClicked一个(和双点击的信号的连接)

创建委托,即返回空指针为编辑器:

class NoEditDelegate: public QStyledItemDelegate {
    public:
      NoEditDelegate(QObject* parent=0): QStyledItemDelegate(parent) {}
      virtual QWidget* createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const {
        return 0;
      }
    };

和以后使用它作为一个自定义的委托为您列

ui->parameterView->setItemDelegateForColumn(0, new NoEditDelegate(this));

似乎喜欢的标准QTreeWidget不允许这样做。我认为有两种方式来这样做:

  1. 使用QTreeView与自己的类源自QAbstractItemModel和复盖标志的功能

  2. 使用QTreeView与QStandardItemModel.然后当你在添加该项目仅设置适当列允许编辑:

这里的一些代码的第二个选择:

QString x, y;
QList<QStandardItem*> newIt;
QStandardItem * item = new QStandardItem(x);
item->setFlags(Qt::ItemIsSelectable | Qt::ItemIsUserCheckable | Qt::ItemIsEnabled | Qt::ItemIsDragEnabled);
newIt.append(item);
item = new QStandardItem(y);
item->setFlags(Qt::ItemIsSelectable | Qt::ItemIsUserCheckable | Qt::ItemIsEnabled | Qt::ItemIsDragEnabled | Qt::ItemIsEditable);
newIt.append(item);
model->appendRow(newIt);

我找到的第二种办法更简单,但这取决于有多少灵活性,您想要与你的模型。

,我发现的最简单的方法是使用Qt :: ItemFlags

void myClass::treeDoubleClickSlot(QTreeWidgetItem *item, int column)
{
    Qt::ItemFlags tmp = item->flags();
    if (isEditable(item, column)) {
        item->setFlags(tmp | Qt::ItemIsEditable);
    } else if (tmp & Qt::ItemIsEditable) {
        item->setFlags(tmp ^ Qt::ItemIsEditable);
    }
}

if的顶部增加了通过OR编辑功能,并且底部检查它是否是那里与AND,然后用XOR移除。

这样的编辑功能,当你想它,当你不加入,并删除。

然后连接此功能可将树部件的itemDoubleClicked()信号,并写出你的“修改或不修改” isEditable()的决定里面

class EditorDelegate : public QItemDelegate
{
    Q_OBJECT

public:
    EditorDelegate(QObject *parent):QItemDelegate(parent){};
    QWidget* createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const;
};

QWidget* EditorDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    if(index.column() == 1)
    {
        return QItemDelegate::createEditor(parent, option, index);
    }
    return nullptr;
}

QTreeWidget

myQTreeWidget::myQTreeWidget()
{
    EditorDelegate *d = new EditorDelegate(this);
    this->setItemDelegate(d);
}

也许有点晚,但可以帮助:

void MyClass::on_treeWidget_itemDoubleClicked(QTreeWidgetItem *item, int column) {
    Qt::ItemFlags flags = item->flags();
    if(column == 0)
    {
        item->setFlags(flags & (~Qt::ItemIsEditable));
    }
    else
    {
        item->setFlags(flags | Qt::ItemIsEditable);
    } 
}

下面0是要进行只读的列的索引。

flags & (~Qt::ItemIsEditable)

设定的ItemIsEditable位置为0不管你的物品的以前的标记。

flags | Qt::ItemIsEditable

将其设置为1而不管前一标记。

我一般是新来的PySide和Python,但我可以通过与QTreeWidget注册为itemClicked回调得到这个工作。在回调,检查列,只称之为“editItem”如果是为了要允许编辑列。

class Foo(QtGui.QMainWindow):
...
def itemClicked(self, item, column):
   if column > 0:
      self.qtree.editItem(item, column)

通过不调用editItem用于列0,该事件被基本上丢弃。

我发现下面很适合我的需要的代码,也“有点”停止 用户编辑列的某些部分:

我基本检查角色,然后列。我只允许在第0列所以编辑如果在任何其他列用户编辑它,然后我停止使用setData编辑和没有改变正在取得。

void treeItemSubclassed::setData(int column, int role, const QVariant &value) {
    if (role == Qt::ItemIsEditable && column != 0){
        return;
    }
    QTreeWidgetItem::setData(column, role, value);
}

集的子树的小部件可编辑与否(树的次),基于该行和列。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top