problemas con codigo para n displays de 7 segmentos

Hola, mi nombre es Matias Haucke, soy nuevo en el foro y algo novato en el tema de programación, el motivo por el cual me dirijo al foro es el siguiente proyecto:

Investigando en Internet no encontré ninguna librería o código en el cual se demuestre como utilizar n displays desde un arduino, visto esto, me dispuse a ampliar un código que encontré para dos dígitos con displays de 7 segmentos.

Mi objetivo es mostrar a través de displays de 7 segmentos 5 pares de números, osea 5 números de dos dígitos , para luego hacer un contador con cada uno e incrementarlos y decrementarlos individualmente mediante unos botones.

Ocupo del pin 2 al 11 inclusive para los catodos, los pines 12,13 y A0 para el shift register y las IO analogicas para ingrasr los botones, dispuestos en un separador de voltaje,para obtener medidas distintas de cada uno en la entrada analogica.para esto utilizo los pines A2,A3,A4,A5 y A6

los botones serian tres, uno para aumentar , otro para disminuir y otro de reset, puestos con resistencias de distintos valores, a una entrada analogica.

Planeo usar un arduino nano, un shift register 74ls164 para los ánodos de los displays, y 10 displays de 7 segmentos de cátodo comun.(al ser un proyecto de prueba, lo he simulado todo en proteus, mediante la librería simulino).

Mi codigo es el siguiente

int dato = 13, reloj =12, limpiar = A0;
int number = 0;                         //variable del numero
int dnum=3;                            //numero de displays
int tmul=48;                             //tiempo de multiplexion
int hab[] = {11,10,9};             //pines que manejan los gnd, el primer elemento del array es la sifra mas significativa del numero
int num[10][8] ={
                  {1, 1, 1, 1, 0, 1, 1, 1},//cero
                  {0, 0, 0, 1, 0, 0, 0, 1},//uno
                  {0, 1, 1, 0, 1, 0, 1, 1},//dos
                  {0, 0, 1, 1, 1, 0, 1, 1},//tres
                  {0, 0, 0, 1, 1, 1, 0, 1},//cuatro
                  {0, 0, 1, 1, 1, 1, 1, 0},//cinco
                  {1, 1, 1, 1, 1, 1, 0, 0},//seis
                  {0, 0, 0, 1, 0, 0, 1, 1},//siete
                  {1, 1, 1, 1, 1, 1, 1, 1},//ocho
                  {0, 0, 0, 1, 1, 1, 1, 1}//nueve
                  };
                  
void setup() {
  // put your setup code here, to run once:
  for(int h = 2 ; h<=13 ; h++){
    pinMode(h,OUTPUT);//defino todos como out para poder usar 11 digitos(arduino nano, uno)
  }
  pinMode(A0,OUTPUT);//LIMPIAR
  for(int i=2 ;i<=11;i++){//apaga todos los catodos negativos del display
    digitalWrite(i,HIGH);
  }
  digitalWrite(A0,LOW);//limpia el registro de desplazamiento
}

void loop() {
  // put your main code here, to run repeatedly:
  multiples(number);
  number = number+1;//es para ir incrementando el numero para las pruebas
  if (number == pow(10,dnum)){//si el numero es igual a un numero que se representa en dnum+1 digitos, vuelve a cero el contador
    number = 0;
  }
  //delay(1000);   ----------------->ver si es necesario para mejorar el mutiplexado
}//fin del loop

//FUNCIONES
int multiples(int number){//divide el numero entero en un arreglo de numeros y agrega ceros en caso de ser un numero chico y no llena el display para pasarlos a la funcion visualizacion
  int j =0;
  int ndisp[dnum];//creo un arreglo para cortar el numero entero
  //esto rellena el array con ceros para que tenga (dnum)digitos
  for(int i=0;i<=(dnum-1) ;i++) {
    ndisp[i]=0;
  }
  //cortar y meter en el array
  for(int k =1 ; k<=dnum;k++){//esto se repite DNUM veces
    int aux=int(number/(pow(10,(dnum-k))));//la funcion int(x) devuelve la parte entera de un numero, ese numero es el number dividido 10 elevado a dnum-k(1000,100,10,1)
    ndisp[k-1]=aux;
    number= (number-(aux*(pow(10,(dnum-k)))));//modifico number para que no tenga la cifra mas significativa que acabamos de ingresar al array
  }
  visualizacion(ndisp);
}
//ejemplo, con dnum =4 y el number=4567
//1º iteracion---->k=1 aux =4     number=567   dnum-k=3
//2º iteracion---->k=2 aux =5     number=67   dnum-k=2
//3º iteracion---->k=3 aux =6     number=7   dnum-k=1
//4º iteracion---->k=4 aux =7     number=0   dnum-k=0
//el arreglo termina {4,5,6,7}
//revisar si anda con las modificaciones

