Aumento de brillo en leds multiplexados

Hola buenas tardes, disculpen estoy haciendo un tipo letrero de leds, pero no puedo sacarle mucho brillo a los leds


aqui dejo mi esquema de como los conecto mi letrero de leds es de 32x7 ahi solo puse 16x7 pero es igual los otros 16 columnas mas.
estoy utilizando para multiplexar el 74hc595 y en esas salidas de cada 595 estoy ocupando un transistor en tipo swicth para cada columna estoy ocupando un bc547 lo he intentado con un bc337 y con un 2n2222 pero brilla igual, y en el control de la tierra estoy ocupando un uln2003.
sin embargo con todo eso sigo sin poder hacer que brille mucho quizas este brillando la mitad un poco menos de la mitad de la luminosidad total, se que no se puede llegar al 100% del brillo porque si ocurre algo que haga que los leds se apaguen no sincronizado puedo quemarlo entonces quiero llegar al 75% del brillo.
me gustaria saber si alguien me podria ayudar a aumentar el brillo me gustaria que fuera mas por software mas que hardware.

char  neko[40]={0B01111111,//N
0B01111111,
0B01111111,
0B00001100,
0B00011000,
0B01111111,
0B01111111,
0B00000000,
0B01111111,//E
0B01111111,
0B01101011,
0B01101011,
0B01101011,
0B01100011,
0B01100011,
0B00000000,
0B01111111,//K
0B01111111,
0B00011100,
0B00011100,
0B00110110,
0B01100011,
0B01000001,
0B00000000,
0B00111110,//O
0B01111111,
0B01100011,
0B01100011,
0B01100011,
0B01111111,
0B00111110,
0B00000000,
0b00000000,//espacio
0b00000000,
0b00000000,
0b00000000,
0b00000000,
0b00000000,
0b00000000,
0b00000000};
void f74595_init(){
   output_bit(DATA,1);
   output_bit(pin_a1,1);
   output_bit(DATA,0);
}
void f74595_clock(){
   output_bit(pin_a1,1);
   output_bit(pin_a1,0);
    output_bit(pin_a2,1);
   output_bit(pin_a2,0);
}
 for(int k=0;k<20;k++){            //Refresco de matriz
             f74595_init();
            for(int j=32;j>0;j--){         //Barrido de Columnas
               f74595_clock();
              output_b(neko[j]);  //Desplazamiento de tabla
               delay_us(550);           //Demora de multiplexado
               output_b(0);
               }
             }

ese es el codigo que ocupo para texto estatico

void f74595_init(){
   output_bit(DATA,1);
   output_bit(pin_a1,1);
   output_bit(DATA,0);
}
void f74595_clock(){
   output_bit(pin_a1,1);
   output_bit(pin_a1,0);
    output_bit(pin_a2,1);
   output_bit(pin_a2,0);
}

void letra(char ro[])  // Se recibe el contenido de BU (6 columnas) y se le denomina RO  
             // el objetivo es acumular todas las columnas en un bufer llamdo PF

{int i;
for(i=0;i<8;i++)
texto[jota+i]=ro[i];     // PF acumula los 6 patrones de cada caracter y los almacena
jota=jota+8;          // al terminar de acumular El puntero JOTA avanza 6 posiciones
output_b(0);
}
void asignacion (char Le){
int i;               //variable local para el SWITCH CASE de cada LETRA
char bu[8];          //BUFFER TEMPORAL que almacenara las columnas del caracter
for(i=0;i<8;i++)     // for que recorre las 6 columnas de cada caracter de la TABLA de caracteres
{
output_b(0);
switch(Le)          //Este SWITCH busca el caracter (bor) en la tabla y lo descompone en columnas
{

case 'A':bu[i]=A[i];break;
case 'B':bu[i]=B[i];break;
case 'C':bu[i]=C[i];break;
case 'D':bu[i]=D[i];break;
case 'E':bu[i]=E[i];break;
case 'F':bu[i]=F[i];break;
case 'G':bu[i]=G[i];break;
case 'H':bu[i]=H[i];break;
case 'I':bu[i]=II[i];break;
case 'J':bu[i]=J[i];break;
case 'K':bu[i]=K[i];break;
case 'L':bu[i]=L[i];break;
case 'M':bu[i]=M[i];break;
case 'N':bu[i]=N[i];break;
case '<':bu[i]=NN[i];break;//Ñ
case 'O':bu[i]=O[i];break;
case 'P':bu[i]=P[i];break;
case 'Q':bu[i]=Q[i];break;
case 'R':bu[i]=R[i];break;
case 'S':bu[i]=S[i];break;
case 'T':bu[i]=T[i];break;
case 'U':bu[i]=U[i];break;
case 'V':bu[i]=V[i];break;
case 'W':bu[i]=W[i];break;
case 'X':bu[i]=X[i];break;
case 'Y':bu[i]=Y[i];break;
case 'Z':bu[i]=Z[i];break;
case 'a':bu[i]=am[i];break;
case 'b':bu[i]=bm[i];break;
case 'c':bu[i]=cm[i];break;
case 'd':bu[i]=dm[i];break;
case 'e':bu[i]=em[i];break;
case 'f':bu[i]=fm[i];break;
case 'g':bu[i]=gm[i];break;
case 'h':bu[i]=hm[i];break;
case 'i':bu[i]=iim[i];break;
case 'j':bu[i]=jm[i];break;
case 'k':bu[i]=km[i];break;
case 'l':bu[i]=lm[i];break;
case 'm':bu[i]=mm[i];break;
case 'n':bu[i]=nm[i];break;
case '>':bu[i]=nnm[i];break;//ñ
case 'o':bu[i]=om[i];break;
case 'p':bu[i]=pm[i];break;
case 'q':bu[i]=qm[i];break;
case 'r':bu[i]=rm[i];break;
case 's':bu[i]=sm[i];break;
case 't':bu[i]=tm[i];break;
case 'u':bu[i]=um[i];break;
case 'v':bu[i]=vm[i];break;
case 'w':bu[i]=wm[i];break;
case 'x':bu[i]=xm[i];break;
case 'y':bu[i]=ym[i];break;
case 'z':bu[i]=zm[i];break;
case ' ':bu[i]=espacio[i];break;
case '1':bu[i]=uno[i];break;
case '2':bu[i]=dos[i];break;
case '3':bu[i]=tres[i];break;
case '4':bu[i]=cuatro[i];break;
case '5':bu[i]=cinco[i];break;
case '6':bu[i]=seis[i];break;
case '7':bu[i]=siete[i];break;
case '8':bu[i]=ocho[i];break;
case '9':bu[i]=nueve[i];break;
case '0':bu[i]=cero[i];break;

case '$':bu[i]=pesos[i];break;
case ',':bu[i]=coma[i];break;
case ':':bu[i]=dospuntos[i];break;
case '!':bu[i]=exclamacionA[i];break;
case '¡':bu[i]=exclamacionB[i];break;
case '+':bu[i]=mas[i];break;
case '-':bu[i]=menos[i];break;
case '(':bu[i]=parentesisA[i];break;
case ')':bu[i]=parentesisB[i];break;
case '¿':bu[i]=interrogacionB[i];break;
case '?':bu[i]=interrogacionA[i];break;
case '#':bu[i]=gato[i];break;
case '.':bu[i]=punto[i];break;
case '%':bu[i]=porcentaje[i];break;
case '"':bu[i]=comillas[i];break;
/*case '}':bu[i]=mayorque[i];break;
case '{':bu[i]=menorque[i];break;*/

case '*':bu[i]=aacentp[i];break;
case '/':bu[i]=eacento[i];break;
case '&':bu[i]=iacento[i];break;
case '[':bu[i]=OACENTO[i];break;
case ']':bu[i]=UACENTO[i];break;

}

}
letra(bu); 
}
         int i,j,k; 
         for(omega=0;omega<tamano-6;omega=omega+3)    // Omega es un puntero de caracteres que avanza de 4 en 4 ya que el mensaje se desplaza 4 caracteres    
             {
            jota=0;
             for(k=0;k<9;k++)   
             {
             if(voltear==0){
             asignacion(mensaje[k+omega]); // Llamamos a la funcion SWATCH que acomoda patrón de columnas del caracter Nro K+Omega en el arreglo  pf[] letra por letra en cada for
             }
              if(voltear==1){
             asignacionVolteada(mensaje[k+omega]); // Llamamos a la funcion SWATCH que acomoda patrón de columnas del caracter Nro K+Omega en el arreglo  pf[] letra por letra en cada for
             }
          continue;
             }
      for(i=0;i<24;i++){         //Recorrido de tabla
         for(k=0;k<velocidad;k++){            //Refresco de matriz
         f74595_init();
            for(j=32;j>0;j--){         //Barrido de Columnas
             f74595_clock();
             output_b(texto[j+i]);  //Desplazamiento de tabla
                delay_us(550);           //Demora de multiplexado
              output_b(0);
               }
            }
         }
       }

