QT信号槽实现分析

1.宏定义

qt中引入了MOC来反射,编译阶段变成 MOC-->预处理-->编译-->汇编-->链接

1-1、Q_OBJECT

这个宏定义了一系列代码,包括元对象和处理的函数

cpp 复制代码
#define Q_OBJECT \
	public: \
	    QT_WARNING_PUSH \
	    Q_OBJECT_NO_OVERRIDE_WARNING \
	    static const QMetaObject staticMetaObject; \
	    virtual const QMetaObject *metaObject() const; \
	    virtual void *qt_metacast(const char *); \
	    virtual int qt_metacall(QMetaObject::Call, int, void **); \
	    QT_TR_FUNCTIONS \
	private: \
	    Q_OBJECT_NO_ATTRIBUTES_WARNING \
	    Q_DECL_HIDDEN_STATIC_METACALL static void qt_static_metacall(QObject *, 		QMetaObject::Call, int, void **); \
	    QT_WARNING_POP \
	    struct QPrivateSignal {}; \
	    QT_ANNOTATE_CLASS(qt_qobject, "")

1-2、signal slot emit

从如下得知,slot和emit只是作一个修饰而已,本身为空没有任何作用,signal也只是声明为pulic

cpp 复制代码
#define signal public
#define slot
#define emit

1-2、qt4中诞生的SIGANL SLOT

可以看到这两个宏也只是把我们输入的函数转成了字符串,后续去匹配

cpp 复制代码
#define SIGANL "2"#a
#define SLOT "1"#a

我们去VS项目--属性--C/C+±-预处理器--预处理文件生成选择:是

发现预编译后宏展开如下。即验证上述

2.信号槽规则

1.信号的参数可以比槽多,反之不行,信号槽可以一对一,一对多,多对一

2.槽函数执行的顺序是按连接时的顺序依次执行的,重复connect会导致多次执行

cpp 复制代码
connect(obj, SIGNAL(sig1), this, SLOT(slot1()));
connect(obj, SIGNAL(sig1), this, SLOT(slot2()));
那么sig1发出时,先执行槽函数 slot1, 再执行槽函数 slot2

3.如果用SIGNAL方式connect,可以不需要作用域,因为上面说过了,他把他转为了字符串。目前遇到好处是可以绑定多态信号槽,而无需引入派生类文件。坏处是不会进行检查,编译时才报warning

qt5的方式connect就需要,好处是写代码时就会进行参数匹配检查

4.连接可以被disconnect删除

5.注意connect第五个参数,详细可以见QT第五个参数,举两个常见例子

在子线程抛出来信号,主线程若不绑定为QueuedConnection或BlockingQueuedConnection,会接收不到。

如果用BlockingQueuedConnection,信号槽不能在同一个线程因为发送完信号后发送者所在线程会阻塞,直到槽函数运行完。本来就阻塞了。更别谈槽函数运行了。死锁了

3.connect实现

connect实现代码非常多,感兴趣的可以到这里阅读:QT5 qobject.cpp

总结下来分为这几步:

1.QObject类对象内部维护了一个名为connectionLists的成员变量,用于记录信号和槽函数的关联

2.MOC 会在预处理阶段根据 Q_OBJECT 宏生成对应的元对象信息,并将这些信息存储在 QObject 类中的一个指针变量中,可以通过 QObject::metaObject() 方法获取

3.在发射信号时,信号方会生成一个携带信号索引和参数的结构体,然后调用 QMetaObject::activate() 方法。QMetaObject::activate() 方法会先根据槽函数所在的类的元对象信息,获取该类存储的槽函数索引,然后根据索引找到相应的槽函数并调用

相关推荐
Elias不吃糖9 分钟前
Qt TCP 网络通信详解(笔记)
笔记·qt·tcp/ip
B站计算机毕业设计之家35 分钟前
深度学习:YOLOv8人体行为动作识别检测系统 行为识别检测识系统 act-dataset数据集 pyqt5 机器学习✅
人工智能·python·深度学习·qt·yolo·机器学习·计算机视觉
雨田嘟嘟12 小时前
QML ChartView 崩溃
qt
Aevget14 小时前
从复杂到高效:QtitanNavigation助力金融系统界面优化升级
c++·qt·金融·界面控件·ui开发
Jay Chou why did15 小时前
0. Qt 安装及源码及报错
qt
nianniannnn21 小时前
Qt布局管理停靠窗口QDockWidget类
开发语言·数据库·c++·qt·qt5·qt6.3
牵牛老人1 天前
Qt 中如何操作 Excel 表格:主流开源库说明介绍与 QXlsx 库应用全解析
qt·开源·excel
牵牛老人1 天前
QXlsx操作Excel深度解析:核心类接口与 Qt C++ 功能解析
qt
长沙红胖子Qt1 天前
关于 Qt5.x版本离线安装可以跳过登录但是实际离线仍需要登录 的解决方法
qt·离线安装·离线无法skip
友友马1 天前
『 QT 』QT控件属性全解析 (二)
开发语言·数据库·qt