#include "SevSeg.h"
SevSeg sevseg;
const double VALOR_ESCALA_CONVERSION_ADC_VOLT = (50.0/4095.0);
int modoDisplay = LOW; //LOw muestra tensión intantánea, HIGH muestra tensión promedio
const int ledVerde = 32;
const int ledRojo = 33;
const int ledAmarillo = 23;
const int ledVioleta = 21;
const int ADC = 34;
const int numeroMuestras = 5;
int contadorMuestras = 0; // de 0-4
float muestrasTensiones[numeroMuestras-1] = {0}; //5 muestras de 0-4
bool primerTensionPromedio = true; //variable para saber cuando calculo el primer tiempo promedio
float tensionPromedio = 0;
//PULSADORES
//pulsador para apagar led alarma tension instantanea
int estadoBotonTI = HIGH;
const int buttonPinTI = 35;
int contadorApagadoLedVerde = 0; //despues de apagar el boton se mantiene apagado por 3seg el led
bool mantenerLedVerdeApagado = false;
//pulsador para apagar led alarma tension promedio
int estadoBotonTP = HIGH;
const int buttonPinTP = 22;
int contadorApagadoLedAmarillo = 0; //despues de apagar el boton se mantiene apagado por 3seg el led
bool mantenerLedAmarilloApagado = false;
//ALARMAS
// Definir las variables para los valores de tensión intantanea
float limiteInferiorTI = 38.0;
float limiteSuperiorTI = 42.0;
float limiteInferiorAppTI = 36.0;
float limiteSuperiorAppTI = 44.0;
// Definir las variables para los valores de tensión promedio
float limiteInferiorTP = 39.0;
float limiteSuperiorTP = 41.0;
float limiteInferiorAppTP = limiteInferiorTI;
float limiteSuperiorAppTP = limiteSuperiorTI;
void setup() {
byte numDigits = 4;
byte digitPins[] = {14, 15, 2, 5};
byte segmentPins[] = {12, 4, 19, 26, 27, 13, 18, 25};
byte hardwareConfig = COMMON_ANODE;
bool resistorsOnSegments = false;
bool updateWithDelays = false;
bool leadingZeros = false;
bool disableDecPoint = false;
pinMode(ledVerde, OUTPUT);
pinMode(ledRojo, OUTPUT);
pinMode(ledAmarillo, OUTPUT);
pinMode(ledVioleta, OUTPUT);
pinMode(buttonPinTI, INPUT_PULLUP);
pinMode(buttonPinTP, INPUT_PULLUP);
pinMode(ADC, INPUT);
sevseg.begin(hardwareConfig, numDigits, digitPins, segmentPins);
Serial.begin(115200);
}
void loop() {
static unsigned long tiempoEjec = millis() + 500;
static unsigned long tiempoEjecTP = millis() + 1000;
int tensionRealEnteraMultiplicada = 0;
float tensionAux = 0;
bool tensionIEstaEnValoresNormales;
bool tensionIEstaEnValoresAlarmaLocal;
bool tensionIEstaEnValoresMinimosApp;
bool tensionIEstaEnValoresMaximosApp;
bool tensionPEstaEnValoresNormales;
bool tensionPEstaEnValoresAlarmaLocal;
bool tensionPEstaEnValoresMinimosApp;
bool tensionPEstaEnValoresMaximosApp;
if(millis() >= tiempoEjec){
tiempoEjec += 500;
int tensionInstantaneaEntera = 0;
mantenerLedVerdeApagado = false;
mantenerLedAmarilloApagado = false;
float tensionMedida = analogRead(ADC);
//los primeros 5 segundos se los toma para calcular la primera tension promedio
if(primerTensionPromedio){
if(millis() >= tiempoEjecTP){
tiempoEjecTP += 1000;
muestrasTensiones[contadorMuestras] = tensionMedida * VALOR_ESCALA_CONVERSION_ADC_VOLT;
contadorMuestras++;
//reseteo el contador si llego a la ultima posicion y ya pasa a calcular el tiempo promedio cada 1 seg
if(contadorMuestras == (numeroMuestras - 1)){
contadorMuestras = 0;
primerTensionPromedio = false;
}
}
}
if((millis() >= tiempoEjecTP) && !primerTensionPromedio){
tiempoEjecTP += 1000;
//Calcular el promedio móvil de la tension
for(int i=0; i <= (numeroMuestras - 1); i++){
tensionAux += muestrasTensiones[i];
}
tensionPromedio = tensionAux/(numeroMuestras - 1);
Serial.println("tension Promedio");//comento estas 2 lineas y no funca (?)
Serial.println(tensionPromedio);
muestrasTensiones[contadorMuestras] = tensionMedida * VALOR_ESCALA_CONVERSION_ADC_VOLT;
contadorMuestras++;
//reseteo el contador si llego a la ultima posicion
if(contadorMuestras == (numeroMuestras - 1)){
contadorMuestras = 0;
}
}
//TENSION INSTANTANEA
float tensionInstantanea = tensionMedida * VALOR_ESCALA_CONVERSION_ADC_VOLT;
tensionInstantaneaEntera = (int) (tensionInstantanea * 100);
tensionIEstaEnValoresNormales = (tensionInstantanea >= limiteInferiorTI) && (tensionInstantanea <= limiteSuperiorTI);
tensionIEstaEnValoresAlarmaLocal = (tensionInstantanea >= limiteInferiorAppTI) && (tensionInstantanea < limiteSuperiorAppTI);
tensionIEstaEnValoresMinimosApp = (tensionInstantanea < limiteInferiorAppTI);
tensionIEstaEnValoresMaximosApp = (tensionInstantanea > limiteSuperiorAppTI);
//TENSION PROMEDIO
float tensionPromedioEntera = (int) (tensionPromedio * 100);
tensionPEstaEnValoresNormales = (tensionPromedio >= limiteInferiorTP) && (tensionPromedio <= limiteSuperiorTP);
tensionPEstaEnValoresAlarmaLocal = (tensionPromedio >= limiteInferiorAppTP) && (tensionPromedio < limiteSuperiorAppTP);
tensionPEstaEnValoresMinimosApp = (tensionPromedio < limiteInferiorAppTP);
tensionPEstaEnValoresMaximosApp = (tensionPromedio > limiteSuperiorAppTP);
// Presentar la medición en el display según el modo
if(modoDisplay == LOW){
sevseg.setNumber(tensionInstantaneaEntera, 2);
}else{
sevseg.setNumber(tensionPromedioEntera, 2);
}
//Logica tension instantanea
if(tensionIEstaEnValoresNormales){
if(!mantenerLedVerdeApagado){
Serial.println("Tensión instantánea en valores normales");
Serial.println(tensionInstantanea, 2);
digitalWrite(ledVerde, HIGH);
digitalWrite(ledRojo, LOW);
}
}
if(!tensionIEstaEnValoresNormales && tensionIEstaEnValoresAlarmaLocal){
Serial.println("Tensión entre instantánea "+ String(limiteInferiorAppTI)+ " y " + String(limiteSuperiorAppTI) + " alarma local encendida");
Serial.println(tensionInstantanea, 2);
digitalWrite(ledVerde, LOW);
digitalWrite(ledRojo, HIGH);
}
if(tensionIEstaEnValoresMaximosApp){
Serial.println("Tensión instantánea superior a la máxima permitida alarma local encendida y se informa a la APP.");
Serial.println(tensionInstantanea, 2);
digitalWrite(ledVerde, LOW);
digitalWrite(ledRojo, HIGH);
}
if(tensionIEstaEnValoresMinimosApp){
Serial.println("Tensión instantánea inferior a la mínima permitida alarma local encendida y se informa a la APP.");
Serial.println(tensionInstantanea, 2);
digitalWrite(ledVerde, LOW);
digitalWrite(ledRojo, HIGH);
}
contadorApagadoLedVerde++;
if(contadorApagadoLedVerde == 6){
contadorApagadoLedVerde = 0;
mantenerLedVerdeApagado = false;
}
//Logica tension promedio
if((millis() >= tiempoEjecTP && !primerTensionPromedio)){
if(tensionPEstaEnValoresNormales){
if(!mantenerLedAmarilloApagado){
Serial.println("Tensión promedio en valores normales");
Serial.println(tensionPromedio, 2);
digitalWrite(ledAmarillo, HIGH);
digitalWrite(ledVioleta, LOW);
}
}
if(!tensionPEstaEnValoresNormales && tensionPEstaEnValoresAlarmaLocal){
Serial.println("Tensión promedio entre "+ String(limiteInferiorAppTP)+ " y " + String(limiteSuperiorAppTP) + " alarma local encendida");
Serial.println(tensionPromedio, 2);
digitalWrite(ledAmarillo, LOW);
digitalWrite(ledVioleta, HIGH);
}
if(tensionPEstaEnValoresMaximosApp){
Serial.println("Tensión promedio superior a la máxima permitida alarma local encendida y se informa a la APP.");
Serial.println(tensionPromedio, 2);
digitalWrite(ledAmarillo, LOW);
digitalWrite(ledVioleta, HIGH);
}
if(tensionPEstaEnValoresMinimosApp){
Serial.println("Tensión promedio inferior a la mínima permitida alarma local encendida y se informa a la APP.");
Serial.println(tensionPromedio, 2);
digitalWrite(ledAmarillo, LOW);
digitalWrite(ledVioleta, HIGH);
}
contadorApagadoLedAmarillo++;
if(contadorApagadoLedAmarillo == 3){
contadorApagadoLedAmarillo = 0;
mantenerLedAmarilloApagado = false;
}
}
}
//PULSADOR tensión instantánea
int estadoActualBotonTI = digitalRead((buttonPinTI));
if (estadoBotonTI != estadoActualBotonTI) {
estadoBotonTI = estadoActualBotonTI;
if (estadoActualBotonTI == LOW) {
digitalWrite(ledVerde, LOW);
mantenerLedVerdeApagado = true;
}
}
//PULSADOR tensión promedio
int estadoActualBotonTP = digitalRead((buttonPinTP));
if (estadoBotonTP != estadoActualBotonTP) {
estadoBotonTP = estadoActualBotonTP;
if (estadoActualBotonTP == LOW) {
digitalWrite(ledAmarillo, LOW);
mantenerLedAmarilloApagado = true;
}
}
sevseg.refreshDisplay();
}