TheFishMan65
New member
I have seen build and pictures, but until I get the Arduino up I have no reason to dig into the code. If there was just more time in the day 
#include <Wire.h>
#include "LCDi2c4bit.h" // this is our new library, note quite in 'system space' yet
#define PWM_BACKLIGHT_PIN 8 // pwm-controlled LED backlight
#define DS1307_I2C_ADDRESS 0x68
//LCDI2C4Bit lcd = LCDI2C4Bit(LCD_MCP_DEV_ADDR, LCD_PHYS_LINES, LCD_PHYS_ROWS, PWM_BACKLIGHT_PIN); //0xa7 is the hardware addr of the i2c chip
LCDI2C4Bit lcd = LCDI2C4Bit(0xa7, 4, 20, PWM_BACKLIGHT_PIN); //0xa7 is the hardware addr of the i2c chip
int i = 0;
char buffer[20];
// Convert decimal numbers to binary coded decimal
byte decToBcd(byte val)
{
return ( (val/10*16) + (val%10) );
}
// Convert binary coded decimal to decimal numbers
byte bcdToDec(byte val)
{
return ( (val/16*10) + (val%16) );
}
// Sets date and time, starts the clock
void setDate(byte second, // 0-59
byte minute, // 0-59
byte hour, // 1-23
byte dayOfWeek, // 1-7
byte dayOfMonth, // 1-31
byte month, // 1-12
byte year) // 0-99
{
Wire.beginTransmission(DS1307_I2C_ADDRESS);
Wire.send(0);
Wire.send(decToBcd(second));
Wire.send(decToBcd(minute));
Wire.send(decToBcd(hour));
Wire.send(decToBcd(dayOfWeek));
Wire.send(decToBcd(dayOfMonth));
Wire.send(decToBcd(month));
Wire.send(decToBcd(year));
Wire.endTransmission();
}
// Gets the date and time
void getDate(byte *second,
byte *minute,
byte *hour,
byte *dayOfWeek,
byte *dayOfMonth,
byte *month,
byte *year)
{
Wire.beginTransmission(DS1307_I2C_ADDRESS);
Wire.send(0);
Wire.endTransmission();
Wire.requestFrom(DS1307_I2C_ADDRESS, 7);
*second = bcdToDec(Wire.receive() & 0x7f);
*minute = bcdToDec(Wire.receive());
*hour = bcdToDec(Wire.receive() & 0x3f);
*dayOfWeek = bcdToDec(Wire.receive());
*dayOfMonth = bcdToDec(Wire.receive());
*month = bcdToDec(Wire.receive());
*year = bcdToDec(Wire.receive());
}
void setup() {
pinMode(8, OUTPUT);
Wire.begin();
lcd.init();
//lcd.clear();
//lcd.cursorTo(0,1);
//lcd.print("Hello World");
// uncomment the next line if you need to set the clock.
// format is second, minute, hour, dayOfWeek, dayOfMonth, month, year;
// once you have set the clock, comment this back out so you don't reset
// each time you upload
setDate(30, 25, 15, 7, 5, 3, 11);
}
void loop()
{
byte second, minute, hour, dayOfWeek, dayOfMonth, month, year;
getDate(&second, &minute, &hour, &dayOfWeek, &dayOfMonth, &month, &year);
digitalWrite(8, HIGH);
lcd.cursorTo(0,0);
lcd.print("T.");
lcd.cursorTo(1,0);
lcd.print("IS. . .");
lcd.cursorTo(2,0);
lcd.print("HYDRAAA!!!!!!");
lcd.cursorTo(3,0);
i = millis()/1000;
sprintf(buffer, "%d:%d:%d", hour, minute, second);
// sprintf(buffer, "Uptime: %d seconds", i);
lcd.print(buffer);
}
So after I uploaded the simple Hydra Test sketch, I am unable to load anything else to the AVR. When I try to upload the sketch, I see the LCD screen blink a few times, then the following errors
Binary sketch size: 2644 bytes (of a 30720 byte maximum)
avrdude: stk500_getsync(): not in sync: resp=0x00
avrdude: stk500_disable(): protocol error, expect=0x14, resp=0x51
I made sure the "Board" was set to the Duemilanove. Have tried to re install my FTDI drivers as well with no luck.
Any help would be great.
that0neguy1126,
do you have another arduino you can test with? It looks like you're not sending the sketch to the right port.
So after I uploaded the simple Hydra Test sketch, I am unable to load anything else to the AVR. When I try to upload the sketch, I see the LCD screen blink a few times, then the following errors
Binary sketch size: 2644 bytes (of a 30720 byte maximum)
avrdude: stk500_getsync(): not in sync: resp=0x00
avrdude: stk500_disable(): protocol error, expect=0x14, resp=0x51
I made sure the "Board" was set to the Duemilanove. Have tried to re install my FTDI drivers as well with no luck.
Any help would be great.
I had this same message. When I had put the Arduino software on my windows 7 machine, the documentation from Arduino said windows detects the ftdi board and installs the software. This didn't happen correctly on my machine, even when I manually selected the inf file for the driver. I found a driver install package on the ftdi website (not arduino website), installed that, and then the error message went away.
Even though I don't have the hardware finished yet, I'm starting to prepare my code. I'm going to use Numlock10's source posted in http://www.reefcentral.com/forums/showpost.php?p=17570550&postcount=234 as a base, and try to build upon the ideas and reef data there to include random clouds and thunderstorms. And maybe even the curve DWZM mentions in post http://www.reefcentral.com/forums/showpost.php?p=17556161&postcount=210 .
I've programmed complex systems in my past (now I'm in senior management, one of those guys who doesn't do any REAL work, just goes to meetings and cocktails :-D ) and I think I can contribute to this coding effort.
I'm thinking that the right way to get there is to write code that works in "slopes" or "segments" with target light intensities, or "light level waypoints". So the setLed function would:
1. Know what the latest light intensity was in the previous time it was called (i.e. last time we were called was 26 seconds ago and light intensity was set to 70%).
2. Know what the next targeted light intensity is and when it needs to reach it in the future (i.e. reach 80% in 174 seconds from now).
3. Calculates based on a linear slope what it should set the actual light intensity to (i.e. to 71.3%, because 26*(80%-70%)/(174+26) = 1.3%)
With that type of setLed algorithm as a base we could create three layers of "light intensity" which could be stacked on top of each other:
1. Basic sunrise/stable/sunset light curve (which could be DWZM's Advanced Aquarist bell like curve).
2. A certain amount of basic clouds that roll by throughout the day.
3. An afternoon thunderstorm, which is darker in average and longer than the basic occasional clouds. This layer would override layer #2, basic clouds.
Clouds and thunderstorms should be treated as "reductors" on top of the basic curve. They shouldn't have their own target values, but rather reduce the value of the current basic curve by X percent.
Every time a new day starts we should "pre-program" the day, pulling the basic curve, then deciding how many basic clouds it will have and when they start and finish, then deciding if there will be or not a thunderstorm. With that you'll calculate a "curve for the day" with a certain amount of "light level waypoints" and then the loop() function only has to call setLed telling it what time of the day it is, and setLed will check what the next "waypoint" is and steer the light in that direction using the slope algorithm I mentioned below.
Making lightning would be a fourth layer on top of that, but much simpler because they are so quick. Probably I wouldn't use the "waypoint" and slope algorithm for lightning, just if inside a thunderstorm randomly decide if it is time for lightning and then do the fancy flashing at max intensity if yes.
This probably sounds more complicated in this explanation than it really is to implement with structured code... as it normally is with code, sometimes it is easier to show with code than trying to explain in writing....
Code like the one I described would fit well specially into multi-purpose controllers that might be interrupted to do something else besides lighting (control temperature, answer http requests, etc). With "light waypoints" guiding the lighting algorithm it would never get lost and always do smooth light transitions.
Well, enough talking, I have the code in my mind, just need time to sit down, write it then test it in some type of dry run mode. Hope to do so in the following days/weeks.
Snorkeler (Fabio Paoli)
#include "Wire.h"
#define DS1307_I2C_ADDRESS 0x68 //set rtc
#include <LiquidCrystal.h> // initialize the library with the numbers of the interface pins
//int bluepins = 9;
//int whitepins = 10;
int moon = 8; // moon light
int iBlueIntensity; //declare the integer of blue intensity
float fBlueIntensity; //declare the floating point version of blue intensity
// RTC variables
byte second, rtcMins, oldMins, rtcHrs, oldHrs, dayOfWeek, dayOfMonth, month, year, psecond;
LiquidCrystal lcd(22,23,24,25,26,27);
//LiquidCrystal lcd(12,13,4,5,6,7); // typically 8, 9, 4, 5, 6, 7
// LED variables (Change to match your needs)
byte bluePins[] = {8}; // PWM pins for blues - if you plan to use the photo stagger, please place the pins in the order you would like them to start
byte whitePins[] = {10}; // PWM pins for whites - if you plan to use the photo stagger, please place the pins in the order you would like them to start
byte blueChannels = 1; // how many PWMs for blues (count from above)
byte whiteChannels = 1; // how many PWMs for whites (count from above)
int photoStagger = 0; // offset for east - west delay on each channel in minutes
int startOffset = 0; // offset for start times in minutes - used if you want to change the start and finish time of the cycle. i.e move it to a later time in the day
int colourOffset = 15; // offset for whites to start after blues start in minutes
byte blueLevel[] = {255}; // max intensity for Blue LED's
byte whiteLevel[] = {255}; // max intensity for White LED's
// Month Data for Start, Stop, Photo Period and Fade (based off of actual times, best not to change)
int daysInMonth[12] = {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}; //Days in each month
int minMinuteStart[12] = {310, 332, 348, 360, 372, 386, 394, 387, 364, 334, 307, 298}; //Minimum start times in each month
int maxMinuteStart[12] = {331, 347, 360, 372, 386, 394, 388, 365, 335, 308, 298, 309}; //Max start time in each month
int minMinuteFade[12] = {350, 342, 321, 291, 226, 173, 146, 110, 122, 139, 217, 282}; //Minimum fade time in each month
int maxMinuteFade[12] = {342, 321, 291, 226, 173, 146, 110, 122, 139, 217, 282, 350}; //Max fade time in each month
int minMinuteStop[12] = {1122, 1120, 1102, 1073, 1047, 1034, 1038, 1050, 1062, 1071, 1085, 1105}; //minimum stop times each month
int maxMinuteStop[12] = {1121, 1103, 1074, 1048, 1034, 1038, 1050, 1061, 1071, 1084, 1104, 1121}; //maximum stop times each month
// Weather variables
int weather = 0; // 0 off, 1 on
int clearDays[12] = {15, 12, 20, 23, 28, 37, 43, 48, 51, 41, 29, 23};
int cloudyDays[12] = {60, 61, 62, 60, 64, 63, 68, 66, 63, 54, 52, 53};
float clearDay = 0.25; // Max cloud value on clear day (percent of max string value)
float cloudyDay = 0.75; // Max cloud value on cloudy day (percent of max string value)
float normalDay = 0.5; // Max cloud value on normal day (percent of max string value)
byte value;
int day, fadeOn, fadeOff, time, pause, count, cloud;
long start, finish;
// Other variables - Do not need to be changed.
int minCounter; // counter that resets at midnight
long secCounter; // counter for seconds - needed for weather
int fadeDuration; // minutes to fade - calculated by map above
int ledStartMins; // minute to start led's - calculated by map above
int ledStopMins; // minute to stop led's - calculated by map above
byte blueMax[] = {0}; // used for over temp protection
byte whiteMax[] = {0}; // used for over temp protection
byte valueBlue[] = {0}; // value for clouds
byte valueWhite[] = {0}; // value for clouds
/****** LED Functions ******/
/***************************/
//function to set LED brightness according to time of day
byte setLed(
int mins, // current time in minutes
byte ledPin, // pin for this channel of LEDs
int start, // start time for this channel of LEDs
int fade, // fade duration for this channel of LEDs
int stop, // stop time for this channel of LEDs
byte ledMax, // max value for this channel of LEDs
long begin, // time cloud cycle begins in seconds
long secs, // current time in seconds
int on, // time for cloud to fade on in seconds
int off, // time for cloud to fade off in seconds
long time, // time of cloud
byte value // value for cloud
// max value for this channel
) {
byte ledVal = 0;
if (mins <= start || mins >= stop) //this is when the LEDs are off, thus ledVal is 255;
{
ledVal = 0;
}
if (mins > start && mins <= start + fade) //this is sunrise
{
ledVal = map(mins, start, start + fade, 0, ledMax);
}
if (mins > start + fade && mins < stop - fade && weather == 1)
{
ledVal = ledMax;
if (count == 1){
if (secs >= begin && secs < begin + fadeOn)
{
ledVal = map(secs, begin, begin + on, ledMax, value);
}
if (secs >= begin + on && secs < begin + on + time)
{
ledVal = value;
}
if (secs >= begin + on + time && secs < begin + on + time + off)
{
ledVal = map(secs, begin + on + time, begin + on + time + off, value, ledMax);
}
if (secs >= begin + on + time + off)
{
ledVal = ledMax;
}
if (secs >= finish)
{
count = 0;
}
}
}
if (mins > start + fade && mins < stop - fade && weather == 0)
{
ledVal = ledMax;
}
if (mins < stop && mins >= stop - fade) //this is the sunset
{
ledVal = map(mins, stop - fade, stop, ledMax, 0);
}
analogWrite(ledPin, ledVal);
return ledVal;
}
/***** RTC Functions *******/
/***************************/
// Convert normal decimal numbers to binary coded decimal
byte decToBcd(byte val)
{
return ( (val/10*16) + (val%10) );
}
// Convert binary coded decimal to normal decimal numbers
byte bcdToDec(byte val)
{
return ( (val/16*10) + (val%16) );
}
// 1) Sets the date and time on the ds1307
// 2) Starts the clock
// 3) Sets hour mode to 24 hour clock
// Assumes you're passing in valid numbers
void setDateDs1307(byte second, // 0-59
byte minute, // 0-59
byte hour, // 1-23
byte dayOfWeek, // 1-7
byte dayOfMonth, // 1-28/29/30/31
byte month, // 1-12
byte year) // 0-99
{
Wire.beginTransmission(DS1307_I2C_ADDRESS);
Wire.send(0);
Wire.send(decToBcd(second)); // 0 to bit 7 starts the clock
Wire.send(decToBcd(minute));
Wire.send(decToBcd(hour)); // If you want 12 hour am/pm you need to set
// bit 6 (also need to change readDateDs1307)
Wire.send(decToBcd(dayOfWeek));
Wire.send(decToBcd(dayOfMonth));
Wire.send(decToBcd(month));
Wire.send(decToBcd(year));
Wire.endTransmission();
}
// Gets the date and time from the ds1307
void getDateDs1307(byte *second,
byte *minute,
byte *hour,
byte *dayOfWeek,
byte *dayOfMonth,
byte *month,
byte *year)
{
// Reset the register pointer
Wire.beginTransmission(DS1307_I2C_ADDRESS);
Wire.send(0);
Wire.endTransmission();
Wire.requestFrom(DS1307_I2C_ADDRESS, 7);
// A few of these need masks because certain bits are control bits
*second = bcdToDec(Wire.receive() & 0x7f);
*minute = bcdToDec(Wire.receive());
*hour = bcdToDec(Wire.receive() & 0x3f); // Need to change this if 12 hour am/pm
*dayOfWeek = bcdToDec(Wire.receive());
*dayOfMonth = bcdToDec(Wire.receive());
*month = bcdToDec(Wire.receive());
*year = bcdToDec(Wire.receive());
}
int moonPhase(int moonYear, int moonMonth, int moonDay)
{
int dayFromYear, dayFromMonth;
double julianDay;
int phase;
if (moonMonth < 3) //keep the month before march
{
moonYear--; //take away a year
moonMonth += 12; //add an extra 12 months (the year taken away from before)
}
++moonMonth;
dayFromYear = 365.25 * moonYear; //get days from current year
dayFromMonth = 30.6 * moonMonth; //get number of days from the current month
julianDay = dayFromYear + dayFromMonth + moonDay - 694039.09; //add them all
julianDay /= 29.53; //divide by the length of lunar cycle
phase = julianDay; //take integer part
julianDay -= phase; //get rid of the int part
phase = julianDay*8 + 0.5; //get it between 0-8 and round it by adding .5
phase = phase & 7; //get a number between 1-7
return phase; //1 == new moon, 4 == full moon
}
/*||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| D E F I N E : O N E S E C O N D |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||*/
void onesecond() //function that runs once per second while program is running
{
byte second, minute, hour, dayOfWeek, dayOfMonth, month, year;
getDateDs1307(&second, &minute, &hour, &dayOfWeek, &dayOfMonth, &month, &year);
lcd.setCursor(0, 0);
if(hour>0)
{
if(hour<=12)
{
lcd.print(hour, DEC);
}
else
{
lcd.print(hour-12, DEC);
}
}
else
{
lcd.print("12");
}
lcd.print(":");
if (minute < 10) {
lcd.print("0");
}
lcd.print(minute, DEC);
//lcd.print(":");
//if (second < 10) {
// lcd.print("0");
//}
//lcd.print(second, DEC);
if(hour<12)
{
lcd.print("am");
}
else
{
lcd.print("pm");
}
lcd.print(" ");
delay(1000);
}
void setup() {
//pinMode(bluepins, OUTPUT),
//pinMode(whitepins, OUTPUT),
pinMode(moon, OUTPUT);
// init I2C
Serial.begin(9600);
Wire.begin();
randomSeed(analogRead(1));
/*||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| S E T U P - D I S P L A Y |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||*/
byte second, minute, hour, dayOfWeek, dayOfMonth, month, year;
Wire.begin();
// Change these values to what you want to set your clock to.
// You probably only want to set your clock once and then remove
// the setDateDs1307 call.
second = 00;
minute = 50;
hour = 6;
dayOfWeek = 0; // Sunday is 0
dayOfMonth = 22;
month = 5;
year = 11;
setDateDs1307(second, minute, hour, dayOfWeek, dayOfMonth, month, year);
// set up the LCD's number of columns and rows:
lcd.begin(16, 2);
// Print a message to the LCD.
lcd.setCursor(1, 0);
lcd.write(0);
lcd.write(1);
lcd.setCursor(4, 0);// set the cursor to column 4, line 0
lcd.print("SaltyDog");
lcd.setCursor(13, 0);
lcd.write(3);
lcd.write(2);
lcd.setCursor(1, 0);
lcd.print("Reef Controller");
delay(2000);
lcd.clear();
lcd.setCursor(3, 0);
lcd.print("Version 1.0");
delay(2000);
lcd.clear();
lcd.setCursor(8, 0);// set the cursor to column 4, line 0
lcd.print("SaltyDog");
}
/***** Main Loop ***********/
/***************************/
void loop(){
onesecond();
float fSecond, fHour, fMinute; //turn the times read from the RTC into float for math ops
byte second, minute, hour, dayOfWeek, dayOfMonth, month, year; //declare variables to hold the times
getDateDs1307(&second, &rtcMins, &rtcHrs, &dayOfWeek, &dayOfMonth, &month, &year);
fSecond = (float) second; //sets fSecond as the float version of the integer second from the RTC
fMinute = (float) minute; //same as above, but for the minute
fHour = (float) hour; //ditto, but for the hour
int lunarCycle = moonPhase(year, month, dayOfMonth); //get a value for the lunar cycle
//--------MOON LED SETUP----------//
if ( ((hour == 7) && (minute < 30)) || (hour < 7))//Off at 730am.
{
fBlueIntensity = 255; //...then we want the blue LED at the max brightness (255)
}
else if (hour > 17) //&& (hour < 19)) // On at 5pm
{
fBlueIntensity = 255 * (((fHour - 17) + (fMinute / 59)) / 7); //...set intensity out of 255 based on time since 17:00
}
else
{
fBlueIntensity = 0;
}
//---------account for the moon cycle with the blue LEDs---------//
if (lunarCycle == 0) //new moon
{
fBlueIntensity /= 2;
}
if ((lunarCycle == 1) || (lunarCycle == 7)) //cresent
{
fBlueIntensity /= 1.75 ;
}
if ((lunarCycle == 2) || (lunarCycle == 6)) //half moon
{
fBlueIntensity /= 1.5;
}
if ((lunarCycle == 3) || (lunarCycle == 5)) //gibbous
{
fBlueIntensity /= 1.25;
}
//full moon is full intensity
//----------FLOAT TO INT-------------//
iBlueIntensity = (int) fBlueIntensity;
//---prepare the intensities to be written to pin----//
if (iBlueIntensity < 0) //if the blue intensity is less then 0, set it to 0
{
iBlueIntensity = 0;
}
//------------and finally, we write the values of the lights to the pins--------------//
analogWrite(moon, iBlueIntensity);
delay(1000);
minCounter = rtcHrs * 60 + rtcMins;
secCounter = (long)minCounter * 60 + (long)second;
// Start and Stop Times, Fade Time Functions
ledStartMins = map(dayOfMonth, 1, daysInMonth[month-1], minMinuteStart[month-1], maxMinuteStart[month-1]) + startOffset; //LED Start time
fadeDuration = map(dayOfMonth, 1, daysInMonth[month-1], minMinuteFade[month-1], maxMinuteFade[month-1]); //LED Fade time
ledStopMins = map(dayOfMonth, 1, daysInMonth[month-1], minMinuteStop[month-1], maxMinuteStop[month-1]) + startOffset; // LED Stop time
// Weather Functions
if (minCounter == 0 && second == 0 || day == 0){
{
day = random(1,101);
}
}
if (count == 0){
if (day <= clearDays[month-1]) // Clear Day
{
int t;
for (t = 0; t < blueChannels; t++)
{
valueBlue[t] = random(blueLevel[t]*clearDay,blueLevel[t]);
}
for (t = 0; t < whiteChannels; t++)
{
valueWhite[t] = random(whiteLevel[t]*clearDay,whiteLevel[t]);
}
}
if (day > clearDays[month-1] && day <= cloudyDays[month-1]) // Cloudy Day
{
int t;
for (t = 0; t < blueChannels; t++)
{
valueBlue[t] = random(blueLevel[t]*normalDay,blueLevel[t]*cloudyDay);
}
for (t = 0; t < whiteChannels; t++)
{
valueWhite[t] = random(whiteLevel[t]*normalDay,whiteLevel[t]*cloudyDay);
}
}
if (day > cloudyDays[month-1]) // Normal Day
{
int t;
for (t = 0; t < blueChannels; t++)
{
valueBlue[t] = random(blueLevel[t]*normalDay,blueLevel[t]);
}
for (t = 0; t < whiteChannels; t++)
{
valueWhite[t] = random(whiteLevel[t]*normalDay,whiteLevel[t]);
}
}
fadeOn = random(5,8); // Fade on of cloud in seconds
fadeOff = random(5,8); // Fade off of cloud in seconds
time = random(30,300); // Length of cloud in seconds
pause = random(5,300); // Time between clouds in seconds
start = secCounter; // Sets cycle start time
finish = start + fadeOn + time + fadeOff + pause; // Sets cylce finish time in seconds
count = 1;
}
int t;
for (t = 0; t < blueChannels; t++)
{
blueMax[t] = blueLevel[t];
}
for (t = 0; t < whiteChannels; t++)
{
whiteMax[t] = whiteLevel[t];
}
// LED State and Serial Print
if (psecond != second){
psecond = second;
/*set LED states
Serial.print("Date - ");
Serial.print(dayOfMonth,DEC);
Serial.print("/");
Serial.print(month,DEC);
Serial.print("/");
Serial.println(year,DEC);
Serial.print("Time - ");
Serial.print(rtcHrs,DEC);
Serial.print(":");
Serial.print(rtcMins,DEC);
Serial.print(":");
Serial.println(second,DEC);
Serial.println("");
Serial.print("Day Value - ");
Serial.println(day);
Serial.print("Fade on - ");
Serial.print(fadeOn);
Serial.println(" seconds");
Serial.print("Length of cloud - ");
Serial.print(time);
Serial.println(" seconds");
Serial.print("Fade off - ");
Serial.print(fadeOff);
Serial.println(" seconds");
Serial.print("Pause before next cloud - ");
Serial.print(pause);
Serial.println(" seconds");
Serial.print("Time cycle started - ");
Serial.println(start);
Serial.print("Time cycle will finish - ");
Serial.println(finish);
Serial.print("Current time in seconds - ");
Serial.println(secCounter);
Serial.println(""); */
update_leds();
}
delay(50);
}
void update_leds( void ){
int i;
byte ledVal;
for (i = 0; i < blueChannels; i++){
ledVal = setLed(minCounter, bluePins[i], ledStartMins + (photoStagger * (i+1)), fadeDuration, ledStopMins - (photoStagger * (i+1)), blueMax[i], start, secCounter, fadeOn, fadeOff, time, valueBlue[i]);
}
for (i = 0; i < whiteChannels; i++){
ledVal = setLed(minCounter, whitePins[i], ledStartMins + colourOffset + (photoStagger * (i+1)), fadeDuration, ledStopMins - colourOffset - (photoStagger * (i+1)), whiteMax[i], start, secCounter, fadeOn, fadeOff, time, valueWhite[i]);
}
}