Hallo, jetzt hab ich das Problemchen mit der Initialisierung von dem DOGM081 LCD gelöst, schon kommt das Nächste. Die Routine für die selbstdefinierten 8 Zeichen ist aus dem Tutorial. Aber es scheint, als wenn ich mehr als 5 Zeichen definiere, dann geht das schief. Beim 6. Zeichen wird das erste korrupt. Beim 7. Zeichen sinds dann zwei. Und bei allen 8 sinds drei. Hat jemand eine Idee ? Ich denke, der Adressbereich ist 0x40 + 8 für jedes weitere Zeichen. Oder ? In dem PDF vom DOGM081 finde ich dazu leider nichts. Viele Grüße Tobi
@ Tobi (Gast) >Ich denke, der Adressbereich ist 0x40 + 8 für jedes weitere Zeichen. >Oder ? Ja. Du musst aufpassen, deine Funktion funktioniert nur, wenn Auto Increment im LCD aktiv ist. MFG Falk
Hallo Falk, hab ich nicht die Auto Inkrement Funktion eingestellt ? In der Init Sequenz steht #06 drin... Viele Grüße Tobi
Was ich auch sehr seltsam finde. Ich habe mal testweise nach der Initialisierung alle 8 Zeichen dargestellt. Dabei gehen die Zeichen 2 und 3 nicht. An einem späteren Zeitpunkt im Programm rufe ich erneut die Routine LCD_Data(... auf und dann gehen die Zeichen 3,4,5,6 und 7 nicht richtig. Zeichen 3 ist leer. Zeichen 4 ist wie Zeichen 2 um eine Pixel-Linie nach oben verschoben. Zeichen 5 ist fast wie Zeichen 1, um eine Pixel-Linie nach oben verschoben. Und Zeichen 7 ist auch fast wie Zeichen 7 sein soll, nur um eine Pixel-Linie nach oben verschoben... Zeichen 6 ist kompletter Datenmüll. Ich versteh das nicht.
Niemand 'ne Idee ? Ich hab mal ein anderes (16x2) Display versucht. Gleiche Symptomatik. Liegt also nicht am DOGM081. Auch wenn ich die Arrays mit den Benutzerdefinitionen tausche ändert sich nichts. Das "fehlerhafte" Bild wandert mit. Aber in der Benutzerdefinition finde ich keinen Fehler. Sobald ich nicht alle 8 Zeichen ins CGRAM lade gehts... (also die restlichen 7). Dabei ist es egal, welches Zeichen ich nicht lade... Ich verstehs nicht. Bin ich blöd oder blind ? Viele Grüße Tobi
Versuch das mal:
void lcd_generatechar(uint8_t code, const uint8_t *data)
{
// Startposition des Zeichens einstellen
lcd_command(LCD_SET_CGADR|(code<<3));
// Bitmuster übertragen
for (uint8_t i=0; i<8; i++)
{
lcd_data(data[i]);
}
lcd_command(0x80); //DD_RAM Adresse 0 setzen, besser ist das
}
Hi
>Bin ich blöd oder blind ?
Das musst du entscheiden. Aber es sieht so aus, als ob du versuchst 9
(0...8) eigene Zeichen in 8 Speicherplätze zu quetschen.
MfG Spess
Hm.
Meine Sequenz schaut grad so aus:
void lcd_generatechar(uint8_t code, const uint8_t *data)
{
// Startposition des Zeichens einstellen
lcd_command(0x40|(code<<3));
// Bitmuster übertragen
for (uint8_t i=0; i<8; i++)
{
lcd_data(data[i]);
}
lcd_command(0x80);
}
Also eigentlich quasi identisch.
Ich habs auch schonmal versucht die Adressen einzeln zu schreiben.
Also 40,48,50,58,60,68,70 und 78.
Spess, der Gedanke kam mir auch. Irgendwie schauts so aus.
Aber ich versteh nicht wo ich das machen würde.
Für mich siehts so aus, als ob ich nur von 0 bis 7 zählen würde.
Tobi schrieb: > Spess, der Gedanke kam mir auch. Irgendwie schauts so aus. > Aber ich versteh nicht wo ich das machen würde. lcd_data(LCD_GC_CHAR0); lcd_data(LCD_GC_CHAR1); lcd_data(LCD_GC_CHAR2); lcd_data(LCD_GC_CHAR3); lcd_data(LCD_GC_CHAR4); lcd_data(LCD_GC_CHAR5); lcd_data(LCD_GC_CHAR6); lcd_data(LCD_GC_CHAR7); lcd_data(LCD_GC_CHAR8); Zähl nach: Sind 9 Stück. (WIe du das durch den Compiler gebracht hast, weiß ich allerdings nicht.) Drum wäre es eine extrem gute Idee, hier
1 | void lcd_generatechar(uint8_t code, const uint8_t *data) |
2 | {
|
3 | // Startposition des Zeichens einstellen
|
4 | lcd_command(0x40|(code<<3)); |
5 | |
6 | // Bitmuster übertragen
|
7 | for (uint8_t i=0; i<8; i++) |
8 | {
|
9 | lcd_data(data[i]); |
10 | }
|
11 | lcd_command(0x80); |
12 | }
|
die übergebene code Nummer sicherheitshalber noch auf 0 bis 7 einzuschränken.
1 | void lcd_generatechar(uint8_t code, const uint8_t *data) |
2 | {
|
3 | // Startposition des Zeichens einstellen
|
4 | lcd_command( 0x40 | ((code & 0x07) << 3) ); |
das schützt schon mal vor falschen Argumenten. Edit: flascher Alarm. Das ist ja nur der Aufruf der Zeichen. Die Definition sieht ok aus. Hmm. Timingproblem? Dem LCD nach der Definition ein wenig Zeit geben?
Öha. Gut das kann sein. Im aktuellen Code steht inzwischen: lcd_generatechar(1, chrdata0); lcd_generatechar(2, chrdata2); lcd_generatechar(3, chrdata3); lcd_generatechar(4, chrdata4); lcd_generatechar(5, chrdata5); lcd_generatechar(6, chrdata6); lcd_generatechar(7, chrdata7); lcd_generatechar(0, chrdata1); Ich glaub, ich hänge mal den ganzen aktuellen Code an. Da hab ich die letzten Tage so oft dran was verändert.
Hab die Zeile mal noch implementiert. Aber es ändert nichts. Ich hab auch nochmal in den originalen Code geschaut. Da wurden nur 8 Zeichen ins CGRAM geschrieben. Es wurde ein LCD_data für das 9. Zeichen angefragt, das stimmt. Aber das ist schon lang raus.
Hi >Ich glaub, ich hänge mal den ganzen aktuellen Code an. >Da hab ich die letzten Tage so oft dran was verändert. Warum postest du nicht C-File? Dann gibt es auch eine Code-Ansicht. MfG Spess
Timing ? Gut möglich, an welcher Stelle ? Nach der Intialisierung ? Zwichen dem CGRAM-Beschreiben ? (Hab ich schonmal 100ms probiert, ging net)
@ Tobi (Gast) >Ich glaub, ich hänge mal den ganzen aktuellen Code an. Und warum hängst du den nicht DIREKT an, als .c Datei? Dann würde er auch schon mit Syntax Highlighting dargestellt werden. Siehe Netiquette.
Sorry. Ich werde es mir in Zukunft merken. 100ms Pause nach der Initialisierung und vor dem ersten Schreiben eines Arrays in das CGRAM ging auch nicht.
Tobi schrieb: > Sorry. Ich werde es mir in Zukunft merken. > > 100ms Pause nach der Initialisierung und vor dem ersten Schreiben eines > Arrays in das CGRAM ging auch nicht. Dazwischen! Nach jeden Byte einfach mal, Hausnummer, 10 Millisekunden warten.
1 | void lcd_generatechar(uint8_t code, const uint8_t *data) |
2 | {
|
3 | // Startposition des Zeichens einstellen
|
4 | lcd_command(0x40|(code<<3)); |
5 | _delay_ms( 10 ); |
6 | |
7 | // Bitmuster übertragen
|
8 | for (uint8_t i=0; i<8; i++) |
9 | {
|
10 | lcd_data(data[i]); |
11 | _delay_ms( 10 ); |
12 | }
|
13 | lcd_command(0x80); |
14 | _delay_ms( 10 ); |
15 | }
|
Ist ein Schuss ins Blaue. Zugegeben.
Gute Idee ! Habs gleich mal ausprobiert... Leider negativ. Weder 10ms, noch 50ms. Sowohl nach dem Commando-Aufruf für die Adresse. Als auch nach jedem Byte.
Holger, irgendwie blick ich da nicht durch. Dein Script ist so allgemeingültig mit so vielen Definitionsvarianten....
Hallo nochmal, kann ich hier auch Teile eines C-Programms attachen ? Ich möchte das Programm auf das Wesentliche reduzieren. Und aber der Netiquette entsprechend keine Text-Files anhängen. Es scheint wohl so, daß nicht (nur?) die LCD Ansteuerungs Routine das Problem ist. In meinem Programm wird ein PGA Lautstärke-Steller angesteuert. Die Lautstärke-Werte werden durch einen Drehinkrementalgeber ermittelt. Also gibt es irgendwo eine Schleife für die Dekodierung des Gray-Codes. Das funktioniert auch. Wenn ich aber z.B. in die Schleife eine zusätzliche Abfrage des B-Portes einfüge, an dem der Taster für das Muting angeschlossen ist, ändern sich die Zeichen, die nicht gehen. Weiterhin habe ich einen Zähler, der die Gray-Code-Schleife hochzählt. Erreicht er einen Wert von 150.000, dann wird das Display mit Leerzeichen geblanked. Diese Abfrage führt ebenfalls dazu, daß sich andere Zeichen nicht mehr richtig darstellen lassen. Wenn ich diese beiden Teile rausnehme, geht immerhin nur noch die 2 nicht mehr. Es scheint also nicht direkt mit den LCD-Routinen zu tun zu haben. Irgendwo pfuscht das Programm da an anderer Stelle rein. Der ermittelte Lautstärkewert steht am Ende in der Variable "zaehler" und wird an die LCD-Routine und den PGA übergeben. Ich dachte auch daran, daß diese Variable dann nicht mehr geht. Aber das stimmt nicht. Auch wenn ich da fixe Werte reinschreibe, hängt die Ausgabe davon ab, ob in der Gray-Code-Schleife die besagten Teile drin sind, oder nicht... Ich versteh das nicht. Viele Grüße Tobi
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.