Go Down

Topic: MAX7219 con 4 display 7 segmenti (Read 840 times) previous topic - next topic

milefori

Buona giornata ragazzi
ho costruito un contattore con 4 display 7 segmenti con il max 7219 ed un Arduino nano il tutto e alimentato con alimentazione esterna,
utilizzo la libreria LedControl,

il tutto funziona,
pero vi chiedo cortesemente se potete spiegarmi due cose:

una e questo "difetto" se do tensione al tutto, si accendono i primi tre display non il quarto,
come inserisco l'usb al pc si accende il quarto,
non capisco come mai,

la seconda cosa riguarda il calcolo delle unita, decine, centinaia migliaia,
posto il codice
Code: [Select]
tmp = cunter;
  unita = tmp % 10;
  tmp = tmp / 10;
  decine = tmp % 10;
  tmp = tmp / 10;
  centinaia = tmp % 10;
  tmp = tmp / 10;
  migliaia = tmp % 10;
  tmp = tmp / 10;


mi sembra un po laborioso,
esiste un modo per renderlo più snello?

ringrazio anticipatamente chi mi può aiutare



Standardoil

#1
May 11, 2019, 05:52 pm Last Edit: May 11, 2019, 05:53 pm by Standardoil
per il problema display spento non saprei, forse vedendo tutto il programma
invece per le unità decine etc etc...
dovresti passare per un array e ciclarlo
una cosa del tipo

Code: [Select]

byte cifre[4];
.
.
.

tmp=counter;
for (byte i=0; i<4:i++)
{
   cifre[i]=tmp%10;
   tmp=tmp/10;
}



che se metti all'inizio una cosa un po' "fuori dalle righe" tipo questa:
Code: [Select]

#define unita cifre[0]
#define decine cifre[1]
#define centinaia cifre[2]
#define migliaia cifre[3]


nianche ti accorgi di usare un vettore
per curiosità, cosa stai facendo?
Non presurrò più la buona fede di chi:
NON indenta, USA la classe String o NON esegue le ricerche
E di chi non risponde alle domande Tante volte è stato segnalato che è sbagliato, quindi NON sono in buona fede
Non bado a studenti, che copino altrove

milefori

Ciao Standardoil grazie di avermi risposto,

ecco il programma per testare il MAX
Code: [Select]

#include "LedControl.h"
#define buton_1 2
#define buton_2 3

LedControl lc = LedControl(12, 11, 10, 1);

unsigned long delaytime = 250;
int cunter = 0;
int unita = 0;
int decine = 0;
int centinaia = 0;
int migliaia = 0;
int tmp = 0;

void setup() {
  Serial.begin(9600);

  lc.shutdown(0, false);
  lc.setIntensity(0, 10);
  lc.clearDisplay(0);

  pinMode(buton_1, INPUT_PULLUP);
  pinMode(buton_2, INPUT_PULLUP);
}

void loop() {

  if (digitalRead(buton_1) == 0) {
    cunter++;
  }
  else if (digitalRead(buton_2) == 0) {
    cunter--;
  }

  tmp = cunter;
  unita = tmp % 10;
  tmp = tmp / 10;
  decine = tmp % 10;
  tmp = tmp / 10;
  centinaia = tmp % 10;
  tmp = tmp / 10;
  migliaia = tmp % 10;
  tmp = tmp / 10;

  lc.setDigit(0, 3, (byte) migliaia, false);
  lc.setDigit(0, 2, (byte) centinaia, false);
  lc.setDigit(0, 1, (byte) decine, false);
  lc.setDigit(0, 0, (byte) unita, false);

  if (cunter > 9999) cunter = 0;
  delay(10);

}


grazie del consiglio per array,
non sono un esperto informatico ma ci provo poi ti so dire,

Quote
per curiosità, cosa stai facendo?
allora spiego cosa vorrei fare,
stampare su 3 display 7 segmenti la temperatura letta da un DS18B20,
oviamente c'è un problema "per me" che la temperatura e un float, mentre per stamare su display devo avere un int,

ora quello che so fare e,
Code: [Select]

