QT上位机串口+STM32单片机项目

第一个自己的上位机小项目,嘿嘿,还是有些成绩感的。

目录

1.先看QT上位机部分

1.首先写一个页面

2.mainwindow.cpp主要函数。

2.form.cpp主要函数

3.STM32部分

1.main函数

3.QT完整代码

1.shangwei.pro

2.form.h

3.mainwindow.h

4.form.cpp

5.main.cpp

6.mainwindow.cpp


 

1.先看QT上位机部分

1.首先写一个页面

QT上位机串口+STM32单片机项目_第1张图片

 点击隐藏BOSS后弹出第二个页面

QT上位机串口+STM32单片机项目_第2张图片

 因为我的语音模块里面是周杰伦反方向的钟,所以我把歌词加进去了,你可以自由更改;

要想QT实现串口,需要两个头文件,加到mainwindow.cpp中

#include          // 提供访问串口的功能
#include      // 提供系统中存在的串口信息

此时会报错,因为工程文件(shangwei.pro)还需要添加

QT       +=serialport

此时就可以正常使用头文件内部的函数了。首先我们要配置串口。

2.mainwindow.cpp主要函数。

配置串口函数:

void MainWindow::on_pushButton_5_clicked()  //打开,关闭
   {    //是OPEN时,代表没有打开串口
        if(ui->pushButton_5->text() == QString("OPEN")) {
            //检查串口是否被占用,再次检查一遍

            //串口配置
            //清空缓冲区
            serial = new QSerialPort;                       //申请内存,并设置父对象
            // 获取计算机中有效的端口号,然后将端口号的名称给端口选择控件
            //QSerialPortInfo::availablePorts()的返回值为QList 每一个可用端口组成的容器
            foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
            {
                serial->setPort(info);
                if(serial->open(QIODevice::ReadWrite))      // 以读写方式打开串口
                {
                                        // 在对象中设置串口
                    qDebug() << "串口打开成功";
                    serial->close();                        // 关闭
                } else
                {
                    qDebug() << "串口打开失败,请重试";
                }
            }

            //设置波特率
            serial->setBaudRate( static_cast (ui->comboBox_2->currentText().toInt()) );
            //设置停止位
            serial->setStopBits( static_cast (ui->comboBox_3->currentText().toInt()));
            //设置数据位
            serial->setDataBits( static_cast (ui->comboBox_6->currentText().toInt()) );
            //设置校验
            serial->setParity  ( static_cast   (ui->comboBox_4->currentIndex()));
            //设置流控
            serial->setFlowControl(QSerialPort::NoFlowControl);


            //改变按钮上的文本
            ui->pushButton_5->setText("CLOSE");
            //输出通道的端口名字
            ui->lineEdit->setText(serial->portName());

            isSerialOpen = serial->open(QIODevice::ReadWrite);
            serial->setDataTerminalReady(true);
            serial->setReadBufferSize(3);
            if (!isSerialOpen) {
                 qDebug()<< QString("Failed to open serial port:")  << serial->errorString();
                 serial->clearError();

              }else {
                    qDebug()<< QString("The serial port is open: ") ;

              }

       }else{

             ui->pushButton_5->setText("OPEN");
             serial->close();
        }

}

我这个波特率,停止位等串口设置依赖于窗口的选择;

QT上位机串口+STM32单片机项目_第3张图片

 选择参数函数:

void MainWindow::initConfig() {


//        //创建对象,并建立信号槽
        serial = new QSerialPort(this);
//        //读函数的信号槽
        QObject::connect(serial, &QSerialPort::readyRead, this, &MainWindow::serial_readyRead);
        //添加波特率
        QStringList baudList;
        baudList << "115200" << "57600" << "9600" ;
        ui->comboBox_2->addItems(baudList);
        ui->comboBox_2->setCurrentText("115200");

        //添加停止位
        QStringList baudList1;
        baudList1 << "0.5" << "1" << "1.5"<<"2" ;
        ui->comboBox_3->addItems(baudList1);
        ui->comboBox_3->setCurrentText("1");

        //添加数据位
        QStringList baudList2;
        baudList2 << "8" << "9"  ;
        ui->comboBox_6->addItems(baudList2);
        ui->comboBox_6->setCurrentText("8");

        //奇偶校验
        QStringList baudList3;
        baudList3 << "NO" << "EVEN"  ;
        ui->comboBox_4->addItems(baudList3);
        ui->comboBox_4->setCurrentText("NO");

}

