Laying out Qt code
-
Hi all!
I'm new to both Python and Qt. The company I work for tends to write quite big classes and store stuff in instance variables even when they could exist outside. I started reading the material at qt.docs.io and was surprised to see the same here. Now I'm wondering: Is there a specific reason for that?
I tend to try to keep my objects as small as possible, because the more instance variables I see in a object, the harder it is to reason about all the states it can be in.
In the following PySide6 example code, why would one put the
QVBoxLayout,QPushButtoninside a QWidget-derived custom class which main reason to exist I'd say is to hold theQLabel? (It needs to be kept around so it can be changed by the click of a button.)Thanks! Regards, Manuel
Code as available at docs.qt.io:
import sys import random from PySide6 import QtCore, QtWidgets, QtGui class MyWidget(QtWidgets.QWidget): def __init__(self): super().__init__() self.hello = ["Hallo Welt", "Hei maailma", "Hola Mundo", "Привет мир"] self.button = QtWidgets.QPushButton("Click me!") self.text = QtWidgets.QLabel("Hello World", alignment=QtCore.Qt.AlignCenter) self.layout = QtWidgets.QVBoxLayout(self) self.layout.addWidget(self.text) self.layout.addWidget(self.button) self.button.clicked.connect(self.magic) @QtCore.Slot() def magic(self): self.text.setText(random.choice(self.hello)) if __name__ == "__main__": app = QtWidgets.QApplication([]) widget = MyWidget() widget.resize(800, 600) widget.show() sys.exit(app.exec())My attempt of doing the same:
#!/usr/bin/env python3 import sys import random from PySide6 import QtCore, QtWidgets, QtGui class TextWidget(): def __init__(self): self.widget = QtWidgets.QLabel("Hello world", alignment=QtCore.Qt.AlignCenter) @QtCore.Slot() def randomize(self): self.widget.setText(random.choice(["Hallo Welt", "Hei maailma", "Hola Mundo", "Привет мир"])) if __name__ == "__main__": application = QtWidgets.QApplication() text = TextWidget() button = QtWidgets.QPushButton("Click me!") button.clicked.connect(text.randomize) layout = QtWidgets.QVBoxLayout() layout.addWidget(text.widget) layout.addWidget(button) mainwindow = QtWidgets.QWidget() mainwindow.setLayout(layout) mainwindow.resize(640, 480) mainwindow.show() sys.exit(application.exec())I'm wondering why
-
Hi and welcome to devnet,
Take both code, now try to write a unit test to validate the widget functionality for each of them.
Also, encapsulation, which code base makes it clear just by reading what the main widget is responsible for ?
Additionally, your Widget class is in fact not a widget and not even a proper QObject and makes your code even harder to reason about. -
Hi @SGaist,
thanks for your reply.
I'm going to read https://doc.qt.io/qtforpython/overviews/qttestlib-tutorial1-example.html and check how nesting the widgets inside each others makes writing the unit tests easier.
I'm open for other advice on how to structure Qt GUI code properly.
Regards, Manuel