int visualizacion(int *dispd){//esta funcon tiene una serie de for para iterar el numero a disponer y el display a encender, para mostrar el numero deseado
  //for (int i = 0; i<= 50; i++){
  for(int j = 0; j<=dnum-1;j++){
    ver(dispd[j], hab[j] );//con el display y el numero elejidos por el for, llama a VER para que muestre los numeros en el shift register y en el display
  }  
  //}
}
int ver (int entrada,int habilitar){//carga la data en el shift register y baja el clock para meter la data al display
  digitalWrite(limpiar,LOW);
  delay(1);
  digitalWrite(limpiar,HIGH);
  digitalWrite(habilitar,HIGH);//ver que ond CN LOS HABILITAR QUE UEDAN EN HIGH
  for (int i = 0;i <=7;i++){
    if(num[entrada][i] ==1){
      digitalWrite(dato,HIGH);//meto los 1 en el shift register
    }
    else{
      digitalWrite(dato, LOW);//meto los 0 en el shift register
    }
    digitalWrite(reloj,HIGH);
    delay(1);
    digitalWrite(reloj, LOW); //pulso del clock
  }
  digitalWrite(habilitar,LOW);//prendo el digito
  delay(tmul);//ver de cambiar el valor de tmul ------------------> POSIBLE FUENTE DEL PROBLEMA?
  digitalWrite(habilitar,HIGH);//apago el digito
  //se pasa al siguiente digito con el for de la funcion visualizacion
}

Al principio empece haciendo a prueba con un solo display, todo fue bien.Pero al poner dos displays, el multiplexado falla y se ve como titila cada dígito, probé bajando el tiempo de multiplexado(la variable tmul)y lo único que hace es empeorar.

Dejo una captura de pantalla de mi esquema en proteus, y la fuente de la librería simulino.

PD:si alguno tiene otra solución para el proyecto que no sea utilizando mi código, o alguna recomendación de como realizarlo de otra forma también es bienvenido!

gracias con antelación,un saludo!

PROTEUS-ARDUINO-1.zip (45.2 KB)

Este en un problema de hardware.

MatiasHaucke:
Planeo usar un arduino nano, un shift register 74ls164 para los ánodos de los displays, y 10 displays de 7 segmentos de cátodo común.

Ya osea pondrás en paralelo los segmentos de los 10 display conectados a las salidas (Q0 a Q6) del shift register y los ánodos a los pines digitales 2 al 11.

Es decir el bus de datos (Q0 a Q6) tendrá que tener el código 7 segmentos definido en la matriz num al mismo momento en que se active un solo anodo (pines 2 al 11)

MatiasHaucke:
Ocupo del pin 2 al 11 inclusive para los cátodos,

No, error para los ánodos, porque tus display son cátodo común. Aquí cuando tengas que mostrar el 8 requerirás prende los 7 led y como un pin de arduino no da mas de 40 mA tendrás apenas 5.7 mA para cada led y se vera muy claro. Tienes que usar un transistor NPN para darle mas corriente. Dependiendo del tamaño del display puede consumir mínimo 15 mA por segmento.

MatiasHaucke:
los pines 12,13 y A0 para el shift register

Ok, no hay problema A0 se puede usar como pin digital 14.

MatiasHaucke:
las IO analogicas para ingrasr los botones, dispuestos en un separador de voltaje,para obtener medidas distintas de cada uno en la entrada analogica.para esto utilizo los pines A2,A3,A4,A5 y A6

No eran 3 los botones ? bueno también se pueden usar como pines digitales y que es un separador de voltaje ? y como es que cada botón te dará medidas distintas ?

Mira este video

Gracias kike por tu respuesta, se me pasaron los transistores de los cátodos, buscare unos adecuados para esto, alguna recomendación para un neófito en electrónica?

Con respecto a los botones, la idea es poner tres botones por cada par de dígitos, de forma que con los mismos pueda aumentar cada cifra del numero grande(number) con un código que todavía no he escrito.

Lo del divisor de voltaje me refiero a algo parecido a esto:

dejo adjuntada otra imagen al respecto

Pero hecho tres veces y con los pulsadores correspondientes en la salida, e esta forma podría hacer una botonera de tres botones y conectarla a una sola entada analógica y medir los valores recibidos para cada botón.

Probé la simulación con proteus y simulino con la modificación de los transistores y no tuvo alteración alguna, sigue siendo muy notorio el barrido que se hace al prender un dígito, apagarlo, prender el siguiente, apagarlo y así.

Esto me esta partiendo la cabeza

Gracias por tu respuesta!

Las fotos deben verse en el post.
Edita los post que incluyen fotos de acuerdo a las normas del foro y como visualizar fotos adjuntas.
Tambien edita los enlaces que deben ir con etiquetas.
Repasa las normas porque evidentemente no te han quedado claras.

mil disculpas, ya esta corregido,si ha de faltar algo, lo corregiré nuevamente, gracias!

Matias, porque no usas la libreria ShiftDispay.h en lugar de tratar de reinventar la polvora ?

genial, gracias kike, no tenia idea de la existencia de esa librería, sin duda le echare un ojo mas tarde para aplicarla en nuevos proyectos! gracias por todo!