第三章 2.4G无线通信模块

四轴飞行器项目记录

第三章 无线通信模块



前言

NRF24L01 是一个非常经典的2.4G无线通信模块,他的资料丰富,操作简单功耗低,很适合近距离点对点小数据量的通信。所以用于控制四轴遥控器上采用的NRF24L01 模块+AP 天线这样通信距离就大大增加,如果两个带 AP 天线的NRF24L01 模块通信距离能够达到 500~1000m。考虑到小四轴的续航和重量,所以四轴上采用的是一款功耗更小,功能更强并且还完全兼容 NRF24L01 的芯片 SI24R1,并且还进行了板载天线。所以本章主要讲解 SI24R1的配置与使用。


一、SI24R1简介

Si24R1 操作方式非常方便,只需要微控制器(MCU)通过 SPI 接口对芯片少数几个寄存器配置即可以实现数据的收发通信。嵌入式 ARQ 基带引擎基于包通信原理,支持多种通信模式,可以手动或全自动 ARQ 协议操作。内部集成收发 FIFO,可以保证芯片与 MCU 数据连续传输,增强型 ARQ基带协议引擎能处理所有高速操作,因此大大降低了 MCU 的系统消耗。

需要注意的是该芯片支持的电压范围:1.9-3.6v
在这里插入图片描述

二、SI24R1的SPI通信协议

1.SI24R1与MCU引脚的连接

STM32 与 SI24R1 是通过 SPI总线进行数据通信的,MCU 作为 SPI通信的主机,SI24R1为从机。
在这里插入图片描述
图中,绿色圈中四个引脚是SPI总线的四个信号线,不再过多解释。CE引脚是SI24R1的使能引脚,当使用SI24R1时需要将此引脚电平置高;IRQ引脚是SI24R1的中断输出引脚,当配置打开SI24R1 的中断时,SI24R1接收完数据或发送完数据都将产生中断相应的 IRQ 引脚电平的变化,这样就可以及时通知 MCU 到 SI24R1中把数据读出或写入,省去了MCU 轮询查看寄存器的过程。SI24R1的中断类型有很多,详细请自行查看手册。


2.SI24R1的工作模式和数据包协议

1)工作模式转换

SI24R1可配置为关断、待机、发送空闲、发送和接受五种工作模式。
在这里插入图片描述

模式PWR_UPCEPRIM_RXFIFO寄存器状态
关断0---
待机10--
接收111接收数据写入RX_FIFO
空闲1-10TX_FIFO无数据
发送110TX_FIFO有数据

利用单片机把它配置成接受模式或者发送模式,还可以配置频道、地址、每次发送的字节数、是否带CRC校验、功率等。

配置成发送模式以后,用单片机把要发送的数据写进去,他就会自动把数据发出去;配置成接收模式以后。单片机通过观察它的IRQ引脚,就可以知道是否接收到数据,IRQ为低电平,说明接受到数据,单片机就可以通过SPI把接收到的数据读取出来。

2)数据包协议(可以略做了解)

Si24R1 基于包通信,支持停等式 ARQ协议。芯片内部 ARQ 协议基带处理引擎,可以不需要外部微控制器干预下,自动实现 ACK 和 NO_ACK 数据包的处理。ARQ 协议基带处理单元支持1到 32字节动态数据长度,数据长度在数据包内。也可以采用固定数据长度,通过寄存器指定基带处理单元完成数据的自动解包、打包、自动回复 ACK 确认信号以及自动重发。该处理单元内部有6个通信管道,可以直接支持1:6星型网络。

ARQ包格式
一个完整的 ARQ 数据包包括前导码、地址、包控制字、负载数据以及 CRC。如下图显示为一个完整的包。
在这里插入图片描述
前导码字段主要用于接收数据同步,发射时芯片自动附上,接收时芯片自动去掉,对用户不可见。

地址字段为接收数据方地址,只有当该地址与芯片的地址寄存器中地址相同时才会接收。地址长度可以通过配置寄存器 AW 配置为 3、或 4、或 5 字节。

包控制字段长度为 9bit, 结构如下图。
在这里插入图片描述
数据包长度子字段指定数据包 32 字节。

PID 子字段告知接收端这个包是一个新的包还是一个重发的包,可以防止接收端多次接收同一个包。发射方通过 SPI写 FIFO,PID 的值自动累加。

