char array und pointer

Ich und die Pointer... das wird wohl nix mehr.

Mein Ziel:
Ich habe einige Icons definiert, die ich auf einem Display ausgeben will.
Aufbau wie folgt. Ico1 ist nur ein Beispiel, Es gibt noch Ico2, Ico3,....

const char Ico1[] PROGMEM{
   0xff, 0xff, 0x00, 0xff, 0xff, 0x00, 0x83, 0xc1, 0x00, 0x86, 0x61, 0x00,
};

Die Ausgabe aufs Display sieht so aus:

display.drawXbm( 0, 0, 24, 24, Ico1);

Die Auswahl, welches Icon angezeit werden soll, hängt von einer Integer Variable ab, und soll zur Laufzeit erfolgen.
Welche Möglichkeiten habe ich:
1.) Mit einer Case-Anweisung immer eine andere display.drawXbm-Anweisung ausführen. (Viel Code)
2.) In der display.drawXbm einen variablen Zeiger auf die Icons. Ja nur wie?
Ich hätte es jetzt mal so probiert:

  char* myIcon = Ico1  // oder Ico2, oder .....;
display.drawXbm( 0, 0, 24, 24, myIcon);

Aber da bleibt ein invalid conversion. Und wenn ich const char* myIcon nehme, dann habe ich wohl nicht viel gewonnen...
3.) Gäbe es so etwas? (Pseudocode)

 int i = 3 // meine Auswahlvariable;
display.drawXbm( 0, 0, 24, 24, Ico(x));

Hab mal weiter probiert.

  int ptr = (int)Ico1;
  Serial.println (ptr);
  display.drawXbm( 0, 0, 24, 24, *ptr);

Mit der ersten Zeile bekomme ich imho die Speicherstelle des Arrays in den Pointer.
Aber wie aoll ich das in dem Aufruf wieder dereferenzieren?
So wie oben getippt gehts nicht :frowning:

Kann dein display.drawXbm() überhaupt mit Pointern ins Progmem umgehen?
Wenn "Ja!", woher weißt du das?
Wenn "Weiß nicht!", dann mache dich schlau.
Wenn "Nein!", dann sägst du am falschen Ast.

Ich kenne drawXBM anstelle drawXbm, aus welcher Bibliothek stammt das?

Hallo,

benötigst du wirklich Zeiger? Ich denke eher nicht.

const byte icon[] PROGMEM{0xff, 0xff, 0x00, 0xff, 0xff, 0x00, 0x83, 0xc1, 0x00, 0x86, 0x61, 0x00};

void setup() {
  Serial.begin(9600);
  
  byte sum_icon = sizeof(icon)/sizeof(icon[0]);

  Serial.println(sum_icon);

  for (byte i=0; i<sum_icon; i++) {
    Serial.print("Index: ");
    Serial.print(i); Serial.print('\t');
    byte data = pgm_read_byte(icon+i);
    Serial.println(data);
  }
}

void loop() {

}

benötigst du wirklich Zeiger? Ich denke eher nicht.

pgm_read_byte(icon+i);
Das ist Zeigerartithmetik in Reinform.

Hallo,

okay, für mich nicht ganz offentsichtlich, also versteckt.
Hat er dann was er möchte oder noch nicht?

Doc_Arduino:
Hat er dann was er möchte oder noch nicht?

Ich glaube, er möchte das Ikon auf dem Display anzeigen.

na das sollte hk007 alleine hinbekommen

okay, für mich nicht ganz offentsichtlich, also versteckt.

byte arr_b[] = {1,2,3};
int  arr_i[] = {1,2,3};


byte * next_b = arr_b+1; // next_b zeigt auf das 2te Element 
int *  next_i = arr_i+1; // next_i zeigt auf das 2te Element

Das +1 setzt also den Zeiger einmal um 1 Byte weiter, und das andere mal um 2 Byte

pgm_read_byte(icon+i); // icon ist ein Zeiger.
pgm_read_byte(&icon[i]); // macht genau das gleiche
pgm_read_byte(&i[icon]); // macht auch genau das gleiche (auch wenn es etwas krank aussieht)

Jeder nackte Array Bezeichner ist ein Zeiger.

na das sollte hk007 alleine hinbekommen

Wollen wir es mal hoffen...

Ohne PROGMEM sehe ich eine Grafik, ohne allerdings erkennen zu können, was das sein soll. Grundsätzlich geht das mit dem Zeiger.

Für das, was Du machen möchtest, benötigst Du wahrscheinlich ein Feld aus Zeigern, über die Du per Index die gewünschte Grafik auswählst.

PROGMEM bei "Arrays of strings".

agmue:
Für das, was Du machen möchtest, benötigst Du wahrscheinlich ein Feld aus Zeigern, über die Du per Index die gewünschte Grafik auswählst.

Yep, genau das wars: :slight_smile: :slight_smile: :slight_smile:

const char WiFi_1_ico[] PROGMEM{0xff, 0xff, 0x00, 0xff, 0xff,.....}
..und noch 4 andere

const char* const WiFi_ico[] PROGMEM = {WiFi_0_ico, WiFi_1_ico, WiFi_2_ico, WiFi_3_ico, WiFi_4_ico, WiFi_5_ico};

display.drawXbm( 0, 0, 24, 24, WiFi_ico[x]);

Jetzt kannich mit dem Index die gewünschte Grafik anzeigen

Ich kenne drawXBM anstelle drawXbm, aus welcher Bibliothek stammt das?

ESP8266_Oled_Driver_for_SSD1306_display