配置完串口函数后需要书写发串口发送数据和接受数据;

发送数据:

void MainWindow::on_pushButton_3_clicked() //发送
{
    if(ui->pushButton_5->text() == QString("CLOSE")) {

            QByteArray data = ui->textEdit_2->toPlainText().toUtf8();
            serial->write(data);
            qDebug() <textEdit->append("请打开串口!!!!!");

    }

}

接收函数:

void MainWindow::serial_readyRead()
{

       //从接收缓冲区中读取数据
        QByteArray buffer = serial->readAll();
        //从界面中读取以前收到的数据
        QString recv = ui->textEdit->toPlainText();
        recv += QString(buffer);
        //清空以前的显示
        ui->textEdit->clear();
        //重新显示
        ui->textEdit->append(recv);
         qDebug() <

清空函数:

void MainWindow::on_pushButton_2_clicked()  //清除  接收
{
    //清除显示
        ui->textEdit->clear();
}

主要函数就这么多,后面会给出完整代码;

2.form.cpp主要函数

其实和上一个函数类型差不多,只是利用槽函数进行发送数据而已

初始化函数:

void Form::on_pushButton_10_clicked()
{
    if(ui->pushButton_10->text() == QString("打开串口")) {

        //串口配置
        //清空缓冲区
        serial = new QSerialPort;                       //申请内存,并设置父对象
        // 获取计算机中有效的端口号,然后将端口号的名称给端口选择控件
        //QSerialPortInfo::availablePorts()的返回值为QList 每一个可用端口组成的容器
        foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
        {
            serial->setPort(info);
            if(serial->open(QIODevice::ReadWrite))      // 以读写方式打开串口
            {
                                    // 在对象中设置串口
                qDebug() << "串口打开成功";
                serial->close();                        // 关闭
            } else
            {
                qDebug() << "串口打开失败,请重试";
            }
        }

        // 参数配置,波特率V
        serial->setBaudRate(QSerialPort::Baud115200);
        // 校验位,校验默认选择无
        serial->setParity(QSerialPort::NoParity);
        // 数据位,数据位默认选择8位
        serial->setDataBits(QSerialPort::Data8);
        // 停止位,停止位默认选择1位
        serial->setStopBits(QSerialPort::OneStop);
        // 控制流,默认选择无
        serial->setFlowControl(QSerialPort::NoFlowControl);


        //改变按钮上的文本
        ui->pushButton_10->setText("关闭串口");
        //输出通道的端口名字


        bool isSerialOpen = serial->open(QIODevice::ReadWrite);
        serial->setDataTerminalReady(true);
        serial->setReadBufferSize(3);
        if (!isSerialOpen) {
             qDebug()<< QString("Failed to open serial port:")  << serial->errorString();
             serial->clearError();
              configSetEnable1(false);
          }else {
                qDebug()<< QString("The serial port is open: ") ;
                configSetEnable1(true);

          }

   }else{
          configSetEnable1(false);
         ui->pushButton_10->setText("打开串口");
         serial->close();
    }
}

发送函数:

void Form::on_pushButton_13_clicked()
{
    QByteArray data ="55";
    serial->write(data);
    qDebug() <

我只列举了主要函数,后面会给出完整的代码。

3.STM32部分

我使用的是信盈达的STM32F103ZET6,JQ8900N-16P 语音模块,MQ135模块,MQ2模块以及DHT11温湿度模块和一块LED屏幕。

STM32部分代码太多,后面会打包成压缩文件,先看一下主函数。

1.main函数

#include "stm32f10x.h"
#include "stm32f10x_conf.h"
#include 
#include 
#include "delay.h"
#include "usart.h"
#include "sys.h"
#include "led.h"
#include "key.h"
#include "relay.h"
#include "beep.h"
#include "time.h"
#include "lcd_gui.h"
#include "pic.h"
#include "touch.h"
#include "dht11.h"
#include "adc.h"


int main()
{
    
    u8 T,H;
	int num=0,i=0,X=0,Y=0;
	u8 ledflag =1;
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
	Delay_Init();                                                  
	USART_Config(115200); 
    BEEPGpioInit();	
	LEDInit();
	KEYGpioInit();
	RELAYInit();
	LCD_Init();
    Adc_Init();	
    Voice_Config(9600);
    int count=5;
	Set_Song_Volume(5);
    
    
    
    
       
        int bo=2;
        char MQ[11]={'#','M','Q','1','3','5',':'};
        char WEN[5];
        char SHI[6];
        char MQ22[10]={'#','M','Q','2',':'};
        SHI[5]='\0';
        WEN[4]='\0';
		WEN[0]='T';
        SHI[0]='H';
        WEN[1]=':';
        SHI[1]=':';
        MQ[10]='\0';
        MQ22[9]='\0';
        
     
     

//	LCD_Dis_String(0,0,"棒打林渊!",0x0000, 0xffff, 2,0);
//	LCD_Dis_String(0,32,"Hello Tomorrow",0x0000, 0xffff, 2,0);
	while(1)
		{
            
            if(uart1_finish_flage)
               {
                  
 
                 if(strcmp(USART1_Rcv_Buff,"11") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                     //处理数据 USART1_Rcv_Buff
                     LED1_ON;
                     //处理结束将数组进行清空
       
                     LCD_Dis_String(0,0,"LED1_ON",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"12") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED1_OFF;
                      LCD_Dis_String(0,0,"LED1_OFF",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"21") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED2_ON;
                      LCD_Dis_String(0,0,"LED2_ON",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"22") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED2_OFF;
                      LCD_Dis_String(0,0,"LED2_OFF",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"31") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED3_ON;
                      LCD_Dis_String(0,0,"LED3_ON",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"32") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED3_OFF;
                      LCD_Dis_String(0,0,"LED3_OFF",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"41") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED4_ON;
                      LCD_Dis_String(0,0,"LED4_ON",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"42") == 0){
                      LCD_Clear(0,239,0,319,0xffff);
                      LED4_OFF;
                      LCD_Dis_String(0,0,"LED4_OFF",0x0000, 0xffff, 2,0);
               
                 }else if(strcmp(USART1_Rcv_Buff,"55") == 0){
                     
                        Set_Song_Volume(count++);
                 }else if(strcmp(USART1_Rcv_Buff,"66") == 0){
                     
                        Set_Song_Volume(count--);
                 }else if(strcmp(USART1_Rcv_Buff,"77") == 0){
                     
                      Appoint_Song_Name("00001");
                 }else if(strcmp(USART1_Rcv_Buff,"88") == 0){
                     
                     Stop_Song();
                 }else if(strcmp(USART1_Rcv_Buff,"99") == 0){
                     
                    Xiayi_Song();
                 }else if(strcmp(USART1_Rcv_Buff,"98") == 0){
                     
                     Shangyi_Song();
                     
                 }else if(strcmp(USART1_Rcv_Buff,"13") == 0){
                     
                     bo=1;
                 }else if(strcmp(USART1_Rcv_Buff,"14") == 0){
                     
                     BEEP_ON;
                 }else if(strcmp(USART1_Rcv_Buff,"15") == 0){
                     
                     BEEP_OFF;
                 }else if(strcmp(USART1_Rcv_Buff,"16") == 0){
                     
                     bo=0;
                 }
                 
                 
                 memset(USART1_Rcv_Buff,0,sizeof(USART1_Rcv_Buff));
                 uart1_count = 0;
                 uart1_finish_flage =0;
             }
               
             
                 if(bo==1){
                     dht11_read_ht(&T,&H);
                     LCD_Clear(0,239,0,319,0xffff);

//                     if(H>80)BEEP_ON ;else BEEP_OFF;
                     WEN[2]=T/10+'0';
                     WEN[3]=T%10+'0';
                    
                     SHI[2]=H/100+'0';
                     SHI[3]=H/10%10+'0';
                     SHI[4]=H%10+'0';
                    
                     int m=ADC_Val_Disp(Mq135);
                     int m2=ADC_Val_Disp(Mq2);
                     MQ[7]=m/100+'0';
                     MQ[8]=m/10%10+'0';
                     MQ[9]=m%10+'0';
                     
                     MQ22[5]=m2/1000+'0';
                     MQ22[6]=m2/100%10+'0';
                     MQ22[7]=m2/10%10+'0';
                     MQ22[8]=m2%10+'0';
                     
                     LCD_Clear(0,239,0,319,0xffff);
                     LCD_Dis_String(0,0,WEN,0x0000, 0xffff, 2,0);
                     LCD_Dis_String(0,32,SHI,0x0000, 0xffff, 2,0);
                     LCD_Dis_String(0,64,MQ,0x0000, 0xffff, 2,0);
                     LCD_Dis_String(0,32*3,MQ22,0x0000, 0xffff, 2,0);
               
                     Delay_ms(500);
                   
                     
                 }else if(bo==0){
                      LCD_Clear(0,239,0,319,0xffff);
                      bo=2;
                 }
                
                 
               }
           
		return 0;
}



先通过QT给单片机发送指令,单片机收到后会判断是哪一种指令,实行相应的操作。

3.QT完整代码

我的文件是这样的

QT上位机串口+STM32单片机项目_第4张图片

1.shangwei.pro

QT       += core gui

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

CONFIG += c++11

# The following define makes your compiler emit warnings if you use
# any Qt feature that has been marked deprecated (the exact warnings
# depend on your compiler). Please consult the documentation of the
# deprecated API in order to know how to port your code away from it.
DEFINES += QT_DEPRECATED_WARNINGS

# You can also make your code fail to compile if it uses deprecated APIs.
# In order to do so, uncomment the following line.
# You can also select to disable deprecated APIs only up to a certain version of Qt.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000    # disables all the APIs deprecated before Qt 6.0.0

SOURCES += \
    form.cpp \
    main.cpp \
    mainwindow.cpp

HEADERS += \
    form.h \
    mainwindow.h

FORMS += \
    form.ui \
    mainwindow.ui
#串口通信
QT       +=serialport

# Default rules for deployment.
qnx: target.path = /tmp/$${TARGET}/bin
else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target

RESOURCES += \
    rec.qrc

2.form.h

#ifndef FORM_H
#define FORM_H

#include 
#include          // 提供访问串口的功能
#include      // 提供系统中存在的串口信息

namespace Ui {
class Form;
}

class Form : public QWidget
{
    Q_OBJECT

public:
    explicit Form(QWidget *parent = nullptr);
    ~Form();

private slots:
    void on_pushButton_clicked();

    void on_pushButton_9_clicked();

    void on_pushButton_2_clicked();

    void on_pushButton_3_clicked();

    void on_pushButton_4_clicked();

    void on_pushButton_5_clicked();

    void on_pushButton_6_clicked();

    void on_pushButton_7_clicked();

    void on_pushButton_8_clicked();

    void on_pushButton_10_clicked();

    void on_pushButton_13_clicked();

    void on_pushButton_14_clicked();

    void on_pushButton_11_clicked();

    void on_pushButton_12_clicked();

    void on_pushButton_16_clicked();

    void on_pushButton_15_clicked();

    void on_pushButton_19_clicked();

    void on_pushButton_20_clicked();

    void on_pushButton_21_clicked();

    void on_pushButton_22_clicked();

private:
    Ui::Form *ui;
    QSerialPort     *serial;              //定义全局的串口对象
    void configSetEnable1(bool b1);


};

#endif // FORM_H

3.mainwindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include 
//串口通信
#include "form.h"
#include          // 提供访问串口的功能
#include      // 提供系统中存在的串口信息


QT_BEGIN_NAMESPACE
namespace Ui { class MainWindow; }
QT_END_NAMESPACE

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    MainWindow(QWidget *parent = nullptr);
    ~MainWindow();

private slots:
    void on_pushButton_clicked();

    void on_pushButton_2_clicked();

    void on_pushButton_3_clicked();

    void on_pushButton_4_clicked();

    void on_pushButton_5_clicked();


private:
    Ui::MainWindow *ui;
    void SerialPortInit(void);
    void initConfig();
    void serial_readyRead();
    void configSetEnable(bool b);
    //串口变量↓
    QSerialPort     *serial;              //定义全局的串口对象
    QStringList     baudList;             //波特率
    QStringList     parityList;           //校验位
    QStringList     dataBitsList;         //数据位
    QStringList     stopBitsList;         //停止位
    QStringList     flowControlList;      //控制流
    bool isSerialOpen;
    Form *form;
};
#endif // MAINWINDOW_H

4.form.cpp

#include "form.h"
#include "ui_form.h"
#include 
#include "mainwindow.h"
#include "QLabel"
#include "QMovie"
Form::Form(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::Form)
{
    ui->setupUi(this);
     configSetEnable1(false);
     QMovie *movie = new QMovie(":/new/prefix1/image/83686B74CD2AF08B32BC013618CD188F.gif");
     ui->label->setMovie(movie);
     movie->start();

     connect(ui->pushButton_17,&QPushButton::clicked,this,[=](){
         movie->stop();
     });
     connect(ui->pushButton_18,&QPushButton::clicked,this,[=](){
         movie->start();
     });

}

Form::~Form()
{
    delete ui;
}

void Form::on_pushButton_clicked()   //点亮LED1
{
            QByteArray data ="11";
            serial->write(data);
            qDebug() <close();
    MainWindow *w=new MainWindow;
    w->show();
    this->close();
}

void Form::on_pushButton_2_clicked()   //熄灭LED1
{
    QByteArray data ="12";
    serial->write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <pushButton_10->text() == QString("打开串口")) {

        //串口配置
        //清空缓冲区
        serial = new QSerialPort;                       //申请内存,并设置父对象
        // 获取计算机中有效的端口号,然后将端口号的名称给端口选择控件
        //QSerialPortInfo::availablePorts()的返回值为QList 每一个可用端口组成的容器
        foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
        {
            serial->setPort(info);
            if(serial->open(QIODevice::ReadWrite))      // 以读写方式打开串口
            {
                                    // 在对象中设置串口
                qDebug() << "串口打开成功";
                serial->close();                        // 关闭
            } else
            {
                qDebug() << "串口打开失败,请重试";
            }
        }

        // 参数配置,波特率V
        serial->setBaudRate(QSerialPort::Baud115200);
        // 校验位,校验默认选择无
        serial->setParity(QSerialPort::NoParity);
        // 数据位,数据位默认选择8位
        serial->setDataBits(QSerialPort::Data8);
        // 停止位,停止位默认选择1位
        serial->setStopBits(QSerialPort::OneStop);
        // 控制流,默认选择无
        serial->setFlowControl(QSerialPort::NoFlowControl);


        //改变按钮上的文本
        ui->pushButton_10->setText("关闭串口");
        //输出通道的端口名字


        bool isSerialOpen = serial->open(QIODevice::ReadWrite);
        serial->setDataTerminalReady(true);
        serial->setReadBufferSize(3);
        if (!isSerialOpen) {
             qDebug()<< QString("Failed to open serial port:")  << serial->errorString();
             serial->clearError();
              configSetEnable1(false);
          }else {
                qDebug()<< QString("The serial port is open: ") ;
                configSetEnable1(true);

          }

   }else{
          configSetEnable1(false);
         ui->pushButton_10->setText("打开串口");
         serial->close();
    }
}

