Вывод минут и секунд на LED матрицу

Adeni
Offline
Зарегистрирован: 26.01.2014

Есть матрица 40х8 на 5 микросхемах MAX7219. Необходимо выводить на нее минуты:секунды:тысячные доли.

Для начала решил вывести только минту и секнды, и столкнулся с проблемой. Такое ощущение что программа тормозит. На матрицу время выводится, но только каждые 11 секунд, т.е. сначала отображается 0:00, затем 0:11, затем 0:22 и т.д. Никак не могу понять, почему такая задержка происходит. Вот скетч, может кто подскажет, что я сделал не так?

#include <LedControl.h>
const int numDevices = 5;      // количество микросхем MAX7219

LedControl svetofor1=LedControl(12,11,10,numDevices);

byte n9[5]={
  B01100000,B10010010,B10010010,B10010100,B01111000}; //Цифра 9 
byte n8[5]={
  B01101100,B10010010,B10010010,B10010010,B01101100}; //Цифра 8
byte n7[5]={
  B11000000,B10000000,B10001110,B10010000,B11100000}; //Цифра 7
byte n6[5]={
  B00111100,B01010010,B10010010,B10010010,B00001100}; //Цифра 6
byte n5[5]={
  B11100100,B10100010,B10100010,B10100010,B10011100}; //Цифра 5
byte n4[5]={
  B00011000,B00101000,B01001000,B11111110,B00001000}; //Цифра 4
byte n3[5]={
  B10000100,B10000010,B10100010,B11010010,B10001100}; //Цифра 3
byte n2[5]={
  B01000010,B10000110,B10001010,B10010010,B01100010}; //Цифра 2
byte n1[5]={
  B00000000,B00000000,B01000010,B11111110,B00000010}; //Цифра 1
byte n0[5]={
  B01111100,B10001010,B10010010,B10100010,B01111100}; //Цифра 0
byte dv[3]={
  B00000000,B01101100,B00000000}; //Символ : 

byte times[17];//40 Сюда записываем итоговое время

void setup(){
  Serial.begin(9600);
  for (int x=0; x<numDevices; x++){
    svetofor1.shutdown(x,false);       //Включаем микросхемы
    svetofor1.setIntensity(x,13);       // Устанавливаем яркость
    svetofor1.clearDisplay(x);         // Очищаем матрицу
  }
}

void loop(){
  milistosec();
}

void milistosec(){ 
  //num=0;
  long tm=millis();
  int minut = tm/60000;//Вычисляем минуты
  char stringminut[2];
  itoa(minut,stringminut,10);//Преобразуем число в строку
  int lenminut = strlen(stringminut);//Определяем сколько символов в минутах
  //Вычисляем секунды
  int secund = (tm %60000)/1000;
  char stringsecund[2];
  itoa(secund,stringsecund,10);//Преобразуем число в строку
  int lensecund = strlen(stringsecund);//Определяем сколько символов в секундах
  //Вычисляем тысячные доли секунды
  int tyssec = (tm %60000)%1000;
  char stringtyssec[3];
  itoa(tyssec,stringtyssec,10);//Преобразуем число в строку
  int lentyssec = strlen(stringtyssec);//Оопределяем сколько символов в сотых секундах*/
  int s7=minut;//Первая цифра - минуты
  int s5=secund/10;//Вторая цифра секунды
  int s4=secund%10;//Третья цифра секунды
  int s2=tyssec/100;//Четвертая  цифра десятые доли
  int s1=(tyssec%100)/10;//Пятая цифра сотые доли
  int s0=((tyssec%100)%10)%10;//Шестая цифра тысячные доли

  casenumber(s7,0); //Записываем минуты
  times[5]=dv[0];times[6]=dv[1];times[7]=dv[2]; //Записываем двоеточие
  casenumber(s5,8); //Записываем первое число секунд
  times[13]=B00000000;//Вставляем пробел между числами
  casenumber(s5,14);//Записываем второе число секунд
  //times[19]=dv[0];
  //times[20]=dv[1];
  //times[21]=dv[2];
  //casenumber(s5,22);
  //times[27]=B00000000;
  //casenumber(s5,28);
  //times[33]=B00000000;
  //casenumber(s5,34);
  //times[39]=B00000000;
  //times[40]=B00000000;

  /*-------------------------------------------------*/
  int column=0;
  for (int j=0;j<8;j++){// Выводим минуты и секунды на матрицу
    svetofor1.setColumn(4,j,times[column]);
    svetofor1.setColumn(3,j,times[column+8]);
    svetofor1.setColumn(2,j,times[column+16]);
    //svetofor1.setColumn(1,j,times[column+24]);
    //svetofor1.setColumn(0,j,times[column+32]);
    column++;
  }  
}

void casenumber(int n,int tcol){//Определяем поступившую цифру, и заносим ее бинарное значение в массив
  //int tcol=ttcol;
  switch(n){
  case 0:
    for (int col=0;col<5;col++){
      times[tcol] = n0[col];
      tcol++;
    }
    break;
  case 1:
    for (int col=0;col<5;col++){
      times[tcol] = n1[col];
      tcol++;
    }
    break;
  case 2:
    for (int col=0;col<5;col++){
      times[tcol] = n2[col];
      tcol++;
    }
    break;
  case 3:
    for (int col=0;col<5;col++){
      times[tcol] = n3[col];
      tcol++;
    }
    break;
  case 4:
    for (int col=0;col<5;col++){
      times[tcol] = n4[col];
      tcol++;
    }
    break;
  case 5:
    for (int col=0;col<5;col++){
      times[tcol] = n5[col];
      tcol++;
    }
    break;
  case 6:
    for (int col=0;col<5;col++){
      times[tcol] = n6[col];
      tcol++;
    }
    break;
  case 7:
    for (int col=0;col<5;col++){
      times[tcol] = n7[col];
      tcol++;
    }
    break;
  case 8:
    for (int col=0;col<5;col++){
      times[tcol] = n8[col];
      tcol++;
    }
    break;
  case 9:
    for (int col=0;col<5;col++){
      times[tcol] = n9[col];
      tcol++;
    }
    break;
  } 
}

 

NeiroN
NeiroN аватар
Offline
Зарегистрирован: 15.06.2013

Програмный SPI - тормозная штука, ножно аппаратный использовать и программу максимально оптимизировать - может тогда и тысячные будет видно. Хотя мне кажется дальше сотых не получится...

Adeni
Offline
Зарегистрирован: 26.01.2014

Аппаратный SPI это, как я понимаю, выход ICSP на Leonardo ?

#include <SPI.h>

SPI.begin();

  digitalWrite(slaveSelectPin,LOW);
  SPI.transfer(address);
  SPI.transfer(value);
  digitalWrite(slaveSelectPin,HIGH); 

 

Adeni
Offline
Зарегистрирован: 26.01.2014

Никак не понимаю как напрямую с микросхемой работать. Т.е. как зажечь скажем 3-ю строку на всех 5 матрицах я понял, а вот как допустим зажечь ту же 3-ю строку только на 2 матрице, никак не пойму. В интернете вычитал по параметр No-op, но как его правильно применять сам не могу допенькать, и простых примеров не нахожу.

Adeni
Offline
Зарегистрирован: 26.01.2014

Решил проблему использованием другой библиотеки, нарытой на просторах интернета. Она работает шустро и о тормозах никаких намеков.

Вот тут описание и файлы для скачивания:

 https://www.pjrc.com/teensy/td_libs_Matrix.html