将小部件属性绑定到 Python 个变量

Binding widget properties to Python variables

试图理解 https://wiki.python.org/moin/PyQt/Binding%20widget%20properties%20to%20Python%20variables :

“将小部件属性绑定到 Python 变量”

在我修改后的代码下方,我花了一些时间,但可以更好地形象化 bind,这里的示例代码的作用:

def bind(objectName, propertyName, type):

    def getter(self):
        return type(self.findChild(QObject, objectName).property(propertyName).toPyObject())
    
    def setter(self, value):
        self.findChild(QObject, objectName).setProperty(propertyName, QVariant(value))
    
    return property(getter, setter)

我的完整代码是:

import sys

from PyQt5.QtWidgets import QWidget, QLineEdit, QTextEdit, QCheckBox, QFormLayout, QPushButton

from PyQt5 import QtWidgets


def bind(objectName, propertyName, type):

    def getter(self):
        return type(self.findChild(QObject, objectName).property(propertyName).toPyObject())
    
    def setter(self, value):
        self.findChild(QObject, objectName).setProperty(propertyName, QVariant(value))
    
    return property(getter, setter)

class Window(QWidget):

    def __init__(self, parent = None):
    
        super().__init__(parent)
        self.nameEdit = QLineEdit()
        self.nameEdit.setObjectName("nameEdit")
        self.addressEdit = QTextEdit()
        self.addressEdit.setObjectName("addressEdit")
        self.contactCheckBox = QCheckBox()
        self.contactCheckBox.setObjectName("contactCheckBox")
        self.button_1 = QPushButton('press me !!!')
        self.button_1.clicked.connect(self.pushButton_1_Pressed)
        
        self.button_2 = QPushButton('press me !!! second')
        self.button_2.clicked.connect(self.pushButton_2_Pressed)
        

        self.layout = QFormLayout(self)
        self.layout.addRow(self.tr("Name:"), self.nameEdit)
        self.layout.addRow(self.tr("Address:"), self.addressEdit)
        self.layout.addRow(self.tr("Receive extra information:"), self.contactCheckBox)
        
        self.layout.addWidget(self.button_1)
        self.layout.addWidget(self.button_2)
        
        self.setLayout(self.layout)
        
        self.name = bind('nameEdit', 'text', str)
        self.address = bind("addressEdit", "plainText", str)
        self.contact = bind("contactCheckBox", "checked", bool)
            
    def pushButton_1_Pressed(self):
        
        print(self.nameEdit.text())
        
        print(self.addressEdit.toPlainText())
        
        print(self.contactCheckBox.isChecked())
        
    def pushButton_2_Pressed(self):

        self.nameEdit.setText('pippo')
        
        
        self.addressEdit.clear()
        self.addressEdit.insertPlainText('papero')
        
        self.contactCheckBox.setChecked(True)
        
        print(self.nameEdit.text())
        
        print(self.addressEdit.toPlainText())
        
        print(self.contactCheckBox.isChecked())

    


if __name__ == "__main__":

    app = QtWidgets.QApplication(sys.argv)
    window = Window()
    window.show()
    sys.exit(app.exec_())


在您将文本插入 QLineEditQTextEdit 或检查 QCheckBox 小部件之后 您可以打印由 bind 定义的变量并按下第二个按钮,您可以同时更改变量值和小部件的 text/values(从 Binding a PyQT/PySide widget to a local variable in Python.[=21 获得一些见解) =]

因为 Python 和 PyQt5 的内部结构对我来说太难了,所以关于 bind 如何在三个小部件的代码中工作的简单描述。

您所指的文章尝试使用 QObjects 属性实现 python properties

由于它是一个 属性,因此不应在 class 中声明,而应在方法级别声明为 class 属性。另一方面,必须更新代码,因为它是为 PyQt4 编写的,其中从 python 到 Qt 的对象之间的转换不是隐式的,考虑到上述情况,解决方案是:

import sys

from PyQt5.QtCore import QObject
from PyQt5.QtWidgets import (
    QApplication,
    QWidget,
    QLineEdit,
    QTextEdit,
    QCheckBox,
    QFormLayout,
    QPushButton,
)


def bind(objectName, propertyName):
    def getter(self):
        return self.findChild(QObject, objectName).property(propertyName)

    def setter(self, value):
        self.findChild(QObject, objectName).setProperty(propertyName, value)

    return property(getter, setter)


class Window(QWidget):
    name = bind("nameEdit", "text")
    address = bind("addressEdit", "plainText")
    contact = bind("contactCheckBox", "checked")

    def __init__(self, parent=None):
        super().__init__(parent)
        self.nameEdit = QLineEdit()
        self.nameEdit.setObjectName("nameEdit")
        self.addressEdit = QTextEdit()
        self.addressEdit.setObjectName("addressEdit")
        self.contactCheckBox = QCheckBox()
        self.contactCheckBox.setObjectName("contactCheckBox")
        self.button_1 = QPushButton("press me !!!")
        self.button_1.clicked.connect(self.pushButton_1_Pressed)

        self.button_2 = QPushButton("press me !!! second")
        self.button_2.clicked.connect(self.pushButton_2_Pressed)

        layout = QFormLayout(self)
        layout.addRow(self.tr("Name:"), self.nameEdit)
        layout.addRow(self.tr("Address:"), self.addressEdit)
        layout.addRow(self.tr("Receive extra information:"), self.contactCheckBox)

        layout.addWidget(self.button_1)
        layout.addWidget(self.button_2)

    def pushButton_1_Pressed(self):
        print(self.name)
        print(self.address)
        print(self.contact)

    def pushButton_2_Pressed(self):
        self.name = "pippo"
        self.address = ""
        self.address += "papero"
        self.contact = True
        print(self.address)
        print(self.contact)


if __name__ == "__main__":

    app = QApplication(sys.argv)
    window = Window()
    window.show()
    sys.exit(app.exec_())