I am aware that Arduinos are not really intended as real time clocks, however, I have been very impressed so far as to its precision holding. I could not find any good SevSeg (I am obviously using the 4 digit display, hence SevSeg!) program on Github, so I modified the “counter“ example provided with the Github SevSeg library:
/*
Extant4Life: clock that continues almost in real time, but not quite.
Adjust the 60000 preciseMillisValue value to account for the program logic in the loop!
This is a very basic version with no ability to adjust the clock reading.
*/
#include "SevSeg.h"
SevSeg sevseg; //Instantiate a seven segment controller object
const int initialTimeSet = 35; //This is just the time of day when the program is uploaded to arduino (0035 atm)
const uint16_t preciseMillisValue = 59820; // Adjust very finely to increase precision
void setup() {
byte numDigits = 4;
byte digitPins[] = { 2, 3, 4, 5 };
byte segmentPins[] = { 6, 7, 8, 9, 10, 11, 12, 13 };
bool resistorsOnSegments = false; // 'false' means resistors are on digit pins
byte hardwareConfig = COMMON_ANODE; // See README.md for options
bool updateWithDelays = false; // Default 'false' is Recommended
bool leadingZeros = true; // Use 'true' if you'd like to keep the leading zeros
bool disableDecPoint = false; // Use 'true' if your decimal point doesn't exist or isn't connected
sevseg.begin(hardwareConfig, numDigits, digitPins, segmentPins, resistorsOnSegments,
updateWithDelays, leadingZeros, disableDecPoint);
sevseg.setBrightness(90);
sevseg.setNumber(initialTimeSet, -1);
}
void loop() {
static unsigned long timer = millis();
static int clockDisplay = initialTimeSet;
if (millis() - timer >= preciseMillisValue) { // 60000 milliSeconds is equal to 1 minute
timer += preciseMillisValue; // Adjust very finely to increase precision
clockDisplay++;
//Due to this program logic (here and below), the 60000 figure needs fine adjustment
//60000 is a little too slow
int secondDigit = (clockDisplay / 10) % 10;
if (secondDigit == 6) {
clockDisplay = clockDisplay + 40;
}
if (clockDisplay == 2400) {
clockDisplay = 0;
}
sevseg.setNumber(clockDisplay, -1);
}
sevseg.refreshDisplay(); // Must run repeatedly
}
/// END ///
Over the past couple of days, I have adjusted the preciseMillisValue. It is getting really accurate now. The main program I am using actually has buttons for adjusting time, but I gave this basic program to avoid too many lines of code.
Do you think there is a point where preciseMillisValue can be adjusted to make it so that it will hold for maybe many days, or even weeks, or are some variables going to come into play that might seriously compromise its integrity over that timespan?
I think it may lose integrity over about 50 days anyway due to the usage of millis(). For now though, it seems pretty good.
Any thoughts?