【QT】信号和槽

img

一、前置示例代码

  1. main.cpp
#include "widget.h"#include <QApplication>int main(int argc, char *argv[])
{QApplication a(argc, argv);		// 应用程序对象a,在Qt中,应用程序对象,有且仅有一个。Widget w;						// 窗口对象w, Widget父类-》 QWidgetw.show();						// 窗口对象w, 默认不会显示,必须调用show方法显示窗口。return a.exec();				// 让应用程序对象a,进入消息循环--》  while(1);
}

  1. widget.h
#ifndef WIDGET_H
#define WIDGET_H#include <QWidget>class Widget : public QWidget
{Q_OBJECTpublic:Widget(QWidget *parent = nullptr);~Widget();signals:void isSignal(int signal = 0);
public slots:void isSlot(int slot);};
#endif // WIDGET_H

  1. widget.cpp
#include "widget.h"
#include <QDebug>Widget::Widget(QWidget *parent) : QWidget(parent)
{// 信号和槽的绑定:connect(this, &Widget::isSignal, this, &Widget::isSlot);// 发送信号:emit isSignal(1);
}Widget::~Widget()
{
}// 槽函数的实现:
void Widget::isSlot(int slot){QString qString;qDebug()<< "我是槽函数,我收到的信号是:" << qString.number(slot);
}

程序输出:

我是槽函数,我收到的信号是: "1"

可以看出,当信号发送后,信号函数的signal 的参数值 “ 1” ,已经成功传递给 槽函数的 接收变量 slot, slot = 1。




二、信号槽如何传递参数

  1. 信号和槽函数的参数,类型必须进行一一对应,如信号的参数为int,槽函数的参数也为int。

信号:

signals:void isSignal(int signal = 0);

槽的定义:

public slots:void isSlot(int slot);

槽的实现:

void Widget::isSlot(int slot){QString qString;qDebug()<< "我是槽函数,我收到的信号是:" << qString.number(slot);
}

发送信号:

emit isSignal(1);

程序输出:

我是槽函数,我收到的信号是: "1"

可以看出,当信号发送后,信号函数的signal 的参数值 “ 1” ,已经成功传递给 槽函数的 接收变量 slot, slot = 1。



  1. 当信号的参数与槽函数的参数数量不同时,只能是信号的参数数量,多于槽函数的参数数量。且前面相同数量的参数类型应一致,信号中多余的参数会被忽略。

信号:

signals:void isSignal(int signal = 0, QString s = "我是信号");

槽的定义:

public slots:void isSlot(int slot);

槽的实现:

void Widget::isSlot(int slot){QString qString;qDebug()<< "我是槽函数,我收到的信号是:" << qString.number(slot);
}

发送信号:

emit isSignal(2, "你好");

程序输出:

我是槽函数,我收到的信号是: "2"

可以看出,当信号发送后,信号函数的signal 的参数值 “ 2” ,被成功传递给 槽函数的 接收变量 slot, slot = 2。而 s = “你好” 被忽略。




三、信号和槽发生重载

  1. teacher.h
signals:void hungry();void hungry(QString foodName);

  1. student.h && student.cpp
public slots:void treat();void treat(QString foodName);void Student::treat(){qDebug()<<"请老师吃饭";
}void Student::treat(QString foodName){qDebug()<<"请老师吃饭,吃:" << foodName.toUtf8().data();
}

  1. widget.h
#include "teacher.h"
#include "student.h"class Widget : public QWidget
{
public:Teacher * ls;Student * st;
};

  1. widget.cpp
#include "widget.h"
#include <QPushButton>
#include <QDebug>//Teacher类 老师类
//student类 学生类
//下课后,老师会触发一个信号,饿了,学生响应信号,请客吃饭Widget::Widget(QWidget *parent) : QWidget(parent)
{//创建一个老师对象this->ls = new Teacher(this);//创建一个学生对象this->st = new Student(this);//连接带参数的信号和槽--1void (Teacher:: * teacherSignal_void)() = &Teacher::hungry;void (Student:: * studentSlot_void)() = &Student::treat;connect(ls,teacherSignal_void,st,studentSlot_void);emit ls->hungry();qDebug()<<"---------------";//连接带参数的信号和槽--2void (Teacher:: * teacherSignal)(QString) = &Teacher::hungry;void (Student:: * studentSlot)(QString) = &Student::treat;connect(ls,teacherSignal,st,studentSlot);emit ls->hungry("宫爆鸡丁");
}Widget::~Widget()
{
}

程序输出:

请老师吃饭
---------------
请老师吃饭,吃: 宫爆鸡丁

此外,我们可以通过setParent函数为 QObject 对象设置一个父对象

//创建一个老师对象
this->ls = new Teacher(this);
//创建一个学生对象
this->st = new Student(this);

当父对象被析构时,它会自动析构其所有的子对象。这意味着无需手动管理子对象的销毁,减轻了开发人员的负担,并确保在不再需要这些子对象时,它们会被正确地释放。




