PyQt5中的QObject对象

QObject

  • 在Qt中QObject是所有类的基类,换而言之是在Qt中所有的类均继承自QObject,这使得QObject中的所有方法在其它类中使用。所以学习QObject中的方法有其特殊的意义。
继承结构测试的方法
from PyQt5.QtCore import QObject

# 创建一个QObject对象
obj = QObject()
# 获得父类
mros = QObject.mro()
for mro in mros:
    print(mro)
# 结果如下:
#     
#     
#     
#     

对象名称、属性相关操作
from PyQt5.QtCore import QObject

# 创建一个QObject对象
obj = QObject()
# 设置对象名称
obj.setObjectName("new_object_name")
# 获取对象名称
obj.objectName()
# 添加对象动态属性与值
obj.setProperty("property_name", value)
# 获得对象某一属性对应的值
obj.property("property")    # 将返回value
# 获取一个对象中通过setProperty()设置的所有属性名称
obj.dynamicPropertyNames()
  • 设置对象名称
obj.setObjectName('new_object_name')
  • 获取对象的名称
obj.objectName()
  • 添加对象动态属性与值
obj.setProperty("property_name",value)
  • 获得对象某一属性对应的值
obj.property("property_name")  # 将返回value
  • 获取一个对象中通过setProperty()设置的所有属性名称
obj.dynamicPropertyNames()
  • 应用场景用于qss的ID选择器和属性选择器,同时可以应用于装饰墙的信号与槽;
父子对象操作
# 创建QObject对象
obj1 = QObject()
obj2 = QObject()
# 设置父对象,将obj1设置为obj2的父对象
print(obj1)		# return:
obj2.setParent(obj1)
# 获取父对象
obj2.parent()		# return:
# 获取所有直接子对象
print(obj2)		# return:
obj1.children()		# return:[]
# 获取某一个指定名称和类型的子对象
obj.findChild(参数1, 参数2, 参数3)
# 获取某多个指定名称和类型的子对象
objfindChildren(参数1, 参数2, 参数3)
  • 应用场景:
    • 涉及到Qt对象的内存管理机制;
    • 如果一个控件没有父控件,则会被当成顶层控件来使用;
    • 如果想要一个控件被包含在控件内部,就需要设置父子关系;
信号处理
  • 需要了解QObject的信号处理,首先需要了解的是什么是信号与槽机制,信号(signal)和槽(slot)是Qt中的核心机制,主要作用在于对象之间的通信。
    • 信号指的是,当一个控件的状态发生改变时,向外发射信息;
    • 槽指的是,一个执行某些操作的函数/方法。所有继承自QWidget的控件都支持“信号与槽”的机制。
      • 一个信号可以连接多个槽函数;
      • 一个信号也可以连接另一个信号;
      • 信号的参数可以是任何python类型;
      • 一个槽可以监听多个信号。
# 基本语法
widget.信号.connect(槽函数)
对象被销毁时发射的信号
  • 对象销毁指的是窗口被关闭
from PyQt5.QtCore import QObject
from PyQt5.QtWidgets import QApplication, QWidget
import sys


class Test_slot(QWidget):
    def __init__(self):
        super().__init__()
        # 创建一个QObject对象
        self.initUI()

    def initUI(self):
        # 创建QObject对象
        obj = QObject()
        obj.destroyed.connect(self.slot_fun)
        self.show()

    # 定义一个槽函数
    def slot_fun(self):
        print("aaaa")


if __name__ == "__main__":
    app = QApplication(sys.argv)
    test = Test_slot()
    sys.exit(app.exec_())
  • 当关闭窗口时,会打印"aaaa"
对象名称发生改变时发射此信号
from PyQt5.QtCore import QObject
from PyQt5.QtWidgets import QApplication, QWidget
import sys


class Test_slot(QWidget):
    def __init__(self):
        super().__init__()
        # 创建一个QObject对象
        self.initUI()

    def initUI(self):
        # 创建QObject对象
        obj = QObject()
        # 设置一个对象名,也可以不设置
        obj.setObjectName("init_object_name")
        obj.objectNameChanged.connect(self.slot_fun)
        # 改变对象名
        obj.setObjectName("new_object_name")
        self.show()

    # 定义一个槽函数
    def slot_fun(self, return_value):
        print("对象名称改变了", return_value)


if __name__ == "__main__":
    app = QApplication(sys.argv)
    test = Test_slot()
    sys.exit(app.exec_())
信号的其他操作
  • 创建QObject对象
obj = QObject()
  • 对象信号连接的一般表达式
