Up and Running

I have the Sensirion SCD30 sensor connected up to my Arduino Yun, so just a quick update.

Below you’ll find a quick hand sketch showing the connection to hook up the sensor. In the the middle the “BOB-12009” handles the level translation from the Arduino DIO 5V signal level to the 3.3V signal level of the CO2 Sensor.

The sensors are reading within a few counts of each other. I did an outdoor calibration on the SCD30 last night, and I turned off automatic background calibration. Reading the doc, for the automatic background calibration to work, it wants to see fresh air for 1hr once a day. I don’t think it will ever see that.

#include <SparkFun_SCD30_Arduino_Library.h>


#include <Wire.h> //I2C needed for sensors
#include <FileIO.h> 
#include <Bridge.h>
#include <YunServer.h>
#include <YunClient.h>
#include <SoftwareSerial.h>

SCD30 airSensor;

//SCD30 Sensor is connected to D2 & D3 for I2C use.
//Bi-level logic converter used to convert the Yun 5V logic level to 3.3V for SCD30

//The 7 segment display is connected to D9 for serial control
const int softwareTx = 9;
const int softwareRx = 8;

SoftwareSerial s7s(softwareRx, softwareTx);


//Set up global variables to store readings
//Continuouslu update the globals on every loop when data is available
float humidity = 0; // [%]
float temperature = 0; // [temperature C]
uint16_t CO2Level = 0;

//These are used to either log or switch (Blink) the display at a fixed interval
unsigned long previousMillisLog;
unsigned long previousMillisBlink;

bool firstPass = true;
bool showTemp = true;

YunServer server;

//Setup gets called once on load
void setup()
{

  Bridge.begin();  //Setup link between linux side and arduino side
  Serial.begin(9600);  //Configure serial port
  FileSystem.begin();  // Setup the file system on the linux side
  Wire.begin();  //Startup the I2C comms

  airSensor.begin(Wire,false);  //startup the SCD30 but disable auto background cal.  It wants to see fresh air for 1hr every day
  
  
  s7s.begin(9600);  //Startup 7 segment display

  Serial.println("Temperature Monitor online!");
  
  server.listenOnLocalhost();  //Have the webserver start listening to requests
  server.begin();


  File dataFile = FileSystem.open("/mnt/sd/datalog.txt", FILE_APPEND);

  delay(2000);

  // if the file is available, write to it:
  if (dataFile) {
    dataFile.println("Logging Begins");
    dataFile.close();

  }
  
  previousMillisLog = millis();
  previousMillisBlink = millis();
  logMeasurements();
  
  clearDisplay();  // Clears display, resets cursor
  //s7s.print("-HI-");  // Displays -HI- on all digits
  //setDecimals(0b111111);  // Turn on all decimals, colon, apos


}

void loop()
{
  char tempString[10]; 
  int tempf;
  
  // Get clients coming from server
  YunClient client = server.accept();

  // There is a new client?
  if (client) {
    // Process request
    process(client);

    // Close connection and free resources.
    client.stop();
  }
  
  if (firstPass == true)
  {
    firstPass = false;
    File dataFile = FileSystem.open("/mnt/sd/datalog.txt", FILE_APPEND);

    //delay(2000);

    // if the file is available, write to it:
    if (dataFile) {
      dataFile.println("Logging Begins");
      dataFile.close();
    }
  }
  
  //Every 30 Seconds log to file
  if(millis() - previousMillisLog > 30000)
  {
    previousMillisLog = millis();
    logMeasurements();
  }

  //Every 5 seconds update display
  if(millis() - previousMillisBlink > 5000)
  {
    previousMillisBlink = millis();
    if (showTemp)
    {
      showTemp = false; //Next time show CO2
      tempf = (temperature)*10;  //Doing this to show decimal plave on display
      sprintf(tempString, "%4d", tempf);
      s7s.print(tempString);
      setDecimals(0b00000100);
    }
    else 
    {
      showTemp = true;  //Next time show temperature
      tempf = CO2Level;
      sprintf(tempString, "%4d", tempf);
      s7s.print(tempString);
      setDecimals(0b00000000);
    }
  }
  if (airSensor.dataAvailable())
  {
    CO2Level = airSensor.getCO2();
    temperature = airSensor.getTemperature();
    humidity = airSensor.getHumidity();
  }
  delay(50);

}


void process(YunClient client) {
  // read the command
  String command = client.readStringUntil('/');

  Serial.println(command);

  if (command.startsWith("temp")) 
    
  

  if (command.startsWith("cal")) 
    
  


}

void tempCommand(YunClient client) {
  String dataString;
  float voltage, degreesC, degreesF;
  dataString += getTimeStamp();
  dataString += "\n Humidity = ";
  
  Serial.println("Hello!");

  client.println("Request Received");


  dataString += humidity;
  dataString += " pct \n Temp = ";
  dataString += (temperature);

  dataString += " \n CO2 = ";
  dataString += CO2Level;
  dataString += " ppm";

  // Send feedback to client
  client.println(dataString);

 
}

void calCommand(YunClient client) {
  String dataString;
  float voltage, degreesC, degreesF;
  dataString += getTimeStamp();
  dataString += "\n Calibrated ";
  airSensor.setForcedRecalibrationFactor(400);
  

  client.println("Request Received");

  // Send feedback to client
  client.println(dataString);

}




String getTimeStamp() {
  String result;
  Process time;
  // date is a command line utility to get the date and the time 
  // in different formats depending on the additional parameter 
  time.begin("date");
  time.addParameter("+%D-%T");  // parameters: D for the complete date mm/dd/yy
                                //             T for the time hh:mm:ss    
  time.run();  // run the command

  // read the output of the command
  while(time.available()>0) {
    char c = time.read();
    if(c != '\n')
      result += c;
  }

  return result;
}



//Prints the various variables directly to the port
//I don't like the way this function is written but Arduino doesn't support floats under sprintf
void logMeasurements()
{
  String dataString;
  //float voltage, degreesC, degreesF;
  dataString += getTimeStamp();
  dataString += ",";
  

  dataString += humidity;
  dataString += ",";
  dataString += temperature;
  dataString += ",";
  dataString += CO2Level;

  File dataFile = FileSystem.open("/mnt/sd/datalog.txt", FILE_APPEND);

  // if the file is available, write to it:
  if (dataFile) {
    dataFile.println(dataString);
    dataFile.close();

  }  
  // if the file isn't open, pop up an error:
  else {
    Serial.println("error opening datalog.txt");
  } 
  
  
}

void clearDisplay()
{
  s7s.write(0x76);  // Clear display command
}

void setDecimals(byte decimals)
{
  s7s.write(0x77);
  s7s.write(decimals);
}