吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 3545|回复: 10
收起左侧

[C&C++ 转载] 从C++ GUI Qt4编程示例看Qt5的信号槽演变

[复制链接]
dbgcode 发表于 2022-2-27 13:11
本帖最后由 dbgcode 于 2022-2-27 14:15 编辑

从C++ GUI Qt4编程示例看Qt5的信号槽演变
本示例是在Qt5.6.3中演示

该书是Qt入门经典书籍,可谓信息量详多,不适合零基础人士。
一、第一章三个小示例引入常用概念。
二、关于信号槽函数重载。


一、示例1带你熟悉Qt编程基本框架和编译步骤
[Asm] 纯文本查看 复制代码
#include <QApplication>     //要在项目PRO文件中添加 QT += widgets,否则编译失败。
#include <QLabel>           //1、是窗口程序必须包含的类,2、是输出helloQt的标签类

int main(int argc, char *argv[])    //所有基于C++的程序必有的入口函数
{
    QApplication app (argc,argv);   //初始化窗口必须的实例,必须在Q_OBJECT宏前定义。
    /*         QLabel *lebel=new QLabel("Hello Qt");     //对象生成在堆上,没有delete,有内存泄漏.
                label->show
    */
    QLabel label("helloQt");        //修改为创建在栈上,由程序自动管理。
    //QLabel label("<h2><i>hello</i>""<font color=red>Qt</font></h2>");
    label.show();                   //显示创建的窗口在代码结束

    return app.exec();          //使程序代码一直执行,进入事件循环,直到用户点击退出。
}

示例2引入了信号槽机制
[Asm] 纯文本查看 复制代码
#include <QApplication>
#include<QPushButton>

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

    QPushButton button("quit");
    button.show();
    //QObject::connect(&button,SIGNAL(clicked(bool)),&app,SLOT(quit()));          //Qt4写法
    QObject::connect(&button,&QPushButton::clicked,&app,&QApplication::quit);   //Qt5写法

    return app.exec();
}

示例3引入布局的概念,让你从繁复的设置部件位置和大小中脱离出来。
[Asm] 纯文本查看 复制代码
#include <QApplication>
#include <QHBoxLayout>
#include <QSlider>
#include <QSpinBox>

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

    QWidget window;
    window.setWindowTitle("Enter You Age");
    QSpinBox spinBox;
    QSlider slider(Qt::Horizontal);
    spinBox.setRange(0,130);
    slider.setRange(0,130);
/*  //带SIGNAL和SLOT的是Qt4通用写法
    QObject::connect(&spinBox,SIGNAL(valueChanged(int)),&slider,SLOT(setValue(int)));
    QObject::connect(&slider,SIGNAL(valueChanged(int)),&spinBox,SLOT(setValue(int)));
*/
    void (QSpinBox::*sb)(int)=&QSpinBox::valueChanged;  //valueChanged有重载,指针要精确匹配函数才能作为信号
    QObject::connect(&spinBox,sb,&slider,&QSlider::setValue);   //Qt5.6写法
    QObject::connect(&slider,&QSlider::valueChanged,&spinBox,&QSpinBox::setValue);
    spinBox.setValue(35);
    QHBoxLayout layout;
    layout.addWidget(&spinBox);
    layout.addWidget(&slider);
    window.setLayout(&layout);

    window.show();
    return app.exec();
}

Qt5和Qt4比较多了两个connnect()函数重载,以及信号槽的类型检查。Qt4在运行时才检查,Qt5可以在编译时检查。
Qt4常用原型和新增函数原型如下:

QObject::connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type = Qt::AutoConnection)
QObject::connect(const QObject *sender, PointerToMemberFunction signal, const QObject *receiver, PointerToMemberFunction method, Qt::ConnectionType type = Qt::AutoConnection)
QObject::connect(const QObject *sender, PointerToMemberFunction signal, Functor functor)
可见Qt4和5的发送者和接收者没有变化或者只是省略而已。不同的只是信号槽的类型变化,以前是字符指针型(需要用相应SIGNAL()或SOLT()宏转换),现在变为函数指针型(直接在函数前加&取地址符就好,书写简单了)。
二、关于信号槽的函数重载
在信号槽没有函数重载时Qt5比Qt4书写简单,且有类型检查,通过上面示例也可以看出来。
有重载时,因为信号槽是函数指针,而函数指针必须要指定的具体的函数,也就是说重载的每个函数都要指定一个函数指针,才能在connect()里使用。
但你没有明确初始化一个重载的信号槽函数时,直接使用信号槽函数的名称,编译器会因为不知道具体调用哪个重载的函数而报错。
上面的示例3使用了C语言的方式处理的信号槽。而在C++中建议是下面的处理方式:

QObject::connect(&spinBox,static_cast<void (QSpinBox::*)(int)>(&QSpinBox::valueChanged),&slider,&QSlider::setValue);
上面是在Qt5.7之前的写法,在Qt5.7及以后的写法是这样:
QObject::connect(&spinBox,qOverload<int>(&QSpinBox::valueChanged),&slider,&QSlider::setValue); //需要C++14
QObject::connect(&spinBox,QOverload<int>::of(&QSpinBox::valueChanged),&slider,&QSlider::setValue); //需要C++11



至于信号槽函数带默认参数时,实现方式就用lambda表达式吧。

免费评分

参与人数 1吾爱币 +7 热心值 +1 收起 理由
苏紫方璇 + 7 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

JBHAODA 发表于 2022-2-27 13:55
小白一名帮顶
cnfitc 发表于 2022-2-27 15:40
boywhocools 发表于 2022-2-27 20:20
xz91168 发表于 2022-2-28 06:46
我一小白,求大佬给个入门C++的好教程,谢谢
spygg 发表于 2022-2-28 20:16
lambda 简单调用还行,有时候有坑,比如变量作用域等问题
我系阿超 发表于 2022-3-4 10:13
顶一下!
a2504278 发表于 2022-3-6 12:51
我看我一年后还会不会看上面的代码,
liyajojo 发表于 2022-5-10 09:44
顶一下!
wangxiaohu104 发表于 2022-5-12 21:05
谢谢楼主分享,
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-11-24 22:14

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表