Elettronicamente.com
La risorsa Italiana per l'elettronica
e l'informatica applicata all'elettronica
  Sponsor
|Home| |Registrazione| |Login| |Disclaimer| |Contattaci| |Guida| |FAQs|
|Download| |Forum| |Links| |MySite|
Cerca in Elettronicamente:
 
I numeri di Elettronicamente.com:
  Iscritti: 12848
  Risorse On-Line: 508
  Links su siti di elettronica: 1304
  Sei il visitatore numero 1170277
Login non eseguito
Descrizione
ID #751  Microcontroller
Pilotare un Display compatibile HD44780   02/08/2009
I display basati sul controllore Hitachi HD44780 sono molto diffusi e facili da usare, questo tutorial spiega come controllare uno dei tanti cloni disponibili, come i KS0066, i S6A0069, i SED1278, i ST7066 o i SPLC780A1. Io ho usato un TM204 (vedi foto) che permette di visualizzare ben 20 caratteri disposti su 4 linee.

Il tutorial contiene anche i codici sorgenti compatibili con DaVE per il Microcontrollore Infineon XE164.
Difficoltà:
Difficoltà di realizzazione o apprendimento. 2 stella/e.

Voto:
4
Voto attuale (1/10) calcolato in base alla media delle votazioni di tutti gli iscritti che hanno votato questa risorsa.

Autore:
boldinid
Autore della risorsa:boldinid
HTML:
In questa casella viene indicato se è disponibile una pagina web da visualizzare.
File:
Allegato disponibile: HD44780.zip
In questa casella viene indicato se è disponibile un file da scaricare.

Crediti Virtuali:
40
Crediti virtuali necessari per scaricare il file allegato:40

Status:
ONLINE
Download file: HD44780.zip
Dimensioni: 3,1 Kb
Devi eseguire il login per poter scaricare questo file.
Pilotare un Display compatibile HD44780
NOTA: Alcune parti di questo tutorial sono state gentilmente concesse dal sito: www.giobe2000.it
Su www.giobe2000.it troverete un altro ottimo tutorial sul controller LCD HD44780:
http://www.giobe2000.it/HW/HD44780/pag/gest_HW.htm


Introduzione a HD44780

Di certo un display LCD è assolutamente inutile senza un circuito elettronico in grado di gestirlo e, dato l'oneroso compito a cui è chiamato, sembra improbabile solo pensare a realizzarlo con componenti discreti. Per questo il mercato offre strutture integrate (moduli) dotate di tutto ciò che serve, montato su un circuito stampato; da un lato è saldato il display e sul lato opposto sono presenti numerosi componenti, tra cui circuiti integrati. Certamente il più importante tra questi è il controller, un componente programmabile con una duplice funzione:

  • dispone della struttura necessaria per gestire fino a 50 (10 * 5) pixel per ciascuno dei possibili caratteri alfanumerici del display, organizzati su una o più righe;
  • assicura l' interfaccia intelligente tra il visualizzatore e il processore o il microcontrollore chiamato a gestirlo.

Il controller di gran lunga più diffuso ed utilizzato sul mercato è senz'altro il controller HD44780 della Hitachi, quasi uno standard di fatto.
Lo schema a blocchi di un display basato su HD44780 è tipicament questo (io riporto lo schema per il modello TM204):


Piedinatura del modulo LCD

