Hallo, ich habe das Display (Datenblatt als Attachement) im 4-Bit Modus angeschlossen und den Initprozess dafür wohl auch richtig implementiert. Wenn ich nun versuche ein Zeichen auf das Display zu schreiben (Funktion sendCharacter), bekomme ich zwar ein Zeichen angezeigt, aber nicht das was ich angebe. Im 8-Bit Modus funktioniert sendCharacter einwandfrei. Muss man wie bei den Kommandos auch bei den Zeichen im 4-Bit Modus eine andere Art der Übertragung implementieren als im 8-Bit Modus? Im Quellcode habe ich den Buchstaben K angegeben. Auf dem Display erscheint aber ein $. Das Tutorial hier über LCDs habe ich mir schon durchgelesen. Ich verstehe aber einfach nicht wo das Problem liegt. Könnt ihr mir weiterhelfen? Gruß Kai
Kai Wierzoch schrieb: > Muss man wie bei > den Kommandos auch bei den Zeichen im 4-Bit Modus eine andere Art der > Übertragung implementieren als im 8-Bit Modus? Naja also du musst ein 8-Bit Zeichen im 4-Bit Modus natürlich in 2x4 Bit zerlegen und nacheinander senden. So wie alle Kommandos auch. Aber das sollte ja klar sein. Ansonsten unterscheidet sich das Senden von Zeichen nicht vom 8-Bit Modus. gruß cyblord
Wie sende ich den ein K in 2x4Bit? Muss ich erst die Hexzahl 0x4B (K) in 0b01001011 umwandeln und dann senden?
Kai Wierzoch schrieb: > Wie sende ich den ein K in 2x4Bit? Muss ich erst die Hexzahl 0x4B (K) > in 0b01001011 umwandeln und dann senden? Also die Zahlendarstellung ist dein Privatvergnügen. Da musst du deine Gedanken mal bisschen ordnen. Alle Kommunikation mit dem Display erfolgt via 4-Bit Bus also gibts da nur Bits. Alle Daten (Zeichen und Kommandos) haben ja 8 Bit. Normalerweise werden die an D0-D7 angelegt und ein Strobe auf Enable ausgelöst. Im 4-Bit Modus werden zuerst die unteren 4 Bits (Nibble) angelegt, dann Enable gestrobed, dann die oberen 4 Bit, und nochmal Strobe auf Enable. gruß cyblord
Kai Wierzoch schrieb: > Wie sende ich den ein K in 2x4Bit? Muss ich erst die Hexzahl 0x4B (K) > in 0b01001011 umwandeln und dann senden? Da muß nix gewandelt werden, ist doch nur eine andere Darstellung desselben. Stattdessen muß das Byte zerlegt und dem LCD in 2 Häppchen (high-nibble und low-nibble) angeboten werden. mfg
1 | void sendCommand(unsigned char command) |
2 | {
|
3 | checkBusy(); |
4 | LCDPORT = command; |
5 | LCDPORT &= ~ ((1<<RW)|(1<<RS)); |
6 | nopAbit(); |
7 | LCDPORT = 0; |
8 | }
|
9 | |
10 | void sendCharacter(unsigned char character) |
11 | {
|
12 | checkBusy(); |
13 | LCDPORT = character; |
14 | LCDPORT &= ~ (1<<RW); |
15 | LCDPORT |= (1<<RS); |
16 | nopAbit(); |
17 | LCDPORT = 0; |
18 | }
|
Das geht natürlich so nicht. Hier werden ja die 8 Bit direkt auf den Port gelegt. Wie soll das gehen wenn du nur 4 Portleitungen verbunden hast? Das sollte aber eigentlich einleuchten. gruß cyblord
cyblord ---- schrieb: > Das geht natürlich so nicht. Hier werden ja die 8 Bit direkt auf den > > Port gelegt. Wie soll das gehen wenn du nur 4 Portleitungen verbunden > > hast? Das sollte aber eigentlich einleuchten. Genau da liegt mein Problem. Wie übertrage ich denn z.B. den Buchstaben K im 4-Bit Modus? Ich muss erst das high-nibble und dann das low-nibble übertragen, aber wie?
cyblord ---- schrieb: > Im 4-Bit Modus werden zuerst die unteren 4 Bits (Nibble) angelegt, dann > Enable gestrobed, dann die oberen 4 Bit, und nochmal Strobe auf Enable. Ich habe jetzt nicht ins Datenblatt geschaut, aber bei meinen LCD-Modul übertrage ich immer zuerst das High und dann das Low Nibble. Hmm, kocht da wieder jeder Hersteller sein eigenes Süppchen? :-)
Kai Wierzoch schrieb: > Ich muss erst das high-nibble und dann das low-nibble > übertragen, aber wie? Indem du erst "character" überträgst (dabei kommt nur das high-nibble beim LCD an, weil nur D4..D7 benutzt werden), dann dein character 4-mal nach links schiebst, so dass das low-nibble in den oberen 4 Bit liegt, und dies dann auch zum LCD überträgst.
Hi
>Hmm, kocht da wieder jeder Hersteller sein eigenes Süppchen? :-)
Eigentlich nicht. Mir ist noch kein Controller untergekommen, der nicht
die Reihenfolge High-Nibble - Low-Nibble hatte.
MfG Spess
Michael schrieb: > Indem du erst "character" überträgst (dabei kommt nur das high-nibble > > beim LCD an, weil nur D4..D7 benutzt werden), dann dein character 4-mal > > nach links schiebst, so dass das low-nibble in den oberen 4 Bit liegt, > > und dies dann auch zum LCD überträgst. Ich habe die Funktion wie folgt abgeändert. Jetzt bekomme ich statt eines $-Zeichens ein / angezeigt.
1 | void sendCharacter(unsigned char character) |
2 | {
|
3 | checkBusy(); |
4 | LCDPORT |= character; |
5 | LCDPORT |= character<<4; |
6 | _delay_ms(250); |
7 | LCDPORT &= ~ (1<<RW); |
8 | LCDPORT |= (1<<RS); |
9 | nopAbit(); |
10 | LCDPORT = 0; |
11 | }
|
Das mit dem <<4 habe ich aus dem Tutorial hier auf mikrocontroller.net. Was mache ich falsch?
Kai Wierzoch schrieb: > Das mit dem <<4 habe ich aus dem Tutorial hier auf mikrocontroller.net. > Was mache ich falsch? Du machst irgendwas stupide nach ohne zu verstehen was du tun sollst. Schau erstmal wo du die 4 Leitungen am Controller genau angeschlossen hast. Beim LCD müssen die laut deinem DB an DB0-DB3 was eigentlich ungewögnlich ist, bei meinem müssen die immer an DB4-DB7. Aber du musst es für dein LCD halt richtig machen. Dann kannst du entscheiden in welche Richtung zu shiften musst. gruß cyblord
cyblord ---- schrieb: > Beim LCD müssen die laut deinem DB an DB0-DB3 Wie kommst du da drauf? Das "... not used ..." übersehen?
Es gibt übrigens schier unendlich viele Implementierungen mit solchen Allerwelt-LCDs, auch im 4-Bit Modus. Beispielsweise die von Peter Fleury. Einfach danach suchen und nutzen.
A. K. schrieb: > cyblord ---- schrieb: >> Beim LCD müssen die laut deinem DB an DB0-DB3 > > Wie kommst du da drauf? Das "... not used ..." übersehen? Jap stimmt. Hab ich in der Hektik falsch gelesen.
Kai Wierzoch schrieb: > Was mache ich falsch? Du maskierst das Low-Nibble in das High-Nibble. Damit der LCD-Controller irgendetwas mitbekommt, mußt du das verschobene Byte aber dorthin übertragen.
Michael schrieb: > Kai Wierzoch schrieb: >> Was mache ich falsch? > > Du maskierst das Low-Nibble in das High-Nibble. Damit der LCD-Controller > irgendetwas mitbekommt, mußt du das verschobene Byte aber dorthin > übertragen. Wie übertrage ich denn das verschobene Byte? Ich dachte, dass ich das mit der o.g. Änderung Der Funktion bereits mache.
Kai Wierzoch schrieb: > Wie übertrage ich denn das verschobene Byte? Schon mal eine LED zum blinken gebracht? Gruß Jobst
Kai Wierzoch schrieb: > Wie übertrage ich denn das verschobene Byte? > Ich dachte, dass ich das mit der o.g. Änderung > Der Funktion bereits mache. Hatte ich dir bereits geschrieben. Du musst für jedes Nibble (4-Bit) einen separaten Impuls auf die Enable Leitung geben. > Schon mal eine LED zum blinken gebracht? Frage ich mich auch. Eigentlich dachte ich am Anfang du hättest etwas Ahnung aber inzwischen scheint es du hast einfach stupide einen Code kopiert und dann willst du ohne jegliches Verständnis davon kurz mal auf 4-Bit Modus umschalten. Dann kopier doch bitte gleich nen Code für 4-Bit.
Stimmt. Ich habe nicht viel Ahnung von uC Programmierung. Ich bin erst seit ca. 1 Monat dabei. Eine LED habe ich schon zum Blinken gebracht. Da musste ich aber nicht auf Taktzyklen achten und Enable Bit setzen usw. usw. Natürlich kann ich eine fertige 4-Bit Code Lösung nehmen. Ich dachte nur, wenn ich selber programmiere, kapiere ich es eher und habe dann das Verständnis dafür. Da habe ich wohl falsch gedacht. Schuldigung. Werde Euch nicht mehr nerven. cyblord ---- schrieb: > Hatte ich dir bereits geschrieben. Du musst für jedes Nibble (4-Bit) > > einen separaten Impuls auf die Enable Leitung geben. Werde ich umsetzen. Vielen Dank. Gruß Kai
Kai Wierzoch schrieb: > dachte nur, wenn ich selber programmiere, kapiere ich es eher und habe > dann das Verständnis dafür. Kann man machen. Andererseits kann man an funktionierendem Code anderer Leute manchmal auch erkennen, was man selber falsch gemacht hat.
Kai Wierzoch schrieb: > Ich > dachte nur, wenn ich selber programmiere, kapiere ich es eher und habe > dann das Verständnis dafür. Guter Ansatz, aber es sieht nicht danach aus als hättest du den Code bisher verstanden, also gehe ich nicht davon aus dass du den selbst programmiert hast. Denn wenn du das Prinzip der LCD Ansteuerung verstanden hättest, dann wüsstest du dass jeder Befehl und jedes Zeichen erst an den Bus angelegt und dann mit der Enable-Leitung reingetaktet wird. Und dann wäre dir auch klar dass man nicht einfach 2x 4 Bit anlegen kann, und dabei nur ein mal Enable taktet. Wer das macht der zeigt doch dass er gar nicht kapiert was da abläuft. Falls du den Code wirklich selber schreiben willst, such dir mal ein besseres Datenblatt, deins ist nicht sooo gut und schau dir den im Netz die üppig vorhandenen Beispielcodes zu 4-Bit an. Hier steht auch noch was dazu: http://www.mikrocontroller.net/articles/AVR-GCC-Tutorial/LCD-Ansteuerung gruß cyblord
Das war nicht böse gemeint. Nur wenn mich jemand fragt, wie man die Daten überträgt, dann frage ich mich, ob derjenige überhaupt schon mal Signale aus einem Controller ausgegeben hat. Also: Nicht eingeschnappt sein! Wir haben hier ganz andere Kandidaten :-) Während Du im 8 Bit Modus immer ein ganzes Byte überträgst, musst Du im 4 Bit Modus die selben 8 Bit in zwei Häppchen a 4 Bit übertragen. So:
1 | _ _ |
2 | E ________/ \_______/ \__ |
3 | |
4 | ___ ___________________ |
5 | RS ___X___________________ 1 = Daten ; 0 = Befehle |
6 | |
7 | ___ _________ _________ |
8 | DB4-7 ___X__D4-D7__X__D0-D3__ |
9 | |
10 | | | | | |
11 | A B C D |
Du setzt also RS auf den richtigen Pegel und legst die oberen 4 Bit von Deinen 8 Bit an die 4 Datenleitungen (A). Dann wird ein Impuls auf die Enable-Leitung gelegt (B). Danach muß ein wenig gewartet werden (ca. 40µs +/- je nach Display) und dann werden die unteren 4 Bit auf den Ausgang gegeben (C). Noch ein Puls auf Enable (D) und nochmal warten. Ganz wichtig ist, daß Du dabei nicht durcheinander kommst, denn das Display erwartet immer 2 Nibbles (Halbbytes). Wenn Du also mal nur 1 oder gar 3 lieferst, geht Dir die Kommunikation flöten. Ist sie erst einmal flöten gegangen, hast Du von Deiner Seite keine Möglichkeit dies festzustellen. Wenn Du Dir unsicher bist, kannst Du das Display in regelmässigen Abständen initialisieren. Aber die saubere Variante ist das nicht. Ach ja: In der Initialisierungsphase bei der Umschaltung von 8 zu 4 Bit werden NUR die 4 oberen Bits zum Display geschickt! Erst wenn zu 4 Bit umgeschaltet wurde, werden beide Nibble gesendet. Gruß Jobst
Ich bin nicht eingeschnappt. Ich bin nur etwas mit der ganzen Display Sache überfordert. Mir ist es ja auch peinlich ständig nachfragen zu müssen. Das mit dem 8-Bit Modus habe ich ja hinbekommen. Nur der 4-Bit Modus macht mich noch fertig. Danke für die Antwort. Ich versuche das mal programmatisch umzusetzen. Gruß Kai
Hi >Das mit dem 8-Bit Modus habe ich ja hinbekommen. Nur der 4-Bit >Modus macht mich noch fertig. Was mich verwundert ist, das du die Initialisierung hinbekommen hast (?) und jetzt an der Ausgabe von einzelnen Zeichen scheiterst. Von RS abgesehen werden die letzten Befehle der Initialisierung genau wie Zeichen ausgegeben. Zeig mal deinen kompletten Code. Mfg Spess
Kai Wierzoch schrieb: > Ich bin nicht eingeschnappt. Ich bin nur etwas mit der ganzen Display > Sache überfordert. Mir ist es ja auch peinlich ständig nachfragen zu > müssen. Das mit dem 8-Bit Modus habe ich ja hinbekommen. Nur der 4-Bit > Modus macht mich noch fertig. Danke für die Antwort. Auch dann ist es nicht verboten, mal anderen Code zu studieren. Gerade wenn du den 8-Bit Mode alleine hingekriegt hast, wofür interessanterweise sogar einiges spricht, wenn man sich die Fehler in deinem Code ansieht, ist es keine Schande sich in anderem Code mal die Unterschiede anzusehen und diesen Code zu studieren. Ganz im Gegenteil, die Fähigkeit fremden Code zu analysieren ist eine wichtige Fähigkeit, die jeder Programmierer lernen muss. Also warum nicht hier damit anfangen?
spess53 schrieb: > Was mich verwundert ist, das du die Initialisierung hinbekommen hast (?) > und jetzt an der Ausgabe von einzelnen Zeichen scheiterst. Weil nur der obere Nibble benutzt wird, so klappt das auch wenn man keinen Plan vom 4Bit-Modus hat.
spess53 schrieb: > Hi > >>Das mit dem 8-Bit Modus habe ich ja hinbekommen. Nur der 4-Bit >>Modus macht mich noch fertig. > > Was mich verwundert ist, das du die Initialisierung hinbekommen hast (?) > und jetzt an der Ausgabe von einzelnen Zeichen scheiterst. Von RS > abgesehen werden die letzten Befehle der Initialisierung genau wie > Zeichen ausgegeben. > > Zeig mal deinen kompletten Code. > > Mfg Spess Der Code ist am Thread angehängt. s.o. Warum ich gerade daran verzweifel weiß ich auch nicht. Aber wahrscheinlich habe ich wirklich keinen Plan. Ich hoffe aber, dass ich ihn noch bekomme, wenn es mal funktioniert.
RS auf "High" oberes Nibble anlegen Enablepuls unteres Nibble anlegen Enablepuls Fertig!
Kai Wierzoch schrieb: > Der Code ist am Thread angehängt. s.o. Warum ich gerade daran verzweifel > weiß ich auch nicht. Aber wahrscheinlich habe ich wirklich keinen Plan. > Ich hoffe aber, dass ich ihn noch bekomme, wenn es mal funktioniert. Das Problem in deinem Code ist zum Bleistift das hier
1 | sendCommand(0b00000000);//Start: Display on/off |
2 | sendCommand(0b11110000);//Display: on, Cursor: on, Cursor: blinkender Block |
in Kombination mit
1 | void sendCommand(unsigned char command) |
2 | {
|
3 | checkBusy(); |
4 | LCDPORT = command; |
5 | LCDPORT &= ~ ((1<<RW)|(1<<RS)); |
6 | nopAbit(); |
7 | LCDPORT = 0; |
8 | }
|
Das was du mit dem doppelten Aufruf von sendCommand machst, sollte in Wirklichkeit die Funktion selber machen. Du übergibst der Funktion ein Byte und die Funktion selbst zerlegt sich das in 2 Stück 4-Bit Einheiten und bringt die auf den Weg. Es ist sinnlos, wenn du dieses Detail dem Aufrufer von sendCommand aufbrummst. Wie gesagt: Such dir anderen LCD-Code, der mit 4-Bit Ansteuerung umgehen kann und studiere, wie es dort gemacht wurde. Du willst es doch nach eigenen Aussagen lernen. Zum Lernen gehört genau das: Auch mal nachsehen, wie andere das machen. Davon kann man eine Menge lernen. Und zwar ohne dass dir hier im Forum die Antworter alles wieder von vorne vorkauen müssen.
Wollte nur bescheid geben, dass es funktioniert. Ich habe ein Beispielcode für 4-Bit Modus gefunden. Vielen Dank für euere Hilfe, Gruß Kai
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.