stm32蓝牙模块通过手机和电脑双向通信

这篇具有很好参考价值的文章主要介绍了stm32蓝牙模块通过手机和电脑双向通信。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

只需将蓝牙连到单片机上,使用usart3(PB10、PB11)作为蓝牙和单片机的数据传输,而电脑的收发数据要是用usart1(PA9、PA10),将数据存入数组中,从而在串口助手中打印值

 1.下面是usart.c文件,将io口和串口初始化,并且加入中断(其中电脑发送时,所用的中断需要回车换行,正常情况下,直接数据存入寄存器,将数据存放在数组中(参考下面usart3的中断))

#include "sys.h"
#include "usart.h"      


//加入以下代码,支持printf函数,而不需要选择use MicroLIB      
#if 1
#pragma import(__use_no_semihosting)             
//标准库需要的支持函数                 
struct __FILE 

    int handle; 

}; 

FILE __stdout;       
//定义_sys_exit()以避免使用半主机模式    
void _sys_exit(int x) 

    x = x; 

//重定义fputc函数 
int fputc(int ch, FILE *f)
{      
    while((USART1->SR&0X40)==0);//循环发送,直到发送完毕   
    USART1->DR = (u8) ch;      
    return ch;
}
#endif 

 
 
#if EN_USART1_RX   //如果使能了接收
u8 USART_RX_BUF[USART_REC_LEN]; 
u8 USART3_RX_BUF[USART_REC_LEN];
//接收缓冲,最大USART_REC_LEN个字节.
//接收状态
//bit15,    接收完成标志
//bit14,    接收到0x0d
//bit13~0,    接收到的有效字节数目
u16 USART_RX_STA=0;
u16 USART3_RX_STA=0; 
//接收状态标记      
  /*1、使能对应串口使用的时钟
2、对应GPIO配置
3、中断配置(中断通道 优先级)
4、串口相关参数配置(波特率 数据位 停止位 等)
5、设置使用的中断
6、使能串口函数
*/


void uart1_init(u32 bound){
    //GPIO端口设置
    GPIO_InitTypeDef GPIO_InitStructure;
    USART_InitTypeDef USART_InitStructure;
    NVIC_InitTypeDef NVIC_InitStructure;
    //打开GPIOA时钟和串口1时钟
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_USART1,ENABLE);
    //配置PA.10复用推挽输出
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
    GPIO_Init(GPIOA,&GPIO_InitStructure);
    //配置PA.9浮空输入
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
    GPIO_Init(GPIOA,&GPIO_InitStructure);
    //中断参数配置
    NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02;在这里存在两个优先级,要区分不能一样
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);    //根据指定的参数初始化VIC寄存器
    //串口参数配置
    USART_InitStructure.USART_BaudRate = bound;
    USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//无硬件控制
    USART_InitStructure.USART_Mode = USART_Mode_Rx|USART_Mode_Tx;//收发模式
    USART_InitStructure.USART_Parity = USART_Parity_No;//无奇偶校验
    USART_InitStructure.USART_StopBits = USART_StopBits_1;//1个停止位
    USART_InitStructure.USART_WordLength = USART_WordLength_8b;//8位数据位
    USART_Init(USART1,&USART_InitStructure);
    
    USART_ITConfig(USART1,USART_IT_RXNE,ENABLE);
    USART_Cmd(USART1,ENABLE);
}

 

        usart1的中断服务函数过程,当接收到从电脑发过来的数据,把接收到的数据保存在 USART_RX_BUF 中,同时在接收状态寄存器(USART_RX_STA)中计数接收到的有效数据个数,当收到回车(回车的表示由 2 个字节组成:0X0D 和 0X0A)的第一个字节 0X0D 时,计数器将不再增加,等待0X0A 的到来,而如果 0X0A 没有来到,则认为这次接收失败,重新开始下一次接收。如果顺利接收到 0X0A,则标记 USART_RX_STA 的第 15 位,这样完成一次接收,并等待该位被其他程序清除,从而开始下一次的接收,而如果迟迟没有收到 0X0D,那么在接收数据超过 USART_REC_LEN 的时候,则会丢弃前面的数据,重新接收。