N. Pin Nome I/O Descrizione
1 Vss Power Massa
2 Vcc Power +5V
3 Vo Analog Regolazione contrasto
4 RS Input Selezione dati/istruzioni
5 R/W Input Read/Write
6 E Input Abilitazione
7 D0 I/O Dati LSB
8 D1 I/O Dati
9 D2 I/O Dati
10 D3 I/O Dati
11 D4 I/O Dati
12 D5 I/O Dati
13 D6 I/O Dati
14 D7 I/O Dati MSB
15 A Power Retroilluminazione (+)
16 K Power Retroilluminazione (GND)
Tab.1 - Assegnazione Pin
  • I pin 1 (Vss) e 2 (Vcc) servono per fornire alimentazione (5 volt); di solito l'assorbimento è contenuto, dell'ordine di pochi mA.
  • Il pin 3 (Vo) è un ingresso analogico al quale si deve fornire una tensione compresa tra 0 e 5V al fine di regolare il contrasto del display, cioè la capacità di rendere più o meno scuri i pixel attivi, per rendere migliore la visualizzazione, in funzione della luminosità dell’ambiente, del display; di solito la regolazione si ottiene con un potenziometro da 10k.
  • Il pin 4 (RS), detto Register Selector, indica la natura dell’informazione presente sul bus dati: se viene forzato a 0 il byte in ingresso sarà interpretato come un comando da eseguire (istruzione), mentre con un 1 sarà ritenuto dato da interpretare.
  • Il pin 5 (R/W) specifica la direzione dei bytes sul bus: se vale 0 si sta scrivendo nella memoria interna LCD, mentre con un 1 questa memoria è sottoposta a lettura.
  • Il pin 6 (E) è il segnale che abilita il dispositivo: quando è a livello alto sincronizza la lettura del dato o del comando predisposto sul bus dati. L'Enable è il vero e proprio segnale di sincronismo, da forzare a 1 quando il dispositivo è pronto a gestire un dato o un comando predisposto sul bus dati (in funzione del valore del busy flag: finché il suo valore è 1 il controller è occupato a gestire i trasferimenti interni e non è in grado di accettare l'istruzione successiva).
  • I pin dal numero 7 al numero 14 (D0-D7) rappresentano il Data Bus su cui avviene la trasmissione o ricezione dati dal display, in base all’operazione che si sta svolgendo
  • I pin 15 e 16, mediante i quali è possibile alimentare l'eventuale luce di retroilluminazione.

    Lo schema di connessione al microcontrollore è molto semplice:

Il transistor BC547 è utilizzato per accendere la retroilluminazione. 

Set Caratteri disponibili in ROM

Questa struttura si basa sulla presenza di una capace memoria CGROM (Character Generator Read Only Memory), contenente i font dei 208 caratteri da 5x8 punti (8320 bit) e dei 32 caratteri da 5x10 punti (1600 bit). Il codice del carattere che si desidera visualizzare, fornito come dato al controller, consente di localizzare la matrice di punti corrispondente all'interno di questa memoria a sola lettura, in accordo con la seguente tabella:

Tab.2 - Codici carattere per matrice 5x8
Tab.2 - Codici carattere per matrice 5x8


Il set di istruzioni

Il componente HD44780 è nato per costituire un'interfaccia con qualunque microprocessore o controllore di processo in grado di fornire i 2 segnali R/W e RS che regolano il traffico d'informazioni del suo bus dati a 8bit. Anche una porta parallela può simulare con estrema facilità questa gestione.
Naturalmente diventa importante imparare le istruzioni che consentono il controllo alla CPU esterna; alcune istruzioni sono dedicate al controllo del visualizzatore, altre alla gestione dei dati sulle 2 RAM.
Le istruzioni (bytes di comando) necessarie per controllare il display sono raccolte nella tabella seguente:

Istruzione Input Data Bus Descrizione Tempo MAX
RS R/W D7 D6 D5 D4 D3 D2 D1 D0
NOP 0 0 0 0 0 0 0 0 0 0 Nessuna operazione 0s
Cancella display 0 0 0 0 0 0 0 1 Cancella il visualizzatore e fa tornare il cursore alla posizione 0. 1,64ms
Cursore a capo 0 0 0 0 0 0 1 - Riporta il cursore alla posizione 0. 1,64ms
Modo d'accesso dei caratteri 0 0 0 0 0 1 I S Imposta la direzione del movimento del cursore (I/D) e specifica se muovere il display (S). Queste operazioni sono fatte durante la lettura/scrittura dati. 40µs
Controllo Display 0 0 0 0 1 D C B Imposta il display On/Off (D), il cursore On/Off (C) e il lampeggio del cursore (B). 40µs
Scorrimento cursore e display 0 0 0 1 S/C R/L - - Imposta il movimento del cursore o lo spostamento del display (S/C) e la direzione del movimento. Il contenuto della DDRAM rimane invariato. 40µs
Impostazioni Funzioni 0 0 1 DL N F - - Imposta la lunghezza dei dati dell'interfaccia (DL), il numero di linee del display (N) e il font del carattere (F). 40µs
Indirizzo CGRAM 0 1 CGRAM Address Imposta l'indirizzo della CGRAM. Il dato CGRAM deve essere inviato o ricevuto dopo questa impostazione. 40µs
Indirizzo DDRAM 1 DDRAM Address Imposta l'indirizzo della DDRAM. Il dato CGRAM deve essere inviato o ricevuto dopo questa impostazione. 40µs
Lettura Bit di Stato/Indirizzo 1 BF Address Counter Legge Busy Flag e l'Address Counter 0s
Scrittura dato 1 0 Dato da scrivere Scrive un dato nella CGRAM o nella DDRAM 40µs
Lettura dato 1 Dato da leggere Legge un dato dalla CGRAM o dalla DDRAM 40µs
Tab.3 - Set di istruzioni del controller HD44780

