mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik seltsames Phänomen Ausgabe auf LCD HD44780


Autor: Dennis (Gast)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

folgendes Problem: Ich möchte mehrere Anweisungen auf einem LCD (2x40 
Zeichen) über einen ATmega32 ausgeben. Die Anweisungen sollen 
hintereinander durch drücken eines Tasters, der am µC angeschlossen ist, 
aufgerufen werden. Mit einem weiteren Taster kann man eine Anweisung 
zurück gehen. Insgesamt habe ich 28 Anweisungen. Das Problem besteht nun 
darin, dass die ersten 5 Anweisungen nicht auf dem Display angezeigt 
werden. Erst wenn der Taster 6 mal gedrückt wurde erscheint Anweisung 6. 
Programmiere ich den µC allerdings für nur insgesamt 20 Anweisungen oder 
weniger funktioniert es einwandfrei. Hat jemand eine Idee? Zur 
Ansteuerung des Displays verwende ich die Library von Peter Fleury und 
zur Tastenentprellung das Debounce-Makro von Peter Dannegger auf der 
Artikelseite. Hier der Code:
#include <avr/io.h>
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <string.h>
#include <debounce.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#include <lcd.c>
#include <lcd.h>

unsigned char step = 0;                      // Schrittvariable


void next_instruction(void)                  // Funktion für den nächsten Schritt
  {
    switch (step) 
    {   
      case 0: 
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 1                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 1                        01/28");
          step = 1; 
        break;
        
      case 1:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 2                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 2                        02/28");
            step = 2; 
        break;
      
      case 2:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 3                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 3                        03/28");
          step = 3; 
        break;
        
      case 3:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 4                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 4                        04/28");
        step = 4; 
        break;
        
        
      case 4: 
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 5                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 5                        05/28");
        step = 5; 
        break;
        
      case 5:  
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 6                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 6                        06/28");
        step = 6; 
        break;
        
      case 6:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 7                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 7                        07/28");
        step = 7; 
        break;
        
      case 7:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 8                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 8                        08/28");
        step = 8; 
        break;
        
      case 8:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 9                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 9                        09/28");
        step = 9; 
        break;
        
      case 9:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 10                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 10                       10/28");
        step = 10; 
        break;
        
      case 10:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 11                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 11                       11/28");
        step = 11; 
        break;
        
      case 11:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 12                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 12                       12/28");
        step = 12; 
        break;
        
      case 12:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 13                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 13                       13/28");
        step = 13; 
        break;
        
      case 13:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 14                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 14                       14/28");
        step = 14; 
        break;
        
      case 14:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 15                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 15                       15/28");
        step = 15; 
        break;
        
      case 15:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 16                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 16                       16/28");
        step = 16; 
        break;
        
      case 16:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 17                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 17                       17/28");
        step = 17; 
        break;
      
      case 17:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 18                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 18                       18/28");
        step = 18; 
        break;

      case 18:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 19                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 19                       19/28");
        step = 19; 
        break;
      
      case 19:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 20                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 20                       20/28");
        step = 20; 
        break;

      case 20:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 21                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 21                       21/28");
        step = 21; 
        break;

      case 21:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 22                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 22                       22/28");
        step = 22; 
        break;

      case 22:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 23                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 23                       23/28");
        step = 23; 
        break;
    
      case 23:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 24                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 24                       24/28");
        step = 24; 
        break;

      case 24:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 25                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 25                       25/28");
        step = 25; 
        break;

      case 25:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 26                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 26                       26/28");
        step = 26; 
        break;

      case 26:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 27                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 27                       27/28");
        step = 27; 
        break;

      case 27:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 28                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 28                       28/28");
        step = 28; 
        break;

        
      default:  break;
    }
    
  }


