Snippets

Peter Scargill Experimental NANO OLED based Power Supply Control

Updated by Peter Scargill

File snippet.txt Modified

  • Ignore whitespace
  • Hide word diff
         sKeypressed = 1;
         instate++;
         updated = 0;
+        updateTimeout = 100;
       }
     }
     else
     }
     else
       dKeypressed = 0;
-    switch (instate)
-    {
-    case 0:
-      if (updated == 0)
-      {
-        gotoXY(0, 1);
-        oled.clearToEOL();
-        updated = 1;
-      }
-      break;
-    case 1:
-      if (updated == 0)
-      {
-        gotoXY(0, 1);
-        LcdP("SET: High V=%d.%d   ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10);
-        oled.clearToEOL();
-        updated = 1;
-      }
-      break;
-    case 2:
-      if (updated == 0)
-      {
-        gotoXY(0, 1);
-        LcdP("SET: Low  V=%d.%d   ", int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10);
-        oled.clearToEOL();
-        updated = 1;
-      }
-      break;
-    case 3:
-      if (updated == 0)
+      switch (instate)
       {
-        gotoXY(0, 1);
-        LcdP("Version 1.01");
-        oled.clearToEOL();
-        updated = 1;
+      case 0:  if (updated == 0)
+                {
+                  gotoXY(0, 1);
+                  oled.clearToEOL();
+                  updated = 1;
+                }
+                break;
+     case 1:  if (updated == 0)
+                {
+                  gotoXY(0, 1);
+                  LcdP("SET: High V=%d.%d   ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10); oled.clearToEOL();
+                  updated = 1;
+                }
+                break;
+     case 2:  if (updated == 0)
+                {
+                  gotoXY(0, 1);
+                  LcdP("SET: Low  V=%d.%d   ", int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10); oled.clearToEOL();
+                  updated = 1;
+                }
+                break;
+     case 3:  if (updated == 0)
+                {
+                  gotoXY(0, 1);
+                  LcdP("Version 1.01"); oled.clearToEOL();
+                  updated = 1;
+                }
+                break;               
+    case 4:  updated=0; instate=0; break;     
       }
-      break;
-    case 4:
-      updated = 0;
-      instate = 0;
-      break;
-    }
-
+  
     if (updateTimeout)
     {
       if (--updateTimeout == 0)
         theState = "warning ";
       }
     }
-    else if (state == 2)
+    else if (state ==2)
     {
-      digitalWrite(WARNING, LOW);
+       digitalWrite(WARNING, LOW);
     }
     else if (state > 2)
     {
       p(",\"status\":\"%s\"}\r\n", theState); // sadly printf here does not support floats
       oled.clearToEOL();
       gotoXY(0, 0);
-      LcdP("POWER SUPPLY CONTROL");
-      oled.clearToEOL();
-
+      LcdP("POWER SUPPLY CONTROL"); oled.clearToEOL();
+ 
       gotoXY(0, 2);
-      LcdP("Current volts: %d.%d", int(vol), ((int(vol * 100)) % 100) / 10);
-      oled.clearToEOL();
+      LcdP("Current volts: %d.%dv", int(vol), ((int(vol * 100)) % 100) / 10); oled.clearToEOL();
       gotoXY(0, 3);
-      LcdP("State: %s", theState);
-      oled.clearToEOL();
+      LcdP("State: %s", theState); oled.clearToEOL();
       gotoXY(0, 4);
-      LcdP("High: %d.%d Low: %d.%d ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10, int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10);
-      oled.clearToEOL();
+      LcdP("High: %d.%dv Low: %d.%dv", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10, int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10); oled.clearToEOL();
       gotoXY(0, 5);
-      LcdP("On:    %05ld:%02ld:%02ld", upSecs / 3600, (upSecs % 3600) / 60, upSecs % 60);
-      oled.clearToEOL();
+      LcdP("On:  %04ldd %02ld:%02ld:%02ld",             secs/86400,(upSecs / 3600) % 24, (upSecs % 3600) / 60, upSecs % 60); oled.clearToEOL();
       gotoXY(0, 6);
-      LcdP("Off:   %05ld:%02ld:%02ld", downSecs / 3600, (downSecs % 3600) / 60, downSecs % 60);
-      oled.clearToEOL();
+      LcdP("Off: %04ldd %02ld:%02ld:%02ld",             secs/86400,(downSecs / 3600) %24 , (downSecs % 3600) / 60, downSecs % 60); oled.clearToEOL();
       gotoXY(0, 7);
-      LcdP("Total: %05ld:%02ld:%02ld", secs / 3600, (secs % 3600) / 60, secs % 60);
-      oled.clearToEOL();
+      LcdP("Tot: %04ldd %02ld:%02ld:%02ld",             secs/86400,(secs / 3600) % 24, (secs % 3600) / 60, secs % 60); oled.clearToEOL();
 
       lightState = 1;
       digitalWrite(LIGHT, HIGH);
         downSecs++;
     }
   }
-}
+}
Updated by Peter Scargill

