毕昇杯之无线通信模块

在这个比赛中,我们使用的是24L01这个无线模块,说句实在话,这个模块的功能不是很强大,出错的机率比较大,加上这个模块需要3.3v供电,所以对于5v的系统来讲,这个模块算比较麻烦的一个,这个模块比较容易坏,也许就是取电哪里,我开始没有共地的原因吧!!!

 

      网络上有许多无线的模块,我觉得开始的时候就不应该选择这个无线,因为模块越简单,编程就越复杂,加上我需要4块单片机之间进行通信,其实程序也就是2对1,温湿度采集单片机A,刷卡采集B,屏幕处理C,以及网络模块D,开始无线程序只是简单的一对一,项目开始的时候,就应该把节点搭建好,否则的话,程序就要进行一次大的调整

      在这里我们的项目就因为调试无线程序,大改了好几次,最终实现的只是A,B对C发送数据,之后复制C这个节点到D,那样A,B也可以对D发送数据,但是这样的程序上有个很大的bug,就是c和D不能进行通信,这样对硬件的调整有相当的坑爹了,为了弥补C和D可以同时控制硬件的难题,我们采用了双头开关,也就是使用卧室灯可以由两个开关进行控制这个原理,这样C和D就可以同时控制硬件

  

  也许到这里,一切的问题貌似结束了,但是,双头开关导致的先天不足,在项目后期,就就完全暴露了,因为双头开关只是仅仅控制灯的开灭,但是却不能使用进一步的算法,比如控制几盏灯以什么样的亮度开着,不能控制风扇以什么样的转速转动,这些都是先天的设计导致的一大败笔~~~~但不得不承认,这样的硬件结构,实现起来比较可靠,他们蔬菜大棚使用的是用一块单片机对硬件进行处理,但是好像不怎么可靠,也许双头开关刚好弥补了无线的不足吧!!!!

 

  好了无线的使用心得就总结到这里,下面看一下如何使用无线搭建两个节点的

     程序下载地址:http://download.csdn.net/detail/generoius/7140597

    下面具体看一下无线通信是怎么样实现的

 

 

温湿度传感器,开发板A的程序:发送地址为:unchar code TxAddr[]={0x34,0x43,0x10,0x10,0x01};

刷卡模块,开发板B的发送地址为:unchar code TxAddr[]={0xc2,0xc2,0xc2,0xc2,0xc1};//发送地址

主机接收处理地址为开发板c的接收地址:unchar code RxAddr0[]={0x34,0x43,0x10,0x10,0x01};//编号3接收地址这个地址和发送方地址一样!

          unchar code RxAddr1[]={0xc2,0xc2,0xc2,0xc2,0xc1};

可以看出主机同时可以接收两个地址传送过来的信号,这里便是通道0和通道1共同监控的地址

 

接下来在看变量设置,在主机中定义了如下两个数组,用来监控接收回来的数据

unchar RevTempDate0[16];//同道0接收数据
unchar RevTempDate1[16];//同道1接收数据

 

之后在看寄存器设置:

这里板子A和板子B的设置都是相差不多,因为主要是发送,所以寄存器设置是一样的

void NRFSetTxMode(unchar *TxDate)

{//发送模式

CE=0; 

NRFWriteTxDate(W_REGISTER+TX_ADDR,TxAddr,TX_ADDR_WITDH);//写寄存器指令+接收地址使能指令+接收地址+地址宽度

NRFWriteTxDate(W_REGISTER+RX_ADDR_P0,TxAddr,TX_ADDR_WITDH);//为了应答接收设备,接收通道0地址和发送地址相同

NRFWriteTxDate(W_TX_PAYLOAD,TxDate,TX_DATA_WITDH);//写入数据 

/******下面有关寄存器配置**************/

NRFWriteReg(W_REGISTER+EN_AA,0x01); // 使能接收通道0自动应答

NRFWriteReg(W_REGISTER+EN_RXADDR,0x01); // 使能接收通道0

NRFWriteReg(W_REGISTER+SETUP_RETR,0x0a); // 自动重发延时等待250us+86us,自动重发10次

NRFWriteReg(W_REGISTER+RF_CH,0x40); // 选择射频通道0x40

NRFWriteReg(W_REGISTER+RF_SETUP,0x07); // 数据传输率1Mbps,发射功率0dBm,低噪声放大器增益

NRFWriteReg(W_REGISTER+CONFIG,0x0e); // CRC使能,16位CRC校验,上电 

CE=1;

Delay(5);//保持10us秒以上

}

 

 