Driver SW per HD44780

Il driver SW è del tutto parametrico e facile da utilizzare con qualunque Microcontrollore anche se non Infineon XE164. Prima di procedere alla compilazione, bisogna procedere a configurare le porte utilizzate per la connessione, il file HD44780.h deve essere perciò modificato a seconda delle proprie esigenze:

// Port Connection Defines
#define RS_LINE                 P1_OUT_P4
#define RW_LINE                 P1_OUT_P5
#define E_LINE                  P1_OUT_P7

#define DATA_PORT               P0
#define DATA_PORT_OUT           P0_OUT
#define DATA_PORT_IN            P0_IN
#define CONTROL_DATA_PORT_0     CONTROLIO_P0_0
#define CONTROL_DATA_PORT_1     CONTROLIO_P0_1
#define CONTROL_DATA_PORT_2     CONTROLIO_P0_2
#define CONTROL_DATA_PORT_3     CONTROLIO_P0_3
#define CONTROL_DATA_PORT_4     CONTROLIO_P0_4
#define CONTROL_DATA_PORT_5     CONTROLIO_P0_5
#define CONTROL_DATA_PORT_6     CONTROLIO_P0_6
#define CONTROL_DATA_PORT_7     CONTROLIO_P0_7
#define CONTROL_RS_LINE         CONTROLIO_P1_4
#define CONTROL_RW_LINE         CONTROLIO_P1_5
#define CONTROL_E_LINE          CONTROLIO_P1_7


Come visibile io ho utilizzato le porte P1.4 per RS, P1.5 per RW, P1.7 per E. La porta dati è connessa alla porta P0 del Microcontrollore XE164 percui i pins P0.0 ... P0.7 devono essere configurati opportunamente dal SW mediante la chiamata della funzione ""LCDinitialize


//****************************************************************************
// @Function     LCDinitialize
//
//----------------------------------------------------------------------------
// @Description   Inizialize LCD display, this fuction is the first routine to call
//   sets the control port and the data port
//
//----------------------------------------------------------------------------
// @Returnvalue   None
//
//----------------------------------------------------------------------------
// @Parameters    None
//
//----------------------------------------------------------------------------
// @Date          21/05/2009
//
//****************************************************************************

void LCDinitialize(void)
{
// Display control Port
 IO_vSetPinOut ( _RS_LINE, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _RW_LINE, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _E_LINE, IO_PUSH_PULL) ;
// Display Data Port
 IO_vSetPortOut ( DATA_PORT, 0xFF);         
 IO_vSetPinOut ( _DATA_PORT_0, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_1, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_2, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_3, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_4, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_5, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_6, IO_PUSH_PULL) ;
 IO_vSetPinOut ( _DATA_PORT_7, IO_PUSH_PULL) ;

 DATA_PORT_OUT = 0x00;
 RS_LINE = 0;
 RW_LINE = 0;
 E_LINE = 1;
 GPT2_waitXXms(20);
 LCDwriteCtrl(0x38); //function set
 GPT2_waitXXms(10);
 LCDwriteCtrl(0x38); //function set
 GPT2_waitXXms(1);
 LCDwriteCtrl(0x08); //disp off
 GPT2_waitXXms(1);
 LCDwriteCtrl(0x06); //entry mode set
 GPT2_waitXXms(1);
 LCDwriteCtrl(0x01); //display clear
 GPT2_waitXXms(10);
 LCDwriteCtrl(0x0c); //disp on
 GPT2_waitXXms(1);
}