int numero;
float reale;

reale = 47.19;
numero = (int)reale;

e fin qui credo vada bene, il problema e come prendere il decimale,
i tuoi consigli mi sarebbero moto preziosi



Standardoil

sarebbero preziosi anche un po'di accenti, ma vabbe'
ma cosa centrano i bottoni con la temperatura?
quello che hai mostrato qui è un contatore-decontatore
per i decimali, basta che decidi quante cifre vuoi avere dopo la virgola
e ragioni in decimi/centesimi/millesimi
per esempio se vuoi leggere i decimi moltiplichi la lettura per 10 e metti una virgola accesa fissa in seconda posizione
se ragioni in centesimo moltiplichi per cento e metti una virgola fissa in terza posizione
si chiama "aritmetica in virgola fissa", si contrappone alla "aritmetica in virgola mobile" dove mobile in inglese viene reso come "floating" (flottante) ecco quindi le variabili float
mah, un po' di teoria prima non farebbe male
Non presurrò più la buona fede di chi:
NON indenta, USA la classe String o NON esegue le ricerche
E di chi non risponde alle domande Tante volte è stato segnalato che è sbagliato, quindi NON sono in buona fede
Non bado a studenti, che copino altrove

milefori

Ciao ho seguito il tuo consiglio per le unità, decine ecc. logicamente funziona che e una meraviglia,

Code: [Select]
ma cosa centrano i bottoni con la temperatura?
niente, era solo per provare se il tutto funziona,

per i decimali forse non mi sono spiegato bene,

per leggere il DS18B20 la libreria mi da un dato float,
mentre la libreria  LedControl accetta solo dati int,

allora se faccio un casting ottengo la parte intera senza il decimale,
ma per avere il decimale int non so come fare

Standardoil

Ciao ho seguito il tuo consiglio per le unità, decine ecc. logicamente funziona che e una meraviglia,


per i decimali forse non mi sono spiegato bene,

punto 1) lo sapevo, grazie per il karma
Punto 2) ti sei spiegato benissimo, è leggere che non ti è uscito bene...
Non presurrò più la buona fede di chi:
NON indenta, USA la classe String o NON esegue le ricerche
E di chi non risponde alle domande Tante volte è stato segnalato che è sbagliato, quindi NON sono in buona fede
Non bado a studenti, che copino altrove

milefori

Scusami per il Karma, provvedo subito

elrospo

#7
May 13, 2019, 06:45 pm Last Edit: May 13, 2019, 06:51 pm by elrospo
Ciao ho seguito il tuo consiglio per le unità, decine ecc. logicamente funziona che e una meraviglia,

Code: [Select]
ma cosa centrano i bottoni con la temperatura?


ma per avere il decimale int non so come fare
prima di spedire il tutto al display devi trasformare  il numero in int moltiplicandolo per 100

poi lo processi con il solito sistema
questo puo andare

unita = tmp % 10;
  tmp = tmp / 10;
  decine = tmp % 10;
  tmp = tmp / 10;
  centinaia = tmp % 10;
  tmp = tmp / 10;
  migliaia = tmp % 10;

spedisci al display solo le tre cifre che ti interessano
e la cifra centrale deve sempre avere il punto acceso
qualcosa del genere

    lc.setDigit(0,0,(byte)decine ,false),
    lc.setDigit(0,1,(byte)centinaia ,true),  // punto decimale acceso
    lc.setDigit(0,2,(byte)migliaia ,false);
 

Maurotec

#8
May 13, 2019, 07:35 pm Last Edit: May 13, 2019, 07:39 pm by Maurotec Reason: Ci rinuncio ad incolonnarle.
In effetti osservando il codice di quella libreria si nota come si preoccupa in modo essenziale di controllare uno più display tramite il MAX. Fornisce delle primitive essenziali che risultano poco pratiche, pertanto servirà creare delle funzioni ad hoc più pratiche da usare in base all'applicazione.

Per praticità si potrebbe iniziare a creare una funzione che visualizza il dato sul display.
dato sara un intero con o senza segno, se è con segno servirà accendere il - negativo sacrificando un display e non potendo visualizzare 9999 ma -999, solo tre cifre.