void Form::on_pushButton_13_clicked()
{
    QByteArray data ="55";
    serial->write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <pushButton->setEnabled(b1);
    ui->pushButton_2->setEnabled(b1);
    ui->pushButton_3->setEnabled(b1);
    ui->pushButton_4->setEnabled(b1);
    ui->pushButton_5->setEnabled(b1);
    ui->pushButton_6->setEnabled(b1);
    ui->pushButton_7->setEnabled(b1);
    ui->pushButton_8->setEnabled(b1);
    ui->pushButton_11->setEnabled(b1);
    ui->pushButton_12->setEnabled(b1);
    ui->pushButton_13->setEnabled(b1);
    ui->pushButton_14->setEnabled(b1);
    ui->pushButton_16->setEnabled(b1);
    ui->pushButton_15->setEnabled(b1);
    ui->pushButton_19->setEnabled(b1);
    ui->pushButton_20->setEnabled(b1);
    ui->pushButton_21->setEnabled(b1);
    ui->pushButton_22->setEnabled(b1);

   // ui->pushButton_9->setEnabled(b1);

}

void Form::on_pushButton_19_clicked()   //启动蜂鸣器
{
    QByteArray data ="14";
    serial->write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <write(data);
    qDebug() <

5.main.cpp

#include "mainwindow.h"

#include 

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    MainWindow w;
    w.show();
    return a.exec();
}

