//#include <virtuabotixRTC.h> //Libreria
#include <Wire.h>
#include <RTClib.h>
#include <LiquidCrystal_I2C.h>
// CLK -> 6, DAT -> 7, RST -> 8 Para DS1302
RTC_DS3231 rtc;
//virtuabotixRTC myRTC(6, 7, 8);
LiquidCrystal_I2C lcd(0x27, 20, 4);
// Caracteres customizados para crear numeros grandes.
uint8_t DEFINICION_CARACTERES[8][8] = {
{ //Esquina superior izquierda
B00111,
B01111,
B11111,
B00000,
B11111,
B11111,
B11111,
B11111
},
{ // Cuadro entero
B11111,
B11111,
B11111,
B00000,
B11111,
B11111,
B11111,
B11111
},
{ ///Esquina inferior izquierda
B11111,
B11111,
B11111,
B00000,
B11111,
B11111,
B01111,
B00111
},
{ //Esquina superior derecha
B11100,
B11110,
B11111,
B00000,
B11111,
B11111,
B11111,
B11111
},
{ //Esquina inferior dereccha
B11111,
B11111,
B11111,
B00000,
B11111,
B11111,
B11110,
B11100
},
{ //Punto bajo
B00000,
B00000,
B00000,
B00000,
B11111,
B11111,
B11111,
B11111
},
{ //Punto alto
B11111,
B11111,
B11111,
B00000,
B00000,
B00000,
B00000,
B00000
},
{// punto fino
B00000,
B00000,
B00000,
B00000,
B11100,
B11100,
B11100,
B11100
}
};
const char DEFINICION_NUMEROS[10][4][4] = {
{ // Definición del 0
{ 0, 1, 1, 3 },
{ 1, 32, 32, 1 },
{ 1, 32, 32, 1 },
{ 2, 1, 1, 4 }
},
{ // Definición del 1
{ 0, 1, 1, 32 },
{ 32, 1, 1, 32 },
{ 32, 1, 1, 32 },
{ 2, 1, 1, 4 }
},
{ // Definición del 2
{ 0, 1, 1, 3 },
{ 5, 5, 5, 1 },
{ 1, 6, 6, 6 },
{ 2, 1, 1, 4 }
},
{ // Definición del 3
{ 0, 1, 1, 3 },
{ 32, 5, 5, 1 },
{ 32, 6, 6, 1 },
{ 2, 1, 1, 4 }
},
{ // Definición del 4
{ 0, 32, 32, 3 },
{ 1, 5, 5, 1 },
{ 6, 6, 6, 1 },
{ 32, 32, 32, 4 }
},
{ // Definición del 5
{ 0, 1, 1, 3 },
{ 1, 5, 5, 5 },
{ 6, 6, 6, 1 },
{ 2, 1, 1, 4 }
},
{ // Definición del 6
{ 0, 1, 1, 3 },
{ 1, 5, 5, 5 },
{ 1, 6, 6, 1 },
{ 2, 1, 1, 4 }
},
{ // Definición del 7
{ 0, 1, 1, 3 },
{ 32, 32, 32, 1 },
{ 32, 32, 32, 1 },
{ 32, 32, 32, 4 }
},
{ // Definición del 8
{ 0, 1, 1, 3 },
{ 1, 5, 5, 1 },
{ 1, 6, 6, 1 },
{ 2, 1, 1, 4 }
},
{ // Definición del 9
{ 0, 1, 1, 3 },
{ 1, 5, 5, 1 },
{ 6, 6, 6, 1 },
{ 2, 1, 1, 4 }
},
};
// Función que muestra un dígito a partir de la columna indicada
void mostrarDigito(int digito, int columna) {
for (int fila = 0; fila < 4; fila++) {
lcd.setCursor(columna, fila);
for (int caracter = 0; caracter < 4; caracter++) {
lcd.print(DEFINICION_NUMEROS[digito][fila][caracter]);
}
}
}
void setup() {
Serial.begin(9600); // Activa serial
lcd.init(); // Inicia lcd
lcd.backlight(); // Enciende retroiluminacion
//lcd.clear();
if (! rtc.begin()) {
Serial.println("Couldn't find RTC");
while (1);
}
if (! rtc.begin()) {
Serial.println("RTC is NOT running!");
rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
}
// Creamos los nuevos caracteres
for (int i = 0; i < 8; i++) {
lcd.createChar(i, DEFINICION_CARACTERES[i]);
}
}
// Las variable las inicializamos a -1 para asegurarnos que al inicio "detecta un cambio" y "refresca" el valor mostrándolo
int anteriorHora = -1; // Para saber cuando cambia la hora y "refrescarla"
int anteriorMinuto = -1; // Para saber cuando cambia el minuto y "refrescarlo"
int anteriorSegundo = -1; // Para saber cuando cambia el segundo y saber cuándo se han de mostrar los dos puntos
unsigned long instanteAnterior = 0; // Para controlar cuando han pasado 500 milisegundos desde que se mostraron los dos puntos
bool esperandoOcultarDosPuntos = false; // Para saber cuando se está esperando a ocultar los dos puntos
void loop() {
DateTime now = rtc.now();
// myRTC.updateTime(); // Esta función actualiza las variables para obtener resultados actuales
if (anteriorHora != now.hour()) { // Si cambia el valor de la hora la muestra
anteriorHora = now.hour();
mostrarDigito((now.hour() / 10) % 10, 0);
mostrarDigito(now.hour() % 10, 5);
}
if (anteriorMinuto != now.minute()) { // Si cambia el valor de los minutos los muestra
anteriorMinuto = now.minute();
mostrarDigito((now.minute() / 10) % 10, 11);
mostrarDigito(now.minute() % 10, 16);
}
if (anteriorSegundo != now.second()) { // Si cambia el valor de los segundos, muestra los dos puntos
anteriorSegundo = now.second();
lcd.setCursor(10, 1);
lcd.print((char)7);
lcd.setCursor(10, 2);
lcd.print((char)7);
instanteAnterior = millis(); // Guardamos el instante actual para saber cuándo transcurren 500 milisegundos
esperandoOcultarDosPuntos = true; // Indicamos que se está esperando a ocultar los dos puntos
}
if ((esperandoOcultarDosPuntos == true) && ((millis() - instanteAnterior) >= 500)) { // Si se está esperando ocultar los dos puntos y han pasado medio segundo
esperandoOcultarDosPuntos = false;
lcd.setCursor(10, 1);
lcd.print(' ');
lcd.setCursor(10, 2);
lcd.print(' ');
}
}