如何在动态创建的 QTabWidget 页面中查看来自 QWidgets 的信号?
Posted
技术标签:
【中文标题】如何在动态创建的 QTabWidget 页面中查看来自 QWidgets 的信号?【英文标题】:How to see signals from QWidgets inside dynamically created QTabWidget pages? 【发布时间】:2013-06-27 13:41:09 【问题描述】:编辑:我想出了一个解决方案,它比我想象的要简单得多。原始代码和顶部的问题。我在下面的“问题”之后的解决方案..
示例
from PyQt4 import QtGui, QtCore
from example_Ui import Ui_MainWindow
from filler_Ui import Form
class TabFiller(Form):
def __init__(self, parent=None):
Form.__init__(self, parent)
def TabButtonClicked(self):
print("Tab button pressed.")
def LineEditChanged(self):
print("LineEdit contents edited in tab page!")
class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.setupUi(self)
tab_filler = [] # create empty list for tab contents
tab_page = [] # create empty list for tab page
tab_count = 0
def CreateNewTab(self):
tab_title = "New Tab : " + str(self.tab_count)
self.tab_filler.append(TabFiller())
self.tab_filler[self.tab_count].label.setText(tab_title)
self.tab_page.append(self.tab_filler[self.tab_count])
self.tabWidget.addTab(self.tab_page[self.tab_count], tab_title)
self.tab_count += 1
def MainButtonPressed(self):
self.CreateNewTab()
if __name__ == '__main__':
import sys
app = QtGui.QApplication(sys.argv)
window = MainWindow()
window.show()
sys.exit(app.exec_())
MainWindow 包含一个 QTabWidget,它是一个 Button。 clicked() 信号已在 QtDesigner 中定义,用于发送到 MainWindow 类中的 MainButtonPressed() 函数。
表单小部件也在 QTdesigner 中创建。用于填充额外的标签页。 这包含一个 Button 小部件和一个 LineEdit 小部件。
问题
我无法理解如何我可以告诉哪个小部件在每个标签中被点击或编辑了。
我知道每个标签页都存储在名为tab_page的列表中。
在 MainWindow 类中,我如何接收当前活动选项卡中给定小部件的 clicked() 或 finishedEditing() 信号?
解决方案
import sys
from PyQt4.QtGui import *
from PyQt4.QtCore import *
from PyQt4 import QtGui
from example_Ui import Ui_MainWindow
from filler_Ui import Form
class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.setupUi(self)
tab_index = 1 # 1 because we already made a default tab in QtDesigner
def LineEditChanged(self):
findWidget = self.tabWidget.widget(self.tabWidget.currentIndex()).findChildren(QtGui.QLineEdit, "lineEdit")
if findWidget[0].isModified() == True:
print("LineEdit contents edited in tab page!")
print("Name of page edited :", "'", self.tabWidget.tabText(self.tabWidget.currentIndex()),"'")
def TabButtonPressed(self):
print("YOU DID IT!")
print("Current Tab Index = ", self.tabWidget.currentIndex())
def CreateNewTab(self, tabNum):
tab_title = "New Tab : " + str(self.tab_index)
self.tabWidget.addTab(Form(), tab_title)
def MainButtonPressed(self):
self.CreateNewTab(self.tab_index)
findWidget = self.tabWidget.widget(self.tab_index).findChildren(QtGui.QPushButton, "tabButton")
findWidget[0].clicked.connect(self.TabButtonPressed)
findWidget = self.tabWidget.widget(self.tab_index).findChildren(QtGui.QLineEdit, "lineEdit")
findWidget[0].editingFinished.connect(self.LineEditChanged)
self.tab_index += 1
if __name__ == '__main__':
app = QtGui.QApplication(sys.argv)
window = MainWindow()
window.show()
sys.exit(app.exec_())
使用它不需要将每个标签页对象存储在列表中。您基本上使用 QTabWidget 来索引您的页面,然后就可以了。
如果有人有比这更优雅的方法,请告知;)
【问题讨论】:
【参考方案1】:正如我编辑的问题中所述,我确实找到了解决方案,即使用 QTabWidget 来“索引”每个动态创建的标签页。
因此,在 QtDesigner 中,我创建了一个带有一个 QTabWidget 和一个按钮的主窗口;
这是它的对象树;
注意:我为“点击我!”添加了一个信号/槽。 QtDesigner 中的按钮,以便在单击该按钮时调用 MainButtonPressed
函数。
为了填充标签页,我还在 QtDesigner 中创建了一个表单,带有一个按钮和一个 QLineEdit 小部件;
还有那个对象树;
我将在这里重现代码。注意:我现在已更新此答案以使用 findChild 而不是上面的 findChildren:
import sys
from PyQt4.QtGui import *
from PyQt4.QtCore import *
from PyQt4 import QtGui
from example_Ui import Ui_MainWindow
from filler_Ui import Form
class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.setupUi(self)
tab_index = 1 # 1 because we already made a default tab in QtDesigner
def LineEditChanged(self):
findWidget = self.tabWidget.widget(self.tabWidget.currentIndex()).findChild(QtGui.QLineEdit, "lineEdit")
if findWidget.isModified() == True:
print("LineEdit contents edited in tab page!")
print("Name of page edited :", "'", self.tabWidget.tabText(self.tabWidget.currentIndex()),"'")
def TabButtonPressed(self):
print("YOU DID IT!")
print("Current Tab Index = ", self.tabWidget.currentIndex())
def CreateNewTab(self, tabNum):
tab_title = "New Tab : " + str(self.tab_index)
self.tabWidget.addTab(Form(), tab_title)
def MainButtonPressed(self):
self.CreateNewTab(self.tab_index)
findWidget = self.tabWidget.widget(self.tab_index).findChild(QtGui.QPushButton, "tabButton")
findWidget.clicked.connect(self.TabButtonPressed)
findWidget = self.tabWidget.widget(self.tab_index).findChild(QtGui.QLineEdit, "lineEdit")
findWidget.editingFinished.connect(self.LineEditChanged)
self.tab_index += 1
if __name__ == '__main__':
app = QtGui.QApplication(sys.argv)
window = MainWindow()
window.show()
sys.exit(app.exec_())
运行时,按“点击我!”主标签页上的按钮创建一个新标签,并将“填充”页面的内容添加到其中。
变量tab_index
跟踪有多少个选项卡,并允许您引用每个选项卡的内容。
要在选项卡中查找小部件,请使用 Qt 的 findChild 函数;
findWidget = self.tabWidget.widget(self.tab_index).findChild(QtGui.QPushButton, "tabButton")
查找特定小部件非常简单。您指定要查找的小部件类型 (QtGui.QPushButton
) 以及您在 QtDesigner 中为其分配的名称 (tabButton
)
在这种情况下,找到的小部件可以由变量 findWidget
引用。
然后您可以像往常一样将信号连接到函数槽;
findWidget.clicked.connect(self.TabButtonPressed)
在这种情况下,我使用新型信号连接方法将 clicked() 信号连接到我程序中名为 TabButtonPressed
的函数。
冲洗并重复您希望使用的标签页上的每个小部件。
之后,真的是一帆风顺;)
我希望这些信息有助于其他人的 GUI 工作。您可能可以对 QToolBox 小部件使用相同的技术。
【讨论】:
以上是关于如何在动态创建的 QTabWidget 页面中查看来自 QWidgets 的信号?的主要内容,如果未能解决你的问题,请参考以下文章
如何使用 QWidget 在 QTabWidget 中包含 QList