Display oled con libreria u8glib non stampa

Buongiorno a tutti stavo lavorando a questo progetto dove volevo gestire con un display oled e un sensore di temperatura una sorta di termostato dove posso impostare la temperatura per mezzo di un keypad, in caso ci fosse il riscaldamento attaccato mostro una fiammella animata in caso di aria condizionata un ghiacciolino. Il mio problema è che se metto le istruzioni semplicemente nel loop funziona perfettamente ma se metto un if per capire quale delle immagini mostrare stampa solo le variabili che contengono la temperatura e non il testo.Non allego tutta la parte delle bitmap perchè risulterebbe troppo lungo il codice, sto utilizzando la libreria u8glib non la 2.

byte rowPins[ROWS] = { 22, 23, 24, 25 };   // Pin per le righe
byte colPins[COLS] = { 26, 27, 28, 29 };  // Pin per le colonne
bool errore = 0, conditioner = 1, firstTime = 0;
char string[4];
char key, oldKey;
int Timp, num, progress;
float Teff;
unsigned long lastAgg;


U8GLIB_SH1106_128X64 u8g(U8G_I2C_OPT_NO_ACK);
Keypad keypad = Keypad(makeKeymap(keys), rowPins, colPins, ROWS, COLS);

void setup() {
  Serial.begin(9600);
  u8g.begin();
  u8g.setFont(u8g_font_9x15B);
  u8g.setColorIndex(1);
  setTemperature();
  setTeff();
}

void loop() {
  if(!firstTime){
    u8g.firstPage();
    do{
      progress = 0;
      delay(50);
      firstTime = 1;
    }while(u8g.nextPage());
  }
  u8g.firstPage();
  do{
    if(Teff > Timp + 3){
      u8g.drawBitmapP(0, 0, 128 / 8, 64, iceallArray[progress]);
    }
    if(Teff < Timp - 3){
      u8g.drawBitmapP(0, 0, 128 / 8, 64, fireallArray[progress]);
    }
    if(Teff >= Timp - 3 && Teff <= Timp + 3){
      u8g.drawBitmapP(0, 0, 128 / 8, 64, done_a_frm0_40);
    }
    u8g.setFont(u8g_font_6x10);
    u8g.drawStr(1, 15, "T. Impostata");
    u8g.drawStr(1, 45, "T. Rilevata");
    u8g.setFont(u8g_font_9x15B);
    if(Timp > 0){
      u8g.setPrintPos(15, 30);
    }else{
      u8g.setPrintPos(6, 30);
    }
    u8g.print(Timp);
    u8g.drawStr(30, 30, " C");
    if(Teff > 0){
      u8g.setPrintPos(15, 60);
    }else{
      u8g.setPrintPos(6, 60);
    }
    u8g.print(Teff);
    u8g.drawStr(60, 60, " C");
    if(millis() - lastAgg >= 200){
      progress = (progress + 1) % 28;
      lastAgg = millis();
    }
  }while(u8g.nextPage());
}

int stringToInt() {
  int somma = 0;
  switch (string[0]) {
    case '+':
      break;
    case '-':
      break;
    default:
      errore = 1;
      break;
  }
  for (int i = 1; i < 3; i++) {
    switch (string[i]) {
      case '0':
        num = 0;
        break;
      case '1':
        num = 1;
        break;
      case '2':
        num = 2;
        break;
      case '3':
        num = 3;
        break;
      case '4':
        num = 4;
        break;
      case '5':
        num = 5;
        break;
      case '6':
        num = 6;
        break;
      case '7':
        num = 7;
        break;
      case '8':
        num = 8;
        break;
      case '9':
        num = 9;
        break;
      default:
        errore = 1;
        break;
    }
    if (!errore) {
      somma = somma + (num * pow(10, 2 - i));
    }
  }
  switch (string[0]) {
    case '+':
      somma = somma;
      break;
    case '-':
      somma = somma * -1;
      break;
    default:
      errore = 1;
      break;
  }


  return somma;
}

