Forum: Mikrocontroller und Digitale Elektronik LCD HD44780 keine Characters


von Johannes Gerken (Gast)


Lesenswert?

Hallo,

ich habe ein HD44780 kompatibles Display (NHD-0420DZW-AG5) an einem 
Xmega angeschlossen. Initalisieren + Alle Befehle funktioniert supper. 
Wenn ich jetzt einen Buchstaben Schreiben will geht nur der Blinkende 
Cursor weiter aber es wird kein Buchstabe Angezeigt.
Ich schalte RW low und RS high, packe das Bitmuster für den ASCII code 
auf die datenleitungen 0-7 und pulsiere dann E...

Jemand eine Idee, woran es liegen könnte?

von Bernhard S. (b_spitzer)


Lesenswert?

Am Quellcode oder an deiner Beschaltung. Beides nicht gezeigt -> 
Glaskugel...

von Johannes Gerken (Gast)


Angehängte Dateien:

Lesenswert?

Hier ist mein code, Beschaltung:
1
#define DATA_PORT PORTA
2
#define LCD_RS IOPORT_CREATE_PIN(PORTB,2)    
3
#define LCD_E  IOPORT_CREATE_PIN(PORTB,0)    
4
#define LCD_RW IOPORT_CREATE_PIN(PORTB,1)
5
#define P_DB0 IOPORT_CREATE_PIN(PORTA,0)
6
#define P_DB1 IOPORT_CREATE_PIN(PORTA,1)
7
#define P_DB2 IOPORT_CREATE_PIN(PORTA,2)
8
#define P_DB3 IOPORT_CREATE_PIN(PORTA,3)
9
#define P_DB4 IOPORT_CREATE_PIN(PORTA,4)
10
#define P_DB5 IOPORT_CREATE_PIN(PORTA,5)
11
#define P_DB6 IOPORT_CREATE_PIN(PORTA,6)
12
#define P_DB7 IOPORT_CREATE_PIN(PORTA,7)
13
14
void lcd_set_write_instruction();
15
void lcd_set_write_data();
16
void lcd_write_byte (char c);
17
void lcd_clear_and_home();
18
void lcd_home();
19
void lcd_goto(uint8_t line, uint8_t pos);
20
void lcd_line_one();
21
void lcd_line_two();
22
void lcd_write_data(char c);
23
void lcd_write_string(char *x, uint8_t len );
24
void lcd_write_string_0(char *x);
25
void lcd_write_string_p(const char *s);
26
void lcd_init();
27
void lcd_set_on_off(uint8_t state);
28
void lcd_write_inst(uint8_t cmd);
29
30
31
32
33
  