当接收到从电脑发过来的数据,把接收到的数据保存在 USART_RX_BUF 中,同时在接收状态寄存器(USART_RX_STA)中计数接收到的有效数据个数,当收到回车(回车的表示由 2 个字节组成:0X0D 和 0X0A)的第一个字节 0X0D 时,计数器将不再增加,等待0X0A 的到来,而如果 0X0A 没有来到,则认为这次接收失败,重新开始下一次接收。如果顺利接收到 0X0A,则标记 USART_RX_STA 的第 15 位,这样完成一次接收,并等待该位被其他程序清除,从而开始下一次的接收,而如果迟迟没有收到 0X0D,那么在接收数据超过 USART_REC_LEN 的时候,则会丢弃前面的数据,重新接收。

void USART1_IRQHandler(void)                    //串口1中断服务程序
{
    u8 Res;
    if(USART_GetITStatus(USART1,USART_IT_RXNE) == SET) //接收标志位是否为1
    {

        Res = USART1->DR;//Res = USART_ReceiveData(USART1)
        if((USART_RX_STA&0x8000) != 1) //未接收完成
        {
            if(USART_RX_STA & 0x4000) //接收0x0D完成 等待0x0A到来
            {
                if(Res == 0x0A)   //如果接收到0x0A 接收完成标志位置1
                {
                    USART_RX_STA |= 0x8000;
                    USART_ClearITPendingBit(USART1,USART_IT_RXNE);
                }
                else                //接收失败 重新接收
                    USART_RX_STA = 0;
            }
            else
            {
                if(Res == 0x0D)  //接收到的数据是否为0x0D
                    USART_RX_STA |= 0x4000; //位14置1
                else //非0x0D 0x0A这两个字符
                {
                    USART_RX_BUF[USART_RX_STA&0x3FFF] = Res; //把数据给数组
                    USART_RX_STA++;                            //数组下标增加
                    if(USART_RX_STA>USART_REC_LEN-1)
                        USART_RX_STA=0;//接收数据错误,重新开始接收    
                }
            }
        }
        
    }

void uart3_init(u32 bound)
    {
    //GPIO端口设置
     GPIO_InitTypeDef GPIO_InitStructure;
     USART_InitTypeDef USART_InitStructure;        
     NVIC_InitTypeDef NVIC_InitStructure;
    //打开GPIOA时钟和串口1时钟
        RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART3,ENABLE);
        RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
    //配置PB11复用推挽输出
     GPIO_InitStructure.GPIO_Pin=GPIO_Pin_11;
     GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
     GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IN_FLOATING;
     GPIO_Init(GPIOB,&GPIO_InitStructure);
     //配置PB10浮空输入
     GPIO_InitStructure.GPIO_Pin=GPIO_Pin_10;
     GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
     GPIO_InitStructure.GPIO_Mode=GPIO_Mode_AF_PP;
     GPIO_Init(GPIOB,&GPIO_InitStructure);    
        //中断参数配置
     NVIC_InitStructure.NVIC_IRQChannel=USART3_IRQn;
     NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0x02;
     NVIC_InitStructure.NVIC_IRQChannelSubPriority=0x03;
     NVIC_InitStructure.NVIC_IRQChannelCmd=ENABLE;
     NVIC_Init (&NVIC_InitStructure);
     //串口参数配置
     USART_InitStructure.USART_BaudRate = bound;
     USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//无硬件控制
     USART_InitStructure.USART_Mode = USART_Mode_Rx|USART_Mode_Tx;//收发模式
     USART_InitStructure.USART_Parity = USART_Parity_No;//无奇偶校验
     USART_InitStructure.USART_StopBits = USART_StopBits_1;//1个停止位
     USART_InitStructure.USART_WordLength = USART_WordLength_8b;//8位数据位
     USART_Init(USART3,&USART_InitStructure);
     
     USART_ITConfig(USART3,USART_IT_RXNE,ENABLE);
     USART_Cmd(USART3,ENABLE);
 }
