最近有空,打算整理一下pyqt5的开发流程
开发环境说明
操作系统window7
python环境python 3.8
开发平台pycharm
PyQt55.15.4

1.下载pyqt5和Qt Designer

3个月前安装的,有点忘了,当时也是一言难尽,pip老是下载不成功,不知道是不是还要安装啥依赖包,参考这个网址看看吧

pip install Sip
pip install pyqt5
pip install pyqt5-tools    PyQt5不再提供Qt Designer等工具,所以需要再安装pyqt5-tools

说明:
	Qt Designer是pyqt5的图形化设计界面,设计好的页面保存为.ui文件 然后执行
pyuic5 -o main.py main.ui 即可将.ui文件转化成.py代码,当然你不想安装的话也可以直接
用pyqt5库里的语法写。

优点:
1,Qt Designer界面控件可以直接拖到自己想要的位置(所见即所得),并进行编辑;如果仅仅是写代码,
还要运行看一下,看看摆放位置是不是自己心仪的位置,这点比较麻烦。(不容杠精反驳)
2,Qt Designer设计完成运行pyuic5命令可以直接生成代码,提高开发效率。

2.利用Qt Designer设计页面

步骤一:打开Qt Designer

pycharm – Tools – External Tools – Qt Designer
在这里插入图片描述

步骤二:设计页面

拖动左侧的图标至页面,摆放到自己想要的位置,并进行UI界面编辑设计。

在这里插入图片描述

步骤三:保存UI文件

b3.ui
在这里插入图片描述

步骤四:.UI文件转.py文件

pyuic5 -o b3.py b3.ui

-- b3.py是要生成的py文件名 ,当然你也可以改成ex01.py啥的
-- b3.ui是我要使用的ui文件

3.架构设计(界面和逻辑分离)

核心思路

##

以该bootloader项目为例分析

UI界面
b3.py
就是刚才.ui文件生成的.py文件(无需改动)
逻辑
ZLG驱动逻辑(因为这个例子要用到硬件驱动,不看可以跳过)
简单的提一下ZLG的python驱动下载、库文件、Demo程序的要点和注意点。

周立功官网找CAN驱动的资料每次都会迷路,如果下面链接点不进去,参照后面图片的指示从官网首页慢慢点进去

周立功驱动资料下载页面传送门
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

下载好周立功驱动python版的库文件、接口文档、上位机例程之后,我只想要驱动,剩下的功能自己开发。

这里有个注意点:
  zlgcan.dll文件
  kerneldlls文件夹
  zlgcan.py
  dev_info.json
这4样要和你的main.py放在同级目录下,并且修改zlgcan.py中调dll文件的路径为当前路径,如下图所示。
这样才不容易出现库文件啥的调用失败,用的时候直接import zlgcan 调zlgcan.py里的函数就好了。

因为我嫌zlgcan.py函数里的原始函数用起来会使得代码可读性变差,我又写了一个zlg_driver.py对zlgcan.py
做了二次封装。

项目Bootloader
在这里插入图片描述
zlgcan.py
在这里插入图片描述

UDS协议逻辑(因为这个例子要用到CAN通信协议,不看可以跳过)

CAN通信模块虽然就只是代替手动发一些UDS协议的指令,但是代码逻辑量还是多的,算是整个项目中工作量最大的地方了,写吐了。(对CAN驱动的UDS不熟悉的可以自行去百度:UDS协议)
在这里插入图片描述

事件绑定逻辑

举个例子
b3.ui
在这里插入图片描述

b3.py
在这里插入图片描述

比如我这里有个单选按钮,在UI生成的b3.py代码里的控件名叫radioButton,我想点击触发一个事件该怎么做呢?
 很简单:
 1,控件绑定事件函数
        #connect_device
        self.radioButton.clicked.connect(self.connect_ZLG)
        self.radioButton_2.clicked.connect(self.disconnect_ZLG)
        将按钮绑定到事件函数self.disconnect_ZLG,然后在事件函数里写自己的逻辑。

2,事件函数逻辑
		比如我这里写了一个关闭驱动并在文本页面打印字符串"Device close."的功能。
	    def disconnect_ZLG(self):
	        self.radioButton.setChecked(False)
	        self.z.close_device()
	        self.textBrowser.append("Device close.")

核心思路:
1, self.控件名.cliced.connect(self.事件函数名)         注意这里connect里写的参数是函数名,
												而不是函数,因此不要带括号()
												
2,然后在事件函数中写自己想要实现的功能逻辑
	

4.pyqt项目打包成exe

步骤一:pip install pyinstaller

步骤二:pyinstaller -F -w main.py

如果main.py在项目里调用了别的py文件,打包的main.py必须是项目中路径下的main.py 否则会提示找不到模块

pyinstaller -F -w ex1.py                   ex1.py为要运行的主py文件

会在当前目录下生成3样东西:

build文件夹		类似于C语言编译的.o文件,中间过程文件
dist文件夹		exe程序主文件
ex1.spec		这个为ex1.exe的配置文件,可以配置一些依赖包啥的,然后运行pyinstaller ex1.spec