este para texto que se mueve.
muchas gracias por su atencion espero me puedan ayudar

hola,
bc547 548 son 100mA de colector máximo, correcto ? 7 leds creo q ya supera ese valor no ?
tienes q enfocarte en el tiempo q está encendido, si aumentando el tiempo el brillo aumenta entonces la solución es por ahí (igualmente ten en cuenta la corriente por el bc547 talvez está pasandosé)
algunos mux los mejoran multiplexando 2 columnas al mismo tiempo en vez de 1 , con eso el tiempo de ON sube...
busca en la datasheet también la peak current de los leds. suele ser casi 10 veces mayor intenta hallar esa info y le puedes aplicar ese pico de corriente asegurandote q sea por el tiempo permitido

Porque no nos provees mas informacioin sobre los LEDs porque son en definitiva los elementos que deben iluminarse mas y para ello hay que hacer lo que dice @osval.
Debes subir la corriente usando un transistor driver mejor que los que estas usando.
Debes bajar el tiempo en que este en ON subiendo la corriente lo que mantiene al LED en condición de trabajo seguro. Eso no se hace a prueba error. Hay que leer la hoja de datos o ser muy cuidadoso.
Yo te recomiendo usar MOSFET en lugar de transistores porque son mas eficientes y tienen mas baja caida de tensión (low Rds).
Para ello tenemos que tener datos de los LEDs.

Aclaro que coincido con @Surbyte pero hago un par de observaciones.

De los 3 modelos de transistores que has probado el que mejor se adapta es el BC337 porque maneja hasta 800 mA.

El problema del brillo bajo se debe a la forma de hacer el multiplexado. No tienes control real de los tiempos, no sabes realmente cuanto tiempo está encendido un "segmento" pero lo más dramático para este caso, no sabes cuanto están apagados.

El multiplexado tienes que manejarlo con interrupciones generadas por un timer si quieres algo realmente efectivo.

Saludos

A eso quería llegar @anon90500195, pero primero lo primero, saber hasta donde se puede aumentar la corriente de LED de lo contrario a ojo sabemos como termina.
Igualmente buena observación respecto al 337. Yo los he abandonado de mis diseños.

hola buenas tardes muchísimas gracias a todos pos sus respuestas.
encontre el datasheet de los leds es este http://www.wayjun.com/Datasheet/Led/3528%20SMD%20LED.pdf
en mi caso es el led blanco
@anon90500195 me imagine que iba por ahí pero realmente no soy muy bueno programando no se si me podrías dar un ejemplo de como se haría eso y ya lo adapto a mi programa, te agradecería mucho eso

Yo lo intentaría pero tengo 2 problemas.

Uno, no tengo ni la más mínima idea de como está "eso" conectado al arduino porque no están los datos (o no los veo).

El segundo, y más importante, todavía estoy tratando de entender la lógica del código porque no está completo.
Y si no logro armar la idea menos puedo codificarla...

Lo que noto es que lo tuyo son los rompecabezas.
Esquema en trozos, código en trozos... :grimacing:
(Es una broma)

Saludos

  #include "RTClib.h"
  #include <EEPROM.h>   
  RTC_DS1307 rtc;
  char datosPer[120];
  float banderazo=0.00,tarifa=0.00;
  int cambioPulsos;