6.mainwindow.cpp

#include "mainwindow.h"
#include "ui_mainwindow.h"
//串口通信
#include 
#include 


MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    initConfig();
    form=new Form;
    QObject::connect(serial, &QSerialPort::readyRead, this, &MainWindow::serial_readyRead);
    //固定大小

}

MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::SerialPortInit()
{
    serial = new QSerialPort;                       //申请内存,并设置父对象

    // 获取计算机中有效的端口号,然后将端口号的名称给端口选择控件
    //QSerialPortInfo::availablePorts()的返回值为QList 每一个可用端口组成的容器
    foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
    {
        serial->setPort(info);
        if(serial->open(QIODevice::ReadWrite))      // 以读写方式打开串口
        {
                                // 在对象中设置串口
            qDebug() << "串口打开成功";
            serial->close();                        // 关闭
        } else
        {
            qDebug() << "串口打开失败,请重试";
        }
    }

    // 参数配置,波特率V
    serial->setBaudRate(QSerialPort::Baud19200);
    // 校验位,校验默认选择无
    serial->setParity(QSerialPort::NoParity);
    // 数据位,数据位默认选择8位
    serial->setDataBits(QSerialPort::Data8);
    // 停止位,停止位默认选择1位
    serial->setStopBits(QSerialPort::OneStop);
    // 控制流,默认选择无
    serial->setFlowControl(QSerialPort::NoFlowControl);

}

