adafruit / Adafruit_SGP30

Arduino library for SGP30
Other
56 stars 38 forks source link

Setting baseline stalls sensor #22

Open bboynton97 opened 4 years ago

bboynton97 commented 4 years ago

SGP30 Unable to Accept Setting Baseline

Description Before my board powers down, I want to record the latest baseline in order to restart the sensor with that baseline later and not have to wait for it to recalibrate. I can pull the baseline no problem, but attempting to set the baseline causes the sensor to output the default values of TVOC 0ppb and eCO2 400ppm. These values never change. When I restart the board without setting the baseline values, it works no problem and starts establishing a new baseline like normal.

I would like to believe this is a code issue because I have troubleshooted every possible alternative issue I could think of over the past 6 hours. I also posted this on the forum to no avail.

Repro

#include <Arduino.h>

#include <Wire.h>        // I2C library
#include "Adafruit_SGP30.h"
#include "DHT.h"
#include <EEPROM.h>

// Flash Memory addresses
#define SGP_CO2_BASELINE    0
#define SGP_TVOC_BASELINE    1

#define DHT_TYPE DHT22

uint32_t getAbsoluteHumidity(float temperature, float humidity) {
    // approximation formula from Sensirion SGP30 Driver Integration chapter 3.15
    const float absoluteHumidity = 216.7f * ((humidity / 100.0f) * 6.112f * exp((17.62f * temperature) / (243.12f + temperature)) / (273.15f + temperature)); // [g/m^3]
    const uint32_t absoluteHumidityScaled = static_cast<uint32_t>(1000.0f * absoluteHumidity); // [mg/m^3]
    return absoluteHumidityScaled;
}

// Create sensors
Adafruit_SGP30 sgp;
DHT dht(DHT_PIN, DHT_TYPE);

void setup() {
  Serial.begin(115200);

  // Enable EEPROM
  EEPROM.begin(64); // 64 bytes of memory

  // Set up DHT22
  dht.begin();

  // Set up SGP30
  if (! sgp.begin()){
    Serial.println("Sensor not found :(");
    while (1);
  }

  // Start at baseline if it exists
  uint16_t co2_baseline = EEPROM.read(SGP_CO2_BASELINE);
  uint16_t tvoc_baseline = EEPROM.read(SGP_TVOC_BASELINE);

  // *** I even tried setting the values manually here with no luck ***   <-----
  // co2_baseline = 0xEE; //238;
  // tvoc_baseline = 0xAF; //175;

  Serial.println("Retrieved baselines from memory:");
  Serial.print(" eCO2: 0x"); Serial.print(co2_baseline, HEX);
  Serial.print(" & TVOC: 0x"); Serial.println(tvoc_baseline, HEX);
  if (co2_baseline != NULL && tvoc_baseline != NULL) {
      Serial.println("Setting baselines");
      sgp.setIAQBaseline(co2_baseline, tvoc_baseline);  // <--- If you remove this line, it runs like normal. With it in, it outputs defaults
  }

  Wire.begin();
  delay(3000);
  Serial.println("setup: done");
}

int counter = 0;
void loop() {
  float rh = dht.readHumidity();
  double  temp = dht.readTemperature();

  sgp.setHumidity(getAbsoluteHumidity(temp, rh));

  if (! sgp.IAQmeasure()) {
      Serial.println("Measurement failed");
      return;
  }

  Serial.print("TVOC "); Serial.print(sgp.TVOC); Serial.print(" ppb\t");
  Serial.print("eCO2 "); Serial.print(sgp.eCO2); Serial.println(" ppm");

  delay(500);

  counter++;
  if (counter == 30) {
    counter = 0;

    uint16_t TVOC_base, eCO2_base;
    if (! sgp.getIAQBaseline(&eCO2_base, &TVOC_base)) {
      Serial.println("Failed to get baseline readings");
      return;
    }
    Serial.print("****Baseline values: eCO2: 0x"); Serial.print(eCO2_base, HEX);
    Serial.print(" & TVOC: 0x"); Serial.println(TVOC_base, HEX);

    EEPROM.write(SGP_CO2_BASELINE, eCO2_base);
    EEPROM.write(SGP_TVOC_BASELINE, TVOC_base);
    EEPROM.commit();
  }
}
gorghino commented 3 years ago

Any news?

Chesteron commented 3 years ago

According to "SGP30 Data Sheet" you need to call first Init command. Have you tried that?

"_After a power-up or soft reset, the baseline of the baseline compensation algorithm can be restored by sending first an “sgp30_iaq_init” command followed by a “sgp30_set_iaqbaseline” command with the two baseline values as parameters in the order as (TVOC, CO2eq)."

caternuson commented 2 years ago

@gorghino Did you try @Chesteron suggestion? Your sketch is not calling IAQinit().

image

gorghino commented 2 years ago

Hi @caternuson , I guess you need to ask @bboynton97 . I haven't the SGP30 with me anymore so I cannot test @Chesteron 's suggestion.