2011-12-21 199 views
4

我已經安裝了python 2.5和PyQt 4.8.6。 Os - Windows Xp Sp2。我使用以下代碼填充TreeWidget:PyQt QTreeWidget.clear()導致崩潰

def updateTreeWidget(self, widget, results): 
     """ Updates the widget with given results """ 
     widget.clear() 
     for item in results: 
      temp = QtGui.QTreeWidgetItem() 
      j = 0 
      for elem in item: 
       temp.setText(j , str(elem)) 
       j += 1 
      widget.addTopLevelItem(temp)  
     for column in range(widget.columnCount()): 
      widget.resizeColumnToContents(column) 

它在第二次使用時會導致崩潰。如果我註釋掉以下行之一:

widget.clear() 

它的工作原理沒有問題。

我每60秒調用一次線程中的函數。這裏是MyThread類的定義。

class MyThread(threading.Thread): 
    def __init__(self, db, widget, function, script, parameter): 
     threading.Thread.__init__(self) 
     self.db = db 
     self.function = function 
     self.script = script 
     self.parameter = parameter 
     self.widget = widget 
     self.event = threading.Event() 

    def run(self):    
     while 1: 
      self.event.wait(60) 
      parameter = [getCurrentTimeStr()] + self.parameter 
      res = self.db.getQuery(self.script % tuple(parameter)) 
      self.function(self.widget, res) 

該線程啓動時初始化主窗口():

class MainWnd(QtGui.QMainWindow): 
    def __init__(self, parent = None): 

     # some code 

     self.db = DbAccess() 

     QtGui.QWidget.__init__(self, parent) 

     self.ui = Ui_mainWnd() 
     self.ui.setupUi(self) 

     self.thread = MyThread(self.db, self.ui.treeWidget, self.updateTreeWidget, self.script, self.param) 
     self.thread.start() 

小部件是使用Qt Designer創建。

+0

您可以顯示創建'QTreeWidget'的代碼部分以及您調用該函數的位置嗎? – alexisdm 2011-12-21 13:39:17

+0

而不是自己計算'j',考慮更多的pythonic解決方案'對於j,元素枚舉(item):'。 – 2011-12-21 13:41:59

回答

2

從與Qt的事件循環不相同的線程更新GUI元素是一個很大的禁忌。

解決此問題的常規方法是使用排隊信號/插槽連接或單線程QTimer傳遞線程邊界並在主線程上執行您的函數。