obj.信号.connect(槽函数)
  • 取消对象信号连接,切断信号与某个槽函数的连接,切断之后可以再次执行连接函数进行重新连接
obj.信号.disconnect()
  • 临时(取消)阻止指定控件所有的信号与槽的连接
obj.blockSignals(True/False)  # True为临时阻断;False为重新连接
  • 查看信号是否被阻断
obj.signalsBlock()  # 返回bool值
  • 返回连接信号接收器的数量(一个信号可以连接多个信号)
obj.receivers(obj.信号)  # 注意传入的应该是一个pyqt的信号
类型判定
  • 类型的判定是一个比较简单的概念,有两个功能:
    • 一个是用于判断某一个对象是否是一个控件;
    • 另一个是判断其是否继承自某一个父类。
判断某一对象是否为控件类别
# 创建几个对象
obj = QObject()
win = QWidget()
btn = QPushButton()
lab = QLable()
# 判断某一对象是否是一个控件
isWidgetType(obj)  # False
isWidgetType(win)  # True
isWidgetType(btn)  # True
isWidgetType(lab)  # True
判断一个对象是否继承(直接继承或间接继承)于某个类
obj.inherits(父类)
对象删除
  • 在Qt中提供了一个对象删除方法deleteLater()。在删除一个对象时,也会解除它与父对象之间的关系。
  • 从字面上理解可以知道,deleteLater()并没有将对象立即销毁,而是向著消息循环发送一个event,下一次著消息循环到这个event之后才会销毁对象;这样的好处是可以在这些延迟删除的时间内完成一些操作,坏处就是内存释放会不及时。
事件处理
  • 信号与槽可以说是对事件机制的高级封装,事件机制是更为底层的概念;用户的操作都会产生一个事件消息(如鼠标点击事件、键盘敲击事件),这些操作事件消息将发送给操作系统,操作系统会将消息分发到对应的应用程序“消息队列”中;应用程序中的消息循环,会不停的监听队列中是否有时间消息。
    PyQt5中的QObject对象_第1张图片
  • 当检测到队列中有时间消息时,就会将事件接收者(receiver)和事件对象(evt)传递给QApplication对象的notify(receriver,evt),再由该方法进行分发,即分发给receiver对象的event(evt)方法,此方法会根据evt的事件类型分发给receiver具体的事件函数;如mousePressEvent(evt)、mousePeleaseEent(evt)等等;
import sys
from PyQt5.Qt import *
# 重写QApplication里面的notify方法
class App(QApplication):
    def notify(self, receiver, evt):
        # 过滤接受器和消息类型
        if receiver.inherits("QPushButton") and evt.type() == QEvent.MouseButtonPress:
            print(receiver, evt)
        return super().notify(receiver, evt)

# 事件会分发给receiver的event()方法,同样我们也也可以改写receiver里面的event方法


class Btn(QPushButton):
    def event(self, evt):
        print(evt)
        return super().event(evt)



# 创建一个应用程序
app = App(sys.argv)
# 控件操作,包括控件的创建、设置、添加子控件等等
window = QWidget()
btn = Btn(window)
btn.setText('button')
btn.move(100, 100)
# 创建槽函数


def slot_fun():
    print('按钮被点击了')
# 创建信号连接机制
btn.pressed.connect(slot_fun)
# 开始执行应用程序,并进入消息循环
window.show()
sys.exit(app.exec_())
定时器
  • 创建一个定时器,可以在规定的时间向外发送一个timerEvent()信号,我们可以改写类里面的timerEvent()方法,从而实现按规定时间执行某一操作;
  • 使用的API有:
# 开启一个计时器,返回一个定时器标识符(time_id)可以用这个time_id关闭定时器
startTimer(ms, Qt.TimerType)

# 定时器执行时间
timerEvent()

# 根据定时器ID,杀死定时器
killTimer(timer_id)
代码示例
# 主要包含了我们常用的一些类,汇总到了一块
from PyQt5.Qt import *
import sys

# 重写QObject对象
class MyObject(QObject):
    def timerEvent(self, evt):
        print(evt)



# 创建一个应用程序对象
app = QApplication(sys.argv)

# 3、控件的操作
# 3.1、创建控件
window = QWidget()  # 创建一个主程序框

obj = MyObject()
# 开启一个定时器
timer_id = obj.startTimer(1000)

# 3.2、设置控件
window.setWindowTitle('')
window.resize(500, 500)
# 3.3、展示控件
window.show()


# 4、应用程序的执行、进入消息循环。使整个程序进入无限循环
sys.exit(app.exec_())

你可能感兴趣的:(PyQt5中的QObject对象)