void previous_instruction(void)                  // Funktion für den vorherigen Schritt
  {
    switch (step) 
    {
      case 2: 
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 1                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 1                        01/28");
          step = 1; 
        break;
        
      case 3:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 2                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 2                        02/28");
            step = 2; 
        break;
      
      case 4:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 3                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 3                        03/28");
          step = 3; 
        break;
        
      case 5:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 4                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 4                        04/28");
        step = 4; 
        break;
        
        
      case 6: 
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 5                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 5                        05/28");
        step = 5; 
        break;
        
      case 7:  
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 6                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 6                        06/28");
        step = 6; 
        break;
        
      case 8:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 7                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 7                        07/28");
        step = 7; 
        break;
        
      case 9:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 8                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 8                        08/28");
        step = 8; 
        break;
        
      case 10:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 9                             ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 9                        09/28");
        step = 9; 
        break;
        
      case 11:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 10                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 10                       10/28");
        step = 10; 
        break;
        
      case 12:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 11                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 11                       11/28");
        step = 11; 
        break;
        
      case 13:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 12                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 12                       12/28");
        step = 12; 
        break;
        
      case 14:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 13                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 13                       13/28");
        step = 13; 
        break;
        
      case 15:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 14                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 14                       14/28");
        step = 14; 
        break;
        
      case 16:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 15                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 15                       15/28");
        step = 15; 
        break;
        
      case 17:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 16                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 16                       16/28");
        step = 16; 
        break;
        
      case 18:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 17                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 17                       17/28");
        step = 17; 
        break;
      
      case 19:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 18                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 18                       18/28");
        step = 18; 
        break;

      case 20:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 19                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 19                       19/28");
        step = 19; 
        break;
      
      case 21:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 20                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 20                       20/28");
        step = 20; 
        break;

      case 22:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 21                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 21                       21/28");
        step = 21; 
        break;

      case 23:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 22                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 22                       22/28");
        step = 22; 
        break;

      case 24:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 23                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 23                       23/28");
        step = 23; 
        break;
    
      case 25:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 24                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 24                       24/28");
        step = 24; 
        break;

      case 26:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 25                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 25                       25/28");
        step = 25; 
        break;

      case 27:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 26                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 26                       26/28");
        step = 26; 
        break;

      case 28:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 27                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 27                       27/28");
        step = 27; 
        break;

      case 29:
        lcd_gotoxy(0,0);
        lcd_puts ("Anweisung 28                            ");
        lcd_gotoxy(0,1);
        lcd_puts ("Anweisung 28                       28/28");
        step = 28; 
        break;
        
      default:  break;
    }
    
  }




//----------------------------------------------

int main(void)
{
  DDRB = 0xFF;                        // PortB als Ausgang schalten
  DDRC = 0xFF;                        // PortC als Ausgang schalten
  DDRD = 0x00;                        // PortD als Eingang schalten
  PORTB = 0x1C;  
  PORTC = 0x00;
  PORTD = 0x00;                      // interne Pull-ups an PORTD deaktivieren

  
  
  lcd_init(LCD_DISP_ON);
  lcd_gotoxy(0,0);
  lcd_puts ("   ***     PROGRAMMABLAUF XY     ***   ");



  
  
  while(1)                        // Überwachen ob und welcher Taster gedrückt wird
  {    
    
      if( debounce( PIND, PD0 ) )              
      {
        next_instruction();
      }
  
      if( debounce( PIND, PD1 ) )              
      {
        previous_instruction();
      }
    
  }   
}


Danke

