(7)Qt中的自定义槽(函数)

news2025/7/19 11:35:52

目录

槽函数定义的规则

关联信号与槽错误的示例

类成员函数函数做槽函数使用

静态类成员函数做槽函数使用

全局函数做槽函数使用

lambda表达式做槽函数使用

使用lambda表达式的注意事项

 注意事项一:

注意事项二:


槽函数定义的规则

1.槽函数返回值类型为void

2.槽函数的参数不能多于信号的参数(只能小于等于信号的参数个数)

关联信号与槽错误的示例

 按钮被点击触发一个点击信号,从而导致死循环,之后会导致程序中断。

m_btn = new QPushButton("Button", this);
//错误的示例
connect(m_btn, &QPushButton::clicked, m_btn, &QPushButton::click);

类成员函数函数做槽函数使用

类中做槽函数的成员函数一般写在public slots下,Qt5以及以上版本可以不写public slots。

#include <QApplication>
#include <QWidget>
#include <QDebug>
#include <QPushButton>
#include <QMessageBox>

//去掉控制台
#pragma comment(linker,"/subsystem:windows /entry:mainCRTStartup")

class Widget : public QWidget
{
	Q_OBJECT							// 使用信号与槽机制必须包含此宏
public:
	Widget(QWidget* parent = nullptr)
		:QWidget(parent)
	{
		setWindowTitle("自定义槽");		// 设置窗口标题
		resize(640, 480);				// 设置窗口大小

		m_btn = new QPushButton("成员函数", this);
		//使用信号与槽关联类成员函数
		connect(m_btn, &QPushButton::pressed, this, &Widget::onPressSlot);	
	}
	~Widget()
	{
	}
public slots:
	void onPressSlot()
	{
		QMessageBox::information(this, "提示", 
			"类成员函数作为槽函数使用", QMessageBox::Ok);
	}
private:
	QPushButton* m_btn = nullptr;
};

int main(int argc, char* argv[]) {

	QApplication a(argc, argv);
	Widget w;
	w.show();

	return a.exec();
}
#include "main.moc"

 

静态类成员函数做槽函数使用

class Widget : public QWidget
{
	Q_OBJECT							// 使用信号与槽机制必须包含此宏
public:
	Widget(QWidget* parent = nullptr)
		:QWidget(parent)
	{
		setWindowTitle("自定义槽");		// 设置窗口标题
		resize(640, 480);				// 设置窗口大小

		m_btn = new QPushButton("成员函数", this);
		//使用信号与槽关联静态类成员函数
		connect(m_btn, &QPushButton::pressed, this, &Widget::onPressSlot1);
		
	}
	~Widget()
	{

	}
public slots:
	static void onPressSlot1()
	{
		QMessageBox::information(nullptr, "提示",
			"静态类成员函数作为槽函数使用", QMessageBox::Ok);
	}
private:
	QPushButton* m_btn = nullptr;
};

 

全局函数做槽函数使用

void globalSlot()
{
	QMessageBox::information(nullptr, "提示",
		"全局函数作为槽函数使用", QMessageBox::Ok);
}

class Widget : public QWidget
{
	Q_OBJECT							// 使用信号与槽机制必须包含此宏
public:
	Widget(QWidget* parent = nullptr)
		:QWidget(parent)
	{
		setWindowTitle("自定义槽");		// 设置窗口标题
		resize(640, 480);				// 设置窗口大小

		m_btn = new QPushButton("全局函数", this);
		//使用信号与槽关联全局函数
		connect(m_btn, &QPushButton::pressed, this, globalSlot);
		
	}
	~Widget()
	{

	}
public slots:
private:
	QPushButton* m_btn = nullptr;
};

 

lambda表达式做槽函数使用

class Widget : public QWidget
{
	Q_OBJECT							// 使用信号与槽机制必须包含此宏
public:
	Widget(QWidget* parent = nullptr)
		:QWidget(parent)
	{
		setWindowTitle("自定义槽");		// 设置窗口标题
		resize(640, 480);				// 设置窗口大小

		m_btn = new QPushButton("lambda", this);
		//lambda表达式做槽函数使用
		connect(m_btn, &QPushButton::pressed, this, []() {
			QMessageBox::information(nullptr, "提示",
				"lambda表达式作为槽函数使用", QMessageBox::Ok);
		});
	}
	~Widget()
	{

	}
public slots:
private:
	QPushButton* m_btn = nullptr;
};

使用lambda表达式的注意事项

这样使用是没有问题的,但是如果想让cnt的值每点击一次就++,就需要使用引用捕获的方式。

m_btn = new QPushButton("Button", this);
int cnt = 0;
connect(m_btn, &QPushButton::pressed, m_btn, [=]() {
	m_btn->setText(QString::number(cnt));
});

 注意事项一:

使用引用捕获的方式捕获cnt会导致错误,因为cnt是一个栈区变量,构造函数结束内存会被销毁。