NO ACK子字段为1时,则表明发射方告知接收端不需要回 ACK 确认信号。对于发射方,使 NO ACK 位为1需要先配置 FEATURE 寄存器中的 EN DYN ACK位为 1,且使用W_TX_PAYLOAD_NOACK 命令写 FIF0。当收到一个这样的包后,接收端不会发送 ACK 确认信号给发射方。(即使接收端工作在 ACK 接收模式)

负载数据字段为发射数据内容,可以最长32字节。

CRC 字段为包的 CRC 值,CRC 支持 8bit 和 16bit 两种,CRC 的长度通过 CONFIG 寄存器中的 CRCO 位配置。

3)ARQ通信模式

在 TX 模式下,发送端自动将前导码、地址、包控制字、负载数据、 CRC 打包。通过射频模块将信号调制通过天线发射

在 RX 模式下,接收端在接收到的解调信号中不断侦测有效地址,一旦侦测到地址与接收地址相同,开始接收数据,如果接收到的数据有效,则将负载数据部分存放入 RX_FIFO 中,并产生中断通知 MCU。 MCU 通过 SPI 接口可随时访问 RX_FIFO 寄存器,进行数据读取。

SI24R1一共有六种通信模式,下面只讲解了ACK通信模式。

ACK模式
当用 W_TX_PAYLOAD 命令对发送端 TX FIFO 写数据时,将数据打包后,数据包中包控制字段 NO_ACK 标志位复位。接收端接收到一帧有效数据后, 产生 RX_DR 中断后,会自动发送一帧 ACK 信号,发送端接收到 ACK 信号,则自动清除 TX FIFO 数据并产生 TX_DS 发射中断,表明此次通信成功。

接收端在发送 ACK 信号时,取接收管道地址作为目标地址来发送 ACK 信号,所以发送端需要设置接收管道 0 地址与自身发送地址相同,以便接收 ACK 信号。

如果发送端在 ARD 时间内没有接收到 ACK 信号,则重新发送上一帧数据。当重发次数达到最大,仍没有收到确认信号时,发送端产生 MAX_RT 中断。 MAX_RT 中断在清除之前不能进行下一步的数据发送。所有中断通过对状态寄存器进行写操作来清除。PLOS_CNT 寄存器在每产生一个 MAX_RT 中断后加 1,用来记录当前频段下,丢失的数据包的数量。 ARC_CNT 寄存器记录当前数据重发的次数,在发送一包新数据时使其复位。最大重发次数与 ARD 时间通过 SETUP_RETR 寄存器来进行配置。接收端开启自动回复 ACK 信号由 EN_AA 寄存器来控制。下图为 ACK 模式下的一次通信完成。
在这里插入图片描述

三、SI24R1的SPI接口和寄存器配置

芯片采用标准的四线 SPI 接口,实测最高读写速度大于 10Mb/S。外部微控制器可
以通过 SPI 接口对芯片进行配置,包括读写功能寄存器、读写 FIFO、读芯片状态、清
除中断等。

1.SPI时序

SPI 操作包括基本的读写操作以及其他的命令操作。
注:只能在 Shutdown、 Standby 和 Idle-TX 模式下才能对寄存器进行配置。

CSN 从高电平翻转为低电平, SPI 接口开始工作。每一次 SPI操作, MISO 输出的第一字节为状态寄存器的值,之后通过命令来确定是否输出值(不输出为高阻态)。命令格式中命令字按从 MSBit 到 LSBit 的顺序输入,数据格式中按从LSByte 到 MSByte 的顺序,每字节中按从 MSBit 到 LSBit 的顺序输入。详细请参考 SPI时序。
在这里插入图片描述
SI24R1 一般作为SPI通信的从机,因此SPI主机的通信时序应以从机为准。通过SI24R1读写时序可以得出,SI24R1的时钟空闲状态为低电平,也就是说“CPOL=0”,SI24R1 在第一个时钟沿进行数据采集,也就是说“CPHA=0”。还可以得出寄存器读写都是先发相应的控制命令,然后进行数据的读或者写交互。


2.寄存器操作命令

寄存器操作命令共有八个。
在这里插入图片描述


3.寄存器数量

寄存器共有24个。
在这里插入图片描述


四、SI24R1与NRF24L01的半双工通信

1.通信条件

两个芯片之间通信,收发双方需要满足4个条件:
1)发射接收频道相同(设置频道寄存器RF_CH,0-125);
2)发射接收地址相同(设置TX_ADDR和RX_ADDR_P0相同,五个8位地址);
3)发射接收数据宽度相同(n <=32);
4)发射接收速率相同(250k,1M,2M);


