// ---------------------------------------------------------
// PANTALLA ST7735 + ENCODER
// PROGRAMA PARA CONTROLAR LA REFRIGERACIÓN DE UNA LATA DE REFESCO
// ---------------------------------------------------------
//--------------------------------------------------------------
//PANTALLA DE TFT LIBRERIAS
#include <Adafruit_GFX.h>
#include <Adafruit_ST7735.h>
#include <SPI.h>
// Pines del Arduino Nano
#define TFT_CS 10
#define TFT_DC 8
#define TFT_RST 9
Adafruit_ST7735 tft = Adafruit_ST7735(TFT_CS, TFT_DC, TFT_RST);
// Variables de temperatura (luego se reemplazan por valores reales)
float temp1 = 23.5;
float temp2 = 27.8;
int tempcons = 0;
// Valores anteriores para evitar parpadeo
float lastTemp1 = -999;
float lastTemp2 = -999;
int lastTempCons = -999;
//Para evitar el parpadeo lo que hacemos que solo vamos a modificar la linea
//donde está el valor a modificar. Si hay una variación del valor almacenado
//en una variable antigua y lo comparamos con una variable actual, son distintos entonces variamos el valor en la pantalla.
// la variable actual se define con temp1 y la antigua lasttemp1. Esto lo hago
//para cada variable que se modificará en la pantalla.
//-----------------------------------------------------------
// ENCODE
//__________________________________________________________
//Son los pines de ardunio que voy a utilizar.
#define PIN_A 2
#define PIN_B 3
#define PIN_PUSH 4
//Variables necesarias para el ENCODE.
volatile int contador = 0;
volatile int lastEncoded = 0;
int Bpulsado = 10;
int BpulsadoOld = -999;
void updateEncoder() {
int MSB = digitalRead(PIN_A); // Most significant bit
int LSB = digitalRead(PIN_B); // Least significant bit
int encoded = (MSB << 1) | LSB;
int sum = (lastEncoded << 2) | encoded;
if (sum == 0b1101 || sum == 0b0100 || sum == 0b0010 || sum == 0b1011) contador++;
if (sum == 0b1110 || sum == 0b0111 || sum == 0b0001 || sum == 0b1000) contador--;
lastEncoded = encoded;
}
//---------------------------------------------------------------
// SONDA DE TEMPERATURA DS18B20
//---------------------------------------------------------------
/*¿Qué hace la librería OneWire?
El DS18B20 usa un protocolo llamado 1‑Wire, donde solo un cable de datos
sirve para comunicarse con el sensor.
La librería OneWire:
Implementa el protocolo 1‑Wire a nivel bajo.
Permite enviar y recibir bits y bytes por el pin de datos.
Gestiona la búsqueda de dispositivos conectados al bus.
Permite identificar cada sensor por su dirección única de 64 bits.
No interpreta temperaturas ni comandos del DS18B20; solo maneja la comunicación.
Piensa en OneWire como el “cableado digital” que permite hablar con el sensor.
¿Qué hace la librería DallasTemperature?
Esta librería está construida encima de OneWire y se encarga de:
Entender los comandos específicos del DS18B20.
Pedir al sensor que mida la temperatura.
Leer la temperatura en °C o °F.
Gestionar varios sensores en el mismo bus.
Simplificar muchísimo el código.
DallasTemperature es el “traductor” que entiende el lenguaje del DS18B20
y te da directamente la temperatura.
*/
#include <OneWire.h>
#include <DallasTemperature.h>
// Pines de cada sonda
#define PIN_SONDA_1 5
#define PIN_SONDA_2 6
// Crear un bus OneWire por cada pin
OneWire oneWire1(PIN_SONDA_1);
OneWire oneWire2(PIN_SONDA_2);
// Crear un objeto DallasTemperature por cada bus
DallasTemperature sensor1(&oneWire1);
DallasTemperature sensor2(&oneWire2);
//---------------------------------------------------------------
//CONFIGURACIÓN INICIAL
//---------------------------------------------------------------
void setup() {
// Inicializar pantalla
tft.initR(INITR_BLACKTAB);
tft.setRotation(1);
tft.fillScreen(ST77XX_BLACK);
tft.setTextSize(2);
// Dibujar textos fijos (solo una vez)
tft.setCursor(5, 5);
tft.setTextColor(ST77XX_YELLOW);
tft.print("TORRE TAJO");
tft.setCursor(5, 25);
tft.setTextColor(ST77XX_RED);
tft.print("T1:");
tft.setCursor(5, 50);
tft.setTextColor(ST77XX_BLUE);
tft.print("T2:");
tft.setCursor(5, 75);
tft.setTextColor(ST77XX_GREEN);
tft.print("TEMP REF");
tft.setCursor(5, 100);
tft.setTextColor(ST77XX_GREEN);
tft.print("T ref:");
// Encoder, Defino los pines del encode como entradas.
pinMode(PIN_A, INPUT_PULLUP);
pinMode(PIN_B, INPUT_PULLUP);
pinMode(PIN_PUSH, INPUT_PULLUP);
attachInterrupt(digitalPinToInterrupt(PIN_A), updateEncoder, CHANGE);
attachInterrupt(digitalPinToInterrupt(PIN_B), updateEncoder, CHANGE);
//SENSOR DE TEMPERARURA
//Abro el puerto Serial de comunicación.
Serial.begin(9600);
sensor1.begin();
sensor2.begin();
Serial.print("Sensores en bus 1: ");
Serial.println(sensor1.getDeviceCount());
Serial.print("Sensores en bus 2: ");
Serial.println(sensor2.getDeviceCount());
//poner los datos del sensor en la pantalla
sensor1.requestTemperatures();
sensor2.requestTemperatures();
sensor1.setWaitForConversion(false);
sensor2.setWaitForConversion(false);
temp1 = sensor1.getTempCByIndex(0);
temp2 = sensor2.getTempCByIndex(0);
}
//---------------------------------------------------------------------------------
//BUCLE INFINITO
//--------------------------------------------------------------------------------------
void loop() {
// -----------------------------
// LECTURA DEL ENCODER
// -----------------------------
int tempcons = contador / 4;
//----------------------------------------
// Botón del encoder
//------------------------------------
if (digitalRead(PIN_PUSH) == LOW) {
Bpulsado = tempcons;
Serial.println("Botón pulsado");
delay(200);
}
//--------------------------------------------------------
//LECTURA DE LOS SENSORES DE TEMPERARURA
//--------------------------------------------------------
sensor1.requestTemperatures();
sensor2.requestTemperatures();
// NO bloquea, devuelve la última conversión disponible
temp1 = sensor1.getTempCByIndex(0);
temp2 = sensor2.getTempCByIndex(0);
// -----------------------------
// ACTUALIZACIÓN DE PANTALLA SIN PARPADEO solo acturaliza si hay un cambio en un valor
// -----------------------------
// Actualizar T1
if (temp1 != lastTemp1) { //mira si hay una variación en la temperatura.
//Borramos solo el texto con el color del fondo
tft.setCursor(60, 25);
tft.setTextColor(ST77XX_BLACK);
tft.print(lastTemp1);
//Escribimos el nuevo texto
tft.setCursor(60, 25);
tft.setTextColor(ST77XX_RED);
tft.print(temp1);
lastTemp1 = temp1;
}
// Actualizar T2
if (temp2 != lastTemp2) {
//Borramos solo el texto con el color del fondo
tft.setCursor(60, 50);
tft.setTextColor(ST77XX_BLACK);
tft.print(lastTemp2);
//Escribimos el nuevo texto
tft.setCursor(60, 50);
tft.setTextColor(ST77XX_BLUE);
tft.print(temp2);
lastTemp2 = temp2;
}
// Actualizar temperatura de refencia seleconada
if (Bpulsado != BpulsadoOld) {
//Borramos solo el texto con el color del fondo
tft.setCursor(110, 75);
tft.setTextColor(ST77XX_BLACK);
tft.print(BpulsadoOld);
//Escribimos el nuevo texto
tft.setCursor(110, 75);
tft.setTextColor(ST77XX_GREEN);
tft.print(Bpulsado);
BpulsadoOld = Bpulsado;
}
// Actualizar T ref (encoder)
if (tempcons != lastTempCons) {
//Borramos solo el texto con el color del fondo
tft.setCursor(100, 100);
tft.setTextColor(ST77XX_BLACK);
tft.print(lastTempCons);
//Escribimos el nuevo texto
tft.setCursor(100, 100);
tft.setTextColor(ST77XX_GREEN);
tft.print(tempcons);
lastTempCons = tempcons;
}
Serial.print("T1 = ");
Serial.print(temp1);
Serial.print(" | T2 = ");
Serial.println(temp2);
}
No hay comentarios:
Publicar un comentario