Forum: Mikrocontroller und Digitale Elektronik Ansteuerung LCD Display an Port C


von Stefan G. (stefan1982)


Lesenswert?

Hallo,

ich habe eine Problem mit meinem Code bei der Ansteuerung des LCD 
Display an einem ATmega16

Ansteuerung LCD Routine:
1
#define LCD_CLEAR    0x01  // clear display     0b 0000 0001
2
#define LCD_HOME    0x02  // cursor home      0b 0000 0010
3
#define LCD_ON      0x0C  // cursor invisible    0b 0000 1100
4
#define LCD_OFF      0x08  // display off      0b 0000 1000
5
#define POS_01      0x80  // line 1 - column 0  0b 1000 0000
6
#define POS_02      0xC0  // line 2 - column 0  0b 1100 0000
7
8
#define  LCDPORT      PORTC  // define port with LCD attached
9
#define  LCDDDR      DDRC  // and its data direction
10
11
// define pins of LCD port
12
#define LCD_PIN_RS    2    
13
#define LCD_PIN_E    3
14
#define LCD_PIN_D4    4
15
#define LCD_PIN_D5    5
16
#define LCD_PIN_D6    6
17
#define LCD_PIN_D7    7
18
19
// DEFINITIONS
20
#define sbi(PORT, bit)     (PORT|=(1<<bit))  // set bit        
21
#define cbi(PORT, bit)     (PORT&=~(1<<bit))  // claear bit
22
#define tbi(PORT, bit)     (PORT^=(1<<bit))  // toggle bit
23
24
#define  COMMAND      0
25
#define DATA      1
26
27
// Function: Toggle enable pin 
28
void toggle_enable_pin(void)
29
{
30
  sbi(LCDPORT, LCD_PIN_E);
31
  cbi(LCDPORT, LCD_PIN_E);  
32
}
33
34
// Send Byte to LCD Controller
35
void lcd_send(unsigned char type, unsigned char c)
36
{
37
  unsigned char sic_c;          // Backup for c
38
  // send high nibble
39
  sic_c = c;                // save original c
40
  sic_c &= ~0x0f;              // set bit 0-3 == 0
41
  if (type==DATA)
42
    sic_c |= (1<<LCD_PIN_RS);      // Data: RS = 1
43
  LCDPORT = sic_c;            // send high nibble
44
  toggle_enable_pin();
45
  // send low nibble
46
  sic_c = c;                // save original c
47
  sic_c = sic_c<<4;            // exchange nibbles
48
  sic_c &= ~0x0f;              // set bit 0-3 == 0
49
  if (type==DATA)
50
    sic_c |= (1<<LCD_PIN_RS);      // Data: RS = 1
51
  LCDPORT = sic_c;            // send low nibble
52
  toggle_enable_pin();
53
  _delay_ms(5);              // Wait for LCD controller
54
}
55
56
// set cursor to line x and column y
57
void lcd_set_cursor(uint8_t x, uint8_t y)
58
{
59
  uint8_t i;
60
 
61
  switch (x) 
62
  {
63
    case 1: i=0x80+0x00+y; break;    // 1. line
64
    case 2: i=0x80+0x40+y; break;    // 2. line
65
    default: return;                   // invalid line
66
  }
67
  lcd_send(COMMAND, i);
68
}
69
70
// Display String on LCD
71
void lcd_write(char *t)
72
{
73
  unsigned char i;
74
  for (i=0;i<255;i++)
75
  {
76
    if (t[i]==0) // End of String -> EXIT
77
      return;
78
    else 
79
      lcd_send(DATA, t[i]);
80
  }
81
}
82
83
84
// initializing LCD Controller see data sheet for details
85
void lcd_init()
86
{
87
  // Set LCD port to Output
88
  LCDPORT = 0x00;
89
  LCDDDR  = 0xFF;
90
91
  _delay_ms(50); // wait for LCD
92
93
  // 4-bit Modus config
94
  sbi(LCDPORT, LCD_PIN_D5);
95
  cbi(LCDPORT, LCD_PIN_D4);
96
97
  // 4-Bit mode start 
98
  sbi(LCDPORT, LCD_PIN_E);
99
  cbi(LCDPORT, LCD_PIN_E);
100
  _delay_ms(5); 
101
102
  // 2 Lines, 4-Bit Mode
103
  lcd_send(COMMAND, 0x28);
104
105
  lcd_send(COMMAND, LCD_OFF);
106
  lcd_send(COMMAND, LCD_CLEAR);
107
108
  lcd_send(COMMAND, 0x06);
109
  lcd_send(COMMAND, LCD_ON);
110
}

