PyQt4:使用QPushButton小部件从QList小部件中删除项目

问题描述:

我正在学习PyQt4(我正在使用4.4.4版本),我对Python(Python 2.5)很新。我有一个QListWidget和一个QPushButton的GUI。我希望用户能够单击以在列表中选择一个条目,然后单击QPushButton并让选定条目消失(从QList中删除)。我在这个问题上一直在抨击我的头一个多星期,我会深表感谢。PyQt4:使用QPushButton小部件从QList小部件中删除项目

目前,我的GUI出现了,我可以选择不同的列表项(一次只有一个),但是当我点击QPushButton时,没有任何反应。选择颜色从蓝色变为灰色,但不删除条目。命令提示符(Windows 7)中不显示错误。

我已经定义了一个函数remove(),我用它作为QPushButton的插槽。我相信QPushButton.connect为Qt Signal to Python Slot提供了正确的定义,基于我见过的类似问题的答案,但是这些项目并未被删除。但是,remove函数甚至没有被触发。我在函数中有一个print语句,但是当我单击QPushButton时,它不会被调用,这是我知道函数没有被调用的原因。

这是我最近的代码:(我在meta-SO上阅读了一篇关于大代码块的非常强烈的帖子,所以我将它缩减为我认为相关的部分:列表创建,按钮创建和删除功能,我试图用作一个插槽,我留下了评论,指出其他部分是什么,所以如果你认为我已经遗漏了一些可以帮助的东西,让我知道和我会重新加入)

class questionGUI(QtGui.QWidget): 
#This class is the window of the gui. 

    def __init__(self): 
     super(questionGUI,self).__init__() 
     #Layout 
     grid = QtGui.QGridLayout() 
     grid.setSpacing(10) 

     #Labels Needed 
     ... 

     #Question List 
     self.qList = QtGui.QListWidget() 
     #print self.qList 
     self.qList.setSelectionMode(QtGui.QAbstractItemView.SingleSelection) 
     entries = ['[Pick Image] <Default>','[Slider Question] <Default>', '[Comment Box] <Default>'] 

     for i in entries: 
      item = QtGui.QListWidgetItem(i) 
      self.qList.addItem(item) 

     #Type select 
     ... 

     #Text insert Needed 
     ... 

     #Buttons Needed 
     deleteButton = QtGui.QPushButton('Delete Question') 
     deleteButton.connect(deleteButton,QtCore.SIGNAL('itemClicked(clicked)'),lambda: self.remove) 

     addQuestionButton = QtGui.QPushButton('Add Question') 
     ... 

     doneButton = QtGui.QPushButton('Done') 
     ... 

     #Parameters Needed 
     ... 

     #Layout Placement and Window dimensions 
     ... 

    def addQuestion(self): 
     ... 

    def remove(self): 
     print 'remove triggered' 
     print self.qList.currentItem() 
     self.qList.removeItemWidget(self.qList.currentItem()) 

... 

我试图发布图片,但我没有足够的声望。如果您认为图片有用,请告诉我,我可以将其发送给您。

+0

PyQt 4.4.4真的很旧。有没有任何理由使用这样一个古老的版本? – Avaris

+0

首先:我为防务承包商工作。我们的IT部门。保持严格控制的“批准”软件列表,这些软件始终是许多版本。我仍在使用Python 2.5。是的,这是愚蠢的。其次:我也不是我自己的电脑上的管理员,所以我不能只下载这个开源软件并使用它们来绕过IT。第三,也是最重要的一点:这是一个项目的一部分,用于更新一个旧的内部软件程序,Py2.5和PyQt4.4.4,这是1000行的线和不断使用。把它离线重写Py3.0和PyQt5中的所有东西不是一种选择。 – SatelliteEyes

+0

我明白了。版本与您的问题无关。它只是让我觉得“奇怪”。但是,如果它与一些遗留代码相关联,这是有道理的。 – Avaris

你中混合的信号:

deleteButton.connect(deleteButton,QtCore.SIGNAL('itemClicked(clicked)'),lambda: self.remove) 

deleteButtonQPushButton,但​​貌似将信号从QListWidget带有错误签名。因为QPushButton没有这个信号,所以没有连接。 Qt不会引发连接失败的错误,但.connect方法有一个bool返回值,指示尝试连接的成功/失败。

另外,作为插槽的lambda: self.remove没有意义。插槽应该是一个可调用的信号发射调用。当然,lambda创建了一个函数,但是您所做的全部是参考方法self.removelambda将被调用,self.remove不会。只需self.remove作为一个插槽就足够了。

您应该使用clicked()信号(或clicked(bool),如果你关心的checked值)按钮:

deleteButton.connect(deleteButton, QtCore.SIGNAL('clicked()'), self.remove) 

编辑

另一个问题:你remove方法不会做你想。 removeItemWidget不会删除项目,它会删除内部的小部件该项目(如果您设置了其中一项)。它与setItemWidget对应。

您应该使用takeItem删除项目。

def remove(self): 
    self.qList.takeItem(self.qList.currentRow()) 
+0

这个工程!非常感谢你的帮助!我认为我基本上需要两个信号:点击列表来选择项目并单击按钮将其删除。 itemClicked是一个QListWidget函数,这是我尝试使用这两个信号。我现在明白,这是不必要的,因为点击列表条目将自动更新当前行或项目,所以明确指出项目已被点击是没有必要的。 – SatelliteEyes

+0

@Avaris请看问题http://*.com/questions/16221810/how-to-handle-mouse-events-in-qt。谢谢。 – Alex