u8 Flag = 0;    这里的flag作为一个标志位,用于打印在串口助手
void USART3_IRQHandler(void)                    //串口3中断服务程序
{
    u8 Res;
    if(USART_GetITStatus(USART3,USART_IT_RXNE) == SET) //接收标志位是否为1
    {
        USART_ClearITPendingBit(USART3,USART_IT_RXNE);
        Res = USART3->DR;//Res = USART_ReceiveData(USART3)
        USART3_RX_BUF[USART_RX_STA&0x3FFF] = Res; //把数据给数组
        USART3_RX_STA++;    
        Flag = 1;
        
    }
}
#endif    

 2.其次在.h文件中声明

#ifndef __USART_H
#define __USART_H
#include "stdio.h"    
#include "sys.h" 

#define USART_REC_LEN              200      //定义最大接收字节数 200
#define EN_USART1_RX             1        //使能(1)/禁止(0)串口1接收
          
extern u8  USART_RX_BUF[USART_REC_LEN]; //接收缓冲,最大USART_REC_LEN个字节.末字节为换行符 
extern u16 USART_RX_STA;                 //接收状态标记    
extern u8  USART3_RX_BUF[USART_REC_LEN]; //接收缓冲,最大USART_REC_LEN个字节.末字节为换行符 
extern u16 USART3_RX_STA; 
extern u8 Flag;
void uart3_init(u32 bound);
void uart1_init(u32 bound);
#endif

3.主函数程序,运行

int main()
{
    u8 i = 0,len;
    NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); //设置NVIC中断分组2:2位抢占优先级,2位响应优先级
    uart3_init(9600);
    uart1_init(9600);
    
    while(1)
    {
        if(Flag == 1)
        {
            printf("%s",USART3_RX_BUF);
            //USART3_RX_STA=0;
            //memset(USART3_RX_BUF,0,sizeof(USART3_RX_BUF));
            Flag = 0;
        }
        
        if(USART_RX_STA&0x8000)
        {
            len=USART_RX_STA&0x3FFF;
            for(i = 0;i<len;i++)
            {
                
                USART_SendData(USART3,USART_RX_BUF[i]);将存入数组的数据,发送到串口3
                while((USART3->SR&0x40) == 0);//等待发送结束  读取USART1 SR寄存器状态为0表示发送未完成 1为发送完成 (判断发送是否成功)
            }
            printf("%s",USART_RX_BUF);
            memset(USART_RX_BUF,0,sizeof(USART_RX_BUF));
            USART_RX_STA = 0;
        }
    }
}文章来源地址https://www.toymoban.com/news/detail-405498.html

