I have been using Arduino for about 2 years now and it seems like a problem I almost always run into with these things is that eventually they start doing random things for unexplainable reason. Things like ignoring lines of code, not responding to user interaction, freezing data readouts, displaying incorrect sensor data, etc.
The problem I currently have is with all each of those issues.. But what's confusing me, is that while I have made VERY few changes to this code over a period of only a couple months, the problems are getting progressively worse over time.
My current project uses a Sainsmart Arduino Nano, a uLCD32-PTu from 4D systems, 2 Dallas DS18B20 temperature sensors and a 2 channel relay. All my controller is meant to do is essentially work as a thermostat. If one of the sensor's heat reading is higher than the corresponding Slider value, turn the corresponding relay on and then off when temperature is lower. Simple enough?
I will focus on one problem at a time in order of significance..
Problem: At completely random times during operation, temperature data that is being sent to display on my LCD will simply freeze it's last read data on the screen...but after a time span of 3 minutes, 5 minutes, or even 15 minutes, it will randomly start reading the live temperature data again.
The other half of my problem, is that if I use the LCD to change either of my slider values, there is sometimes a VERY long delay in response to the value change, or sometimes no response at all when it should be, and used to be immediate. Further confusing me, if I change the value of a slider, it sometimes seems to control the wrong corresponding relay.
Clearly, my Arduino is getting VERY confused somewhere and I have no idea why it's blocking and having other issues like this.. I may just need a set of fresh eyes to proof read my code and make sure I'm doing data calls correctly. Has anyone had a problem like this and if so, how did you fix it?
Here is my code
#define CHANNEL1 8 //LowSpeed RELAY
#define CHANNEL2 9 //HighSpeed RELAY
#include <genieArduino.h>
#include <OneWire.h>
#include <DallasTemperature.h>
#define ONE_WIRE_BUS 2 //DALLAS serial sensors go into input 3
// Setup a oneWire instance to communicate with any OneWire devices
OneWire oneWire(ONE_WIRE_BUS);
// Pass our oneWire reference to Dallas Temperature.
DallasTemperature sensors(&oneWire);
DeviceAddress coolant = { 0x28, 0x1F, 0x70, 0x66, 0x04, 0x00, 0x00, 0x0B };
DeviceAddress cooly = { 0x28, 0xB3, 0x58, 0x66, 0x04, 0x00, 0x00, 0xEC };
int sliderVal = 170;
int sliderVal2 = 190;
int slider0_val = 190;//Set point for high speed fan
int slider1_val = 170;//Set point for low speed fan
int humidity, t, temp;
void setup()
{
pinMode(CHANNEL1, OUTPUT); //Low Speed Fan RELAY
pinMode(CHANNEL2, OUTPUT); //High Speed Fan RELAY
sensors.begin(); // DALLAS sensors begin reading
sensors.setResolution(coolant, 10);
sensors.setResolution(cooly, 10);
genieBegin (GENIE_SERIAL, 56000); //Serial0 for 4D Display
genieAttachEventHandler(myGenieEventHandler);
//Reset the Display (change D4 to D2 if you have original 4D Arduino Adaptor)
pinMode(4, OUTPUT); // Set D4 on Arduino to Output (4D Arduino Adaptor V2 - Display Reset)
digitalWrite(4, 1); // Reset the Display via D4
delay(100);
digitalWrite(4, 0); // unReset the Display via D4
delay (3500); //let the display start up
//Preset values upon device turn on
genieWriteObject(GENIE_OBJ_LED_DIGITS, 6, sliderVal2);
genieWriteObject(GENIE_OBJ_SLIDER, 0, sliderVal2);
genieWriteObject(GENIE_OBJ_LED_DIGITS, 8, sliderVal);
genieWriteObject(GENIE_OBJ_SLIDER, 1, sliderVal);
}
void loop()
{
static long waitPeriod = millis();
genieDoEvents(); // Do this every loop, checks the input buffer for data from the display and runs myGenieEventHandler()
sensors.requestTemperatures();
//Read from sensor every 100ms and write to the display
//delay(1000);
if (millis() >= waitPeriod)
{
temp = (t * 1.8) + 32; //Convert *C to *F.
//sensors.requestTemperatures();
float inside = sensors.getTempF(coolant);
float outside = sensors.getTempF(cooly);
//float tempC = sensors.getTempC(insideThermometer);
//insideThermometer = sensors.requestTemperatures(); // Send the command to get DALLAS temperatures
float tempF;
sensors.requestTemperatures();
Serial.println (inside);////////GOOOD CODE
Serial.println (outside);///////GOOD CODE AGAIN... YAY!
genieWriteObject(GENIE_OBJ_LED_DIGITS, 0, inside);//The first line of code in the section gets ignored for some reason...?? copy and paste
genieWriteObject(GENIE_OBJ_ANGULAR_METER, 0, inside);//HOME SCREEN TEMP GAUGE.........FORM 0
genieWriteObject(GENIE_OBJ_LED_DIGITS, 0, inside);//HOME SCREEN TEMP..................FORM 0
genieWriteObject(GENIE_OBJ_LED_DIGITS, 1, outside);//LOW SPEED FAN CONTROL.............FORM 1
genieWriteObject(GENIE_OBJ_LED_DIGITS, 7, outside);//HIGH SPEED FAN CONTROL............FORM 5
genieWriteObject(GENIE_OBJ_LED_DIGITS, 9, outside); //HOME SCREEN OUTPUT SENSOR........FORM 0
genieWriteObject(GENIE_OBJ_ANGULAR_METER, 1, outside);//HOME SCREEN COOLANT OUTPUT GAUGE.......FORM 0
//waitPeriod = millis() + 1000; //originally set to 10, now set to 1000 for testing purposes update:value change seemed to make it worse
///////////NEEDS TO CHANGE SENSORS//////////////////////
if (slider0_val > outside)//FAN SLIDER SET POINT WITH DALLAS SENSOR...For some reason it's responding in polar opposites of the command?
{
digitalWrite(CHANNEL1, HIGH); // FAN
}
else
{
digitalWrite(CHANNEL1, LOW); // FAN
}
/////////////////////////////////////////////////////
if (slider1_val > outside)
{
digitalWrite(CHANNEL2, HIGH);
}
else
{
digitalWrite(CHANNEL2, LOW);
}
}
}
void myGenieEventHandler(void)
{
genieFrame Event;
genieDequeueEvent(&Event);
//If the cmd received is from a Reported Event
if (Event.reportObject.cmd == GENIE_REPORT_EVENT)
{
if (Event.reportObject.object == GENIE_OBJ_SLIDER) // If the Reported Message was from a Slider
{
if (Event.reportObject.index == 0) // If Slider0
{
slider0_val = genieGetEventData(&Event); // Receive the event data from the Slider0
Serial.println (slider0_val);////////GOOOD CODE WE'LL SEE
}
}
}
//If the cmd received is from a Reported Event
if (Event.reportObject.cmd == GENIE_REPORT_EVENT)
{
if (Event.reportObject.object == GENIE_OBJ_SLIDER) // If the Reported Message was from a Slider
{
if (Event.reportObject.index == 1) // If Slider1
{
slider1_val = genieGetEventData(&Event); // Receive the event data from the Slider1
Serial.println (slider1_val);////////GOOOD CODE WE'LL SEE
}
}
}
////////////////////////////////////////////////
//If the cmd received is from a Reported Object, which occurs if a Read Object is requested in the main code, reply processed here.
if (Event.reportObject.cmd == GENIE_REPORT_OBJ)
{
//Put code in here, like the above, if you want to process data when you have used a genieReadObject in your main loop
//Currently there are none, so this section has no code.
//Filter out the Object and the Index like above, and then same the data into a variable as required.
}
}