当前位置:网站首页>C2-qt serial port debugging assistant 2021.10.21
C2-qt serial port debugging assistant 2021.10.21
2022-06-22 02:44:00 【Morning and evening rain】
Qt Realize serial port debugging assistant
1. The goal is
Realize serial port debugging assistant , The interface style is concise , Configurable key communication parameters include , Baud rate 、 Stop bit 、 Data bits 、 Check bit ; We can use 16 Binary transmit data , With 16 Base or ascii Code receiving data , Support to save the received data to local txt.
notes : see FPGA Lower computer serial port code implementation , Please check out FPGA Serial port communication
download FPGA Serial communication engineering documents and codes , Please check out FPGA Serial port communication vivado engineering
2. step
2.1.pro Add , Serial port module .
The module Qt5 Support ,Qt4 I won't support it ;
QT += serialport
2.2 Serial port related classes
#include <QtSerialPort/QSerialPortInfo>
#include <QtSerialPort/QSerialPort>
QSerialPortInfo This class will get the serial port information , as follows :
qDebug()<<"serialPortName:"<<info.portName();
qDebug() << "Description : " << info.description();
qDebug() << "Manufacturer: " << info.manufacturer();
qDebug() << "Serial Number: " << info.serialNumber();
qDebug() << "System Location: " << info.systemLocation();
QSerialPort There are many ways , As basic as open、close、read、write Method , And error handling 、 Set serial port parameters and other methods , Will coordinate the work , Jointly complete the operation of serial port sending and receiving .
2.3 Interface prototype construction
Some interface layout details , The typesetting principle is fully reflected in the following interface prototype with infinite fidelity , This setup does not require manual code .
2.4 Interface logic
(1) call Init() function , The initialization function will complete the following functions
First, check the current online serial port device , And write it into the drop-down box ;
Initialize baud rate selection drop-down box , And check bits 、 Stop bit 、 Data bits ;
Set the default to 16 Base display ;
Clear receive buffer ( Black areas ).
(2) Make button function connection
” Scan the serial port “ Button to rescan the current serial port device , And update its status to the corresponding drop-down box ;
“ Open the serial port ” Button to issue serial port configuration and open serial port , Add open failure mode to prompt the user , Successfully added and opened, the button changes to “ Turn off the serial port ”;
" Turn off the serial port " The button will clear Serial port and close the serial port ;
“ Clear receive ” take textEdit clear fall ;
“ Save window ” Save the contents of the current receiving box to... Under the project directory txt, And clear the current receiving frame ;
“ send out ” Data processing operation will be performed and sent to the open serial port , Of course, there will be a prompt of serial port failure ;
“ Clear send ” The current send box will be cleared ;
(3) Adjust interface logic details
“ A serial port choice ”QFrame Fixed size , Does not change with the size of the interface ;
“ A serial port choice ” The overall vertical layout after the horizontal layout of the middle horizontal elements ;
“ Receiving frame ” Read only mode ;
Set up “ Receiving frame ” Style sheets , Black background , Green font ;
“ Send box ” Show me by default logo;
2.5 The underlying logic
(1) Get the current configuration function , The return value is the enumeration type , convenient “ Open the serial port ” Called when the , Take the current configuration of the check bit as an example , as follows :
enum QSerialPort::Parity MainWindow::getParity()
{
QString currentParityBit = ui->checkBit_Sel->currentText();
if (currentParityBit == "None")
return QSerialPort::NoParity;
else if (currentParityBit == "Odd")// Odd number
return QSerialPort::OddParity;
else if (currentParityBit == "Even")// Even check
return QSerialPort::EvenParity;
else
return QSerialPort::UnknownParity;
}
(2) receive data , The serial port data buffer will send a signal when receiving data &QSerialPort::readyRead, Therefore, the user only needs to write the slot function and link it .
notice:
(2.1) For example, the other party sends 0x11、0x22、0x33、0x44、0x55, The data of , It may trigger many times ReadSerialData() call , This is not the end of the collection 5 Data , Will trigger once , But the data read away , I won't read it again next time , This can be assured ;
(2.2) Here we need to judge what is read QByteArray Of buffer Is it empty , I have encountered during debugging , Empty data , It also triggers an entry into the slot function ;
(2.3) receive ( send out ) The data type is QByteArray The type of , The receiving side needs to perform data type conversion to facilitate display processing
str.append(QString::number((ary[i]&0xff),16));//QByteArray-->QString
(2.4) Receive operation read、readAll, And send operation write Are non blocking operations , That is, function execution , Whether or not all data is received ( send out ), Functions will immediately return , The program will continue .
(2.5) Support 16 The display of decimal system 、Ascii Display of codes ( Two types of data processing )
(3) send data
The default in accordance with the 16 Send data in hexadecimal mode , Therefore, only 16 Hexadecimal related character input , Other characters will not be allowed .
3. Code
3.1.cpp File code
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QDebug>
#include <QMessageBox>
#include <QFile>
#include <QTextStream>
#include <QByteArray>
#include <QTextDecoder>
#include <QTextCodec>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
, ui(new Ui::MainWindow)
{
ui->setupUi(this);
//QAbstractNativeEventFilter QT System event filter , For example, the serial port plug-in can identify
// That is, real-time detection of equipment status by means of interruption
Init();// Initialization function , effect : Scan the online serial port ; Fill baud rate 、 Check bit 、 Data bits 、 Stop bit widget
// Rescan the online serial port ( Displays the current device status )
connect(ui->scanBtn,&QPushButton::clicked,[=](){
ui->comboBox->clear();
foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
{
ui->comboBox->addItem(info.portName());
}
});
// Turn on the serial button
connect(ui->openBtn,&QPushButton::clicked,[=](){
if(ui->openBtn->text()==" Open the serial port ")
{
// qDebug()<<getBaud()<<getParity()<<getdataBits()<<getstopBits();
mySerialPort->setPortName(ui->comboBox->currentText());
mySerialPort->setBaudRate(getBaud());
mySerialPort->setParity(getParity());
mySerialPort->setDataBits(getdataBits());
mySerialPort->setStopBits(getstopBits());
// mySerialPort->setFlowControl(QSerialPort::NoFlowControl); // TODO: FlowControl
// mySerialPort->setReadBufferSize(0); // The buffer is infinite
if(!(mySerialPort->open(QSerialPort::ReadWrite)))
{
// The standard dialog box prompts that opening the serial port failed
QMessageBox::warning(this," Warning "," Failed to open serial port ");
}
else
{
ui->openBtn->setText(" Turn off the serial port ");
}
}
else
{
mySerialPort->clear();
mySerialPort->close();
ui->openBtn->setText(" Open the serial port ");
}
});
// Save button
connect(ui->saveBtn,&QPushButton::clicked,[=](){
QFile file("UART_Rec.txt");
file.open(QIODevice::Append);
// Use QTextStream write file
QTextStream tsm(&file);
tsm<<ui->reci_Edit->toPlainText();
ui->reci_Edit->clear();
file.close();
});
// Clear the receive button
connect(ui->clearRecBtn,&QPushButton::clicked,[=](){
ui->reci_Edit->clear();
});
// Clear the send button
connect(ui->clearXferBtn,&QPushButton::clicked,[=](){
ui->xferEdit->clear();
});
// Send button
connect(ui->xferBtn, &QPushButton::clicked, this, [=](){
if(!mySerialPort->isOpen())
{
QMessageBox::information(this," Tips "," Please open the serial port first ");
}
else
{
// // Get the send box character
QString str = ui->xferEdit->document()->toPlainText();
if (str.isEmpty())
{
QMessageBox::information(this," Tips "," Please enter the sending content first ");
}
// Default 16 Base send , Filter useless characters Include 0x
else
{
char ch;
bool flag = false;
uint32_t i, len;
// Get rid of useless symbols
str = str.replace(' ',"");
str = str.replace(',',"");
str = str.replace('\r',"");
str = str.replace('\n',"");
str = str.replace('\t',"");
str = str.replace("0x","");
str = str.replace("0X","");
str = str.replace('\\',"");
str = str.replace(':',"");
str = str.replace('?',"");
str = str.replace(';',"");
// Judge the validity of data
for(i = 0, len = str.length(); i < len; i++)
{
ch = str.at(i).toLatin1();
if (ch >= '0' && ch <= '9')
{
flag = false;
}
else if (ch >= 'a' && ch <= 'f')
{
flag = false;
}
else if (ch >= 'A' && ch <= 'F')
{
flag = false;
}
else
{
flag = true;
}
}
if(flag)
{
QMessageBox::warning(this," Warning "," The input contains illegal 16 Hexadecimal characters ");
}
else
{
//QString turn QByteArray
QByteArray xferAry = str.toUtf8();
mySerialPort->write(xferAry);
}
}
}
});
// receive Buffer
connect(mySerialPort,&QSerialPort::readyRead,[=](){
if(ui->hex_Rtn->isChecked())
{
// With 16 Base display
QByteArray ary = mySerialPort->readAll();
qDebug()<<ary;
QString str;
str.clear();
for (int i = 0;i<ary.size()-2 ;i++ ) {
str.append(QString::number((ary[i]&0xff),16));// take 16 Hexadecimal output as is
// str.append(" ");
}
ui->reci_Edit->append(str);
// ui->reci_Edit->append("\n");
}
else
{
// With Ascii Code display Ascii Code means 16 The character corresponding to base , Namely ascii One of the rules 16 Mapping between base and character
ui->reci_Edit->append(mySerialPort->readAll());
ui->reci_Edit->append("\n");
}
});
}
MainWindow::~MainWindow()
{
if(mySerialPort->isOpen())
{
mySerialPort->clear();
mySerialPort->close();
}
delete mySerialPort;
delete ui;
}
enum QSerialPort::Parity MainWindow::getParity()
{
QString currentParityBit = ui->checkBit_Sel->currentText();
if (currentParityBit == "None")
return QSerialPort::NoParity;
else if (currentParityBit == "Odd")// Odd number
return QSerialPort::OddParity;
else if (currentParityBit == "Even")// Even check
return QSerialPort::EvenParity;
else
return QSerialPort::UnknownParity;
}
enum QSerialPort::BaudRate MainWindow::getBaud()
{
bool ok;
enum QSerialPort::BaudRate ret;
switch (ui->baud_Sel->currentText().toLong(&ok, 10))
{
case 1200:
ret = QSerialPort::Baud1200;
break;
case 2400:
ret = QSerialPort::Baud2400;
break;
case 4800:
ret = QSerialPort::Baud4800;
break;
case 9600:
ret = QSerialPort::Baud9600;
break;
case 19200:
ret = QSerialPort::Baud19200;
break;
case 38400:
ret = QSerialPort::Baud38400;
break;
case 57600:
ret = QSerialPort::Baud57600;
break;
case 115200:
ret = QSerialPort::Baud115200;
break;
default:
ret = QSerialPort::UnknownBaud;
break;
}
return ret;
}
enum QSerialPort::StopBits MainWindow::getstopBits()
{
QString currentStopBits = ui->stopBit_Sel->currentText();
if (currentStopBits == "1")
return QSerialPort::OneStop;
else if (currentStopBits == "1.5")
return QSerialPort::OneAndHalfStop;
else if (currentStopBits == "2")
return QSerialPort::TwoStop;
else
return QSerialPort::UnknownStopBits;
}
enum QSerialPort::DataBits MainWindow::getdataBits()
{
QString currentDataBits = ui->dataBit_Sel->currentText();
if(currentDataBits == "5")
return QSerialPort::Data5;
else if (currentDataBits == "6")
return QSerialPort::Data6;
else if (currentDataBits == "7")
return QSerialPort::Data7;
else if (currentDataBits == "8")
return QSerialPort::Data8;
else
return QSerialPort::UnknownDataBits;
}
void MainWindow::Init()
{
// First scan the current serial port , initialization COM Port selection component
QStringList myPortName;
foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
{
myPortName << info.portName();
qDebug()<<"serialPortName:"<<info.portName();
qDebug() << "Description : " << info.description();
qDebug() << "Manufacturer: " << info.manufacturer();
qDebug() << "Serial Number: " << info.serialNumber();
qDebug() << "System Location: " << info.systemLocation();
}
myPortName.sort();
ui->comboBox->addItems(myPortName);
// Initialize the baud rate component
QStringList myBaud;
myBaud.clear();
myBaud<<"1200"<<"2400"<<"4800"<<"9600"<<"19200"<<"38400"<<"57600"<<"115200";
ui->baud_Sel->addItems(myBaud);
ui->baud_Sel->setCurrentText("9600");
// Initialize stop bit
QStringList mystopBits;
mystopBits.clear();
mystopBits<<"1"<<"1.5"<<"2";
ui->stopBit_Sel->addItems(mystopBits);
ui->stopBit_Sel->setCurrentText("1");
// Initialize check bit
QStringList mycheckBits;
mycheckBits.clear();
mycheckBits<<"None"<<"Even"<<"Odd";
ui->checkBit_Sel->addItems(mycheckBits);
ui->checkBit_Sel->setCurrentText("None");
// Initialize data bits
QStringList mydataBits;
mydataBits.clear();
mydataBits<<"5"<<"6"<<"7"<<"8";
ui->dataBit_Sel->addItems(mydataBits);
ui->dataBit_Sel->setCurrentText("8");
ui->hex_Rtn->setChecked(true);// The default setting is 16 Base display
ui->reci_Edit->clear();
}
3.2.h Code
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include <QtSerialPort/QSerialPortInfo>
#include <QtSerialPort/QSerialPort>
QT_BEGIN_NAMESPACE
namespace Ui {
class MainWindow; }
QT_END_NAMESPACE
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
MainWindow(QWidget *parent = nullptr);
~MainWindow();
enum QSerialPort::Parity getParity();
enum QSerialPort::BaudRate getBaud();
enum QSerialPort::StopBits getstopBits();
enum QSerialPort::DataBits getdataBits();
void Init();
// Create a serial port object
QSerialPort *mySerialPort = new QSerialPort();
private:
Ui::MainWindow *ui;
};
#endif // MAINWINDOW_H
4. effect
Use virtual serial port software VSPD Virtual serial port , Use mature software XCOM V2.0( Punctual atomic serial port debugging assistant ) Communicate with your own software , Can be seen clearly , Software receiving and sending are normal .VSPD For software acquisition and installation, please see Tool class – Virtual serial tools

