【信号与槽机制】

news2024/11/24 22:37:53

信号与槽机制

  • 🌟 信号函数
  • 🌟 槽函数
  • 🌟 连接函数
  • 🌸 QObejct::connect函数剖析
  • 🌟 官方文档中给出的定义
  • 🌟《Qt 5.9 C++开发指南》中的定义

在这里插入图片描述

🌟 信号函数

信号是一种特殊的成员函数,用于在特定事件发生时发出通知。一个类可以定义一个或多个信号,并在适当的时候发射(emit)这些信号。信号通常声明为 signals 关键字的一部分。

  • 范例:
    MyPushButton是一个自定义按钮控件类,继承于QPushButton。
class MyPushButton : public QPushButton
{
    Q_OBJECT
	explicit  MyPushButton(QWidget *parent = nulltpr);
signals://声明信号关键字
	//点击信号,是Qt预定义提供的信号
    void clicked();
    //发送按钮名称信号,自定义的信号
	void sendBtnNameSignal(const QString &btnName);
};
  • 发信号需要使用一个关键字:emit
void MyPushButton::MyPushButton(QWidget *parent)
	: QPushButton(parent)
{
	emit sendBtnNameSignal("btn");//在构造中发出发送按钮名称信号
}

🌟 槽函数

槽是普通的成员函数,用于响应信号。槽函数的特殊之处在于它们可以连接到一个或多个信号,以便在相关的信号被发射时被调用。

  • 范例:
    MyTextEdit是一个自定义富文本编辑控件类,继承于QTextEdit。
class MyTextEdit: public QTextEdit
{
    Q_OBJECT
//slots:是声明槽函数的关键字,public slots:表明这个一个公有成员槽函数
public slots:
	void SetBtnNameSlot(const QString &btnName);//设置按钮名称槽函数
};

🌟 连接函数

设置完信号函数和槽函数之后,它们还无法进行信息传递,还需要添加一个connect()函数,连接这两个不同类的成员函数。

  • 范例:
    MyWidget是一个自定义界面类,继承于QWidge。我在其中定义了一个MyPushButton 类和一个MyTextEdit类。
class MyPushButton;
class MyTextEdit;
class MyWidget: public QWidge
{
    Q_OBJECT
	explicit MyWidget(QWidge *parent = nullptr){
		m_btn = new MyPushButton();
		m_text = new MyTextEdit();
		//前提:是QObject的子类,上一篇blog已经说过原因。
		//connec函数连接信号函数和槽函数
		connect(m_btn,&MyPushButton::sendBtnNameSignal,
			m_text,&MyTextEdit::SetBtnNameSlot,Qt::UniqueConnection);
	}
private :
	MyPushButton *m_btn = nullptr;
	MyTextEdit *m_text = nullptr;
};

通过设置连接函数,两个不同对象中的成员函数得以进行消息传递。

🌸 QObejct::connect函数剖析

✨函数原型:

[static] QMetaObject::Connection QObject::connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type = Qt::AutoConnection)

通过传入指向发送者对象的指针和该对象的信号函数的地址以及指向接收者对象的指针和该对象的槽函数地址。

  • 通常,可以使用SIGNAL宏和SLOT宏将信号、槽函数包起来,这种写法要求至少写出信号函数和槽函数的传参类型。
  • 一个信号可以连接多个槽函数,同样,一个槽函数可以连接多个信号函数。
  • connect函数本身是线程安全的,但考虑到可能存在复杂的多线程环境,应当谨慎处理对象生存周期、跨线程连接和多线程并发访问等问题。
  • 关于第五个参数Qt::ConnectionType,缺省情况下会使用Qt::AutoConnection.这个参数决定了接收到信号后是立即执行槽函数,还是排队执行槽函数。
ConnectionType				  Value 			Description
Qt::AutoConnection 				0				(默认值)如果接收器存放在发出信号的线程中,则使用QT :: DirectConnection。否则,使用QT :: QueuedConnection。发射信号时确定连接类型。
Qt::DirectConnection			1				槽函数会在信号发出被响应时立即执行,并且,槽函数会被放在信号线程中执行。
Qt::QueuedConnection			2				当信号发射时,槽函数的调用请求会被放入接收对象所在线程的事件队列中,等待事件循环处理。适用于跨线程通信。
Qt::BlockingQueuedConnection	3				与qt :: QueuedConnection相同,只是信号函数会阻塞直到槽函数返回。如果接收者对象和发送者对象在同一个线程中,则不得使用此连接,否则应用程序将死锁。
Qt::UniqueConnection			0x80			用于确保信号与槽之间的连接是唯一的。如果已经存在相同的信号与槽连接,再次使用 Qt::UniqueConnection 连接时,连接操作将会失败,从而避免建立重复的连接
  • 如果在消息传递时使用了自定义的数据类型,需要先将该类型注册到元对象系统中,否则connect会失败。
//注册QVector<AgendaInfo>到元类型中
qRegisterMetaType<QVector<AgendaInfo>>("QVector<AgendaInfo>");

✨函数原型:

[static] QMetaObject::Connection QObject::connect(const QObject *sender, PointerToMemberFunction signal, const QObject *context, Functor functor, Qt::ConnectionType type = Qt::AutoConnection)
  • 这个函数原型中,支持将信号发送给一个QObejct的类的成员函数,并且在连接时无需列出函数的传参类型,Qt会为你去做检查的工作。
  • 因此,这个函数原型可以支持将匿名函数(lambda)作为连接的槽函数。
 QObject::connect(socket, &QTcpSocket::connected, this, [=] () {
          socket->write("GET " + page + "\r\n");
      }, Qt::AutoConnection);
  • Note: Qt::UniqueConnections do not work for lambdas, non-member functions and functors; they only apply to connecting to member functions.[译文]:Qt::UniqueConnections 这种连接方式不支持用于连接槽函数为匿名函数、非成员函数,connect函数会报错。

🌟 官方文档中给出的定义

Signals and slots are used for communication between objects. The signals and slots mechanism is a central feature of Qt and probably the part that differs most from the features provided by other frameworks. Signals and slots are made possible by Qt's meta-object system. [译文]:信号和插槽用于对象之间的通信。信号和插槽机制是QT的主要特征,可能是与其他框架提供的功能不同的部分。信号和插槽通过QT的元对象系统使其成为可能。

🌟《Qt 5.9 C++开发指南》中的定义

Qt 使用信号与槽的机制实现对象间通信,它隐藏了复杂的底层实现,完成信号与槽的关联后,发射信号时并不需要知道Qt是如何找到槽函数的。Qt信号与槽机制与 Delphi 和 C++ Builder 的“事件一一响应” 较类似,但是更加灵活。
某些开发架构使用回调函数(callback)实现对象间通信。与回调函数相比,信号与槽的执行速度稍微慢 ,因为需要查找连接的对象和槽函数 ,但是这种区别在应用程序运行时是感觉不到的,而其提供的灵活性却比回调函数强很多。

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1666506.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

JVM 类加载机制

JVM 类加载机制分为五个部分&#xff1a;加载&#xff0c;验证&#xff0c;准备&#xff0c;解析&#xff0c;初始化&#xff0c;下面我们就分别来看一下这五个过程。 加载 加载是类加载过程中的一个阶段&#xff0c;这个阶段会在内存中生成一个代表这个类的 java.lang.class 对…

用户管理中心——登录功能

用户管理中心——登录功能 一、用户登录1. 登录设计2. 登录方法实现实现细节逻辑删除实现代码 3. 登录接口实现4. 测试 二、用户管理用户管理接口 一、用户登录 1. 登录设计 2. 登录方法实现 实现细节 首先在接口中com.example.demo.service.UserService定义一个用户登录doL…

HSB色彩模式计算详解

HSB色彩模式计算详解 前些天撰文几篇介绍了几种圆形和矩形的HSB绘制方法。后2篇介绍了HSB的计算方法。我感到不是很详细&#xff0c;今再补充说明计算方法。 圆形H调色板选色,计算 Rad, ang, L&#xff0c; return H 计算二点距离 L&#xff0c;取色点到圆心距离 x0250;…

https://是怎么实现的?

默认的网站建设好后都是http访问模式&#xff0c;这种模式对于纯内容类型的网站来说&#xff0c;没有什么问题&#xff0c;但如果受到中间网络劫持会让网站轻易的跳转钓鱼网站&#xff0c;为避免这种情况下发生&#xff0c;所以传统的网站改为https协议&#xff0c;这种协议自己…

【牛客】SQL201 查找薪水记录超过15条的员工号emp_no以及其对应的记录次数t

1、描述 有一个薪水表&#xff0c;salaries简况如下&#xff1a; 请你查找薪水记录超过15条的员工号emp_no以及其对应的记录次数t&#xff0c;以上例子输出如下&#xff1a; 2、题目建表 drop table if exists salaries ; CREATE TABLE salaries ( emp_no int(11) NOT N…

【深入理解MySQL的索引数据结构】

文章目录 &#x1f50a;博主介绍&#x1f964;本文内容&#x1f4d5;索引底层数据结构与算法&#x1f4d9;索引数据结构&#x1f4d8;二叉树&#x1f4d8;红黑树&#x1f4d8;Hash&#x1f4d8;B-Tree&#x1f4d8;BTree &#x1f4d9;表在不同存储引擎的存储结构&#x1f4d8;…

react18【系列实用教程】useContext —— Context 机制实现越层组件传值 (2024最新版)

什么是 Context 机制&#xff1f; Context 机制是 react 实现外层组件向内层组件传值的一种方案&#xff0c;父组件可以向其内部的任一组件传值&#xff0c;无论是子组件还是孙组件或更深层次的组件。 实现步骤 1.使用createContext方法创建一个上下文对象 Ctx 2.在顶层组件中通…

基恩士PLC-KV5500基础入门