File snippet.txt Modified

  • Ignore whitespace
  • Hide word diff
-// See blog entry here http://tech.scargill.net/gpio-the-hard-way/
-
 #include <Wire.h>
 #include "SSD1306Ascii.h"
 #include "SSD1306AsciiWire.h"
   oled.begin(&Adafruit128x64, I2C_ADDRESS);
   oled.set400kHz();
   oled.setFont(Adafruit5x7);
-
   uint32_t m = micros();
 
   Serial.begin(57600);
     }
     else
       dKeypressed = 0;
-
-    if (instate == 0)
+    switch (instate)
     {
+    case 0:
       if (updated == 0)
       {
         gotoXY(0, 1);
-        LcdP("                    ");
+        oled.clearToEOL();
         updated = 1;
       }
-    }
-    if (instate == 1)
-    {
+      break;
+    case 1:
       if (updated == 0)
       {
         gotoXY(0, 1);
         LcdP("SET: High V=%d.%d   ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10);
+        oled.clearToEOL();
         updated = 1;
       }
-    }
-    if (instate == 2)
-    {
+      break;
+    case 2:
       if (updated == 0)
       {
         gotoXY(0, 1);
         LcdP("SET: Low  V=%d.%d   ", int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10);
+        oled.clearToEOL();
         updated = 1;
       }
-    }
-    if (instate == 3)
-    {
+      break;
+    case 3:
+      if (updated == 0)
+      {
+        gotoXY(0, 1);
+        LcdP("Version 1.01");
+        oled.clearToEOL();
+        updated = 1;
+      }
+      break;
+    case 4:
       updated = 0;
       instate = 0;
+      break;
     }
 
     if (updateTimeout)
         theState = "warning ";
       }
     }
+    else if (state == 2)
+    {
+      digitalWrite(WARNING, LOW);
+    }
     else if (state > 2)
     {
       digitalWrite(WARNING, HIGH);
       {
         state = 0;
         digitalWrite(RELAY, LOW);
+        digitalWrite(WARNING, LOW);
         downSecs = 0;
         //analogWrite(PIN_PWM,255); // only 3v3 intended so this will likely do
         theState = "standby ";
       p("{\"voltage\":");
       Serial.print(vol);
       p(",\"status\":\"%s\"}\r\n", theState); // sadly printf here does not support floats
-
+      oled.clearToEOL();
       gotoXY(0, 0);
       LcdP("POWER SUPPLY CONTROL");
+      oled.clearToEOL();
 
       gotoXY(0, 2);
       LcdP("Current volts: %d.%d", int(vol), ((int(vol * 100)) % 100) / 10);
+      oled.clearToEOL();
       gotoXY(0, 3);
       LcdP("State: %s", theState);
+      oled.clearToEOL();
       gotoXY(0, 4);
       LcdP("High: %d.%d Low: %d.%d ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10, int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10);
+      oled.clearToEOL();
       gotoXY(0, 5);
       LcdP("On:    %05ld:%02ld:%02ld", upSecs / 3600, (upSecs % 3600) / 60, upSecs % 60);
+      oled.clearToEOL();
       gotoXY(0, 6);
       LcdP("Off:   %05ld:%02ld:%02ld", downSecs / 3600, (downSecs % 3600) / 60, downSecs % 60);
+      oled.clearToEOL();
       gotoXY(0, 7);
       LcdP("Total: %05ld:%02ld:%02ld", secs / 3600, (secs % 3600) / 60, secs % 60);
+      oled.clearToEOL();
 
       lightState = 1;
       digitalWrite(LIGHT, HIGH);
         downSecs++;
     }
   }
-}
+}
Updated by Peter Scargill