void setup() 
{
  pinMode(2,OUTPUT);pinMode(3,OUTPUT);pinMode(4,OUTPUT);pinMode(5,OUTPUT);pinMode(6,OUTPUT);pinMode(7,OUTPUT);pinMode(8,OUTPUT);pinMode(9,OUTPUT);pinMode(10,OUTPUT);pinMode(11,OUTPUT);
  pinMode(12,OUTPUT);pinMode(13,OUTPUT);pinMode(22,OUTPUT);pinMode(23,OUTPUT);pinMode(24,OUTPUT);pinMode(25,OUTPUT);pinMode(26,OUTPUT);pinMode(27,OUTPUT);pinMode(28,OUTPUT);pinMode(29,INPUT);
  pinMode(30,OUTPUT);pinMode(31,OUTPUT);pinMode(32,OUTPUT);pinMode(33,OUTPUT);pinMode(34,OUTPUT);pinMode(35,OUTPUT);pinMode(36,OUTPUT);pinMode(37,OUTPUT);pinMode(38,OUTPUT);pinMode(39,OUTPUT);
  pinMode(40,OUTPUT);pinMode(41,OUTPUT);pinMode(42,OUTPUT);pinMode(43,OUTPUT);pinMode(44,OUTPUT);pinMode(45,OUTPUT);pinMode(46,OUTPUT);pinMode(47,OUTPUT);pinMode(48,OUTPUT);pinMode(49,OUTPUT);
   pinMode(19,INPUT); pinMode(20,INPUT);
  attachInterrupt(digitalPinToInterrupt(18), sensor, FALLING);
  Serial.begin(9600);
  Serial3.begin(9600);
  //BT.begin(9600);
   if (!rtc.begin()) {
  //Serial.println(F("Couldn't find RTC"));
      while (1);
   }
/*  if (rtc.lostPower()) {
      rtc.adjust(DateTime(F(__DATE__), F(__TIME__))); 
   }*/
  if(EEPROM[42]==254 && EEPROM[41]==254 && EEPROM [40]!=254){
    cambioPulsos=EEPROM[40];
  }
  if(EEPROM[42]==254 && EEPROM[41]!=254 && EEPROM [40]!=254){
    cambioPulsos=(EEPROM[40]*100)+EEPROM[41];
  }
  if(EEPROM[42]!=254 && EEPROM[41]!=254 && EEPROM [40]!=254){
    cambioPulsos=(EEPROM[40]*10000)+(EEPROM[41]*100)+EEPROM[42];
  }
  if(EEPROM[1]==254){
    banderazo=EEPROM[0]/100.00;
  }
  if(EEPROM[1]!=254){
  banderazo=((EEPROM[0]*100)+EEPROM[1])/100.00;
  }
  if(EEPROM[3]==254){
    tarifa=EEPROM[2]/100.00;
  }
  if(EEPROM[3]!=254){
  tarifa=((EEPROM[2]*100)+EEPROM[3])/100.00;
  }
   for(int t=0;t<4;t++){
    datosPer[t]=' ';
   }
   for(int s=1;s<10;s++){
    datosPer[EEPROM[43]+s]=' ';
   }
     for(int a=0;a<EEPROM[43];a++){
    switch(EEPROM.read(45+a)){
      case 65:datosPer[a+4]='A';break;
      case 66:datosPer[a+4]='B';break;
      case 67:datosPer[a+4]='C';break;
      case 68:datosPer[a+4]='D';break;
      case 69:datosPer[a+4]='E';break;
      case 70:datosPer[a+4]='F';break;
      case 71:datosPer[a+4]='G';break;
      case 72:datosPer[a+4]='H';break;
      case 73:datosPer[a+4]='I';break;
      case 74:datosPer[a+4]='J';break;
      case 75:datosPer[a+4]='K';break;
      case 76:datosPer[a+4]='L';break;
      case 77:datosPer[a+4]='M';break;
      case 78:datosPer[a+4]='N';break;
      case 165:datosPer[a+4]='Ñ';break;
      case 79:datosPer[a+4]='O';break;
      case 80:datosPer[a+4]='P';break;
      case 81:datosPer[a+4]='Q';break;
      case 82:datosPer[a+4]='R';break;
      case 83:datosPer[a+4]='S';break;
      case 84:datosPer[a+4]='T';break;
      case 85:datosPer[a+4]='U';break;
      case 86:datosPer[a+4]='V';break;
      case 87:datosPer[a+4]='W';break;
      case 88:datosPer[a+4]='X';break;
      case 89:datosPer[a+4]='Y';break;
      case 90:datosPer[a+4]='Z';break;
      case 48:datosPer[a+4]='0';break;
      case 49:datosPer[a+4]='1';break;
      case 50:datosPer[a+4]='2';break;
      case 51:datosPer[a+4]='3';break;
      case 52:datosPer[a+4]='4';break;
      case 53:datosPer[a+4]='5';break;
      case 54:datosPer[a+4]='6';break;
      case 55:datosPer[a+4]='7';break;
      case 56:datosPer[a+4]='8';break;
      case 57:datosPer[a+4]='9';break;
      case 32:datosPer[a+4]=' ';break;
    }
  }
}
    int const AM[8]={B01111110,B00001001,B00001001,B00001001,B00001001,B00001001,B01111110,B00000000};
    int const BM[8]={B01111111,B01001001,B01001001,B01001001,B01001001,B01001001,B00110110,B00000000};
    int const CM[8]={B00111110,B01000001,B01000001,B01000001,B01000001,B01000001,B00100010,B00000000};
    int const DM[8]={B01111111,B01000001,B01000001,B01000001,B01000001,B00100010,B00011100,B00000000};
    int const EM[8]={B01111111,B01001001,B01001001,B01001001,B01001001,B01000001,B01000001,B00000000};
    int const FM[8]={B01111111,B00001001,B00001001,B00001001,B00001001,B00000001,B00000001,B00000000};
    int const GM[8]={B00111110,B01000001,B01000001,B01001001,B01001001,B01001001,B01111010,B00000000};
    int const HM[8]={B01111111,B00001000,B00001000,B00001000,B00001000,B00001000,B01111111,B00000000};
    int const IM[8]={B01000001,B01000001,B01000001,B01111111,B01000001,B01000001,B01000001,B00000000};
    int const JM[8]={B00110000,B01000000,B01000000,B01000000,B01000000,B01000000,B00111111,B00000000};
    int const KM[8]={B01111111,B00001000,B00010100,B00100010,B01000001,B01000001,B00000000,B00000000};
    int const LM[8]={B01111111,B01000000,B01000000,B01000000,B01000000,B01000000,B01000000,B00000000};
    int const MM[8]={B01111111,B00000010,B00000100,B00001000,B00000100,B00000010,B01111111,B00000000};
    int const NM[8]={B01111111,B00000010,B00000100,B00001000,B00010000,B00100000,B01111111,B00000000};
    int const NNM[8]={B01111101,B00000101,B00001001,B00010001,B00100001,B01000001,B01111101,B00000000};
    int const OM[8]={B00111110,B01000001,B01000001,B01000001,B01000001,B01000001,B00111110,B00000000};
    int const PM[8]={B01111111,B00001001,B00001001,B00001001,B00001001,B00001001,B00000110,B00000000};
    int const QM[8]={B00111110,B01000001,B01000001,B01000001,B01010001,B00100001,B01011110,B00000000};  
    int const RM[8]={B01111111,B00001001,B00001001,B00001001,B00011001,B00101001,B01000110,B00000000};
    int const SM[8]={B01000110,B01001001,B01001001,B01001001,B01001001,B01001001,B00110001,B00000000};
    int const TM[8]={B00000001,B00000001,B00000001,B01111111,B00000001,B00000001,B00000001,B00000000};
    int const UM[8]={B00111111,B01000000,B01000000,B01000000,B01000000,B01000000,B00111111,B00000000};
    int const VM[8]={B00001111,B00010000,B00100000,B01000000,B00100000,B00010000,B00001111,B00000000};
    int const WM[8]={B01111111,B00100000,B00010000,B00001000,B00010000,B00100000,B01111111,B00000000};
    int const XM[8]={B01000001,B00100010,B00010100,B00001000,B00010100,B00100010,B01000001,B00000000};
    int const YM[8]={B00000001,B00000010,B00000100,B01111000,B00000100,B00000010,B00000001,B00000000};
    int const ZM[8]={B01000001,B01100001,B01010001,B01001001,B01000101,B01000011,B01000001,B00000000};
    int const ESPACIO[8]={B00000000,B00000000,B00000000,B00000000,B00000000,B00000000,B00000000,B00000000};
     int const cero[8]={B00111110,B01000011,B01000101,B01001001,B01010001,B01100001,B00111110,B00000000};
     int const uno[8]={B00000000,B01000000,B01000010,B01111111,B01000000,B01000000,B00000000,B00000000};
     int const dos[8]={B01000010,B01100001,B01100001,B01010001,B01011001,B01001001,B01000110,B00000000};
     int const tres[8]={B00100010,B01000001,B01000001,B01000001,B01001001,B01001001,B00110110,B00000000};
     int const cuatro[8]={B00001111,B00001000,B00001000,B00001000,B00001000,B00001000,B01111111,B00000000};
     int const cinco[8]={B01001111,B01001001,B01001001,B01001001,B01001001,B01001001,B00110001,B00000000};
     int const seis[8]={B00111110,B01001001,B01001001,B01001001,B01001001,B01001001,B00110010,B00000000};
     int const siete[8]={B00000001,B00000001,B01100001,B00010001,B00001001,B00000101,B00000011,B00000000};
     int const ocho[8]={B00110110,B01001001,B01001001,B01001001,B01001001,B01001001,B00110110,B00000000};
     int const nueve[8]={B00000110,B01001001,B01001001,B01001001,B01001001,B01001001,B00111110,B00000000};
     int const punto[8]={B00000000,B01100000,B01100000,B00000000,B00000000,B00000000,B00000000,B00000000};
     int const dosPuntos[8]={B00000000,B00110110,B00110110,B00000000,B00000000,B00000000,B00000000,B00000000};
     int const diagonal[8]={B01000000,B00100000,B00010000,B00001000,B00000100,B00000010,B00000001,B00000000};
     int const cero5[5]={B00111110,B01000001,B01000001,B00111110,B00000000};
     int const uno5[5]={B01000000,B01111111,B01000010,B00000000,B00000000};
     int const dos5[5]={B01100010,B01010001,B01001001,B01000110,B00000000};
     int const tres5[5]={B00100010,B01001001,B01001001,B00110110,B00000000};
     int const cuatro5[5]={B00001111,B00001000,B00001000,B01111111,B00000000};  
     int const cinco5[5]={B01001111,B01001001,B01001001,B00110001,B00000000};
     int const seis5[5]={B00111110,B01001001,B01001001,B00110010,B00000000};
     int const siete5[5]={B00000001,B00001001,B00001001,B01111111,B00000000};
     int const ocho5[5]={B00110110,B01001001,B01001001,B00110110,B00000000};
     int const nueve5[5]={B01000110,B01001001,B01001001,B00111110,B00000000};
     int const espacio5[5]={B00000000,B00000000,B00000000,B00000000,B00000000 };
////////////////////////////////////////COMPARADOR 8////////////////////////////////////////////////////////////////////////
char texto[72];
int jota,omega=0;
void letra(char ro[])  // Se recibe el contenido de BU (6 columnas) y se le denomina RO  
             // el objetivo es acumular todas las columnas en un bufer llamdo PF

