2 列のデータがQTreeWidgetItem
あるのですが、2 列目だけを編集可能にする方法はありますか? 私が次のことをするとき:
QTreeWidgetItem* item = new QTreeWidgetItem();
item->setFlags(item->flags() | Qt::ItemIsEditable);
すべての列が編集可能になります。
2 列のデータがQTreeWidgetItem
あるのですが、2 列目だけを編集可能にする方法はありますか? 私が次のことをするとき:
QTreeWidgetItem* item = new QTreeWidgetItem();
item->setFlags(item->flags() | Qt::ItemIsEditable);
すべての列が編集可能になります。
回避策を使用して、QTreeWidget の特定の列のみを編集可能にすることができます。
1) QTreeWidget の editTriggers プロパティを NoEditTriggers に設定します。
2) アイテムの挿入時に、QTreeWidgetItem オブジェクトの Qt:ItemIsEditable フラグを設定します
3) 次のスロットを QTreeWidget オブジェクトの「itemDoubleClicked」シグナルに接続します。
void MainWindow::onTreeWidgetItemDoubleClicked(QTreeWidgetItem * item, int column)
{
if (isEditable(column)) {
ui.treeWidget->editItem(item, column);
}
}
ここで、「isEditable」は、編集可能な列に対して true を返し、編集不可能な列に対して false を返す関数です。
私は最近同じ問題を抱えていて、DoubleClicked のものだけでなく、すべての EditTriggers (およびダブルクリックされた信号への接続) で動作するソリューションを発見しました。
エディターに NULL ポインターを返すデリゲートを作成します。
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));
andを使用するのをやめ、andを使用する必要があるようQTreeWidget
です。「ウィジェット」クラスは、より抽象的ながより柔軟なバージョンの具体的な実装である便利なクラスです。列に適切な値を返す呼び出しがあります。QTreeWidgetItem
QTreeView
QAbstractItemModel
QAbstractItemModel
flags(QModelIndex index)
標準の QTreeWidget ではこれが許可されていないようです。これを行うには2つの方法があると思います:
QAbstractItemModel から派生した独自のクラスで QTreeView を使用し、フラグ関数をオーバーライドします
QStandardItemModel で QTreeView を使用します。次に、アイテムを追加するときに、適切な列を設定して編集を許可します。
2 番目のオプションのコードを次に示します。
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);
2 番目のアプローチの方が簡単だと思いますが、それはモデルにどの程度の柔軟性が必要かによって異なります。
私が見つけた最も簡単な方法は、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);
}
私は一般的にPySideとPythonを初めて使用しますが、itemClickedコールバック用にQTreeWidgetに登録することで、これを機能させることができました。コールバック内で、列を確認し、編集を許可する列の場合にのみ「editItem」を呼び出します。
class Foo(QtGui.QMainWindow):
...
def itemClicked(self, item, column):
if column > 0:
self.qtree.editItem(item, column)
列0に対してeditItemを呼び出さないことにより、イベントは基本的に破棄されます。
行と列に基づいて、ツリー ウィジェットの子を編集可能にするかどうか (ツリーのアイテム) を設定します。