File snippet.txt Modified

  • Ignore whitespace
  • Hide word diff
 #include <Wire.h>
 #include "SSD1306Ascii.h"
 #include "SSD1306AsciiWire.h"
+#include <EEPROM.h>
+
+struct
+{
+  float highV;
+  float lowV;
+  uint16_t check;
+} myVars;
 
 // 0X3C+SA0 - 0x3C or 0x3D
 #define I2C_ADDRESS 0x3C
 #define SWITCHON 3.7
 #define SWITCHOFF 3.1
 
-uint32_t secs=0;
-uint32_t upSecs=0;
-uint32_t downSecs=0;
+#define SET 5
+#define UP 6
+#define DOWN 7
+
+uint32_t secs = 0;
+uint32_t upSecs = 0;
+uint32_t downSecs = 0;
 
 void LcdP(char *fmt, ...)
 {
 }
 
 uint32_t mymillis = 0;
+uint32_t my100millis = 0;
 uint8_t lightState = 0;
 uint8_t state = 0; // 0 is power up, 1 is on, 2 is turning off
 float vol;
 uint16_t lightOnSet = 2;
 uint16_t lightOffSet = 1022;
 
-float offVoltage = SWITCHOFF;
-float onVoltage = SWITCHON;
+float average = 0;
 
-float average=0;
+uint8_t updateTimeout = 0;
 
 char *theState = "standby";
 