void MainWindow::on_pushButton_clicked()
{
   form->show();
   serial->close();
   this->close();
}

void MainWindow::on_pushButton_2_clicked()  //清除  接收
{
    //清除显示
        ui->textEdit->clear();
}

void MainWindow::on_pushButton_3_clicked() //发送
{
    if(ui->pushButton_5->text() == QString("CLOSE")) {

            QByteArray data = ui->textEdit_2->toPlainText().toUtf8();
            serial->write(data);
            qDebug() <textEdit->append("请打开串口!!!!!");

    }

}

void MainWindow::on_pushButton_4_clicked() //清除发送
{
    //清除显示
    ui->textEdit_2->clear();
}

void MainWindow::on_pushButton_5_clicked()  //打开,关闭
   {    //是OPEN时,代表没有打开串口
        if(ui->pushButton_5->text() == QString("OPEN")) {
            //检查串口是否被占用,再次检查一遍

            //串口配置
            //清空缓冲区
            serial = new QSerialPort;                       //申请内存,并设置父对象
            // 获取计算机中有效的端口号,然后将端口号的名称给端口选择控件
            //QSerialPortInfo::availablePorts()的返回值为QList 每一个可用端口组成的容器
            foreach(const QSerialPortInfo &info,QSerialPortInfo::availablePorts())
            {
                serial->setPort(info);
                if(serial->open(QIODevice::ReadWrite))      // 以读写方式打开串口
                {
                                        // 在对象中设置串口
                    qDebug() << "串口打开成功";
                    serial->close();                        // 关闭
                } else
                {
                    qDebug() << "串口打开失败,请重试";
                }
            }

            //设置波特率
            serial->setBaudRate( static_cast (ui->comboBox_2->currentText().toInt()) );
            //设置停止位
            serial->setStopBits( static_cast (ui->comboBox_3->currentText().toInt()));
            //设置数据位
            serial->setDataBits( static_cast (ui->comboBox_6->currentText().toInt()) );
            //设置校验
            serial->setParity  ( static_cast   (ui->comboBox_4->currentIndex()));
            //设置流控
            serial->setFlowControl(QSerialPort::NoFlowControl);


            //改变按钮上的文本
            ui->pushButton_5->setText("CLOSE");
            //输出通道的端口名字
            ui->lineEdit->setText(serial->portName());

            isSerialOpen = serial->open(QIODevice::ReadWrite);
            serial->setDataTerminalReady(true);
            serial->setReadBufferSize(3);
            if (!isSerialOpen) {
                 qDebug()<< QString("Failed to open serial port:")  << serial->errorString();
                 serial->clearError();

              }else {
                    qDebug()<< QString("The serial port is open: ") ;

              }

       }else{

             ui->pushButton_5->setText("OPEN");
             serial->close();
        }

}