Le funzioni seguenti non necessitano di molti commenti:
  • void LCDhome(void);        --> setta il cursore nella posizione Home
  • void LCDclear(void);         --> pulisce lo schermo
  • void LCDdispON(void);     --> accende il display
  • void LCDdispOFF(void);    --> spegne il display
  • void LCDgoToPos(ubyte line, ubyte pchar);     --> sposta il cursore in (line, pchar)
Il cuore del Driver SW è la funzione "LCDwriteString":
//****************************************************************************
// @Function     LCDwriteString
//
//----------------------------------------------------------------------------
// @Description   Write  a string
//
//----------------------------------------------------------------------------
// @Returnvalue   None
//
//----------------------------------------------------------------------------
// @Parameters     String to be written
//
//----------------------------------------------------------------------------
// @Date          21/05/2009
//
//****************************************************************************
void LCDwriteString(sbyte *string)
{
 uword inx=0;
 while(string[inx] != '\0')
 {
  LCDwriteChar(string[inx]);
  inx++;
 }
}

Infine la funzione "LCDtest" permette di eseguire una sequenza di visualizzazione a modi test di accensione:
//****************************************************************************
// @Function      LCDtest
//
//----------------------------------------------------------------------------
// @Description   Test the correct functioning of displaly
//
//----------------------------------------------------------------------------
// @Returnvalue   None
//
//----------------------------------------------------------------------------
// @Parameters    None
//
//----------------------------------------------------------------------------
// @Date          21/05/2009
//
//****************************************************************************
void LCDtest(void)
{
 ubyte check1[] = {0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff};
 ubyte check2[] = {0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80, 0xff, 0x80};
 LCDgoToPos(1,1);
 LCDwriteString(check1);
 LCDgoToPos(2,1);
 LCDwriteString(check2);
 LCDgoToPos(3,1);
 LCDwriteString(check1);
 LCDgoToPos(4,1);
 LCDwriteString(check2);
 LCDwait60cycles();
 LCDgoToPos(1,1);
 LCDwriteString(check2);
 LCDgoToPos(2,1);
 LCDwriteString(check1);
 LCDgoToPos(3,1);
 LCDwriteString(check2);
 LCDgoToPos(4,1);
 LCDwriteString(check1);
 LCDwait60cycles();
 LCDclear();
}

Nota:
Il Driver SW per HD44780 si basa su due funzioni di ritardo per poter eseguire le operazioni con le corrette tempistiche (così come definite nella Tab.3):
  • void LCDwait60cycles(void);     --> una semplice funzione per eseguire un breve ritardo
  • extern void GPT2_waitXXms (unsigned int i);   // Not defined in this project file since is application related. In case of not having any available timer, just replace with a \for{ _nop();}  statement
Percui dovete predisporre la funzione "GPT2_waitXXms" che avrà lo scopo di ritardare l'esecuzione di xx msec (cioè esegue un ritardo pari a "i" in millisecondi, ad esempio "GPT2_waitXXms (5)" deve generare un ritardo pari a 5 msec).

Futuri Sviluppi


Anche se non ne ho parlato, dovete sapere che è anche possibile definire il proprio set di caratteri e realizzare semplici grafiche come ad esempio un visualizzatore a barra (proporzionale perciò ad una grandezza analogica):

Buon lavoro !!!!
  Cloud
 Elettronicamente.com  PICmicro  RS232 FT232 P8X32A Parallax PIC16F84 Programmatore Elettronica PCB Circuito Stampato Fotoincisione Microchip PIC16F876 Linguaggio AVR Linux NE555 ARM HD44780 DISPLAY LCD Alimentatore XE164 Infineon LED Amplificatore Laboratorio Resistenza Condensatore Termometro PWM relazione
www.Elettronicamente.com
Utenti attualmente connessi:
(Nessuno)