单片机论坛

 找回密码
 立即注册
QQ登录 只需一步,快速开始
搜索
查看: 161|回复: 2
打印 上一主题 下一主题
收起左侧

单片机驱动bmp280气压传感器实现应用源码

[复制链接]
跳转到指定楼层
楼主
之前用bmp280,网上的资源很少,尤其是51单片机用这个模块的,所以现在任务做好了,模块调通,附上成果,供大家参考免去弯路。废话不多说,附件是bmp280的c和h文件,没带程序,程序有很多乱七八糟的什么4463,opt101,dht11,pcf8563.。。。。就不带了,欢迎坛友一起讨论



单片机源程序如下:
  • #include <string.h>
  • #include "bmp280111.h"
  • #include  <math.h>    //Keil library  
  • #include  <stdlib.h>  //Keil library  
  • #include  <stdio.h>   //Keil library       
  • #include  <INTRINS.H> //Keil library  
  • #include "sensor_am21xx.h"
  • #define   uchar unsigned char
  • #define   uint unsigned int       

  • #define        BMP280_SlaveAddress   0xec          //定义器件在IIC总线中的从地址                              

  • #define OSS 0        // Oversampling Setting (note: code is not set up to use other OSS values)

  • unsigned short dig_T1;
  • short dig_T2;
  • short dig_T3;
  • unsigned short dig_P1;
  • short dig_P2;
  • short dig_P3;
  • short dig_P4;
  • short dig_P5;
  • short dig_P6;
  • short dig_P7;
  • short dig_P8;
  • short dig_P9;


  • void delay()    //略微延时  6us约>4.7us
  • {
  • _nop_();
  •   _nop_();
  •    _nop_();
  •     _nop_();
  •          _nop_();
  •           _nop_();
  • }
  • void iic_start()   //启动信号
  • {
  •   SDA=1;
  •   SCL=1;
  •   delay();
  •   SDA=0;
  •   delay();
  •   SCL=0;
  • }
  • void iic_stop()  //停止信号
  • {
  •         SDA=0;
  •         SCL=1;
  •         delay();
  •         SDA=1;
  •         delay();
  •         SCL=0;
  • }

  • void iic_ack()   //应答信号
  • {
  •         uchar i=0;
  •         SCL=1;
  •         delay();
  •         while((SDA==1)&&(i<255))
  •         i++;
  •         SCL=0;
  •         delay();
  • }

  • void iic_send_byte(uchar bat)  //发送数据
  • {
  •         uchar i,temp;
  •         temp=bat;
  •         for(i=0;i<=7;i++)
  •         {
  •           temp=temp<<1;
  •           SCL=0;
  •           SDA=CY;
  •           delay();
  •           SCL=1;
  •           delay();
  •         }
  •         SCL=0;
  •         delay();
  •         SDA=1;
  •         delay();
  • }

  • unsigned char iic_rev()  //接受数据
  • {
  •   uchar temp,i;
  •   SCL=0;
  •   delay();
  •   SDA=1;
  •   for(i=0;i<=7;i++)
  •   {
  •    SCL=1;
  •    delay();
  •    temp=(temp<<1)|SDA;
  •    SCL=0;
  •    delay();
  •   }
  •   delay();
  •   return temp;
  • }


  • uchar Single_Read(uchar ST_Address)
  • {
  •         uchar REG_data;
  •         //uchar bit;
  •        
  •         iic_start();         //起始信号
  •         iic_send_byte(BMP280_SlaveAddress);           //发送设备地址+写信号
  •         iic_ack();
  •         iic_send_byte(ST_Address);             //发送存储单元地址
  •         iic_ack();
  •         iic_start();                          //起始信号
  •         iic_send_byte(BMP280_SlaveAddress+1);         //发送设备地址+读信号
  •         iic_ack();
  •         REG_data = iic_rev();     
  •         iic_ack();    //最后一个数据需要回NOACK
  •         return REG_data;
  • }

  • void Single_Write(uchar SlaveAddress,uchar REG_Address,uchar REG_data)
  • {
  •     iic_start();                       //起始信号
  •     iic_send_byte(SlaveAddress);   //发送设备地址+写信号
  •         iic_ack();
  •         iic_send_byte(REG_Address);    //内部寄存器地址
  •         iic_ack();
  •         iic_send_byte(REG_data);       //内部寄存器数据
  •         iic_ack();
  •         iic_stop();                   //发送停止信号
  • }

  • //*********************************************************
  • //读出BMP085内部数据,连续两个
  • //*********************************************************
  • short Multiple_read(uchar ST_Address)
  • {   
  •         uchar msb, lsb;
  •         short _data;
  •        
  •         lsb = Single_Read(ST_Address);
  •         msb = Single_Read(ST_Address+1);
  •        
  •         _data = msb << 8;
  •         _data |= lsb;       
  •         //rt_kprintf("data is %x %x\n",msb,lsb);
  •         return _data;
  • }
  • //*********************************************************
  • //读出BMP085内部数据,连续三个
  • //*********************************************************
  • long Multiple_three_read(uchar ST_Address)
  • {   
  •         uchar msb, lsb,xlsb;
  •         long _data = 0;
  •        
  •         msb = Single_Read(ST_Address);
  •         lsb = Single_Read(ST_Address+1);
  •         xlsb = Single_Read(ST_Address+2);
  •        
  •         //rt_kprintf("data is %x %x %x\n",msb,lsb,xlsb);
  •        
  • //         _data = msb << 16;                ////stm32可以这么用,51有的单片机不可以,重要!!!
  • //         _data |= lsb << 8;       
  • //         _data |= xlsb;
  • //         _data = _data >> 4;
  •         _data=(long)(((uint32_t)msb<<12)|((uint32_t)lsb<<4)|((uint32_t)xlsb>>4));
  •         return _data;
  • }

  • //**************************************************************

  • //初始化BMP280,根据需要请参考pdf进行修改**************
  • void Init_BMP280(void)
  • {
  •         unsigned short temp = 0;
  •         unsigned char write_byte;

  •         temp = Single_Read(0xd0);//读取id、判断iic是否正常模块是否正常,读取出来的地址是0x58就是对的
  • //         if(temp==0x58)printf("BMP280 ID IS: 0x%X\n",temp);
  • //         else printf("BMP280 ID IS FAIL: 0x%X\n",temp);

  •         dig_T1 = Multiple_read(0x88);
  •         dig_T2 = Multiple_read(0x8A);
  •         dig_T3 = Multiple_read(0x8C);
  •         dig_P1 = Multiple_read(0x8E);
  •         dig_P2 = Multiple_read(0x90);
  •         dig_P3 = Multiple_read(0x92);
  •         dig_P4 = Multiple_read(0x94);
  •         dig_P5 = Multiple_read(0x96);
  •         dig_P6 = Multiple_read(0x98);
  •         dig_P7 = Multiple_read(0x9A);
  •         dig_P8 = Multiple_read(0x9C);
  •         dig_P9 = Multiple_read(0x9E);



  •         write_byte = 0x91;//write_byte
  •         Single_Write(BMP280_SlaveAddress,0xf4,0xb3);
  •         write_byte = 0x00;//配置
  •         Single_Write(BMP280_SlaveAddress,0xf5,5<<2);//5<<2
  •         //rt_thread_delay(RT_TICK_PER_SECOND);
  •         Delay_N1ms(200);       
  • }
  • //***********************************************************************

  • long bmp280Convert(void)
  • {
  •         long adc_T;
  •         long adc_P;
  •         long var1, var2,t_fine,T,p;

  •          //rt_kprintf("----------------------------\n");
  •        
  •         //adc_T = Multiple_three_read(0xFA);
  •         adc_T = Multiple_three_read(0xFA);    // 读取温度
  •         //adc_P = Multiple_three_read(0xF7);
  •         adc_P = Multiple_three_read(0xF7); // 读取压强

  •         if(adc_P == 0)
  •         {
  •                 return 0;
  •         }
  •         //Temperature
  •         var1 = (((double)adc_T)/16384.0-((double)dig_T1)/1024.0)*((double)dig_T2);
  •         //rt_kprintf("var1 is %d\n",var1);
  •         var2 = ((((double)adc_T)/131072.0-((double)dig_T1)/8192.0)*(((double)adc_T)/131072.0-((double)dig_T1)/8192.0))*((double)dig_T3);
  •         //rt_kprintf("var2 is %d\n",var2);
  •        
  •         t_fine = (uint32)(var1+var2);
  •         //rt_kprintf("t_fine is %d\n",t_fine);
  •        
  •         T = (var1+var2)/5120.0;
  •         T = T;
  •         //rt_kprintf("temperature is %d\n",T);
  •        
  •         var1 = ((double)t_fine/2.0)-64000.0;
  •         //rt_kprintf("var1 is %d\n",var1);
  •        
  •         var2 = var1*var1*((double)dig_P6)/32768.0;
  •         //rt_kprintf("var2 is %d\n",var2);
  •        
  •         var2 = var2+var1*((double)dig_P5)*2.0;
  •         //rt_kprintf("var2 is %d\n",var2);
  •        
  •         var2 = (var2/4.0)+(((double)dig_P4)*65536.0);
  •         //rt_kprintf("var2 is %d\n",var2);
  •        
  •         var1 = (((double)dig_P3)*var1*var1/524288.0+((double)dig_P2)*var1)/524288.0;
  •         //rt_kprintf("var1 is %d\n",var1);
  •        
  •         var1 = (1.0+var1/32768.0)*((double)dig_P1);
  •         //rt_kprintf("var1 is %d\n",var1);
  •        
  •         p = 1048576.0-(double)adc_P;
  •         //rt_kprintf("p is %d\n",p);

  •         p = (p-(var2/4096.0))*6250.0/var1;
  •         //rt_kprintf("p is %d\n",p);
  • ……………………

  • …………限于本文篇幅 余下代码请从51黑下载附件…………
  • 复制代码

    所有资料51hei提供下载:
    bmp280111.rar (2.85 KB, 下载次数: 10)




    评分

    参与人数 1黑币 +50 收起 理由
    admin + 50 共享资料的黑币奖励!
    查看全部评分
    分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
    收藏收藏1 转播转播 分享分享 分享淘帖 顶 踩
    回复 使用道具 举报
    沙发
    zaza21 发表于 2018-2-9 17:45 | 只看该作者
    我之前那个确实不能读取280的。试着跑了一下您的程序,感觉读出来的值好像还是有点不对。有空咱交流一下呗
    回复 使用道具 举报
    板凳
    zaza21 发表于 2018-2-9 17:47 | 只看该作者
    你好,我之前发的程序后面试了一下确实无法读取280。看您已经做出来了,于是就跑来试了一下,感觉数值好像有点不对,有空咱交流一下
    回复 使用道具 举报
    您需要登录后才可以回帖 登录 | 立即注册
    本版积分规则
    QQ|手机版|小黑屋|单片机论坛
    Powered by 单片机教程网
    快速回复 返回顶部 返回列表