四、信号与槽的参数不对应–使用Lambda表达式

widget.cpp

#include "widget.h"
#include "ui_widget.h"
#include <QPushButton>
#include <QDebug>//Teacher类 老师类
//student类 学生类
//下课后,老师会触发一个信号,饿了,学生响应信号,请客吃饭Widget::Widget(QWidget *parent) :QWidget(parent),ui(new Ui::Widget)
{ui->setupUi(this);//创建一个老师对象this->zt = new Teacher(this);//创建一个学生对象this->st = new Student(this);//点击一个按钮,再进行下课QPushButton * btn = new QPushButton("下课",this);setFixedSize(600,400);//连接带参数的信号和槽//指针->地址,函数指针->函数地址void (Teacher::*teacherSignal)(QString) = &Teacher::hungry;void (Student::*studentSlot)(QString) = &Student::treat;connect(zt,teacherSignal,st,studentSlot);//信号连接信号 一个信号触发另一个信号//-----------------------------------------------------connect(btn,&QPushButton::clicked,zt,teacherSignal);//-----------------------------------------------------
}Widget::~Widget()
{delete ui;
}

程序报错:

static assertion failed: Signal and slot arguments are not compatible

clicked信号的原型为:

void clicked(bool checked = false)

hungry槽的原型为:

 void hungry(QString foodName);

原因为信号的参数与槽函数参数不对应。 bool型 和 QString 的类型不同。



正确写法:

connect(btn,&QPushButton::clicked,zt,teacherSignal);

改为:

connect(btn,&QPushButton::clicked,ls, [this](){emit ls->hungry("宫爆鸡丁");
});

程序输出:

请老师吃饭,吃: 宫爆鸡丁请老师吃饭,吃: 宫爆鸡丁请老师吃饭,吃: 宫爆鸡丁请老师吃饭,吃: 宫爆鸡丁




参考连接:

《Qt5:信号和槽使用示例》

qt报错:static assertion failed: Signal and slot arguments are not compatible

信号槽如何传递参数(或带参数的信号槽)

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Centos8 降低gcc版本至gcc-7.3

1 首先卸载系统中的gcc sudo yum remove gcc 2 重新安装gcc-7.3 sudo dnf group install “Development Tools” 然后再次卸载gcc sudo yum remove gcc 然后发现centos-release-scl-rh已经安装了 sudo yum install centos-release-scl-rh yum -y install devtoolset-7-gcc dev…

docker、docker-compose安装教程,很详细

docker、docker-compose安装教程&#xff0c;很详细 一、卸载旧版1、查看有没有安装过旧版2、停止docker3、删除安装过docker的相关包4、删除docker相关的镜像和容器 二、docker安装1、设置阿里云镜像2、查看所有docker3、安装最新版本4、安装指定版本 三、使用前准备1、启动do…

苍穹外卖-01

苍穹外卖-01 课程内容 软件开发整体介绍苍穹外卖项目介绍开发环境搭建导入接口文档Swagger 项目整体效果展示&#xff1a; ​ 管理端-外卖商家使用 ​ 用户端-点餐用户使用 当我们完成该项目的学习&#xff0c;可以培养以下能力&#xff1a; 1. 软件开发整体介绍 作为一名…

关于nacos的配置获取失败及服务发现问题的排坑记录

nacos配置更新未能获取到导致启动报错 排查思路&#xff1a; 1、是否添加了nacos的启动pom依赖 参考&#xff1a; <dependency><groupId>com.alibaba.cloud</groupId><artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId><…

openEuler 22.03 LTS 安装 Docker CE 和 Dcoker Compose

openEuler 使用 DNF 安装 Docker CE 1024&#xff0c;节日快乐&#xff01;回归正题&#xff0c;DNF 安装 DockerOS 系统环境准备安装 docker-ce 步骤1、更新系统2、安装必要的软件包3、添加 Docker CE 存储库4、更新索引缓存并安装 Docker CE5、启动 Docker 服务6、查看 Docke…

数据挖掘和大数据的区别

数据挖掘 一般用于对企业内部系统的数据库进行筛选、整合和分析。 操作对象是数据仓库&#xff0c;数据相对有规律&#xff0c;数据量较少。 大数据 一般指对互联网中杂乱无章的数据进行筛选、整合和分析。 操作对象一般是互联网的数据&#xff0c;数据无规律&#xff0c;…

【ELK】日志系统部署

一、ELK日志分析系统 1、ELK的组成 ElasticSearchLogStashKibana ELK基于这三个开源日志的收集、存储、检索和可视化的解决方案&#xff1b;可帮助用户快速定位和分析应用程序的故障&#xff0c;监控应用程序性能和安全&#xff0c;以及提供丰富的数据分析和展示功能。 2、完…

C++(Chapter 3)