+uint8_t instate = 0;
+uint8_t updated = 0;
+uint8_t sKeypressed = 0;
+uint8_t uKeypressed = 0;
+uint8_t dKeypressed = 0;
+
 float voltage()
 {
   // read the input on analog pin 0
 
 void gotoXY(int x, int y)
 {
-  oled.setCursor(x,y);
+  oled.setCursor(x, y);
 }
 
 //------------------------------------------------------------------------------
-void setup() {
-  Wire.begin();         
+void setup()
+{
+  EEPROM.get(0, myVars);
+  if (myVars.check != 0x52d2)
+  {
+    myVars.check = 0x52d2;
+    myVars.highV = SWITCHON;
+    myVars.lowV = SWITCHOFF;
+    EEPROM.put(0, myVars);
+  }
+  Wire.begin();
   oled.begin(&Adafruit128x64, I2C_ADDRESS);
-  oled.set400kHz();  
-  oled.setFont(Adafruit5x7);  
+  oled.set400kHz();
+  oled.setFont(Adafruit5x7);
 
   uint32_t m = micros();
 
   pinMode(LIGHT, OUTPUT);
   pinMode(RELAY, OUTPUT);
   pinMode(WARNING, OUTPUT);
+  pinMode(SET, INPUT_PULLUP);
+  pinMode(UP, INPUT_PULLUP);
+  pinMode(DOWN, INPUT_PULLUP);
+
+  average = voltage();
 
-  average=voltage();
-  
-  oled.clear(); 
+  oled.clear();
   LcdP("Init....\r\n");
   //oled.println("Hello world!");
- // oled.println("A long line");
+  // oled.println("A long line");
   //oled.println();
   //oled.set2X();
- // oled.println("2X demo");
- // oled.set1X();
+  // oled.println("2X demo");
+  // oled.set1X();
   //oled.print("\nmicros: ");
- // oled.print(micros() - m);
+  // oled.print(micros() - m);
+  my100millis = millis() + 1000;
 }
 //------------------------------------------------------------------------------
 void loop()
 {
+
   // put your main code here, to run repeatedly:
 
+  if (my100millis <= millis()) // 100ms for key check
+  {
+    my100millis += 100;
+    if (digitalRead(SET) == 0)
+    {
+      if (sKeypressed == 0)
+      {
+        sKeypressed = 1;
+        instate++;
+        updated = 0;
+      }
+    }
+    else
+      sKeypressed = 0;
+    if (digitalRead(UP) == 0)
+    {
+      if (uKeypressed == 0)
+      {
+        uKeypressed = 1;
+        if (instate == 1)
+          myVars.highV += 0.1;
+        else if (instate == 2)
+          myVars.lowV += 0.1;
+        updated = 0;
+        updateTimeout = 100;
+      }
+    }
+    else
+      uKeypressed = 0;
+    if (digitalRead(DOWN) == 0)
+    {
+      if (dKeypressed == 0)
+      {
+        dKeypressed = 1;
+        if (instate == 1)
+          myVars.highV -= 0.1;
+        else if (instate == 2)
+          myVars.lowV -= 0.1;
+        updated = 0;
+        updateTimeout = 100;
+      }
+    }
+    else
+      dKeypressed = 0;
+
+    if (instate == 0)
+    {
+      if (updated == 0)
+      {
+        gotoXY(0, 1);
+        LcdP("                    ");
+        updated = 1;
+      }
+    }
+    if (instate == 1)
+    {
+      if (updated == 0)
+      {
+        gotoXY(0, 1);
+        LcdP("SET: High V=%d.%d   ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10);
+        updated = 1;
+      }
+    }
+    if (instate == 2)
+    {
+      if (updated == 0)
+      {
+        gotoXY(0, 1);
+        LcdP("SET: Low  V=%d.%d   ", int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10);
+        updated = 1;
+      }
+    }
+    if (instate == 3)
+    {
+      updated = 0;
+      instate = 0;
+    }
+
+    if (updateTimeout)
+    {
+      if (--updateTimeout == 0)
+      {
+        instate = 0;
+        updated = 0;
+        EEPROM.put(0, myVars);
+      }
+    }
+  }
+
   if (mymillis <= millis())
   {
-    vol=voltage();
-    average+=(vol/16.0);
-    average=average*16.0/17.0;
-    vol=average;
+    vol = voltage();
+    average += (vol / 16.0);
+    average = average * 16.0 / 17.0;
+    vol = average;
     if (state == 0)
     {
-      if (vol > onVoltage)
+      if (vol > myVars.highV)
       {
         if (onDelay == 0)
         {
-          onDelay = ONDELAY*2;
+          onDelay = ONDELAY * 2;
           theState = "starting";
         }
       }
     }
     else if (state == 1)
-    {  
-      if (vol < offVoltage)
+    {
+      if (vol < myVars.lowV)
       {
-        state = (WAITING*2) + 2;
+        state = (WAITING * 2) + 2;
         theState = "warning ";
       }
     }
       if (state == 2)
       {
         state = 0;
-        digitalWrite(RELAY, LOW); downSecs=0;
+        digitalWrite(RELAY, LOW);
+        downSecs = 0;
         //analogWrite(PIN_PWM,255); // only 3v3 intended so this will likely do
         theState = "standby ";
       }
     else
       digitalWrite(WARNING, LOW);
 
-    if (vol > onVoltage)
+    if (vol > myVars.highV)
     {
       if (onDelay)
       {
         {
           state = 1;
           //analogWrite(PIN_PWM,128); // only 3v3 intended so this will likely do
-          theState = "active  "; upSecs=0;
+          theState = "active  ";
+          upSecs = 0;
         }
       }
     }
-else
-  {
+    else
+    {
       if (onDelay)
       {
-        onDelay=0; theState = "standby "; state=0;
-      }    
-  }
-  
+        onDelay = 0;
+        theState = "standby ";
+        state = 0;
+      }
+    }
+
     if (lightState == 0)
     {
-     p("{\"voltage\":");
+      p("{\"voltage\":");
       Serial.print(vol);
       p(",\"status\":\"%s\"}\r\n", theState); // sadly printf here does not support floats
-      
-      gotoXY(0,0); LcdP("POWER SUPPLY CONTROL");
-      
-      gotoXY(0,2); LcdP("Current volts: %d.%d",int(vol),((int(vol*100))%100)/10);
-      gotoXY(0,3); LcdP("State: %s",theState);
-      gotoXY(0,4); LcdP("High: %d.%d Low: %d.%d ",int(onVoltage),((int(onVoltage*100))%100)/10,int(offVoltage),((int(offVoltage*100))%100)/10);
-      gotoXY(0,5); LcdP("On:    %05ld:%02ld:%02ld",upSecs/3600,(upSecs%3600)/60, upSecs%60);      
-      gotoXY(0,6); LcdP("Off:   %05ld:%02ld:%02ld",downSecs/3600,(downSecs%3600)/60, downSecs%60);  
-      gotoXY(0,7); LcdP("Total: %05ld:%02ld:%02ld",secs/3600,(secs%3600)/60, secs%60);
+
+      gotoXY(0, 0);
+      LcdP("POWER SUPPLY CONTROL");
+
+      gotoXY(0, 2);
+      LcdP("Current volts: %d.%d", int(vol), ((int(vol * 100)) % 100) / 10);
+      gotoXY(0, 3);
+      LcdP("State: %s", theState);
+      gotoXY(0, 4);
+      LcdP("High: %d.%d Low: %d.%d ", int(myVars.highV), ((int(myVars.highV * 100)) % 100) / 10, int(myVars.lowV), ((int(myVars.lowV * 100)) % 100) / 10);
+      gotoXY(0, 5);
+      LcdP("On:    %05ld:%02ld:%02ld", upSecs / 3600, (upSecs % 3600) / 60, upSecs % 60);
+      gotoXY(0, 6);
+      LcdP("Off:   %05ld:%02ld:%02ld", downSecs / 3600, (downSecs % 3600) / 60, downSecs % 60);
+      gotoXY(0, 7);
+      LcdP("Total: %05ld:%02ld:%02ld", secs / 3600, (secs % 3600) / 60, secs % 60);
 
       lightState = 1;
       digitalWrite(LIGHT, HIGH);
       mymillis = millis() + lightOnSet;
     }
     else
-    {  
+    {
       lightState = 0;
       digitalWrite(LIGHT, LOW);
       mymillis = millis() + lightOffSet;
       secs++;
-      if (state==1) upSecs++; else downSecs++;
+      if (state == 1)
+        upSecs++;
+      else
+        downSecs++;
     }
   }
 }
Updated by Peter Scargill

File snippet.txt Modified

  • Ignore whitespace
  • Hide word diff
+// See blog entry here http://tech.scargill.net/gpio-the-hard-way/
+
 #include <Wire.h>
 #include "SSD1306Ascii.h"
 #include "SSD1306AsciiWire.h"
Created by Peter Scargill

File snippet.txt Added

  • Ignore whitespace
  • Hide word diff
+#include <Wire.h>
+#include "SSD1306Ascii.h"
+#include "SSD1306AsciiWire.h"
+
+// 0X3C+SA0 - 0x3C or 0x3D
+#define I2C_ADDRESS 0x3C
+
+SSD1306AsciiWire oled;
+
+#define LIGHT 12
+#define RELAY 11
+#define WARNING 10
+
+#define WAITING 60
+#define ONDELAY 20
+
+#define SWITCHON 3.7
+#define SWITCHOFF 3.1
+
+uint32_t secs=0;
+uint32_t upSecs=0;
+uint32_t downSecs=0;
+
+void LcdP(char *fmt, ...)
+{
+  char buf[128]; // resulting string limited to 128 chars
+  va_list args;
+  va_start(args, fmt);
+  vsnprintf(buf, 128, fmt, args);
+  va_end(args);
+  oled.print(buf);
+}
+
+uint32_t mymillis = 0;
+uint8_t lightState = 0;
+uint8_t state = 0; // 0 is power up, 1 is on, 2 is turning off
+float vol;
+uint8_t onDelay = 0;
+
+uint16_t lightOnSet = 2;
+uint16_t lightOffSet = 1022;
+
+float offVoltage = SWITCHOFF;
+float onVoltage = SWITCHON;
+
+float average=0;
+
+char *theState = "standby";
+
+float voltage()
+{
+  // read the input on analog pin 0
+  int sensorValue = analogRead(A0);
+  // Convert the analog reading (which goes from 0 - 1023) to a voltage (0 - 5V):
+  float vols = sensorValue * (5.0 / 1023.0);
+  // print out the value you read:
+  return (vols);
+}
+
+void p(char *fmt, ...)
+{
+  char buf[128]; // resulting string limited to 128 chars
+  va_list args;
+  va_start(args, fmt);
+  vsnprintf(buf, 128, fmt, args);
+  va_end(args);
+  Serial.print(buf);
+}
+
+void gotoXY(int x, int y)
+{
+  oled.setCursor(x,y);
+}
+
+//------------------------------------------------------------------------------
+void setup() {
+  Wire.begin();         
+  oled.begin(&Adafruit128x64, I2C_ADDRESS);
+  oled.set400kHz();  
+  oled.setFont(Adafruit5x7);  
+
+  uint32_t m = micros();
+
+  Serial.begin(57600);
+  digitalWrite(LIGHT, LOW);
+  digitalWrite(RELAY, LOW);
+  digitalWrite(WARNING, LOW);
+  pinMode(LIGHT, OUTPUT);
+  pinMode(RELAY, OUTPUT);
+  pinMode(WARNING, OUTPUT);
+
+  average=voltage();
+  
+  oled.clear(); 
+  LcdP("Init....\r\n");
+  //oled.println("Hello world!");
+ // oled.println("A long line");
+  //oled.println();
+  //oled.set2X();
+ // oled.println("2X demo");
+ // oled.set1X();
+  //oled.print("\nmicros: ");
+ // oled.print(micros() - m);
+}
+//------------------------------------------------------------------------------
+void loop()
+{
+  // put your main code here, to run repeatedly:
+
+  if (mymillis <= millis())
+  {
+    vol=voltage();
+    average+=(vol/16.0);
+    average=average*16.0/17.0;
+    vol=average;
+    if (state == 0)
+    {
+      if (vol > onVoltage)
+      {
+        if (onDelay == 0)
+        {
+          onDelay = ONDELAY*2;
+          theState = "starting";
+        }
+      }
+    }
+    else if (state == 1)
+    {  
+      if (vol < offVoltage)
+      {
+        state = (WAITING*2) + 2;
+        theState = "warning ";
+      }
+    }
+    else if (state > 2)
+    {
+      digitalWrite(WARNING, HIGH);
+      state--;
+      if (state == 2)
+      {
+        state = 0;
+        digitalWrite(RELAY, LOW); downSecs=0;
+        //analogWrite(PIN_PWM,255); // only 3v3 intended so this will likely do
+        theState = "standby ";
+      }
+    }
+    else
+      digitalWrite(WARNING, LOW);
+
+    if (vol > onVoltage)
+    {
+      if (onDelay)
+      {
+        if (--onDelay == 0)
+        {
+          state = 1;
+          //analogWrite(PIN_PWM,128); // only 3v3 intended so this will likely do
+          theState = "active  "; upSecs=0;
+        }
+      }
+    }
+else
+  {
+      if (onDelay)
+      {
+        onDelay=0; theState = "standby "; state=0;
+      }    
+  }
+  
+    if (lightState == 0)
+    {
+     p("{\"voltage\":");
+      Serial.print(vol);
+      p(",\"status\":\"%s\"}\r\n", theState); // sadly printf here does not support floats
+      
+      gotoXY(0,0); LcdP("POWER SUPPLY CONTROL");
+      
+      gotoXY(0,2); LcdP("Current volts: %d.%d",int(vol),((int(vol*100))%100)/10);
+      gotoXY(0,3); LcdP("State: %s",theState);
+      gotoXY(0,4); LcdP("High: %d.%d Low: %d.%d ",int(onVoltage),((int(onVoltage*100))%100)/10,int(offVoltage),((int(offVoltage*100))%100)/10);
+      gotoXY(0,5); LcdP("On:    %05ld:%02ld:%02ld",upSecs/3600,(upSecs%3600)/60, upSecs%60);      
+      gotoXY(0,6); LcdP("Off:   %05ld:%02ld:%02ld",downSecs/3600,(downSecs%3600)/60, downSecs%60);  
+      gotoXY(0,7); LcdP("Total: %05ld:%02ld:%02ld",secs/3600,(secs%3600)/60, secs%60);
+
+      lightState = 1;
+      digitalWrite(LIGHT, HIGH);
+      switch (state)
+      {
+      case 0:
+        if (onDelay)
+        {
+          lightOnSet = 80;
+          lightOffSet = 944;
+        }
+        else
+        {
+          lightOnSet = 1;
+          lightOffSet = 1023;
+        }
+        digitalWrite(RELAY, LOW);
+        break; // battery is low
+      case 1:
+        lightOnSet = 980;
+        lightOffSet = 44;
+        digitalWrite(RELAY, HIGH);
+        break; // battery is ok
+      default:
+        lightOnSet = 512;
+        lightOffSet = 512;
+        break; // intermediate state;
+      }
+      mymillis = millis() + lightOnSet;
+    }
+    else
+    {  
+      lightState = 0;
+      digitalWrite(LIGHT, LOW);
+      mymillis = millis() + lightOffSet;
+      secs++;
+      if (state==1) upSecs++; else downSecs++;
+    }
+  }
+}