void drawKeypad(int progress) {
  if (errore) {
    u8g.firstPage();
    do {
      u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_schermata_errore);
    } while (u8g.nextPage());
    delay(2000);
  } else {
    switch (progress) {
      case 0:
        if (string[0] == '-') {
          u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Prima_schermata_sistemi_con_il_meno);
        } else if (string[0] == '+') {
          u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Prima_schermata_sistemi_);
        }
        break;

      case 1:
        if (string[0] == '-') {
          u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Prima_schermata_sistemi_con_il_meno);
        } else if (string[0] == '+') {
          u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Prima_schermata_sistemi_);
        }
        u8g.setPrintPos(Position[0], 48);
        u8g.print(string[1]);
        break;

      case 2:
        if (string[0] == '-') {
          u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Prima_schermata_sistemi_con_il_meno);
        } else if (string[0] == '+') {
          u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Prima_schermata_sistemi_);
        }
        u8g.setPrintPos(Position[0], 48);
        u8g.print(string[1]);
        u8g.setPrintPos(Position[1], 48);
        u8g.print(string[2]);
        break;
    }
  }
}

void verificaCorrettezza(int progress, char tasto) {
  switch (progress) {
    case 0:
      if (tasto != '+' && tasto != '-') {
        errore = 1;
      }
      break;

    case 1:
      if (tasto == '+' || tasto == '-' || tasto == 'A' || tasto == 'B' || tasto == 'C' || tasto == 'D') {
        errore = 1;
      }
      break;

    case 2:
      if (tasto == '+' || tasto == '-' || tasto == 'A' || tasto == 'B' || tasto == 'C' || tasto == 'D') {
        errore = 1;
      }
      break;
  }
}

void setTemperature() {
  do {
    errore = 0;
    u8g.firstPage();
    do {
      u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Insert_screen);
    } while (u8g.nextPage());

    for (int i = 0; i < 3 && !errore; i++) {
      key = keypad.waitForKey();
      verificaCorrettezza(i, key);
      if (!errore) {
        string[i] = key;
        oldKey = key;
        delay(50);
      }
      u8g.firstPage();
      do {
        drawKeypad(i);
      } while (u8g.nextPage());
    }
    Timp = stringToInt();
  } while (errore);
  delay(1500);
}

void setTeff(){
  do {
    errore = 0;
    u8g.firstPage();
    do {
      u8g.drawBitmapP(0, 0, 128 / 8, 64, bitmap_Insert_screen);
    } while (u8g.nextPage());

    for (int i = 0; i < 3 && !errore; i++) {
      key = keypad.waitForKey();
      verificaCorrettezza(i, key);
      if (!errore) {
        string[i] = key;
        oldKey = key;
        delay(50);
      }
      u8g.firstPage();
      do {
        drawKeypad(i);
      } while (u8g.nextPage());
    }
    Teff = stringToInt();
  } while (errore);
  delay(1500);
}

Si prega di utilizzare la lingua inglese nella parte inglese del forum. La domanda è stata spostata nella parte italiana del forum.

Cioè dentro la do ... while se hai quei tre if per le bitmap, poi le 2 u8g.drawStr() non mostrano il testo ?

esatto, sul display viene l' immagine le due temperature ma non le scritte dei u8g.drawStr().

    //if(Teff > Timp + 3){
    //  u8g.drawBitmapP(0, 0, 128 / 8, 64, iceallArray[progress]);
    //}
    //if(Teff < Timp - 3){
    //  u8g.drawBitmapP(0, 0, 128 / 8, 64, fireallArray[progress]);
    //}
    //if(Teff >= Timp - 3 && Teff <= Timp + 3){
    u8g.drawBitmapP(0, 0, 128 / 8, 64, done_a_frm0_40);
    //}
    u8g.setFont(u8g_font_6x10);
    u8g.drawStr(1, 15, "T. Impostata");
etc

E se modifichi così cosa vedi ? (cioè togli if e fai solo una drawbitmap)

@pipposalva:

:warning:
Ti segnalo che, nella sezione in lingua Inglese, si può scrivere SOLO in Inglese ... quindi, per favore, la prossima volta presta più attenzione in quale sezione metti i tuoi post; questa volta esso è stato spostato, da un moderatore della sezione di lingua Inglese, nella sezione di lingua Italiana ... la prossima volta potrebbe venire direttamente eliminato. Grazie.

In quel caso mi mostra le informazioni correttamente

Prova così:

    if(Teff > Timp + 3) {
      u8g.drawBitmapP(0, 0, 128 / 8, 64, iceallArray[progress]);
    } else if(Teff < Timp - 3) {
      u8g.drawBitmapP(0, 0, 128 / 8, 64, fireallArray[progress]);
    } else {            //non serve if(Teff >= Timp - 3 && Teff <= Timp + 3)
      u8g.drawBitmapP(0, 0, 128 / 8, 64, done_a_frm0_40);
    }
    u8g.setFont(u8g_font_6x10);
    u8g.drawStr(1, 15, "T. Impostata");

Non credo cambia ma almeno non hai il terzo if.

