///************************************************************************/ // usando LCD 20X4 // Version : 1.0 // microcontrolador : AVR ATMega8 // Autor : Aguivone // descrição : usando lcd interface de 4 bits // data : 20/10/2011. // //************************************************************************/ #define F_CPU 4000000UL // 4 MHz #include <avr/io.h> #include <avr/interrupt.h> #include <stdio.h> #include <util/delay.h> #include <string.h> /////////////////////////////////////variaveis usada no lcd /////////////////////////////////////////// #define LCD PORTC //define qual porta vai usar //o pino r/w é conectado ao terra pois não é feita nenhuma leitura no display //configuração: // // pino display / pino da porta selecionada // // D4 = bit 0 da porta // D5 = bit 1 da porta // D6 = bit 2 da porta // D7 = bit 3 da porta // // RS = bit 4 da porta // EN = bit 5 da porta // /////////////////////////////////////////////////Funções usadas no LCD///////////////////////////////////////////// void inicializa_LCD(void) { _delay_ms(15);//tempo para estabilizar a tensão e preparar o display // o primeiro digito é de controle e o segundo configuração LCD = 0X22;//nesse momento o display ainda está em modo 8bits solicita modo de 4 bits _delay_ms(1);//tempo estabilizar o pino LCD = 0X02;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15); // é preciso colocar este comando pelo menos 2 vezes para que funcione o display LCD = 0X22;//nesse momento o display está em modo 4bits _delay_ms(1);//tempo estabilizar o pino LCD = 0X02;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15); ////////entrou no modo 4bits///////////////////////////////////// LCD = 0X28;//nesse momento o display está em modo 4bits,manda usar 2 linhas _delay_ms(1);//tempo estabilizar o pino LCD =0X08;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15); /////////////////////envia 0X01 - limpar display //////////////////////////////////// LCD = 0X20;//manda limpar o display _delay_ms(1);//tempo estabilizar o pino LCD = 0X00;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag LCD = 0X21;//segundo nibble (limpa display) _delay_ms(1);//tempo estabilizar o pino LCD = 0X01;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag /////////////////////envia 0X06 - movimento e pisca do display//////////////////////////////////// LCD = 0X20;//manda deslocar a direita (0x06) _delay_ms(1);//tempo estabilizar o pino LCD = 0X00;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15); LCD = 0X26;//segundo nibble (desloca a direita) _delay_ms(1);//tempo estabilizar o pino LCD = 0X06;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag /////////////////////envia 0X0C - desliga display //////////////////////////////////// LCD = 0X20;//cursor desligado (0X0C) _delay_ms(1);//tempo estabilizar o pino LCD = 0X00;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag LCD = 0X2C;//segundo nibble (cursor deligado) _delay_ms(1);//tempo estabilizar o pino LCD = 0X0C;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag /////////////////////envia 0X2F - modo 4bits modo 4 linhas tipo de fonte //////////////////////////////////// LCD = 0X22;//cursor desligado (0X2F) _delay_ms(1);//tempo estabilizar o pino LCD = 0X02;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag LCD = 0X2F;//segundo nibble (cursor deligado) _delay_ms(1);//tempo estabilizar o pino LCD = 0X0F;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_ms(15);//substitui a leitura do busy flag } // escreve nibble void escr(unsigned char crt,int vlr) { if(vlr == 1) { LCD = crt | 0X30 ;//escreve dados _delay_us(30);//tempo estabilizar o pino LCD = crt | 0X10;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_us(30); } else { LCD = crt | 0X20 ;//escreve comando _delay_us(30);//tempo estabilizar o pino LCD = crt | 0X00;//ao passar do nivel alto para o nivel baixo ele faz leitura _delay_us(30); } } // escreve caracter ou comando void escreve(unsigned char carac,int val) { unsigned char temp=carac; carac = ((carac >> 4) & 0X0F); temp = temp & 0X0F; escr(carac,val); //escreve primeiro nibble escr(temp,val); //escreve segundo nibble } void impri_lcd(char frase[17]) { unsigned int indice=0; unsigned int tamanho = strlen(frase); while(indice<tamanho) { if(frase[indice]=='\n')//linha 1 { escreve(0X80,0); } if(frase[indice]=='\r')//linha2 { escreve(0XBF,0);// } if(frase[indice]=='@')//linha 3 { escreve((0X94),0); } if(frase[indice]=='$')//linha4 { escreve((0XD4),0); } if((frase[indice]!='\r') && (frase[indice]!='\n') && (frase[indice]!='@') && (frase[indice]!='$'))//dados { if(indice<18) { escreve(frase[indice],1); } } indice++; } } //////////////////////////////////////////////função principal/////////////////////////////////////////// int main(void) { DDRC = 0XFF; //inicializa portC // DDRD = 0XFE; //inicializa portD inicializa_LCD(); impri_lcd("\nTESTE DE LCD 20X4 "); impri_lcd("\r AGUIVONE "); impri_lcd("@escrevendo nas "); impri_lcd("$4 linhas! "); for(;;) { //faz nada! } } /////////////////////////////////////////////////////////////////////////////////////////////////////////