今天我们要延伸昨天的概念,开始来讲解我们如何设计 controller.py
https://github.com/howarder3/ironman2021_PyQt5_photoshop/tree/main/day05_pyqt_template
细节我们在昨天已经有提过了,这个是我们设计「视觉化应用的精神」
接下来我们会以「程序的角度」,来说明怎麽样写这样的程序
我们设计完 UI.py 後,再来我们要设计 controller.py,
我们可以先看下图,先有个架构理解我们在做什麽:
之前在网路上看到的程序码,很多都会将程序进入点也写在这里
并将 controller.py 命名为 start.py 或 strat_UI.py 之类的
这边读者只要有一只程序会有包含「UI.py」、「controller.py」的概念,
相信就能对网路上大部分的范例程序码能够进行初步的解读,
(之前我就是卡在 UI 与 control 的概念整个混在同一支程序码中,所以学得非常混乱XD)
这个范例是我看来不少文章後,做给自己的特制版
Ui_MainWindow,是 Qt dedigner 预设产生出 .py 档就会取名的 class 封装後的名称,建议没必要不需要特别去更改
from PyQt5 import QtWidgets, QtGui, QtCore
from UI import Ui_MainWindow
class MainWindow(QtWidgets.QMainWindow):
def __init__(self):
# in python3, super(Class, self).xxx = super().xxx
super(MainWindow, self).__init__()
self.ui = Ui_MainWindow()
self.ui.setupUi(self)
self.setup_control()
def setup_control(self):
# TODO
self.ui.textEdit.setText('Happy World!')
if __name__ == '__main__':
import sys
app = QtWidgets.QApplication(sys.argv)
window = MainWindow()
window.show()
sys.exit(app.exec_())
上面的范例程序,有调整过适合套用在往後要设计的各种 UI 程序里面,
我们接下来只需要改动的地方都在「setup_control()」之中,
例如像上面范例中的
def setup_control(self):
# TODO
self.ui.textEdit.setText('Happy World!')
我们将我们设计的「UI程序」,封装後储存在「self.ui」中,
而 self.ui 里面的 textEdit,就是我们这次修改内容的目标。
我们使用 .setText 修改成 'Happy World!',就能得到以下的结果。
程序码是一样的,为了不让读者还需要特别回去翻,
我们这边在附上范例一次,请将他存成「UI.py」,
或自行去修改上面提到的「from UI import Ui_MainWindow」的「UI」档名。
from PyQt5 import QtCore, QtGui, QtWidgets
class Ui_MainWindow(object):
def setupUi(self, MainWindow):
MainWindow.setObjectName("MainWindow")
MainWindow.resize(800, 600)
self.centralwidget = QtWidgets.QWidget(MainWindow)
self.centralwidget.setObjectName("centralwidget")
self.textEdit = QtWidgets.QTextEdit(self.centralwidget)
self.textEdit.setGeometry(QtCore.QRect(270, 290, 104, 71))
self.textEdit.setObjectName("textEdit")
MainWindow.setCentralWidget(self.centralwidget)
self.menubar = QtWidgets.QMenuBar(MainWindow)
self.menubar.setGeometry(QtCore.QRect(0, 0, 800, 21))
self.menubar.setObjectName("menubar")
MainWindow.setMenuBar(self.menubar)
self.statusbar = QtWidgets.QStatusBar(MainWindow)
self.statusbar.setObjectName("statusbar")
MainWindow.setStatusBar(self.statusbar)
self.retranslateUi(MainWindow)
QtCore.QMetaObject.connectSlotsByName(MainWindow)
def retranslateUi(self, MainWindow):
_translate = QtCore.QCoreApplication.translate
MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
self.textEdit.setHtml(_translate("MainWindow", "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.0//EN\" \"http://www.w3.org/TR/REC-html40/strict.dtd\">\n"
"<html><head><meta name=\"qrichtext\" content=\"1\" /><style type=\"text/css\">\n"
"p, li { white-space: pre-wrap; }\n"
"</style></head><body style=\" font-family:\'PMingLiU\'; font-size:9pt; font-weight:400; font-style:normal;\">\n"
"<p style=\" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;\">Hello World!</p></body></html>"))
将「controller.py」、「UI.py」准备好後,
执行我们的程序,目前这个 「controller.py」也包含着我们程序的进入点。
python controller.py
为了符合当初我们想的架构,如下图,
我们让 controller.py 独立出来,专心做控制的动作就好,
这样也更符合 Design Pattern 的 「单一职责原则 (SRP)」
真正的实现我们上述所说的:
用「controller.py」去 import「UI.py」来使用
用「start.py」去 import「controller.py」来使用
另外,在 python3 当中,super(MainWindow_controller, self).init() 的写法,
可以简写为 super().init()
from PyQt5 import QtWidgets, QtGui, QtCore
from UI import Ui_MainWindow
class MainWindow_controller(QtWidgets.QMainWindow):
def __init__(self):
super().__init__() # in python3, super(Class, self).xxx = super().xxx
self.ui = Ui_MainWindow()
self.ui.setupUi(self)
self.setup_control()
def setup_control(self):
# TODO
self.ui.textEdit.setText('Happy World!')
from PyQt5 import QtWidgets
from controller import MainWindow_controller
if __name__ == '__main__':
import sys
app = QtWidgets.QApplication(sys.argv)
window = MainWindow_controller()
window.show()
sys.exit(app.exec_())
今天我们完成了一支 Qt 程序大致的模板,
之後我们都可以照着这个模板进行後续的开发!
★ 本文也同步发於我的个人网站(会有内容目录与显示各个小节,阅读起来更流畅):【PyQt5】Day 5 - 开始来设计我们的 controller.py,改以「程序角度」来说明如何建立 PyQt 的系统
FB登入 第10步:开启 /app/res/values/strings.xml 档案。 FB会自动...
昨天轻松的安装完Xcode环境後,想必各位已经迫不及待想大显身手了吧! 但是吃紧弄破碗,就让我们先来...
UML Portal 是什麽? 开始之前,先说一下 Portal 其实是 React 比较常用的 ...
前言 快要结束了,今天要继续写 admin_bp。今天的内容会用到 JS,但我不会多加解释。 pos...
前言 fctix 这个输入法平台是直接就可从套件管理程序安装呒虾米输入法,我翻了一下资料,fcitx...