到了这里,关于stm32蓝牙模块通过手机和电脑双向通信的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 蓝牙模块(HC-05)与手机连接,蓝牙与蓝牙互联,电脑通过蓝牙控制单片机

    HC-05蓝牙模块,USB TO TTL手机APP为SPP蓝牙串口 第一章:蓝牙模块配置 一:HC-05与USB TO TTL连接 EN:为使能引脚,一般不接 VCC:接USB TO TTL模块的5v脚(3.3v不亮) GND:接USB TO TTL模块的GND脚 TXD:接USB TO TTL模块的RXD脚 RXD:接USB TO TTL模块的TXD脚 STATE:状态引脚,一般不接 二:进入

    2024年02月12日
    浏览(26)
  • 亚博k210视觉模块与stm32双向通信

    【K210模块】使用UART模块发送和接收数据_KevinGuo457的博客-CSDN博客 K210的串口_uart_a.write_飞鸟211的博客-CSDN博客 ①每隔1s终端以及串口助手收到消息并显示 ②通过串口助手发送123,K210收到数据并显示 这里如果想要指定K210接收的数据,判断条件不能直接用==(原因参考上面的链接

    2024年04月23日
    浏览(25)
  • stm32与手机进行蓝牙通信(超详细版)

            本人也是小白,看了很多博客都没做出来,如果你也是小白,希望这篇文章可以帮助你。      这篇文章是为了实现蓝牙控制stm32灯翻转,并且stm32每次返回给手机的数字加3,需要其他的功能可直接根据模板改。 软件下载链接:串口调试助手:UartAssist串口调试助

    2024年02月09日
    浏览(16)
  • HC-05(ZS-040)蓝牙模块使用详情(蓝牙模块配置、手机蓝牙控制单片机、蓝牙与蓝牙之间的通信)含51、32程序

    HC-05是一款主从一体化的蓝牙模块,因此其使用起来比较方便,只需要进行简单的配置即可。 本文就 手把手的介绍小白入手模块后如何使用 。 对于模块使用:1、蓝牙配置→2、手机与蓝牙的传输→3、手机通过蓝牙模块控制单片机→4、一对蓝牙之间主—从传输数据,这是一个

    2023年04月09日
    浏览(35)
  • STM32--- 蓝牙HC-08 (两模块间主从通信)

    1.1  开发软硬环境 芯片型号:STM32F103RCT6 开发软件:Keil5  (v5.31+AC5,最常用) 代码用库:标准固件库 蓝牙模块:HC-08 (汇承家的;  缺点:小贵 ,优点:pdf+串口助手+APP+小程序,完美) USB转TTL模块: CH9340C  (Type-C接口,win10可免驱动,比CH340和CP2102爽) 1.2  代码下载链接

    2024年02月03日
    浏览(22)
  • ESP32用作经典蓝牙串口透传模块与手机进行串口通信

    ESP32-WROOM-32模组集成了双模蓝牙包括传统蓝牙(BR/EDR)、低功耗蓝牙(BLE)和 Wi-Fi,具有广泛的用途:Wi-Fi 支持极大范围的通信连接,也支持通过路由器直接连接互联网;而蓝牙可以让用户连接手机或者广播 Bluetooth LE Beacon 以便于信号检测。 蓝牙特性: • 支持标准 Class-1、

    2024年02月09日
    浏览(17)
  • 学习 stm32 无线蓝牙模块HC05配置与应用(手机蓝牙连接发送参数)

    最近学习使用HC05 蓝牙模块进行单片机 连接使用,进行手机端数据通信,用到了,和大家分享一下。 HC05 蓝牙模块介绍 HC05 模块,是 ALIENTEK 生成的一款高性能主从一体蓝牙串口模块,可以同各种带蓝牙功能的电脑、蓝牙主机、手机、PDA、PSP 等智能终端配对,该模块支持非常

    2024年01月16日
    浏览(19)
  • HC05蓝牙模块AT指令与手机蓝牙控制STM32板载LED

    本文讲述了HC-05蓝牙模块的配置和其与STM32F103单片机的连接。 代码使用 HAL库函数 编写。 常见的HC-05模块: 通过使用AT指令,我们对蓝牙模块可以进行查看版本号、波特率、配对密码、设置/查询设备名称等多达30多种配置方式。 硬件连接:使用USB转TTL模块连接电脑和蓝牙模块

    2024年02月11日
    浏览(24)
  • STM32F1 + 蓝牙HC08 与 手机APP通信

    1.1  开发软硬环境 芯片型号:STM32F103RCT6 开发软件:Keil5  (v5.31+AC5,最常用) 代码用库:标准固件库 蓝牙模块:HC-08 (HC家的,小贵 ,配套图解、串口助手、APP、小程序,完美) USB转TTL模块: CH9340C  (Type-C接口,win10可免驱动,比CH340和CP2102爽) 1.2  代码下载链接 百度网

    2024年02月04日
    浏览(27)
  • 手把手教你使用--常用模块--HC05蓝牙模块,无线蓝牙串口透传模块,(实例:手机蓝牙控制STM32单片机点亮LED灯)

    最近在学STM32,基本的学完了,想学几个模块来巩固一下知识,就想到了蓝牙模块。玩啥好难过有很多博客教怎么连的,但自己看起来还是有点糊涂。模块的原理和知识点我就不讲解了,这里我主要 手把手 记录一下我是如何对蓝牙模块进行学习和使用的。 所使用的资料和工

    2024年02月02日
    浏览(25)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包