|
|
@ -1,6 +1,6 @@
|
|
|
|
#include <EveryTimer.h>
|
|
|
|
#include <EveryTimer.h>
|
|
|
|
#include <OneShotTimer.h>
|
|
|
|
#include <OneShotTimer.h>
|
|
|
|
|
|
|
|
#include <DHT.h>
|
|
|
|
#include <TimeLib.h>
|
|
|
|
#include <TimeLib.h>
|
|
|
|
#include <TFT_FastPin.h>
|
|
|
|
#include <TFT_FastPin.h>
|
|
|
|
#include <TFT_ILI9341.h>
|
|
|
|
#include <TFT_ILI9341.h>
|
|
|
@ -15,6 +15,27 @@
|
|
|
|
#define TFT_DC 48
|
|
|
|
#define TFT_DC 48
|
|
|
|
#define TFT_CS 49
|
|
|
|
#define TFT_CS 49
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#define DHTPIN 32 // Digital pin connected to the DHT sensor
|
|
|
|
|
|
|
|
// Feather HUZZAH ESP8266 note: use pins 3, 4, 5, 12, 13 or 14 --
|
|
|
|
|
|
|
|
// Pin 15 can work but DHT must be disconnected during program upload.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Uncomment whatever type you're using!
|
|
|
|
|
|
|
|
//#define DHTTYPE DHT11 // DHT 11
|
|
|
|
|
|
|
|
#define DHTTYPE DHT22 // DHT 22 (AM2302), AM2321
|
|
|
|
|
|
|
|
//#define DHTTYPE DHT21 // DHT 21 (AM2301)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Connect pin 1 (on the left) of the sensor to +5V
|
|
|
|
|
|
|
|
// NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1
|
|
|
|
|
|
|
|
// to 3.3V instead of 5V!
|
|
|
|
|
|
|
|
// Connect pin 2 of the sensor to whatever your DHTPIN is
|
|
|
|
|
|
|
|
// Connect pin 4 (on the right) of the sensor to GROUND
|
|
|
|
|
|
|
|
// Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Initialize DHT sensor.
|
|
|
|
|
|
|
|
// Note that older versions of this library took an optional third parameter to
|
|
|
|
|
|
|
|
// tweak the timings for faster processors. This parameter is no longer needed
|
|
|
|
|
|
|
|
// as the current DHT reading algorithm adjusts itself to work on faster procs.
|
|
|
|
|
|
|
|
DHT dht(DHTPIN, DHTTYPE);
|
|
|
|
// Use hardware SPI (on Uno, #13, #12, #11) and the above for CS/DC
|
|
|
|
// Use hardware SPI (on Uno, #13, #12, #11) and the above for CS/DC
|
|
|
|
TFT_ILI9341 tft = TFT_ILI9341();
|
|
|
|
TFT_ILI9341 tft = TFT_ILI9341();
|
|
|
|
extern "C" char __data_start[]; // start of SRAM data
|
|
|
|
extern "C" char __data_start[]; // start of SRAM data
|
|
|
@ -137,6 +158,11 @@ boolean upd = true;
|
|
|
|
boolean s1, s2, s3, s4;
|
|
|
|
boolean s1, s2, s3, s4;
|
|
|
|
String outtext2 = "";
|
|
|
|
String outtext2 = "";
|
|
|
|
int linecount = 0;
|
|
|
|
int linecount = 0;
|
|
|
|
|
|
|
|
int brightness = 255;
|
|
|
|
|
|
|
|
int uda[] = {};
|
|
|
|
|
|
|
|
int sla[] = {10, 90, 300, 280};
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void setup(void) {
|
|
|
|
void setup(void) {
|
|
|
|
batteryupd.Every(10000, checkBat);
|
|
|
|
batteryupd.Every(10000, checkBat);
|
|
|
@ -153,6 +179,7 @@ void setup(void) {
|
|
|
|
pinMode(9, INPUT_PULLUP);
|
|
|
|
pinMode(9, INPUT_PULLUP);
|
|
|
|
setTime(0);
|
|
|
|
setTime(0);
|
|
|
|
Serial.begin(9600);
|
|
|
|
Serial.begin(9600);
|
|
|
|
|
|
|
|
dht.begin();
|
|
|
|
//tft.reset();
|
|
|
|
//tft.reset();
|
|
|
|
#if defined(ILI9341_RST_PIN) // reset like Adafruit does
|
|
|
|
#if defined(ILI9341_RST_PIN) // reset like Adafruit does
|
|
|
|
FastPin<ILI9341_RST_PIN>::setOutput();
|
|
|
|
FastPin<ILI9341_RST_PIN>::setOutput();
|
|
|
@ -181,7 +208,7 @@ void setup(void) {
|
|
|
|
}
|
|
|
|
}
|
|
|
|
clearLog();
|
|
|
|
clearLog();
|
|
|
|
printFastCText("Booting GreenhouseOS...");
|
|
|
|
printFastCText("Booting GreenhouseOS...");
|
|
|
|
printFastCText("");
|
|
|
|
printFastCText("Version: 0.1.5");
|
|
|
|
printFastCText("");
|
|
|
|
printFastCText("");
|
|
|
|
delay(250);
|
|
|
|
delay(250);
|
|
|
|
if(!didDraw) {
|
|
|
|
if(!didDraw) {
|
|
|
@ -254,6 +281,13 @@ void loop(void) {
|
|
|
|
Serial.print("\tPressure = "); Serial.println(p.z);
|
|
|
|
Serial.print("\tPressure = "); Serial.println(p.z);
|
|
|
|
int x = 320 - p.y;
|
|
|
|
int x = 320 - p.y;
|
|
|
|
int y = p.x;
|
|
|
|
int y = p.x;
|
|
|
|
|
|
|
|
if(y < 130 && y > 50 && menu == 1) {
|
|
|
|
|
|
|
|
sla[3] = x - 10;
|
|
|
|
|
|
|
|
if(sla[3] < 0) sla[3] = 0;
|
|
|
|
|
|
|
|
if(sla[3] > 280) sla[3] = 280;
|
|
|
|
|
|
|
|
analogWrite(6, map(sla[3], 0, 280, 25, 255));
|
|
|
|
|
|
|
|
drawSlider(sla);
|
|
|
|
|
|
|
|
}
|
|
|
|
if (x < 160 && y < 130) {
|
|
|
|
if (x < 160 && y < 130) {
|
|
|
|
button(0, 0);
|
|
|
|
button(0, 0);
|
|
|
|
}
|
|
|
|
}
|
|
|
@ -266,21 +300,46 @@ void loop(void) {
|
|
|
|
if (x > 160 && y > 130) {
|
|
|
|
if (x > 160 && y > 130) {
|
|
|
|
button(1, 1);
|
|
|
|
button(1, 1);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
if ((batteryupd.m_milliseconds - millis() + batteryupd.m_lastRunTimestamp) / 250 == 0 && menu == 2) {
|
|
|
|
|
|
|
|
upd = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (upd) {
|
|
|
|
if (upd) {
|
|
|
|
if (menu == 0) {
|
|
|
|
if (menu == 0) {
|
|
|
|
drawButton(0, 20, 160, 110, "Settings", "ILI9341_YELLOW");
|
|
|
|
drawButton(0, 20, 160, 110, "System", "ILI9341_YELLOW");
|
|
|
|
drawButton(160, 20, 160, 110, "Stats", "ILI9341_GREEN");
|
|
|
|
drawButton(160, 20, 160, 110, "Stats", "ILI9341_GREEN");
|
|
|
|
|
|
|
|
drawButton(0, 130, 160, 110, "Options", "ILI9341_BLUE");
|
|
|
|
|
|
|
|
drawButton(160, 130, 160, 110, "Stop", "ILI9341_BLACK");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (menu == 1) {
|
|
|
|
if (menu == 1) {
|
|
|
|
drawButton(0, 130, 160, 110, "Reset", "ILI9341_GREEN");
|
|
|
|
drawButton(0, 130, 160, 110, "Reset", "ILI9341_GREEN");
|
|
|
|
drawButton(0, 20, 320, 110, "Stop", "ILI9341_RED");
|
|
|
|
drawButton(0, 20, 320, 110, "", "ILI9341_RED");
|
|
|
|
|
|
|
|
drawSlider(sla);
|
|
|
|
drawButton(160, 130, 160, 110, "Back", "ILI9341_BLUE");
|
|
|
|
drawButton(160, 130, 160, 110, "Back", "ILI9341_BLUE");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (menu == 2) {
|
|
|
|
if (menu == 2) {
|
|
|
|
drawButton(160, 130, 160, 110, "Back", "ILI9341_BLUE");
|
|
|
|
//debug = true;
|
|
|
|
displayText(2, 30, false, 4);
|
|
|
|
//printFastCText("pressed");
|
|
|
|
|
|
|
|
drawButton(0, 20, 320, 220, "", "ILI9341_BLACK");
|
|
|
|
|
|
|
|
float h = dht.readHumidity();
|
|
|
|
|
|
|
|
// Read temperature as Celsius (the default)
|
|
|
|
|
|
|
|
float t = dht.readTemperature();
|
|
|
|
|
|
|
|
// Read temperature as Fahrenheit (isFahrenheit = true)
|
|
|
|
|
|
|
|
float f = dht.readTemperature(true);
|
|
|
|
|
|
|
|
String txt = "Humidity: ";
|
|
|
|
|
|
|
|
txt += h;
|
|
|
|
|
|
|
|
txt += "%";
|
|
|
|
|
|
|
|
displayText(2, 30, false, txt, 4);
|
|
|
|
|
|
|
|
txt = "Temperature: ";
|
|
|
|
|
|
|
|
txt += f;
|
|
|
|
|
|
|
|
txt += " degrees";
|
|
|
|
|
|
|
|
displayText(2, 53, false, txt, 4);
|
|
|
|
|
|
|
|
txt = (water.m_milliseconds - millis() + water.m_lastRunTimestamp) / 60000;
|
|
|
|
|
|
|
|
txt += " minutes until water";
|
|
|
|
|
|
|
|
displayText(2, 76, false, txt, 4);
|
|
|
|
// moisture, temperature, next cycle, how much water, power usage, sensor connections
|
|
|
|
// moisture, temperature, next cycle, how much water, power usage, sensor connections
|
|
|
|
|
|
|
|
drawButton(160, 130, 160, 110, "Back", "ILI9341_BLUE");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
upd = false;
|
|
|
|
upd = false;
|
|
|
|
}
|
|
|
|
}
|
|
|
@ -355,7 +414,7 @@ void checkBat() {
|
|
|
|
delay(10);
|
|
|
|
delay(10);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if(analogRead(1) > 910) {
|
|
|
|
if(analogRead(1) > 910) {
|
|
|
|
out += "Using solar poower";
|
|
|
|
out += "Using solar power";
|
|
|
|
} else {
|
|
|
|
} else {
|
|
|
|
out += map(y / 20, 572, 859, 0, 100);
|
|
|
|
out += map(y / 20, 572, 859, 0, 100);
|
|
|
|
out += "%";
|
|
|
|
out += "%";
|
|
|
@ -383,6 +442,8 @@ void checkBat() {
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void runWater() {
|
|
|
|
void runWater() {
|
|
|
|
|
|
|
|
drawButton(0, 20, 320, 220, "Watering! Please wait.", ILI9341_WHITE);
|
|
|
|
|
|
|
|
upd = true;
|
|
|
|
getMoisture();
|
|
|
|
getMoisture();
|
|
|
|
if(s1 && map(soil1.touchRead(0), 0, 1023, 0, 100) <= 50) {
|
|
|
|
if(s1 && map(soil1.touchRead(0), 0, 1023, 0, 100) <= 50) {
|
|
|
|
int td = 50 - map(soil1.touchRead(0), 0, 1023, 0, 100);
|
|
|
|
int td = 50 - map(soil1.touchRead(0), 0, 1023, 0, 100);
|
|
|
@ -426,6 +487,17 @@ void runWater() {
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
void getMoisture() {
|
|
|
|
void getMoisture() {
|
|
|
|
|
|
|
|
float h = dht.readHumidity();
|
|
|
|
|
|
|
|
// Read temperature as Celsius (the default)
|
|
|
|
|
|
|
|
float t = dht.readTemperature();
|
|
|
|
|
|
|
|
// Read temperature as Fahrenheit (isFahrenheit = true)
|
|
|
|
|
|
|
|
float f = dht.readTemperature(true);
|
|
|
|
|
|
|
|
String txt = "[ OK ] Humidity: ";
|
|
|
|
|
|
|
|
txt += h;
|
|
|
|
|
|
|
|
txt += "%, Temperature: ";
|
|
|
|
|
|
|
|
txt += f;
|
|
|
|
|
|
|
|
txt += " F";
|
|
|
|
|
|
|
|
printFastCText(txt);
|
|
|
|
if (s1) {
|
|
|
|
if (s1) {
|
|
|
|
float t1 = soil1.getTemp();
|
|
|
|
float t1 = soil1.getTemp();
|
|
|
|
int sm1 = map(soil1.touchRead(0), 0, 1023, 0, 100);
|
|
|
|
int sm1 = map(soil1.touchRead(0), 0, 1023, 0, 100);
|
|
|
@ -633,6 +705,7 @@ void printFastCText(String text) { // NOTE: text MUST be under 53 characters lon
|
|
|
|
tft.setCursor(0, 0);
|
|
|
|
tft.setCursor(0, 0);
|
|
|
|
tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
|
|
|
|
tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
|
|
|
|
tft.setTextSize(1);
|
|
|
|
tft.setTextSize(1);
|
|
|
|
|
|
|
|
tft.setTextFont(1);
|
|
|
|
//int cursory = linecount * 8;
|
|
|
|
//int cursory = linecount * 8;
|
|
|
|
//for (int x = linecount - 1; x >= 0; x--) {
|
|
|
|
//for (int x = linecount - 1; x >= 0; x--) {
|
|
|
|
//tft.setCursor(0, cursory - 8);
|
|
|
|
//tft.setCursor(0, cursory - 8);
|
|
|
@ -649,7 +722,7 @@ void scrollAddress(uint16_t vsp) {
|
|
|
|
tft.writedata(vsp);
|
|
|
|
tft.writedata(vsp);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void drawButton(int x, int y, int w, int h, char* text, char* color) {
|
|
|
|
void drawButton(int x, int y, int w, int h, char* text, word color) {
|
|
|
|
tft.fillRect(x, y, w, h, ILI9341_BLACK);
|
|
|
|
tft.fillRect(x, y, w, h, ILI9341_BLACK);
|
|
|
|
tft.setTextFont(4);
|
|
|
|
tft.setTextFont(4);
|
|
|
|
tft.fillRect(x, y, w, h, color);
|
|
|
|
tft.fillRect(x, y, w, h, color);
|
|
|
@ -683,23 +756,35 @@ void button(int x, int y) {
|
|
|
|
digitalWrite(9, LOW); // RESET
|
|
|
|
digitalWrite(9, LOW); // RESET
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (y == 0) {
|
|
|
|
if (y == 0) {
|
|
|
|
// STOP CODE HERE
|
|
|
|
//do nothing
|
|
|
|
water.Stop();
|
|
|
|
}
|
|
|
|
|
|
|
|
if (x == 1 && y == 1) {
|
|
|
|
menu = 0;
|
|
|
|
menu = 0;
|
|
|
|
upd = true;
|
|
|
|
upd = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
else if (menu == 2) {
|
|
|
|
if (x == 1 && y == 1) {
|
|
|
|
if (x == 1 && y == 1) {
|
|
|
|
menu = 0;
|
|
|
|
menu = 0;
|
|
|
|
upd = true;
|
|
|
|
upd = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
delay(250);
|
|
|
|
delay(250);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void displayText(int x, int y, boolean center, String text, int size) {
|
|
|
|
void displayText(int x, int y, boolean center, String text, int size) {
|
|
|
|
if (center) {
|
|
|
|
if (center) {
|
|
|
|
tft.drawCentreString(text, x, y, size);
|
|
|
|
tft.drawCentreString(text.c_str(), x, y, size);
|
|
|
|
} else {
|
|
|
|
} else {
|
|
|
|
tft.drawString(text, x, y, size);
|
|
|
|
tft.drawString(text.c_str(), x, y, size);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void drawSlider(int data[]) {
|
|
|
|
|
|
|
|
int x = data[0];
|
|
|
|
|
|
|
|
int y = data[1];
|
|
|
|
|
|
|
|
int w = data[2];
|
|
|
|
|
|
|
|
int d = data[3];
|
|
|
|
|
|
|
|
tft.fillRect(x, y, w, 20, ILI9341_BLACK);
|
|
|
|
|
|
|
|
tft.fillRect(x + d, y, 20, 20, ILI9341_GREEN);
|
|
|
|
|
|
|
|
}
|
|
|
|