Contador del pulsos a binario

¡NECESITO DE SU AYUDA!. con arduino LEONARDO estoy intentado hacer un sumador de pulsos de un botón y que la suma me lo dé en binario con LED´S. Tengo un problema en el software y es que, no me almacena el valor de contador++ al parecer porque no hace nada. Es la primera vez que uso matrices.

int LEDP[] = {2, 3, 4, 5, 6, 7, 8, 9};
int num2;
int contador = 0;
int botton1y2 = 10;
void setup() {
  for (int i = 0; i < 8; i++) {
    pinMode(LEDP[i], OUTPUT);
  }
  pinMode(botton1y2, INPUT);
}
void loop() {
  //----------------------------Empieza con los leds apagados
  for (int i = 0; i < 8; i++) {
    digitalWrite(LEDP[i], LOW);
  }
  //-----------------------------SUMA las pulsaciones 
  if (digitalRead(botton1y2)==HIGH){   //espera hasta el LED encienta
    while(digitalRead(botton1y2)==HIGH){  //mientas el botón siga pulsado
      delay(10);
    }
     if(digitalRead(botton1y2)==LOW){  //Hasta que el LED se apague
      contador++;
      delay (10);
 //-------------------------------- CONVIERTE la pulsacion a Binario
        if (contador >= 0 && contador <= 255){
          num2 = contador;
            for (int i = 0; i < 8; i++) {
              if (num2 % 2 == 1) {
                digitalWrite(LEDP[i], HIGH);
              }
              else {
               digitalWrite(LEDP[i], LOW);
              }
              num2 = num2 / 2;
              }
            delay(10);  
        }
      }
  }
delay(10);
}

Amigo, tienes varios errores, tratare de explicartelos:

El primero es que veo que no has comprendido como trabaja el void loop(), ¿el porque digo esto?
Pones esto:

