• QT信号槽


    目录

    信号槽的概念

    按钮的常用信号

    自定义槽函数

    自定义信号函数

    自定义槽和信号注意的事项

    信号与槽的拓展

    lambda表达式


    信号槽的概念

    信号槽是Qt框架引以为豪的机制之一。所谓信号槽,实际就是观察者模式。当某个事件发生之后,比如,按钮检测到自己被点击了一下,它就会发出一个信号 (signal)这种发出是没有目的的,类似广播。如果有对象对这个信号感兴趣,它就会使用连接(connect) 函数,意思是,将想要处理的信号和自己的一个函数 (称为槽 (slot) )绑定来处理这个信号。也就是说,当信号发出时,被连接的槽函数会自动被回调。这就类似观察者模式:当发生了感兴趣的事件,某一个操作就会被自动触发。

    connect()函数最常用的一般形式:
    connect(sender, signal. receiver, slot):
    参数解释:
            sender:发出信号的对象
            signal:发送对象发出的信号
            receiver:接收信号的对象
            slot:接收对象在接收到信号之后所需要调用的函数 (槽函数)

    1. #include "widget.h"
    2. #include
    3. Widget::Widget(QWidget *parent)
    4. : QWidget(parent)
    5. {
    6. //创建一个按钮 点击按钮关闭窗口this->close();
    7. QPushButton *b = new QPushButton("点击关闭",this);
    8. //设置点击按钮 产生信号 会调用window close函数
    9. connect(b,&QPushButton::clicked,this,&Widget::close);
    10. }
    11. Widget::~Widget()
    12. {
    13. }

    按钮的常用信号

    在帮助中搜索QPushButton

    点击信号

    查看常用信号(点击 按下 释放 触发)

    自定义槽函数

    在类中public slots:下声明槽函数

    1. #include "widget.h"
    2. #include
    3. #include
    4. Widget::Widget(QWidget *parent)
    5. : QWidget(parent)
    6. {
    7. b = new QPushButton;
    8. b->setParent(this);
    9. b->setText("点击发送信号");
    10. //注册信号与槽的连接
    11. //槽函数可以是普通的成员函数 还可以是槽函数
    12. //如果信号没有参数 槽函数也不能有参数 如果信号有参数 槽函数可以有也可以没有参数
    13. connect(b,&QPushButton::pressed,this,&Widget::print);
    14. }
    15. void Widget::print()
    16. {
    17. qDebug()<<"收到信号,打印信息";
    18. }
    19. Widget::~Widget()
    20. {
    21. }

    可以看到,按钮被点击后信息被打印

    自定义信号函数

    父窗口点击按钮隐藏父窗口显示子窗口,子窗口点击按钮隐藏子窗口,并且发送信号10,

    父窗口收到信号10,显示父窗口

    sonwidget.h

    1. #ifndef SONWIDGET_H
    2. #define SONWIDGET_H
    3. #include
    4. #include
    5. class Sonwidget : public QWidget
    6. {
    7. Q_OBJECT
    8. public:
    9. explicit Sonwidget(QWidget *parent = nullptr);
    10. QPushButton *b2;
    11. signals://信号
    12. //信号没有返回值 可以有参数 信号函数不需要定义 只需要声明
    13. void window_hide_signal(int a);
    14. public slots://槽
    15. void emit_mysignal();
    16. };
    17. #endif // SONWIDGET_H

    widget.h

    1. #ifndef WIDGET_H
    2. #define WIDGET_H
    3. #include
    4. #include "sonwidget.h"
    5. #include
    6. class Widget : public QWidget
    7. {
    8. Q_OBJECT
    9. public:
    10. Widget(QWidget *parent = 0);
    11. ~Widget();
    12. Sonwidget *sonwindow;
    13. QPushButton *b1;
    14. public slots:
    15. void button_cd();
    16. void signal_cd(int a);
    17. };
    18. #endif // WIDGET_H

    widget.cpp

    1. #include "widget.h"
    2. #include
    3. Widget::Widget(QWidget *parent)
    4. : QWidget(parent)
    5. {
    6. this->setWindowTitle("父窗口");
    7. sonwindow = new Sonwidget;
    8. sonwindow->show();
    9. b1 = new QPushButton();
    10. b1->setText("隐藏父窗口,显示子窗口");
    11. b1->setParent(this);
    12. connect(b1,&QPushButton::clicked,this,&Widget::button_cd);
    13. connect(sonwindow,&Sonwidget::window_hide_signal,this,&Widget::signal_cd);
    14. }
    15. void Widget::button_cd()
    16. {
    17. this->hide();
    18. this->sonwindow->show();
    19. }
    20. void Widget::signal_cd(int a)
    21. {
    22. qDebug()<
    23. this->show();
    24. this->sonwindow->hide();
    25. }
    26. Widget::~Widget()
    27. {
    28. }

    sonwidget.cpp

    1. #include "sonwidget.h"
    2. #include
    3. Sonwidget::Sonwidget(QWidget *parent) : QWidget(parent)
    4. {
    5. this->setWindowTitle("子窗口");
    6. b2 = new QPushButton();
    7. b2->setText("隐藏子窗口,显示父窗口");
    8. b2->setParent(this);
    9. connect(b2,&QPushButton::clicked,this,&Sonwidget::emit_mysignal);
    10. }
    11. void Sonwidget::emit_mysignal()
    12. {
    13. window_hide_signal(10);//发送10
    14. }

    10被打印

    自定义槽和信号注意的事项

    发送者和接收者都需要是 QObject 的子类 (当然,槽函数是全局函数、Lambda 表达式等无需接收者的时候除外);

    信号和槽函数返回值是 void

    信号只需要声明,不需要实现,槽函数需要声明也需要实现

    槽函数是普通的成员函数,作为成员函数,会受到 public、private、protected 的影响;

    使用 emit 在恰当的位置发送信号;

    使用 connect()函数连接信号和槽。

    任何成员函数、static 函数、全局函数和 Lambda 表达式都可以作为槽函数

    信号槽要求信号和槽的参数一致,所谓一致,是参数类型一致。

    如果信号和槽的参数不一致,允许的情况是,槽函数的参数可以比信号的少,即便如此,槽函数存在的那些参数的顺序也必须和信号的前面几个一致起来。这是因为,你可以在槽函数中选择忽略信号传来的数据 (也就是槽函数的参数比信号的少)。

    信号与槽的拓展

    一个信号可以和多个槽相连

            如果是这种情况,这些槽会一个接一个的被调用,但是它们的调用顺序是不确定的。多个信号可以连接到一个槽,只要任意一个信号发出,这个槽就会被调用。

    一个信号可以连接到另外的一个信号

            当第一个信号发出时,第二个信号被发出。除此之外,这种信号-信号的形式和信号-槽的形式没有什么区别。

    槽可以被取消链接

            这种情况并不经常出现,因为当一个对象 delete 之后,Qt 自动取消所有连接到这个对象上面的槽。

    信号槽可以断开

            利用 disconnect 关键字是可以断开信号槽的

    使用 Lambda 表达式

            在使用 Qt 5的时候,能够支持 Qt 5的编译器都是支持 Lambda 表达式的。在连接信号和槽的时候,槽函数可以使用 Lambda 表达式的方式进行处理。

    lambda表达式

    lambda表达式用于定义并创建匿名的函数对象,以简化编程工作

    1. #include "widget.h"
    2. #include
    3. Widget::Widget(QWidget *parent)
    4. : QWidget(parent)
    5. {
    6. b = new QPushButton("点击",this);
    7. int a = 10;
    8. //槽函数可以是一个lambda表达式
    9. //lambda表达式中[]写=,代表将上面的函数的局部变量以值传递的方式传入表达式
    10. //lambda表达式中[]写&,代表将上面的函数的局部变量以引用的方式传入表达式
    11. //lambda表达式中[]写a,代表将上面的函数的局部变量a以值传递的方式传入表达式
    12. //lambda表达式中[]写a,b,代表将上面的函数的局部变量a和b以值传递的方式传入表达式
    13. //lambda表达式中[]写&a,代表将上面的函数的局部变量a以引用的方式传入表达式
    14. //mutable修饰的作用是可以修改传入lambda中的值
    15. //->代表lambda返回值的类型是int
    16. connect(b,&QPushButton::clicked,this,[=]()mutable->{
    17. qDebug()<
    18. qDebug()<<"点击成功";
    19. });
    20. }
    21. Widget::~Widget()
    22. {
    23. }

  • 相关阅读:
    Markdown 教程之如何在 Markdown 文档中添加流程图、方程式和交互式图形
    现代图片性能优化及体验优化指南 - 图片资源的容错及可访问性处理
    bytebuffer 内部结构
    单片机IO口控制12V电压通断,MOS和三极管电路
    尼莫地平PEG-PLGA纳米粒|葛根素PEG-PLGA纳米粒(Pue-NPs)|负载替米沙坦PLGA纳米粒
    python05_流程控制
    Linux命令(93)之su
    GEE教程——利用Global 4-class PALSAR-2/PALSAR Forest数据提取指定区域的森林和影像下载
    SparkMlib 之随机森林及其案例
    Strategies to Improve Signal-to-Noise Ratio in Communication
  • 原文地址:https://blog.csdn.net/2301_77164542/article/details/133410191