5. reflection
Two ideas ,1.USB It belongs to hot plug device , The system can dynamically detect the insertion and disconnection of equipment , So how to make your software dynamically view the connection status of serial port devices ? actually ,Qt Provides “ interrupt ” Interface , It can be upgraded ;
2. Now it only supports 16 Base send , Support 16 Base number 、ascii Code reception , So can we consider using serial port to transmit Chinese characters ? actually ,Qt Support multiple character sets , Try it .
边栏推荐
- Dernière publication: neo4j Graph Data Science GDS 2.0 et aurads ga
- Object detection -- how to use labelimg annotation tool
- Latest release: neo4j figure data science GDS 2.0 and aurads GA
- In the era of industrial Internet, there is no real center
- Get to know unity3d (project structure, third-party plug-in of probuilder)
- An article thoroughly learns to draw data flow diagrams
- Global exception handling
- GraphAcademy 课程讲解:《Neo4j 图数据科学简介》
- On Monday, I asked the meaning of the | -leaf attribute?
- Wechat applet film and television review and exchange platform system graduation design (1) development outline
猜你喜欢
![[2. merge sort]](/img/60/5e87cffabd91af0155ae681f5bf0ba.png)
[2. merge sort]

fatal error: png++/png. Hpp: no that file or directory

Brief analysis of application source code of neo4j intelligent supply chain