2.Tx模式初始化过程

在这里插入图片描述


3.Rx模式初始化过程

在这里插入图片描述


4.中断函数处理

SI24R1 的中断是根据初始化时配置的中断,然后满足条件后就会在IRQ引脚上产生一个低电平,来通知 MCU 进行相应的反应。由于实时性的要求,所以采用外部中断来捕获 IRQ 引脚的下降沿,如果捕获到下降沿就进入中断服务函数中进行处理。

例如:配置 SI24R1 为发送中断时,一旦 SI24R1 收到接收方返回的 ACK 时,IRQ引脚就会产生一个低电平,这时 EXIT 外部中断捕获到了这个下降沿,就会产生一个中断。


5.读入数据

代码如下(示例):

#include "nrf2401.h"
#include "spi.h"
#include "delay.h"
#include "stdio.h"
#include "led.h"
#include "remotedata.h"
#include "structconfig.h"
#include "stdlib.h"
#include "paramsave.h"

/************************************************************************
*代码移植修改区
*只需要根据原理图修改对应的端口时钟 端口 引脚
************************************************************************/
#define RCC_NRF_SCN   RCC_AHB1Periph_GPIOB  //端口时钟
#define NRF_SCN_PORT  GPIOB                 //端口
#define NRF_SCN       GPIO_Pin_12           //引脚

#define RCC_NRF_CE    RCC_AHB1Periph_GPIOA  //端口时钟
#define NRF_CE_PORT   GPIOA                 //端口
#define NRF_CE        GPIO_Pin_8            //引脚

#define RCC_NRF_IRQ   RCC_AHB1Periph_GPIOB  //端口时钟
#define NRF_IRQ_PORT  GPIOB                 //端口
#define NRF_IRQ       GPIO_Pin_2            //引脚
/**************************************************************************/

//设置引脚电平
#define NRF_SCN_LOW   NRF_SCN_PORT->BSRRH |= NRF_SCN 
#define NRF_SCN_HIGH  NRF_SCN_PORT->BSRRL |= NRF_SCN
#define NRF_CE_LOW    NRF_CE_PORT->BSRRH  |= NRF_CE
#define NRF_CE_HIGH   NRF_CE_PORT->BSRRL  |= NRF_CE
//读取引脚电平
//#define NRF_IRQ_READ  (NRF_IRQ_PORT->IDR & NRF_IRQ)
#define NRFAddrMax 50 //NRF最后一个字节地址最大为50
uint8_t NRFaddr = 0xFF; //初始化NRF最后一字节地址

uint8_t NRF_TX_DATA[TX_PAYLO_WIDTH];//NRF发送缓冲区
uint8_t NRF_RX_DATA[RX_PAYLO_WIDTH];//NRF接收缓冲区

uint8_t TX_ADDRESS[TX_ADR_WIDTH]={0x34,0x43,0x10,0x10,0xFF}; //发送地址
uint8_t RX_ADDRESS[RX_ADR_WIDTH]={0x34,0x43,0x10,0x10,0xFF}; //接收地址

void NRF24L01_Config(void);
void NRF_GetAddr(void);

/*****************************************************************************
*函  数:void NRF24l01_Init(void)
*功  能:NRF引脚GPIO初始化
*参  数:无
*返回值:无
*备  注:无
*****************************************************************************/
void NRF24l01_Init(void)
{
  GPIO_InitTypeDef GPIO_InitStructure;
  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB|RCC_AHB1Periph_GPIOA, ENABLE);
	
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;       
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;      
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; 
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; 

  GPIO_InitStructure.GPIO_Pin = NRF_SCN; //NRF的片选信号SCN 
  GPIO_Init(NRF_SCN_PORT, &GPIO_InitStructure);
  GPIO_ResetBits(NRF_SCN_PORT,NRF_SCN);
	
  GPIO_InitStructure.GPIO_Pin = NRF_CE; //NRF的片选信号SCN 
  GPIO_Init(NRF_CE_PORT, &GPIO_InitStructure);
  GPIO_ResetBits(NRF_CE_PORT,NRF_CE);
		
  SPI2_Init(); //SPI2初始化
	
  NRF24L01_Check(); //检查NRF24L01是否与MCU通信                                    
	
  NRF_SCN_HIGH; //失能NRF
  NRF_CE_LOW; //待机模式
	
 // NRF24L01_Config();  //配置NRF并初始化为接收模式
}

