查看: 3623|回复: 14

[讨论] 商城里卖的PM2.5激光粉尘传感器,对应代码问题很多啊

[复制链接]
本帖最后由 zuyang 于 2016-3-25 18:12 编辑

DFRobot商城里面卖的PM2.5激光粉尘传感器:
product.png


商品地址: http://www.dfrobot.com.cn/goods-1113.html

Wiki页面地址: http://wiki.dfrobot.com.cn/index.php/(SKU:SEN0177)PM2.5%E6%BF%80%E5%85%89%E7%B2%89%E5%B0%98%E4%BC%A0%E6%84%9F%E5%99%A8


Wiki里面给的代码是这样的:
  1. //******************************
  2. //*Copyright (c) 2015, DFRobot
  3. //*All rights reserved
  4.   //*Abstract: Read value of PM1,PM2.5 and PM10 of air quality
  5. //*
  6. //*Version:V2.0
  7. //*Author:Jason
  8. //*Date:Feb.2016
  9. //******************************
  10. #include <Arduino.h>
  11. #define LENG 32
  12. char buf[LENG];

  13. int PM01Value=0;          //define PM1.0 value of the air detector module
  14. int PM2_5Value=0;         //define PM2.5 value of the air detector module
  15. int PM10Value=0;         //define PM10 value of the air detector module

  16. void setup()
  17. {
  18.   Serial.begin(115200);
  19. }

  20. void loop()
  21. {
  22.   if(Serial.available())
  23.   {
  24.     Serial.readBytes(buf,LENG);
  25.     if(buf[0] == 0x42 && buf[1] == 0x4d){
  26.       if(checkValue(buf,LENG)){
  27.         PM01Value=transmitPM01(buf); //count PM1.0 value of the air detector module
  28.         PM2_5Value=transmitPM2_5(buf);//count PM2.5 value of the air detector module
  29.         PM10Value=transmitPM10(buf); //count PM10 value of the air detector module
  30.       }           
  31.     }
  32.   }
  33.   static unsigned long OledTimer=millis();  
  34.     if (millis() - OledTimer >=1000)
  35.     {
  36.       OledTimer=millis();
  37.       
  38.       Serial.print("PM1.0: ");  //send PM1.0 data to bluetooth
  39.       Serial.print(PM01Value);
  40.       Serial.println("  ug/m3");            
  41.    
  42.       Serial.print("PM2.5: ");  //send PM1.0 data to bluetooth
  43.       Serial.print(PM2_5Value);
  44.       Serial.println("  ug/m3");     
  45.       
  46.       Serial.print("PM10:  ");  //send PM1.0 data to bluetooth
  47.       Serial.print(PM10Value);
  48.       Serial.println("  ug/m3");   
  49.     }
  50.   
  51. }
  52. char checkValue(char *thebuf, char leng)
  53. {  
  54.   char receiveflag=0;
  55.   int receiveSum=0;
  56.   char i=0;

  57.   for(i=0;i<leng;i++)
  58.   {
  59.   receiveSum=receiveSum+thebuf[i];
  60.   }
  61.    
  62.   if(receiveSum==((thebuf[leng-2]<<8)+thebuf[leng-1]+thebuf[leng-2]+thebuf[leng-1]))  //check the serial data
  63.   {
  64.     receiveSum=0;
  65.     receiveflag=1;
  66.   }
  67.   return receiveflag;
  68. }

  69. int transmitPM01(char *thebuf)
  70. {
  71.   int PM01Val;
  72.   PM01Val=((thebuf[4]<<8) + thebuf[5]); //count PM1.0 value of the air detector module
  73.   return PM01Val;
  74. }

  75. //transmit PM Value to PC
  76. int transmitPM2_5(char *thebuf)
  77. {
  78.   int PM2_5Val;
  79.   PM2_5Val=((thebuf[6]<<8) + thebuf[7]);//count PM2.5 value of the air detector module
  80.   return PM2_5Val;
  81.   }

  82. //transmit PM Value to PC
  83. int transmitPM10(char *thebuf)
  84. {
  85.   int PM10Val;
  86.   PM10Val=((thebuf[8]<<8) + thebuf[9]); //count PM10 value of the air detector module  
  87.   return PM10Val;
  88. }
复制代码

还是今年二月份更新的,但是,烧到板子上,接好传感器,并没有结果出来。

我自己分析的原因如下:

1.传感器串口的波特率是9600,Wiki页面里面已经写清楚了,代码里面使用的是115200
BTL.png


