1

後でより複雑なプロジェクトのために QTreeModel と QTreeView を使用して簡単なテスト プログラムを作成しています。この単純なプログラムでは、QTreeView で予想されるように、縮小または展開できるグループにデータがあります。データは、さまざまなデータ列で並べ替えることもできます (QTreeView.setSortingEnabled が True)。各ツリー項目はデータのリストであるため、TreeModel クラスに実装されているソート関数は、組み込みの Python リスト ソートを使用します。

self.layoutAboutToBeChanged.emit()  
self.rootItem.childItems.sort(key=lambda x: x.itemData[col], reverse=order)  
for item in self.rootItem.childItems:  
    item.childItems.sort(key=lambda x: x.itemData[col], reverse=order)  
self.layoutChanged.emit()

問題は、ルートの子項目の並べ替えを変更するたびに (ツリーの深さが 2 レベルしかないため、これが子を持​​つ唯一のレベルです)、ノードが以前のように必ずしも展開されないことです。何も展開したり折りたたんだりせずに並べ替えを元に戻すと、ノードは並べ替えの変更前と同じように展開されます。
誰かが私が間違っていることを説明できますか? ソートされたノードで QModelIndex を適切に再割り当てしていないと思われますが、よくわかりません。

4

2 に答える 2

2

「私が間違っていること」という質問に答えるには、layoutChanged() を発行する前に、永続的なモデル インデックスを更新していません。モデルのクライアントは、モデルのデータがどのように移動したかを魔法のように知りません。たとえば、インデックス (2,0,root) が移動して (12,0,root) になったことを知りません。

変更を伝える方法は、レイアウト シグナルを送信することです。あなたはその部分が正しいです。Qt は、保持している QModelIndex を QPersistentModelIndex に変換することで、layoutAboutToBeChanged() に応答する可能性が最も高いです。layoutChanged() を取得すると、それらを元に戻します。その間に、その QPersistentModelIndex リストを調べて、新しい場所でインデックスを更新することになっています。ドキュメントで layoutChanged() シグナルを確認してください。

于 2010-12-11T10:41:34.660 に答える
1

ソート用に QSortFilterProxyModel を実装することで問題を解決しました。

于 2010-04-17T05:05:41.797 に答える