C(三) 1.引用 1.引用的概念 引用的概念:引用不是新定义一个变量&#xff0c;而是给已存在变量取了一个别名&#xff0c;编译器不会为引用变量开辟内存空间&#xff0c;它和它引用的变量共用同一块内存空间。 引用的语法:类型& 引用变量名(对象名) 引用实体 ; 例如: #i…

MySQL---表的增查改删(CRUD基础)

文章目录 什么是CRUD&#xff1f;新增&#xff08;Create&#xff09;单行数据 全列插入多行数据 指定列插入 查询&#xff08;Retrieve&#xff09;全列查询指定列查询查询字段为表达式起别名查询去重查询排序查询条件查询分页查询 修改&#xff08;Update&#xff09;删除&…

【QT】其他常用控件1

新建项目 scrollArea 滚动 toolBox 插入 tabWidget stackedWidget 切换 索引是0 运行后&#xff0c;没有切换按钮&#xff0c;结合pushbutton&#xff0c;加两个Button 代码 #include "widget.h" #include "ui_widget.h"Widget::Widget(QWidget *parent)…

Centos8: 安装python2, 并设置默认版本

文章目录 原本centos上已经有python3.6了&#xff0c;因为要运行旧代码&#xff0c;需要安装python2版本。 #在CentOS 8上安装Python 2 sudo dnf install python2#设置默认Python版本 python2 sudo alternatives --set python /usr/bin/python2#设置默认Python版本 python3 sud…

DevOps持续集成-Jenkins(4)

❤️作者简介&#xff1a;2022新星计划第三季云原生与云计算赛道Top5&#x1f3c5;、华为云享专家&#x1f3c5;、云原生领域潜力新星&#x1f3c5; &#x1f49b;博客首页&#xff1a;C站个人主页&#x1f31e; &#x1f497;作者目的&#xff1a;如有错误请指正&#xff0c;将…

【刷题-PTA】堆栈模拟队列(代码+动态图解)

【刷题-PTA】堆栈模拟队列(代码动态图解) 文章目录 【刷题-PTA】堆栈模拟队列(代码动态图解)题目输入格式:输出格式:输入样例:输出样例: 分析题目区分两栈解题思路伪代码动图演示代码测试 题目 题目描述 : 设已知有两个堆栈S1和S2&#xff0c;请用这两个堆栈模拟出一个队列Q。 …

css-渐变色矩形

效果图&#xff1a; 代码&#xff1a; html: <!DOCTYPE html> <html><head><meta charset"utf-8"><meta name"viewport" content"initial-scale1.0, user-scalableno" /><title></title><link …

ES6初步了解生成器

生成器函数是ES6提供的一种异步编程解决方案&#xff0c;语法行为与传统函数完全不同 语法&#xff1a; function * fun(){ } function * gen(){console.log("hello generator");}let iterator gen()console.log(iterator)打印&#xff1a; 我们发现没有打印”hello…

Leetcode-Easy题解1-回文数字

目录 解法1解法2 解法1 自己的想法,直接转成字符串首尾俩下标同时遍历比较 class Solution {public boolean isPalindrome(int x) {if(x<0){return false;}String strString.valueOf(x);int i0;for (;i<str.length()>>1;i){if(str.charAt(i)!str.charAt(str.leng…

DAY33 1005. K次取反后最大化的数组和 + 134. 加油站 + 135. 分发糖果

1005. K次取反后最大化的数组和 题目要求&#xff1a;给定一个整数数组 A&#xff0c;我们只能用以下方法修改该数组&#xff1a;我们选择某个索引 i 并将 A[i] 替换为 -A[i]&#xff0c;然后总共重复这个过程 K 次。&#xff08;我们可以多次选择同一个索引 i。&#xff09; …

Godot 官方2D C#重构(3):TileMap使用

文章目录 前言Godot Tilemap使用Tilemap使用TileSet和TilemapTilemap 图片资源添加TileSet&#xff0c;开始切图导入图片切图 简单添加TileMap如何使用 Auto Tilemap使用Auto Tilemap 前言 Godot 官方 教程 Godot 2d 官方案例C#重构 专栏 Godot 2d 重构 github地址 Godot Tilem…

互联网Java工程师面试题·Spring篇·第三弹

目录 ​编辑 4、注解 4.1、什么是基于注解的容器配置 4.2、如何在 spring 中启动注解装配&#xff1f; 4.3、Component, Controller, Repository,Service 有何区别&#xff1f; 4.4、Required 注解有什么用&#xff1f; 4.5、Autowired 注解有什么用&#xff1f; 4.6、…

当前JavaEE初阶的阶段知识总结

当前JavaEE初阶的阶段知识总结 多线程 文件IO 文件系统操作 ~~ File类. 文件内容操作 ~~ 读文件,写文件. IO 流对象. 流(Stream),形象的比喻,读取文件,就像水流一样,读写文件的时候,和水流类似,读100字节,可以一次读1个字节,100次完成;也可以一次读10个字节,10次完成…… 在…