2.直接使用Serial.readBytes函数,因为传感器是每秒自动发送数据,这样读取的数据起始位是随机的,根本无法继续对数据进行处理。


3.buf的类型为char,应该为unsigned char。类型为char时,会导致checksum出错(认为读取结果有负数),也会导致PM2.5的结果有负数出现。



下面是我修改的代码:
PM.zip (1.23 KB, 下载次数: 89)

kevinzhang19701  中级技匠

发表于 2016-3-29 12:47:48

顺便咨询两个问题:

1. 一处是这里的“,5”是什么意思?

123132cqcyzv4qgvx2ww4c.jpg

2. 另一处是这里,为什么用millis()作延迟,而不是delay()?我更换为delay()后试过,PM数据突然全变成了5位数!!
123319zpyg0d5cejbbwjpe.jpg
回复 支持 1 反对 0

使用道具 举报

Cain  初级技匠

发表于 2016-3-24 16:57:41

厉害,支持了,一直觉得PM2.5的库写得太讨巧
回复 支持 反对

使用道具 举报

zuyang  见习技师
 楼主|

发表于 2016-3-24 16:59:59

Cain 发表于 2016-3-24 16:57
厉害,支持了,一直觉得PM2.5的库写得太讨巧

去年还是有PM2.5库的,今年二月代码更新之后就没有用自己写的库了
回复 支持 反对

使用道具 举报

MoonShine  中级技匠

发表于 2016-3-24 17:02:06

我也试过,还是你仔细啊!
回复 支持 反对

使用道具 举报

Jason_G  高级技师

发表于 2016-3-24 23:19:13

您好,这个样例代码是我提供的,对于代码中的问题给你们带来诸多不便,深表歉意,感谢您对提供的样例代码的修正,学习了,非常感谢!
原来的库因为其中使用的硬件串口的库和高版本的IDE存在不兼容的问题,导致模块发送过来的数据读取存在问题,所以没有继续使用。波特率的问题我很纳闷,我测试代码是9600,对数据的处理的确不够严谨。
感谢您的指正!
回复 支持 反对

使用道具 举报

kevinzhang19701  中级技匠

发表于 2016-3-25 12:12:58

有意思,是细心人。
回复 支持 反对

使用道具 举报

Cain  初级技匠

发表于 2016-3-29 15:44:16

问下,你编译的环境是?试过在Arduino上,但编译不过的,第一个报错就是数值类型转换没有做
回复 支持 反对

使用道具 举报

diaosi  学徒

发表于 2016-6-17 19:06:43

Cain 发表于 2016-3-29 15:44
问下,你编译的环境是?试过在Arduino上,但编译不过的,第一个报错就是数值类型转换没有做 ...

您好,我看wiki上更新了您的代码。我先上来用软串口不行,换成硬串口出数据了。。是为什么?
回复 支持 反对

使用道具 举报

Cain  初级技匠

发表于 2016-6-21 11:04:53

diaosi 发表于 2016-6-17 19:06
您好,我看wiki上更新了您的代码。我先上来用软串口不行,换成硬串口出数据了。。是为什么? ...

在wiki中教程样例为了配合教程对程序进行了修改,连接的是硬件串口。在代码开头说明中也有提到,请根据连线图来使用。而楼主的源程序的确使用的是软串口,这样能释放硬件串口,也是个不错的选择
回复 支持 反对

使用道具 举报

xxl84  学徒

发表于 2016-12-21 09:30:05

都是牛人。学习了。
回复 支持 反对

使用道具 举报

aaaak  学徒

发表于 2017-1-13 21:01:20

非常感谢,我在网上找了很多办法,都没有成功,只有这个成功了,让我给Serial口领取特殊值,又充满希望.
回复 支持 反对

使用道具 举报

独自酒醉  学徒

发表于 2017-7-22 23:47:04

刚接触PM2.5,先看看,谢谢!
回复 支持 反对

使用道具 举报

2289247852018  学徒

发表于 2018-1-30 14:35:46

谢谢了,试试看
回复 支持 反对

使用道具 举报

kingaoieong1990  学徒

发表于 2018-4-14 10:18:14

我使用了你的Code (貼上了wiki的)
但是我一直都是出 0
然後試了一下
發覺檢測不了第一個 byte 0x42
想問一下會是什麽問題呢?
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

为本项目制作心愿单
购买心愿单
心愿单 编辑
wifi气象站

硬件清单

btnicon
我也要做!
点击进入购买页面
上海智位机器人股份有限公司 沪ICP备09038501号-4

© 2013-2016 Comsenz Inc. Powered by Discuz! X3.4 Licensed

mail