如果有依赖包的话,直接运行exe是会报错的,将依赖包导入后正常可运行。(依赖包说明看步骤三)


运行dist文件夹中的ex1.exe并进行测试,发现程序可以运行;
并且在没有python环境的电脑上可以直接使用(亲测核实可用)。

步骤三:加载依赖包

    要用到依赖包的,把依赖包(文件、文件夹都可以)直接拖入dist文件夹中,放的位置和你项目里的主py文件
对应的位置关系一样。
	简而言之,把dist类比成你的项目,依赖包该放什么位置对应放进去就好了。
	可以类比对照着下面两个图理解。
	
	看明白了,觉得很简单了吧? 网上一堆人写的用pyinstaller啥啥啥命令,又或者是让你去改.spec配置文件
,但是又说不清楚的垃圾文章,看的我头都晕了,真的是又麻烦又垃圾。

项目名bootloader
在这里插入图片描述
dist文件夹
在这里插入图片描述

步骤四:exe程序测试(非python环境可用——亲测可用)

当初用pyinstaller ex1.py 和 pyinstaller -F -w ex1.py发现前者生成的dist文件中有很多pyqt5.dll
啥的包,而后者很简洁啥都没有,我在怀疑后者在无Python环境的电脑中是否可用?

    照着pyinstaller -F -w main.py编译出的3个东西(build文件夹、dist文件夹、ex1.spec),
然后依赖包配好,整理成一个文件夹,并且在当前电脑可运行后;我将整理成的文件夹拷到别的没有python环境的
电脑上运行,发现可以直接用。

(不用质疑为什么里面没有pyqt5.dll或者啥啥py文件,这些估计都变成了build文件夹里的中间文件了)

5.其他(bootloader项目用到的一些技术)

SREC文件解析

SREC、Hex、Bin等烧录文件格式完全解读

简略提一提解析构造

示例: S31500A6A0AA0070002011A4000079A4000079A40000CB
说明
S3Type
15指0x15,count(地址+数据+校验和),一个16位count增1,也就是每数2位count增1
00A6A0AA32位地址
data数据
CBchecksum

进度条实现思路

在这里插入图片描述

例:self.progressBar.setProperty("value", 24)
24表示设置进度条的值为24%(数字和绿色进度条是根据value设置的值对应变化的)

也就是说,我们可以在循环中,按百分比去set进度条的值。

例如: self.progressBar.setProperty("value", ((i+1)/total)*100)

6.总结

1,界面和架构分离的设计思路(主Py)

##

2,UI界面可以独立成一个Py文件供主py导入

如果需要预览纯UI界面的py文件,直接运行是打不开的;

需要在if__main__()函数这样写:
    app = QApplication(sys.argv)    # 创建应用程序
    mainwindow = QMainWindow()      # 创建主窗口
    ui = Ui_MainWindow()            # 调用Ui_MainWindow类主窗口
    ui.setupUi(mainwindow)          # 向主窗口添加控件
    mainwindow.show()               # 显示窗口
    sys.exit(app.exec_())           # 程序执行循环

3,打包exe

7.打包后遇到的问题

用命令pyinstaller -F -w main.py  (main.py必须是项目中路径下的main.py 否则会提示找不到模块)

打包后的exe(不能单独拿出来,只能build文件夹和dist文件夹放一起)

可以在无python环境的电脑下运行

pyinstaller 打包的exe在某些win7上面报错 faild to execute script pyi_rth_multiprocessing

在这里插入图片描述

参考这篇:pyinstaller 打包的exe在某些win7上面报错 faild to execute script pyi_rth_multiprocessing

本人已经核实:

1,用python3.6以上版本的环境打包的exe在有些win7电脑没有KB2533623补丁,需要把这个windows补丁打上,
按提示重启即可打开exe。

2.用python3.6环境再打包一下项目,编译出来的exe可以在没有KB2533623补丁的win7打开。

也就是说:

打包环境说明
python3.6以上未安装python环境的电脑可用;部分未打KB2533623补丁的Win7电脑会打不开报错
python3.6未安装python环境的电脑可用;任何win7、win10等都能用(不用打补丁)

作为一个打工仔,你总不可能要求客户去打补丁吧?
但是我的电脑上的python环境又是python3.8,我得下一个python3.6环境,但是pip又会默认是3.8的,
(平时都不用python3.6)我又懒得配置。
于是乎,我想到了一个法子。

1,下载python3.6环境

2,打开pycharm,新建一个虚拟环境的工程,环境选择你下载的python3.6路径

3,将要打包的文件复制粘贴到这个新的虚拟环境工程下

4,在pycharm控制台pip下载pyinstaller以及一些你报红的import的包
(我这里目前就只有一个pyqt5要下载,虚拟环境的下载速度感觉比本地快得多)

5,在控制台pyinstaller -F -w main.py   (main.py为要打包的exe)

6,如果有依赖包dll啥的放好,build和dist放一起,exe要在dist下打开,不多赘述了。

经过以上操作,打包后的exe可以在任何windows电脑上打开,包括无python环境的电脑。
Logo

鸿蒙生态一站式服务平台。

更多推荐