Qt学习记录(二)

这篇博客记录了在Qt中如何自定义信号和槽函数来实现教师下课后学生请客吃饭的场景。通过创建Teacher和Student类,定义饿信号和请客吃饭的槽函数,详细展示了信号与槽的使用,包括有参数的信号和槽的实现。同时,还介绍了信号与槽的多种连接方式和参数匹配规则。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

需求:定义teacher和student类,实现下课后,老师发出饿信号,学生请客吃饭

  • 新建项目,项目名称为SignalsAndSlots,基类选择QWidget

类选择

建立完成后,项目界面如下所示:

2

右键点击项目名称SignalsAndSlots,选择添加新文件,选择C++ class

3

建立Teacher类,基类选择QObject,界面如下所示:

4

同理添加Student类,选择基类QObject,添加完成后,界面如下所示:

5

红色所示为新添加的student和teacher类。

建立好项目后,对需求进行实现,首先对teacher.h自定义饿信号,代码如下:

#ifndef TEACHER_H
#define TEACHER_H

#include <QObject>

class Teacher : public QObject
{
    Q_OBJECT
public:
    explicit Teacher(QObject *parent = nullptr);

signals:
    //自定义信号需要写到signlas下
    //信号返回类型必须为void
    //信号只需要声明,不需要实现
    //信号可以有参数,可以重载
    void hungry();

public slots:
};

#endif // TEACHER_H

关于自定义信号,注意事项如下:

  • 自定义信号需要写到signals
  • 信号返回类型必须为void
  • 信号只需要声明,不需要实现
  • 信号可以有参数,可以重载

student.h定义槽函数,做修改如下:

#ifndef STUDENT_H
#define STUDENT_H

#include <QObject>

class Student : public QObject
{
    Q_OBJECT
public:
    explicit Student(QObject *parent = nullptr);

signals:

public slots:
    //自定义槽函数最好写在slots下
    //返回类型void
    //需要声明,也需要实现
    //槽函数可以有参数,也可以重载
    void treat();
};

#endif // STUDENT_H

自定义槽函数注意事项如下:

  • 自定义槽函数最好写在slots下
  • 返回类型void
  • 需要声明,也需要实现
  • 槽函数可以有参数,也可以重载

studen.cpp实现槽函数如下:

#include "student.h"
#include<QDebug>
Student::Student(QObject *parent) : QObject(parent)
{

}
void Student::treat()
{
    qDebug()<<"请客吃饭";
}

widget.h中包含teacher.h和studen.h头文件,并对下课触发老师饿信号函数进行定义

#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>
#include"teacher.h"
#include"student.h"

class Widget : public QWidget
{
    Q_OBJECT

public:
    Widget(QWidget *parent = 0);
    Teacher* zt;
    Student* st;
    void classOver();
    ~Widget();
};

#endif // WIDGET_H

widget.cpp中进行具体实现

#include "widget.h"

Widget::Widget(QWidget *parent)
    : QWidget(parent)
{
    //将zt,st对象与widget绑定,不用考虑内存释放问题
    zt = new Teacher(this);
    st = new Student(this);


    //老师发出饿信号,学生请客吃饭
    connect(zt,&Teacher::hungry,st,&Student::treat);
    //下课信号发出,触发老师饿信号
    classOver();
}

void Widget::classOver()
{
    //触发信号
    //老师饿属于自定义信号,触发自定义信号需要emit关键字
    emit zt->hungry();
}
Widget::~Widget()
{

}

输出结果如下:

6

接下来增加信号和槽函数的有参函数,并进行信号传递

teacher.h信号中增加有参信号

void hungry(QString foodname);

student.h槽函数增加有参槽函数

void treat(QString foodname);

student.cpp对有参槽函数进行实现

void Student::treat(QString foodname)
{
    //qDebug()<<"请客吃饭,吃"<<foodname<<endl;
    //将QString转换为char*类型
    qDebug()<<"请客吃饭,吃"<<foodname.toUtf8().data();
}

widget.cpp中classover增加对有参函数的触发,并传入参数

void Widget::classOver()
{
    //触发信号
    //老师饿属于自定义信号,触发自定义信号需要emit关键字
    //emit zt->hungry();
    //触发有参信号
    emit zt->hungry("宫保鸡丁");
}

widget.cpp中Widget构造函数中增加对有参信号和槽函数的处理,为了调用有参函数,定义有参函数指针,指向函数

//函数指针,指向有参函数
    void(Teacher:: * teacherSignal)(QString) = &Teacher::hungry;
    void(Student:: * studentSlot)(QString) = &Student::treat;
    connect(zt,teacherSignal,st,studentSlot);

结果如下:带“ ”为QString类型,不带“ ”为char*类型

7

  • 利用按钮控制下课信号

对widget.cpp进行修改如下:

#include "widget.h"
#include<QPushButton>
Widget::Widget(QWidget *parent)
    : QWidget(parent)
{
    //将zt,st对象与widget绑定,不用考虑内存释放问题
    zt = new Teacher(this);
    st = new Student(this);


    QPushButton* btn = new QPushButton("click",this);
    resize(600,400);

    //老师发出饿信号,学生请客吃饭
    //connect(zt,&Teacher::hungry,st,&Student::treat);
    //下课信号发出,触发老师饿信号

    //函数指针,指向有参函数
    void(Teacher:: * teacherSignal)(QString) = &Teacher::hungry;
    void(Student:: * studentSlot)(QString) = &Student::treat;
    connect(zt,teacherSignal,st,studentSlot);

    //利用按钮触发信号
    connect(btn,&QPushButton::clicked,this,&Widget::classOver);
    //classOver();
}

void Widget::classOver()
{
    //触发信号
    //老师饿属于自定义信号,触发自定义信号需要emit关键字
    //emit zt->hungry();
    //触发有参信号
    emit zt->hungry("宫保鸡丁");
}
Widget::~Widget()
{

}

每次点击按钮,输出“请客吃饭,吃 宫保鸡丁”,结果如下:

8

信号和槽知识补充:

  • 信号可以连接信号
  • 一个信号可以连接多个槽函数
  • 多个信号可以连接一个槽函数
  • 信号参数个数可以多余槽参数个数,但是类型必须一一对应
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值