www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Vektor als Switchkriterium


Autor: Bruno (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo zusammen.

Ich bin gerade dabei ein Display mit Menüführung zu programmieren. Das 
läuft auch solange, bis ich am Ende des Menüs ankomme und es darum geht 
mir Werte anzeigen zu lassen. Die Menüsprünge realisiere ich mittels 
Vektoren, die auf ein Struct aus Strings zeigen. Diese werden dann 
ausgegeben. Läuft 1a solange ich nur Strings anzeigen muß. Jetzt möchte 
ich aber auf Werte zurück greifen und diese Anzeigen. Dafür benötige ich 
viele verschiedene Funktionen und nicht die Standardroutine.

Lange Rede kurzer Sinn. Kann ich mit einer Switch-Anweisung irgendwie 
auch auf einen Vektor verweisen?

Gruß Bruno

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hä?


Klingt aber danach, also ob die Antwort auf deine Frage "Nein"
lautet.

Da ich aber nicht wirklich kapiert habe, was du da machst, kann
ich dir auch keine Alternative vorschlagen.

Autor: Bruno (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Vllcht kannst dui dich an den Thread erinnern

Beitrag "strlen bei mehrdimensionalen Strings"

Ich möchte jetzt nicht auf ein Subdisplay verweisen, sondern auf eine 
Funktion.
MenuEntry MainMenu[] =
  {
    { { "Hilfe", "Help" },      NULL },
    { { "Bearbeiten", "Edit" }, &EditScreen },
    { { "Beenden", "Exit" },    NULL }
  };

Autor: Stefan (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Etwa sowas?
typedef struct
{
  unsigned int  bla;          // Parameter 1
  unsigned int  blub;         // Parameter 2
  void (*p_func)(void);       // Funktions-Pointer
} Cmd_Tab;


void test_func (void)
{
  ...
  return;
} 

const Cmd_Tab Test_Tab =
        {0x0000,            // Param 1
         0x0001,            // Param 1
         test_func          // Funktions-Pointer
        };


Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Bruno wrote:
> Vllcht kannst dui dich an den Thread erinnern
>
> Beitrag "strlen bei mehrdimensionalen Strings"
>
> Ich möchte jetzt nicht auf ein Subdisplay verweisen, sondern auf eine
> Funktion.
>
>
> MenuEntry MainMenu[] =
>   {
>     { { "Hilfe", "Help" },      NULL },
>     { { "Bearbeiten", "Edit" }, &EditScreen },
>     { { "Beenden", "Exit" },    NULL }
>   };
> 

OK.

Dann musst du deine Struktur erweitern.
Die besteht jetzt nicht mehr aus den 2 Einträgen, sondern aus 3
typedef void (*FuncPtr) ( void );


// Ein Eintrag (Menuepunkt) im Scrollbereich
typedef struct MenueEntry_ {
  Text                   m_Text;
  struct DisplayScreen_* m_pSubDisplay;
  FuncPtr                m_pFunction;
} MenuEntry;

wobei der dritte Eintrag der Funktionspointer ist. Die Auswerte-
funktion checkt jetzt einfach ab, welcher der beiden Pointer
nicht NULL ist. Ist es der SupDisplay Pointer, dann wird ein
Untermenü angezeigt. Ist es der Funktionspointer, dann wird die
Funktion aufgerufen.
void doCopy()
{
}

void doCut()
{
}

void doPaste()
{
}

// "Bearbeiten" Display
MenuEntry EditMenu[] =
  {
    { { "Kopieren",     "Copy" },  NULL, doCopy },
    { { "Ausschneiden", "Cut" },   NULL, doCut },
    { { "Einsetzen",    "Paste" }, NULL, doPaste }
  };

...

void HandleDisplay( DisplayScreen * pDisplay )
{
   ...  // konstante Teile des Screens aufbauen

   HandleMenu( pDisplay->ScrollArea.Entries,
               pDisplay->ScrollArea.m_Size );
}

void HandleMenu( MenuEntry* Entries, size_t NrEntries )
{
  size_t i;
  
  for( i = 0; i < NrEntries; ++i ) {
    // GetCurrentText( &Entries[i].m_Text ) )  ausgeben und so
    // das Menü aufbauen
  }

  // du hast eine Rückmeldung vom Benutzer und musst sie
  // jetzt auswerten

  // an dieser Stelle enthält i den Index des ausgewählten
  // Eintrags
  //
  // Checken ob es eine Funktion dafür gibt, wenn ja aufrufen
  if( Entries[i].pFunction != NULL )
    (*Entries[i].pFunction)();

  // Wenn es ein Submenü gibt, dann dieses auswählen
  if( Entries[i].m_pSubDisplay != NULL )
    HandleDisplay( Entries[i].m_pSubDisplay );
}



Beachten musst du nur, dass alle Funktionen immer die gleichen
Argumente haben, falls du welche brauchst. Das kann auch mal
bedeuten, dass eine Funktion Argumente bekommt, die sie nicht
benötigt.
Die tatsächlichen Argumente nimmst du ebenfalls mit in die
Struktur auf, damit sie beim Funktionsaufruf zur Verfügung
stehen.

zb.
typedef void (*FuncPtr) ( int * );


// Ein Eintrag (Menuepunkt) im Scrollbereich
typedef struct MenueEntry_ {
  Text                   m_Text;
  struct DisplayScreen_* m_pSubDisplay;
  FuncPtr                m_pFunction;
  int*                   m_pArg1;
} MenuEntry;


void doIncrement( int * pArg )
{
  (*pArg)++;
}

void doDecrement( int * pArg )
{
  (*pArg)--;
}

int Counter;
int Anzahl;

// "Bearbeiten" Display
MenuEntry EditMenu[] =
  {
    { { "Counter erhöhen", "inc Counter" },    NULL, doIncrement, &Counter },
    { { "Coutner verringern", "dec Counter" }, NULL, doDecrement, &Counter },
    { { "Anzahl erhöhen", "inc Anzahl" },    NULL, doIncrement, &Anzahl },
    { { "Anzahl verringern", "dec Anzahl" }, NULL, doDecrement, &Anzahl },
    { { "Beenden",    "Exit" }, NULL, NULL, NULL }
  };

...

void HandleDisplay( DisplayScreen * pDisplay )
{
  do {
    ...  // konstante Teile des Screens aufbauen

  } while(  HandleMenu( pDisplay->ScrollArea.Entries,
                        pDisplay->ScrollArea.m_Size );
}

uint8_t HandleMenu( MenuEntry* Entries, size_t NrEntries )
{
  size_t i;
  
  for( i = 0; i < NrEntries; ++i ) {
    // GetCurrentText( &Entries[i].m_Text ) )  ausgeben und so
    // das Menü aufbauen
  }

  // du hast eine Rückmeldung vom Benutzer und musst sie
  // jetzt auswerten

  // an dieser Stelle enthält i den Index des ausgewählten
  // Eintrags
  //
  // Checken ob es eine Funktion dafür gibt, wenn ja aufrufen
  if( Entries[i].pFunction != NULL )
    (*Entries[i].pFunction)( m_pArg1 );

  // Wenn es ein Submenü gibt, dann dieses auswählen
  if( Entries[i].m_pSubDisplay != NULL )
    HandleDisplay( Entries[i].m_pSubDisplay );

  return Entries[i].pFunction != NULL || Entries[i].m_pSubDisplay != NULL;
}

Autor: Bruno (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Jetzt brauche ich erst mal Verarbeitungszeit.
Aber danke für den/die Ansatz/Lösung.

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Bruno wrote:
> Jetzt brauche ich erst mal Verarbeitungszeit.
> Aber danke für den/die Ansatz/Lösung.

Ist sehr simpel.
Im Grunde wurde einfach nur in die Struktur ein zusätzlicher
Member mit aufgenommen. Alles andere ergibt sich daraus.

Autor: Bruno (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Na ja so simpel war das nicht. Wenn man an einem bestehenden Programm an 
der Basis fummelt kommt oft nur quatsch raus. Auf dem ganzen Jedöns 
basieren ca 20k Code. Aber der Ansatz war super. So in der Art hatte ich 
das auch geplant. Nur die Codestelle
(*Entries[i].pFunction)( m_pArg1 )

war mir nicht geläufig.
Danke nochmal² für die Hilfe.

Gruß Bruno

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.