/*****************************************************************************
*函  数:uint8_t NRF24l01_write_reg(uint8_t reg,uint8_t value)
*功  能:写一字节数据到寄存器
*参  数:reg: 寄存器地址
*        val:  要写入的数据
*返回值:status
*备  注:NRF2401代码移植只需把SPI驱动修改成自己的即可
*****************************************************************************/
uint8_t NRF24l01_write_reg(uint8_t reg,uint8_t value)
{
	uint8_t status;
	NRF_SCN_LOW;
	status=SPI2_WriteReadByte(reg);
	SPI2_WriteReadByte(value);
	NRF_SCN_HIGH;
	return status;
}

/*****************************************************************************
*函  数:uint8_t NRF24l01_read_reg(uint8_t reg)
*功  能:读一字节数据到寄存器
*参  数:reg: 寄存器地址
*返回值:reg_val
*备  注:NRF2401代码移植只需把SPI驱动修改成自己的即可
*****************************************************************************/
uint8_t NRF24l01_read_reg(uint8_t reg)
{
	uint8_t reg_val;
	NRF_SCN_LOW;
	SPI2_WriteReadByte(reg);
	reg_val = SPI2_WriteReadByte(0xff);
	NRF_SCN_HIGH;
	return reg_val;
}

/*****************************************************************************
*函  数:uint8_t NRF24L01_Write_Buf(uint8_t reg, uint8_t *pBuf, uint8_t len)
*功  能:写一组数据到寄存器
*参  数:reg: 寄存器地址
*       pBuf: 要写入数据的地址
*        len:  要写入的数据长度
*返回值:status
*备  注:NRF2401代码移植只需把SPI驱动修改成自己的即可
*****************************************************************************/
uint8_t NRF24L01_Write_Buf(uint8_t reg, uint8_t *pBuf, uint8_t len)
{
	uint8_t status;
	int i;
	NRF_SCN_LOW;
	status = SPI2_WriteReadByte(reg);
	for( i=0;i<len;i++)
	{
		SPI2_WriteReadByte(*pBuf);
		pBuf++;
	}
	NRF_SCN_HIGH;
	return status;
}

/*****************************************************************************
*函  数:uint8_t NRF24L01_Read_Buf(uint8_t reg, uint8_t *pBuf, uint8_t len)
*功  能:读一组数据到寄存器
*参  数:reg: 寄存器地址
*       pBuf: 要读取数据的地址
*        len:  要读取的数据长度
*返回值:status
*备  注:NRF2401代码移植只需把SPI驱动修改成自己的即可
*****************************************************************************/
uint8_t NRF24L01_Read_Buf(uint8_t reg, uint8_t *pBuf, uint8_t len)
{
	uint8_t status;
	int i;
	NRF_SCN_LOW;
	status = SPI2_WriteReadByte(reg);
	for(i = 0;i < len ;i++)
	{
		*pBuf = SPI2_WriteReadByte(0xff);
		pBuf++;
	}
	NRF_SCN_HIGH;
	return status;
}

/*****************************************************************************
*函  数:void NRFset_Mode(uint8_t mode)
*功  能:切换NRF2401的工作模式模式
*参  数:无
*返回值:无
*备  注:无
*****************************************************************************/
void NRFset_Mode(uint8_t mode)
{
	if(mode == IT_TX)
	{
	  NRF_CE_LOW;
	  NRF24l01_write_reg(W_REGISTER+CONFIG,IT_TX);
    NRF24l01_write_reg(W_REGISTER+STATUS,0X7E); //清除所有中断,防止一进去发送模式就触发中断	
	  NRF_CE_HIGH;
	 // delay_us(15);
	}
	else
	{
	  NRF_CE_LOW;
	  NRF24l01_write_reg(W_REGISTER+CONFIG,IT_RX);//配置为接收模式
	  NRF24l01_write_reg(W_REGISTER+STATUS,0X7E); //清除所有中断,防止一进去接收模式就触发中断
	  NRF_CE_HIGH;
	  delay_us(200);
	}
		
}