Autor: smatlok (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
reiner zufall dasses überhaupt läuft.. initialisiere step in main() und 
lass mal step in der main schleife hoch+runterzählen und übergeb den 
konkreten wert an die funktion als parameter.

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

Bewertung
0 lesenswert
nicht lesenswert
Und denk mal darüber nach, deine Texte in ein Stringarray zu legen, die 
du mit der step Variablen indizierst. Das ist doch Unmenge an Code für 
nichts, mit massenhaft Textduplikaten.

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

Bewertung
0 lesenswert
nicht lesenswert
Sind eigentlich deine restlichen Dinge die du bei jedem step machst in 
previous_step bzw next_step immer gleich, d.h. wenn bei next_step der 
step 2 von 1 ausgehend erreicht wird, passiert dann das gleiche, wie 
wenn step 2 von previous_step von der 3 aus erreicht wird?

Wenn ja, dann solltest du unbedingt deine Systematik auf jeden Fall 
ändern. Du hast eine Funktion show_step und das erhöhen bzw. erniedrigen 
ist nicht das Bier dieser Funktion, sondern passiert ausserhalb. Dein 
Gedöns mit PORTB ist, soweit ich das auf die Schnelle gesehen habe, auch 
in allen Fällen gleich nur PORTC wird anders behandelt.

Alles in allen sieht es so aus, als ob man die Funktionalität leicht 
mittels Tabellen und einer Abarbeitungsmaschine (ähnlich einer 
State-maschine) einfach implementieren kann.

Edit:
Nein, eigentlich ist eine State-maschine in einer Tabelle schon ziemlich 
genau der Ansatz um das Programm extrem zu vereinfachen. Es sei denn, da 
kommt noch was dazu, was man jetzt noch nicht absehen kann.

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Dennis (Gast)

Was soll der Unsinn mit dem ellenlangen Code im Posting? Im Anhang ist 
er prima aufgehoben. Siehe Netiquette!
Und wie bereits gesagt, das macht man mit Arrays und einer 
Statemachine.

MFG
Falk

Autor: Hc Zimmerer (mizch)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du hast Strings mit 40 Zeichen (41 Bytes) Länge.  Je Schritt zeigst Du 2 
davon an, macht 80 Zeichen (82 Bytes).  Pro case hast du 28 Einträge. 
Du hältst die Strings unpassenderweise im initialisierten SRAM, nicht im 
Flash.

Insgesamt hast Du also
 2 * 28 * 82 Bytes = 4592 Bytes 
 an Strings im SRAM.  Der ATmega32 hat 4kBytes SRAM.  Merkst Du was?

Autor: Mike Hammer (-scotty-)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Nur Gemecker von den Forumshirschen, aber keine Lösung des Problems,
war ja klar. Beantwortet doch mal die Frage des TO. Den Code solltet
ihr doch gar nicht diskutieren. Klar, Profis programmieren das mit
minimalem Aufwand, aber jeder hat mal angefangen und macht das erst
mal umständlich, nur funktionieren sollte es.

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

Bewertung
0 lesenswert
nicht lesenswert
Mike Hammer schrieb:
> Nur Gemecker von den Forumshirschen, aber keine Lösung des Problems,
> war ja klar. Beantwortet doch mal die Frage des TO.

Die ist längst beantwortet.
Viel zu viel SRAM verbraucht.

> Den Code solltet
> ihr doch gar nicht diskutieren.

Doch.
Mit einer einfacheren SW-Architektur hätte er viel weniger SRAM 
verbraucht.

> Klar, Profis programmieren das mit
> minimalem Aufwand, aber jeder hat mal angefangen und macht das erst
> mal umständlich,

drum sagen wir ihm ja auch, wie man es besser machen kann.

Autor: Dennis (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Um ehrlich zu sein befasse ich mich mit mikrocontrollern sehr selten und 
mache das hier nur nebenbei....deshalb ergeben sich mir ne menge fragen 
auf euere antworten...

smatlok schrieb:
> reiner zufall dasses überhaupt läuft.. initialisiere step in main() und
>
> lass mal step in der main schleife hoch+runterzählen und übergeb den
>
> konkreten wert an die funktion als parameter.


ich dachte man initialisiert globale variablen immer am anfang des 
codes? hab es mal ausprobiert und es erscheint eine fehlermeldung, dass 
der compiler die variable step in der funktion next_step() nicht kennt. 
und ist es nicht wurst ob ich die variable in der mainschleife hochzähle 
oder in der funktion?
ich glaube nicht dass es ein zufall ist dass es mit weniger anweisungen 
klappt.

Falk Brunner schrieb:
> Und wie bereits gesagt, das macht man mit Arrays und einer
>
> Statemachine.

wusste bisher nicht was eine statemachine ist aber nachdem ich mir den 
artikel durchgelesen hab sieht mein programm doch exakt so aus (vgl 
erstes bsp in dem artikel) nur dass meine variable step heist und nicht 
state.

Karl heinz Buchegger schrieb:
> Mit einer einfacheren SW-Architektur hätte er viel weniger SRAM
>
> verbraucht.

und wenn man strings in einem array abspeichert verbraucht man weniger 
speicher als wenn man jeden einzelnen string abspeichert? Warum?



ich will das eigentlich zügig ohne großen aufwand erledigt haben und da 
das eigentliche problem ja der mangelnde platz an sram ist, ist doch das 
abspeichern der strings im flash die schnellste lösung wenn auch nicht 
die eleganteste...

Autor: 900ss D. (900ss)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Dennis schrieb:
> ich dachte man initialisiert globale variablen immer am anfang des
> codes?

Deine Initialisierung funktioniert genauso gut. Lass dir da mal nichts 
einreden.

> wusste bisher nicht was eine statemachine ist aber nachdem ich mir den
> artikel durchgelesen hab sieht mein programm doch exakt so aus (vgl
> erstes bsp in dem artikel) nur dass meine variable step heist und nicht
> state.

Ja, da hast du recht. Verstehe auch nicht warum da der Falk meinte, du 
sollst eine Statemachine bauen. Er hatte wohl eine andere elegantere 
Struktur im Kopf. Aber das von einem Anfänger verlangen/erwarten?

>
> Karl heinz Buchegger schrieb:
>> Mit einer einfacheren SW-Architektur hätte er viel weniger SRAM
>>
>> verbraucht.
>
> und wenn man strings in einem array abspeichert verbraucht man weniger
> speicher als wenn man jeden einzelnen string abspeichert? Warum?

Nein, dass ist natürlich nicht der Fall. Aber du hast elendig viele 
gleiche Anteile in den Strings. Die gleichen Strings könntest du nur 
einmal ablegen und dann mehrere Ausgaben starten für jeden Step. Erst 
den für alle gemeinsamen Text "Anweisung ", dann die Stepnummer und dann 
gotoxy(35,1) und noch die Ausgabe "18/28" oder so. Die vielen 
Leerzeichen brauchst du als String doch garnicht. Der String "Anweisung 
" wäre dann nur einmal da und nicht über 40 mal. Und schon würde auch 
dein SRAM reichen.
z.B.:
static char sAnweisung[] = "Anweisung";  // Text "Anweisung " ist so nur einmal vorhanden
char buffer[20];

sprintf(buffer,"%s %2d",sAnweisung, step);  // "Anweisung " + step nummer als String vorbereiten
lcd_gotoxy(0,0);
lcd_puts(buffer)             // "Anweisung step" ausgeben
lcd_gotoxy(0,1);
lcd_puts(buffer)
sprintf(buffer,"%2d/28",step);  // step/max. Step als String vorbereiten
lcd_gotoxy(35,1);
lcd_puts(buffer)
step = 27; 

> ich will das eigentlich zügig ohne großen aufwand erledigt haben und da
> das eigentliche problem ja der mangelnde platz an sram ist, ist doch das
> abspeichern der strings im flash die schnellste lösung wenn auch nicht
> die eleganteste...

Das so zu erledigen geht natürlich auch.

Dein nicht ausreichendes SRAM wird sicher der Grund sein, warum du solch 
ein merkwürdiges Verhalten hast. Das es überhaupt läuft, ist schon ein 
wunder. Aber das wurde ja schon gesagt.

Ich muss sagen, auch wenn ich die Meinung der "Platzhirsche" hier sehr 
schätze, dass ihre Antwort hier suboptimal war. Sicher kann man alles 
besser und hübscher machen. Aber als Anfänger(?) ist es auf einem 
einfachen Wege erstmal OK finde ich. Dabei lernt man schonmal etwas. Ich 
bin echt verwundert. Wenn ein Anfänger ein komplexes Projekt mit einem 
AVR aufziehen will und hier fragt, dann rät man ihm mit einer LED und 
einem Taster anzufangen. Hier erwartet man umgekehrt gleich gute und 
ordentliche Programmstrukturen u.s.w.. Für einen Anfänger finde ich das 
oben garnicht so schlecht.

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

Bewertung
0 lesenswert
nicht lesenswert
900ss D. schrieb:

> einem Taster anzufangen. Hier erwartet man umgekehrt gleich gute und
> ordentliche Programmstrukturen u.s.w.. Für einen Anfänger finde ich das
> oben garnicht so schlecht.

Na ja.
Zumindest so hätte man das ja doch machen können. Das wäre ziemlich 
naheliegend:
void show_instruction( uint8_t schritt )
{
  switch( schritt ) 
  {   
    case 0: 
    lcd_gotoxy(0,0);
    lcd_puts ("Anweisung 1                             ");
    lcd_gotoxy(0,1);
    lcd_puts ("Anweisung 1                        01/28");
    break;
        
  case 1:
    lcd_gotoxy(0,0);
    lcd_puts ("Anweisung 2                             ");
    lcd_gotoxy(0,1);
    lcd_puts ("Anweisung 2                        02/28");
    break;

  ...
}

int main()
{
  ...

  lcd_init(LCD_DISP_ON);
  lcd_gotoxy(0,0);
  lcd_puts ("   ***     PROGRAMMABLAUF XY     ***   ");
  
  step = 0;

  while( 1 )
  {    
    if( debounce( PIND, PD0 ) )              
    {
      if( step < 29 ) {
        step++;
        show_instruction( step );
      }
    }

    if( debounce( PIND, PD1 ) )              
    {
      if( step > 0 ) {
        step--;
        show_instruction( step );
      }
    }
  }   
}

damit hätte man schon mal die doppelte Aufzählung aller steps in 
previous_... und next_... weg, weil es previous_... und next_... schon 
gar nicht mehr gibt, sondern nur noch 1 Funktione die einen Parameter 
bekommt, für welchen Schritt sie die Anzeige aufbereiten soll.

Vo da ist es dann kein weiter Weg mehr, dass man realisiert, dass doch 
im Grunde alle cases in der Funktion dasselbe machen. Also legt man sich 
die gleich in eine Tabelle, die aus den beiden Texten für einen Status 
besteht.
struct state
{
  char * text1;
  char * text2;
};

struct states States[] = 
{
  { "Anweisung 1                             ",
    "Anweisung 1                        01/28" },

  { "Anweisung 2                             ",
    "Anweisung 2                        02/28" },

  ... die restlichen 26 States
};

void show_instruction( uint8_t schritt )
{
  if( schritt < sizeof(States) / sizeof(*States) ) {   // sicher ist sicher
    lcd_gotoxy(0,0);
    lcd_puts( States[schritt].text1 );
    lcd_gotoxy(0,1);
    lcd_puts( States[schritt].text2 );
  }
}

int main()
{
  ...

  lcd_init(LCD_DISP_ON);
  lcd_gotoxy(0,0);
  lcd_puts ("   ***     PROGRAMMABLAUF XY     ***   ");
  
  step = 0;

  while( 1 )
  {    
    if( debounce( PIND, PD0 ) )              
    {
      if( step < 29 ) {
        step++;
        show_instruction( step );
      }
    }

    if( debounce( PIND, PD1 ) )              
    {
      if( step > 0 ) {
        step--;
        show_instruction( step );
      }
    }
  }   
}

die restlichen Informationen, die sonst noch zu einem State gehören, 
kann man auch noch in die Tabelle verfrachten und hat dort dann die 
komplette Info beisammen, was in einem State alles zu tun ist (und wenn 
man will kann man in die Tabelle dann auch noch den jeweiligen Vorgänger 
btw. Nachfolgezustand mit angeben.

Vorteil des Ganzen: Änderungsaufwand ist kleiner und vor allen Dingen 
übersichtlicher, weil alles an einer Stelle beisammen ist und nicht über 
2 Funktionen verstreut (und dort auch noch dupliziert) ist.

Das man die Texte dann allesamt ins Flash verlegt ist dann der nächste 
Schritt. Dadurch, dass die Anzeigefunktion jetzt viel einfacher ist, ist 
das programmtechnisch keine Hexerei, in den Daten ist es sowieso nicht 
mehr als einfach nur eine entsprechende Attributierung der Texte per 
Makro.

Autor: 900ss D. (900ss)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Karl heinz Buchegger schrieb:
> .... Vorteil des Ganzen: ....

Ja du hast ja Recht. Aber trotzdem ist das schon eine Stufe komplexer 
und nicht mehr nur die LED am AVR sondern auch ein Pegelwandler mit 
Schieberegister um 80 LEDS anzusteuern (oder so) ;-)

Unsere beiden Verbesserungen machen da schon was hübsches draus ;-)

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

Bewertung
0 lesenswert
nicht lesenswert
900ss D. schrieb:
> Karl heinz Buchegger schrieb:
>> .... Vorteil des Ganzen: ....
>
> Ja du hast ja Recht. Aber trotzdem ist das schon eine Stufe komplexer

Funktionen mit Argumenten sind komplex?

OK, ich zieh meinen Einwand zurück.

Autor: 900ss D. (900ss)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Karl heinz Buchegger schrieb:
> Funktionen mit Argumenten sind komplex?

Mensch, heute hast du deinen Hut wohl mit dem Hammer aufgesetzt ;-)

> OK, ich zieh meinen Einwand zurück.

Und auch noch beleidigt. Tzzzz Tzzzz Tzzzz.... ;-)

