lunes, 16 de diciembre de 2019

Los pulsadores (II)

En esta entrada vamos a realizar dos programas cuya lógica es más complicada de lo que en un principio podría parecer. En el primero de ellos se trata de encender y apagar un LED con un único pulsador, de manera que, si está apagado, al pulsar se encienda y, si está encendido, al pulsar se apague.

/* 
 * encendidoApagadoPulsandoA.ino
 * Encendido-Apagado del primer led de la segunda fila
 * con el pulsador A. Si está apagado, al pulsar se
 * enciende; si está encendido, al pulsar se apaga.
*/

boolean pulsadorA;
/*
 * hasLevantado: variable que nos indicará si hemos
 * quitado el dedo del pulsador, para evitar que mientras
 * mantenemos presionado el programa lo detecte como 
 * nuevas pulsaciones.
 */
boolean hasLevantado=true;
/*
 * estaApagado: para guardar el estado del LED, encendido
 * (false) o apagado (true).
 */
boolean estaApagado=true; //

void setup() {
  pinMode(28,OUTPUT);    //Programamos los pines
  pinMode(23,OUTPUT);    //como salidas.
  pinMode(5, INPUT);     //pin pulsador como entrada
  digitalWrite(28,HIGH); //Activamos la fila.
  digitalWrite(23,HIGH); //apagamos LED 
}

void loop() {
  pulsadorA=digitalRead(5);
  /*
   * si pulsado y has levantado previamente y está 
   * apagado, entonces lo enciendo.
   */
  if (pulsadorA==0 && hasLevantado && estaApagado) {
    digitalWrite(23,LOW);
    hasLevantado=false;   //ahora lo tenemos presionado.
    estaApagado=false;    //el LED está encendido.
  }
  /*
   * si pulsado y has levantado previamente y no (!) está
   * apagado, entonces lo apago.
   */
  if (pulsadorA==0 && hasLevantado && !estaApagado) {
    digitalWrite(23,HIGH);
    hasLevantado=false;
    estaApagado=true;     //ahora el LED está apagado
  }
  /*
   * si pulsador levantado hago hasLevantado cierto (true)
   */
  if (pulsadorA==1){
    hasLevantado=true;
  }
  delay(30);             //evita los rebotes del pulsador
}
En el segundo programa se trata de encender uno a uno los 5 LEDs de la segunda fila conforme vamos accionando el pulsador A.

/*
 *encendidoProgresivoFila2Pulsador.ino
 *Los led de la fila 2 se van encendiendo
 *de uno en uno cada vez que accionamos
 *el pulsador A.
*/

boolean pulsadorA;
boolean hasLevantado;
/*
 * n: variable de tipo byte (número entero
 * entre 0 y 255), para contar las pulsaciones
 * realizadas
 */
byte n=0;

void setup() {
  pinMode(28,OUTPUT);
  pinMode(7,OUTPUT);
  pinMode(9,OUTPUT);
  pinMode(23,OUTPUT);
  pinMode(24,OUTPUT);
  pinMode(25,OUTPUT);
  pinMode(5,INPUT);
  digitalWrite(28,HIGH); //activamos la fila.
  digitalWrite(25,HIGH); //desactivamos las columnas
  digitalWrite(24,HIGH); //para apagar los LEDs
  digitalWrite(23,HIGH);
  digitalWrite(9,HIGH);
  digitalWrite(7,HIGH);
}

void loop() {
  pulsadorA=digitalRead(5);
  /*
   * si pulsador A accionado y lo has levantado
   * previamente, entonces incrementamos n
   */
  if(pulsadorA==0 && hasLevantado){               
    n++;        //incrementamos n (también n=n+1;)
    if(n==6){
      n=0;      //para volver a iniciar el ciclo
    }  
    hasLevantado=false; 
  }
  /*
   * si levantamos el pulsador 
   * le damos el valor true a la variable.
   */
  if(pulsadorA==1){
    hasLevantado=true;
  }
  /*
   * Ahora vamos encendiendo los LEDs según
   * el valor de n.
   */
  if(n==0){
    digitalWrite(23,HIGH); //apagamos todos los LEDs 
    digitalWrite(24,HIGH);
    digitalWrite(25,HIGH);
    digitalWrite(9,HIGH);
    digitalWrite(7,HIGH);
  }
  if(n==1){
    digitalWrite(23,LOW);  //encendemos el primer LED
  }
  if(n==2){
    digitalWrite(24,LOW);  //encendemos el segundo LED
  }
  if(n==3){
    digitalWrite(25,LOW);  //encendemos el tercer LED
  }
  if(n==4){
    digitalWrite(9,LOW);   //encendemos el cuarto LED
  }
  if(n==5){
    digitalWrite(7,LOW);   //encendemos el quinto LED
  }
  delay(30);               //evita los rebotes del pulsador
}
Vamos a tratar de simplificar la escritura del programa anterior. Para ello, en primer lugar, vamos a utilizar un "array" (matriz); se trata de un conjunto de variables agrupadas bajo un mismo nombre y podemos seleccionar mediante un índice. Crearemos un array con los números de los pines de las columnas internas de los LEDs y luego lo usaremos para simplificar la parte final del programa:
/*
 *encendidoProgresivoFila2Pulsador.ino
 *Los led de la fila 2 se van encendiendo
 *de uno en uno cada vez que accionamos
 *el pulsador A.
 */