/*****************************************************************************
*函  数:void NRF24L01_Config(void)
*功  能:NRF基本参数配置,并初始化为接收模式
*参  数:无
*返回值:无
*备  注:无
*****************************************************************************/
void NRF24L01_Config(void)
{
	NRF_CE_LOW;
	NRF24l01_write_reg(W_REGISTER+SETUP_AW, 0x03); //配置通信地址的长度,默认值时0x03,即地址长度为5字节
	NRF24L01_Write_Buf(W_REGISTER+TX_ADDR,(uint8_t*)TX_ADDRESS,TX_ADR_WIDTH); //写TX节点地址 
	NRF24L01_Write_Buf(W_REGISTER+RX_ADDR_P0,(uint8_t*)TX_ADDRESS,RX_ADR_WIDTH); //设置TX节点地址,主要为了使能ACK
	NRF24l01_write_reg(W_REGISTER+SETUP_RETR,0x1A); //设置自动重发间隔时间:500us + 86us;最大自动重发次数:10次 0x1A
	
	NRF24l01_write_reg(W_REGISTER+EN_RXADDR,0x01);//使能通道0的接收地址  
	NRF24l01_write_reg(W_REGISTER+EN_AA,0x01); //使能通道0自动应答
	NRF24l01_write_reg(W_REGISTER+RX_PW_P0,RX_PAYLO_WIDTH);//选择通道0的有效数据宽度  
	NRF24L01_Write_Buf(W_REGISTER+RX_ADDR_P0,(uint8_t*)RX_ADDRESS,RX_ADR_WIDTH); //写RX节点地址
	NRF24l01_write_reg(W_REGISTER+RF_CH,30); //设置RF通道为40hz(1-64Hz都可以)
	NRF24l01_write_reg(W_REGISTER+RF_SETUP,0x27); //设置TX发射参数,0db增益,2Mbps,低噪声增益关闭 (注意:低噪声增益关闭/开启直接影响通信,要开启都开启,要关闭都关闭0x0f)0x07
	
	NRFset_Mode(IT_RX); //默认为接收模式
	
	NRF_CE_HIGH;
}	

/*****************************************************************************
*函  数:uint8_t NRF24L01_TxPacket(uint8_t *txbuf)
*功  能:NRF发送一包数据
*参  数:txbuf:要发送数据地址
*返回值:无 
*备  注:无
*****************************************************************************/
void NRF24L01_TxPacket(uint8_t *txbuf)
{
	NRF_CE_LOW;	
	NRF24L01_Write_Buf(W_REGISTER+TX_ADDR,(uint8_t*)TX_ADDRESS,TX_ADR_WIDTH);  //写TX节点地址 
	NRF24L01_Write_Buf(W_REGISTER+RX_ADDR_P0,(uint8_t*)TX_ADDRESS,RX_ADR_WIDTH); //设置TX节点地址,主要为了使能ACK
	NRF24L01_Write_Buf(W_RX_PAYLOAD,txbuf,TX_PAYLO_WIDTH); //写数据到TX_BUFF
  NRF24l01_write_reg(W_REGISTER+CONFIG,0x0e);	//设置为发送模式,开启所有中断
	NRF24l01_write_reg(W_REGISTER+STATUS,0X7E); //清除所有中断,防止一进去发送模式就触发中断
  NRF_CE_HIGH;
	delay_us(10);  //CE持续高电平10us
}

/*****************************************************************************
*函  数:uint8_t NRF24L01_RxPacket(uint8_t *rxbuf)
*功  能:NRF接收一包数据
*参  数:rxbuf:接收数据存储地址
*返回值:无
*备  注:无
*****************************************************************************/
void NRF24L01_RxPacket(uint8_t *rxbuf)
{
	NRF_CE_LOW;
	NRF24L01_Read_Buf(R_RX_PAYLOAD,rxbuf,TX_PAYLO_WIDTH);//读取RX的有效数据
	NRF24l01_write_reg(FLUSH_RX,0xff); //清除RX FIFO(注意:这句话很必要)
	NRF_CE_HIGH;
}
/*****************************************************************************
*函  数:uint8_t NRF24L01_testConnection(void)
*功  能:检查NRF2401与MCU的SPI总线是否通信正常
*参  数:无
*返回值:1已连接 0未连接
*备  注:无
*****************************************************************************/
uint8_t NRF24L01_testConnection(void)
{
	uint8_t buf[5]={0XA5,0XA5,0XA5,0XA5,0XA5};
	uint8_t i; 	 
	NRF24L01_Write_Buf(W_REGISTER+TX_ADDR,buf,5); //写入5个字节的地址.	
	NRF24L01_Read_Buf(TX_ADDR,buf,5); //读出写入的地址  
	for(i=0;i<5;i++)
	if(buf[i]!=0XA5)break;	 							   
	if(i!=5)return 0; //检测24L01错误	
	return 1;	//检测到24L01
}	
void NRF24L01_Check(void)
{
	while(!NRF24L01_testConnection())
	{
		printf("\rNRF2401 no connect...\r\n");
		RGB_LED_Red();//红灯常亮
	}
}

