aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordakkar <dakkar@thenautilus.net>2022-03-27 12:48:36 +0100
committerdakkar <dakkar@thenautilus.net>2022-03-27 12:48:36 +0100
commit3443edf23337fb5d9ce63075ead80c4779cf823a (patch)
tree7010ca3559702ab816686d4fbc9c26f51a3b10c2
parentbattery voltage, move display around (diff)
downloadenv-sensor-3443edf23337fb5d9ce63075ead80c4779cf823a.tar.gz
env-sensor-3443edf23337fb5d9ce63075ead80c4779cf823a.tar.bz2
env-sensor-3443edf23337fb5d9ce63075ead80c4779cf823a.zip
break code into logical components
-rw-r--r--battery.h24
-rw-r--r--co2.h62
-rw-r--r--data.h10
-rw-r--r--display.h63
-rw-r--r--main.ino174
-rw-r--r--pm.h63
6 files changed, 243 insertions, 153 deletions
diff --git a/battery.h b/battery.h
index 825a3ab..e53341b 100644
--- a/battery.h
+++ b/battery.h
@@ -1,19 +1,16 @@
#pragma once
#include <Arduino.h>
+#include "data.h"
+
/*
code inspired by https://gist.github.com/jenschr/dfc765cb9404beb6333a8ea30d2e78a1
*/
class Battery {
+private:
uint8_t pin;
-public:
- /*
- the schematics at
- https://github.com/Xinyuan-LilyGO/LilyGo-T5-Epaper-Series/tree/master/schematic
- show a voltage divider connected to pin 35
- */
- Battery(uint8_t _pin=35) : pin(_pin) {};
+
float voltage() {
/*
Comment from the gist:
@@ -35,4 +32,17 @@ public:
*/
return (float)(analogRead(pin)) / 4095*2*3.3*1.1;
}
+public:
+ /*
+ the schematics at
+ https://github.com/Xinyuan-LilyGO/LilyGo-T5-Epaper-Series/tree/master/schematic
+ show a voltage divider connected to pin 35
+ */
+ Battery(uint8_t _pin=35) : pin(_pin) {};
+
+ void start() {}
+ bool dataReady() { return true; }
+ void read(SensorData *data) {
+ data->batteryVoltage = voltage();
+ }
};
diff --git a/co2.h b/co2.h
new file mode 100644
index 0000000..ac963f4
--- /dev/null
+++ b/co2.h
@@ -0,0 +1,62 @@
+#pragma once
+
+#include <Arduino.h>
+
+#include <SensirionI2CScd4x.h>
+#include <Wire.h>
+
+#include "data.h"
+
+class CO2 {
+private:
+ SensirionI2CScd4x scd4x;
+
+public:
+ CO2() : scd4x() {}
+
+ void start() {
+ uint16_t error;
+ char errorMessage[256];
+
+ scd4x.begin(Wire);
+
+ // stop potentially previously started measurement
+ error = scd4x.stopPeriodicMeasurement();
+ if (error) {
+ Serial.print("CO2 stopPeriodicMeasurement() error: ");
+ errorToString(error, errorMessage, 256);
+ Serial.println(errorMessage);
+ }
+
+ error = scd4x.setAutomaticSelfCalibration(1);
+ if (error) {
+ Serial.print("CO2 setAutomaticSelfCalibration() error: ");
+ errorToString(error, errorMessage, 256);
+ Serial.println(errorMessage);
+ }
+
+ // Start Measurement
+ error = scd4x.startPeriodicMeasurement();
+ if (error) {
+ Serial.print("CO2 startPeriodicMeasurement() error: ");
+ errorToString(error, errorMessage, 256);
+ Serial.println(errorMessage);
+ }
+ }
+
+ bool dataReady() {
+ return true;
+ }
+
+ void read(SensorData *data) {
+ uint16_t error;
+ char errorMessage[256];
+
+ error = scd4x.readMeasurement(data->co2, data->temperature, data->humidity);
+ if (error) {
+ Serial.print("CO2 readMeasurement() error: ");
+ errorToString(error, errorMessage, 256);
+ Serial.println(errorMessage);
+ }
+ }
+};
diff --git a/data.h b/data.h
new file mode 100644
index 0000000..1689f65
--- /dev/null
+++ b/data.h
@@ -0,0 +1,10 @@
+#pragma once
+#include <sps30.h>
+
+struct SensorData {
+ uint16_t co2;
+ float temperature;
+ float humidity;
+ float batteryVoltage;
+ struct sps30_measurement pm;
+};
diff --git a/display.h b/display.h
new file mode 100644
index 0000000..fdab3f3
--- /dev/null
+++ b/display.h
@@ -0,0 +1,63 @@
+#pragma once
+
+#define LILYGO_T5_V213 // needed for the display libraries
+
+#include <boards.h>
+#include <GxEPD.h>
+#include <GxGDEH0213B73/GxGDEH0213B73.h> // screen model, probably correct
+#include <Fonts/FreeMonoBold9pt7b.h>
+#include <GxIO/GxIO_SPI/GxIO_SPI.h>
+#include <GxIO/GxIO.h>
+
+#include "data.h"
+
+class Display {
+private:
+ GxIO_Class io;
+ GxEPD_Class display;
+
+public:
+ Display() :
+ io(SPI, EPD_CS, EPD_DC, EPD_RSET),
+ display(io, EPD_RSET, EPD_BUSY)
+ {}
+
+ void start() {
+ SPI.begin(EPD_SCLK, EPD_MISO, EPD_MOSI);
+
+ display.init();
+ display.setTextColor(GxEPD_BLACK);
+ display.setRotation(3);
+ display.setFont(&FreeMonoBold9pt7b);
+ }
+
+ void show(const SensorData *data) {
+ display.fillScreen(GxEPD_WHITE);
+
+ display.setCursor(0,20);
+ display.print("Co2 ");
+ display.print(data->co2);
+
+ display.setCursor(100,20);
+ display.print("t");
+ display.print(data->temperature,1);
+
+ display.setCursor(150,20);
+ display.print(" h");
+ display.print(data->humidity,0);
+ display.print("%");
+
+ display.setCursor(0,45);
+ display.println(" PM");
+ display.print(" 1.0 "); display.println(data->pm.mc_1p0,1);
+ display.print(" 2.5 "); display.println(data->pm.mc_2p5,1);
+ display.print(" 4.0 "); display.println(data->pm.mc_4p0,1);
+ display.print("10.0 "); display.println(data->pm.mc_10p0,1);
+
+ display.setCursor(100,45);
+ display.print("Batt "); display.print(data->batteryVoltage);
+
+ // "partial" update
+ display.updateWindow(0, 0, GxEPD_WIDTH, GxEPD_HEIGHT, false);
+ }
+};
diff --git a/main.ino b/main.ino
index ce9f981..8dcb387 100644
--- a/main.ino
+++ b/main.ino
@@ -1,164 +1,46 @@
#include <Arduino.h>
-#include <SensirionI2CScd4x.h>
-#include <sps30.h>
#include <Wire.h>
-#define LILYGO_T5_V213 // needed for the display libraries
-
-#include <boards.h>
-#include <GxEPD.h>
-#include <GxGDEH0213B73/GxGDEH0213B73.h> // screen model, probably correct
-#include <Fonts/FreeMonoBold9pt7b.h>
-#include <GxIO/GxIO_SPI/GxIO_SPI.h>
-#include <GxIO/GxIO.h>
-
+#include "data.h"
#include "battery.h"
+#include "display.h"
+#include "co2.h"
+#include "pm.h"
-GxIO_Class io(SPI, EPD_CS, EPD_DC, EPD_RSET);
-GxEPD_Class display(io, EPD_RSET, EPD_BUSY);
-SPIClass SDSPI(VSPI); // for sdcard
-
-SensirionI2CScd4x scd4x;
-
-Battery batt;
-
-uint16_t co2 = 0;
-float temperature = 0.0f;
-float humidity = 0.0f;
-struct sps30_measurement m;
-
-void showThings(bool all=false) {
- display.fillScreen(GxEPD_WHITE);
-
- display.setCursor(0,20);
- display.print("Co2 ");
- display.print(co2);
+Battery battery;
+PM pm;
+CO2 co2;
- display.setCursor(100,20);
- display.print("t");
- display.print(temperature,1);
+SensorData data;
- display.setCursor(150,20);
- display.print(" h");
- display.print(humidity,0);
- display.print("%");
-
- display.setCursor(0,45);
- display.println(" PM");
- display.print(" 1.0 "); display.println(m.mc_1p0,1);
- display.print(" 2.5 "); display.println(m.mc_2p5,1);
- display.print(" 4.0 "); display.println(m.mc_4p0,1);
- display.print("10.0 "); display.println(m.mc_10p0,1);
-
- display.setCursor(100,45);
- display.print("Batt "); display.print(batt.voltage());
-
- // "partial" update
- display.updateWindow(0, 0, GxEPD_WIDTH, GxEPD_HEIGHT, false);
-}
+Display display;
void setup() {
+ Serial.begin(115200);
+ while (!Serial) {
+ delay(100);
+ }
- Serial.begin(115200);
- while (!Serial) {
- delay(100);
- }
-
- // the board's definition says SCL=23, but I have SCL=22
- Wire.begin(21,22);
-
- SPI.begin(EPD_SCLK, EPD_MISO, EPD_MOSI);
-
- display.init();
- display.setTextColor(GxEPD_BLACK);
- display.setRotation(3);
- display.setFont(&FreeMonoBold9pt7b);
+ // the board's definition says SCL=23, but I have SCL=22
+ Wire.begin(21,22);
- showThings();
+ display.start();
+ display.show(&data);
- uint16_t error;
- char errorMessage[256];
+ battery.start();
+ co2.start();
+ pm.start();
+ Serial.println("Waiting for first measurement... (5 sec)");
- scd4x.begin(Wire);
-
- // stop potentially previously started measurement
- error = scd4x.stopPeriodicMeasurement();
- if (error) {
- Serial.print("Error trying to execute stopPeriodicMeasurement(): ");
- errorToString(error, errorMessage, 256);
- Serial.println(errorMessage);
- }
-
- error = scd4x.setAutomaticSelfCalibration(1);
- if (error) {
- Serial.print("Error trying to execute setAutomaticSelfCalibration(): ");
- errorToString(error, errorMessage, 256);
- Serial.println(errorMessage);
- }
-
- // Start Measurement
- error = scd4x.startPeriodicMeasurement();
- if (error) {
- Serial.print("Error trying to execute startPeriodicMeasurement(): ");
- errorToString(error, errorMessage, 256);
- Serial.println(errorMessage);
- }
-
- // this will try to re-init Wire, emit a warning, and carry on
- sensirion_i2c_init();
-
- while (sps30_probe() != 0) {
- Serial.print("SPS sensor probing failed\n");
- delay(500);
- }
-
- int16_t ret;
- uint8_t auto_clean_days = 4;
- uint32_t auto_clean;
-
- ret = sps30_set_fan_auto_cleaning_interval_days(auto_clean_days);
- if (ret) {
- Serial.print("error setting the auto-clean interval: ");
- Serial.println(ret);
- }
-
- ret = sps30_start_measurement();
- if (ret < 0) {
- Serial.print("error starting measurement\n");
- }
-
- Serial.println("Waiting for first measurement... (5 sec)");
+ delay(5000);
}
void loop() {
- uint16_t error;
- char errorMessage[256];
-
- delay(5000);
-
- error = scd4x.readMeasurement(co2, temperature, humidity);
-
- char serial[SPS30_MAX_SERIAL_LEN];
- uint16_t data_ready;
- int16_t ret;
-
- do {
- ret = sps30_read_data_ready(&data_ready);
- if (ret < 0) {
- Serial.print("error reading data-ready flag: ");
- Serial.println(ret);
- } else if (!data_ready)
- Serial.print("data not ready, no new measurement available\n");
- else
- break;
- delay(100); /* retry in 100ms */
- } while (1);
-
- ret = sps30_read_measurement(&m);
-
- if (error || ret <0 || co2 ==0) {
- return;
- }
+ if (battery.dataReady()) battery.read(&data);
+ if (pm.dataReady()) pm.read(&data);
+ if (co2.dataReady()) co2.read(&data);
- showThings();
+ display.show(&data);
+
+ delay(5000);
}
diff --git a/pm.h b/pm.h
new file mode 100644
index 0000000..634c1b4
--- /dev/null
+++ b/pm.h
@@ -0,0 +1,63 @@
+#pragma once
+
+#include <sps30.h>
+
+#include "data.h"
+
+class PM {
+private:
+ uint8_t auto_clean_days;
+public:
+ PM(uint8_t acd=4) :auto_clean_days(acd) {}
+
+ void start() {
+ // this will try to re-init Wire, emit a warning, and carry on
+ sensirion_i2c_init();
+
+ while (sps30_probe() != 0) {
+ Serial.print("PM sensor probing failed\n");
+ delay(500);
+ }
+
+ int16_t ret;
+
+ ret = sps30_set_fan_auto_cleaning_interval_days(auto_clean_days);
+ if (ret) {
+ Serial.print("PM setting the auto-clean interval error: ");
+ Serial.println(ret);
+ }
+
+ ret = sps30_start_measurement();
+ if (ret < 0) {
+ Serial.print("PM starting measurement error\n");
+ }
+ }
+
+ bool dataReady() {
+ uint16_t data_ready;
+ int16_t ret;
+
+ ret = sps30_read_data_ready(&data_ready);
+ if (ret < 0) {
+ Serial.print("PM reading data-ready flag error: ");
+ Serial.println(ret);
+ return false;
+ } else if (!data_ready) {
+ return false;
+ }
+
+ return true;
+ }
+
+ void read(SensorData *data) {
+ char serial[SPS30_MAX_SERIAL_LEN];
+ int16_t ret;
+
+ ret = sps30_read_measurement(&(data->pm));
+
+ if (ret <0) {
+ Serial.print("PM reading measurement error: ");
+ Serial.println(ret);
+ }
+ }
+};