Witam
Niestety mimo wielu prób nie udaje mi się wyświetlić nic na ww. wyświetlaczu.
Zachowuje się on tak jakby był tylko podłaczony pod zasilanie czy pali się pierwszy wiersz z zapalonymi wszystkimi pikselami.
Zamieszczam poniżej kod programu i miałbym wielką prośbe o przeanalizowanie go w celu znalezienie błędów.
LCD podłączony do Atmega16 ustawionej na 4Mhz (wszystko pod PORTC - RS 0, E 2, D4:D7 odpowiednio 4:7, R/W do masy). Program ma sterować 4bitowo bez sprawdzania zajetości sterownika wyświetlacza.
kod:
Poprawiłem temat bo widzę że już koledze sił nie starczyło i proszę na przyszłość nie usuwać wpisu moderacyjnego.
Robak
Niestety mimo wielu prób nie udaje mi się wyświetlić nic na ww. wyświetlaczu.
Zachowuje się on tak jakby był tylko podłaczony pod zasilanie czy pali się pierwszy wiersz z zapalonymi wszystkimi pikselami.
Zamieszczam poniżej kod programu i miałbym wielką prośbe o przeanalizowanie go w celu znalezienie błędów.
LCD podłączony do Atmega16 ustawionej na 4Mhz (wszystko pod PORTC - RS 0, E 2, D4:D7 odpowiednio 4:7, R/W do masy). Program ma sterować 4bitowo bez sprawdzania zajetości sterownika wyświetlacza.
kod:
// PROGRAM OBSLUGUJACY WYSWIETLACZ LCD (2X16 ZNAKOW) //
// Atmega16, 4Mhz, //
/////////////////////////////////////////////////////
//--------------------------------------------------
// Biblioteki:
#include <avr/io.h>
#include <inttypes.h>
//--------------------------------------------------
// Makra upraszczajace dostep do portow:
#define PORT(X) XPORT(X) //podanie w programie: PORT(D) zinterpretuje jako "PORTD"
#define XPORT(X) (PORT##X)
#define PIN(X) XPIN(X)
#define XPIN(X) (PIN##X)
#define DDR(X) XDDR(X)
#define XDDR(X) (DDR##X)
//--------------------------------------------------
// Definicje wyprowadzen:
#define LCD_RS 0
#define LCD_RSPORT C
#define LCD_E 2
#define LCD_EPORT C
#define LCD_DPORT C
#define LCD_D4 4
//--------------------------------------------------
// Komendy sterujace wyswietlaczem:
#define LCDC_CLS 0x01
#define LCDC_HOME 0x02
#define LCDC_MODE 0x04
#define LCDC_MODER 0x02
#define LCDC_MODEL 0
#define LCDC_MODEMOVE 0x01
#define LCDC_ON 0x08
#define LCDC_ONDISPLAY 0x04
#define LCDC_ONCURSOR 0x02
#define LCDC_ONBLINK 0x01
#define LCDC_SHIFT 0x10
#define LCDC_SHIFTDISPLAY 0x08
#define LCDC_SHIFTR 0x04
#define LCDC_SHIFTL 0
#define LCDC_FUNC 0x20
#define LCDC_FUNC8b 0x10
#define LCDC_FUNC4b 0
#define LCDC_FUNC2L 0x08
#define LCDC_FUNC1L 0
#define LCDC_FUNC5x10 0x4
#define LCDC_FUNC5x7 0
#define LCDC_CGRAM 0x40
#define LCDC_DDRAM 0x80
//---------------------------------------------------
// Definicje opoznien:
#define delay250ns() {asm volatile("nop"::);}
#define delayus8(t)\
{asm volatile( \
"delayus8_loop%=: \n\t"\
"nop \n\t"\
"dec %[ticks] \n\t"\
"brne delayus8_loop%= \n\t"\
: :[ticks]"r"(t) );}
//DEC - 1 cykl; BRNE - 2 cykle; +1 x nop; Zegar 4Mhz
void delay100us8(uint8_t t)
{
while(t>0)
{
delayus8(100)
--t;
}
}
//-------------------------------------------------
// Funkcje niskiego poziomu:
#define LCD_EPULSE() \
{PORT(LCD_EPORT) |= 1<<LCD_E; \
delay250ns(); \
PORT(LCD_EPORT) &= ~(1<<LCD_E);}
// LCD_EPULSE - strobuje dostep do wyswietlacza (zalaczamy czas na pobranie danych lub rozkazow)
void LCD_sendHalf(uint8_t data)
{
data = (data & 0x0F) << LCD_D4;
PORT(LCD_DPORT) = (PORT(LCD_DPORT) & ~(0x0F<<LCD_D4)) | data;
LCD_EPULSE();
}
void LCD_send(uint8_t data)
{
LCD_sendHalf(data>>4); //starsza czesc
LCD_sendHalf(data); //mlodsza czesc
delayus8(120);//120 us
}
//-------------------------------------------------
// Funkcje wysylajace komendy i dane:
void LCD_command(uint8_t command)
{
PORT(LCD_RSPORT) &= ~(1<<LCD_RS); //przeslanie instrykcji; RS = 0
LCD_send(command);
}
void LCD_data(uint8_t data) //przeslanie danych do DD RAM; RS = 1
{
PORT(LCD_RSPORT) |= 1<<LCD_RS;
LCD_send(data);
}
void LCD_cls(void) //czyszczenie wyswietlacza
{
LCD_command(LCDC_CLS);
delay100us8(48);
}
void LCD_home(void) //ustawianie wyswietlacza w pozycji home
{
LCD_command(LCDC_HOME);
delay100us8(50);
}
//-------------------------------------------------
// Inicjacja Wyswietlacza:
void LCD_init(void)
{
delay100us8(150);
PORT(LCD_RSPORT) &= ~(1<<LCD_RS);
LCD_sendHalf((LCDC_FUNC | LCDC_FUNC8b)>>LCD_D4);
delay100us8(41);
LCD_sendHalf((LCDC_FUNC | LCDC_FUNC8b)>>LCD_D4);
delay100us8(2);
LCD_sendHalf((LCDC_FUNC | LCDC_FUNC4b)>>LCD_D4);
delay100us8(2);
//teraz jest juz 4b, koniec korzystania z sendHalf
LCD_command(LCDC_FUNC | LCDC_FUNC4b | LCDC_FUNC2L | LCDC_FUNC5x7);
LCD_command(LCDC_ON);
LCD_cls();
LCD_command(LCDC_MODE | LCDC_MODEL);
LCD_command(LCDC_ON | LCDC_ONDISPLAY);
}
//-------------------------------------------------
//PETLA GLOWNA:
int main(void)
{
//inicjalizacja portow
DDR(LCD_DPORT) |= 1<<LCD_E | 1<<LCD_RS | 0x0F<<LCD_D4;
DDRA |= 1<<0;//podciagniecie diodki sprawdzajacej czy program przejdzie
//przygotowanie wyswietlacza
LCD_init();
//podanie danych na wyswietlacz
LCD_data('H');
LCD_data('E');
LCD_data('L');
LCD_data('L');
LCD_data('O');
PORTA |= 1<<0;//wl. diodki sprawdzajacej
return 0;
}Poprawiłem temat bo widzę że już koledze sił nie starczyło i proszę na przyszłość nie usuwać wpisu moderacyjnego.
Robak