这里主要值做好板子c的接收设置,熟悉datasheet的人,就会知道nrf24l01有6个通道,可以同时监控6个节点传过来的数据,这个与起性比价形成鲜明的对比

void NRFSetRXMode()

{

CE=0;

NRFWriteTxDate(W_REGISTER+RX_ADDR_P0,RxAddr0,TX_ADDR_WITDH); // 接收设备接收通道0使用和发送设备相同的发送地址

NRFWriteTxDate(W_REGISTER+RX_ADDR_P1,RxAddr1,TX_ADDR_WITDH); // 接收设备接收通道1使用和发送设备相同的发送地址



NRFWriteReg(W_REGISTER+EN_AA,0x03); // 使能数据通道0和1自动应答

NRFWriteReg(W_REGISTER+EN_RXADDR,0x03); // 使能接收通道0和1



NRFWriteReg(W_REGISTER+RX_PW_P0,TX_DATA_WITDH); // 接收通道0选择和发送通道相同有效数据宽度

NRFWriteReg(W_REGISTER+RX_PW_P1,TX_DATA_WITDH); // 接收通道1选择和发送通道相同有效数据宽度



NRFWriteReg(W_REGISTER+RF_CH,0x40);// 选择射频通道0x40 

NRFWriteReg(W_REGISTER+RF_SETUP,0x07); // 数据传输率1Mbps,发射功率0dBm,低噪声放大器增益

NRFWriteReg(W_REGISTER+CONFIG,0x0f); // CRC使能,16位CRC校验,上电,接收模式 

CE = 1; 

NRFDelay(5); 

}

 

再来看他是如何区分来自不同通道的数据的

void GetDate() 

{

unchar RX_P_NO;//接收通道号

sta=NRFReadReg(R_REGISTER+STATUS);//发送数据后读取状态寄存器

if(RX_DR)     // 判断是否接收到数据

{

RX_P_NO=sta&0x0e;//获取通道号

CE=0;//待机

switch(RX_P_NO)

{

case 0x00:NRFReadRxDate(R_RX_PAYLOAD,RevTempDate0,RX_DATA_WITDH);break;// 从RXFIFO读取数据通道0

case 0x02:NRFReadRxDate(R_RX_PAYLOAD,RevTempDate1,RX_DATA_WITDH);break;// 从RXFIFO读取数据通道1

default:break;

}

lcd_pos(1,0);

write_string(RevTempDate0);

lcd_pos(2,0);

write_string(RevTempDate1);



MAX232SendDate();//发送数据到上位机    

NRFWriteReg(W_REGISTER+STATUS,0xff); //接收到数据后RX_DR,TX_DS,MAX_PT都置高为1,通过写1来清楚中断标

CSN=0;

NRFSPI(FLUSH_RX);//用于清空FIFO !!关键!!不然会出现意想不到的后果!!!大家记住!! 

CSN=1;    

}

//NRFWriteReg(W_REGISTER+STATUS,0xff); //接收到数据后RX_DR,TX_DS,MAX_PT都置高为1,通过写1来清楚中断标    

}

 

我没有在往下面研究了,到这里的无线发送就够用了,还有一个事情,就是多看datasheet,结合例子看,调试程序串口是个好东西,好了,无线总结到这里!!

 

版权所有,转载请注明链接地址:http://www.cnblogs.com/fengdashen/p/3642757.html

技术讨论QQ:1070937053

你可能感兴趣的:(通信)