Using hook based on xposed framework

GraphAcademy 课程讲解:《Neo4j 图数据科学基础》

最新发布:Neo4j 图数据科学 GDS 2.0 和 AuraDS GA

EMC Radiation Emission rectification - principle Case Analysis

Zhixiang Jintai rushes to the scientific innovation board: the annual revenue is 39.19 million, the loss is more than 300million, and the proposed fund-raising is 4billion

Asemi Schottky diode 1N5819 parameters, 1N5819 replacement, 1N5819 source

Graphacademy course explanation: introduction to neo4j graph data science
随机推荐
EMC radiation emission rectification - principle case analysis
智翔金泰冲刺科创板:年营收3919万亏损超3亿 拟募资40亿
[7. high precision division]
Get to know unity3d (project structure, third-party plug-in of probuilder)
Wechat applet film and television comment exchange platform system graduation design completion (6) opening defense ppt
FPGA-Xilinx 7系列FPGA DDR3硬件设计规则
Fabric. JS iText set italics manually
B-Tree
Global exception handling
Graphacademy course explanation: Fundamentals of neo4j graph data science
Kubernetes code generator use
[8. One dimensional prefix and]
EMC辐射发射整改-原理案例分析
fatal error: png++/png.hpp: 没有那个文件或目录
Write your own kubernetes controller
[4. high precision addition]
Microblog closes publishing multiple part-time fraud information illegal accounts: how to crack down on data fraud
Technical exploration: 360 digital subjects won the first place in the world in ICDAR OCR competition
【1. 快速排序】
Automated tools - monitoring file changes