ATtiny 13 c LCD-дисплеем.
Posted: 28 Apr 2013 14:30
Доброго времени суток! Обращаюсь к Вам, так как не могу доделать схему к курсовому, а завтра защита. Выручте, пожалуйста. Задание в файле.
Улыбнуло......more4ok wrote:..... не могу доделать схему к курсовому, а завтра защита. Выручте.....
Code: Select all
// Подключение LCD HD44780 к AVR через регистр сдвига
#include <tiny45.h>
#include <delay.h>
// Команды для управления портами LCD
/* RS */
#define RS1 registr(0x01, 1)
#define RS0 registr(0x01, 0)
/* E */
#define E1 registr(0x02, 1)
#define E0 registr(0x02, 0)
/* D4 */
#define D41 registr(0x04, 1)
#define D40 registr(0x04, 0)
/* D5 */
#define D51 registr(0x08, 1)
#define D50 registr(0x08, 0)
/* D6 */
#define D61 registr(0x10, 1)
#define D60 registr(0x10, 0)
/* D7 */
#define D71 registr(0x20, 1)
#define D70 registr(0x20, 0)
// Функция установки курсора в указанную точку
#define lcd_gotoxy(x, y) write_to_lcd(0x80|((x)+((y)*0x40)), 0)
volatile static unsigned char tempdata = 0;
// Функция передачи данных в регистр
void registr(unsigned char data, unsigned char WriteOrErase)
{
if(WriteOrErase == 1)
tempdata = (tempdata|data);
else
tempdata &= ~(data);
PORTB.1 = 0; // ST_CP 0
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x80)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x40)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x20)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x10)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x08)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x04)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x02)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.2 = 0; // SH_CP 0
if(tempdata & 0x01)PORTB.0 = 1;
else PORTB.0 = 0;
PORTB.2 = 1; // SH_CP 1
PORTB.1 = 1; // ST_CP 1
}
// Функция передачи данных или команды в LCD
void write_to_lcd(unsigned char p, unsigned char rs)
{
if(rs == 1) RS1;
else RS0;
E1;
if(p&0x10) D41; else D40;
if(p&0x20) D51; else D50;
if(p&0x40) D61; else D60;
if(p&0x80) D71; else D70;
E0;
delay_ms(2);
E1;
if(p&0x01) D41; else D40;
if(p&0x02) D51; else D50;
if(p&0x04) D61; else D60;
if(p&0x08) D71; else D70;
E0;
delay_ms(2);
}
// Функция инициализации LCD
void lcd_init(void)
{
write_to_lcd(0x02, 0); // Курсор в верхней левой позиции
write_to_lcd(0x28, 0); // Шина 4 бит, LCD - 2 строки
write_to_lcd(0x0C, 0); // Разрешаем вывод изображения, курсор не виден
write_to_lcd(0x01, 0); // Очищаем дисплей
}
// Функция вывода строки
void lcd_puts(char *str)
{
unsigned char i = 0;
while(str)
write_to_lcd(str[i++], 1);
}
// Функция вывода переменной
void lcd_num_to_str(unsigned int value, unsigned char nDigit)
{
switch(nDigit)
{
case 4: write_to_lcd((value/1000)+'0', 1);
case 3: write_to_lcd(((value/100)%10)+'0', 1);
case 2: write_to_lcd(((value/10)%10)+'0', 1);
case 1: write_to_lcd((value%10)+'0', 1);
}
}
// Функция чтения АЦП
int readADC(unsigned char ch)
{
ADMUX = ch; // Выбираем канал АЦП
ADCSRA |= (1 << ADSC); // Запускаем преобразование
while((ADCSRA & (1 << ADSC))); // Ждем окончания преобразования
return(ADCW*11/4); // Возвращаем значение АЦП
}
void main(void)
{
DDRB = 0b00000111; // Настраиваем входы/выходы
ADCSRA |= (1 << ADEN) // Разрешение АЦП
|(1 << ADPS2)|(1 << ADPS1); // Предделитель на 64
ACSR |= (1 << ACD); // Выключаем аналаговый компаратор
DIDR0 |= (1 << ADC3D)|(1 << ADC2D); // Отключаем неиспользуемые цифровые входы
lcd_init(); // Инициализация дисплея
write_to_lcd(0x01, 0); // Очищаем дисплей
lcd_gotoxy(0, 0); // Выводим строки на LCD
lcd_puts("U1 = . V");
lcd_gotoxy(0, 1);
lcd_puts("U2 = . V");
while(1)
{
lcd_gotoxy(5, 0);
lcd_num_to_str(readADC(2)/100, 2); // Выводим данные АЦП1 на LCD
lcd_gotoxy(8, 0);
lcd_num_to_str(readADC(2)%100/10, 1);
lcd_gotoxy(5, 1);
lcd_num_to_str(readADC(3)/100, 2); // Выводим данные АЦП2 на LCD
lcd_gotoxy(8, 1);
lcd_num_to_str(readADC(3)%100/10, 1);
delay_ms(50);
}
}