m_btn = new QPushButton("Button", this);
int cnt = 0;
connect(m_btn, &QPushButton::pressed, m_btn, [=,&cnt]() {
	m_btn->setText(QString::number(cnt++));
});

使用mutable的方式解决上述问题

m_btn = new QPushButton("Button", this);
int cnt = 0;
connect(m_btn, &QPushButton::pressed, m_btn, [=]() mutable{
	m_btn->setText(QString::number(cnt++));
});

使用静态变量解决上述问题

m_btn = new QPushButton("Button", this);
static int cnt = 0;
connect(m_btn, &QPushButton::pressed, m_btn, [=](){
	m_btn->setText(QString::number(cnt++));
});

注意事项二:

 当m_btn是类成员变量时,使用引用捕获的方式捕获是没有错误的。

m_btn = new QPushButton("Button", this);
static int cnt = 0;
connect(m_btn, &QPushButton::pressed, m_btn, [&](){
	m_btn->setText(QString::number(cnt++));
});

当m_btn是局部变量的时候,使用引用捕获的方式会直接导致程序中断。因为此时的m_btn为栈区内存,构造函数结束之后内存被释放。因此,尽量避免使用引用捕获的方式去捕获。

auto m_btn = new QPushButton("Button", this);
static int cnt = 0;
connect(m_btn, &QPushButton::pressed, m_btn, [&](){
	m_btn->setText(QString::number(cnt++));
});

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

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

相关文章

多图解析KMP算法原理

KMP是什么 KMP是一种字符串匹配算法&#xff0c;能够判断字符串s2&#xff0c;是否为字符串s1的子串 例如&#xff1a;s1 "abd123def"&#xff0c;s2 "123"&#xff0c;KMP会返回4&#xff0c;代表s2是s1的子串&#xff0c;第一个匹配的下标为3 假设s…

线程池及源码分析

目录 1 java构建线程的方式 2 线程池的7个参数 3 线程池属性标识&线程池的状态 3.1 核心属性 3.2 线程池的状态 4 线程池的执行流程 5 添加工作线程的流程 6 Worker的封装&后续任务的处理 1 java构建线程的方式 一般就3~4种&#xff1a; 继承Thread&#xff…

迎接新年,暂且用Python绘制几个中国结吧

前言 今天就来分享几个用python绘制的图案吧 马上就要迎来新年了 就绘制了几个中国结&#xff0c;嘿嘿 话不多说&#xff0c;直接展示一下代码和效果图吧 更多学习资料与源码点击文章末尾名片领取 1. 效果图&#xff1a; 代码展示 import turtle turtle.screensize(600,…

GPDB插件安装工具之gppkg

gppkg命令gppkg是一个python3编写的打包脚本&#xff0c;在整个集群中安装.gppkg格式的Greenplum数据库扩展&#xff08;例如PL/Java、PL/R和MADlib&#xff09;及其依赖项&#xff0c;位于/usr/local/cloudberry-db/bin/gppkg(自己安装的gpdb目录)&#xff0c;安装到$GPHOME里…

1个寒假能学多少网络安全知识?

现在可以看到很多标题都声称三个月内就可以转行网络安全领域&#xff0c;并且成为月入15K的网络工程师。那么&#xff0c;这个寒假的时间能学多少网络安全知识&#xff1f;是否能入门网络安全工程师呢&#xff1f; 答案是肯定的。 虽然网络完全知识是一门广泛的学科&#xff…

ccc-sklearn-13-朴素贝叶斯(1)

朴素贝叶斯 一种直接衡量标签和特征之间概率关系的有监督学习算法&#xff0c;专注分类的算法&#xff0c;基于概率论和数理统计的贝叶斯理论。在计算的过程中&#xff0c;假设特征之间条件独立&#xff0c;不进行建模&#xff0c;采用后验估计。 sklearn中的朴素贝叶斯 类含…

1-选择题练手

1.采用递归方式对顺序表进行快速排序&#xff0c;下列关于递归次数的叙述中&#xff0c;正确的是 A.每次划分后&#xff0c;先处理较长的分区可以减少递归次数 B.递归次数与初始数据的排列次序无关 C.每次划分后&#xff0c;先处理较短的分区可以减少递归次数 D.递归次数与…

DaVinci:键 - 外部蒙版

调色页面&#xff1a;键Color&#xff1a;Key在调色页面&#xff0c;可以轻松地从媒体池将某个片段拖至节点面板中&#xff0c;以作为外部蒙版。或者&#xff0c;在节点上右击选择“添加蒙版” Add Matte。若无附加&#xff0c;则可以选择本节点片段的明度信息作为外部蒙版。当…

hbase2.x orphan regions on filesystem(region丢失)问题修复

