Код: Выделить всё
// ЗАПИСЬ ПОЛУБАЙТА
void LCD_WRITE_NIBBLE(unsigned char TEMP_NIBBLE) {
PORTD |= TEMP_NIBBLE; // запись в порт
_delay_ms(1);
E_ENABLE;
_delay_ms(2);
E_DISABLE;
_delay_ms(1);
PORTD &= 0b00001111;
}
Код: Выделить всё
// ЗАПИСЬ ПОЛУБАЙТА
void LCD_WRITE_NIBBLE(unsigned char TEMP_NIBBLE) {
PORTD |= TEMP_NIBBLE; // запись в порт
_delay_ms(1);
E_ENABLE;
_delay_ms(2);
E_DISABLE;
_delay_ms(1);
PORTD &= 0b00001111;
}
Аlex писал(а):servmv писал(а):Не работает без задержки.Аlex писал(а):Но у Вас, по всей видимости, "всё работает" только из-за бешеных задержек в функции LCD_WRITE_NIBBLE.
servmv писал(а):Они только там и есть) я вас не понимаю
Аlex писал(а):Некоторые операции, во время инициализации, требуют ожидания выполнения. Делается это либо задержками, либо чтением состояния из дисплея.Код: Выделить всё
void LCD_INIT()
{
RS_DISABLE;
LCD_WRITE_NIBBLE(0b00110000); // 0_0_1_DL_N_F_0_0 (0010 N(0-1на строка, 1-2ве строки)000) 00101000
LCD_WRITE_NIBBLE(0b00110000);
LCD_WRITE_NIBBLE(0b00110000);
LCD_WRITE_NIBBLE(0b00100000);
LCD_WRITE_DATA(0b00000001); // очистка дисплея
LCD_WRITE_DATA(0b00101000);
LCD_WRITE_DATA(0b00001000); // полное выключение дисплея
LCD_WRITE_DATA(0b00000100); // сдвиг курсора отключен
LCD_WRITE_DATA(0b00001100); // включение дисплея
RS_ENABLE;
}
Но у Вас, по всей видимости, "всё работает" только из-за бешеных задержек в функции LCD_WRITE_NIBBLE.
"убрать" - я имел ввиду уменьшить, чтобы не такие были большие. Там микросекунд достатоно, особенно на стробе по EN.а дальше мусор на дисплее если как вы говорите убрать паузы.
по инструкции
Код: Выделить всё
void LCD_INIT()
{
_delay_ms(16);
RS_DISABLE;
LCD_WRITE_NIBBLE(0b00110000); // 0_0_1_DL_N_F_0_0 (0010 N(0-1на строка, 1-2ве строки)000) 00101000
_delay_ms(5);
LCD_WRITE_NIBBLE(0b00110000);
_delay_us(110);
LCD_WRITE_NIBBLE(0b00110000);
_delay_us(40);
LCD_WRITE_NIBBLE(0b00100000);
_delay_us(40);
LCD_WRITE_DATA(0b00000001); // очистка дисплея / 2мс
_delay_ms(2);
LCD_WRITE_DATA(0b00101000);
_delay_us(40);
LCD_WRITE_DATA(0b00001000); // полное выключение дисплея
_delay_us(40);
LCD_WRITE_DATA(0b00000100); // сдвиг курсора отключен
_delay_us(40);
LCD_WRITE_DATA(0b00001100); // включение дисплея
RS_ENABLE;
}
Код: Выделить всё
// ЗАПИСЬ ПОЛУБАЙТА
void LCD_WRITE_NIBBLE(unsigned char TEMP_NIBBLE) {
PORTD |= TEMP_NIBBLE; // запись в порт
_delay_us(300);
E_ENABLE;
_delay_us(500);
E_DISABLE;
_delay_us(300);
PORTD &= 0b00001111;
}
Код: Выделить всё
E_ENABLE;
_delay_us(1);
E_DISABLE;
Код: Выделить всё
#include <avr/io.h>
#define F_CPU 16000000UL
#include <util/delay.h>
Код: Выделить всё
#define RS_ENABLE PORTB |= (1 << 0) // Пин RS
#define RS_DISABLE PORTB &=~ (1 << 0) //
#define E_ENABLE PORTB |= (1 << 1) // Пин E
#define E_DISABLE PORTB &=~ (1 << 1) //
//P.S. На данном модуле есть управление подсветкой что для меня было сюрпризом) т.к. на схеме этого не было, установлен транзистор на катоде подсветки. можно управлять так:
#define BACKLIGHT_ENABLE PORTB |= (1 << 2) // Пин подсветки
#define BACKLIGHT_DISABLE PORTB &=~ (1 << 2) //ну там вам решать вкл\выкл или замутить шим для регулировки яркости.
#define LCD_PORT PORTD
Код: Выделить всё
void LCD_INIT()
{
_delay_ms(16);
RS_DISABLE;
LCD_WRITE_NIBBLE(0b00110000); // 0_0_1_DL_N_F_0_0 (0010 N(0-1на строка, 1-2ве строки)000) 00101000
_delay_ms(5);
LCD_WRITE_NIBBLE(0b00110000);
_delay_us(110);
LCD_WRITE_NIBBLE(0b00110000);
_delay_us(40);
LCD_WRITE_NIBBLE(0b00100000);
_delay_us(40);
LCD_WRITE_DATA(0b00000001); // очистка дисплея / 2мс
_delay_ms(2);
LCD_WRITE_DATA(0b00101000);
_delay_us(40);
LCD_WRITE_DATA(0b00001000); // полное выключение дисплея
_delay_us(40);
LCD_WRITE_DATA(0b00000100); // сдвиг курсора отключен
_delay_us(40);
LCD_WRITE_DATA(0b00001100); // включение дисплея
RS_ENABLE;
}
// ЗАПИСЬ ПОЛУБАЙТА
void LCD_WRITE_NIBBLE(unsigned char TEMP_NIBBLE) {
PORTD |= TEMP_NIBBLE; // запись в порт
_delay_us(300);
E_ENABLE;
_delay_us(500);
E_DISABLE;
_delay_us(300);
PORTD &= 0b00001111;
}
// ФУНКЦИЯ ОТПРАВКИ СИМВОЛА
void LCD_WRITE_CHAR(unsigned char TEMP_WRITE_CHAR) {
RS_ENABLE;
LCD_WRITE_DATA(TEMP_WRITE_CHAR);
}
// ФУНКЦИЯ ОТПРАВКИ КОМАНДЫ
void LCD_WRITE_CMD(unsigned char TEMP_WRITE_CMD) {
RS_DISABLE;
LCD_WRITE_DATA(TEMP_WRITE_CMD);
RS_ENABLE;
}
// ЗАПИСЬ В ПОРТ КОММАНДЫ ИЛИ ДАННЫХ (ОПРЕДЕЛЯЕТСЯ RS), используется в LCD_WRITE_CHAR и LCD_WRITE_CMD
void LCD_WRITE_DATA(unsigned char TEMP_WRITE_DATA) {
LCD_WRITE_NIBBLE(TEMP_WRITE_DATA & 0xF0); // старшый полубайт
LCD_WRITE_NIBBLE(TEMP_WRITE_DATA << 4); //младший полубайт
}
void LCD_OFF() {
LCD_WRITE_CMD(0b00001000);
}
void LCD_ON() {
LCD_WRITE_CMD(0b00001100);
}
// Установка курсора, КУРСОР НЕ СДВИГАЕТСЯ!!! так настроено при инициализации. LINE = 0 - первая строка, 1 - вторая строка.
void LCD_SET_CURSOR(unsigned char LINE, unsigned char POS) {
POS |= 0b10000000;
if (LINE == 0x01)
{
POS |= 0x40;
}
LCD_WRITE_CMD(POS);
}
Аlex писал(а):Странно...
А можно марку дисплея ? Или лучше ссылочку на ДШ.
