Forum: Compiler & IDEs [CodeVision] variablen C struct in Funktion übergeben für Menübeschreibung


von Christoph S. (mcseven)


Lesenswert?

Hi *,

ich stehe vor folgendem Problem:
Ich habe eine Grafikroutine, die soll ein (Text-)Menü mit mehreren 
Auswahlmöglichkeiten zeichnen. Außerdem ist die Routine animiert, das 
bedeutet, ich muß ihr mehrere Texte übergeben, die dann immer Pixelweise 
verschoben werden.

Das Problem ist, dass jedes Menü unterschiedlich ist, mal sind es 10 
Möglichkeiten, mal nur 5.

Ein Struct dagegen ist ja mehr oder weniger fest definiert.

Struktur im Menü:
{
  unsigned char Menueueberschrift[10];
  unsigned char AnzahlMenueItems;
  unsigned char Menueitems[][10]; //Das mag der CodeVision nicht, ein
  // char-array muss in jeder dimension festgelegt werden,
  // also z.B. Menuitems[5][10]
  // würde aber ne gigantische Platzverschwendung, wenn ich mal
  // ein menü mit nur einem statt 5 items hätte
}

Also z.B.
{
  "TESTHead1"
  2
  {"Test12345", "Test15"}
}

aber auch
{
  "TESTHead2"
  4
  {"Test12349", "Test17", "Test14", "Test1"}
}

Selbstverständlich könnte man die Anzahl der Items irgendwo 
rausbekommen, ich weiß nur nicht mit welcher Funktion. Aber wie kann ich 
so einen "variablen" struct definieren und wie sähe die 
Funktionsdefinition aus?

void glcd_drawMenu(flash struct *lalala, char oldItem, char 
selectedItem) {
  //tu was
}

Anmerkung: die beiden Chars brauche ich für die Animation, damit ich 
weiß, von wo nach wo ich scrollen muss...

Danke,
Christoph

von T. H. (pumpkin) Benutzerseite


Lesenswert?

Machs mit einer verketteten Liste.

von Christoph S. (mcseven)


Lesenswert?

Und wie definiere ich in nem Struct ne verkettete Liste, bzw. wie 
definiere ich im Programmspeicher die Daten für die verkettete Liste?

von Jörg W. (dl8dtl) (Moderator) Benutzerseite


Lesenswert?

Du kannst ein array of pointers machen:

const char *s[] = { "Hi", "low", "foo", "bar"};

Wenn du das aber zum Bestandteil einer struct machen willst, dann
setzt das voraus, dass der Compiler "flexible array members" gemäß
C99 kennt (GCC, in dessen Forum du ja postest, kann das), und dieses
Array muss sich am Ende der struct befinden.  Leider lässt sich der
Trick "sizeof(array) / sizeof(array[0])" für ein solches in der
Initialisierung nicht anwenden, du musst die Elemente also schon
mit der Hand zählen.

Der Speicherplatz für die Strings selbst wird dabei vom Compiler
anonym belegt, und es wird nur ein Zeiger auf den Anfang eines jeden
Strings im Array gespeichert.

von Christoph S. (mcseven)


Lesenswert?

Hi,

Danke Dir für Deine Antwort.
also ich habe jetzt:
1
flash struct Menu {
2
  unsigned char Header[16];
3
  unsigned int ItemCount;
4
  unsigned char *Items[];
5
} MainMenu[2] = {
6
  { 
7
    "Konfiguration",
8
    6,
9
    {"Uhrzeit/Datum", "Temperatur",  "Display", "DCF77", "Wecker", "-- Zurück --" }
10
  },
11
  { 
12
    "Configuration",
13
    6,
14
    {"Time/Date",     "Temperature", "Display", "DCF77", "Alarm Clock", "-- Back --"}
15
  }
16
};

Der Compiler compiliert, der Assembler allerdings wirft einen Fehler:
1
_MainMenu:
2
  .DB  0x4B,0x6F
3
  .DB  0x6E,0x66
4
  .DB  0x69,0x67
5
  .DB  0x75,0x72
6
  .DB  0x61,0x74
7
  .DB  0x69,0x6F
8
  .DB  0x6E,0x0
9
  .DB  0x0,0x0
10
  .DB  0x6,0x0
11
  .DB  LOW(_3+0x00),HIGH(_3+0x00)
12
  .DB  LOW(_3+0x0E),HIGH(_3+0x0E)
13
  .DB  LOW(_3+0x19),HIGH(_3+0x19)
14
  .DB  LOW(_3+0x21),HIGH(_3+0x21)
15
  .DB  LOW(_3+0x27),HIGH(_3+0x27)
16
  .DB  LOW(_3+0x2E),HIGH(_3+0x2E)
17
  .DB  0x43,0x6F
18
  .DB  0x6E,0x66
19
  .DB  0x69,0x67
20
  .DB  0x75,0x72
21
  .DB  0x61,0x74
22
0x690x6F //###### HIER Fehler unexpected INT
23
0x6E0x0
24
0x00x0
25
0x60x0
26
LOW(_4+0x00)HIGH(_4+0x00)
27
LOW(_4+0x0A)HIGH(_4+0x0A)
28
LOW(_4+0x16)HIGH(_4+0x16)
29
LOW(_4+0x1E)HIGH(_4+0x1E)
30
LOW(_4+0x24)HIGH(_4+0x24)
31
LOW(_4+0x30)HIGH(_4+0x30)
32
  .DEF _spitemp=R5
33
  .DEF _contrast=R4
34
  .DEF _screenstate=R7
35
  .DEF _menustate=R6
36
  .DEF _old_menustate=R9
37
  .DEF _i=R8
38
  .DEF _month=R11

Was mach ich denn falsch? Oder ist der Compiler schuld?

Und wäre folgender Code dann richtig:
1
unsigned int getMenuItemCount(flash Menu *menuToPaint) {
2
  unsigned char nrOfItems;
3
  //z.B. Anzahl der Items bekommen:
4
  nrOfItems = menuToPaint->ItemCount;
5
  return nrOfItems;
6
}
7
8
unsigned int tempCount;
9
tempCount = getMenuItemCount(MainMenu[0]); //tempCount = 6
10
tempCount = getMenuItemCount(MainMenu[1]); //tempCount = 6

Danke,
Christoph

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.