如何启用/禁用基于QTreeView事件的项目?

问题描述:

我希望在发送特定信号时启用/禁用QTreeWidget中的可检查项目。如何启用/禁用基于QTreeView事件的项目?

下面的代码DOWS不起作用:

model = QStandardItemModel() 
view = QTreeView() 
view.setModel(model) 
rootItem = QStandardItem() 
rootItem = model.invisibleRootItem() 

categoryItem = QStandardItem(item) 
categoryItem.setCheckable(True) 
rootItem.appendRow(categoryItem) 

signalSource.availabilityChanged.connect(categoryItem.setEnabled) 

它产生错误:

TypeError: unhashable type: 'PySide.QtGui.QStandardItem' 

是否有经由信号/槽改变QStandardItem的状态或数据的解决方案?

+0

你可以发布完整的回溯和'signalSource'的定义吗? – Avaris 2012-03-11 10:56:56

这看起来像在PySide中的错误,因为connect应该接受任何调用(示例代码正常工作PyQt4中)。

作为一种变通方法,尝试在拉姆达包装QStandardItem方法:

signalSource.availabilityChanged.connect(
    lambda enable: categoryItem.setEnabled(enable)) 

编辑

要连接在一个循环的项目,使用默认参数,就像这样:

for button in buttonList: 
    item = QStandardItem("Test") 
    ... 
    button.toggled.connect(
     lambda enable, item=item: item.setEnabled(enable)) 
+0

谢谢。这帮了很多。 – leviathan 2012-03-14 17:21:16

+0

@leviathan。查看我的更新回答,了解如何在循环中使用'lambda'。 – ekhumoro 2012-03-14 22:56:05

在ekhumoros答案的帮助下,我找到了解决问题的方法,但它似乎是PyS中一个丑陋的解决方法ide,使用发件人来正确连接信号。

import sys 
import argparse 
import signal 

#import sip 
#sip.setapi('QString', 2) 
#from PyQt4.QtGui import QApplication, QWidget, QVBoxLayout, QHBoxLayout, QPushButton, QStandardItemModel, QStandardItem, QTreeView 
from PySide.QtGui import QApplication, QWidget, QVBoxLayout, QHBoxLayout, QPushButton, QStandardItemModel, QStandardItem, QTreeView 


class MainWindow(QWidget): 
    def __init__(self, parent=None): 
       QWidget.__init__(self, parent) 

       buttonList = [] 
       for i in xrange(10): 
        button = QPushButton("1") 
        button.setCheckable(True) 
        buttonList.append(button) 

       model = QStandardItemModel() 
       view = QTreeView() 

       view.setModel(model) 

       layout = QVBoxLayout() 
       self.setLayout(layout) 

       buttonLayout = QHBoxLayout() 
       layout.addLayout(buttonLayout) 

       for button in buttonList: 
        buttonLayout.addWidget(button) 

       layout.addWidget(view) 

       rootItem = QStandardItem() 
       rootItem = model.invisibleRootItem() 

       self.itemList = {} 
       for button in buttonList: 
        item = QStandardItem("Test") 
        item.setCheckable(True) 
        rootItem.appendRow(item) 
        self.itemList[button] = item 

        # Works with PyQt4, but not with PySide 
        #button.toggled.connect(item.setEnabled) 
        # Workaround for PySide 
        button.toggled.connect(self.workaround) 

       for button in buttonList: 
        button.setChecked(True) 


      def workaround(self, enable): 
       self.itemList[self.sender()].setEnabled(enable) 


def main(argv): 
    app = QApplication(argv) 
    w = MainWindow() 
    w.show() 
    retcode = app.exec_() 


if __name__ == "__main__": 
    main(sys.argv) 

只使用lambda结构在循环中不起作用。它只是连接所有信号和最后一个参考来迭代。