折腾了两天还是弄出来了。什么24L01介绍就不要了,淘宝资料一堆。
使用的单片机型号是STMF103ZET6.还是简单介绍几点:
1.硬件连接
如图标记右下角是1脚
CE:模式控制线
CSN:SPI片选线
SCK:SPI时钟线
VCC:3.3V供电
MOSI:SPI数据线(主机输出,从机输入)
MISO:SPI数据线(主机输入,从机输出)
IRQ:中断信号线。中断时变为低电平,在以下三种情况变低:Tx FIFO 发完并且收到ACK(使能ACK情况下)、
Rx FIFO 收到数据、达到最大重发次数。
1.一发一收单片机和电脑通信已调通
和电脑通信,还需要USB_NRF24L01这样的一个模块
需要注意,之前一直被这个USB模块误导了,它有一个上位机可以读取配置信息。一直以为配置信息时存放在
NRF24L01模块中。其实不是,配置信息存放在USB模块上面。
通过串口AT指令,设置目标地址和本地地址以及频道、空中速率、校验方式等信息如图
在单片机程序中设置一样的参数,如图是截取的部分代码
const uchar TX_ADDRESS[TX_ADR_WIDTH]= {0x34,0x43,0x10,0x10,0x01}; //发送地址
const uchar RX_ADDRESS[RX_ADR_WIDTH]= {0x34,0x43,0x10,0x10,0x01}; //接收地址
NRF24L01_Write_Reg(nRF_WRITE_REG+RF_CH,0); //设置RF通道为2.400GHz 频率=2.4+0GHz
NRF24L01_Write_Reg(nRF_WRITE_REG+RF_SETUP,0x0F); //设置TX发射参数,0db增益,2Mbps,低噪声增益开启
NRF24L01_Write_Reg(nRF_WRITE_REG+CONFIG,0x0f); //配置基本工作模式的参数;PWR_UP,EN_CRC,16BIT_CRC
单片机发送端的本机地址(接收地址)和发送地址要一样,这样才能进行ACK应答。因为nRF24L01
在确认收到数据后记录地址,并以此地址为目标地址发送应答信号。
附件中赋予实现源码(采用模拟SPI通信的方式),需要硬件SIP自行修改即可。
2.一发一收单片机和单片机通信已调通
同样如1。两块单片机相互进行通信时,需要注意设置相同的目标地址和本地地址
以及频道、空中速率、校验方式。在程序中已经体现,详情看程序源码即可。
在程序中需要注意这点:
nRF24L01+实际发送字节数为32个,用户可用的字节为1-31个, 第0个字节系
统保留,用于每次传输的数据包长度统计;例如串口发送“abc”(ASCII码,3个
字节),实际传输时3abc(第0个字节就为3),接收端实际处理时应根据第0字节中
的数来判断收到的数据包长度。 模块通信协议如下图:
同样接收程序中也是这样,第一个位是数据长度。解析时从第二个位开始解析即可。
(这里需要特别注意的是:Byte0是系统保留位,用于统计数据包长度,这个只是针对于我
使用了这中上位机模块如果你是两个24L01相互通信,完全不用考虑这个)
在程序代码中这里可以体现出来:
rece_buf[1]=0x01;
rece_buf[2]=0x02;
rece_buf[3]=0x03;
rece_buf[4]=0x04;
rece_buf[5]=0x05;
rece_buf[0]=5; //一共要发送5个字节,rece_buf[0]必须是5
3.多发一收单片机和单片机通信已调通
需要实现多发一收的话,需要先先理解下面两个图
nRF24L01 在接收模式下可以接收6路不同通道的数据,如图。每一个数据通道使用不同的地址,但
是共用相同的频道。也就是说 6 个不同的nRF24L01设置为发送模式后可以与同一个设置为接收模式的
nRF24L01 进行通讯,而设置为接收模式的nRF24L01可以对这 6 个发射端进行识别。数据通道0是唯一
的一个可以配置为 40 位自身地址的数据通道。1~5数据通道都为 8 位自身地址和32位公用地址。所有的
数据通道都可以设置为增强型 ShockBurst 模式。
nRF24L01 在确认收到数据后记录地址,并以此地址为目标地址发送应答信号。在发送端,数据通道0
被用做接收应答信号,因此,数据通道 0的接收地址要与发送端地址相等以确保接收到正确的应答信号
数据通道是通过寄存器 EN_RXADDR来设置的,默认状态下只有数据通道0和数据通道 1是开启状
态的。
每一个数据通道的地址是通过寄存器 RX_ADDR_Px 来配置的。通常情况下不允许不同的数据通道设
置完全相同的地址。
数据通道 0 有 40位可配置地址。数据通道1~5 的地址为: 32 位共用地址+各自的地址(最低字节)。
图 7 所示的是数据通道 1~5 的地址设置方法举例。所有数据通道可以设置为多达40位,但是 1~5数据通
道的最低位必须不同 。
产生应答信号,此应答信号的目标地址为接收通道地址 。(所以正如上上个图所示发送端的发送地址
结合两个图来进行看,总结来说在程序中的配置如图:
const uchar RX_ADDRESS0[RX_ADR_WIDTH]= {0xE7,0xD3,0xF0,0x35,0x77}; //接收地址0通道
const uchar RX_ADDRESS1[RX_ADR_WIDTH]= {0xC2,0xC2,0xC2,0xC2,0xC2}; //接收地址1通道
const uchar RX_ADDRESS2[1]= {0xC3}; //接收地址2通道
const uchar RX_ADDRESS3[1]= {0xC4}; //接收地址3通道
const uchar RX_ADDRESS4[1]= {0xC5}; //接收地址4通道
const uchar RX_ADDRESS5[1]= {0xC6}; //接收地址5通道
NRF24L01_Write_Buf(nRF_WRITE_REG+RX_ADDR_P0,(uchar*)RX_ADDRESS0,RX_ADR_WIDTH); //设置TX节点地址,主要为了使能ACK
NRF24L01_Write_Buf(nRF_WRITE_REG+RX_ADDR_P1,(uchar*)RX_ADDRESS1,RX_ADR_WIDTH); //设置TX节点地址,主要为了使能ACK
NRF24L01_Write_Buf(nRF_WRITE_REG+RX_ADDR_P2,(uchar*)RX_ADDRESS2,1); //设置TX节点地址,主要为了使能ACK
NRF24L01_Write_Buf(nRF_WRITE_REG+RX_ADDR_P3,(uchar*)RX_ADDRESS3,1); //设置TX节点地址,主要为了使能ACK
NRF24L01_Write_Buf(nRF_WRITE_REG+RX_ADDR_P4,(uchar*)RX_ADDRESS4,1); //设置TX节点地址,主要为了使能ACK
NRF24L01_Write_Buf(nRF_WRITE_REG+RX_ADDR_P5,(uchar*)RX_ADDRESS5,1); //设置TX节点地址,主要为了使能ACK
4.一发多收单片机和单片机通信只有理论(未调试)
在技术手册上面,看到只有描述多发一收的情况。但是没有一发多少,或者一发指定的单片机收。理论上可以实现的。
一种方法:通过设置地址,几个接收模块设置不同的地址,发的一方直接通过发送到指定的地址模块
二种方法:通过设置为不同的频道。NRF24L01可以使用频道是2.400GHz~2.512GHZ。几个不同的接收端
设置不同的频道,但是这种方法只适用于从机个数不是很多的情况。从机数量过多的话,频道会比较相互接近会产生数据干
扰。所以设置频道时,尽量拉开频道之间的距离。
可以参考这位网友点击打开链接
5.最后附上调试成功的代码点击打开链接