学习计划
功能作用
1.对象名称,属性。
应用场景
- 进行控件样式的分组管理
from PyQt5.Qt import *
class Window(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle("QObject的学习")
self.resize(500, 500)
self.setup_ui()
def setup_ui(self):
self.QObject对象名称和属性的操作()
def QObject对象名称和属性的操作(self):
# *************测试API***************开始
# obj = QObject()
# obj.setObjectName("notice")
# print(obj.objectName())
# obj.setProperty("notice_level", "error")
# obj.setProperty("notice_level2", "warning")
# print(obj.property("notice_level"))
# print(obj.dynamicPropertyNames())
# **************测试API**************结束
# *************案例演示***************开始
with open("QObject.qss", "r") as f:
#全局app(应用)对象,根据文件中的指示进行样式设置
qApp.setStyleSheet(f.read())
label = QLabel(self)
#设置属性名称,在qss中用#指定
label.setObjectName("notice")
label.setProperty("notice_level", "warning")
label.setText("社会小香猪")
# label.setStyleSheet("font-size: 20px; color: red;")
label2 = QLabel(self)
#设置属性名称,在qss中用#指定
label2.move(100, 100)
label2.setObjectName("notice")
label2.setProperty("notice_level", "error")
label2.setText("人狠话不多")
label3 = QLabel(self)
#设置属性名称,在qss中用#指定
label3.move(150, 150)
label3.setObjectName("notice")
label3.setProperty("notice_level", "normal")
label3.setText("xxxx")
btn = QPushButton(self)
btn.setObjectName("notice")
btn.setText("btn")
btn.move(50, 50)
# *************案例演示***************结束
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())
2.父子对象的操作
应用场景
- 便于内存管理,如:父对象被删除,子对象会被自动删除不会保留下来占用内存空间。
om PyQt5.Qt import *
class Window(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle("QObject的学习")
self.resize(500, 500)
self.setup_ui()
def setup_ui(self):
self.QObject对象的父子关系操作()
def QObject对象的父子关系操作(self):
# *************测试API***************开始
# obj0 = QObject()
# obj1 = QObject()
# obj2 = QObject()
# obj3 = QObject()
# obj4 = QObject()
# obj5 = QObject()
# obj1.setParent(obj0)
# obj2.setParent(obj0)
# obj2.setObjectName("2")
# #不属于容器的控件不能设置QObject为父对象,必须为容器,如:QWidget
# # label = QLabel()
# # label.setParent(obj0)
# obj3.setParent(obj1)
# obj3.setObjectName("3")
# obj4.setParent(obj2)
# obj5.setParent(obj2)
# #获取直接父对象
# print(obj1.parent())
# #获取直接子对象
# print(obj0.children())
# #添加筛选条件的寻找子对象,3为指定对象名下的控件,并查找直接子对象
# print(obj0.findChild(QObject, "3", Qt.FindDirectChildrenOnly))
# print(obj0.findChildren(QObject))
# *************测试API***************结束
# *************内存管理机制***************开始
obj1 = QObject()
self.obj1 = obj1
obj2 = QObject()
obj2.setParent(obj1)
# 监听obj2对象被释放
obj2.destroyed.connect(lambda : print("obj2对象被释放了"))
del self.obj1
# *************内存管理机制***************结束
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())
3.信号处理
应用场景
- 核心部分!!!用于实现各种功能的响应。
测试信号
from PyQt5.Qt import *
class Window(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle("QObject的学习")
self.resize(500, 500)
self.setup_ui()
def setup_ui(self):
self.QObject信号的操作()
def QObject信号的操作(self):
# *************API***************开始
###1.destroyed信号
# #创建obj对象
# self.obj = QObject()
# #设槽
# def destroy_cao(obj):
# print("对象被释放了", obj)
# #将槽函数连接到信号上
# self.obj.destroyed.connect(destroy_cao)
# #释放obj对象,触发信号
# del self.obj
###2.objectNameChanged信号
# self.obj = QObject()
# def obj_name_cao(name):
# print("对象名称发生了改变", name)
# #一个信号连接多个槽
# def obj_name_cao2(name):
# print("对象名称发生了改变2", name)
# self.obj.objectNameChanged.connect(obj_name_cao)
# self.obj.objectNameChanged.connect(obj_name_cao2)
# #获取当前对象信号的槽函数数量
# print(self.obj.receivers(self.obj.objectNameChanged))
# self.obj.setObjectName("xxx")
# #断开信号与槽之间的连接
# # self.obj.objectNameChanged.disconnect()
# #获取当前对象信号与槽的连接是否断开:False
# print(self.obj.signalsBlocked(), "1")
# #是否临时取消信号与槽之间的连接
# self.obj.blockSignals(True)
# #获取当前对象信号与槽的连接是否断开:True
# print(self.obj.signalsBlocked(), "2")
# self.obj.setObjectName("ooo")
# #重新建立信号与槽之间的连接
# self.obj.blockSignals(False)
# #获取当前对象信号与槽的连接是否断开:False
# print(self.obj.signalsBlocked(), "3")
# self.obj.setObjectName("xxoo")
# *************API***************结束
# *************信号与槽案例***************开始
btn = QPushButton(self)
btn.setText("点击我")
def cao():
print("点我嘎哈?")
btn.clicked.connect(cao)
# *************信号与槽案例***************结束
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())
4.类型判定
应用场景
- 判定对象控件类型
- 判定控件是否继承自某一控件
from PyQt5.Qt import *
class Window(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle("QObject的学习")
self.resize(500, 500)
self.setup_ui()
def setup_ui(self):
# self.QObject类型判定()
def QObject类型判定(self):
# *************API***************开始
# obj = QObject()
# w = QWidget()
# btn = QPushButton()
# label = QLabel()
# objs = [obj, w, btn, label]
# #循环判断继承类型
# for o in objs:
# #是否是Widget类型控件
# print(o.isWidgetType())
# #是否继承自QWidget
# print(o.inherits("QWidget"))
# #是否继承自QPushButton
# print(o.inherits("QPushButton"))
# *************API***************结束
# *************案例***************开始
label1 = QLabel(self)
label1.setText("社会小香猪")
label1.move(100, 100)#移动控件,避免重叠
label2 = QLabel(self)
label2.setText("人狠话不多")
label2.move(150, 150)#移动控件,避免重叠
# # del label2
# label2.deleteLater()
btn = QPushButton(self)
btn.setText("点我")
btn.move(200, 200)#移动控件,避免重叠
for widget in self.children():
print(widget)
#判断是否是Widget类型,并更改样式:三个都是
# if widget.isWidgetType():
# widget.setStyleSheet("background-color: cyan;")
#判断是否继承自QLabel:两个
if widget.inherits("QLabel"):
widget.setStyleSheet("background-color: cyan;")
# *************案例***************结束
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())
5.对象删除
应用场景
from PyQt5.Qt import *
class Window(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle("QObject的学习")
self.resize(500, 500)
self.setup_ui()
def setup_ui(self):
self.QObject对象删除()
def QObject对象删除(self):
obj1 = QObject()
#如果不将obj1挂在window下那么他就会因为没有引用而
#立即销毁,从而将两个子控件也销毁。
self.obj1 = obj1
obj2 = QObject()
obj3 = QObject()
obj3.setParent(obj2)
obj2.setParent(obj1)
obj1.destroyed.connect(lambda : print("obj1被释放了"))
obj2.destroyed.connect(lambda : print("obj2被释放了"))
obj3.destroyed.connect(lambda : print("obj3被释放了"))
#直接del只是将指向obj2的连接删除了
#真正的obj2会等待程序停止后统一删除。
# del obj2
#向主消息循环发送了一个event,进行稍后删除,真正的将obj2释放了
#不仅解除了引用,还解除了与父对象的连接
obj2.deleteLater()
#两种删除方式都不是立刻删除,都是等主循环结束后才删除,所以还是可以看到子节点
print(obj1.children())
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())
7.定时器
应用场景
- 案例一:倒计时
- 案例二:创建窗口,并且窗口尺寸随时间不断变化
# 0. 导入需要的包和模块
from PyQt5.Qt import *
import sys
#案例一:倒计时
class MyLabel(QLabel):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.setText("10")
self.move(100, 100)
self.setStyleSheet("font-size: 22px;")
#自定义函数,用于更改初始秒数
def setSec(self, sec):
#可以通过输入秒数来自定义倒计时,默认是10s
self.setText(str(sec))
#自定义函数,用于开启倒计时
def startMyTimer(self, ms):
self.timer_id = self.startTimer(ms)
#该类需要重写,即每次到时间执行的操作都在这
def timerEvent(self, *args, **kwargs):
print("xx")
# 1.获取当前的标签的内容,并进行类型转换
current_sec = int(self.text())
current_sec -= 1
#int数据不能放到文本里,需要转成文本
self.setText(str(current_sec))
#设定结束条件,结束定时器
if current_sec == 0:
print("停止")
self.killTimer(self.timer_id)
# 1. 创建一个应用程序对象
app = QApplication(sys.argv)
# 2. 控件的操作
# 2.1 创建控件
window = QWidget()
# 2.2 设置控件
window.setWindowTitle("QObject定时器的使用")
window.resize(400, 400)
#建立输出文本框
label = MyLabel(window)
label.setSec(10)
label.startMyTimer(1000)
# 2.3 展示控件
window.show()
# 3. 应用程序的执行, 进入到消息循环
sys.exit(app.exec_())
#案例二:随时间不断变化窗口尺寸(不停止一直增加,需要手动关闭)
class MyWidget(QWidget):
#该类需要重写,即每次到时间执行的操作都在这
def timerEvent(self, *args, **kwargs):
current_w = self.width()
current_h = self.height()
self.resize(current_w + 10, current_h + 10)
# 1. 创建一个应用程序对象
app = QApplication(sys.argv)
# 2. 控件的操作
# 2.1 创建控件
window = MyWidget()
# 2.2 设置控件
window.setWindowTitle("QObject定时器的使用")
window.move(100,100)
window.resize(100, 100)
window.startTimer(1000)
# 2.3 展示控件
window.show()
# 3. 应用程序的执行, 进入到消息循环
sys.exit(app.exec_())