int main(..._qt串口通信例程">
赞
踩
如果用qt写程序作为上位机,然后通过和usb和下位机通信的时候,就需要用到qt中的串口通信了。
1).pro 添加:
QT +=serialport
2)主函数 main.cpp 添加:
#include "mywidget.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
myWidget w;
w.show();
return a.exec();
}
3)myWidget.h 添加:
#ifdef WIN32 #pragma execution_character_set("utf-8") #endif #ifndef MYWIDGET_H #define MYWIDGET_H #include <QWidget> #include <QSerialPort> #include <QSerialPortInfo> #include <QDebug> #include <QMessageBox> namespace Ui { class myWidget; } class myWidget : public QWidget { Q_OBJECT public: explicit myWidget(QWidget *parent = 0); ~myWidget(); void initUI(); public slots: void receiveInfo(); private slots: void on_m_OpenPortButton_clicked(); void on_btn_Send_clicked(); private: Ui::myWidget *ui; private: QStringList getPortNameList(); // 获取所有可用的串口列表 QSerialPort* m_serialPort; // 串口类 QStringList m_portNameList; // 端口名列表 private: void sendInfo(char* info,int len); void sendInfo(QString &info); void convertStringToHex(const QString &str, QByteArray &byteData); char convertCharToHex(char ch); }; #endif // MYWIDGET_H
4)myWidget.cpp 添加:
#include "mywidget.h" #include "ui_mywidget.h" myWidget::myWidget(QWidget *parent) : QWidget(parent), ui(new Ui::myWidget) { ui->setupUi(this); m_serialPort = new QSerialPort(); this->setWindowTitle("QSerialPort"); // 设置默认选项 ui->m_OpenPortButton->setText("打开串口"); ui->cBox_PortName->addItems(getPortNameList()); ui->cBox_DataBits->setCurrentIndex(1); ui->cBox_BaudRate->setCurrentIndex(2); } myWidget::~myWidget() { delete ui; m_serialPort->close(); delete m_serialPort; } // 1、获得有效串行端口 QStringList myWidget::getPortNameList() { QStringList m_serialPortName; foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts()) { m_serialPortName << info.portName(); //QMessageBox::information(this,tr("提示"),tr("serialPortName: %1").arg(info.portName()),QMessageBox::Ok); //qDebug()<<"serialPortName:"<<info.portName(); } return m_serialPortName; } // 2、连接、断开 void myWidget::on_m_OpenPortButton_clicked() { if(m_serialPort->isOpen())//如果串口已经打开了 先给他关闭了 { // m_serialPort->flush(); // m_serialPort->clear(); m_serialPort->close(); } else { //当前选择的串口名字 m_serialPort->setPortName(ui->cBox_PortName->currentText()); //用ReadWrite 的模式尝试打开串口 if(!m_serialPort->open(QIODevice::ReadWrite)) { QMessageBox::warning(this,tr("提示"),tr("串口打开失败!"),QMessageBox::Ok); return; } // 串口设置: m_serialPort->setFlowControl(QSerialPort::NoFlowControl); //无流控制 // 1、波特率和读写方向 switch(ui->cBox_BaudRate->currentIndex()) { case 0: m_serialPort->setBaudRate(QSerialPort::Baud2400,QSerialPort::AllDirections); break; case 1: m_serialPort->setBaudRate(QSerialPort::Baud4800,QSerialPort::AllDirections); break; case 2: m_serialPort->setBaudRate(QSerialPort::Baud9600,QSerialPort::AllDirections);//9600 比特率 break; case 3: m_serialPort->setBaudRate(QSerialPort::Baud19200,QSerialPort::AllDirections); break; case 4: m_serialPort->setBaudRate(QSerialPort::Baud57600,QSerialPort::AllDirections); break; case 5: m_serialPort->setBaudRate(QSerialPort::Baud115200,QSerialPort::AllDirections); break; default: break; } // 2、数据位 switch(ui->cBox_DataBits->currentIndex()) { case 0: m_serialPort->setDataBits(QSerialPort::Data6);//6 bit 数据位 break; case 1: m_serialPort->setDataBits(QSerialPort::Data7);//7 bit 数据位 break; case 2: m_serialPort->setDataBits(QSerialPort::Data8);//8 bit 数据位 break; default: break; } // 3、停止位 switch(ui->cBox_StopBits->currentIndex()) { case 0: m_serialPort->setStopBits(QSerialPort::OneStop);//1 bit停止位 break; case 1: m_serialPort->setStopBits(QSerialPort::OneAndHalfStop); //1.5 bit停止位 break; case 2: m_serialPort->setStopBits(QSerialPort::TwoStop); //2 bit break; default: break; } // 4、校验位 switch(ui->cBox_Parity->currentIndex()) { case 0: m_serialPort->setParity(QSerialPort::EvenParity); break; case 1: m_serialPort->setParity(QSerialPort::OddParity); break; default: m_serialPort->setParity(QSerialPort::NoParity); break; } connect(m_serialPort,SIGNAL(readyRead()),this,SLOT(receiveInfo())); } ui->m_OpenPortButton->setText(m_serialPort->isOpen()?tr("关闭串口") : tr("连接串口")); ui->m_OpenPortButton->setStyleSheet(m_serialPort->isOpen()?"color: red;":"color: black;"); } // 3、信息接收 void myWidget::receiveInfo() { QByteArray info = m_serialPort->readAll(); //qDebug()<<"receive info:"<<info; if(!info.isEmpty()) { QString str = ui->textEdit_receive->toPlainText(); str+=tr(info); ui->textEdit_receive->clear(); ui->textEdit_receive->append(str); } info.clear(); // QByteArray hexData = info.toHex(); // //这里面的协议 你们自己定义就行 单片机发什么 代表什么 我们这里简单模拟一下 // if(hexData == "0x10000") // { // //do something // } // else if(hexData == "0x100001") // { // //do something // } } // 4、发送按钮 void myWidget::on_btn_Send_clicked() { m_serialPort->write(ui->textEdit_send->toPlainText().toLatin1()); } //写两个函数 向单片机发送数据: // 信息发送函数一: void myWidget::sendInfo(char* info,int len) { for(int i=0; i<len; ++i) { printf("0x%x\n", info[i]); } m_serialPort->write(info,len);//这句是真正的给单片机发数据 用到的是QIODevice::write 具体可以看文档 } // 信息发送函数二: void myWidget::sendInfo(QString &info) { QByteArray sendBuf; if (info.contains(" ")) { info.replace(QString(" "),QString(""));//我这里是把空格去掉,根据你们定的协议来 } qDebug()<<"Write to serial: "<<info; convertStringToHex(info, sendBuf); //把QString 转换 为 hex m_serialPort->write(sendBuf); //这句是真正的给单片机发数据 用到的是QIODevice::write 具体可以看文档 } // 基本和单片机交互数据都是16进制的 // Qstring 转为16进制的函数 void myWidget::convertStringToHex(const QString &str, QByteArray &byteData) { int hexdata,lowhexdata; int hexdatalen = 0; int len = str.length(); byteData.resize(len/2); char lstr,hstr; for(int i=0; i<len; ) { //char lstr, hstr=str[i].toLatin1(); if(hstr == ' ') { i++; continue; } i++; if(i >= len) break; lstr = str[i].toLatin1(); hexdata = convertCharToHex(hstr); lowhexdata = convertCharToHex(lstr); if((hexdata == 16) || (lowhexdata == 16)) break; else hexdata = hexdata*16+lowhexdata; i++; byteData[hexdatalen] = (char)hexdata; hexdatalen++; } byteData.resize(hexdatalen); } //另一个 函数 char 转为 16进制 char myWidget::convertCharToHex(char ch) { /* 0x30等于十进制的48,48也是0的ASCII值,, 1-9的ASCII值是49-57,,所以某一个值-0x30,, 就是将字符0-9转换为0-9 */ if((ch >= '0') && (ch <= '9')) return ch-0x30; else if((ch >= 'A') && (ch <= 'F')) return ch-'A'+10; else if((ch >= 'a') && (ch <= 'f')) return ch-'a'+10; else return (-1); }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。