//----------------------------Empieza con los leds apagados
  for (int i = 0; i < 8; i++) {
    digitalWrite(LEDP[i], LOW);

Te debe quedar claro que el loop se repite infinitamente, muchísimas veces por segundo(siempre y cuando no uses delay),
por lo que cada ciclo del loop apagas todos los led

Ahora:

 if (digitalRead(botton1y2)==HIGH){   //espera hasta el LED encienta
    while(digitalRead(botton1y2)==HIGH){  //mientas el botón siga pulsado
      delay(10);
    }

esto es redundante y es un gran error, por eso muy seguido contesto que los while los debes usar con mucho cuidado, si lees bien la segunda linea dice, mientras el boton esté en alto, ejecuta un delay de 10 milisegundos por lo que todo el tiempo que esté pulsado el boton el arduino solo estará en pausa

vamos a la linea que sigue:

if(digitalRead(botton1y2)==LOW){  //Hasta que el LED se apague
      contador++;
      delay (10);

Como te dije antes el void loop() se ejecuta muchas veces por segundo, por lo que mientras el boton esté liberado, el contador subirá tan rápidamente que en un abrir y cerrar de ojos la variable contador tendra un valor de mas de 100

Aparte de todo ésto, debes tener en cuenta que los botones rebotan, por lo que ahi tienes un problema mas a resolver.
En conclusión,tienes que quitar las primeras lineas que apagan los led. Para el contador tienes que detectar el cambio de flanco del boton para evitar que el contador se dispare. Y debes de dejar de usar while.
Te recomiendo antes de seguir te pases a la sección de documentacion aqui encontraras buenos tutoriales y videos, busca algunos que hablan sobre el uso de pulsadores y como evitar los rebotes.
Cuando tengas dominado el uso del pulsador, puedes pasar a la siguiente parte que es mostrar en los led el numero en binario

Muchas gracias RIG, encontré algunos errores que no noté y es por eso que modifiqué así mi código.

int LEDP[] = {2, 3, 4, 5, 6, 7, 8, 9};    //mis pines a ocuparán serán del 2 al 9
int num2;                               
int contador = 0;                                //Una curiosidad, si puse esto... estoy inicializando contador con valor inicial 0 o en el pin 0??.
int botton1y2 = 10;
void setup() {
  for (int i = 0; i < 8; i++) {
    pinMode(LEDP[i], OUTPUT);
  }
  pinMode(botton1y2, INPUT);
}
void loop() {
//-----------------------------SUMA las pulsaciones 
  if (digitalRead(botton1y2)==HIGH){   //Solo entra hasta que el botón se pulse. Si no se pulsa quedará sin hacer nada hasta que se pulse
     while(digitalRead(botton1y2)==HIGH){  //Su función es dejar en pausa hasta que se suelte el botón
     delay(10); 
     }                         
     if(digitalRead(botton1y2)==LOW){  //Solo entra hasta que el botón se suelte 
      contador++;                      //se incrementa el valor del contador
 //-------------------------------- CONVIERTE el valor de (contador) a Binario
        if (contador >= 0 && contador <= 255){ //primero debe de estar en el rango de 0 a 255 (1 byte) ya que son 8 leds (bits)
          num2 = contador;                     //se le pasa de la variable contador (numero de veces pulsados) a la variable "num2"
            for (int i = 0; i < 8; i++) {      //ciclo for desde valor i=0 (LEDP[0]= pin 2) al valor i=7 (LEDP[7]= pin 9) ENCIENDE O APAGA LOS LED´S
              if (num2 % 2 == 1) {             //si se cumple... 
                digitalWrite(LEDP[i], HIGH);   //enciente el LEDP[i]
              }
              else {
               digitalWrite(LEDP[i], LOW);     //de lo contrario se apaga
              }
              num2 = num2 / 2;                 //y se divide por 2 hasta que i=8 
              }
            delay(100);  
        }
      }
  }
delay(100);
}

le quité lo de apagar los leds en un principio también le quité el delay del contador++ ya que al parecer tienes mucha razón con lo de que sumaría y sumaría por 10 mili-segundos, pero en lo de While yo creo que no hay problema si lo dejo, ya que su función es esa, pausar el programa hasta que se suelte el botón aunque también pude ver programas que no lo necesitaban, no se si pase algo, según creo yo que no hay diferencia.

Sharys:
le quité lo de apagar los leds en un principio también le quité el delay del contador++ ya que al parecer tienes mucha razón con lo de que sumaría y sumaría por 10 mili-segundos, pero en lo de While yo creo que no hay problema si lo dejo, ya que su función es esa, pausar el programa hasta que se suelte el botón aunque también pude ver programas que no lo necesitaban, no se si pase algo, según creo yo que no hay diferencia.

Vas muy bien Sharys animo.

int contador = 0;                         //Una curiosidad, si puse esto... estoy inicializando contador con valor inicial 0 o en el pin 0??.

No es el pin a no ser que uses la variable con pinMode(). Te recomiendo cambiar esta variable a tipo byte asi no tienes que comprobar ya que de hecho sus valores estarán entre 0-255.

Me gusta como te las ingeniaste para extraer los bits de la variable contador pero es mucho mas sencillo si usas la función bitRead() en combinación con tu matriz LEDP[]. Estudia un poquito esta función y estoy seguro que reduces tu nuevo código.

Como te dice RIG seria bueno que sepas sobre el problema de "rebote" en los pulsadores, solo por cocimiento futuro pero te cuento que quizás sin saber con este código solucionas dicho problema:

while(digitalRead(botton1y2) == HIGH){  //Su función es dejar en pausa hasta que se suelte el botón
   delay(10); 
}

Por ultimo yo le quitaría los 2:

delay(100);

No tiene ningún sentido.

Enhorabuena por tu implementación de la conversión a binario. Seguramente tu experiencia en C es escasa y por eso tiene mucho mérito lo que has hecho. Yo vengo a hacerte partícipe de mis conocimientos en C a nivel de tratamiento de bits y cómo haría yo la conversión a binario.

Un inciso: no hace falta “limitar” los valores de la variable contador ya que cuando el valor pase de 255 a 256 los ocho bits menos significativos pasan a valer cero y “vuelta a empezar” por sí solo. Cierto es que si la declaras de tipo byte te ahorras un byte. Pero eso no es crítico. Así que, independientemente de si contador es de tipo integer o de tipo byte, no hace falta el if siguiente:

        if (contador >= 0 && contador <= 255){ //primero debe de estar en el rango de 0 a 255 (1 byte) ya que son 8 leds (bits)

En las llamada a la función digitalWrite en lugar poner LOW podemos poner un cero y en lugar de HIGH podemos poner un valor distinto de cero (1, 2, 234 o cualquier otro valor que no sea cero). Así que en lugar de ver si num2 % 1 es un 1 para usar el valor HIGH y si es un 0 usar el LOW podemos usar directamente el resultado de la operación y sustituir las líneas:

              if (num2 % 2 == 1) {             //si se cumple...
                digitalWrite(LEDP[i], HIGH);   //enciente el LEDP[i]
              }
              else {
               digitalWrite(LEDP[i], LOW);     //de lo contrario se apaga
              }

… por la única línea de código:

              digitalWrite(LEDP[i], num2 % 2);   //enciente o apaga el LEDP[i]

Al igual que ponemos contador++ en lugar de poner contador = contador + 1 también podemos poner num2 /= 2 en lugar de num2 = num2 / 2. La línea:

              num2 = num2 / 2;                 //y se divide por 2 hasta que i=8

… puede ponerse así:

              num2 /= 2;                       //y se divide por 2 hasta que i=8

Dividir por dos y “desplazar a la derecha” una vez los bits de un entero produce el mismo efecto, así que en lugar de num2 /= 2 (num2 = num2 / 2) podemos usar el operador >> (desplazar a la derecha). Por lo que podemos sustituir la instrucción anterior por num2 >>= 1 (num2 = num2 >> 1). Quedando la línea:

              num2 >>= 1;                       //y se desplazan una vez los bit a la derecha hasta que i=8

Usando otro operador de bits también podemos sustituir la operación num2 % 2. En su lugar podemos realizar la operación a nivel de bits num2 & 1.

Si “juntamos” todo lo dicho hasta ahora la conversión nos queda así:

 //-------------------------------- CONVIERTE el valor de (contador) a Binario
        num2 = contador;                     //se le pasa de la variable contador (numero de veces pulsados) a la variable "num2"
        for (int i = 0; i < 8; i++) {      //ciclo for desde valor i=0 (LEDP[0]= pin 2) al valor i=7 (LEDP[7]= pin 9) ENCIENDE O APAGA LOS LED´S
          digitalWrite(LEDP[i], num2 & 1); //enciente o apaga el LEDP[i]
          num2 >>= 1;                      //y se desplazan una vez los bit a la derecha hasta que i=8
          delay(100);
        }

Otro detalle: al igual que definimos e inicializamos a cero la variable i al principio del for para luego modificar e incrementar al final del for, podemos hacer algo semejante con la variable num2 en el mismo for aprovechando, entre otras cosas, que son del mismo tipo. Podemos definir y modificar la variable num2 separando por comas:

 //-------------------------------- CONVIERTE el valor de (contador) a Binario
        for (int i = 0, num2 = contador; i < 8; i++, num2 >>= 1) {      //ciclo for desde valor i=0 (LEDP[0]= pin 2) al valor i=7 (LEDP[7]= pin 9) ENCIENDE O APAGA LOS LED´S
          digitalWrite(LEDP[i], num2 & 1); //enciente o apaga el LEDP[i]
          delay(100);
        }

Se han quitado las líneas de la operación num2 >>= 1 y la de la asignación num2 = contador para “ponerlas” en el for. Otra línea que ya no hace falta es la de la definición int num2; al principio del programa ya que la variable se está definiendo en el for.

El programa, con todas las modificaciones, quedaría así:

int LEDP[] = {2, 3, 4, 5, 6, 7, 8, 9};    //mis pines a ocuparán serán del 2 al 9
int contador = 0;                                //Una curiosidad, si puse esto... estoy inicializando contador con valor inicial 0 o en el pin 0??.
int botton1y2 = 10;
void setup() {
  for (int i = 0; i < 8; i++) {
    pinMode(LEDP[i], OUTPUT);
  }
  pinMode(botton1y2, INPUT);
}
void loop() {
//-----------------------------SUMA las pulsaciones
  if (digitalRead(botton1y2)==HIGH) {   //Solo entra hasta que el botón se pulse. Si no se pulsa quedará sin hacer nada hasta que se pulse
    while (digitalRead(botton1y2)==HIGH) {  //Su función es dejar en pausa hasta que se suelte el botón
      delay(10);
    }                         
    if (digitalRead(botton1y2)==LOW) {  //Solo entra hasta que el botón se suelte
      contador++;                     //se incrementa el valor del contador
      // CONVIERTE el valor de (contador) a Binario
      for (int i = 0, num2 = contador; i < 8; i++, num2 >>= 1) {
        digitalWrite(LEDP[i], num2 & 1); //enciente o apaga el LEDP[i]
      }
    }
  }
  delay(100);
}

Si buscas códigos que traten con bits, verás que se parecen bastante al código que te he puesto. Sé que de entrada se ve muy ofuscado y confuso, pero cuanto antes empieces a trabajar con los operadores de bits antes te “acostumbrarás” a ellos.

Muchas garcias, Kike_GL y IgnoranteAbsoluto que de ignorante no se le nota nada. Pues eh estado viendo sus correcciones tambien investigando lo que dicen y despues de analizar y leer, mi código ah quedado así.

int LEDP[] = {2, 3, 4, 5, 6, 7, 8, 9};
byte botton1y2 = 10;
int tiempoAntirrebote = 10; //Una centecima de segundo para asegurarnos de que se estabilice la señal
int contador = 0;
int estadoBoton;
int estadoBotonAnterior; 
void setup() {
  for (int i = 0; i < 8; i++) {
    pinMode(LEDP[i], OUTPUT);
  }
  pinMode(botton1y2, INPUT);
}
void loop() {
  estadoBoton = digitalRead(botton1y2);  
  if(estadoBoton != estadoBotonAnterior){
    if(antirebote(botton1y2)){
      contador++;
      binario(contador); 
    }
  } estadoBotonAnterior = estadoBoton;
}  
void binario(int x){           //función binario
    for (int i = 0; i < 8; i++){
    digitalWrite(LEDP[i], bitRead(x,i));
    if (bitRead(x,i) == 1){
     digitalWrite(LEDP[i], HIGH); 
    }else{
     digitalWrite(LEDP[i], LOW); 
    }
    }
}
boolean antirebote (int pin){
  int tiempo = 0;
  int estado; 
  int estadoAnterior;

  do{
    estado = digitalRead(pin);
    if(estado != estadoAnterior){
      tiempo = 0;
      estadoAnterior = estado;
    }else{
      tiempo++; 
    }
  }while(tiempo < tiempoAntirrebote);
  return estado; 
}

Como ya se habrán dado cuenta le puse una función para el Debounce que me encontré por ahí tambien modifique el de bitRead() con el Array, que son temás que recien descrubrí y es por eso que me eh encontrado muchas fallas. Y nuevamente gracias gnoranteAbsoluto por dedicarle un tiempo y usaré los consejos para que con el tiempo mis códigos se vean muy profesionales y cortos.
Que les parece, por el momento no le encuentro fallas a mi lógica pero soy inexperto.

Al poner:

    digitalWrite(LEDP[i], bitRead(x,i));

... ya no hace falta que pongas:

    if (bitRead(x,i) == 1){
     digitalWrite(LEDP[i], HIGH); 
    }else{
     digitalWrite(LEDP[i], LOW); 
    }

Todo ese código lo puedes quitar. Creo que "se te ha quedado" sin querer.