接线方法
1. 电源连接
VCC:连接到5V电源(如果使用3.3V供电的单片机,请确保模块也兼容3.3V)。
GND:连接到地(GND)。
注意:虽然HC-05/HC-06模块可以接受3.3V至6V的电压输入,但其I/O电平为3.3V。如果你的单片机工作在5V电平,建议使用电平转换器以避免损坏模块。
2. 串行通信连接
TXD(HC-05/HC-06的发送端):连接到单片机的RXD(接收端),通常是P3.0引脚。
RXD(HC-05/HC-06的接收端):连接到单片机的TXD(发送端),通常是P3.1引脚。由于HC-05/HC-06的RXD引脚需要3.3V逻辑电平,而51单片机的TXD输出为5V,因此需要一个分压电路来将5V降到3.3V。
微信小程序搜索蓝牙调试助手,一般用的HCBLE串口助手,这个后面调试代码可以用。用于手机和蓝牙通信
该代码主要作用是手机发送数据给蓝牙,蓝牙把数据传递给单片机,单片机使用定时器和中断去检测串口是否有数据,然后控制led的亮灭,简单实验。
code:
#include <REGX52.H>
sbit LED = P2^1; // 定义LED连接的引脚
void UART_Init() {
TMOD = 0x20; // 设置定时器1为模式2,8位自动重装
TH1 = 0xFD; // 波特率设置为9600bps(适用于11.0592MHz晶振)
SCON = 0x50; // 8位数据, 1位停止位, REN使能
TR1 = 1; // 启动定时器1
}
void UART_ISR() interrupt 4 {
if (RI) { // 如果是接收中断
char receivedData = SBUF; // 读取接收缓冲区
RI = 0; // 清除接收中断标志位
// 根据接收到的数据控制LED
if(receivedData == '1') {
LED = 0; // 打开LED
} else if(receivedData == '0') {
LED = 1; // 关闭LED
}
// 回发数据
SBUF = receivedData; // 将接收到的数据发送回去
while(!TI); // 等待发送完成
TI = 0; // 清除发送中断标志位
}
}
void main() {
UART_Init(); // 初始化UART
EA = 1; // 开启全局中断
ES = 1; // 开启串口中断
while(1) {
// 主循环可以添加其他任务
}
}
3.代码解释
UART_Init
函数是初始化定时器
TMOD = 0x20
;
TMOD 是定时器模式寄存器(Timer Mode Register),用于设置定时器的工作模式。
0x20 的二进制表示为 0010 0000。
高四位(TMOD[7:4])对应定时器1的配置:0010 表示模式2,即8位自动重装载模式。
低四位(TMOD[3:0])对应定时器0的配置,这里没有使用定时器0,所以保持为0。
物理意义:将定时器1设置为模式2,8位自动重装载模式。在这种模式下,定时器计数溢出后会自动从TH1重新加载初始值,这有助于产生稳定的波特率。TH1 = 0xFD
;
TH1 是定时器1的高字节寄存器(Timer High byte Register for Timer 1)。
0xFD 对应十进制的253。在12MHz晶振下,为了获得9600bps的波特率,需要设置定时器1的重装载值为253(即0xFD)。
物理意义:设置定时器1的重装载值为253,这样当定时器1溢出时,它会自动重载这个值,从而生成9600bps的波特率。SCON = 0x50
;
SCON 是串行控制寄存器(Serial Control Register),用于配置串口通信的模式和状态。
0x50 的二进制表示为 0101 0000。
第7位(SM0)和第6位(SM1)为 01,表示选择串口工作在模式1(8位UART,可变波特率)。
第5位(SM2)为 0,表示禁用多机通信模式。
第4位(REN)为 1,表示允许接收数据。
其余位与当前配置无关。
物理意义:配置串口工作在模式1,允许接收数据,并设置为8位数据、1位停止位的格式。TR1 = 1
;
TR1 是定时器1的运行控制位(Timer Run Control bit for Timer 1)。
将其设置为 1 表示启动定时器1。
物理意义:启动定时器1,使其开始计数并生成所需的波特率信号。
总结
这段代码的主要目的是初始化51单片机的UART模块,以实现基于串行通信的功能。具体步骤包括:
设置定时器1为模式2(8位自动重装载模式),以便生成稳定的波特率。
根据系统晶振频率和所需的波特率(9600bps),设置定时器1的重装载值。
配置串口工作模式为模式1(8位UART,可变波特率),并允许接收数据。
启动定时器1,使整个串口通信系统开始工作。
通过这些配置,你的单片机可以通过串口与外部设备(如蓝牙模块HC4)进行数据交换。
- void UART_ISR() interrupt 4
- interrupt 4:表示这是一个中断服务程序,对应的中断向量号为4。在51单片机中,中断向量号4对应的是串行口中断。
UART_ISR:这是你为这个中断服务程序起的名字,你可以根据需要更改这个名字。
RI 是接收中断标志位(Receive Interrupt Flag)。当串口接收到一个字节的数据时,硬件会自动将这个标志位置位(设置为1)。
这个条件语句检查是否发生了接收中断。如果发生了接收中断,则执行大括号内的代码块。 - char receivedData = SBUF;
SBUF 是串行数据缓冲寄存器(Serial Buffer Register),用于存储接收到的数据或要发送的数据。
这行代码从 SBUF 中读取接收到的数据,并将其存储在变量 receivedData 中。 - RI = 0;
清除接收中断标志位。每次处理完接收中断后,必须手动清除这个标志位,以便能够响应下一次接收中断。 - SBUF = receivedData;:将接收到的数据写入 SBUF,准备通过串口发送出去。
- while(!TI);:等待发送完成。
- TI 是发送中断标志位(Transmit Interrupt
Flag),当数据发送完成后,硬件会自动将这个标志位置位(设置为1)。这里使用一个循环来等待 TI 变为1,即等待数据发送完成。 TI =
0;:清除发送中断标志位。每次发送完数据后,必须手动清除这个标志位,以便能够响应下一次发送中断。
总结
这段代码实现了一个简单的串行通信中断服务程序,其功能包括:
接收数据:当串口接收到一个字节的数据时,触发接收中断,并从中断服务程序中读取该数据。
控制LED:根据接收到的数据(字符 '1' 或 '0')来控制连接到P2.1引脚的LED的状态。
回发数据:将接收到的数据通过串口发送回去,以便在蓝牙设备上显示接收到的数据。
通过这种方式,你可以实现通过蓝牙模块发送指令来控制单片机上的LED,并且可以看到发送的数据被回传到蓝牙设备上进行验证。这种机制对于调试和双向通信非常有用。