South UK
Offline
Sr. Member
Karma: 1
Posts: 482
|
 |
« on: February 24, 2012, 07:13:56 pm » |
Hi all. I am in the process of making my first 'proper' arduino project. I'm putting together a thermstat to switch on my boiler at a set temperature. I am not experienced at all with programming so the source code has taken a while to get working as I wanted it too. Basically I am reading the value from a pot, mapping it to a temperature range, and using this value to switch a digital output if the measured temperature is less than the desired. It does this with else, if statements. I have also added some maths to take the average of a few temp measurements around the house, so I would like to use a switch and lets say, if its value is closed / high, the measured temperature will switch to the average reading, and if its open / low the measured temperature will switch to the single local sensor reading. I have been trying to get this to work by reading a digital input, deciding if the value is low or high and then using that high or low variable in the 'else if' statement that switches the output, but my efforts have failed because the output pin stays active all the time  I hope its only something simple, but if someone could point it out it would save me a lot of headaches  the first lot of code below is the edited (non working) code as explained above, and the second lot is before i started to try and read the switch and stopped it working in case I have really messed it up. /* The circuit: * LDR connected to analog pin 0. * LED / transistor connected from digital pin 3 to ground * LCD RS pin to digital pin 7 * LCD EN pin to digital pin 8 * LCD D4 pin to digital pin 9 * LCD D5 pin to digital pin 10 * LCD D6 pin to digital pin 11 * LCD D7 pin to digital pin 12 * LCD R/W pin to ground * 10K resistor: * ends to +5V and ground * wiper to LCD VO pin (pin 3) * LCD LED+ (15) pin transistor * LCD LED- (16) to ground * Thermisor divider 1 output to analog pin 1 * Thermisor divider 2 output to analog pin 2 */
// These constants won't change. They're used to give names // to the pins used: const int select = A0; // Analog input pin that the temp select pot is attached to const int analogInPin = A1; // Analog input pin that the lDR is attached to const int analogOutPin = 3; // Analog (PWM) output pin that the BACKLIGHT is attached to const int coldPin = 2; // Digital output pin that the COLD RELAY is attached to const int frostPin = 4; // Digital output pin that the frost warning is attached to //const int hotPin = 5; // Digital output pin that the HOT LED is attached to const int out = A2; // Analog input that the 'Out' thermistor is connected too const int hall = A3; // Analog input that the 'Hall' thermistor is connected too const int bed = A4; // Analog input that the 'Bed' thermistor is connected too const int bath = A5; // Analog input that the 'Bath' thermistor is connected too const int lounge = A6; // Analog input that the 'Lounge' thermistor is connected too const int kitchen = A7; // Analog input that the 'Kitchen' thermistor is connected too const int modeButton = 6; //Digital input that the mode button is connected too
//Parameters
const int coldTemp = 10; // lower do something threshold in degrees c const int hotTemp = 20; // upper do something threshold in degrees c const int setPointLow = 5; // lowest temp available const int setPointHigh = 25; // highest temp available const int frostWarning = 10; // outside frost warning threshold float hysteresis = 0.4; // error margin float averageTemp = 0; //place to store average reading float desired = 0; //place to store selected mode float buttonState = 0; //place to store current selected mode
const int minLight = 80; // at or below this light level, use minimum backlight intensity const int maxLight = 920; // at or above this light level, use maximum backlight intensity const int minBacklight = 5; // lowest backlight intensity to use const int maxBacklight = 255; // highest backlight intensity to use
// include the library code: #include <LiquidCrystal.h> #include <math.h>
#define NUMSAMPLES 64
double convert(double RawADC) { double Temp; Temp = log(((10240000/RawADC) - 10000)); Temp = 1 / (0.001129148 + (0.000234125 + (0.0000000876741 * Temp * Temp ))* Temp ); Temp = Temp - 273.15; // Convert Kelvin to Celcius
return Temp; }
// initialize the library with the numbers of the interface pins LiquidCrystal lcd(7, 8, 9, 10, 11, 12);
int sensorValue1 = 0; // value read from the pot int sensorValue = 0; // value read from the LDR int outputValue = 0; // value output to the PWM (analog out) int setPoint = 0; // value set point
void setup() { lcd.begin(20, 4); delay(100); pinMode(3, OUTPUT); //LCD BACKLIGHT pinMode(coldPin, OUTPUT); //COLD WARNING pinMode(frostPin, OUTPUT); //OUTSIDE FROST WARNING pinMode(modeButton, INPUT); //MODE SELECT BUTTON }
void loop() { // LDR PART int sum = 0; for (int i=0; i<16; i++) // do some averaging too { sum += analogRead(analogInPin); } sensorValue = sum/16;
// map it to the range[0..255] of the analog out outputValue = sensorValue/4; // easier than map function outputValue = map(constrain(sensorValue, minLight, maxLight), minLight, maxLight, minBacklight, maxBacklight );
// change the analog out value: analogWrite(analogOutPin, outputValue);
// temp select part
sensorValue1 = analogRead(select); setPoint = map (sensorValue1, 0, 1023, setPointLow, setPointHigh);
// TEMPERATURE PART uint8_t i; float average = 0; //input1 float average1 = 0; //input2 float average2 = 0; //input3 float average3 = 0; //input4 float average4 = 0; //input5 float average5 = 0; //input6 for (i=0; i< NUMSAMPLES; i++) { average += analogRead(out); average1 += analogRead(hall); average2 += analogRead(bed); average3 += analogRead(bath); average4 += analogRead(lounge); average5 += analogRead(kitchen); delay(10); } average /= NUMSAMPLES; average1 /= NUMSAMPLES; average2 /= NUMSAMPLES; average3 /= NUMSAMPLES; average4 /= NUMSAMPLES; average5 /= NUMSAMPLES;
double outTemp = convert(average); double hallTemp = convert(average1); double bedTemp = convert(average2); double bathTemp = convert(average3); double loungeTemp = convert(average4); double kitchenTemp = convert(average5);
//PRINT HALL TEMP AND DO THERMOSTAT DUTIES
lcd.clear(); lcd.setCursor(0,0); lcd.print ("Hal: "); lcd.print(hallTemp, 1); //lcd.print((char)223); //lcd.print ("c");
buttonState = digitalRead(modeButton); if(buttonState == HIGH) desired = 0; else if (buttonState == LOW) desired = 1;
if(desired = 0 && hallTemp <setPoint - hysteresis) digitalWrite(coldPin, HIGH); // set the LED on else if (desired = 0 && hallTemp >setPoint + hysteresis) digitalWrite(coldPin, LOW); // set the LED off else if (desired = 1 && averageTemp >setPoint + hysteresis) digitalWrite(coldPin, HIGH); // set the LED off else if (desired = 1 && averageTemp >setPoint + hysteresis) digitalWrite(coldPin, LOW); // set the LED off
//print set temp lcd.setCursor(11,4); lcd.print ("Set: ");
if(setPoint <setPointLow +1) lcd.print((char)42); else if (setPoint >setPointLow) lcd.print(setPoint);
//PRINT LOUNGE TEMP lcd.setCursor(11,0); lcd.print ("Lng: "); lcd.print(loungeTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT KITCHEN TEMP lcd.setCursor(0,1); lcd.print ("Kit: "); lcd.print(kitchenTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT BED TEMP lcd.setCursor(11,1); lcd.print ("Bed: "); lcd.print(bedTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT BATH TEMP lcd.setCursor(0,2); lcd.print ("Bth: "); lcd.print(bathTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT OUT TEMP lcd.setCursor(0,4); lcd.print ("Out: "); lcd.print(outTemp, 1); //lcd.print((char)223); //lcd.print ("c");
if(outTemp <frostWarning - hysteresis) digitalWrite(frostPin, HIGH); // set the LED on else if (outTemp >frostWarning + hysteresis) digitalWrite(frostPin, LOW); // set the LED off //PRINT average temp averageTemp = hallTemp + bedTemp + bathTemp + loungeTemp + kitchenTemp; averageTemp = averageTemp/5; lcd.setCursor(11,2); lcd.print ("Ave: "); lcd.print(averageTemp, 1); //lcd.print((char)223); //lcd.print ("c");
delay(1000); }
|
|
|
|
|
Logged
|
|
|
|
|
South UK
Offline
Sr. Member
Karma: 1
Posts: 482
|
 |
« Reply #1 on: February 24, 2012, 07:14:08 pm » |
/* The circuit: * LDR connected to analog pin 0. * LED / transistor connected from digital pin 3 to ground * LCD RS pin to digital pin 7 * LCD EN pin to digital pin 8 * LCD D4 pin to digital pin 9 * LCD D5 pin to digital pin 10 * LCD D6 pin to digital pin 11 * LCD D7 pin to digital pin 12 * LCD R/W pin to ground * 10K resistor: * ends to +5V and ground * wiper to LCD VO pin (pin 3) * LCD LED+ (15) pin transistor * LCD LED- (16) to ground * Thermisor divider 1 output to analog pin 1 * Thermisor divider 2 output to analog pin 2 */
// These constants won't change. They're used to give names // to the pins used: const int select = A0; // Analog input pin that the temp select pot is attached to const int analogInPin = A1; // Analog input pin that the lDR is attached to const int analogOutPin = 3; // Analog (PWM) output pin that the BACKLIGHT is attached to const int coldPin = 2; // Digital output pin that the COLD RELAY is attached to const int frostPin = 4; // Digital output pin that the frost warning is attached to //const int hotPin = 5; // Digital output pin that the HOT LED is attached to const int out = A2; // Analog input that the 'Out' thermistor is connected too const int hall = A3; // Analog input that the 'Hall' thermistor is connected too const int bed = A4; // Analog input that the 'Bed' thermistor is connected too const int bath = A5; // Analog input that the 'Bath' thermistor is connected too const int lounge = A6; // Analog input that the 'Lounge' thermistor is connected too const int kitchen = A7; // Analog input that the 'Kitchen' thermistor is connected too
//Parameters
const int coldTemp = 10; // lower do something threshold in degrees c const int hotTemp = 20; // upper do something threshold in degrees c const int setPointLow = 5; // lowest temp available const int setPointHigh = 25; // highest temp available const int frostWarning = 10; // outside frost warning threshold float hysteresis = 0.4; // error margin float averageTemp = 0; //place to store average reading
const int minLight = 80; // at or below this light level, use minimum backlight intensity const int maxLight = 920; // at or above this light level, use maximum backlight intensity const int minBacklight = 5; // lowest backlight intensity to use const int maxBacklight = 255; // highest backlight intensity to use
// include the library code: #include <LiquidCrystal.h> #include <math.h>
#define NUMSAMPLES 64
double convert(double RawADC) { double Temp; Temp = log(((10240000/RawADC) - 10000)); Temp = 1 / (0.001129148 + (0.000234125 + (0.0000000876741 * Temp * Temp ))* Temp ); Temp = Temp - 273.15; // Convert Kelvin to Celcius
return Temp; }
// initialize the library with the numbers of the interface pins LiquidCrystal lcd(7, 8, 9, 10, 11, 12);
int sensorValue1 = 0; // value read from the pot int sensorValue = 0; // value read from the LDR int outputValue = 0; // value output to the PWM (analog out) int setPoint = 0; // value set point
void setup() { lcd.begin(20, 4); delay(100); pinMode(3, OUTPUT); //LCD BACKLIGHT pinMode(coldPin, OUTPUT); //COLD WARNING pinMode(frostPin, OUTPUT); //OUTSIDE FROST WARNING }
void loop() { // LDR PART int sum = 0; for (int i=0; i<16; i++) // do some averaging too { sum += analogRead(analogInPin); } sensorValue = sum/16;
// map it to the range[0..255] of the analog out outputValue = sensorValue/4; // easier than map function outputValue = map(constrain(sensorValue, minLight, maxLight), minLight, maxLight, minBacklight, maxBacklight );
// change the analog out value: analogWrite(analogOutPin, outputValue);
// temp select part
sensorValue1 = analogRead(select); setPoint = map (sensorValue1, 0, 1023, setPointLow, setPointHigh);
// TEMPERATURE PART uint8_t i; float average = 0; //input1 float average1 = 0; //input2 float average2 = 0; //input3 float average3 = 0; //input4 float average4 = 0; //input5 float average5 = 0; //input6 for (i=0; i< NUMSAMPLES; i++) { average += analogRead(out); average1 += analogRead(hall); average2 += analogRead(bed); average3 += analogRead(bath); average4 += analogRead(lounge); average5 += analogRead(kitchen); delay(10); } average /= NUMSAMPLES; average1 /= NUMSAMPLES; average2 /= NUMSAMPLES; average3 /= NUMSAMPLES; average4 /= NUMSAMPLES; average5 /= NUMSAMPLES;
double outTemp = convert(average); double hallTemp = convert(average1); double bedTemp = convert(average2); double bathTemp = convert(average3); double loungeTemp = convert(average4); double kitchenTemp = convert(average5);
//PRINT HALL TEMP AND DO THERMOSTAT DUTIES
lcd.clear(); lcd.setCursor(0,0); lcd.print ("Hal: "); lcd.print(hallTemp, 1); //lcd.print((char)223); //lcd.print ("c");
if(hallTemp <setPoint - hysteresis) digitalWrite(coldPin, HIGH); // set the LED on else if (hallTemp >setPoint + hysteresis) digitalWrite(coldPin, LOW); // set the LED off
//print set temp lcd.setCursor(11,4); lcd.print ("Set: ");
if(setPoint <setPointLow +1) lcd.print((char)42); else if (setPoint >setPointLow) lcd.print(setPoint);
//PRINT LOUNGE TEMP lcd.setCursor(11,0); lcd.print ("Lng: "); lcd.print(loungeTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT KITCHEN TEMP lcd.setCursor(0,1); lcd.print ("Kit: "); lcd.print(kitchenTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT BED TEMP lcd.setCursor(11,1); lcd.print ("Bed: "); lcd.print(bedTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT BATH TEMP lcd.setCursor(0,2); lcd.print ("Bth: "); lcd.print(bathTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//PRINT OUT TEMP lcd.setCursor(0,4); lcd.print ("Out: "); lcd.print(outTemp, 1); //lcd.print((char)223); //lcd.print ("c");
if(outTemp <frostWarning - hysteresis) digitalWrite(frostPin, HIGH); // set the LED on else if (outTemp >frostWarning + hysteresis) digitalWrite(frostPin, LOW); // set the LED off //PRINT average temp averageTemp = hallTemp + bedTemp + bathTemp + loungeTemp + kitchenTemp; averageTemp = averageTemp/5; lcd.setCursor(11,2); lcd.print ("Ave: "); lcd.print(averageTemp, 1); //lcd.print((char)223); //lcd.print ("c");
delay(1000); }
|
|
|
|
|
Logged
|
|
|
|
|
Seattle, WA USA
Online
Brattain Member
Karma: 314
Posts: 35518
Seattle, WA USA
|
 |
« Reply #2 on: February 24, 2012, 07:32:58 pm » |
int sum = 0; for (int i=0; i<16; i++) // do some averaging too { sum += analogRead(analogInPin); } sensorValue = sum/16; Great names. We can tell exactly what is going on. Not. What is this supposed to be doing? What is connected to the analogInPin? What does some generic sensorValue mean? const int analogInPin = A1; // Analog input pin that the lDR is attached to So, why doesn't the name reflect the use? outputValue = sensorValue/4; // easier than map function outputValue = map(constrain(sensorValue, minLight, maxLight), minLight, maxLight, minBacklight, maxBacklight );
// change the analog out value: analogWrite(analogOutPin, outputValue); minLight, maxLight, minBackLight, and maxBackLight are good names. outputValue is a lousy name, as is analogOutPin. // temp select part
sensorValue1 = analogRead(select); setPoint = map (sensorValue1, 0, 1023, setPointLow, setPointHigh); More mixing of good names and lousy names. It's hard to follow what this is supposed to do, with generic names. What is connected to the select pin?
Is this really necessary? float average = 0; //input1 float average1 = 0; //input2 float average2 = 0; //input3 float average3 = 0; //input4 float average4 = 0; //input5 float average5 = 0; //input6 Did you say something? I couldn't hear you over this code screaming ARRAY! average /= NUMSAMPLES; average1 /= NUMSAMPLES; average2 /= NUMSAMPLES; average3 /= NUMSAMPLES; average4 /= NUMSAMPLES; average5 /= NUMSAMPLES; Why are these not numbered 1 to 6? lcd.print((char)42); as opposed to lcd.print('*');? outputValue = sensorValue/4; // easier than map function outputValue = map(constrain(sensorValue, minLight, maxLight), minLight, maxLight, minBacklight, maxBacklight ); You assign outputValue a value, then assign it another value. OK. buttonState = digitalRead(modeButton); Wouldn't the modeButton (pin) define the mode? if(buttonState == HIGH) desired = 0; else if (buttonState == LOW) desired = 1; So, after all this, desired = !digitalRead(modeButton). Why not just code that? After all that, it isn't clear what part of the code you are having problems with? What doesn't works as you want?
|
|
|
|
|
Logged
|
|
|
|
|
Global Moderator
Melbourne, Australia
Offline
Shannon Member
Karma: 218
Posts: 13897
Lua rocks!
|
 |
« Reply #3 on: February 24, 2012, 07:40:22 pm » |
Paul missed one: if(desired = 0 && hallTemp <setPoint - hysteresis) That makes desired become zero. Better read up on the difference between = and ==.
|
|
|
|
|
Logged
|
|
|
|
|
South UK
Offline
Sr. Member
Karma: 1
Posts: 482
|
 |
« Reply #4 on: February 24, 2012, 08:48:41 pm » |
excellent, it is working as I hoped now thanks for the help. This was the crucial bit I had wrong.. desired = digitalRead(modeButton);
if(desired == HIGH && hallTemp <setPoint - hysteresis) digitalWrite(coldPin, HIGH); // set the LED on else if (desired == HIGH && hallTemp >setPoint + hysteresis) digitalWrite(coldPin, LOW); // set the LED off else if (desired == LOW && averageTemp <setPoint + hysteresis) digitalWrite(coldPin, HIGH); // set the LED off else if (desired == LOW && averageTemp >setPoint + hysteresis) digitalWrite(coldPin, LOW); // set the LED off while I very much appreciate all the advice and the time you took to compose a reply, there is no need to be sarcastic. I am aware my code is far from perfect and could be greatly improved which is something I plan to work on - I have little experience with programming. I'm not sure how I could link these together? outputValue = sensorValue/4; // easier than map function outputValue = map(constrain(sensorValue, minLight, maxLight), minLight, maxLight, minBacklight, maxBacklight ); I have looked at arrays before in brief detail but I not sure how this could be changed into one? float average = 0; //input1 float average1 = 0; //input2 float average2 = 0; //input3 float average3 = 0; //input4 float average4 = 0; //input5 float average5 = 0; //input6 I understand all of your other points and I will go though and amend my code. Thanks again -Dan
|
|
|
|
|
Logged
|
|
|
|
|
Seattle, WA USA
Online
Brattain Member
Karma: 314
Posts: 35518
Seattle, WA USA
|
 |
« Reply #5 on: February 24, 2012, 09:48:33 pm » |
I have looked at arrays before in brief detail but I not sure how this could be changed into one? float average = 0; //input1 float average1 = 0; //input2 float average2 = 0; //input3 float average3 = 0; //input4 float average4 = 0; //input5 float average5 = 0; //input6 becomes float average[6]; for(int i=0; i<6; i++) { average[i] /= NUMSAMPLES; }
|
|
|
|
|
Logged
|
|
|
|
|
Des Moines, WA - USA
Offline
God Member
Karma: 21
Posts: 703
|
 |
« Reply #6 on: February 24, 2012, 11:12:20 pm » |
Without meaning to be annoying something a little easier to maintain float average[NUMSAMPLES];
for ( int i = 0; i < NUMSAMPLES; i++ ) { average[i] /= NUMSAMPLES; }
Or less often used but generally faster: for ( int i = NUMSAMPLES; i--; ) { average[i] /= NUMSAMPLES; }
|
|
|
|
|
Logged
|
|
|
|
|
Seattle, WA USA
Online
Brattain Member
Karma: 314
Posts: 35518
Seattle, WA USA
|
 |
« Reply #7 on: February 24, 2012, 11:16:20 pm » |
something a little easier to maintain True, but lets get OP to start using arrays first, before introducing all the subtleties that will trip him or her later.
|
|
|
|
|
Logged
|
|
|
|
|
South UK
Offline
Sr. Member
Karma: 1
Posts: 482
|
 |
« Reply #8 on: February 26, 2012, 06:54:13 pm » |
I have been trying for a while but can't get the array working. When I replace the old with the new code in your post I get errors on the next bit of code stating all the averages, average4.. were not declared in this scope? Not sure how I declare them?
|
|
|
|
|
Logged
|
|
|
|
|
Seattle, WA USA
Online
Brattain Member
Karma: 314
Posts: 35518
Seattle, WA USA
|
 |
« Reply #9 on: February 26, 2012, 07:40:57 pm » |
When I replace the old with the new code in your post I get errors on the next bit of code stating all the averages, average4.. were not declared in this scope? Not sure how I declare them? Show us the code and the errors.
|
|
|
|
|
Logged
|
|
|
|
|
Des Moines, WA - USA
Offline
God Member
Karma: 21
Posts: 703
|
 |
« Reply #10 on: February 26, 2012, 08:04:24 pm » |
I have looked at arrays before in brief detail but I not sure how this could be changed into one? float average = 0; //input1 float average1 = 0; //input2 float average2 = 0; //input3 float average3 = 0; //input4 float average4 = 0; //input5 float average5 = 0; //input6 becomes float average[6]; for(int i=0; i<6; i++) { average[i] /= NUMSAMPLES; }
Having looked over dtokez code more I think what Paul suggested is a good idea but doesn't match exactly what dtokez code is doing so it is not a drop-in replacement for what dtokez had to begin with, thus my modification of Paul's code won't work for dtokez directly either.
|
|
|
|
|
Logged
|
|
|
|
|
Dallas, Texas
Offline
Sr. Member
Karma: 1
Posts: 256
|
 |
« Reply #11 on: February 27, 2012, 10:17:06 am » |
Paul missed one: if(desired = 0 && hallTemp <setPoint - hysteresis) That makes desired become zero. Better read up on the difference between = and ==. I'll add, that's why a lot of people like to do: if(0 == desired && hallTemp <setPoint - hysteresis) Because if you forget the second '=', you wind up with an assignment to a literal rather than a variable, which the compiler will catch. Thusly, completely avoiding the problem in the first place.
|
|
|
|
|
Logged
|
|
|
|
|
South UK
Offline
Sr. Member
Karma: 1
Posts: 482
|
 |
« Reply #12 on: February 27, 2012, 07:13:36 pm » |
Ok, I'm a bit lost with that one so I will leave that for now - it works so at least I can improve it later. I have now had another idea, I would like to loop the section of code that reads the pot input and updates the LCD, because at the moment the LCD will only refresh once the entire program has run - I don't need to update the temperatures that often.
I thought maybe I could use a for loop, and a counter that will loop the bit of code I just talked about through x amount of times, then run the rest of my code to the end
How would I go about doing this? I have only found examples in which a delay inside the for loop is used, or a variety that waits forever for an event before it moves on?
Thanks!
|
|
|
|
|
Logged
|
|
|
|
|
South UK
Offline
Sr. Member
Karma: 1
Posts: 482
|
 |
« Reply #13 on: February 28, 2012, 09:42:14 am » |
Forgot to post the code that I am currently working with - it is a little cleaner now /* The circuit: * LDR connected to analog pin 0. * LED / transistor connected from digital pin 3 to ground * LCD RS pin to digital pin 7 * LCD EN pin to digital pin 8 * LCD D4 pin to digital pin 9 * LCD D5 pin to digital pin 10 * LCD D6 pin to digital pin 11 * LCD D7 pin to digital pin 12 * LCD R/W pin to ground * 10K resistor: * ends to +5V and ground * wiper to LCD VO pin (pin 3) * LCD LED+ (15) pin transistor * LCD LED- (16) to ground * Thermisor divider 1 output to analog pin 1 * Thermisor divider 2 output to analog pin 2 */
// These constants won't change. They're used to give names // to the pins used: const int tempSelectPot = A0; // Analog input pin that the temp select pot is attached to const int LDRPin = A1; // Analog input pin that the lDR is attached to const int LCDBackLight = 3; // Analog (PWM) output pin that the BACKLIGHT is attached to const int coldPin = 2; // Digital output pin that the COLD RELAY is attached to const int frostPin = 4; // Digital output pin that the frost warning LED is attached to //const int hotPin = 5; // Digital output pin that the HOT LED is attached to const int out = A2; // Analog input that the 'Out' thermistor is connected too const int hall = A3; // Analog input that the 'Hall' thermistor is connected too const int bed = A4; // Analog input that the 'Bed' thermistor is connected too const int bath = A5; // Analog input that the 'Bath' thermistor is connected too const int lounge = A6; // Analog input that the 'Lounge' thermistor is connected too const int kitchen = A7; // Analog input that the 'Kitchen' thermistor is connected too const int modeButton = 6; //Digital input that the mode button is connected too
//floating point values float averageTemp = 0; //place to store average reading float desired = 0; //place to store selected mode
//Parameters**************
//const int hotTemp = 20; // upper do something threshold in degrees c const int setPointLow = 5; // lowest desired temp available to select in degrees c const int setPointHigh = 25; // highest desired temp available to select in degrees c const int frostWarning = 5; // outside frost warning LED on threshold in degrees c float hysteresis = 0.4; // Temperature error switching margin to avoid rapid activation in degrees c
const int minLight = 80; // at or below this light level, use minimum backlight intensity const int maxLight = 920; // at or above this light level, use maximum backlight intensity const int minBacklight = 10; // lowest backlight intensity to use const int maxBacklight = 255; // highest backlight intensity to use
// include the library code: #include <LiquidCrystal.h> #include <math.h>
#define NUMSAMPLES 32 // Number of analog samples to take
double convert(double RawADC) { double Temp; Temp = log(((10240000/RawADC) - 10000)); Temp = 1 / (0.001129148 + (0.000234125 + (0.0000000876741 * Temp * Temp ))* Temp ); Temp = Temp - 273.15; // Convert Kelvin to Celcius
return Temp; }
// initialize the library with the numbers of the interface pins LiquidCrystal lcd(7, 8, 9, 10, 11, 12);
int potRead = 0; // value read from the pot int LDRRead = 0; // value read from the LDR int outputValue = 0; // value output to the PWM (analog out) int setPoint = 0; // value set point
void setup() { lcd.begin(20, 4); delay(100); //Declare pin modes pinMode(3, OUTPUT); //LCD BACKLIGHT pinMode(coldPin, OUTPUT); //COLD WARNING pinMode(frostPin, OUTPUT); //OUTSIDE FROST WARNING pinMode(modeButton, INPUT); //MODE SELECT BUTTON digitalWrite(modeButton, HIGH); //set input button to 5v to use internal pull up }
void loop() { // LDR controlled LCD backlight via PWM part int sum = 0; for (int i=0; i<16; i++) // take 16 samples from the analog input { sum += analogRead(LDRPin); } LDRRead = sum/16; // divide by the amount of samples for the average value
// map it to the range[0..255] of the analog output that the LCD backlight it connected to outputValue = LDRRead/4; // alternative to map function for scaling down from analog input outputValue = map(constrain(LDRRead, minLight, maxLight), minLight, maxLight, minBacklight, maxBacklight );
// change the analog out value to adjust LCD backlight intensity analogWrite(LCDBackLight, outputValue);
// Desired temperature selection via potentiometer part potRead = analogRead(tempSelectPot); setPoint = map (potRead, 0, 1023, setPointLow, setPointHigh);
// Temperature measurement and averaging part uint8_t i; float average1 = 0; //input1 float average2 = 0; //input2 float average3 = 0; //input3 float average4 = 0; //input4 float average5 = 0; //input5 float average6 = 0; //input6 for (i=0; i< NUMSAMPLES; i++) { average1 += analogRead(out); average2 += analogRead(hall); average3 += analogRead(bed); average4 += analogRead(bath); average5 += analogRead(lounge); average6 += analogRead(kitchen); delay(10); } average1 /= NUMSAMPLES; average2 /= NUMSAMPLES; average3 /= NUMSAMPLES; average4 /= NUMSAMPLES; average5 /= NUMSAMPLES; average6 /= NUMSAMPLES;
double outTemp = convert(average1); double hallTemp = convert(average2); double bedTemp = convert(average3); double bathTemp = convert(average4); double loungeTemp = convert(average5); double kitchenTemp = convert(average6);
//Clear the LCD ready for fresh data to be printed lcd.clear();
//THERMOSTAT DUTIES desired = digitalRead(modeButton);
if(desired == HIGH && hallTemp <setPoint - hysteresis) { digitalWrite(coldPin, HIGH); // set the LED on lcd.setCursor(19,4); lcd.print((char)165); // print symbol for local temp selection } else if (desired == HIGH && hallTemp >setPoint + hysteresis) { digitalWrite(coldPin, LOW); // set the LED off lcd.setCursor(19,4); lcd.print((char)165); // print symbol for local temp selection } else if (desired == LOW && averageTemp <setPoint + hysteresis) { digitalWrite(coldPin, HIGH); // set the LED off lcd.setCursor(19,4); lcd.print((char)219); // print symbol for average temp selection } else if (desired == LOW && averageTemp >setPoint + hysteresis){ digitalWrite(coldPin, LOW); // set the LED off lcd.setCursor(19,4); lcd.print((char)219); // print symbol for average temp selection }
//Print desired set point temp to LCD lcd.setCursor(11,4); lcd.print ("Set: ");
if(setPoint <setPointLow +1) lcd.print((char)42); // print symbol for frost protection setting else if (setPoint >setPointLow) lcd.print(setPoint);
//Print average temp to LCD averageTemp = hallTemp + bedTemp + bathTemp + loungeTemp + kitchenTemp; // temp zones to take average from averageTemp = averageTemp/5; // divide by number of temp zones to get average
lcd.setCursor(11,2); lcd.print ("Ave: "); lcd.print(averageTemp, 1); //lcd.print((char)223); //lcd.print ("c"); //Print hall temp to LCD lcd.setCursor(0,0); lcd.print ("Hal: "); lcd.print(hallTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//Print lounge temp to LCD lcd.setCursor(11,0); lcd.print ("Lng: "); lcd.print(loungeTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//Print kitchen temp to LCD lcd.setCursor(0,1); lcd.print ("Kit: "); lcd.print(kitchenTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//Print bedroom temp to LCD lcd.setCursor(11,1); lcd.print ("Bed: "); lcd.print(bedTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//Print bathroom temp to LCD lcd.setCursor(0,2); lcd.print ("Bth: "); lcd.print(bathTemp, 1); //lcd.print((char)223); //lcd.print ("c");
//Print outside temp to LCD lcd.setCursor(0,4); lcd.print ("Out: "); lcd.print(outTemp, 1); //lcd.print((char)223); //lcd.print ("c");
// Exterior frost warning LED part if(outTemp <frostWarning - hysteresis) digitalWrite(frostPin, HIGH); // set the LED on else if (outTemp >frostWarning + hysteresis) digitalWrite(frostPin, LOW); // set the LED off
delay(1000); }
|
|
|
|
|
Logged
|
|
|
|
|
Global Moderator
UK
Online
Brattain Member
Karma: 138
Posts: 19067
I don't think you connected the grounds, Dave.
|
 |
« Reply #14 on: February 28, 2012, 09:50:46 am » |
float average1 = 0; //input1 float average2 = 0; //input2 float average3 = 0; //input3 float average4 = 0; //input4 float average5 = 0; //input5 float average6 = 0; //input6 for (i=0; i< NUMSAMPLES; i++) { average1 += analogRead(out); average2 += analogRead(hall); average3 += analogRead(bed); average4 += analogRead(bath); average5 += analogRead(lounge); average6 += analogRead(kitchen); delay(10); } average1 /= NUMSAMPLES; average2 /= NUMSAMPLES; average3 /= NUMSAMPLES; average4 /= NUMSAMPLES; average5 /= NUMSAMPLES; average6 /= NUMSAMPLES;
double outTemp = convert(average1); double hallTemp = convert(average2); double bedTemp = convert(average3); double bathTemp = convert(average4); double loungeTemp = convert(average5); double kitchenTemp = convert(average6);
This just screams "array and for loop"
|
|
|
|
|
Logged
|
Pete, it's a fool looks for logic in the chambers of the human heart.
|
|
|
|
|