|
本帖最后由 HuaShine2015 于 2015-3-18 15:58 编辑
这是自己接触Arduino以来做的第二个作品。 一个手持式PM2.5读取装置,可以远程使用BLE4.0通讯读取检测值。
Arduino源代码和Android通讯apk的源代码都有共享在百度网盘:http://pan.baidu.com/s/1bnGWKMz
主要材料有:Arduino pro mini x1
GP2Y1010AU x1
GP2Y1010AU配套150欧电阻 x1
GP2Y1010AU配套220uF电容 x1
CC2540 BLE 模块 x1
LCD5110模块 x1
DHT模块 x1
LED x2
按键 x1
原理框图:
作品外观:
Android远程通讯APP界面:
PM2.5/PM10国家检测标准如下:
下位机Arduino源码机接线说明: - /*
- PM10/2.5 Auto Tester
- -- by Shine.Hua 2014.03.13
- PM2.5 GP2Y1010AU Sensor:
- Sharp pin 1 (V-LED) => 5V (connected one 150ohm resister to VCC,and connected one 220uf cap to GND)
- Sharp pin 2 (LED-GND) => Arduino GND pin
- Sharp pin 3 (LED) => Arduino pin D5
- Sharp pin 4 (S-GND) => Arduino GND pin
- Sharp pin 5 (Vo) => Arduino A1 pin
- Sharp pin 6 (Vcc) => 5V
-
- DHT11 Sensor:
- Dht pin 1 => 5V
- Dht pin 2 => Arduino pin 4 (connected one 5K resister to VCC)
- Dht pin 3 => NG
- Dht pin 4 => Arduino GND pin
-
- CC2540 BLE 4.0 :
- pin 1 GND => Arduino GND pin
- pin 2 VCC => 3.3V
- pin 6 EN => Arduino pin D13
- pin 14 BRTS => Arduino pin D2
- pin 16 TX => Arduino pin D0 RX
- pin 17 RX => Arduino pin D1 TX
-
- LCD5110:
- CLK - Arduino Pin D8
- DIN - Arduino Pin D9
- DC - Arduino Pin D10
- RST - Arduino Pin D11
- CE - Arduino Pin D12
- BLK - Arduino Pin D7
- VCC - 5V/3.3V
- GND - Arduino GND pin
-
- PM Value Alert_LED (Red):
- VCC - Arduino Pin D6 (connected to 220ohm resister)
- GND - Arduino GND pin
- PM Value Warning_LED (Yellow):
- VCC - Arduino Pin D14 (connected to 220ohm resister) //D14 = A0;
- GND - Arduino GND pin
-
- Wakeup_Key:
- pin 1 - Arduino Pin D3
- pin 2 - Arduino GND pin
- */
- #include <dht11.h> //加载DHT11温湿度模块函数库
- #include <LCD5110_Basic.h> //加载LCD模块函数库
- #define DHT11PIN 4 //定义MCD对应DHT11的侦测PIN常量
- LCD5110 myGLCD(8,9,10,11,12); //定义MCD对应5110 LCD的连接PIN
- extern uint8_t SmallFont[];
- extern uint8_t MediumNumbers[];
- dht11 DHT11; //创建DHT11对象
- int YLED = 14; //定义LED,蓝牙,GP2Y1010AU,相关使能PIN
- int BLLED = 7;
- int RLED = 6;
- int EN = 13;
- int WAKEUP = 3;
- int BRTS = 2;
- int dustPin = A1;
- int ledPower = 5;
- int blTime = 0; //定义相关温湿度颗粒度数据处理变量
- int delayTime = 280;
- int delayTime2 = 40;
- int dustVal = 0;
- float offTime = 9680.0;
- float voltage = 0.0;
- float humidity = 0.0;
- float temperature = 0.0;
- float dustdensity = 0.0;
- float ppmpercf = 0.0;
- String inputString = ""; //定义串口接收缓存字符串
- boolean stringComplete = false;
- boolean wakeUp = false;
- void init_device(){ //开机初始化业务代码块
-
- myGLCD.InitLCD(60); //显示开机画面和点灯
- myGLCD.setFont(SmallFont);
- myGLCD.print("PM2.5 AutoTest", CENTER, 0);
- myGLCD.print("V1.0", CENTER, 16);
- myGLCD.print("| |", CENTER, 32);
- delay(200);
- for (int i=0; i<12; i++)
- {
- digitalWrite(RLED, HIGH);
- digitalWrite(YLED, HIGH);
- digitalWrite(BLLED, HIGH);
- myGLCD.print("\", 6+(i*6), 32);
- delay(500);
- digitalWrite(RLED, LOW);
- digitalWrite(YLED, HIGH);
- digitalWrite(BLLED, LOW);
- }
- bt_init(); //初始化蓝牙
- delay(500);
- myGLCD.clrScr(); //清屏幕
-
- }
- void bt_init(){ //以下为蓝牙业务处理代码
-
- digitalWrite(EN, LOW);
- digitalWrite(BRTS, HIGH);
-
- }
- void bt_send(){
-
- digitalWrite(EN, LOW);
- digitalWrite(BRTS, LOW);
-
- }
- void bt_sleep(){
-
- digitalWrite(BRTS, HIGH);
- digitalWrite(EN, HIGH);
-
- }
- void lcd_dp(float tmp, float hum, float dus){ //正常工作数据监视画面业务代码
-
- myGLCD.setFont(SmallFont);
- myGLCD.print(" ", RIGHT, 0);
- myGLCD.print("Hum(%):", LEFT, 0);
- myGLCD.printNumF((float)hum, 1, RIGHT, 0);
-
- myGLCD.print(" ", RIGHT, 8);
- myGLCD.print("Temp(oC):", LEFT, 8);
- myGLCD.printNumF((float)tmp, 1, RIGHT, 8);
-
- myGLCD.print("Dust(ug/m3):", LEFT, 16);
- myGLCD.print(" ", CENTER, 32);
- myGLCD.print(" ", CENTER, 40);
- myGLCD.setFont(MediumNumbers);
- myGLCD.printNumF((float)dus * 1000.0, 1, CENTER, 32);
-
- }
- void com_prt(float tmp, float hum, float dus){ //串口格式话输出当前数据业务代码
-
- Serial.print(hum);
- Serial.print(",");
- Serial.print(tmp);
- Serial.print(",");
- Serial.println((float)(dus * 1000.0));
-
- }
- boolean detect_pm(float dus){ //PM颗粒度逻辑判断代码,中度污染点亮黄色LED警告
- //重度污染点亮红色LED报警
- if(dus < 75.0){ //判断方式根据国家PM2.5空气质量标准(24小时平均值)
- digitalWrite(YLED, LOW); //优 ---> 0~35ug/m3
- digitalWrite(RLED, LOW); //良 ---> 35~75ug/m3
- }else if((dus >= 75.0)&&(dus < 150.0)){ //轻度污染 ---> 75~115ug/m3
- digitalWrite(YLED, HIGH); //中度污染 ---> 115~150ug/m3
- digitalWrite(RLED, LOW); //中度污染 ---> 150~250ug/m3
- return 1; //严重污染 ---> >250ug/m3
- }else if(dus >= 150.0){
- digitalWrite(YLED, LOW);
- digitalWrite(RLED, HIGH);
- return 1;
- }
- return 0;
-
- }
- void setup(){ //MCU初始化入口代码
-
- Serial.begin(115200);
- inputString.reserve(120);
- pinMode(ledPower,OUTPUT);
- pinMode(BLLED,OUTPUT);
- pinMode(RLED,OUTPUT);
- pinMode(YLED,OUTPUT);
- pinMode(EN,OUTPUT);
- pinMode(BRTS,OUTPUT);
- pinMode(WAKEUP,INPUT_PULLUP);
-
- init_device(); //调用设备初始化代码块
- attachInterrupt(1, wake_up, LOW); //开启外部中断1,侦测唤醒按钮
-
- }
- void loop(){
-
- ctrl_bl(); //调用背光点亮延迟并行代码
- main_case(); //调用信号采集和数据处理主业务代码
-
- if (stringComplete) { //BLE4.0模块接收到连接设备的信息后会转发到MCU串口输入
- //此处会对串口输入的命令做识别和处理
- if(inputString.endsWith("get#")){ //远程连接设备要求取得当前温湿度和颗粒度侦测数值
- bt_init(); //以下为MCU串口输出固定格式的数据给远程设备
- bt_send();
- delay(10);
- com_prt(temperature, humidity, dustdensity);
- delay(5);
- bt_init();
- }else if(inputString.endsWith("sleep#")){ //远程连接设备要求休眠蓝牙模块,进入脱机工作模式
- bt_sleep(); //MCU关闭BLE
- }else if(inputString.endsWith("lighton#")){ //远程连接设备要求开启背光
- digitalWrite(BLLED, HIGH);
- }else if(inputString.endsWith("lightoff#")){ //远程连接设备要求关闭背光
- digitalWrite(BLLED, LOW);
- }
- inputString = "";
- stringComplete = false;
-
- }
- delay(800);
-
- }
- void ctrl_bl(){ //背光点亮延迟并行处理的业务代码块
- //(在没有硬件延迟的处理电路时可以用此软件方式并行处理)
- if(wakeUp){
- blTime++;
- if(blTime > 50){
- digitalWrite(BLLED, LOW);
- wakeUp = false;
- }
- }
-
- }
- void main_case(){ //信号采集和数据处理主业务代码
-
- DHT11.read(DHT11PIN);
- humidity = DHT11.humidity;
- temperature = DHT11.temperature;
- digitalWrite(ledPower,LOW);
- delayMicroseconds(delayTime);
- dustVal=analogRead(dustPin);
- delayMicroseconds(delayTime2);
- digitalWrite(ledPower,HIGH);
- delayMicroseconds(offTime);
- voltage = dustVal * 0.00488; //此处颗粒度计算算法公式来源于网络
- dustdensity = 0.172 * voltage - 0.0999;
- //ppmpercf = (voltage-0.0256) * 120000;
- //if (ppmpercf < 0){
- // ppmpercf = 0;
- //}
- if (dustdensity < 0 ){ //滤除传感器失效数据
- dustdensity = 0;
- }
- if (dustdensity > 0.5){ //滤除传感器爆表后无效数据
- dustdensity = 0.5;
- }
-
- //com_prt(temperature, humidity, dustdensity);
- lcd_dp(temperature, humidity, dustdensity); //调用数据显示业务代码块
- detect_pm(dustdensity * 1000.0); //调用PM数值判断报警代码块
-
- }
- void serialEvent() { //串口事件中断业务代码
-
- while (Serial.available() > 0) {
- char inChar = (char)Serial.read();
- inputString += inChar;
- if ((inChar == '\n')||(inChar == '#')) {
- stringComplete = true;
- }
- }
-
- }
- void wake_up(){ //唤醒按键触发业务代码,主要作用1.唤醒背光
- //2.在用户关闭蓝牙模块后唤醒蓝牙模块
- bt_init();
- digitalWrite(BLLED, HIGH);
- blTime = 0;
- wakeUp = true;
-
- }
复制代码
Android端Apk源代码如有需要请到我网盘共享地址下载http://pan.baidu.com/s/1bnGWKMz
主要参考google开发网站BLE相关实例代码。
IOS端程序目前无力开发,如有IOS猿感兴趣可以配合做一下。蓝牙模块厂商资料也一并共享在网盘了
内部有相关service和特征码资料,只要你对iBean了解应该很快。下位机通讯协议很简单:
MCU接收到UART终端请求且内容为"get#"会返回当前“湿度值,温度值,颗粒度值”
MCU接收到UART终端请求且内容为"lighton#"会点亮LCD背光
MCU接收到UART终端请求且内容为"lightoff#"会关闭LCD背光
MCU接收到UART终端请求且内容为"sleep#"会关闭蓝牙脱机运行
后记:
此原型机设计有如下两点缺陷,造成后来Android上位机编写时做曲线页面显示功能时
发现需要手机端按时间不断去去读取资料,这种方式已违背了BLE低功耗,短连接,简单资料的方针
后来就暂时没有做进去,下次有机会改进,MCU先暂存当天和前天的数据,有请求就按JSON格式一次发送
1. 没有加入RTC时钟
2. 没有外部存储方式(SD,TF),内部EEPROM较小 |
本帖子中包含更多资源
您需要 登录 才可以下载或查看,没有帐号?注册
x
评分
-
查看全部评分
|