home-automation/hardware/arduino/Plant_Monitor/ino/ino.ino

163 lines
5.5 KiB
C++

// Images used for display
#include "cat-grass.h" // cat_grass
#include "catnip.h" // catnip
#include "christmas-cactus.h" // christmas_cactus
#include "tarragon.h" // tarragon
#include "humidity.h" // humidity
#include "temp_humidity.h" // temp_humidity
#include "temperature.h" // temperature
#include "battery_0.h" // 0% battery
#include "battery_25.h" // 25% battery
#include "battery_50.h" // 50% battery
#include "battery_75.h" // 75% battery
#include "battery_100.h" // 100% battery
#include "warning.h" // warning (filled in)
// Adafruit temp/humidity sensor
// We are using the SHT10
// Humid accuracy +/- 5%
// Steady accuracy between 10-80
// example at 10/90 +/- 6%, 0/100 +/- 7.5%
#include "SHT1x.h"
#define dataPin A5
#define sckPin A1 //serial clock
SHT1x th_sensor(dataPin, sckPin);
// 2.9" Waveshare 3-color (red) e-ink setup
// mapping suggestion for Arduino DUE
// BUSY -> 7, RST -> 9, DC -> 8, CS-> 77, CLK -> 76, DIN -> 75
// SPI pins are on 6 pin 2x3 SPI header
// mapping suggestion for ESP32, e.g. LOLIN32, see .../variants/.../pins_arduino.h for your board
// NOTE: there are variants with different pins for SPI ! CHECK SPI PINS OF YOUR BOARD
// BUSY -> 21, RST -> 14, DC -> 15, CS -> 27, CLK -> SCK(5), DIN -> MOSI(18), GND -> GND, 3.3V -> 3.3V
// base class GxEPD2_GFX can be used to pass references or pointers to the display instance as parameter, uses ~1.2k more code
// enable or disable GxEPD2_GFX base class
#define ENABLE_GxEPD2_GFX 1
#include <GxEPD2_BW.h>
#include <GxEPD2_3C.h>
#include "DejaVuSansMono-Bold.8.h"
#define MAX_DISPAY_BUFFER_SIZE 15000ul // ~15k is a good compromise
#define MAX_HEIGHT(EPD) (EPD::HEIGHT <= MAX_DISPAY_BUFFER_SIZE / (EPD::WIDTH / 8) ? EPD::HEIGHT : MAX_DISPAY_BUFFER_SIZE / (EPD::WIDTH / 8))
#define MAX_HEIGHT_3C(EPD) (EPD::HEIGHT <= (MAX_DISPAY_BUFFER_SIZE / 2) / (EPD::WIDTH / 8) ? EPD::HEIGHT : (MAX_DISPAY_BUFFER_SIZE / 2) / (EPD::WIDTH / 8))
//GxEPD2_3C<GxEPD2_290c, MAX_HEIGHT_3C(GxEPD2_290c)> display(GxEPD2_290c(/*CS=77*/ SS, /*DC=*/ 8, /*RST=*/ 9, /*BUSY=*/ 7));
GxEPD2_3C<GxEPD2_290c, GxEPD2_290c::HEIGHT> display(GxEPD2_290c(/*CS*/ 27, /*DC=*/ 15, /*RST=*/ 14, /*BUSY=*/ 21));
// Fuel Gauge
#include "MAX17043.h"
float batt_voltage;
float batt_percent;
// Delay cheats
const unsigned long SECOND = 1000;
const unsigned long HOUR = 3600 * SECOND;
// Temp/Humidity reading vars
float temp_c;
float humid;
void setup()
{
// Initialize Fuel Gauge
FuelGauge.begin();
delay(100);
FuelGauge.reset();
delay(100);
FuelGauge.quickstart();
delay(100);
// Initialize display
display.init(115200);
display.setFullWindow();
display.setRotation(1);
display.setFont(&DejaVuSansMono_Bold8pt7b);
display.setTextColor(GxEPD_BLACK);
}
void loop()
{
// Clear and reset display for first run
display.firstPage();
display.clearScreen();
while (display.nextPage());
display.firstPage();
display.setCursor(0, 0);
// Wake Fuel Gauge
if (FuelGauge.isSleeping()) {
FuelGauge.wake();
}
// Battery Level
display.println();
batt_voltage = FuelGauge.voltage();
batt_percent = FuelGauge.percent();
if (batt_percent > 95) {
display.drawInvertedBitmap(0, 0, battery_100, 32, 32, GxEPD_BLACK);
}
else if (batt_percent > 75) {
display.drawInvertedBitmap(0, 0, battery_75, 32, 32, GxEPD_BLACK);
}
else if (batt_percent > 50) {
display.drawInvertedBitmap(0, 0, battery_50, 32, 32, GxEPD_BLACK);
}
else if (batt_percent > 25) {
display.drawInvertedBitmap(0, 0, battery_25, 32, 32, GxEPD_RED);
}
else {
display.drawInvertedBitmap(0, 0, battery_0, 32, 32, GxEPD_RED);
}
display.print(" ");
display.print(batt_percent);
display.print("% / ");
display.print(batt_voltage);
display.println("V");
// Show battery alert if active
if (FuelGauge.alertIsActive()) {
display.drawInvertedBitmap(265, 0, warning, 32, 32, GxEPD_RED);
}
// Sleep Fuel Gauge to save power
FuelGauge.sleep();
// Read values from the sensor
humid = th_sensor.readHumidity();
// Since the humidity reading requires the temperature we simply
// retrieve the reading capture from the readHumidity() call. See the lib.
temp_c = th_sensor.retrieveTemperatureC();
display.drawInvertedBitmap(0, 35, temperature, 32, 32, GxEPD_BLACK);
display.println();
display.print(" ");
display.print(temp_c * 9 / 5 + 32);
display.print("F");
display.print(" / ");
display.print(temp_c);
display.println("C");
display.drawInvertedBitmap(0, 67, humidity, 32, 32, GxEPD_BLACK);
display.println();
display.print(" ");
display.print(humid);
display.println("%");
// Draw icons for plant status
display.drawInvertedBitmap(0, 96, cat_grass, 32, 32, GxEPD_BLACK);
display.drawInvertedBitmap(37, 96, catnip, 32, 32, GxEPD_BLACK);
display.drawInvertedBitmap(74, 96, tarragon, 32, 32, GxEPD_BLACK);
display.drawInvertedBitmap(111, 96, christmas_cactus, 32, 32, GxEPD_BLACK);
display.drawInvertedBitmap(148, 96, cat_grass, 32, 32, GxEPD_RED);
display.drawInvertedBitmap(185, 96, catnip, 32, 32, GxEPD_RED);
display.drawInvertedBitmap(222, 96, tarragon, 32, 32, GxEPD_RED);
display.drawInvertedBitmap(259, 96, christmas_cactus, 32, 32, GxEPD_RED);
// Flush display output
while (display.nextPage());
// Hibernate the display to save power
//display.hibernate();
// Delay looping (deep sleep goes here in the future)
delay(10*60*SECOND);
}