配置进入接收模式:
[objc] view plain copy
void NRF_RX_Mode(void)
{
NRF_CE_LOW();
SPI_NRF_WriteBuf(NRF_WRITE_REG+RX_ADDR_P0,RX_ADDRESS,RX_ADR_WIDTH);//写RX节点地址
SPI_NRF_WriteReg(NRF_WRITE_REG+EN_AA,0x01); //使能通道0的自动应答
SPI_NRF_WriteReg(NRF_WRITE_REG+EN_RXADDR,0x01);//使能通道0的接收地址
SPI_NRF_WriteReg(NRF_WRITE_REG+RF_CH,CHANAL); //设置RF通信频率
SPI_NRF_WriteReg(NRF_WRITE_REG+RX_PW_P0,RX_PLOAD_WIDTH);//选择通道0的有效数据宽度
SPI_NRF_WriteReg(NRF_WRITE_REG+RF_SETUP,0x07); //设置TX发射参数,0db增益,1Mbps,低噪声增益开启
SPI_NRF_WriteReg(NRF_WRITE_REG+CONFIG, 0x0f); //配置基本工作模式的参数;PWR_UP,EN_CRC,16BIT_CRC,接收模式
NRF_CE_HIGH(); /*CE拉高,进入接收模式*/
delay_ms(100); //CE拉高一段时间
}
配置进入发射模式:
[objc] view plain copy
void NRF_TX_Mode(void)
{
NRF_CE_LOW();
SPI_NRF_WriteBuf(NRF_WRITE_REG+TX_ADDR,TX_ADDRESS,TX_ADR_WIDTH); //写TX节点地址;
SPI_NRF_WriteBuf(NRF_WRITE_REG+RX_ADDR_P0,RX_ADDRESS,RX_ADR_WIDTH); //设置TX节点地址,主要为了使能ACK;
SPI_NRF_WriteReg(NRF_WRITE_REG+EN_AA,0x01); //使能通道0的自动应答;
SPI_NRF_WriteReg(NRF_WRITE_REG+EN_RXADDR,0x01); //使能通道0的接收地址;
SPI_NRF_WriteReg(NRF_WRITE_REG+SETUP_RETR,0x1a);//设置自动重发间隔时间:500us + 86us;最大自动重发次数:10次;
SPI_NRF_WriteReg(NRF_WRITE_REG+RF_CH,CHANAL); //设置RF通道为CHANAL;
SPI_NRF_WriteReg(NRF_WRITE_REG+RF_SETUP,0x07); //设置TX发射参数,0db增益,1Mbps,低噪声增益开启;
SPI_NRF_WriteReg(NRF_WRITE_REG+CONFIG,0x0e); //配置基本工作模式的参数;PWR_UP,EN_CRC,16BIT_CRC,发射模式,开启所有中断;
/*CE拉高,进入发送模式*/
NRF_CE_HIGH();
delay_ms(100); //CE要拉高一段时间才进入发送模式
}
NRF24L01的开机自检:
[objc] view plain copy
u8 NRF_Check(void)
{
u8 buf[5]={0xC2,0xC2,0xC2,0xC2,0xC2};
u8 buf1[5];
u8 i;
SPI_NRF_WriteBuf(NRF_WRITE_REG+TX_ADDR,buf,5); /*写入5个字节的地址. */
SPI_NRF_ReadBuf(TX_ADDR,buf1,5); /*读出写入的地址 */
for(i=0;i<5;i++) /*比较*/
{
if(buf1!=0xC2)
break;
}
if(i==5)
return SUCCESS ; //MCU与NRF成功连接
else
return ERROR ; //MCU与NRF不正常连接
}
数据发送:
[objc] view plain copy
u8 NRF_Tx_Dat(u8 *txb)
{
u8 state;
NRF_CE_LOW(); /*ce为低,进入待机模式1*/
SPI_NRF_WriteBuf(WR_TX_PLOAD,txb,TX_PLOAD_WIDTH); /*写数据到TX BUF 最大 32个字节*/
NRF_CE_HIGH(); /*CE为高,txb非空,发送数据包 */
while(NRF_Read_IRQ()!=0); /*等待发送完成中断 */
state = SPI_NRF_ReadReg(STATUS); /*读取状态寄存器的值 */
SPI_NRF_WriteReg(NRF_WRITE_REG+STATUS,state); /*清除TX_DS或MAX_RT中断标志*/
SPI_NRF_WriteReg(FLUSH_TX,NOP); //清除TX FIFO寄存器
/*判断中断类型*/
if(state&MAX_RT) //达到最大重发次数
return MAX_RT;
else if(state&TX_DS) //发送完成
return TX_DS;
else
return ERROR; //其他原因发送失败
}
数据接收,可放在主函数里循环检测,也可更换为中断模式检测:
[objc] view plain copy
u8 NRF_Rx_Dat(u8 *rxb)
{
u8 state;
NRF_CE_HIGH(); //进入接收状态
/*等待接收中断*/
//while(NRF_Read_IRQ()!=0);///////////////////////////////////////////////
NRF_CE_LOW(); //进入待机状态
state = SPI_NRF_ReadReg(STATUS); /*读取status寄存器的值*/
if(state&RX_DR) /*判断是否接收到数据*/ //接收到数据
{
SPI_NRF_WriteReg(NRF_WRITE_REG+STATUS,state);/* 清除中断标志*/
SPI_NRF_ReadBuf(RD_RX_PLOAD,rxb,RX_PLOAD_WIDTH);//读取数据
// SPI_NRF_WriteReg(FLUSH_RX,NOP); //清除RX FIFO寄存器
return RX_DR;
}else
return ERROR; //没收到任何数据
}
主循环任务程序如下:
[objc] view plain copy
void nrf_task(voidvoid *pdata)
{
while(NRF_Check()!=SUCCESS){
<span style="white-space:pre"> </span>delay_ms(100);
}
NRF_TX_Mode();//主动请求连接
nrf_Txbuf[0]='H';
nrf_Txbuf[1]='E';
nrf_Txbuf[2]='L';
nrf_Txbuf[3]='L';
nrf_Txbuf[4]='0';
do
{
status = NRF_Tx_Dat(nrf_Txbuf);
}while((status != TX_DS)&(status != MAX_RT));//发送成功或者到达最大重发次数
<span style="white-space:pre"> </span>if(status == MAX_RT)
{
USART1_printf( USART1,"Connection Failed\r\n");
}
<span style="white-space:pre"> </span>memset(nrf_Txbuf,0,sizeof(nrf_Txbuf));
NRF_RX_Mode();//配置为接收模式
while(1)
{
/*等待接收数据*/
status = NRF_Rx_Dat(nrf_Rxbuf);
/*判断接收状态*/
if(status == RX_DR)//接收到数据中断标志
{
Usb_SendData((char*)nrf_Rxbuf,strlen((char*)nrf_Rxbuf));//通过USB转发
}
if(0 != strlen((char*)nrf_Txbuf))//发送缓冲不为空
{
NRF_TX_Mode();//主动请求连接
do
{
status = NRF_Tx_Dat(nrf_Txbuf);
delay_ms(10);
}while((status != TX_DS)&(status != MAX_RT));//发送成功或者到达最大重发次数
memset(nrf_Txbuf,0,sizeof(nrf_Txbuf));
NRF_RX_Mode();//配置为接收模式
}
delay_ms(100);
}
} |