/*****************************************************************************
*函  数:void EXTI2_IRQHandler(void)
*功  能:NRF(全双工)的外中断处理函数
*参  数:无
*返回值:无
*备  注: NRF的所有中断事件都在次函数中给予相应的处理
*****************************************************************************/
void EXTI2_IRQHandler(void)
{                    
	uint8_t sta;
	if(EXTI_GetITStatus(EXTI_Line2) != RESET )
	{
		RunTimer_Test();
		 NRF_CE_LOW;//拉低CE,以便读取NRF中STATUS中的数据
		 sta = NRF24l01_read_reg(R_REGISTER+STATUS); //读取STATUS中的数据,以便判断是由什么中断源触发的IRQ中断
		
		/* 发送完成中断 TX_OK */
		if(sta & TX_OK)                                   
		{										
		  NRFset_Mode(IT_RX);	
			NRF24l01_write_reg(W_REGISTER+STATUS,TX_OK); //清除发送完成标志·
		  NRF24l01_write_reg(FLUSH_TX,0xff); //清除TX_FIFO
			//printf("Sent OK!!!!\r\n");
		}
		/* 接收完成中断 RX_OK */
		if(sta & RX_OK) 
		{	
      NRF24L01_RxPacket(NRF_RX_DATA);	
      Remote_Data_ReceiveAnalysis();
			NRF24l01_write_reg(W_REGISTER+STATUS,RX_OK); //清除发送完成标志·
			//printf("Receive OK!!!!\r\n");	
		}
		/* 达到最大重发次数中断  MAX_TX */
		if(sta & MAX_TX)                                  
		{											
			NRFset_Mode(IT_RX);
			NRF24l01_write_reg(W_REGISTER+STATUS,MAX_TX);//清除接达到最大重发标志
			NRF24l01_write_reg(FLUSH_TX,0xff); //清除TX_FIFO
			//printf("Sent Max Data!!!\r\n"); 
		}
		EXTI_ClearITPendingBit(EXTI_Line2);
	}
}

/*****************************************************************************
*函  数:void NRF_GetAddr(void)
*功  能:给飞机获取上的NRF获取一个地址
*参  数:无
*返回值:无 
*备  注:此函数需要与遥控器的对频函数联合使用否者NRF通信不成功,
         如果自己做的的遥控器可直接用固定地址
*****************************************************************************/
void NRF_GetAddr(void)
{
	if(NRFaddr > NRFAddrMax)//当 NRFaddr大于NRFAddrMax,就说明次时NRF还未初始化完成
	{
	  srand(SysTick->VAL);//给随机数种子
		//printf("SysTick->VAL:%d\r\n",SysTick->VAL);
		NRFaddr = rand()%NRFAddrMax;//随机获取NRF最后一字节地址(地址:0~50)
    PID_WriteFlash();//保存此地址Flash
	}else if(NRFaddr != TX_ADDRESS[TX_ADR_WIDTH-1])
	{
		TX_ADDRESS[TX_ADR_WIDTH-1] = NRFaddr;
		RX_ADDRESS[TX_ADR_WIDTH-1] = NRFaddr;
	  NRF24L01_Config();
	//printf("NRFAddr:%d\r\n",NRFaddr);
	}
}

/*****************************************************************************
*函  数:void NRF_Test(void)
*功  能:MRF通信测试函数
*参  数:无
*返回值:无 
*备  注:测试时用
*****************************************************************************/
void NRF_Test(void)
{
	uint8_t t=0;
	static uint8_t mode,key;
	mode = ' ';
	key=mode;
	for(t=0;t<32;t++)
	{
		key++;
		if(key>('~'))key=' ';
		NRF_TX_DATA[t]=key;	
	}
	mode++; 
	if(mode>'~')mode=' ';  	  		
	NRF24L01_TxPacket(NRF_TX_DATA);
}


总结

以上就是本次学习以及记录内容。

  • 16
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值