P.S. penso che non ha senso per quel sensore 2 decimali su temperatura effettiva, essendo una print classica, per float, secondo parametro=numero decimali, default=2, passa 1
u8g.print(Teff,1);

Ho provato a sostituire con la sua condizione ma il problema persiste, stampa le misurazioni e l'animazione senza problemi ma le stringhe se le perde.

Tentativi:

  1. prova a mettere stampa bitmap DOPO il pezzo in cui stampi valori+testo

  2. visto che puoi usare setPrintPos e print, anche x la frase fissa usa:
    u8g.setPrintPos(1,15); u8g.print("T. Impostata");
    invece di:
    u8g.drawStr(1, 15, "T. Impostata");

È questa la riga che visualizza la fiammella?
Mi stupisce il fatto che x, y siano 0, 0 e che l'icona sia grande w16 x h64. Potrei facilmente pensare che l'icona è grande w128 x h64 e allora e normale che cancella tutto e sopra poi ci scrivi i valori.

PS: sono imbastardito dalle tante librerie oled e quindi non mi ricordo i dettagli di u8glib.

Io quella fiammella se voglio visualizzarla in quella posizione ad occhio x vale 88 e y zero.

Ciao.

il problema persiste comunque.

si l'icona è grande 128 e 64 perchè ho generato la bitmap su tutto lo schermo perchè mi dava problemi nello stampare soltanto un 50x50 e dopo il 128/8 l'ho trovato online e non ho compreso del tutto il motivo ma se metto semplicemente 128 non funziona correttamente, comunque dubito che il problema sia la grandezza della bitmap perchè se non metto l'if non da problemi ma funziona perfettamente.

Una prova la farei, al posto della animazione ci metti una icona fissa, nella giusta posizione x, y. Ad esempio questa icona:

const uint8_t rook_bitmap[] PROGMEM = {
  0x00,         // 00000000 
  0x55,         // 01010101
  0x7f,          // 01111111
  0x3e,         // 00111110
  0x3e,         // 00111110 
  0x3e,         // 00111110
  0x3e,         // 00111110 
  0x7f           // 01111111
};
u8g.drawBitmapP( 0, 0, 1, 8, rook_bitmap);

Cosi siamo sicuri di non sforare la ram, se funziona il problema è da ricercare nell'animazione.

Ciao.

ho provato un po' anche usando delle immagini delle immagini fisse e ho scoperto che così non mi danno problemi mentre se uso l'animazioni si, può essere un problema legato alla memoria? Perchè avevo già optato per un Arduino mega dato che l'uno non aveva abbastanza memoria flash per tutte le bitmap salvate con progmem, ho visto che lei accennava alla ram forse i problemi sono dovuti a quella?

Se ci sono problemi di flash o ram dopo la compilazione dovrebbe dirti la dimensione di flash e di ram occupata.
Come ho scritto, ci sono tante librerie grafiche inclusa quella che ho scritto io per me, e ognuno fa a modo suo, ad esempio per disegnare la bitmap specifico la dimensione in pixel orizzontale (width) e quella verticale (height), quindi con la tua immagine 128 x 64, scrivere 128, 64 nella chiamata a funzione. u8glib invece vuole la dimensione orizzontale in byte, quindi 128 / 8 da 16 byte orizzontale.

Risolto e compreso perché 128 / 8, mi chiedo di quanti frame è composta l'animazione, leggendo il codice arrivo a dedurre 29 frame che se sono tutti grandi 128x64 ognuno richiede 1024 byte di flash, la mega offre 256K e quindi non ci dovrebbe essere alcun problema.

Vedo anche che usi due modi differenti di scrivere il testo, io proverei ad usare il metodo che funziona per scrivere il valore anche per visualizzare l'etichette T. Impostata se possibile.

La cosa che mi sorprende è che se ogni frame e grande 128 x 64, quando viene disegnato sovrascrive l'area dove compare il testo con pixel neri, cioè cancella le scritte. L'effetto dovrebbe essere ben visibile come un fastidioso "sfarfallio", inoltre c'è un consumo di cicli cpu che forse non ti servono poiché l'applicazione è semplice.

Io posso quasi passare per ossessionato nei confronti dei cicli cpu sprecati, tanto che se già una digitalWrite è stata eseguita in un ciclo trovo il modo di non eseguirla nei cicli successivi. Figuriamoci se ho scritto sul display 20.5 e al secondo ciclo il valore è sempre lo stesso che lo scrivo a fare. Però come vedi qui:

il risultato è ottimo.

Ciao.

1 Like

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.