Ich meinte dein Gesamtkonstrukt, also das umschalten der States u.s.w. 
u.s.w.

Sicher zu verstehen, aber als Anfänger mußt du da auch erst drauf 
kommen. Da überlegst du dir doch erstmal was SEHR einfaches, einfach 
gerade runter.

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

Bewertung
0 lesenswert
nicht lesenswert
Nein.
Aber einen gewissen Grundstock an Kentnissen setzte ich schon vorraus, 
wenn jemand ein Projekt durchziehen will.
Arrays und Funktionen mit Argumenten gehören dazu.

Wer Klemptnerarbeiten machen will, wird auch nicht weit kommen, wenn 
alles was er kann ein Rohr mit Isolierband umwickeln ist.

Ist nun mal so.
(Kann auch sein, das ich es einfach nur leid bin, wieder und immer 
wieder mit anzusehen, wie Menschen glauben Computer programmieren ist so 
ähnlich wie Wurstbrötchen essen. Kann doch jeder, muss man nichts können 
oder lernen. Und hinterher ist das Geschrei groß ....

Autor: Dennis (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Deine Vergleiche find ich etwas unpassend zumal, dass das was ich 
geschrieben habe nicht direkt falsch ist sondern einfach 
ressourcenraubend.
Mir war es ehrlich gesagt beim schreiben nicht bewusst, dass es auch 
eleganter geht aber mit den aufgezeigten Beispielen wird mir auch 
einiges klarer und nur so lernt man ja auch dazu. Nebenbei bilde ich mir 
absolut nicht ein dass ich perfekt programmieren kann...keine ahnung wie 
ich so einen eindruck hinterlassen habe...
Trotzdem Danke für die Hilfe...werde es morgen ausprobieren...

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.