问题描述&#xff1a;orphan regions on filesystem 可以通过主master web页面的HBCK Report查看 也可以通过hbck2工具查看 # 查看指定表 hbase hbck -j $HBASE_HOME/lib/hbase-hbck2-1.3.0-SNAPSHOT.jar addFsRegionsMissingInMeta default:tableName # 查看命名空间下所有…

Yolov5+TensorRT-生成dll-python/c++调用dll

YOlov5-6.0TensorRTdllpython/c调用简介1.项目环境2.TensorRT验证1.在tensorrtx-yolov5-v6.0\yolov5目录下新建build目录2.编写CMake.txt,根据自己目录更改2&#xff08;OpenCV_DIR&#xff09;、3&#xff08;TRT_DIR&#xff09;、10&#xff08;Dirent_INCLUDE_DIRS&#xf…

LabVIEW网络服务器何使用,有哪些不同

LabVIEW网络服务器何使用&#xff0c;有哪些不同NI有几款不同的Web服务器&#xff0c;可使用不同的产品并覆盖不同的用例。它们具有非常相似的名称&#xff0c;可以互换使用&#xff0c;但每个都提供不同的功能。应用程序Web服务器描述&#xff1a;NI应用Web服务器加载使用LabV…

企业微信商户号是什么?如何开通?

企业微信作为一款优秀的移动办公工具&#xff0c;与微信全方位打通&#xff0c;既可以与客户沟通交流&#xff0c;也可以在达成交易后直接进行对公收款&#xff0c;但是前提是要开通企业微信商户号。前言企业微信和微信都出自腾讯&#xff0c;而且企业微信全方位连接微信&#…

C#,图像二值化(16)——全局阈值的力矩保持算法(Moment-proserving Thresholding)及其源代码

1、力矩保持法 提出了一种基于矩保持原理的自动阈值选择方法。以这样的方式确定地计算阈值&#xff0c;即在输出画面中保留输入画面的时刻。实验结果表明&#xff0c;该方法可以将给定的图像阈值化为有意义的灰度级。该方法描述了全局阈值&#xff0c;但也适用于局部阈值。 A…

企业微信开发——企业内部自建应用开发(第二篇)---JS_SDK配置

企业微信如果想要使用企业微信的JS_SDK来实现拍照、定位等等功能&#xff0c;就需要预先在使用到的页面进行配置&#xff0c;当然你可以做全局配置。对于JS_SDK的配置设计前端和后端的统一配置。下面我来说明下具体的步骤。特别说明&#xff1a;1、企业微信有的接口需要配置wx.…

shader基础入门(1)

本文基于unity免费公开课“Hi Shader以及网络公开资料等书写”遵循开源协议。 MeshFilter网格过滤器 从海量资源中挑选适合的Mesh将他交给MeshRender MeshRenderer 网格渲染器 负责把MeshFilter丢过来的Mesh&#xff0c;绘制显示到我们的场景中 Material 材质球 Material…

多线程之死锁

目录&#xff1a; 1.什么是死锁&#xff1f; 2.可重入与不可重入 3.发生死锁的三个典型情况 4.发生死锁的四个必要条件 5.如何破除死锁&#xff1f; 1.什么是死锁&#xff1f; 谈到死锁&#xff0c;程序猿们都心存忌惮&#xff0c;因为程序一旦出现死锁&#xff0c;就会导…

深度学习训练营之鸟类识别

深度学习训练营之鸟类识别原文链接环境介绍前置工作设置GPU导入数据并进行查找数据处理可视化数据配置数据集残差网络的介绍构建残差网络模型训练开始编译结果可视化训练样本和测试样本预测原文链接 &#x1f368; 本文为&#x1f517;365天深度学习训练营 中的学习记录博客&am…

机器学习:如何解决类别不平衡问题

类别不平衡是一个常见问题&#xff0c;其中数据集中示例的分布是倾斜的或有偏差的。 1. 简介 类别不平衡是机器学习中的一个常见问题&#xff0c;尤其是在二元分类领域。当训练数据集的类分布不均时会发生这种情况&#xff0c;从而导致训练模型存在潜在偏差。不平衡分类问题的示…

【Unity云消散】理论基础:实现SDF的8SSEDT算法

距离元旦假期已经过去5天了&#xff08;从31号算起&#xff01;&#xff09;&#xff0c;接着开始学习&#xff01; 游戏中的很多渲染效果都离不开SDF&#xff0c;那么SDF究竟是什么呢&#xff1f;到底是个怎么样的技术&#xff1f;为什么能解决那么多问题&#xff1f; 1 SD…

git介绍及环境搭建

git介绍及环境搭建Git介绍Git安装流程配置用户信息git工作流程与常用命令问题点总结主要工作流程git工作流程与原理总结Git介绍 1.Git是什么&#xff1f; Git版本控制系统是一个分布式的系统,是用来保存工程源代码历史状态(游戏存档)的命令行工具 GIT是一个命令行工具,用于版…