{int i;
for(i=0;i<8;i++)
texto[jota+i]=ro[i];     // PF acumula los 6 patrones de cada caracter y los almacena
jota=jota+8;          // al terminar de acumular El puntero JOTA avanza 6 posiciones
}
void asignacion (char Le){
int i;               //variable local para el SWITCH CASE de cada LETRA
char bu[8];          //BUFFER TEMPORAL que almacenara las columnas del caracter
for(i=0;i<8;i++)     // for que recorre las 6 columnas de cada caracter de la TABLA de caracteres
{
switch(Le)          //Este SWITCH busca el caracter (bor) en la tabla y lo descompone en columnas
{
case 'A':bu[i]=AM[i];break;
case 'B':bu[i]=BM[i];break;
case 'C':bu[i]=CM[i];break;
case 'D':bu[i]=DM[i];break;
case 'E':bu[i]=EM[i];break;
case 'F':bu[i]=FM[i];break;
case 'G':bu[i]=GM[i];break;
case 'H':bu[i]=HM[i];break;
case 'I':bu[i]=IM[i];break;
case 'J':bu[i]=JM[i];break;
case 'K':bu[i]=KM[i];break;
case 'L':bu[i]=LM[i];break;
case 'M':bu[i]=MM[i];break;
case 'N':bu[i]=NM[i];break;
case 'Ñ':bu[i]=NNM[i];break;
case 'O':bu[i]=OM[i];break;
case 'P':bu[i]=PM[i];break;
case 'Q':bu[i]=QM[i];break;
case 'R':bu[i]=RM[i];break;
case 'S':bu[i]=SM[i];break;
case 'T':bu[i]=TM[i];break;
case 'U':bu[i]=UM[i];break;
case 'V':bu[i]=VM[i];break;
case 'W':bu[i]=WM[i];break;
case 'X':bu[i]=XM[i];break;
case 'Y':bu[i]=YM[i];break;
case 'Z':bu[i]=ZM[i];break;
case ' ':bu[i]=ESPACIO[i];break;
case '1':bu[i]=uno[i];break;
case '2':bu[i]=dos[i];break;
case '3':bu[i]=tres[i];break;
case '4':bu[i]=cuatro[i];break;
case '5':bu[i]=cinco[i];break;
case '6':bu[i]=seis[i];break;
case '7':bu[i]=siete[i];break;
case '8':bu[i]=ocho[i];break;
case '9':bu[i]=nueve[i];break;
case '0':bu[i]=cero[i];break;
case ':':bu[i]=dosPuntos[i];break;
case '/':bu[i]=diagonal[i];break;
case '.':bu[i]=punto[i];break;
}

}
letra(bu); 
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////    
int blue=0,contadorSensor0=0,mostrarMenus=0,mostrarSensor=0,contadorSensor=0,contadorTarifa=2,led=0,buzzer=0,ledcont=0,buzzercont=0;
int primero=0,contando=0,mostrarPagar=0,mostrarTarifa=0,primerMuestra=0,mostrarDatos=0,dia=0,noche=0,segund;
char cadena[255]; //Creamos un array de caracteres de 256 cposiciones
  int i=0; //Tamaño actual del array
  String numero;
void loop() {
int reloj=0;
  inicio:
while(blue==1){
  digitalWrite(7,HIGH);
  digitalWrite(32,HIGH);
  PORTA=B00011000;
  int cc=-1;
  if(digitalRead(50)==1){
                 while(digitalRead(50)==1)
                {
                delay(220);
                }
                blue=0;
                primero=1;
                reloj=0;
                goto inicio;
              }  
  if(Serial3.available())
              {
                //@ para banderazo 1 direccion 0 y 1
                //# para tarifa 1 direccion 2 y 3
                //$ para banderazo 2 direccion 4 y 5 
                //& para tarifa 2 direccion 6 y 7
                //_ para banderazo 3 direccion 8 y 9
                //- para tarifa 3 direccion 10 y 11
                //( para banderazo 4 direccion 12 y 13
                //) para tarifa 4 direccion 14 y 15
                //= para banderazo 5 direccion 16 y 17
                //% para tarifa 5 direccion 18 y 19
                //" para banderazo 6 direccion 20 y 21
                //* para tarifa 6 direccion 22 y 23
                //` para banderazo 7 direccion 24 y 25
                //: para tarifa 7 direccion 26 y 27
                /// para banderazo 8 direccion 28 y 29
                //! para tarifa 8 direccion 30 y 31
                //¡ para banderazo 9 direccion 32 y 33
                //? para tarifa 9 direccion 34 y 35
                //+ para banderazo 10 direccion 36 y 37
                //; para tarifa 10 direccion 38 y 39
                //÷ 
                //¿
                char dato=Serial3.read(); //Guarda los datos carácter a carácter en la variable "dato"
                cadena[i++]=dato; //Vamos colocando cada carácter recibido en el array "cadena"   
                if(dato=='\n')
                {
                 
                    if(cadena[0]=='@'){
                      cc=0;
                    }
                    if(cadena[0]=='#'){
                      cc=2;
                    }
                    if(cadena[0]=='$'){
                      cc=4;
                    }
                    if(cadena[0]=='&'){
                      cc=6;
                    }
                    if(cadena[0]=='_'){
                      cc=8;
                    }
                    if(cadena[0]=='-'){
                      cc=10;
                    }
                    if(cadena[0]=='('){
                      cc=12;
                    }
                    if(cadena[0]==')'){
                      cc=14;
                    }
                    if(cadena[0]=='='){
                      cc=16;
                    }
                    if(cadena[0]=='%'){
                      cc=18;
                    }
                    if(cadena[0]=='"'){
                      cc=20;
                    }
                    if(cadena[0]=='*'){
                      cc=22;
                    }
                    if(cadena[0]=='`'){
                      cc=24;
                    }
                    if(cadena[0]==':'){
                      cc=26;
                    }
                    if(cadena[0]=='/'){
                      cc=28;
                    }
                    if(cadena[0]=='!'){
                      cc=30;
                    }
                    if(cadena[0]=='{'){
                      cc=32;
                    }
                    if(cadena[0]=='?'){
                      cc=34;
                    }
                    if(cadena[0]=='+'){
                      cc=36;
                    }
                    if(cadena[0]==';'){
                      cc=38;
                    }
                    if(cadena[0]=='}'){
                      cc=-1;
                       for (int a=1;a<i;a++){
                      numero=numero+cadena[a];
                      }
                      int tar=numero.toInt();
                      if(tar<254){
                        EEPROM.write(40,tar);
                        EEPROM.write(41,254);
                        EEPROM.write(42,254);
                      }
                      if(tar>254 && tar <10000){
                        EEPROM.write(40,tar/100);
                        EEPROM.write(41,tar%100);
                        EEPROM.write(42,254);
                      }
                      if(tar>10000){
                        EEPROM.write(40,tar/10000);
                        EEPROM.write(41,(tar%10000)/100);
                        EEPROM.write(42,tar%100);
                      }
                    }
                    if(cadena[0]=='<'){
                      cc=-1;
                      EEPROM.write(43,i-3);
                      for(int u=1;u<i-2;u++){
                        EEPROM.put(u+44,cadena[u]);
                      }
                    }
                    if(cc!=-1){
                      for (int a=1;a<i;a++){
                      numero=numero+cadena[a];
                      }
                      int tar=(numero.toFloat())*100;
                      EEPROM.write(cc,tar/100);
                      if(tar<255){
                        EEPROM.write(cc,tar);
                        EEPROM.write(cc+1,254);
                      }
                      if(tar>254){
                        EEPROM.write(cc,tar/100);
                      EEPROM.write(cc+1,tar%100);
                      }
                  }
                  cc=-1;
                  numero="";
                  i=0;
              }
          }
}
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
while(primero==0){
  int const DECO[32]={B01111111,B01000001,B01000001,B01000001,B01000001,B00100010,B00011100,B00000000,//D
                      B01111111,B01001001,B01001001,B01001001,B01001001,B01000001,B01000001,B00000000,
                      B00111110,B01000001,B01000001,B01000001,B01000001,B01000001,B00100010,B00000000,
                      B00111110,B01000001,B01000001,B01000001,B01000001,B01000001,B00111110,B00000000};
              for(int k=0;k<100;k++)//Refresco de matriz
         {            
            for(int j=32;j>=0;j--)//Barrido de Columnas
            {  
              if(j<20){
               digitalWrite(j+30,HIGH);
              }
              if(j>19){
                digitalWrite(j-18,HIGH);
              }
              PORTA=DECO[j];
               delayMicroseconds(550);           //Demora de multiplexado
               PORTA=B00000000;
              if(j<20){
               digitalWrite(j+30,LOW);
              }
              if(j>19){
                digitalWrite(j-18,LOW);
              }
               }
               if(k==99){
               primero=1;
               }
               }  
  }
    while(primero==1){
      if(reloj==0){
        DateTime now = rtc.now();
        if(now.hour()>21 && now.hour()<6 && noche==0){
          dia=0;
          noche=1;
          contadorTarifa+=1;
          if(EEPROM[((contadorTarifa-1)*4)+1]==254){
                  banderazo=EEPROM[(contadorTarifa-1)*4]/100.00;
                }
                if(EEPROM[((contadorTarifa-1)*4)+1]!=254){
                banderazo=((EEPROM[(contadorTarifa-1)*4]*100)+EEPROM[((contadorTarifa-1)*4)+1])/100.00;
                }
                if(EEPROM[(contadorTarifa*4)-1]==254){
                  tarifa=EEPROM[(contadorTarifa*4)-2]/100.00;
                }
                if(EEPROM[(contadorTarifa*4)-1]!=254){
                tarifa=((EEPROM[(contadorTarifa*4)-2]*100)+EEPROM[((contadorTarifa*4)-1)])/100.00;
                }
        }
        if(now.hour()>5 && now.hour()<22 && dia==0){
          dia=1;
          noche=0;
          contadorTarifa-=1;
          if(EEPROM[((contadorTarifa-1)*4)+1]==254){
                  banderazo=EEPROM[(contadorTarifa-1)*4]/100.00;
                }
                if(EEPROM[((contadorTarifa-1)*4)+1]!=254){
                banderazo=((EEPROM[(contadorTarifa-1)*4]*100)+EEPROM[((contadorTarifa-1)*4)+1])/100.00;
                }
                if(EEPROM[(contadorTarifa*4)-1]==254){
                  tarifa=EEPROM[(contadorTarifa*4)-2]/100.00;
                }
                if(EEPROM[(contadorTarifa*4)-1]!=254){
                tarifa=((EEPROM[(contadorTarifa*4)-2]*100)+EEPROM[((contadorTarifa*4)-1)])/100.00;
                }
        }
       int libre[32]={
        B01111111,B01000000,B01000000,B01000000,B00000000,B01000001,B01111111,B01000001,B00000000,B01111111,B01001001,B01001001,
        B00110110,B00000000,B01111111,B00011001,B00101001,B01000110,B00000000,B01111111,B01001001,B01001001,B01000001,B00000000
        };
        if(contadorTarifa<10){
      for(int p=0;p<8;p++){
    if(contadorTarifa==1){
      libre[25+p]=uno[p];
    }
    if(contadorTarifa==2){
      libre[25+p]=dos[p];
    }
    if(contadorTarifa==3){
      libre[25+p]=tres[p];
    }
    if(contadorTarifa==4){
      libre[25+p]=cuatro[p];
    }
    if(contadorTarifa==5){
      libre[25+p]=cinco[p];
    }
    if(contadorTarifa==6){
      libre[25+p]=seis[p];
    }
    if(contadorTarifa==7){
      libre[25+p]=siete[p];
    }
    if(contadorTarifa==8){
      libre[25+p]=ocho[p];
    }
    if(contadorTarifa==9){
      libre[25+p]=nueve[p];
      }
    }
  }
   if(contadorTarifa==10){
    libre[25]=B01000010;
    libre[26]=B01111111;
    libre[27]=B01000000;
    libre[28]=B00000000;
    libre[29]=B00111110;
    libre[30]=B01000001;
    libre[31]=B00111110;
    libre[32]=B00000000;
  }
              for(int k=0;k<250;k++)//Refresco de matriz
         {            
            for(int j=32;j>=0;j--)//Barrido de Columnas
            { 
              if(digitalRead(19)==1){
                 while(digitalRead(19)==1)
                {
                delay(220);
                }
                reloj=3;
                mostrarDatos=1;
                for(int a=0;a<72;a++){
                  texto[a]=255;
                }
                goto inicio;
              }  
             if(digitalRead(51)==1){
                 while(digitalRead(51)==1)
                {
                delay(220);
                }
                mostrarMenus=1;
                mostrarTarifa=1;
                primero=2;
                goto inicio;
              }   
              if(digitalRead(50)==1){
                 while(digitalRead(50)==1)
                {
                delay(220);
                }
                mostrarMenus=1;
                mostrarSensor=1;
                primero=2;
                goto inicio;
              }
              if(digitalRead(53)==1){
                 while(digitalRead(53)==1)
                {
                delay(220);
                }
                led=1;
                digitalWrite(A0,HIGH);
                DateTime now = rtc.now();
                segund=now.second();
                mostrarMenus=1;
                contando=1;
                primero=2;
                goto inicio;
              }
               if(j<20){
               digitalWrite(j+30,HIGH);
              }
              if(j>19){
                digitalWrite(j-18,HIGH);
              }
              PORTA=libre[j];
               delayMicroseconds(550);           //Demora de multiplexado
               PORTA=B00000000;
              if(j<20){
               digitalWrite(j+30,LOW);
              }
              if(j>19){
                digitalWrite(j-18,LOW);
              }
               }
              if(k==200){
                for(int a=0;a<72;a++){
                  texto[a]=255;
                }
                reloj=1;
                }
              }
              
    }
    while(reloj==1 || mostrarDatos==1){
      int largo;
      DateTime now = rtc.now();
                String ano=(String)now.year();
                String mes=(String)now.month();
                String dia=(String)now.day();
                String hora=(String)now.hour();
                String minuto=(String)now.minute();
                String seg=(String)now.second();
                String espacios="       ";
                String espaciossimple=" ";
                String puntos=":";
                String guion="/";
                String horario=espacios+hora+puntos+minuto+puntos+seg+espaciossimple+dia+guion+mes+guion+ano+espacios;
                int longintud_mensaje=horario.length()+1;
                char horario1[longintud_mensaje];
                horario.toCharArray(horario1,longintud_mensaje);
                      if(reloj==1){
                        largo=longintud_mensaje-1;
                      }
                      if(mostrarDatos==1){
                        largo=EEPROM[43]+3;
                      }
    for(omega=0;omega<largo;omega=omega+3)    // Omega es un puntero de caracteres que avanza de 4 en 4 ya que el mensaje se desplaza 4 caracteres    
            { 
            jota=0;
             for(int k=0;k<9;k++)   
             {
              if(mostrarDatos==1){
                asignacion(datosPer[k+omega]);
              }
              if(reloj==1){
             asignacion(horario1[k+omega]); // Llamamos a la funcion SWATCH que acomoda patrón de columnas del caracter Nro K+Omega en el arreglo  pf[] letra por letra en cada for
              }          
          continue;
             }
        for(int l=0;l<24;l++)
               {  
         for(int k=0;k<4;k++)//Refresco de matriz
         {            
            for(int j=32;j>=0;j--)//Barrido de Columnas
            {    
              if(digitalRead(19)==1){
                 while(digitalRead(19)==1)
                {
                delay(220);
                }
                if(mostrarDatos==0){
                  for(int a=0;a<72;a++){
                  texto[a]=255;
                  
                }
                reloj=3;
                mostrarDatos=1;
                }
                if(mostrarDatos==1){
                  for(int a=0;a<72;a++){
                  texto[a]=255;
                }
                reloj=0;
                mostrarDatos=0;
                }
                goto inicio;
              }      
              if(digitalRead(51)==1){
                 while(digitalRead(51)==1)
                {
                delay(220);
                }
                mostrarMenus=1;
                mostrarTarifa=1;
                primero=2;
                goto inicio;
              }   
              if(digitalRead(50)==1){
                 while(digitalRead(50)==1)
                {
                delay(220);
                }
                mostrarMenus=1;
                mostrarSensor=1;
                primero=2;
                goto inicio;
              }
              if(digitalRead(53)==1){
                 while(digitalRead(53)==1)
                {
                delay(220);
                }
                digitalWrite(A0,HIGH);
                led=1;
                DateTime now = rtc.now();
                segund=now.second();
                mostrarMenus=1;
                contando=1;
                primero=2;
                goto inicio;
              }   
               if(j<20){
               digitalWrite(j+30,HIGH);
              }
              if(j>19){
                digitalWrite(j-18,HIGH);
              }
               PORTA=texto[j+l];
                delayMicroseconds(550);           //Demora de multiplexado
                PORTA=B00000000;
              if(j<20){
               digitalWrite(j+30,LOW);
              }
              if(j>19){
                digitalWrite(j-18,LOW);
              }
               }
         }
      }
      if(omega>longintud_mensaje-12 && mostrarDatos==0){
        for(int a=0;a<72;a++){
                  texto[a]=255;
                }
            reloj=0;
            goto inicio;
            }
    }
  }
    }
   while(mostrarMenus==1){
     DateTime now=rtc.now();
      int refre;
      int const tarifas[32]={B00000001,B01111111,B00000001,B00000000,B01111110,B00001001,B00001001,B01111110,B00000000,B01111111,B00011001,B00101001,
                             B01000110,B00000000,B01000001,B01111111,B01000001,B00000000,B01111111,B00001001,B00001001,B00000001,B00000000,B01111110,
                             B00001001,B00001001,B01111110,B00000000,B01001111,B01001001,B01001001,B01111001};
        int const pagar[32]={B01111111,B00001001,B00001001,B00001001,B00000110,B00000000,B01111110,B00001001,B00001001,B00001001,B01111110,B00000000,
                             B00111110,B01000001,B01001001,B01001001,B01111010,B00000000,B01111110,B00001001,B00001001,B00001001,B01111110,B00000000,
                             B01111111,B00001001,B00011001,B00101001,B01000110,B00000000,B00000000,B00000000};
      String esp=" ";
      ////////////////////////////tarifa/////////////////////
      int binaumento [32]; 
      if(contando==1 && mostrarPagar==0){
      String aument=(String)banderazo;
      String tarif;
      if(banderazo>0.01){
        tarif=esp+esp+esp+aument;
        binaumento[0]=B00000000;
        binaumento[1]=B00000000;
        binaumento[2]=B00000000;
      }
      if(banderazo>9.99 && banderazo<100){
        tarif=esp+esp+aument;
        binaumento[0]=B00000000;
         binaumento[1]=B00000000;
         binaumento[2]=B00000000;
      }
      if(banderazo>99.99 && banderazo<1000){
        tarif=esp+aument;
        binaumento[0]=B00000000;
        binaumento[1]=B00000000;
        binaumento[2]=B00000000;
      }
      if(banderazo>1000){
        tarif=aument;
      }
      int longiAument=tarif.length()+1;
      char aument1[longiAument];
      tarif.toCharArray(aument1,longiAument);
      int contaum=0;
      for(int p=0;p<7;p++){
        if(aument1[p]!='.'){
          for(int y=0;y<5;y++){
            if(aument1[p]==' '){
              binaumento[y+contaum]=espacio5[y];
            }
            if(aument1[p]=='0'){
              binaumento[y+contaum]=cero5[y];
            }
            if(aument1[p]=='1'){
              binaumento[y+contaum]=uno5[y];
            }
            if(aument1[p]=='2'){
              binaumento[y+contaum]=dos5[y];
            }
            if(aument1[p]=='3'){
              binaumento[y+contaum]=tres5[y];
            }
            if(aument1[p]=='4'){
              binaumento[y+contaum]=cuatro5[y];
            }
            if(aument1[p]=='5'){
              binaumento[y+contaum]=cinco5[y];
            }
            if(aument1[p]=='6'){
              binaumento[y+contaum]=seis5[y];
            }
            if(aument1[p]=='7'){
              binaumento[y+contaum]=siete5[y];
            }
            if(aument1[p]=='8'){
              binaumento[y+contaum]=ocho5[y];
            }
            if(aument1[p]=='9'){
              binaumento[y+contaum]=nueve5[y];
            }
          }
          contaum=contaum+5;
        }
        if(aument1[p]=='.'){
          binaumento[contaum]=B01000000;
          binaumento[contaum+1]=B00000000;
          contaum=contaum+2;
        }
      }
      }
      ///////////////////////////////////////////////////////
      ////////////////////////////pulsos/////////////////////
      int pulsos [32];
      if(mostrarSensor==1 || primerMuestra==1){
        String cont;
        if(mostrarSensor==1){
         cont=(String)contadorSensor;
        }
        if(primerMuestra==1){
         cont=(String)contadorTarifa;
        }
  String contadorEspacios;
  if(contadorSensor<10 || contadorTarifa<10){
    contadorEspacios=esp+esp+esp+cont;
  }
  if((contadorSensor>9 && contadorSensor<100) || contadorTarifa==10){
    contadorEspacios=esp+esp+cont;
  }
  if(contadorSensor>99 && contadorSensor<1000){
    contadorEspacios=esp+cont;
  }
   if(contadorSensor>999){
    contadorEspacios=cont;
  }
      int longi=contadorEspacios.length()+1;
  char contadorSensor1[longi];
  contadorEspacios.toCharArray(contadorSensor1,longi);
      int co=0; 
      for(int a=0;a<4;a++){
        for(int s=0;s<8;s++){
          if(contadorEspacios[a]==' '){
            pulsos[s+co]=ESPACIO[s];
          }
          if(contadorEspacios[a]=='1'){
            pulsos[s+co]=uno[s];
          }
          if(contadorEspacios[a]=='2'){
            pulsos[s+co]=dos[s];
          }
          if(contadorEspacios[a]=='3'){
            pulsos[s+co]=tres[s];
          }
          if(contadorEspacios[a]=='4'){
            pulsos[s+co]=cuatro[s];
          }
          if(contadorEspacios[a]=='5'){
            pulsos[s+co]=cinco[s];
          }
          if(contadorEspacios[a]=='6'){
            pulsos[s+co]=seis[s];
          }
          if(contadorEspacios[a]=='7'){
            pulsos[s+co]=siete[s];
          }
          if(contadorEspacios[a]=='8'){
            pulsos[s+co]=ocho[s];
          }
          if(contadorEspacios[a]=='9'){
            pulsos[s+co]=nueve[s];
          }
          if(contadorEspacios[a]=='0'){
            pulsos[s+co]=cero[s];
          }
        }
        co=co+8;
      }
      }
//////////////////////////////////////////////////////////////////
if(mostrarSensor==1 || primerMuestra==1){
  refre=30;
}
if(mostrarSensor!=1 && primerMuestra==0){
  refre=32;
}
         for(int k=0;k<3;k++)//Refresco de matriz
         {            
            for(int j=32;j>=0;j--)//Barrido de Columnas
            { 
              if(led==1){
                if(ledcont==900){
                  ledcont=0;
                  led=0;
                  digitalWrite(A0,LOW);
                }
                ledcont+=1;
              }
              if(buzzer==1){
                if(buzzercont==900){
                  buzzercont=0;
                  buzzer=0;
                  digitalWrite(A1,LOW);
                }
                buzzercont+=1;
              }
              if(digitalRead(53)==1 && mostrarSensor==0 && mostrarTarifa==0 && primerMuestra==0){
                 while(digitalRead(53)==1)
                {
                delay(220);
                }
                if(mostrarPagar==1){
                primero=1;
                reloj=0;
                mostrarPagar=0;
                mostrarMenus=0;
                 if(EEPROM[((contadorTarifa-1)*4)+1]==254){
                    banderazo=EEPROM[(contadorTarifa-1)*4]/100.00;
                  }
                  if(EEPROM[((contadorTarifa-1)*4)+1]!=254){
                  banderazo=((EEPROM[(contadorTarifa-1)*4]*100)+EEPROM[((contadorTarifa-1)*4)+1])/100.00;
                  }
                contadorSensor=0;
                }
                if(contando==1){
                contando=0;
                mostrarPagar=1;   
                }
                goto inicio;
              }    
              if(digitalRead(50)==1 && mostrarSensor==1){
                 while(digitalRead(50)==1)
                {
                delay(220);
                }
                mostrarSensor=0;
                primero=1;
                mostrarMenus=0;
                reloj=0;
                contadorSensor=0;
                goto inicio;           
              }
              if(digitalRead(50)==1 && mostrarTarifa==1){
                 while(digitalRead(50)==1)
                {
                delay(220);
                }
                mostrarMenus=0;
                mostrarTarifa=0;
                blue=1;
                goto inicio;           
              }
              if((digitalRead(53)==1 && mostrarTarifa==1) || (digitalRead(53)==1 && primerMuestra==1)){
                 while(digitalRead(53)==1)
                {
                delay(220);
                }
                if(EEPROM[((contadorTarifa-1)*4)+1]==254){
                  banderazo=EEPROM[(contadorTarifa-1)*4]/100.00;
                }
                if(EEPROM[((contadorTarifa-1)*4)+1]!=254){
                banderazo=((EEPROM[(contadorTarifa-1)*4]*100)+EEPROM[((contadorTarifa-1)*4)+1])/100.00;
                }
                if(EEPROM[(contadorTarifa*4)-1]==254){
                  tarifa=EEPROM[(contadorTarifa*4)-2]/100.00;
                }
                if(EEPROM[(contadorTarifa*4)-1]!=254){
                tarifa=((EEPROM[(contadorTarifa*4)-2]*100)+EEPROM[((contadorTarifa*4)-1)])/100.00;
                }
                mostrarTarifa=0;
                primero=1;
                mostrarMenus=0;
                reloj=0;
                primerMuestra=0;
                goto inicio;           
              }
              if(digitalRead(51)==1 && mostrarTarifa!=0){
                 while(digitalRead(51)==1)
                {
                delay(220);
                }
                if(primerMuestra==1){
                   contadorTarifa+=2;
                   if(contadorTarifa==11){
                    contadorTarifa=1;    
                   }
                   if(contadorTarifa==12){
                    contadorTarifa=2;    
                   }
                }  
                if(primerMuestra==0){
                mostrarTarifa=2;
                primerMuestra=1;
                }     
              }
              if(contando==1 || mostrarSensor==1){  
                  int cambioT=now.second()-segund;
                  int cambioporTimepo;
                  if(cambioT<0){
                    cambioporTimepo=60-((cambioT)*-1);
                  }
                  if(cambioT>-1){
                    cambioporTimepo=cambioT;
                  } 
                  if(cambioporTimepo==45){
                   banderazo=banderazo+tarifa;
                   digitalWrite(A0,HIGH);
                   led=1;
                   digitalWrite(A1,HIGH);
                   buzzer=1;
                  contadorSensor=0; 
                  now=rtc.now();
                  segund=now.second();
                  }
                if(contadorSensor0==1){
                   now=rtc.now();
                  segund=now.second();
                contadorSensor0=0;
                contadorSensor+=1;
                }
                if(contadorSensor==cambioPulsos && contando==1){
                  banderazo=banderazo+tarifa;
                  digitalWrite(A1,HIGH);
                  buzzer=1;
                  contadorSensor=0;
                }
              }
                   if(j<20){
               digitalWrite(j+30,HIGH);
              }
              if(j>19){
                digitalWrite(j-18,HIGH);
              }
               if(contando==1){
                PORTA=binaumento[j];
               }
               if(mostrarSensor==1 || primerMuestra==1){
               PORTA=pulsos[j];
               }
               if(mostrarPagar==1){
               PORTA=pagar[j];
               }
               if(mostrarTarifa==1){
               PORTA=tarifas[j];
               }
                delayMicroseconds(550);           //Demora de multiplexado
                 PORTA=B00000000;
              if(j<20){
               digitalWrite(j+30,LOW);
              }
              if(j>19){
                digitalWrite(j-18,LOW);
              }
               }
         }
    }
}
void sensor(){
  contadorSensor0=1;
}

Es que no lo puse completo por que es muy largo la verdad jajajajajaj y solo puse las partes donde muestro como lo hago, porque tengo dos versiones esta que es con un arduino mega 2560 sin usar un 74hc595 sino directo a todo los pines y tengo otro que si utilizo el 74hc595 pero ese codigo es pic.
y no se si halla mucha diferencia entre sacarle mas brillo usando el 74hc595 (que es el que mas me importa) o sin usarlo (hablando del lado del softaware).
no se si gustes tambien te paso el codigo del pic que es mucho mas simple porque este muestra y hace cosas muy distintas que el que tengo en el pic, la manera en que almaceno los datos y los muestro en la multiplexacion es la misma para ambas. pero no puse el codigo del pic porque no se si este permitido preguntar sobre pic que comparte codigo con arduino jejejeje

Muy rápidamente veo cosas como esta y te digo que vas por muy mal camino en un programa donde el problema es el brillo.
Vas a tener que dar un salto de calidad, millis(), máquina de estados, etc, como minimo y TIMER para controlar los leds y solo concentrarse en cuales se encienden y con que brillo.

La hoja de datos dice que la corriente pico de los leds es 200mA
Asi que debes garantizar que tus transitores drivers lo manejen sin problema y lo mismo para la fuente cuando actives todas las salidas simultaneas si fuera el caso.

muchas gracias @Surbyte lo voy a implimentar lo unico que nunca he usado es el TIMER se que existen 5 timer en arduino mega. cual de los 5 me podria ser mas util en estos caso? y que frecuencia seria utili usarlo?

El Timer que vas a usar es uno solo, no importa cual. Imagina que fuera Timer1 por elegir uno.
La frecuencia de trabajo puede ser por ejemplo 1Khz, pero en 1Khz o sea cada 1 mseg tu decides que hacer con tus leds. Cuento 7x7 leds.
Definirás un ciclo de trabajo, uno que te de ese pico de corriente respetando el Area de funcionamiento seguro del LED.
Olvidé un dato importante. Los 200mA dice que deben aplicarse asi
*Pulse width 0.1msec duty 1/10
Un ancho de pulso de 100 useg con un ciclo de trabajo del 10%.
Así que tienes 100useg en ON y 900 useg OFF para totalizar 1 mseg o sea 1Khz.

Se fija el timer del Arduino, y cuando se produce una interrupción se ejecuta la rutina del Timer que actualizas los puertos de todos los leds.
En todo momento tu solo dirás si se deben encender o apagar el bit de cada puerto.
Tal como ya lo haces en tu código.
Igualmente hay que hacer cuentas porque como usas los 595 que son por desplazamiento hay que considerar que todo lleva tiempo.
Estoy pensando en voz alta. si me permitís y puede que la frecuencia deba ser mayor para garantizar el barrido serial de todos los leds, digamos son 7 tramas.
Se debe garantizar esos 100useg en cada LED y no mas.

a ya muchisimas gracias en serio, gracias a todos pos su ayuda lo implementare, solo una duda mas, para aclarar, dentro de mi progama estoy ocupando una interrupcion externa

attachInterrupt(digitalPinToInterrupt(18), sensor, FALLING);
void sensor(){
  contadorSensor0=1;
}

que es esta, entonces por lo que entiendo el timer lo tengo que configurar a 1kHz y este timer funciona de igual manera que mi inturrepcion, tengo que crear una funcion para el timer y dentro de ese timer tengo que programar el encendio y el apagado de los leds, dando un ejemplo muy burdo:

void encendido(){
digitalWrite(25,HIGH);
delayMicroseconds(100);
}
void apagado(){
digitalWrite(25,LOW);
delayMicroseconds(900);
}

obviamente es super basico porque el contador que es el delay se cambia por los valores del timer o esos delay los cambio por millis()?

Si pero no.

No puedes usar delay() ni delayMicroseconds() dentro de una rutina de atención de interrupción.
Además la rutina tiene que ser lo más corta posible, muy rápida.

Cuando me pueda poner a verlo con tu esquema te lo explico mejor pero te doy la idea.

Si tienes que apagar los LED si o si antes de encender los siguientes, dentro de la misma rutina de interrupción, primero apagas los que ya están encendidos y luego enciendes los nuevos.

Lo que no tengo claro todavía (no pude dedicarme) es si realmente necesitas apagarlos como haces tu o si ya se apagan solos al cambiar de columna.

Dame un tiempo, pero piénsalo como te dije más arriba, olvidate de los delays que de eso se encarga el timer y apaga los LEDs encendidos justo antes de encender los siguientes.

Te dejo de muestra la rutina que uso para un cronómetro con display de 7 segmentos y 8 digitos sobre un Nano de los que solo uso 6 en esta versión (ya se que no es lo mismo que lo tuyo, es solo como ejemplo de como encaralo)

ISR(TIMER1_COMPA_vect){

  static byte dcount = 0; // contador de digitos, se incrementa con cada interrupción para apuntar al digito a mostrar
  byte lobyte, hibyte; // necesario para "repartir" un byte en 2 ports diferentes según a que PORT pertenece cada pin utilizado

// desactiva todos los cátodos (conectados a los pines analógicos del Nano, usados en modo digital)
  PORTC = (PORTC & 0xC0) | 0b00111111;  
// Actualiza los segmentos del digito actual
  lobyte = SEGMENTS[digits[dcount]]; // matriz donde almaceno los segmentos a encender para formar los dígitos
  lobyte |= (dpoints >> dcount) << 7;  // encender punto decimal? (Usa el punto como separador de min, seg y centésimas, dpoints es la máscara de bits que marca el punto de cual digito debe encender)
  hibyte = lobyte >> 6; // tomo los 2 bits superiores
  lobyte = lobyte << 2; // aislo los 6 bits inferiores y "acomodo" a su posición en el port
  PORTD = (PORTD & 0x03) | lobyte; // enciende parte de los segmentos
  PORTB = (PORTB & 0xFC) | hibyte; // y la otra parte
// Activa catodos en secuencia en A0 a A6 segun dcont (aquí realmente se encienden los segmentos)
  PORTC = (PORTC & 0xC0) | CATHODES[dcount];  // CATHODES almacena las mascaras bits para cada cátodo, podría simplemente desplazar bits pero así es más rápido
  dcount++;  // incrementa el digito para la proxima llamada
  dcount %= 6;  // pone a 0 cuando llega a 6
  
}

Te lo documenté lo mejor que pude, espero lo entiendas.

Como ves, los segmentos quedan encendidos hasta que llega la próxima interrupción que lo primero que hace es apagarlos al deshabilitar los cátodos.
En definitiva cada dígito está 1 mseg encendido y 5 mseg apagado pero el brillo es muy bueno y no hay parpadeo.
El tiempo de encendido se varía cambiando la frecuencia del timer, yo usé 1KHz porque lo uso de base de tiempo para el cronómetro pero en otras pruebas bajando hasta 150Hz no tenía parpadeo.
Como tienes muchas columnas vas a tener que trabajar con frecuencias altas, empieza con 1KHz a ver si no hay parpadeo.

Te dejo link a un Calculador de timer y lo que para mí es la biblia de las interrupciones

Saludos

1 Like

gracias en serio, ya me quedo mas claro, si me llegase a tener alguna duda no hay problema en que te contacte verdad?

Ninguno.

Saludos

PD: Te aclaro algo del código que me olvide y si lo mirás tal vez no entiendas.
SEGMENTS[ ] como dije almacena la máscara de bits para los segmentos pero la acceso con otro array como parámetro, digits[ ] que almacena los dígitos que tiene que mostrar siendo digits[5] las decenas de minutos y digits[0] las unidades de centésimas.
O sea, si tengo que mostrar "00:37:65" en digits[ ] están almacenados los valores 0; 0; 3; 7; 6; 5.
Es como tu buffer, bah. :wink:

Hola buenas noches, espero se encuentre muy bien
disculpe he estado intentado hacer lo que me dijeron y creo que si lo conseguí porque si brilla un poco mas sin uso de transistores.
Estoy ocupando como me dijeron con
duty 1/10, osea 100 micro segundo prendido y 900 micro segundos apagado totalizando 1 mili segundo.
lo que pasa es que ahora el brillo varia, es decir prender con poco luminosidad y se va haciendo mas brilloso hasta que llega al punto mas brilloso y vuelve a bajar el brillo y así sucesivamente pero de manera algo rápida, entre que empieza en poco brillo y llega al máximo brillo y vuelve a empezar ha de ser como 500 milisegundo aproximadamente, algo rápido pero si se llega a notar como va variando ese brillo.

 #include <TimerOne.h>
void setup() {
  pinMode(2,OUTPUT);pinMode(3,OUTPUT);pinMode(4,OUTPUT);pinMode(5,OUTPUT);pinMode(6,OUTPUT);pinMode(7,OUTPUT);pinMode(8,OUTPUT);pinMode(9,OUTPUT);pinMode(10,OUTPUT);pinMode(11,OUTPUT);
  pinMode(12,OUTPUT);pinMode(13,OUTPUT);pinMode(22,OUTPUT);pinMode(23,OUTPUT);pinMode(24,OUTPUT);pinMode(25,OUTPUT);pinMode(26,OUTPUT);pinMode(27,OUTPUT);pinMode(28,OUTPUT);pinMode(29,INPUT);
  pinMode(30,OUTPUT);pinMode(31,OUTPUT);pinMode(32,OUTPUT);pinMode(33,OUTPUT);pinMode(34,OUTPUT);pinMode(35,OUTPUT);pinMode(36,OUTPUT);pinMode(37,OUTPUT);pinMode(38,OUTPUT);pinMode(39,OUTPUT);
  pinMode(40,OUTPUT);pinMode(41,OUTPUT);pinMode(42,OUTPUT);pinMode(43,OUTPUT);pinMode(44,OUTPUT);pinMode(45,OUTPUT);pinMode(46,OUTPUT);pinMode(47,OUTPUT);pinMode(48,OUTPUT);pinMode(49,OUTPUT);
   pinMode(19,INPUT); pinMode(1,INPUT); pinMode(A2,OUTPUT);
  // put your setup code here, to run once:
Timer1.initialize(1000);         // Dispara cada 1 ms
Timer1.attachInterrupt(ISR_Prendido); 
//Serial.begin(19200);
}
int led=32,multiplexado=0,intervalo=1000;
unsigned long contador=0,previo=0;
void loop() {
  // put your main code here, to run repeatedly:
int const DECO[33]={B01111111,B01111111,B01000001,B01000001,B01000001,B01000001,B00100010,B00011100,B00000000,//D
                      B01111111,B01001001,B01001001,B01001001,B01001001,B01000001,B01000001,B00000000,//E
                      B00111110,B01000001,B01000001,B01000001,B01000001,B01000001,B00100010,B00000000,//C
                      B00111110,B01000001,B01000001,B01000001,B01000001,B01000001,B00111110,B00000000};//O
              for(int k=0;k<100;k++)//Refresco de matriz
         {  
               if(multiplexado==1){
                  contador=micros();
                  PORTA=DECO[led];
                  if(contador-previo>=1000){
                    PORTA=B00000000;
                    previo=contador;
                     if(led<21){
               digitalWrite(led+29,LOW);
              }
              if(led>20 && led<30){
                digitalWrite(led-19,LOW);
              }
              if(led>29 && led<32){
                digitalWrite(led-18,LOW);
              }
              if(led==32){
                digitalWrite(A2,LOW);
              } 
                 led-=1;
                if(led==0){
                  led=32;
                }
                multiplexado=0;
                  }
               }
                }
  }
  void ISR_Prendido (){ 
        if(led<21){
               digitalWrite(led+29,LOW);
              }
              if(led>20 && led<30){
                digitalWrite(led-19,LOW);
              }
              if(led>29 && led<32){
                digitalWrite(led-18,LOW);
              }
              if(led==32){
                digitalWrite(A2,LOW);
              } 
               
               if(led<21){
               digitalWrite(led+29,HIGH);
              }
              if(led>20 && led<30){
                digitalWrite(led-19,HIGH);
              }
              if(led>29 && led<32){
                digitalWrite(led-18,HIGH);
              }
              if(led==32){
                digitalWrite(A2,HIGH);
              } 
                multiplexado=1;
}

este es mi código utilice directamente la librería TimerOne, para llegar a ser un poco mas preciso en mis tiempo.
aquí solo estoy haciendo pruebas para ver que funcionara por lo que es el código completo de mi prueba. cuando este bien ya lo adaptare a mi código final que anteriormente les mande.
me podrían decir si estoy bien o no y en que estoy mal y que podría mejor.
muchas gracias por su atención

Las variables led y multiplexado las tienes que declarar como volatile

Saludos

listo y en cuanto a mi código, esta bien así?
porque he estado intentado jugar con los tiempo respetando los tiempos de encendido y apagado congruentes pero siempre obtengo ese brillo que varia, si disminuyo mas el tiempo de apagado se apaga por completo si lo hago mas rapido empieza a parpadear y lo mismo para el tiempo de encendido :frowning:

El código, así como lo presentas, cuesta mucho seguirlo. Edita y acomoda el texto del loop() respetando el indentado sino quita las ganas de leerlo (que quede como la ISR al menos).

Por otro lado, estuve leyendo tus comentarios anteriores y no entiendo el sentido de tener los LEDs encendidos solo 1/10 del tiempo. Si están 9/10 del tiempo apagados ¿cómo quieres que tengan buen brillo?

Saludos

Opino como @anon90500195, códigos no formateados (usa autoformat del IDE) me lleva mucho tiempo asi que paso de dar una devolución.
A modo de contribución solo lo ordené.

#include <Arduino.h>

#include <TimerOne.h>
void setup()
{
    for (int i=2; i<39; i++) {
        if (i =!14)
            pinMode(i, OUTPUT);
        else 
            i = 21;
    }
    pinMode(19, INPUT);
    pinMode(1, INPUT);
    pinMode(A2, OUTPUT);
    // put your setup code here, to run once:
    Timer1.initialize(1000); // Dispara cada 1 ms
    Timer1.attachInterrupt(ISR_Prendido);
    //Serial.begin(19200);
}

int led = 32, multiplexado = 0, intervalo = 1000;
unsigned long contador = 0, previo = 0;
void loop()
{
    // put your main code here, to run repeatedly:
    int const DECO[33] = {B01111111, B01111111, B01000001, B01000001, B01000001, B01000001, B00100010, B00011100, B00000000, //D
                          B01111111, B01001001, B01001001, B01001001, B01001001, B01000001, B01000001, B00000000,            //E
                          B00111110, B01000001, B01000001, B01000001, B01000001, B01000001, B00100010, B00000000,            //C
                          B00111110, B01000001, B01000001, B01000001, B01000001, B01000001, B00111110, B00000000};           //O
    for (int k = 0; k < 100; k++)                                                                                            //Refresco de matriz
    {
        if (multiplexado == 1)
        {
            contador = micros();
            PORTA = DECO[led];
            if (contador - previo >= 1000)
            {
                PORTA = B00000000;
                previo = contador;
                if (led < 21)
                {
                    digitalWrite(led + 29, LOW);
                }
                if (led > 20 && led < 30)
                {
                    digitalWrite(led - 19, LOW);
                }
                if (led > 29 && led < 32)
                {
                    digitalWrite(led - 18, LOW);
                }
                if (led == 32)
                {
                    digitalWrite(A2, LOW);
                }
                led -= 1;
                if (led == 0)
                {
                    led = 32;
                }
                multiplexado = 0;
            }
        }
    }
}
void ISR_Prendido()
{
    if (led < 21)
    {
        digitalWrite(led + 29, LOW);
    }
    if (led > 20 && led < 30)
    {
        digitalWrite(led - 19, LOW);
    }
    if (led > 29 && led < 32)
    {
        digitalWrite(led - 18, LOW);
    }
    if (led == 32)
    {
        digitalWrite(A2, LOW);
    }

    if (led < 21)
    {
        digitalWrite(led + 29, HIGH);
    }
    if (led > 20 && led < 30)
    {
        digitalWrite(led - 19, HIGH);
    }
    if (led > 29 && led < 32)
    {
        digitalWrite(led - 18, HIGH);
    }
    if (led == 32)
    {
        digitalWrite(A2, HIGH);
    }
    multiplexado = 1;
}