Vamos a ver si consigo escribir todo esto según las normas del foro ya que es mi primera pregunta con código, diagrama y demás en el foro.
Primero os cuento lo que quiero hacer y luego os pongo el diagrama y el código.
Esto es parte de un proyecto más grande, que estoy rehaciendo bien poco a poco. Por eso en el diagrama veréis algún elemento más que se inicializa en el código, pero no se usa de momento. He preferido dejarlo por si estuviera afectando a lo que no termina de funcionar...
Bien, esto es va a ser una especie de cerradura con clave. La parte que estoy desarrollando ahora es en la que el sistema esta dormido, hasta que se acerca alguien. En ese momento el sensor PIR lo detecta y enciende, para que se pueda operar.
Es un arduino MEGA 2560, pero no el original, una compatible.
El problema es que actualmente el funcionamiento es así:
- Arranca
- Cuando no detecta a nadie se apaga
- Si no ha pasado mucho tiempo y detecta algo el sensor PIR despierta (si ha pasado mucho tiempo ya no despierta)
- Cuando vuelve a no detectar nada se vuelve a dormir
- Ya no despierta nunca más
Aquí tenéis mi código:
// Para el manejo de la pantalla
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
//Para el manerjo del teclado
#include <Keypad.h>
//Para dormir
#include <avr/sleep.h>
//CONFIGURACION TECLADO
//determinamos numero de filas y columnas del teclado matricial, es este caso 4x3
const byte filas = 4; //numero de filas
const byte columnas = 3; //numero de columnas
//dos vectores donde colocaremos los pines de arduino asociados al teclado matricial:
byte pinsFilas[filas] = {24, 34, 32, 28}; //pines donde van conectadas las filas
byte pinsColumnas[columnas] = {26, 22, 30}; //pines donde van conectadas las columnas
//establecemos la matriz que nos dara cada uno de los valores del teclado matricial
char teclas[filas][columnas] = {
{'1', '2', '3'},
{'4', '5', '6'},
{'7', '8', '9'},
{'*', '0', '#'}
};
//FIN _CONFIGURACION TECLADO
//OBJETOS
//Creamos el objeto teclado
Keypad teclado = Keypad(makeKeymap(teclas), pinsFilas, pinsColumnas, filas, columnas);
//Crear el objeto lcd dirección 0x27 y 20 columnas x 4 filas
LiquidCrystal_I2C lcd(0x27, 20, 4);
//FIN OBJETOS
//SENSORES
//Sensor de Ultrasonidos
const int EchoPin = 40;
const int TriggerPin = 38;
const int hueco = 4;
//Sensor PIR
const int pinPIR = 19; //INT.2 en Pin 19 para Arduino MEGA
//FIN SENSORES
///////////////////////////////////////////////////////////////////////////
// FUNCION: setup //
// Inicialización de la placa //
///////////////////////////////////////////////////////////////////////////
void setup() {
Serial.begin(9600);
Serial.print("\r\n");
Serial.println ("setup");
//Inicializa sensor ultra sonidos
pinMode(TriggerPin, OUTPUT);
pinMode(EchoPin, INPUT);
//Inicializa sensor PIR
pinMode(pinPIR, INPUT_PULLUP);
// Inicializa la pantalla
lcd.backlight(); // Encender la luz de fondo.
lcd.init(); // Inicializar el LCD
lcd.clear(); // Limpiar la pantalla
//FIN Inicializa la pantalla
} // FIN FUNCION setup()
///////////////////////////////////////////////////////////////////////////
// FUNCION: loop //
// Bucle principal //
///////////////////////////////////////////////////////////////////////////
void loop() {
Serial.println ("loop"); //Quitar
lcd.clear();
Serial.println ("leemos PIR");
int presencia = digitalRead(pinPIR); //leemos sensor PIR
if (presencia == HIGH){ //Si hay alguien delante
Serial.println ("loop-Hay alguien"); //Quitar
lcd.clear();
lcd.setCursor(0,0);
lcd.print("HOLA MUNDO!");
delay(1000);
}
else{ //Si NO hay alguien delante
Serial.println ("loop-NO hay alguien"); //Quitar
lcd.clear();
lcd.setCursor(0,0);
lcd.print("ADIOS");
delay (1000);
aDormir();
}
} // FIN FUNCION loop()
///////////////////////////////////////////////////////////////////////////
// FUNCION: aDormir //
// Se encarga de preparar y poner al sistema en modo ahorro energia. //
// Tambien del despertar //
///////////////////////////////////////////////////////////////////////////
void aDormir(){
Serial.println ("aDormir");
sleep_enable(); // activamos el modo dormir
attachInterrupt(digitalPinToInterrupt(pinPIR), aDespertar, HIGH); // Añadimos una interrupción para despertar del modo Sleep. En este caso asociada al sensor de movimiento PIR y cuando este de señal de presencia (HIGH)
set_sleep_mode (SLEEP_MODE_PWR_DOWN); // Elegimos el modo de "dormir" en este caso PWR_DOWN
delay (1000);
lcd.noBacklight(); // Apagamos la luz de la pantalla
lcd.off(); // Apagamos la pantalla
sleep_cpu(); // "Dormimos" la placa
//aqui continua cuando vuelve
sleep_disable(); // Desactivamos el modo dormir
lcd.on(); // Encendemos la pantalla
lcd.backlight(); // Encendemos la luz de la pantalla
}
///////////////////////////////////////////////////////////////////////////
// FUNCION: aDespertar //
// Es llamada con una interrupción para despertar a la placa //
// //
///////////////////////////////////////////////////////////////////////////
void aDespertar(){
Serial.println ("aDespertar");
detachInterrupt(digitalPinToInterrupt(pinPIR)); // Quitamos la interrupción
}
He hecho mediciones en el sensor PIR, para ver si el problema es que se apagaba todo o que el sensor no estaba bien, pero devuelve sus 3 y pico voltios cuando detecta movimiento y 0.19 cuando no, devolviendo estos valores incluso cuando ya no despierta.
He leido y releido documentación y posts, y llegado hasta es código, pero no encuentro donde puedo estar fallando. Seguramente se me haya pasado alguna cosa por alto, pero no termino de dar con que es. Y es una pena, porque creo que un esqueleto así es una buena base para muchos proyectos...
Acepto humildemente cualquier comentario, referencia a articulos y lo que sea. Mil gracias por adelantado.