void MainWindow::initConfig() {


//        //创建对象,并建立信号槽
        serial = new QSerialPort(this);
//        //读函数的信号槽
        QObject::connect(serial, &QSerialPort::readyRead, this, &MainWindow::serial_readyRead);
        //添加波特率
        QStringList baudList;
        baudList << "115200" << "57600" << "9600" ;
        ui->comboBox_2->addItems(baudList);
        ui->comboBox_2->setCurrentText("115200");

        //添加停止位
        QStringList baudList1;
        baudList1 << "0.5" << "1" << "1.5"<<"2" ;
        ui->comboBox_3->addItems(baudList1);
        ui->comboBox_3->setCurrentText("1");

        //添加数据位
        QStringList baudList2;
        baudList2 << "8" << "9"  ;
        ui->comboBox_6->addItems(baudList2);
        ui->comboBox_6->setCurrentText("8");

        //奇偶校验
        QStringList baudList3;
        baudList3 << "NO" << "EVEN"  ;
        ui->comboBox_4->addItems(baudList3);
        ui->comboBox_4->setCurrentText("NO");

}

void MainWindow::serial_readyRead()
{

       //从接收缓冲区中读取数据
        QByteArray buffer = serial->readAll();
        //从界面中读取以前收到的数据
        QString recv = ui->textEdit->toPlainText();
        recv += QString(buffer);
        //清空以前的显示
        ui->textEdit->clear();
        //重新显示
        ui->textEdit->append(recv);
         qDebug() <comboBox_2->setEnabled(b);
//    ui->comboBox_3->setEnabled(b);
//    ui->comboBox_6->setEnabled(b);
//    ui->comboBox_4->setEnabled(b);

//    //
//    ui->pushButton_3->setEnabled(!b);
}

4.STM32完整代码

代码太多,后面会打包成压缩文件。

文件包

5.实现效果

实现效果就是和按钮名字相同,电脑点击播放音乐单片机会播放音乐,点击点亮LED1,LED1会点亮。点击刷新数据,LCD会显示收集的温湿度数据和MQ135数据,以及MQ2的数据。

你可能感兴趣的:(qt,开发语言,单片机,stm32)