基于QT的CAN通讯数据实时波形显示(连载六)========“添加线程“和”不同class间变量传输“

本文详细介绍了如何在QT环境中通过添加线程文件、修改线程程序、主文件修改、添加抛出函数以及验证数据传输来实现不同文件间的数据变量传输,避免使用全局变量。通过信号和槽函数,实现了数据从主线程到子线程的正确传递和接收,确保了数据传输的实时性和准确性。
摘要由CSDN通过智能技术生成

前言

    此文仅仅添加不同文件中数据变量传输问题。不用添加全局变量,仅仅利用信号和槽函数完成局部变量传输。适用于编写单片机的小伙伴无法解决全局变量和子函数之间变量调用问题。

第一部分:添加线程文件

    (1)第一步,添加文件,在项目中,右键,添加add new。

    (2)添加c和h文件

    (3)点击choose后,出现以下界面,在name中添加名字:datadeal,在baseclass中选择QObject(这一步很重要),同时选择图中选项,然后确定,确定,就可以添加一个c和一个h文件了。

第二部分:修改线程程序

    (1)由于添加的为object文件,所以将以下两个部分改为线程的class。第一张是h文件,第二张是c文件。这两个部分必须修改,切记。这样就变成了线程的类文件。

第三部分:主文件修改

    (1)这时可以点击pro文件,看到以下情况,c和h文件已经添加到主文件里。这里是自动添加,不用管。

    同时在mainwindow或者在你自己的主c文件里(不是main)添加h文件。这时文件已经添加完毕,编辑和运行,无错误,证明线程文件添加正确。

#include "datadeal.h"

第四部分:添加抛出函数(就这样叫吧,比较形象)

    (1)datadeal的h文件中,添加下列程序。这个为datadeal线程文件的槽函数声明,也就是接收函数声明。

private slots:
    void receiveData(uint8_t data0,uint8_t data1,uint8_t data2,uint8_t data3,uint8_t data4,uint8_t data5,uint8_t data6,uint8_t data7);

    (2)datadeal的c文件中,添加下列程序。这个为对应h文件的接收函数主体。其中debug为验证传输的数据是否正确。

void datadeal::receiveData(uint8_t data0, uint8_t data1, uint8_t data2, uint8_t data3, uint8_t data4, uint8_t data5, uint8_t data6, uint8_t data7)
{
    qDebug()<<data0<<data1<<data2<<data3<<data4<<data5<<data6<<data7;    
}

    (3)mainwindow的h文件中,添加信号函数的声明。

signals:
    void sendData(uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t);

    (4)mainwindow的c文件里添加执行函数。除了emit函数,其他函数都是can的接收程序,每接收一次数据,debug一次,并发送一次。

    注意:发送8个数据,也要接收8个数据,数据类型也需要对应。同时这个函数发送字符串也是可以的,已经试验过。

    if(ReceiveNum>0)
    {
        for (int i = 0; i < ReceiveNum; i++)
        {
            CANID = Receive[i].ID;
            for (int j = 0; j < 8; j++)
            {
               gnDataBuffer[j] = Receive[i].Data[j];
            }
            qDebug() << gnDataBuffer[0]<< gnDataBuffer[1]<< gnDataBuffer[2]<< gnDataBuffer[3]<< gnDataBuffer[4]<< gnDataBuffer[5]<< gnDataBuffer[6]<< gnDataBuffer[7];
            emit sendData(gnDataBuffer[0],gnDataBuffer[1],gnDataBuffer[2],gnDataBuffer[3],gnDataBuffer[4],gnDataBuffer[5],gnDataBuffer[6],gnDataBuffer[7]);
        }      
    }

     (5)链接函数。接收和发送函数都有,必须将两个联系起来,一个信号函数,一个槽函数。格式就是这样,不知道为啥,都得一一对应。这段程序在ui->setupUi(this)下面。这个位置必须在这个位置。

    datadeal *dlg = new datadeal;
    connect(this,SIGNAL(sendData(uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t)),dlg,SLOT(receiveData(uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t,uint8_t)));

    注:由于链接函数在mainwindow里面,所以信号用的this,槽函数在datadeal的class里面,所以必须先声明一个datadeal的类,这样就将信号的槽函数链接起来了。试验了将此函数放入生成的datadeal的主体的以下位置:

    发现不能将信号和槽函数链接。同时也尝试了线程函数,也不行。所以最好放在刚才说的位置。并且考虑到程序的可观性,将所有函数的链接都放在ui->setupUi(this)下才比较好。

第五部分:验证数据传输

    (1)利用CAN产生的数据进行验证,1s传输一次。打印的报文中:1为接收的帧数,8 25x为接收数据,一一对应,同时发现执行emit函数后,会立刻执行槽函数的打印程序(这点和面对逻辑程序不同)。这样就将mainwindow里面的数据传输到datadeal中。此种方法可以用在不同class定义的变量的传输问题。非常好用。

    (2)利用正常数据帧验证

    可以观察到128为报头8000,挨着的两帧数据相同,其中第一帧为直接打印,第二帧为传输数据后打印,可以证实传输数据在正常传输CAN帧的情况下正确。

    注:由于小伙伴需要源代码的时间不同,登录邮箱界面太多麻烦,所以建立了一个订阅号,如果有问题或者需要源码,可添加订阅号,留言后会发送源代码或者有任何问题可留言,将积极解决提出的问题。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值