boolean pulsadorA;
boolean hasLevantado;
byte n=0;
byte pinesCol[5]={23,24,25,9,7};
/*
 *Hemos creado un array de 5 elementos de tipo byte.
 *A cada uno de ellos podemos acceder mediante un índice:
 *pinesCol[0] sería 23, pinesCol[1] sería 24,... pinesCol[4] sería 7.
 */

void setup() {
  pinMode(28,OUTPUT);
  pinMode(7,OUTPUT);
  pinMode(9,OUTPUT);
  pinMode(23,OUTPUT);
  pinMode(24,OUTPUT);
  pinMode(25,OUTPUT);
  pinMode(5,INPUT);
  digitalWrite(28,HIGH); //activamos la fila.
  digitalWrite(25,HIGH); //desactivamos las columnas
  digitalWrite(24,HIGH); //para apagar los LEDs
  digitalWrite(23,HIGH);
  digitalWrite(9,HIGH);
  digitalWrite(7,HIGH);
}

void loop() {
  pulsadorA=digitalRead(5);
  
  if(pulsadorA==0 && hasLevantado){               
    n++;
    if(n==6) n=0; 
    hasLevantado=false; 
  }
  
  if(pulsadorA==1){
    hasLevantado=true;
  }
  
  if(n==0){
    digitalWrite(23,HIGH); //apagamos todos los LEDs 
    digitalWrite(24,HIGH);
    digitalWrite(25,HIGH);
    digitalWrite(9,HIGH);
    digitalWrite(7,HIGH);
  }
/*
 *Ahora utilizamos pinesCol para ir encendiendo los LEDs
 *dependiendo del valor que tenga n. 
 *Por ejemplo: si n=1 digitalWrite (pinesCol[n-1], LOW)
 *                    digitalWrite (pinesCol[0], LOW)
 *                    digitalWrite (23, LOW)
 *El íncide del array empieza en 0, por eso restamos 1 a n. 
 */
 if(n>0){
    digitalWrite(pinesCol[n-1],LOW);
   }
   delay(30);               //evita los rebotes del pulsador
}
La segunda simplificación consiste en utilizar el buble "for". Con él podemos repetir un determinado número de veces las instrucciones que deseemos:
/*
 *encendidoProgresivoFila2Pulsador.ino
 *Los led de la fila 2 se van encendiendo
 *de uno en uno cada vez que accionamos
 *el pulsador A.
*/

boolean pulsadorA;
boolean hasLevantado;
byte n=0;
byte pinesCol[5]={23,24,25,9,7};

void setup() {
  pinMode(28,OUTPUT);
  /*
   * Vamos a repetir 5 veces la instrucción pinMode
   * for(declaración variable; condición; incremento)
   * for(byte i=0;             i<5;       i++)
   * Mientras se cumpla la condición se vuelven a ejecutar
   * las instrucciones encerradas entre las llaves, con
   * la variable i incrementada en cada ciclo.
   * pinMode(pinesCol[0], OUTPUT)....pinMode(pinesCol[4],OUTPUT)
   */
  for(byte i=0; i<5; i++){
    pinMode(pinesCol[i],OUTPUT);
  }
  pinMode(5,INPUT);
  digitalWrite(28,HIGH);
  for(byte i=0; i<5; i++){
    digitalWrite(pinesCol[i],HIGH);
  }
}

void loop() {
  pulsadorA=digitalRead(5);

  if(pulsadorA==0 && hasLevantado){               
    n++;
    if(n==6) n=0;  
    hasLevantado=false; 
  }
  
  if(pulsadorA==1){
    hasLevantado=true;
  }
  
  if(n==0){
    for(byte i=0; i<5; i++){
      digitalWrite(pinesCol[i],HIGH);
    }
  if(n>0){
    digitalWrite(pinesCol[n-1],LOW);
  }
  delay(30);
}









No hay comentarios:

Publicar un comentario