34
//this function is directly called from main
35
//it init the display and trys to print some test chars. The result is only a blinking cursor that moves
36
void lcd_init()
37
{
38
39
    ioport_configure_pin(LCD_E, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
40
    ioport_configure_pin(LCD_RS, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
41
    ioport_configure_pin(LCD_RW, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
42
    
43
    ioport_configure_pin(P_DB0, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
44
    ioport_configure_pin(P_DB1, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
45
    ioport_configure_pin(P_DB2, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
46
    ioport_configure_pin(P_DB3, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
47
    ioport_configure_pin(P_DB4, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
48
    ioport_configure_pin(P_DB5, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
49
    ioport_configure_pin(P_DB6, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT);
50
    ioport_configure_pin(P_DB7, IOPORT_INIT_LOW | IOPORT_DIR_OUTPUT); 
51
52
  _delay_ms(250);
53
 
54
  // LCD display initialisation by instruction magic sequence
55
  lcd_set_write_instruction();
56
  lcd_write_inst(0x38);      // function set
57
  _delay_ms(100);
58
  lcd_write_inst(0x08);      // display on/off control
59
  _delay_ms(100);
60
  lcd_write_inst(0x01);      // display clear
61
  _delay_ms(100);
62
  lcd_write_inst(0x06);      // entry mode set
63
  _delay_ms(100);
64
  lcd_write_inst(0x02);
65
  _delay_ms(100);
66
  lcd_write_inst(0x0F);      
67
  _delay_ms(100);
68
  lcd_write_inst(0x0F);      
69
  _delay_ms(100);
70
  lcd_write_inst(0x39);      
71
  _delay_ms(100);
72
73
lcd_write_inst(0x80);  
74
75
  lcd_write_data('A');
76
  lcd_write_data('B');
77
  lcd_write_data('C');
78
  lcd_write_data('D');
79
  lcd_write_data('E');
80
81
82
 _delay_ms(100);
83
84
85
}
86
87
88
89
 void lcd_set_on_off(uint8_t state)
90
 {
91
   lcd_set_write_instruction();
92
   if(state==1)
93
   {
94
     lcd_write_byte(0x0F);
95
   }
96
   if(state==0)
97
   {
98
     lcd_write_byte(0x08);
99
   }
100
  
101
 }
102
 
103
// This function clears the RS line to write a command
104
void lcd_set_write_instruction()
105
 {
106
  ioport_set_pin_low(LCD_RS);    // set RS line low 
107
  _delay_ms(1);
108
}
109
 
110
 
111
// This function sets the RS line to write data
112
void lcd_set_write_data()
113
 {
114
  ioport_set_pin_high(LCD_RS);    // set RS line high
115
  _delay_ms(1);
116
  
117
}
118
 
119
120
121
 
122
// This function writes a byte to the LCD
123
void lcd_write_byte (char c)
124
 {
125
   ioport_set_pin_low(LCD_RW);
126
int output[CHAR_BIT];
127
int i;
128
for (i = 0; i < CHAR_BIT; ++i)
129
 {
130
  output[i] = (c >> i) & 1;
131
}
132
//manual approach
133
if(output[0]==1)
134
{
135
  ioport_set_pin_high(P_DB0);
136
}
137
else
138
{
139
  ioport_set_pin_low(P_DB0);
140
}
141
if(output[1]==1)
142
{
143
  ioport_set_pin_high(P_DB1);
144
}
145
else
146
{
147
  ioport_set_pin_low(P_DB1);
148
}
149
if(output[2]==1)
150
{
151
  ioport_set_pin_high(P_DB2);
152
}
153
else
154
{
155
  ioport_set_pin_low(P_DB2);
156
}
157
if(output[3]==1)
158
{
159
  ioport_set_pin_high(P_DB3);
160
}
161
else
162
{
163
  ioport_set_pin_low(P_DB3);
164
}
165
if(output[4]==1)
166
{
167
  ioport_set_pin_high(P_DB4);
168
}
169
else
170
{
171
  ioport_set_pin_low(P_DB4);
172
}
173
if(output[5]==1)
174
{
175
  ioport_set_pin_high(P_DB5);
176
}
177
else
178
{
179
  ioport_set_pin_low(P_DB5);
180
}
181
if(output[6]==1)
182
{
183
  ioport_set_pin_high(P_DB6);
184
}
185
else
186
{
187
  ioport_set_pin_low(P_DB6);
188
}
189
if(output[7]==1)
190
{
191
  ioport_set_pin_high(P_DB7);
192
}
193
else
194
{
195
  ioport_set_pin_low(P_DB7);
196
}
197
_delay_us(100);
198
  
199
  //DATA_PORT.OUT = c;      // Place data on Data Port
200
  ioport_set_pin_high(LCD_E);    // set E line high
201
  _delay_us(100);
202
  ioport_set_pin_low(LCD_E);    // set E line low to latch data into LCD
203
  _delay_ms(1);
204
}
205
 
206
 
207
// This function clears LCD and sets address to beginning of first line
208
void lcd_clear_and_home()
209
 {
210
  lcd_set_write_instruction();
211
  lcd_write_byte(0x01);
212
  _delay_ms(2);
213
  lcd_write_byte(0x02);
214
  _delay_ms(1);
215
 } 
216
 
217
// This function sets address to beginning of first line
218
void lcd_home()
219
{
220
  lcd_set_write_instruction();
221
  lcd_write_byte(0x02);
222
  _delay_ms(1);
223
}
224
 
225
 
226
// This function moves cursor to a given line and position
227
//  line is either 0 (first line) or 1 (second line)
228
//  pos is the character position from 0 to 15.
229
void lcd_goto(uint8_t line, uint8_t pos)
230
{
231
  uint8_t position = 0;
232
 
233
  lcd_set_write_instruction();
234
  switch(line)
235
  {
236
    case 0: position = 0;
237
    break;
238
    case 1: position = 0x40;
239
    break;
240
  }
241
    lcd_write_byte(0x80 | (position + pos));
242
}
243
 
244
 
245
// This function moves the cursor to 1st character of 1st line
246
void lcd_line_one() { lcd_goto(0, 0); }
247
 
248
 
249
// This function moves the cursor to 1st character if 2nd line
250
void lcd_line_two() { lcd_goto(1, 0); }
251
 
252
 
253
// This function writes a character to the LCD
254
void lcd_write_data(char c)
255
{
256
  //ioport_set_pin_high(P_LED2);
257
  lcd_set_write_data();
258
  lcd_write_byte(c);
259
//  lcd_write_inst(0x14);
260
  //ioport_set_pin_low(P_LED2);
261
}
262
 
263
void lcd_write_inst(uint8_t cmd)
264
{
265
  lcd_set_write_instruction();
266
  lcd_write_byte(cmd);
267
}
268
 
269
// This function writes a string (in SRAM) of given length to the LCD
270
void lcd_write_string(char *x, uint8_t len )
271
{
272
  while (--len > 0)
273
    lcd_write_data(*x++);
274
}
275
 
276
 
277
// This function writes a null-terminated string (in SRAM) to the LCD
278
void lcd_write_string_0(char *x)
279
{
280
  while (*x)
281
    lcd_write_data(*x++);
282
}
283
 
284
 
285
// Same as above, but the string is located in program memory,
286
//  so "lpm" instructions are needed to fetch it, and a \0
287
//  must be defined at the end of the string to terminate it.
288
void lcd_write_string_p(const char *s)
289
{
290
  char c;
291
 
292
  for (c = pgm_read_byte(s); c; ++s, c = pgm_read_byte(s))
293
    lcd_write_data(c);
294
}

von Bernhard S. (b_spitzer)


Lesenswert?

Bei Deinem Display ist Pin 3 als NC bezeichnet... üblicherweise ist dort 
die Konstrastspannung!?!? Woher hast Du die Pinbelegung?

von Bernhard S. (b_spitzer)


Lesenswert?

ok, gerade gesehen, dass das ein OLED ist. Also Kontrast und 
Hintergrundbeleuchtung sind damit hinfällig.
Wieso setzt Du bei der Initialisierung einige Register mehrfach auf 
gleiche bzw. unterschiedliche Werte??

von Hans Peter B. (Gast)


Lesenswert?

Warum hast du nicht die Ratschläge der Leute von AVRfreaks beherzigt, 
die sich sie Mühe machten deinen "Heuhaufen" näher anzusehen?
http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&p=952269

Du hättest wenigstens die dir aufgezeigten Fehler eliminieren können, 
bevor du das Forum gewechselt hast?

Hans Peter

von Johannes Gerken (Gast)


Lesenswert?

wirklich?
"Fehler"?
Die haben mir nicht einen Fehler gezeigt, die initalisierungs sequenz 
habe ich so vom NHD bekommen. Die haben mir gesagt, dass meinche 
Controller von denen sonnst nicht richtig initalisieren. Ich habe es 
auch schon anders und so wie im Datenblatt(was nicht geht) getestet.

"Hans Peter B" auf deine Antwort kann die Welt gerne verzichten....

von Bernhard S. (b_spitzer)


Lesenswert?

Hans Peter B. schrieb:
> Du hättest wenigstens die dir aufgezeigten Fehler eliminieren können,
> bevor du das Forum gewechselt hast?

Und du hättest auch lernen können, dass man bei solchen Problemen gleich 
mit Schaltplan und Quellcode ankommt. Die erste Antwort auf AVRfreaks 
war doch:
> Code? Schematics?

==> Beratungsresistent...

Zu Deinem Code: ist der Controller wirklich sooo vermurkst, dass man um 
einen 8-Bit Port mit einem 8-Bit Wert zu setzen erstmal ein Array aus 
INT füllen muss um anschließend eine IF/ELSE Orgie abzulassen??

Auch der Hinweis auf AVRfreaks zur mehrfachen Initialisierung einiger 
Register hast Du noch nicht geändert:

> ...(0x39); // 'Function set ' REDUNDANT and ILLEGAL

From the 'Function Set' information a few pages after Table 6:

 Note: Perform the function at the head of the program before executing 
any instructions (except for the read busy flag and address 
instruction). From this point, the function set instruction cannot be 
executed unless the interface data length is changed.

===>>> It is quite possible that this extra 'Function Set' at the end is 
causing your problem.  <<<===


Wirf mal die letzte Zeile aus deiner Initialisierung raus und passe die 
erste ggf. an.

von Bernhard S. (b_spitzer)


Lesenswert?

Boing...
Wieso versorgst Du das Display mit 5V, den Controller mit (vermutlich) 
3,3V? Laut Datenblatt ist "H" Level Input = 0.9 VDD also 4,5V bei 5V 
Versorgung (erscheint mir zwar recht hoch, aber wenn die das fordern)

Das Display kann auch 3V, also umklemmen.

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
Noch kein Account? Hier anmelden.