Qt串口类QSerialPort的进一步封装

  • Qt的串口类每次获取到电脑上存在的所有的串口都需要使用一下代码:
    foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts()) //遍历所有可用串口
    {
        portNameList.push_back(info.portName());
    }
  • 每次刷新操作可以重新读取当前可用的串口
void SerialPort::refreshSerialPort()
{
    if(this->isOpen()){
        this->close();
    }
    portNameList.clear();   
    foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts()) 
    {
        portNameList.push_back(info.portName());
    }
}
  • readyRead()信号会在有数据时就触发,这时可能并没有接收到含有结尾标志位(“\r\n”等)的所有数据 。我对该部分做了封装
	connect(this, &SerialPort::readyRead, this,[this]() {
        this->dataReceived();
    });

void SerialPort::dataReceived()
{
    QByteArray data = this->readAll();                      // 读取数据
    if(!data.isEmpty())                                 // 接收到数据
    {
        QString str = std::move(readBuf);  // 返回纯文本
        str += tr(data);                                // 数据是一行一行传送的,要保存所有数据
        int index = str.indexOf(endChar);                // 找到,返回索引值,找不到,返回-1
        if(index != -1)//接收到结尾标志符
        {
            readyData=std::move(str);                          // 将数据放入控件中
            dataReady();                               //数据已经准备好,发送信号
        }else{
            readBuf=std::move(str);
        }
    }
}

以下是源文件

serialport.h
#ifndef SERIALPORT_H
#define SERIALPORT_H

#include <QObject>
#include <QtSerialPort/QSerialPort>         // 提供访问串口的功能
#include <QtSerialPort/QSerialPortInfo>     // 提供系统中存在的串口信息

class SerialPort: public QSerialPort
{
    Q_OBJECT
public:
    SerialPort(QSerialPort*parent=nullptr);

    void                    refreshSerialPort();                 // 刷新串口 //关闭当前打开的串口
    bool                    setSerialPort(int index);            //设置串口
    void                    setEndMarker(QString endMarker);     //设置以 "\r\n" "\r" "\n"等结尾
    std::vector<QString>    getPortNameList();
    QString                 getData();
public slots:
    // 串口槽函数
    void                    dataReceived();                      // 接收数据
    // 串口槽函数
    void                    dataSend(QString data);              // 发送数据
signals:
    void                    dataReady();
private:

    std::vector<QString>    portNameList;                        //当前存在的串口列表
    int                     curPortIndex=0;
    QString                 readyData;                           //接收到的准备好的数据,(已去掉结尾标识符)
    QString                 readBuf;                             //未读取到结尾标识符的临时数据缓冲区
    QString                 endMarker="\r\n";
};
#endif // SERIALPORT_H
serialport.cpp
#include "serialport.h"

SerialPort::SerialPort(QSerialPort*parent)
    :QSerialPort(parent)
{
    // 参数配置
    // 波特率,波特率默认选择57600 ,禁止用户点击
    this->setBaudRate(QSerialPort::Baud9600);
    //ui->BaudBox->setDisabled(true);

    // 校验,校验默认选择无
    this->setParity(QSerialPort::NoParity);

    // 数据位,数据位默认选择8位
    this->setDataBits(QSerialPort::Data8);

    // 停止位,停止位默认选择1位
    this->setStopBits(QSerialPort::OneStop);

    // 控制流,默认选择无
    this->setFlowControl(QSerialPort::NoFlowControl);

    
    // 刷新串口
    refreshSerialPort();


    connect(this, &SerialPort::readyRead, this,[this]() {
        this->dataReceived();
    });
}


// 刷新串口
void SerialPort::refreshSerialPort()
{
    if(this->isOpen()){
        this->close();
    }
    portNameList.clear();   
    foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts()) //添加新串口
    {
        portNameList.push_back(info.portName());
    }
}
bool SerialPort::setSerialPort(int index)
{
    if(this->isOpen()){
        this->close();
    }
    curPortIndex=index;
    this->setPortName(this->portNameList[index]);             //设置串口号
    if (this->open(QIODevice::ReadWrite)){
        //qDebug()<<"serial "<<this->portNameList[index]<<"open succcess"<<endl;
        return true;
    }
    //qDebug()<<"serial "<<this->portNameList[index]<<"open faild"<<endl;
    return false;
}
// 接收数据,使用read () / readLine () / readAll ()
void SerialPort::dataReceived()
{
    QByteArray data = this->readAll();                      // 读取数据
    if(!data.isEmpty())                                 // 接收到数据
    {
        QString str = std::move(readBuf);  // 返回纯文本
        str += tr(data);                                
        //qDebug() << "str info: " << str<<endl;
         // 清除之前的数据,防止追加,因为每次获取的数据不一样
        int index = str.indexOf(endMarker);                // 找到,返回索引值,找不到,返回-1
        if(index != -1)//接收到结尾标志符
        {
            readyData=std::move(str);                          // 将数据放入控件中
            dataReady();                               //数据已经准备好,发送信号
        }else{
            readBuf=std::move(str);
        }
    }
}
QString SerialPort::getData()
{
    return this->readyData;
}
// 发送数据,write ()
void SerialPort::dataSend(QString data)
{
    this->write(data.toLatin1());      // 串口发送数据
}
std::vector<QString> SerialPort::getPortNameList(){
    return this->portNameList;
}
void SerialPort::setEndMarker(QString endMarker){     //设置以 "\r\n" "\r" "\n"等结尾
    this->endMarker=endMarker;
}
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值