Hallo,
ich habe hier ein "Displaytech Ltd, LCD Module 204A Series"
(HD44780 controller) an einem ATmega48 mit 4 Bit Mode mit der
LCD library von Peter Fleury in Betrieb.
Funktioniert soweit gut, außer ich setze LCD_WRAP_LINES=1.
Die DDRAM Adressen habe ich nach dem Datenblatt angepasst:
#define LCD_START_LINE1 0x00
#define LCD_START_LINE2 0x40
#define LCD_START_LINE3 0x14
#define LCD_START_LINE4 0x54
Das Problem ist, dass man in der zweiten Displayzeile "festhängt".
D.h., man kann über die Zeile 2 hinausschreiben, es macht auch
einen automatischen Zeilenwechsel, dann aber nicht von Zeile 3
in Zeile 4, sonder wieder in Zeile 2.
Die Adressierung bei diesem Display funktioniert so:
1: 0x00 ... 0x13 =>
3: 0x14 ... 0x27 =>
2: 0x40 ... 0x53 =>
4: 0x54 ... 0x67 =>
1: 0x00 ......
Das Problem ist, dass er am Ende von Zeile 3 auf 0x40 vorrückt, was
aber schon wieder der Start von Zeile 2 ist.
Was geht ist, dass man schon ab 0x27 den Zeilenumbruch macht,
das ist halt sehr unschön, da nun ein Zeichen am Ende hier fehlt.
Hier dazu die Veränderung:
void lcd_putc(char c){
.
.
#elif LCD_LINES==4
if (pos==LCD_START_LINE1+LCD_DISP_LENGTH) { // == 0x14
lcd_write((1<<LCD_DDRAM)+LCD_START_LINE2,0);
}else if (pos==LCD_START_LINE2+LCD_DISP_LENGTH) { // == 0x54
lcd_write((1<<LCD_DDRAM)+LCD_START_LINE3,0);
//}else if ( pos == 0x40 ) { // == 0x40 ?!
//}else if ( pos == 0x27 ) { // so halt 1 Zeichen zu kurz
lcd_write((1<<LCD_DDRAM)+LCD_START_LINE4,0);
}else if (pos==LCD_START_LINE4+LCD_DISP_LENGTH) { // == 0x68
lcd_write((1<<LCD_DDRAM)+LCD_START_LINE1,0);
}
Hat jmd. eine Idee, wie man das richtig machen könnte?
Mir fällt leider keine Möglichkeit mehr ein.
Vielen Dank im Voraus,
Rainer Snell
Die LCD_WRAP_LINES=1 Funktionalität habe ich nur eingebaut wegen einigen billigen 1*16 Zeichen Displays, die intern aus zwei aneinandergefügten 1*8 Displays bestehen. Funktioniert es mit LCD_WRAP_LINES=0 ?
Mit LCD_WRAP_LINES=0 ist es kein Problem.
Er schreibt dann von Zeile 1 in Zeile 3, von Zeile 3 in Zeile 2 und
von Zeile 2 in Zeile 4 weiter.
Das Problem des in Zeile 2 gefangen seins mit LCD_WRAP_LINES=1 kommt
daher, dass in der Funktion "void lcd_putc(char c)" durch die vier
"if" bzw. "else if" geprüft wird, ob
LCD_START_LINE{1-4}+LCD_DISP_LENGTH
erreicht wurde.
Die Adressierung meines Displays sagt:
Zeile 1: 0x00 ... 0x13 =>
Zeile 3: 0x14 ... 0x27 =>
Zeile 2: 0x40 ... 0x53 =>
Zeile 4: 0x54 ... 0x67 =>
Zeile 1: 0x00 ......
Was mit LCD_WRAP_LINES=1 bedeutet, wenn er am Ende von Zeile 3 ist,
sollte LCD_START_LINE3+LCD_DISP_LENGTH gleich 0x28 sein, was aber
leider nicht passt, da 0x40 richtig ist.
Mit 0x40 wird man aber auch nicht glücklich, da dies ja eben die
erste Adresse der Zeile 2 ist, und er so gleich nach Zeile 4 springt.
Leider fällt mir hier keine Lösung ein, zumindest nicht nach der Art
der DDRAM Address Map Überprüfung.
Sezte LCD_WRAP_LINES=0
Wie sieht die Ausgabe auf dem LCD aus bei:
lcd_puts("Line1\nLine2\nLine3\nLine4");
Er macht genau das, was er auch soll: ------------------------ Line1 Line2 Line3 Line4 ------------------------ Bei LCD_WRAP_LINES=0 klappt auch alles. Die einzige Möglichkeit die ich für einen automatischen Zeilenumbruch (also LCD_WRAP_LINES=1) sehe ist die Zeichen der aktuellen Zeile zu zählen BEVOR das Zeichen geschrieben wird.
>Er macht genau das, was er auch soll:
Das habe ich auch erwartet.
Wie schon în meinem ersten Posting erwähnt, LCD_WRAP_LINES muss =0 sein
für dein Display !
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.