#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <DHT.h>
#include <LCD.h>
#include <DS3231.h>
LiquidCrystal_I2C lcd(0X27, 2, 1, 0, 4, 5, 6, 7); // 0x27 is the I2c bus for a unmodified back pack
const byte RelayPin = 4;
DS3231 rtc(SDA, SCL);
Time ti;
const byte OnHour[] = {12, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11};
const byte OnMin[] = {0, 1, 3, 5, 7, 9};
const byte OffHour[] = {12, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11};
const byte OffMin[] = {2, 4, 6, 8, 10};
//Globals for dht sensor
#define DHTPIN 8 // what pin its connected to
#define DHTTYPE DHT22 // DHT 22 (AM2302)
DHT dht (DHTPIN, DHTTYPE);// Initialize DHT sensor for normal 16mhz Arduino
//humidity control points
#define SETPOINT 90.0
#define DEADBAND 2.0
//These just make code easier to read
#define HUMIDIFIER 9 //instead of using 9 for pin 9 we will name it HUMIDIFIER
#define FAN 4
#define ON false
//the relay is sort of backwards. a low/0/false output is actually on
#define OFF true //the relay is sort of backwards. a high/1/true output is actually on
//the setup routine only executes once, when the ardunio is powered on
void setup() {
Serial.begin(9600);
rtc.begin();
pinMode(RelayPin, OUTPUT);
digitalWrite(RelayPin, LOW);
pinMode (FAN, OUTPUT);
pinMode(HUMIDIFIER, OUTPUT);
digitalWrite(HUMIDIFIER, OFF);
digitalWrite(FAN, OFF);
//activate LCD module
lcd.begin(16, 2); // for 16x2 LCD module
lcd.setBacklightPin(3, POSITIVE);
lcd.setBacklight(HIGH);
dht.begin();
//Print a message to the LCD.
lcd.setCursor(0, 0);
lcd.print("Temp");
lcd.setCursor(0, 1);
lcd.print("Humidity");
}
bool isInByteList(byte value, const byte *array, byte length)
{
for (byte i = 0; i < length; i++)
if (array[i] == value)
return true;
return false;
}
void loop() {
ti = rtc.getTime();
Serial.print(ti.hour);
Serial.print(" hour(s), ");
Serial.print(ti.min);
Serial.print(" minute(s)");
Serial.println(" ");
delay (1000);
if (isInByteList(ti.hour, OnHour, sizeof OnHour) && isInByteList(ti.min, OnMin, sizeof OnMin))
{
digitalWrite(RelayPin, LOW);
Serial.println("LIGHT ON");
}
else if (isInByteList(ti.hour, OffHour, sizeof OffHour) && isInByteList(ti.min, OffMin, sizeof OffMin))
{ digitalWrite(RelayPin, HIGH);
Serial.print("LIGHT OFF");
}
}
//Read the temperature and humidity into floating point variables
float h = dht.readHumidity();
float t = dht.readTemperature();
//Move the cursor to the end of the word temp: and print the reading to 2 decimal places
lcd.setCursor(6, 0);
lcd.print(t, 2);
//Move the cursor to the end of the word Humidity: and print the reading to 2 decimal places
lcd.setCursor(10, 1);
lcd.print(h, 2);
//Now begin with the control logic
if (digitalRead(HUMIDIFIER) == ON)
{
//If the humidifier is on, check to see if the humidity is above set point
if (humidity > SETPOINT + DEADBAND)
//we've reached the upper limit, so kill the humidifier
digitalWrite(HUMIDIFIER, OFF);
digitalWrite(FAN, ON);
}
else
{
// If the humidifier is off, check to see if humidity is below setpoint
if (humidity < SETPOINT - DEADBAND)
// We've reached the lower limit, so kiick on the humidifier
digitalWrite(HUMIDIFIER, ON);
digitalWrite(FAN, OFF);
}
}
]
Sorry, it keeps giving me a lcd does not name a type, however if I run the timer project on it's own it works, and the humdity project on it's own it works
Why are you using two LCD libraries?
It's the only way I could get it to work
What kind of LCD do you have? i.e. is it i2c?
I2c 16x2
Ok I have managed to get it to up load to the board now, hopefully it will work
First thing is to clear up some of the blank lines and use Tools > auto format (or Ctrl+t) and fix all the bracket misalingments so that the code compiles. It will help you to see things if you place every { and } on its own line.
Where does loop() end?
Why does your code have ] as the last item?
What LiquidCrystal_I2C.h library are you using, and does it have a constructor like you used?
#include <LiquidCrystal_I2C.h>
//#include <LCD.h>
LiquidCrystal_I2C lcd(0X27, 2, 1, 0, 4, 5, 6, 7); // 0x27 is the I2c bus for a unmodified back pack
It is strongly recommended that you use the hd44780.h library.
Some instructions are here
https://forum.arduino.cc/index.php?topic=636787.msg4313109#msg4313109
Thanks guys for all your advice, I managed to get my code uploaded and with a few tweaks it's working as I had hoped
cattledog:
First thing is to clear up some of the blank lines and use Tools > auto format (or Ctrl+t) and fix all the bracket misalingments so that the code compiles. It will help you to see things if you place every { and } on its own line.Where does loop() end?
Why does your code have ] as the last item?What LiquidCrystal_I2C.h library are you using, and does it have a constructor like you used?
#include <LiquidCrystal_I2C.h>
//#include <LCD.h>
LiquidCrystal_I2C lcd(0X27, 2, 1, 0, 4, 5, 6, 7); // 0x27 is the I2c bus for a unmodified back pack
It is strongly recommended that you use the hd44780.h library. Some instructions are here https://forum.arduino.cc/index.php?topic=636787.msg4313109#msg4313109
so I took your advice and cleaned up the code, it has functioning perfectly for a few days, just seems
like the timer is changing and no longer on an off every 15 minutes, seem to be going closer to 20 min now, would the delays in the circuit be causing this?
#include <DS3231.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <DHT.h>
const byte RelayPin = 4;
DS3231 rtc(SDA, SCL);
Time ti;
LiquidCrystal_I2C lcd(0X27, 2, 1, 0, 4, 5, 6, 7); // 0x27 is the I2c bus for a unmodified back pack
//Globals for dht sensor
#define DHTPIN 7 // what pin its connected to
#define DHTTYPE DHT22 // DHT 22 (AM2302)
DHT dht (DHTPIN, DHTTYPE);// Initialize DHT sensor for normal 16mhz Arduino
//humidity control points
#define SETPOINT 90.0
#define DEADBAND 2.0
#define FAN 5
//These just make code easier to read
#define HUMIDIFIER 9 //instead of using 9 for pin 9 we will name it HUMIDIFIER
#define ON false //the relay is sort of backwards. a low/0/false output is actually on
#define OFF true //the relay is sort of backwards. a high/1/true output is actually on
void setup() {
Serial.begin(9600);
lcd.clear();
while (!Serial);
rtc.begin();
pinMode(RelayPin, OUTPUT);
digitalWrite(RelayPin, LOW);
pinMode (FAN, OUTPUT);
pinMode(HUMIDIFIER, OUTPUT);
digitalWrite (HUMIDIFIER, OFF);
digitalWrite (FAN, OFF);
//activate LCD module
lcd.begin(16, 2); // for 16x2 LCD module
lcd.setBacklightPin(3, POSITIVE);
lcd.setBacklight(HIGH);
dht.begin();
//Print a message to the LCD.
lcd.setCursor(0, 0);
lcd.print("Temp");
lcd.setCursor(0, 1);
lcd.print("Humidity");
} void SetRelayOnState(bool newOnState)
{
static bool currentOnState = true;
// Only print when the state changes
if (newOnState == currentOnState)
return; // Nothing to do
currentOnState = newOnState;
if (currentOnState)
{
digitalWrite(RelayPin, LOW);
Serial.println("RELAY ON");
}
else
{
digitalWrite(RelayPin, HIGH);
Serial.println("RELAY OFF");
}
}
void loop() {
delay(5000);
//Read the temperature and humidity into floating point variables
float h = dht.readHumidity();
float t = dht.readTemperature();
//Cheack to make sure we got numbers back.if not print a error
if (isnan(h) || isnan(t)) {
lcd.setCursor(0, 0);
lcd.print ("restart Ardrino");
//Bail-we cant work with things that aren't numbers!
return;
}
//Move the cursor to the end of the word temp: and print the reading to 2 decimal places
lcd.setCursor(6, 0);
lcd.print(t, 2);
//Move the cursor to the end of the word Humidity: and print the reading to 2 decimal places
lcd.setCursor(10, 1);
lcd.print(h, 2);
//Now begin with the control logic
if (digitalRead(HUMIDIFIER) == ON)
{
//If the humidifier is on, check to see if the humidity is above set point
if (h > SETPOINT + DEADBAND)
{
//we've reached the upper limit, so kill the humidifier
{ digitalWrite(HUMIDIFIER, OFF);
digitalWrite(FAN , OFF);
}
}
}
else
{
// If the humidifier is off, check to see if humidity is below setpoint
if (h < SETPOINT - DEADBAND)
// We've reached the lower limit, so kiick on the humidifier
{ digitalWrite(HUMIDIFIER, ON);
digitalWrite(FAN, ON);
}
}
static int currentMinute = -1;
ti = rtc.getTime();
// Show time at the start of each new minute
if (ti.min != currentMinute)
{
currentMinute = ti.min;
Serial.print(ti.hour);
Serial.print(" hour(s), ");
Serial.print(ti.min);
Serial.println(" minute(s)");
}
if (ti.min % 30 < 15)
{
// For the first half of every half hour, turn on the Relay
SetRelayOnState(true);
}
else
{
// For the second half of every half hour, turn off the Relay
SetRelayOnState(false);
}
}
this is my latest code
it has functioning perfectly for a few days, just seems
like the timer is changing and no longer on an off every 15 minutes, seem to be going closer to 20 min now, would the delays in the circuit be causing this?
It's certainly easy enough to change the one call to delay(5000) to a millis() based "blink without delay" timer and test this hypothesis.
However, if your serial prints indicate that you are switching at 15 minute intervals but with an external clock that looks more like 20 minute intervals I would suspect the rtc is not keeping accurate time. There are certainly plenty of counterfeit chips running around in these $1 modules. I would recommend a simple test sketch where you read the rtc with a millis() timer, and compare the rtc output to both accumulated millis() and an external clock. You may find that millis() is more accurate than the rtc .