Stessa cosa andrebbe fatta per visualizzare un numero in virgola mobile:

X = digit spento, # digit

#  #  #   #  
X X  0.  1
X X  0.  2
X X  0.  3
ecc
9. 9  9   9
-   9. 9   9
-   9  9.  9


Ciao.

Standardoil

prima di spedire il tutto al display devi trasformare  il numero in int moltiplicandolo per 100

.
.
.

unita = tmp % 10;
  tmp = tmp / 10;
  decine = tmp % 10;
  tmp = tmp / 10;
  centinaia = tmp % 10;
  tmp = tmp / 10;
  migliaia = tmp % 10;

che è la stessa cosa che gli avevo detto io, con in meno la gestione di un array invece che 4 variabili slegate
Non presurrò più la buona fede di chi:
NON indenta, USA la classe String o NON esegue le ricerche
E di chi non risponde alle domande Tante volte è stato segnalato che è sbagliato, quindi NON sono in buona fede
Non bado a studenti, che copino altrove

milefori

La modalità di calcolo suggeritami da Standardoil mi piace e funziona,
ora approfitto della vostra disponibilità per chiedere due cose,

1°) sul MAX c'è un piedino siglato DP che presumo sia per pilotare il punto, non riesco a trovare in libreria la
     funzione per portare alto quel piedino, cortesemente qualcuno sa come fare?
2°) mi rimane sempre quel problema del display collegato ad il pin DIG0 che all'avvio non si attiva, ma se inserisco l'usb di programmazione si attiva, oppure se premo un pulsante.

mille grazie a tutti per il vostro tempo che mi dedicate

Maurotec

Quote
1°) sul MAX c'è un piedino siglato DP che presumo sia per pilotare il punto, non riesco a trovare in libreria la
     funzione per portare alto quel piedino, cortesemente qualcuno sa come fare?
Come ti hanno suggerito non funziona?
Code: [Select]
lc.setDigit(0, 2, (byte) centinaia, true);

Quote
2°) mi rimane sempre quel problema del display collegato ad il pin DIG0 che all'avvio non si attiva, ma se inserisco l'usb di programmazione si attiva, oppure se premo un pulsante.
Hai allegato schema?


milefori

Ciao Maurotec

Code: [Select]
Come ti hanno suggerito non funziona?
Si funziona bene, leggo il DS18B20 e stampo su tre display, il punto decimale per ora l'ho collegato con una resistenza da 330ohm  a Vcc, perche non so come attivare il piedino DP del MAX,

allego lo schema

Maurotec

#13
May 15, 2019, 08:32 pm Last Edit: May 15, 2019, 08:38 pm by Maurotec
Quote
perche non so come attivare il piedino DP del MAX
Dallo schema il pin DP del MAX non è collegato ai 4 display per questo non si accende. Pertanto collega i 4 DP di ogni digit assieme e poi connettilo al DP del MAX. Ogni digit è composta da 7 segmenti per comporre il simbolo, più 1 per il punto, in totale 8 segmenti.

Dopo, il punto per ogni digit lo accendi con:
Code: [Select]

lc.setDigit(0, 2, (byte) centinaia, true);    // true accende DP sul digit 2

e lo spegni con:
Code: [Select]

lc.setDigit(0, 2, (byte) centinaia, false);    // false spegne DP sul digit 2


Rimane da capire come mai DIG0 lavora solo con USB.


Standardoil

beh, visto che dallo schema DG0 manco c'è...
sarebbe bene che lo OP, dopo aver magicamente messo a posto la sua ortografia mettesse a posto anche lo schema e ci desse l'ultima e aggiornata versione di schema e programma
così magari qualcosa si capisce
Non presurrò più la buona fede di chi:
NON indenta, USA la classe String o NON esegue le ricerche
E di chi non risponde alle domande Tante volte è stato segnalato che è sbagliato, quindi NON sono in buona fede
Non bado a studenti, che copino altrove

Go Up