CC2530下ZigBee协议栈中添加BH1750数字光照传感器

来源:互联网 发布:ubuntu 邮件 编辑:程序博客网 时间:2024/06/07 20:07

项目里需要获得光照强度,之前用的是光敏电阻,但是光敏电阻实在不精确,换用BH1750数字光照传感器。网上购买后,送的资料都是单片机的,移植到ZigBee协议栈里面,时序有些问题,在网上找的一些资料,很杂乱。主要出现两个问题:一、读取不到数据;二、读取到的数据是乱的。

仔细研究之后,发现,第一个问题读不到数据,八成是延时函数有差别;第二个问题,一直以为是时序的问题,纠结了很久还是没弄好,后来突然想把数据处理的地方单独弄出来测试,结果正是这里,采集到数据,转为字符串的时候,数据类型跟所需要的数据类型有差,最大范围不同,可能每个人宏或者自定义的数据类型都不太一样,所以移植过来的时候,虽然名字一样,但是实际上定义的时候不一样,导致使用的时候不容易发现问题。

下面贴上代码。(之前在网上看到别人做的bh1750,想问他买代码,结果告诉我一个代码要我80,瞬间无语,还好自己弄出来了 ,共享给大家,也给自己提个醒,最是觉得没有问题的地方,往往就是问题所在,需时刻抱有怀疑的态度)

BH1750.h:

#ifndef __BH1750_H#define __BH1750_H#include <ioCC2530.h>#define st(x)      do { x } while (__LINE__ == -1)#define HAL_IO_SET(port, pin, val)        HAL_IO_SET_PREP(port, pin, val)#define HAL_IO_SET_PREP(port, pin, val)   st( P##port##_##pin## = val; )#define HAL_IO_GET(port, pin)   HAL_IO_GET_PREP( port,pin)#define HAL_IO_GET_PREP(port, pin)   ( P##port##_##pin)#define LIGHT_SCK_0()         HAL_IO_SET(1,3,0)#define LIGHT_SCK_1()         HAL_IO_SET(1,3,1)#define LIGHT_DTA_0()         HAL_IO_SET(1,1,0)#define LIGHT_DTA_1()         HAL_IO_SET(1,1,1)#define LIGHT_DTA()          HAL_IO_GET(1,1)#define LIGHT_SCK()          HAL_IO_GET(1,3)#define SDA_W() (P1DIR |=(1 << 1)  )#define SDA_R() (P1DIR &=~(1 << 1) )                       #define LIGHT_INIT()                           \do{                                            \P1SEL &= ~0x08;                        \P1DIR |=0x08;                           \P1_3 = 1;                                  \                                 \P1SEL &= ~0x02;                        \P1DIR |= 0x02;                         \P1_1 = 1;                              \}while(0)extern unsigned short get_light(void);#endif // __BH1750_H


BH1750.c:

#include "BH1750.h"#include "OnBoard.h"void halMcuWaitUs(uint16 usec){    while(usec--)    {        asm("nop");        asm("nop");        asm("nop");        asm("nop");        asm("nop");        asm("nop");        asm("nop");        asm("nop");        asm("nop");        asm("nop");    }}//以ms延时void halMcuWaitMs(uint16 msec){    while(msec--)        halMcuWaitUs(1000);}void delay_us(){  halMcuWaitUs(1); // MicroWait(1);}void delay_5us(){  halMcuWaitUs(5);  //MicroWait(5);}void delay_10us(){  halMcuWaitUs(10);  //MicroWait(10);}void delay_nms(int n){  halMcuWaitMs(n);}/****************************/static void start_i2c(void){  SDA_W() ;  LIGHT_DTA_1();//  LIGHT_SCK_1() ;//  delay_us() ;  LIGHT_DTA_0() ;  delay_us()  ;  LIGHT_SCK_0() ;  delay_us()  ;  //delay()  ;}static void stop_i2c(void){  SDA_W() ;  LIGHT_DTA_0() ;  delay_us();  LIGHT_SCK_1() ;  delay_us();  LIGHT_DTA_1() ;  delay_us();  LIGHT_SCK_0() ;  delay_us();  }static char i2c_send(unsigned char val)                 {        int i;        char error=0;        SDA_W();        for(i=0x80;i>0;i/=2){if(val&i)LIGHT_DTA_1();elseLIGHT_DTA_0();delay_us();LIGHT_SCK_1() ; delay_us();LIGHT_SCK_0() ;delay_us();}        LIGHT_DTA_1();        SDA_R();        delay_us();        //delay_us();        LIGHT_SCK_1() ;         delay_us();        if(LIGHT_DTA())            error=1;        delay_us();        LIGHT_SCK_0() ;        return error;        }static char i2c_read(char ack){        int i;        char val=0;        LIGHT_DTA_1();        //SDA_R();        for(i=0x80;i>0;i/=2)                {                                                LIGHT_SCK_1() ;                        delay_us();                        SDA_R();                        //SDA_W();                        //LIGHT_DTA_0();                        //LIGHT_DTA_0() ;                                                //delay_us();                        if(LIGHT_DTA())                                val=(val|i);                        delay_us();                        //SDA_R();                        LIGHT_SCK_0() ;                        delay_us();                                                                }        SDA_W();        if(ack)                LIGHT_DTA_0();        else                LIGHT_DTA_1();        delay_us();        LIGHT_SCK_1() ;        delay_us();        LIGHT_SCK_0() ;        LIGHT_DTA_1();        return val;        }unsigned short get_light(void){                unsigned char ack1=1;        unsigned char ack2=1;        unsigned char ack3=1;        unsigned char ack4=1;        unsigned char ack5=1;        unsigned char ack6=1;        unsigned char ack7=1;                unsigned char t0;        unsigned char t1;        unsigned short t;        P1DIR |= (1 << 1);        delay_nms(200);start_i2c();ack1=i2c_send(0x46);if(ack1)return 255;ack2=i2c_send(0x01);if(ack2)return 254;stop_i2c();           //initstart_i2c();ack3=i2c_send(0x46);if(ack3)return 253;ack4=i2c_send(0x01);if(ack4)return 252;stop_i2c();//powerstart_i2c();ack5=i2c_send(0x46);if(ack5)return 251;ack6=i2c_send(0x10);if(ack6)return 250;stop_i2c();                             delay_nms(1500);        start_i2c();        ack7=i2c_send(0x47);if(ack7)return 249;                                t0 = i2c_read(1);        t1 = i2c_read(0);        stop_i2c();        t =  ((short)t0)<<8;        t |= t1;        return t;}

在主函数中加入以下函数(注意,此处就是最容易忽视的地方,uint应该是unsigned int,不能是范围太小的类型):

char wan,qian,bai,shi,ge;void conversion(unsigned int temp_data)    {    wan=(uint)temp_data/10000 ;    temp_data=temp_data%10000;     qian=(uint)temp_data/1000 ;    temp_data=temp_data%1000;      bai=(uint)temp_data/100;    temp_data=temp_data%100;        shi=(uint)temp_data/10;    temp_data=temp_data%10;          ge=(uint)temp_data;}
调用光照获取函数,讲数据转为字符串:

uint32 w;        w = get_light()/1.2;    conversion(w);    char buf[5];    buf[0] = wan + 48;    buf[1] = qian + 48;    buf[2] = bai + 48;    buf[3] = shi + 48;    buf[4] = ge + 48;
得到字符数组后,就很随意了。



阅读全文
0 0
原创粉丝点击