Python基础之用PyQt5界面代码分离以及自定义一个槽函数
最近开发一个项目,需要用到界面,遇到界面不能实时更新的问题,看到网上很多用槽函数,但是大多都是些button的,并不是我需要的,要么就是整数的,后来自己进行尝试,写了一个自定义的槽函数处理treewidget,特地分享出来。
背景:用QT Designer设计了一个界面,在程序运行中间调用界面,并随着程序的运行会更新treewidget。
问题1:如果在界面Class中写运行程序,那么结果会等到程序运行结束,最后界面出来,但是此时界面上已经是最终结果
解答:因为会等到程序结束才会加入界面mainloop中,执行到最后一句话,界面才会显示,所以解决办法就是将中间需要处理的代码放到线程中,这样就不会妨碍程序往下走了。
问题二:在线程中代码会需要更新界面,但是界面往往卡顿,只有鼠标点cmd窗口,在点回界面时,数据才刷新,不能更好的看到程序运行的结果。
解答:PyQt5中不友好支持子线程中对界面的设置,需要使用槽函数,信号触发的方式来更新界面。
为了更好的演示,这里先介绍一下把界面和代码分离的方法
现在开始自定义槽函数。
先看分离后的函数:
treeview4_test.py
- from PyQt5.QtWidgets import QApplication, QMainWindow, QFileDialog
- from PyQt5 import QtCore, QtGui, QtWidgets
- import treeview4
- import treeview_data
- import sys
- class MainCode(QMainWindow, treeview4.Ui_MainWindow):
- def __init__(self):
- QMainWindow.__init__(self)
- treeview4.Ui_MainWindow.__init__(self)
- self.setupUi(self)
- # 设置列宽
- self.treeWidget.setColumnWidth(0, 200)
- _translate = QtCore.QCoreApplication.translate
- self.initial_tree_view(_translate)
- self.treeWidget.expandAll()
- def initial_tree_view(self, _translate):
- list_objects = []
- test1 = treeview_data.DataCollection()
- test1.set_module({"Test1": "waiting"})
- test1.add_item({"a1": "waiting"})
- test1.add_item({"b1": "waiting"})
- test1.add_item({"c1": "waiting"})
- list_objects.append(test1)
- test2 = treeview_data.DataCollection()
- test2.set_module({"Test2": "waiting"})
- test2.add_item({"a2": "waiting"})
- test2.add_item({"b2": "waiting"})
- test2.add_item({"c2": "waiting"})
- test2.add_item({"d2": "waiting"})
- list_objects.append(test2)
- test3 = treeview_data.DataCollection()
- test3.set_module({"Test3": "waiting"})
- test3.add_item({"a2": "waiting"})
- test3.add_item({"b2": "waiting"})
- test3.add_item({"c2": "waiting"})
- test3.add_item({"d2": "waiting"})
- list_objects.append(test3)
- for object_num, object_module in enumerate(list_objects):
- item_0 = QtWidgets.QTreeWidgetItem(self.treeWidget)
- brush = QtGui.QBrush(QtGui.QColor(176, 165, 172))
- brush.setStyle(QtCore.Qt.SolidPattern)
- item_0.setBackground(0, brush)
- for module_name, module_result in object_module.module.items():
- brush = QtGui.QBrush(QtGui.QColor(0, 255, 0))
- brush.setStyle(QtCore.Qt.SolidPattern)
- item_0.setBackground(1, brush)
- self.treeWidget.topLevelItem(object_num).setText(0, _translate("MainWindow", module_name))
- self.treeWidget.topLevelItem(object_num).setText(1, _translate("MainWindow", module_result))
- for item_num, item_dic in enumerate(object_module.items):
- for item_name, item_result in item_dic.items():
- item_1 = QtWidgets.QTreeWidgetItem(item_0)
- self.treeWidget.topLevelItem(object_num).child(item_num).setText(0, _translate("MainWindow",
- item_name))
- self.treeWidget.topLevelItem(object_num).child(item_num).setText(1, _translate("MainWindow",
- item_result))
- if __name__ == "__main__":
- app = QApplication(sys.argv)
- md = MainCode()
- md.show()
- app.exec_()
- # sys.exit(app.exec_())
然后调用子线程进行刷新:
- from PyQt5.QtWidgets import QApplication, QMainWindow, QFileDialog
- from PyQt5 import QtCore, QtGui, QtWidgets
- import treeview4
- import treeview_data
- import sys
- import threading
- import time
- class MainCode(QMainWindow, treeview4.Ui_MainWindow):
- list_result_update = QtCore.pyqtSignal([int, int, str])
- def __init__(self):
- QMainWindow.__init__(self)
- treeview4.Ui_MainWindow.__init__(self)
- self.setupUi(self)
- # 设置列宽
- self.treeWidget.setColumnWidth(0, 200)
- _translate = QtCore.QCoreApplication.translate
- self.initial_tree_view(_translate)
- self.treeWidget.expandAll()
- # 用列表触发槽函数
- self.list_result_update.connect(self.modified_treewidget)
- # 线程函数
- self.run()
- def run(self):
- th = threading.Thread(target=self.go_update)
- th.setDaemon(True)
- th.start()
- def initial_tree_view(self, _translate):
- list_objects = []
- test1 = treeview_data.DataCollection()
- test1.set_module({"Test1": "waiting"})
- test1.add_item({"a1": "waiting"})
- test1.add_item({"b1": "waiting"})
- test1.add_item({"c1": "waiting"})
- list_objects.append(test1)
- test2 = treeview_data.DataCollection()
- test2.set_module({"Test2": "waiting"})
- test2.add_item({"a2": "waiting"})
- test2.add_item({"b2": "waiting"})
- test2.add_item({"c2": "waiting"})
- test2.add_item({"d2": "waiting"})
- list_objects.append(test2)
- test3 = treeview_data.DataCollection()
- test3.set_module({"Test3": "waiting"})
- test3.add_item({"a2": "waiting"})
- test3.add_item({"b2": "waiting"})
- test3.add_item({"c2": "waiting"})
- test3.add_item({"d2": "waiting"})
- list_objects.append(test3)
- for object_num, object_module in enumerate(list_objects):
- item_0 = QtWidgets.QTreeWidgetItem(self.treeWidget)
- brush = QtGui.QBrush(QtGui.QColor(176, 165, 172))
- brush.setStyle(QtCore.Qt.SolidPattern)
- item_0.setBackground(0, brush)
- for module_name, module_result in object_module.module.items():
- brush = QtGui.QBrush(QtGui.QColor(0, 255, 0))
- brush.setStyle(QtCore.Qt.SolidPattern)
- item_0.setBackground(1, brush)
- self.treeWidget.topLevelItem(object_num).setText(0, _translate("MainWindow", module_name))
- self.treeWidget.topLevelItem(object_num).setText(1, _translate("MainWindow", module_result))
- for item_num, item_dic in enumerate(object_module.items):
- for item_name, item_result in item_dic.items():
- item_1 = QtWidgets.QTreeWidgetItem(item_0)
- self.treeWidget.topLevelItem(object_num).child(item_num).setText(0, _translate("MainWindow",
- item_name))
- self.treeWidget.topLevelItem(object_num).child(item_num).setText(1, _translate("MainWindow",
- item_result))
- def modified_treewidget(self, num_one, num_two, str_one):
- _translate = QtCore.QCoreApplication.translate
- self.treeWidget.topLevelItem(num_one).child(num_two).setText(1, _translate(
- "MainWindow",
- str_one))
- def go_update(self):
- time.sleep(1)
- # 更新treeview
- self.list_result_update.emit(1, 1, "aaaaaaa")
- if __name__ == "__main__":
- app = QApplication(sys.argv)
- md = MainCode()
- md.show()
- app.exec_()
- # sys.exit(app.exec_())
现在就完成了自定义槽函数了。
Python基础之用PyQt5界面代码分离以及自定义一个槽函数的更多相关文章
- 基于Python接口自动化测试框架+数据与代码分离(进阶篇)附源码
引言 在上一篇<基于Python接口自动化测试框架(初级篇)附源码>讲过了接口自动化测试框架的搭建,最核心的模块功能就是测试数据库初始化,再来看看之前的框架结构: 可以看出testcase ...
- python基础--小数据池,代码块的最详细、深入剖析
本文转至太白金星 一,id,is,== 在Python中,id是什么?id是内存地址,那就有人问了,什么是内存地址呢? 你只要创建一个数据(对象)那么都会在内存中开辟一个空间,将这个数据临时加在到内存 ...
- Python基础库之jieba库的使用(第三方中文词汇函数库)
各位学python的朋友,是否也曾遇到过这样的问题,举个例子如下: “I am proud of my motherland” 如果我们需要提取中间的单词要走如何做? 自然是调用string中的spl ...
- python基础-requests模块、异常处理、Django部署、内置函数、网络编程
网络编程 urllib的request模块可以非常方便地抓取URL内容,也就是发送一个GET请求到指定的页面,然后返回HTTP的响应. 校验返回值,进行接口测试: 编码:把一个Python对象编码转 ...
- Python基础总结之第十一天开始【再深入一下函数,重新认识一下】(新手可相互督促)
感谢最近大家的关注,希望我的学习笔记对大家有帮助!也感谢各位的评论和推荐,请多多指教. 在重新认识函数之前,我们先看两个函数.一个是我们在前面笔记经常用到的print() :另一个是input() ...
- PyQt(Python+Qt)学习随笔:Qt Designer中连接Action和槽函数
在Designer中试了半天,终于找到了Action添加槽函数的方法,操作步骤: 在Designer右边界面中点击鼠标右键 确保信号/槽编辑被勾选,如图是未勾选的情况:. 勾选后会出现信号和槽的编辑界 ...
- python基础===如何优雅的写代码(转自网络)
本文是Raymond Hettinger在2013年美国PyCon演讲的笔记(视频, 幻灯片). 示例代码和引用的语录都来自Raymond的演讲.这是我按我的理解整理出来的,希望你们理解起来跟我一样顺 ...
- python基础知识-8-三元和一行代码(推导式)
python其他知识目录 1.三元运算(三目运算) 三元运算符就是在赋值变量的时候,可以直接加判断,然后赋值格式:[on_true] if [expression] else [on_false]re ...
- Python基础之用PyQt5写一个tabview
前面学习了menu的画图,现在学习tabview的画图,关于怎么打开designer.exe部分就不详细介绍了. 第一步:拖动一个Tab Widget控件到窗口去. 将控件拖上去之后就是这个样子,默认 ...
随机推荐
- 【Android编程】android平台的MITM瑞士军刀_cSploit源码解析及中间人攻击复现
/文章作者:Kali_MG1937 作者博客ID:ALDYS4 QQ:3496925334 未经允许,禁止转载/ 何为MITM欺骗,顾名思义,中间人攻击的含义即为在局域网中充当数据包交换中间人的角色 ...
- canal+mysql+kafka实时数据同步安装、配置
canal+mysql+kafka安装配置 概述 简介 canal译意为水道/管道/沟渠,主要用途是基于 MySQL 数据库增量日志解析,提供增量数据订阅和消费. 基于日志增量订阅和消费的业务包括 数 ...
- 身为一枚优秀的程序员必备的基于Redis的分布式锁和Redlock算法
1 前言 今天开始来和大家一起学习一下Redis实际应用篇,会写几个Redis的常见应用. 在我看来Redis最为典型的应用就是作为分布式缓存系统,其他的一些应用本质上并不是杀手锏功能,是基于Redi ...
- 孟老板 ListAdapter封装, 告别Adapter代码 (四)
BaseAdapter系列 ListAdapter封装, 告别Adapter代码 (一) ListAdapter封装, 告别Adapter代码 (二) ListAdapter封装, 告别Adapter ...
- 音视频点播服务基础系列(Fmpeg常用命令)
前言 公司业务中有一些场景需要用到服务端音视频剪辑技术,最开始为了快速上线使用的是某公有云的商用解决方案,但由于费用太高所以我们团队经过一个星期的冲刺,给出了一个FFmpeg+Serverless的解 ...
- CSS 奇思妙想 | 全兼容的毛玻璃效果
通过本文,你能了解到 最基本的使用 CSS backdrop-filter 实现磨砂玻璃(毛玻璃)的效果 在至今不兼容 backdrop-filter 的 firefox 浏览器,如何利用一些技巧性的 ...
- 最多能创建多少个 TCP 连接?
我是一个 Linux 服务器上的进程,名叫小进. 老是有人说我最多只能创建 65535 个 TCP 连接. 我不信这个邪,今天我要亲自去实践一下. 我走到操作系统老大的跟前,说: "老操,我 ...
- 二叉搜索树(Binary Search Tree)(Java实现)
@ 目录 1.二叉搜索树 1.1. 基本概念 1.2.树的节点(BinaryNode) 1.3.构造器和成员变量 1.3.公共方法(public method) 1.4.比较函数 1.5.contai ...
- layui 监听checkbox 、radio、switch选中改变事件
form.on('checkbox(filter)', function(data){ console.log(data.elem); //得到checkbox原始DOM对象 console.log( ...
- 重新整理 .net core 实践篇————cookie 安全问题[三十八]
前言 简单整理一下cookie的跨站攻击,这个其实现在不常见,因为很多公司都明确声明不再用cookie存储重要信息,不过对于老站点还是有的. 正文 攻击原理: 这种攻击要达到3个条件: 用户访问了我们 ...