/* D. Brooks, December 2015 Interface to Telaire SMART Dust Sensor SM-PWM-01A (see Mouser Electronics 527-SM-PWM-01A) See http://www.amphenol-sensors.com/en/products/co2/co2-modules/3222-telaire-smart-dust-sensor#download for data sheet and application notes. See https://www.arduino.cc/en/Reference/PulseIn for pulseIn() function. Pins labeled 1-5, right to left looking down on top of device, black housing at right (rightmost pin is GND). pin 1 = GND pin 2 = P2 signal out (large particles, 3~10 um) pin 3 = +5V pin 4 = P1 signal out (small particles, 1~2 um) pin 5 no connection Run the fan from the +3.3V pin and GND on the Arduino. Connect the DHT22 sensor red/black wires to +5V/GND and the yellow wire to D8. */ #define ECHO_TO_FILE 1 #define ECHO_TO_SERIAL 0 #include #include "RTClib.h" #include #define DHTPIN 8 #define DHTTYPE DHT22 RTC_DS1307 rtc; DHT dht(DHTPIN,DHTTYPE); #include #include File logfile; char filename[]="LOGGER00.CSV"; const int chipSelect=10, lineFeed=0, P1 = 6, P2 = 7; int pin,n_pulses=0; unsigned long duration,min_duration=1000000,max_duration=0; unsigned long starttime; // unsigned long waittime=500000; // microseconds to wait for pulse to complete before return from pulseIn() unsigned long sampletime_ms = 30000; //sample 30 s unsigned long lowpulseoccupancy = 0; float ratio,concentration,dayFrac; float tc,h; void setup() { Serial.begin(9600); Wire.begin(); rtc.begin(); //rtc.adjust(DateTime(__DATE__,__TIME__)); pinMode(P1,INPUT); pinMode(P2,INPUT); starttime = millis();//get the current time; #if ECHO_TO_FILE SDsetup(); logfile.println("ch,Date,Time,Day_frac,#_pulses,pulse_occupancy,avg_duration,min_duration,max_duration,T_C,RH"); logfile.flush(); #endif #if ECHO_TO_SERIAL Serial.println("ch,Date,Time,Day_frac,#_pulses,pulse_occupancy,avg_duration,min_duration,max_duration,T_C,RH"); #endif } void loop() { starttime=millis(); readPulses(1); // read P1 pulses ` starttime=millis(); readPulses(2); // read P2 pulses } void readPulses(int P) { //Serial.print("Reading P"); Serial.println(P); if (P==1) pin=P1; else pin=P2; do { duration = pulseIn(pin,LOW); // pulseIn() returns pulse length, microseconds if (duration>0) { n_pulses++; if (durationmax_duration) max_duration=duration; lowpulseoccupancy += duration; } } while ( (millis()-starttime) < sampletime_ms) ; if (P==1) { #if ECHO_TO_SERIAL Serial.print("P1:, "); #endif; #if ECHO_TO_FILE logfile.print("P1:, "); #endif } else { #if ECHO_TO_SERIAL Serial.print("P2:, "); #endif #if ECHO_TO_FILE logfile.print("P2:, "); #endif } if (n_pulses>0) { ratio = 0.1*lowpulseoccupancy/sampletime_ms; // pulse occupancy percentage 0<=100 h=dht.readHumidity(); tc=dht.readTemperature(); #if ECHO_TO_SERIAL DisplayTime(lineFeed); Serial.print(n_pulses); Serial.print(", "); Serial.print(ratio,2); Serial.print(", "); Serial.print((float)lowpulseoccupancy/n_pulses,1); Serial.print(", "); Serial.print(min_duration); Serial.print(", "); Serial.print(max_duration); Serial.print(", "); Serial.print(tc,1); Serial.print(", "); Serial.print(h,1); Serial.println(); #endif #if ECHO_TO_FILE WriteTime(lineFeed); logfile.print(n_pulses); logfile.print(", "); logfile.print(ratio,2); logfile.print(", "); logfile.print((float)lowpulseoccupancy/n_pulses,1); logfile.print(", "); logfile.print(min_duration); logfile.print(", "); logfile.print(max_duration); logfile.print(", "); logfile.print(tc,1); logfile.print(", "); logfile.print(h,1); logfile.println(); logfile.flush(); #endif n_pulses=0; } else { #if ECHO_TO_SERIAL DisplayTime(lineFeed); Serial.print("0, 0, 0, 0, 0. "); Serial.print(tc,1); Serial.print(", "); Serial.print(h,1); Serial.println(); #endif #if ECHO_TO_FILE WriteTime(lineFeed); logfile.print("0, 0, 0, 0, 0, "); logfile.print(tc,1); logfile.print(", "); logfile.print(h,1); logfile.println(); logfile.flush(); #endif } min_duration=1000000; max_duration=0; lowpulseoccupancy = 0; } void WriteTime(boolean lineFeed) { // to SD card file buffer DateTime now=rtc.now(); dayFrac=now.day()+now.hour()/24.+now.minute()/1440.+now.second()/86400.; logfile.print(now.year()); logfile.print('/'); logfile.print(now.month()); logfile.print('/'); logfile.print(now.day()); logfile.print(','); logfile.print(now.hour()); logfile.print(':'); logfile.print(now.minute()); logfile.print(':'); logfile.print(now.second()); logfile.print(", "); logfile.print(dayFrac,4); if (lineFeed) logfile.println(); else logfile.print(", "); } void DisplayTime(boolean lineFeed) { DateTime now=rtc.now(); dayFrac=now.day()+now.hour()/24.+now.minute()/1440.+now.second()/86400.; Serial.print(now.year()); Serial.print('/'); Serial.print(now.month()); Serial.print('/'); Serial.print(now.day()); Serial.print(','); Serial.print(now.hour()); Serial.print(':'); Serial.print(now.minute()); Serial.print(':'); Serial.print(now.second()); Serial.print(", "); Serial.print(dayFrac,4); if (lineFeed) Serial.println(); else Serial.print(", "); } void SDsetup() { // initialize the SD card Serial.print("Initializing SD card..."); // make sure that the default chip select pin is set to // output, even if you don't use it: pinMode(10, OUTPUT); // see if the card is present and can be initialized: if (!SD.begin(chipSelect)) { Serial.println("Card failed, or not present"); // don't do anything more: return; } Serial.println("card initialized."); // create a new file for (uint8_t i = 0; i < 100; i++) { filename[6] = i/10 + '0'; filename[7] = i%10 + '0'; if (! SD.exists(filename)) { // only open a new file if it doesn't exist logfile = SD.open(filename, FILE_WRITE); break; // leave the loop! } } if (! logfile) { Serial.println("couldnt create file"); } Serial.print("Logging to: "); Serial.println(filename); }