Hauptprogramm:
1
int main()
2
{  lcd_init();
3
  lcd_send(COMMAND, LCD_CLEAR); ;
4
  lcd_set_cursor(1, 0); lcd_write (" Test Hallo");
5
while (1)    
6
  {  
7
  }
8
}


Das LCD Display ist wie folgt angeschlossen:

Pin

1 GND
2 Vcc
3 Kontrast (Daran liegt es nicht)
4 PC2
5 GND
6 PC3
11 PC4
12 PC5
13 PC6
14 PC7

Woran könnte es liegen, wenn ich das Display einschalte ist die erste 
Reihe  schwarz....mehr passiert nicht!!

Danke schon mal

von Karl H. (kbuchegg)


Lesenswert?

Ohne weiter nachgeshehen zu haben:

Probleme, PORTC, ATMega16

-> ist das JTAG Interface abgeschaltet? (die Fuse JTAGEN abschalten)

von Stefan G. (stefan1982)


Lesenswert?

Oha nein.....

.....stimmt darüber habe ich schonmal was gelesen....wie mache ich 
das???

von Stefan G. (stefan1982)


Lesenswert?

Ok, jetzt hab ichs abgeschaltet,

allerdings habe ich jetzt anstatt einer Zeile die schwarz ist zwei 
Zeilen die schwarz sind

von Georg G. (df2au)


Lesenswert?

Stefan Grunner schrieb:
> // initializing LCD Controller see data sheet for details

Das solltest du als erstes mal machen und die Initialisierungsroutine 
entsprechend anpassen.

Und das hier
  sic_c = sic_c<<4;            // exchange nibbles
  sic_c &= ~0x0f;              // set bit 0-3 == 0

macht auch nicht das, was du vermutlich erwartest.

von Karl H. (kbuchegg)


Lesenswert?

Dann stell mal den Kontrast des LCD sauber ein. Am Poti drehen, welches 
du ja für die Einstellung der Kontrastspannung vorgesehen hast.

von Stefan G. (stefan1982)


Lesenswert?

Das versteh ich nicht....was ist daran falsch?

von Karl H. (kbuchegg)


Lesenswert?

Georg G. schrieb:

> Und das hier
>   sic_c = sic_c<<4;            // exchange nibbles
>   sic_c &= ~0x0f;              // set bit 0-3 == 0
>
> macht auch nicht das, was du vermutlich erwartest.

:-)
Der Kommentar ist falsch, der Code ist aber ok.

Erwarten wird er nicht viel, den Code hat er nicht selbst geschrieben, 
den hab ich schon mal gesehen.

@TO
Wo stammt der Code eigentlich her? Das ist so ziemlich der 
miselsichtigste LCD Code, der hier immer wieder mal auftaucht.

von Stefan G. (stefan1982)


Lesenswert?

Oha..

klar das Poti....bestehend aus den 6 Widerständen auf dem 
Steckbrett....wo einer dann doch zuviel war....also es läuft dann jetzt 
mit abgeschalteten JTag...

Vielen dank Leute

von Georg G. (df2au)


Lesenswert?

Die erste Zeile schiebt sic_c um 4 Stellen nach links und füllt rechts 
mit Nullen auf. Nix mit vertauschen.

: Bearbeitet durch User
von Karl H. (kbuchegg)


Lesenswert?

Georg G. schrieb:
> Die erste Zeile schiebt sic_c um 4 Stellen nach links und füllt rechts
> mit Nullen auf. Nix mit vertauschen.

Ignorier den Kommentar einfach.
Mach ich auch :-)

Wer sowas, wie die lcd_init Funktion für eine ordentliche 
Initialisierung hält, sich nicht darum kümmert, dass Pulse auch eine 
gewisse Mindestlänge haben müssen, dem kannst du korrekte Kommentare 
nicht zutrauen. Zumal diese Art der Kommentierung sowieso eine von der 
sinnlosen Sorte ist.

: Bearbeitet durch User
von Georg G. (df2au)


Lesenswert?

Die zweite Zeile hätte man auch etwas schöner schreiben können. Der TO 
ist offenbar Bayer (doppelte Verneinung, döas ham ma nia net anders 
gmacht)
sic_c &= 0xf0; wäre imho lesbarer.

von Karl H. (kbuchegg)


Lesenswert?

Ich finde ja den Teil hier
1
#define LCD_PIN_RS    2    
2
#define LCD_PIN_E    3
3
#define LCD_PIN_D4    4
4
#define LCD_PIN_D5    5
5
#define LCD_PIN_D6    6
6
#define LCD_PIN_D7    7
gelungen.
Der suggeriert eine Konfigurierbarkeit, die .... einfach nicht vorhanden 
ist.

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.