zoukankan      html  css  js  c++  java
  • nRF24L01无线介绍

    引脚功能

    CE:RX或TX模式选择
    CSN:SPI片选信号
    SCK:SPI时钟
    MOSI:SPI数据输入
    MISO:SPI数据输出
    IRQ:可屏蔽中断脚

    时序
    51测试程序
    实测可用!

    #define TX_ADR_WIDTH    5
    #define RX_ADR_WIDTH    5
    #define TX_PLOAD_WIDTH  32
    #define RX_PLOAD_WIDTH  32
    
    #define MAX_TX  	0x10	//达到最大发送次数中断
    #define TX_OK   	0x20	//TX发送完成中断
    #define RX_OK   	0x40	//接收到数据中断
    
    const uchar TX_ADDRESS[TX_ADR_WIDTH]={0xEE,0xDD,0xCC,0xBB,0xAA};	//发送地址
    const uchar RX_ADDRESS[RX_ADR_WIDTH]={0xAA,0xBB,0xCC,0xDD,0xEE};
    
    sbit CE   = P2^7;
    sbit CSN  = P2^6;
    sbit MISO = P2^3;
    sbit MOSI = P2^4;
    sbit SCK  = P2^5;
    sbit IRQ  = P2^2;
    
    sbit LED=P1^0;
    
    void delay_us(uchar num)
    {
    	uchar i; 
    	for(i=0;i>num;i++)
     	_nop_();
    }
    
    void delay(uint t)
    {
    	uchar k;
    	while(t--)
    	for(k=0;k<200;k++);
    }
    
    uchar SPI_RW(uchar byte)
    {
    	uchar bit_ctr;
    	for(bit_ctr=0;bit_ctr<8;bit_ctr++) // output 8-bit
    	{
    		MOSI = (byte & 0x80); // output 'byte', MSB to MOSI
    		byte = (byte << 1); // shift next bit into MSB..
    		SCK = 1; // Set SCK high..
    		byte |= MISO; // capture current MISO bit
    		SCK = 0; // ..then set SCK low again
    	}
    	return(byte); // return read byte
    }
    
    uchar SPI_Write_Reg(uchar reg, uchar value)
    {
    	uchar status;
    	CSN = 0; // CSN low, init SPI transaction
    	status = SPI_RW(reg); // select register
    	SPI_RW(value); // ..and write value to it..
    	CSN = 1; // CSN high again
    	return(status); // return nRF24L01 status byte
    }
    
    uchar SPI_Write_Buf(uchar reg, uchar *pBuf, uchar bytes)
    {
    	uchar status,byte_ctr;
    	CSN = 0; // Set CSN low, init SPI tranaction
    	status = SPI_RW(reg); // Select register to write to
    	for(byte_ctr=0; byte_ctr<bytes; byte_ctr++) // then write all
    		SPI_RW(*pBuf++);
    	CSN = 1; // Set CSN high again
    	return(status); // return nRF24L01 status byte
    }
    
    void RX_Mode_Init(void)
    {
    	CE=0;
    	SPI_Write_Buf(WRITE_REG + TX_ADDR, TX_ADDRESS, TX_ADR_WIDTH);
    	SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, RX_ADDRESS, RX_ADR_WIDTH);
    	SPI_Write_Reg(WRITE_REG + EN_AA, 0x01); // Enable Auto.Ack:Pipe0
    	SPI_Write_Reg(WRITE_REG + EN_RXADDR, 0x01); // Enable Pipe0
    	SPI_Write_Reg(WRITE_REG + RF_CH, 0);
    	SPI_Write_Reg(WRITE_REG + RX_PW_P0, TX_PLOAD_WIDTH);
    	SPI_Write_Reg(WRITE_REG + RF_SETUP, 0x0f);
    	SPI_Write_Reg(WRITE_REG + CONFIG, 0x0f); // Set PWR_UP bit, enable
    	CE = 1; // Set CE pin high to enable RX device
    }
    
    uchar SPI_Read_Reg(uchar reg)
    {
    	uchar reg_val;
    	CSN = 0; // CSN low, initialize SPI communication
    	SPI_RW(reg); // Select register to read from..
    	reg_val = SPI_RW(0); // ..then read registervalue
    	CSN = 1; // CSN high, terminate SPI communication
    	return(reg_val); // return register value
    }
    
    uchar NRF24L01_TxPacket(uchar *txbuf)
    {
    	uchar state;
       
    	CE=0;
    	SPI_Write_Buf(WR_TX_PLOAD,txbuf,TX_PLOAD_WIDTH); //写数据到TX_BUF
     	CE=1;
    	while(IRQ==1); //等待发送完成
    	LED = ~LED;
    	state=SPI_Read_Reg(STATUS);  
    	SPI_Write_Reg(WRITE_REG+STATUS,state); //清除中断标志TX_DS或MAX_RT
    	if(state&MAX_TX) //达到最多重发中断
    	{
    		SPI_Write_Reg(FLUSH_TX,0xff); //清除TX FIFO寄存器
    		return MAX_TX; 
    	}
    	if(state&TX_OK) //发送完成
    	{
    		return TX_OK;
    	}
    	return 0xff; //发送失败
    }
    
    void Send_Buf(uchar *buf)
    {
    	CE=0;
    	SPI_Write_Reg(WRITE_REG+CONFIG,0x0e);
    	CE=1;
    	delay_us(15);
    	NRF24L01_TxPacket(buf);
    	CE=0;
    	SPI_Write_Reg(WRITE_REG+CONFIG, 0x0f);
    	CE=1;	
    }
    
    int main()
    {
    	uchar buf[TX_PLOAD_WIDTH];
    	
    	RX_Mode_Init();
    	
    	buf[0]=2; //无线串口模块需要第一位标识长度(忽略)
    	buf[1]=0xaa;
    	buf[2]=0x55;
    	
    	while(1)
    	{
    		Send_Buf(buf);
    		
    		delay(1000);
    	}
    }
    

    模块不能自发自收

    TX_ADDR和RX_ADDR_P0地址可以相同。但是TX_ADDR是目标板地址,RX_ADDR_P0是本模块地址。只有收发地址配置正确才能收发成功

    最主要是RX_Mode_Init中寄存器的配置:
    RF_CH,射频通道频率。收发必须一致(F0= 2400 + RF_CH [MHz])
    RF_SETUP,射频寄存器。数据传输速率、发射功率、低噪声放大增益,收发必须一致
    CRCO,校验方式。收发必须一致

  • 相关阅读:
    P1312 [NOIP2011 提高组] Mayan 游戏
    Codeforces Round 736
    CF487E Tourists
    荏苒
    数论
    [NOI2009] 二叉查找树 题解
    元素
    线性基
    杂录
    SQL中关于Join、Inner Join、Left Join、Right Join、Full Join、On、 Where区别
  • 原文地址:https://www.cnblogs.com/zhangxuechao/p/11709588.html
Copyright © 2011-2022 走看看