一、准备工作&#xff1a; 1.准备的东西&#xff1a;一个基恩士PLC-KV5500模块。两个自复位开关&#xff0c;24v LED灯一个&#xff0c;24v开关电源一个&#xff0c;KV5500端子台IO线缆&#xff1b;有编程软件的电脑一台。 编程软件&#xff1a; 基恩士PLC-KV5500接线图&…

妙笔生花,创作无限——WonderPen妙笔 for Mac

写作&#xff0c;是灵感的流淌&#xff0c;是心灵的独白。WonderPen妙笔 for Mac&#xff0c;为您的灵感插上翅膀&#xff0c;让您的创作更加流畅自如。它拥有简洁直观的界面设计&#xff0c;让您的思绪在纯净的写作环境中自由飞翔。多种写作模式&#xff0c;满足您不同的创作需…

vue2基础语法02——计算属性、方法、侦听器

vue2基础语法02——计算属性、方法、侦听器 1. 计算属性 computed1.1 为什么要用计算属性1.2 简单例子1.2.1 例子1.2.2 计算属性缓存 1.3 计算属性的 setter 2. 方法 methods2.1 例子2.2 说明2.3 简单方法替换实现 3. 侦听属性 watch3.1 介绍3.2 值的情况3.2.1 对应回调函数3.2…

halcon学习之一维测量基础

目录 创建测量矩形&#xff0c;获取测量句柄 gen_measure_rectangle2&#xff08;&#xff09; 使用句柄进行测量 measure_pos&#xff08;&#xff09; 修改参数Threshold 修改参数Transition 修改参数select 参数RowEdge&#xff0c;ColumnEdge&#xff0c;Distance …

KAN网络

目录 背景知识 什么是神经网络&#xff1f; 神经网络发展史 MP神经元模型 感知机模型 KAN 引言 MLP架构vsKAN架构 从数学定理方面来看&#xff1a; 从算法层面上看&#xff1a; 从实际应用过程看&#xff1a; KAN的架构细节 KAN的准确性 KAN的可解释性 监督学习…

验证搜索二叉树

目录 题目 方法一 思路 优化 方法二 思维误区 递归关系推导 代码实现 题目 98. 验证二叉搜索树 难度&#xff1a;中等 给你一个二叉树的根节点root &#xff0c;判断其是否是一个有效的二叉搜索树。 有效 二叉搜索树定义如下&#xff1a; 节点的左子树只包含…

虚幻五关卡制作学习笔记

1.创建一个移动平台 这个移动平台的功能&#xff1a;从箭头1移动到箭头2来回移动&#xff0c;可移动时发绿光&#xff0c;不可移动时发红光 首先&#xff0c;创建两个材质&#xff0c;发红光和绿光 然后我们创建一个actor蓝图类&#xff0c;添加两个arrow组件&#xff0c;两个…

设计模式-结构型-适配器模式-Adapter

地址类 public class Address {public void street() {System.out.println("普通的街道");}public void zip() {System.out.println("普通的邮政编码");}public void city() {System.out.println("普通的城市");} } 荷兰地址类 public class …

计算机服务器中了locked勒索病毒怎么解决,locked勒索病毒解密恢复工具

在网络技术飞速发展的时代&#xff0c;通过网络开展各项工作业务成为众多企业的首选&#xff0c;网络也为企业的生产运营提供了极大便利&#xff0c;大大提升了企业办公效率&#xff0c;但是利用网络避免不了网络威胁的存在&#xff0c;数据安全问题一直是企业关心的主要话题。…

【效率开发】游戏开发Debug效率方法总结

"程序员的一半生命都浪费在了调试上。" ——Brian Kernighan&#xff08;计算机科学家&#xff0c;曾参与开发C语言&#xff09; &#xff08;图片来源&#xff1a;forbesindia&#xff09; Debug无疑是程序员最头疼&#xff0c;也是耗费时间最多的一个环节&#xf…

智慧停车场管理系统主要组成

智慧泊车场办理体系&#xff0c;完成了泊车办理过程中的车辆类型分类、出场时的车牌辨认、行进路线的引导、空余车位诱导&#xff0c;以及准备离场前的反向寻车和方便缴费等全部环节。这六个流程中&#xff0c;泊车场对车辆的办理&#xff0c;进步了泊车场的运行效率&#xff0…

如何远程访问?

远程访问是指在不同的地理位置之间通过网络连接来实现对目标设备或系统的访问。无论是在个人生活还是商业领域&#xff0c;远程访问都起到了重要的作用&#xff0c;帮助人们实现高效的工作和便捷的生活。本文将介绍一款名为【天联】的组网产品&#xff0c;它是一款强大的异地组…

祝天下母亲节快乐!虚无!——早读(逆天打工人爬取热门微信文章解读)

练功加精力哦 引言Python 代码第一篇 人民日报【夜读】人与人之间最好的关系&#xff1a;遇事靠谱&#xff0c;懂得感恩第二篇 冯站长之家 三分钟新闻早餐结尾 感恩与善行 是人生旅途中的灯塔 怀感恩之心 行小善之事 它们将指引我们走向光明 引言 今天是母亲节 祝天下的所有母…