找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 14649|回復(fù): 25
打印 上一主題 下一主題
收起左側(cè)

單片機(jī)驅(qū)動bmp280氣壓傳感器實(shí)現(xiàn)應(yīng)用源碼

  [復(fù)制鏈接]
跳轉(zhuǎn)到指定樓層
樓主
ID:165424 發(fā)表于 2018-1-24 10:45 | 只看該作者 回帖獎勵 |倒序?yàn)g覽 |閱讀模式
之前用bmp280,網(wǎng)上的資源很少,尤其是51單片機(jī)用這個模塊的,所以現(xiàn)在任務(wù)做好了,模塊調(diào)通,附上成果,供大家參考免去彎路。廢話不多說,附件是bmp280的c和h文件,沒帶程序,程序有很多亂七八糟的什么4463,opt101,dht11,pcf8563.。。。。就不帶了,歡迎壇友一起討論



單片機(jī)源程序如下:
  1. #include <string.h>
  2. #include "bmp280111.h"
  3. #include  <math.h>    //Keil library  
  4. #include  <stdlib.h>  //Keil library  
  5. #include  <stdio.h>   //Keil library       
  6. #include  <INTRINS.H> //Keil library  
  7. #include "sensor_am21xx.h"
  8. #define   uchar unsigned char
  9. #define   uint unsigned int       

  10. #define        BMP280_SlaveAddress   0xec          //定義器件在IIC總線中的從地址                              

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

  12. unsigned short dig_T1;
  13. short dig_T2;
  14. short dig_T3;
  15. unsigned short dig_P1;
  16. short dig_P2;
  17. short dig_P3;
  18. short dig_P4;
  19. short dig_P5;
  20. short dig_P6;
  21. short dig_P7;
  22. short dig_P8;
  23. short dig_P9;


  24. void delay()    //略微延時(shí)  6us約>4.7us
  25. {
  26. _nop_();
  27.   _nop_();
  28.    _nop_();
  29.     _nop_();
  30.          _nop_();
  31.           _nop_();
  32. }
  33. void iic_start()   //啟動信號
  34. {
  35.   SDA=1;
  36.   SCL=1;
  37.   delay();
  38.   SDA=0;
  39.   delay();
  40.   SCL=0;
  41. }
  42. void iic_stop()  //停止信號
  43. {
  44.         SDA=0;
  45.         SCL=1;
  46.         delay();
  47.         SDA=1;
  48.         delay();
  49.         SCL=0;
  50. }

  51. void iic_ack()   //應(yīng)答信號
  52. {
  53.         uchar i=0;
  54.         SCL=1;
  55.         delay();
  56.         while((SDA==1)&&(i<255))
  57.         i++;
  58.         SCL=0;
  59.         delay();
  60. }

  61. void iic_send_byte(uchar bat)  //發(fā)送數(shù)據(jù)
  62. {
  63.         uchar i,temp;
  64.         temp=bat;
  65.         for(i=0;i<=7;i++)
  66.         {
  67.           temp=temp<<1;
  68.           SCL=0;
  69.           SDA=CY;
  70.           delay();
  71.           SCL=1;
  72.           delay();
  73.         }
  74.         SCL=0;
  75.         delay();
  76.         SDA=1;
  77.         delay();
  78. }

  79. unsigned char iic_rev()  //接受數(shù)據(jù)
  80. {
  81.   uchar temp,i;
  82.   SCL=0;
  83.   delay();
  84.   SDA=1;
  85.   for(i=0;i<=7;i++)
  86.   {
  87.    SCL=1;
  88.    delay();
  89.    temp=(temp<<1)|SDA;
  90.    SCL=0;
  91.    delay();
  92.   }
  93.   delay();
  94.   return temp;
  95. }


  96. uchar Single_Read(uchar ST_Address)
  97. {
  98.         uchar REG_data;
  99.         //uchar bit;
  100.        
  101.         iic_start();         //起始信號
  102.         iic_send_byte(BMP280_SlaveAddress);           //發(fā)送設(shè)備地址+寫信號
  103.         iic_ack();
  104.         iic_send_byte(ST_Address);             //發(fā)送存儲單元地址
  105.         iic_ack();
  106.         iic_start();                          //起始信號
  107.         iic_send_byte(BMP280_SlaveAddress+1);         //發(fā)送設(shè)備地址+讀信號
  108.         iic_ack();
  109.         REG_data = iic_rev();     
  110.         iic_ack();    //最后一個數(shù)據(jù)需要回NOACK
  111.         return REG_data;
  112. }

  113. void Single_Write(uchar SlaveAddress,uchar REG_Address,uchar REG_data)
  114. {
  115.     iic_start();                       //起始信號
  116.     iic_send_byte(SlaveAddress);   //發(fā)送設(shè)備地址+寫信號
  117.         iic_ack();
  118.         iic_send_byte(REG_Address);    //內(nèi)部寄存器地址
  119.         iic_ack();
  120.         iic_send_byte(REG_data);       //內(nèi)部寄存器數(shù)據(jù)
  121.         iic_ack();
  122.         iic_stop();                   //發(fā)送停止信號
  123. }

  124. //*********************************************************
  125. //讀出BMP085內(nèi)部數(shù)據(jù),連續(xù)兩個
  126. //*********************************************************
  127. short Multiple_read(uchar ST_Address)
  128. {   
  129.         uchar msb, lsb;
  130.         short _data;
  131.        
  132.         lsb = Single_Read(ST_Address);
  133.         msb = Single_Read(ST_Address+1);
  134.        
  135.         _data = msb << 8;
  136.         _data |= lsb;       
  137.         //rt_kprintf("data is %x %x\n",msb,lsb);
  138.         return _data;
  139. }
  140. //*********************************************************
  141. //讀出BMP085內(nèi)部數(shù)據(jù),連續(xù)三個
  142. //*********************************************************
  143. long Multiple_three_read(uchar ST_Address)
  144. {   
  145.         uchar msb, lsb,xlsb;
  146.         long _data = 0;
  147.        
  148.         msb = Single_Read(ST_Address);
  149.         lsb = Single_Read(ST_Address+1);
  150.         xlsb = Single_Read(ST_Address+2);
  151.        
  152.         //rt_kprintf("data is %x %x %x\n",msb,lsb,xlsb);
  153.        
  154. //         _data = msb << 16;                ////stm32可以這么用,51有的單片機(jī)不可以,重要!。
  155. //         _data |= lsb << 8;       
  156. //         _data |= xlsb;
  157. //         _data = _data >> 4;
  158.         _data=(long)(((uint32_t)msb<<12)|((uint32_t)lsb<<4)|((uint32_t)xlsb>>4));
  159.         return _data;
  160. }

  161. //**************************************************************

  162. //初始化BMP280,根據(jù)需要請參考pdf進(jìn)行修改**************
  163. void Init_BMP280(void)
  164. {
  165.         unsigned short temp = 0;
  166.         unsigned char write_byte;

  167.         temp = Single_Read(0xd0);//讀取id、判斷iic是否正常模塊是否正常,讀取出來的地址是0x58就是對的
  168. //         if(temp==0x58)printf("BMP280 ID IS: 0x%X\n",temp);
  169. //         else printf("BMP280 ID IS FAIL: 0x%X\n",temp);

  170.         dig_T1 = Multiple_read(0x88);
  171.         dig_T2 = Multiple_read(0x8A);
  172.         dig_T3 = Multiple_read(0x8C);
  173.         dig_P1 = Multiple_read(0x8E);
  174.         dig_P2 = Multiple_read(0x90);
  175.         dig_P3 = Multiple_read(0x92);
  176.         dig_P4 = Multiple_read(0x94);
  177.         dig_P5 = Multiple_read(0x96);
  178.         dig_P6 = Multiple_read(0x98);
  179.         dig_P7 = Multiple_read(0x9A);
  180.         dig_P8 = Multiple_read(0x9C);
  181.         dig_P9 = Multiple_read(0x9E);



  182.         write_byte = 0x91;//write_byte
  183.         Single_Write(BMP280_SlaveAddress,0xf4,0xb3);
  184.         write_byte = 0x00;//配置
  185.         Single_Write(BMP280_SlaveAddress,0xf5,5<<2);//5<<2
  186.         //rt_thread_delay(RT_TICK_PER_SECOND);
  187.         Delay_N1ms(200);       
  188. }
  189. //***********************************************************************

  190. long bmp280Convert(void)
  191. {
  192.         long adc_T;
  193.         long adc_P;
  194.         long var1, var2,t_fine,T,p;

  195.          //rt_kprintf("----------------------------\n");
  196.        
  197.         //adc_T = Multiple_three_read(0xFA);
  198.         adc_T = Multiple_three_read(0xFA);    // 讀取溫度
  199.         //adc_P = Multiple_three_read(0xF7);
  200.         adc_P = Multiple_three_read(0xF7); // 讀取壓強(qiáng)

  201.         if(adc_P == 0)
  202.         {
  203.                 return 0;
  204.         }
  205.         //Temperature
  206.         var1 = (((double)adc_T)/16384.0-((double)dig_T1)/1024.0)*((double)dig_T2);
  207.         //rt_kprintf("var1 is %d\n",var1);
  208.         var2 = ((((double)adc_T)/131072.0-((double)dig_T1)/8192.0)*(((double)adc_T)/131072.0-((double)dig_T1)/8192.0))*((double)dig_T3);
  209.         //rt_kprintf("var2 is %d\n",var2);
  210.        
  211.         t_fine = (uint32)(var1+var2);
  212.         //rt_kprintf("t_fine is %d\n",t_fine);
  213.        
  214.         T = (var1+var2)/5120.0;
  215.         T = T;
  216.         //rt_kprintf("temperature is %d\n",T);
  217.        
  218.         var1 = ((double)t_fine/2.0)-64000.0;
  219.         //rt_kprintf("var1 is %d\n",var1);
  220.        
  221.         var2 = var1*var1*((double)dig_P6)/32768.0;
  222.         //rt_kprintf("var2 is %d\n",var2);
  223.        
  224.         var2 = var2+var1*((double)dig_P5)*2.0;
  225.         //rt_kprintf("var2 is %d\n",var2);
  226.        
  227.         var2 = (var2/4.0)+(((double)dig_P4)*65536.0);
  228.         //rt_kprintf("var2 is %d\n",var2);
  229.        
  230.         var1 = (((double)dig_P3)*var1*var1/524288.0+((double)dig_P2)*var1)/524288.0;
  231.         //rt_kprintf("var1 is %d\n",var1);
  232.        
  233.         var1 = (1.0+var1/32768.0)*((double)dig_P1);
  234.         //rt_kprintf("var1 is %d\n",var1);
  235.        
  236.         p = 1048576.0-(double)adc_P;
  237.         //rt_kprintf("p is %d\n",p);

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

  241. …………限于本文篇幅 余下代碼請從51黑下載附件…………
復(fù)制代碼

所有資料51hei提供下載:
bmp280111.rar (2.85 KB, 下載次數(shù): 450)




評分

參與人數(shù) 1黑幣 +50 收起 理由
admin + 50 共享資料的黑幣獎勵!

查看全部評分

分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏10 分享淘帖 頂3 踩
回復(fù)

使用道具 舉報(bào)

沙發(fā)
ID:209899 發(fā)表于 2018-2-9 17:45 | 只看該作者
我之前那個確實(shí)不能讀取280的。試著跑了一下您的程序,感覺讀出來的值好像還是有點(diǎn)不對。有空咱交流一下唄
回復(fù)

使用道具 舉報(bào)

板凳
ID:209899 發(fā)表于 2018-2-9 17:47 | 只看該作者
你好,我之前發(fā)的程序后面試了一下確實(shí)無法讀取280?茨呀(jīng)做出來了,于是就跑來試了一下,感覺數(shù)值好像有點(diǎn)不對,有空咱交流一下
回復(fù)

使用道具 舉報(bào)

地板
ID:165424 發(fā)表于 2018-2-24 16:13 | 只看該作者
zaza21 發(fā)表于 2018-2-9 17:47
你好,我之前發(fā)的程序后面試了一下確實(shí)無法讀取280?茨呀(jīng)做出來了,于是就跑來試了一下,感覺數(shù)值好像 ...

可以留個聯(lián)系方式
回復(fù)

使用道具 舉報(bào)

5#
ID:165424 發(fā)表于 2018-2-24 16:14 | 只看該作者
zaza21 發(fā)表于 2018-2-9 17:47
你好,我之前發(fā)的程序后面試了一下確實(shí)無法讀取280?茨呀(jīng)做出來了,于是就跑來試了一下,感覺數(shù)值好像 ...

論壇需要審核,上午回復(fù)你的下午還沒有審核通過,有點(diǎn)慢
回復(fù)

使用道具 舉報(bào)

6#
ID:305849 發(fā)表于 2018-4-19 16:11 | 只看該作者
我想要積分
回復(fù)

使用道具 舉報(bào)

7#
ID:313227 發(fā)表于 2018-4-21 17:06 | 只看該作者
感謝樓主分享,用SPI驅(qū)動280的太少了
回復(fù)

使用道具 舉報(bào)

8#
ID:252000 發(fā)表于 2018-8-12 23:54 | 只看該作者
感謝感謝
回復(fù)

使用道具 舉報(bào)

9#
ID:462402 發(fā)表于 2019-1-7 21:31 | 只看該作者
這能測氣壓高度嗎?
回復(fù)

使用道具 舉報(bào)

10#
ID:472304 發(fā)表于 2019-3-9 10:45 | 只看該作者
我現(xiàn)在也準(zhǔn)備用BMP280芯片。
看了一下程序,有兩個問題:
    1.#include "sensor_am21xx.h" 這個是什么意思?指哪個單片機(jī)?
    2.#include "MA82G.h"這個呢?
回復(fù)

使用道具 舉報(bào)

11#
ID:165424 發(fā)表于 2019-4-13 23:50 | 只看該作者
4125027 發(fā)表于 2019-3-9 10:45
我現(xiàn)在也準(zhǔn)備用BMP280芯片。
看了一下程序,有兩個問題:
    1.#include "sensor_am21xx.h" 這個是什么 ...

這兩個是頭文件調(diào)用,單片機(jī)用的是ma82g5b32
回復(fù)

使用道具 舉報(bào)

12#
ID:556497 發(fā)表于 2019-6-26 16:23 | 只看該作者
最近在測試,讀取的溫度有點(diǎn)高,大氣壓力不穩(wěn)定,好頭疼啊,尤其大氣壓,數(shù)值偶爾會突變,這樣即使標(biāo)定的話,也不會準(zhǔn)確,好頭疼,有沒有調(diào)試成功的看看啊
回復(fù)

使用道具 舉報(bào)

13#
ID:382507 發(fā)表于 2019-7-13 19:56 | 只看該作者
謝謝分享
回復(fù)

使用道具 舉報(bào)

14#
ID:604530 發(fā)表于 2019-8-28 01:19 | 只看該作者
一直在找這個
回復(fù)

使用道具 舉報(bào)

15#
ID:263517 發(fā)表于 2019-9-24 18:23 | 只看該作者
這個程序用的時(shí)候發(fā)現(xiàn)一個問題   讀取的氣壓值會逐漸減小   減小的速度非常慢
回復(fù)

使用道具 舉報(bào)

16#
ID:620978 發(fā)表于 2019-10-17 17:38 | 只看該作者
您好,我用的51單片機(jī)燒錄后,顯示不出數(shù)據(jù),是用IIC嗎?
這是全部代碼嗎,還是只是部分文件?
回復(fù)

使用道具 舉報(bào)

17#
ID:647448 發(fā)表于 2019-11-22 20:07 | 只看該作者
bme280大氣壓力溫濕度傳感器程序
回復(fù)

使用道具 舉報(bào)

18#
ID:647448 發(fā)表于 2019-11-23 13:21 | 只看該作者
不是完整程序
回復(fù)

使用道具 舉報(bào)

19#
ID:55207 發(fā)表于 2020-6-17 21:15 | 只看該作者
正要用到這個模塊,學(xué)習(xí)一下
回復(fù)

使用道具 舉報(bào)

20#
ID:72088 發(fā)表于 2020-10-20 11:28 | 只看該作者
BMP280中文資料沒找到,網(wǎng)上沒有,英文看不懂,哎
回復(fù)

使用道具 舉報(bào)

21#
ID:825140 發(fā)表于 2021-7-3 08:44 | 只看該作者
樓樓我最近在做一個用bmp280測室內(nèi)外大氣壓差的項(xiàng)目,我測試的時(shí)候發(fā)現(xiàn)兩個傳感器的差值會隨著時(shí)間變化,比如說早上+5pa,下午+50帕,或者有的直接從+100pa變成-100多帕,請問樓樓有什么經(jīng)驗(yàn)分享一下嗎

U594`[S73FWFT}F$TM4(VSR.png (837.23 KB, 下載次數(shù): 78)

U594`[S73FWFT}F$TM4(VSR.png
回復(fù)

使用道具 舉報(bào)

22#
ID:483991 發(fā)表于 2021-7-3 09:17 | 只看該作者

一上線就想著要別人給積分!誰讓你不給別人點(diǎn)贊,發(fā)評論加關(guān)注呢?活該你沒有分!
回復(fù)

使用道具 舉報(bào)

23#
ID:975054 發(fā)表于 2021-12-23 10:02 | 只看該作者
triggerfan 發(fā)表于 2021-7-3 08:44
樓樓我最近在做一個用bmp280測室內(nèi)外大氣壓差的項(xiàng)目,我測試的時(shí)候發(fā)現(xiàn)兩個傳感器的差值會隨著時(shí)間變化,比 ...

近日參考當(dāng)?shù)靥鞖忸A(yù)報(bào)氣壓數(shù)據(jù),發(fā)現(xiàn)BMP280氣壓數(shù)據(jù)總是偏低約1850Pa(相當(dāng)于海拔高了150米了);后來讀取全部修正因子及公式里的所有變量計(jì)算值,發(fā)現(xiàn):
一是dig_P1數(shù)值為-30205(手冊例子是+34677,無意間看到有個官方API資料里說該值范圍是30000到40000),但未影響最終計(jì)算結(jié)果,用手冊數(shù)值或任何其他+數(shù)代入結(jié)果誤差極大;
二是實(shí)測公式里最后一個var1總是=0,造成后面氣壓計(jì)算值總是低1850Pa左右,我干脆寫了條語句if var1=0  retune p跳過去了,實(shí)際只獲取前面的計(jì)算值p,也就是說沒有用到dig_7.8.9三個修正參數(shù)還準(zhǔn)確;不知道為什么,但感覺總比我自己最后直接+1850Pa修訂值好一些.

全部實(shí)測參數(shù)20211214下午/1215:
adc_T = 528832
adc_P = 470864
var1  = 125868.1
var2  = -350.2
t_fine= 125517
T     = 24.5
dig_T1 = 28204  //1129讀數(shù)28160不同(dig_T1對溫度影響極大少0.7℃):原來讀之前延時(shí)一下就一致,新代碼卻無影響,但應(yīng)該加上;
dig_T2 = 26586
dig_T3 = -1000
dig_P1 = -30205            //與手冊(要求30000-42000)差距大!但結(jié)果可以;直接代入正數(shù)倒過來結(jié)果影響極大不準(zhǔn);
dig_P2 = -10760
dig_P3 = 3024
dig_P4 = 211
dig_P5 = 437
dig_P6 = -7
dig_P7 = 15500
dig_P8 = -14600
dig_P9 = 6000
var1 = -1241.5
var2 = -329.3
var2 = -1085400.0
var2 = 13556750.0
var1 = 25.5
var1 = 35358.5
p = 577712.0             
p = 101531.9             //這個值比較準(zhǔn)!后面-1.86Kpa相當(dāng)于高了155m挺多的,
//var1 = 0.0             //就這個不對!舍棄后面公式取前面p值就比較準(zhǔn)確!;
//var2 = -45238.2             
//p = 99673.2             //這個值誤差大!
//Px= -1858▲H =   0m   //要特別留意該值變化,可能比直接自己加修訂值準(zhǔn)確些:
      -1590▲H = 778m     吸氣,+778m內(nèi)誤差268Pa22.3m,22.3/778=2.9%,可接受);
      -1957▲H =-290m     吹氣,-290m也誤差 99Pa8.25m,8.25/290=2.8%,可接受);
回復(fù)

使用道具 舉報(bào)

24#
ID:237753 發(fā)表于 2022-1-26 11:26 | 只看該作者
有與單片機(jī)的連接方式嗎
回復(fù)

使用道具 舉報(bào)

25#
ID:1011179 發(fā)表于 2022-3-17 20:49 | 只看該作者
為什么頭文件只有一個而里面包含的頭文件很多?沒給全?
回復(fù)

使用道具 舉報(bào)

26#
ID:262 發(fā)表于 2022-3-18 06:00 | 只看該作者
回復(fù)

使用道具 舉報(bào)

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規(guī)則

手機(jī)版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術(shù)交流QQ群281945664

Powered by 單片機(jī)教程網(wǎng)

快速回復(fù) 返回頂部 返回列表