Пятница, 17.05.2024, 10:04
Главная
Приветствую Вас, Гость
Статистика



Онлайн лист

Онлайн всего: 1
Гостей: 1
Пользователей: 0



Реклама



Главная » Статьи » Микроконтроллеры

Наверх


Attiny2313 + Семисигментный индикатор
     Одним из удобных средств отображения информации является Семисегментный индикатор. Немного почитать о нем можно здесь. В общих словах один такой индикатор состоит из 8-ми светодиодов соединенных либо катодами либо анодами, отсюда и названия индикатор с общим катодом или с общим анодом.
     Эти индикаторы очень удобны для отображения циферной информаци,  например в вольтметре, термометре, часах и т.д.
     В подключении и управлении таким индикатором нет ничего сложного, и сейчас мы в этом убедимся.
На схеме ниже я привел пример подключения семисигментного индикатора c общим катодом к микроконтроллеру Attiny2313:


     Работу с индикатором можно представить как работу с светодиодами, набором светодиодов, с небольшим отличием, чтобы вывести необходимый символ на индикатор нам будет зажечь определенную комбинацию этих светодиодов. Кстати, часто, для защиты портов  микроконтроллера, как и в случае с обычными светодиодами ставят токоограничивающие резисторы, последовательно с каждым светодиодом. Иногда резисторы можно не ставить, когда мощность индикатора не слишком велика ( ток протекающий через один светодиод не превышает допустимого значения тока на входе микроконтроллера).  Эту информацию можно найти в даташите на микроконтроллер и в даташите на конкретную модель индикатора.  Для симуляции в PROTEUS'е резисторы нам не понадобятся, но если поставить резисторы 200-470 Ом, то на коректроность симуляции это не повлияет.

     Как видно из схемы каждый сегмент у нас подключен к отдельному пину микроконтроллера, обычно их на один больше - сегмент точки, но в данной модели точки нет. Общий катод у нас подключен к "земле". Значит чтобы вывести на индикатор символ нам нужно на несколько выходов микроконтроллера подать логическую "1" ( 5В).

 На этом изображении указаны названия сегментов. В PROTEUS'е на этом индикаторе почему то назначение выводов не подписаны, но сверху вниз идут в алфавитном порядке: A B C D E F G, точки нет.

Выводить сигналы на каждую ногу порта одновременно можно несколькими способами:
Двоичный:
С учетом нашей схемы получаем код следующего вида
PORTB = 0bDPGHEDCBA;
0b - что порту мы присваиваем двоичное значение, а в место букв нужно подставить 0 и 1 , т.е. те сегменты которые должны светится будут единицами, а остальные -0. К примеру  цифра 5 будет выглядеть PORTB=0b01101101.

Шестнадцатеричный:
Здесь все тоже крайне просто, только двоичные значения символов нужно перевести в шестнадцатиричный, что можно сделать  даже с помощью встроенного в Windows калькулятора в режиме программист. ВЫвод той же самой 5-ки на индикатор будет уже выглядеть так:
 PORTB=0x6D; 

Ниже приведу таблицу в обоих видах для цифр 0-9:
  Символ Двоичный вид Шестнадцатиричный вид
 0 0b00111111 0x3F
 1 0b01101111 0x6F
 2 0b01111111 0x7F
 3 0b00000111 0x7
 4 0b01111101 0x7D
 5 0b01101101 0x6D
 6 0b01100110 0x66
 7 0b01001111 0x4F
 8 0b01011011 0x5B
 9 0b00000110 0x6

 В каком виде использовать это уже скорее дело вкуса и удобства.

Пример

      Ниже пример программы, которая выводит на индикатор ( подключенный по схеме выше) цифры от 1 до 0 по кругу:



#include <tiny2313.h> 
#include <delay.h>

#define pause delay_ms(300) // Задержка в 300 миллисекунд

void avr_init(void)
{
#pragma optsize-
CLKPR=0x80;
CLKPR=0x00;
#ifdef _OPTIMIZE_SIZE_
#pragma optsize+
#endif
PORTA=0x00;
DDRA=0x00;
PORTB=0x00;
DDRB=0xFF;
PORTD=0x00;
DDRD=0xFF;
TCCR0A=0x00;
TCCR0B=0x00;
TCNT0=0x00;
OCR0A=0x00;
OCR0B=0x00;
TCCR1A=0x00;
TCCR1B=0x00;
TCNT1H=0x00;
TCNT1L=0x00;
ICR1H=0x00;
ICR1L=0x00;
OCR1AH=0x00;
OCR1AL=0x00;
OCR1BH=0x00;
OCR1BL=0x00;
GIMSK=0x00;
MCUCR=0x00;
TIMSK=0x00;
USICR=0x00;
ACSR=0x80;

};
void main(void)
{
avr_init();
while (1)
{
PORTB=0b00000110; //1
pause;
PORTB=0b01011011; //2
pause;
PORTB=0b01001111; //3
pause;
PORTB=0b01100110; //4
pause;
PORTB=0b01101101; //5
pause;
PORTB=0b01111101; //6
pause;
PORTB=0b00000111; //7
pause;
PORTB=0b01111111; //8
pause;
PORTB=0b01101111; //9
pause; PORTB=0b00111111; //0
pause;
};
}









     
     Программа получилась очень простой: выводим символ "1" ждем 300 миллисекунд выводи символ "2" и т.д.
Важный момент в настройках контроллера не забудьте установить PORTB на выход командой
DDRB=0xFF; // Все пины(ножки) порта настроены как выходы 
PORTD=0x00; // Изначально на всех пинах установлен 0
Результат выполнения программы:



Массив
Создаем массив из наших символов:

char chisla[10]={0x3F,0x6,0x5B,0x4F,0x66,0x6D,0x7D,0x7,0x7F,0x6F};

chisla[10] - это название нашего массива, а в [] указано количество символов, далее через запятую в {} записываем значения наших символов, в моем случае это цифры 0-9.
       Для того чтобы вывести например все тот же символ "5" нужно просто  написать:
PORTB = chisla[6]; // Присвоить порту значение под номером 6 из массива chisla[], причем не забываем что в массиве нумерация начинается не с 1, а с 0. 

Подключение нескольких индикаторов.


     В большинстве случаев одного индикатора будет мало, поэтому сейчас разберемся как подключить несколько штук.

     Из схемы видим что все индикаторы включены параллельно, за исключением выводов общих катодов. 
Общие катоды теперь подключены не напрямую к земле, а через транзисторы. В голову сразу приходит вопрос: "а зачем?". И ответ прост, для управления. Если оставить катоды просто на земле то на все индикаторы будет выводится один и тот же символ, так как параллельное подключение. А с помощью открытия транзистора мы выбираем индикатор, который будет работать. Принцип работы сводится к следующему:  открываем транзистор индикатора и выводим на него информацию закрываем транзистор, открываем транзистор следующего индикатор и выводим информацию на него, закрываем транзистор, и так для каждого индикатора. Получается что в каждый момент времени у нас работает только один индикатор, но если переключение сделать быстрым (как минимум быстрее 24 раз в секунду) то глаз начинает воспринимать как статичную картинку и мы не видим переключения.
     Транзисторы управляются свободными ногами микроконтроллера, в нашем случае этоPORTD.

     Привожу код программы которая написана для схемы выше и выводит  на индикаторы цифры: 1 2 3 4, причем на каждом индикаторе будет светится только своя цифра:


#include <tiny2313.h> 
#include <delay.h>

#define pause delay_ms(50)
#define seg1 PORTD.0
#define seg2 PORTD.1
#define seg3 PORTD.2
#define seg4 PORTD.3

char chisla[10]={0x3F,0x6,0x5B,0x4F,0x66,0x6D,0x7D,0x7,0x7F,0x6F};

void avr_init(void)
{
#pragma optsize-
CLKPR=0x80;
CLKPR=0x00;
#ifdef _OPTIMIZE_SIZE_
#pragma optsize+
#endif
PORTA=0x00;
DDRA=0x00;
PORTB=0x00;
DDRB=0xFF;
PORTD=0x00;
DDRD=0xFF;
TCCR0A=0x00;
TCCR0B=0x00;
TCNT0=0x00;
OCR0A=0x00;
OCR0B=0x00;
TCCR1A=0x00;
TCCR1B=0x00;
TCNT1H=0x00;
TCNT1L=0x00;
ICR1H=0x00;
ICR1L=0x00;
OCR1AH=0x00;
OCR1AL=0x00;
OCR1BH=0x00;
OCR1BL=0x00;
GIMSK=0x00;
MCUCR=0x00;
TIMSK=0x00;
USICR=0x00;
ACSR=0x80;

};
void main(void)
{
avr_init();
while (1)
{
seg1 = 1;
PORTB=chisla[4];
pause;
seg1=0;
pause;
seg2 = 1;
PORTB=chisla[3];
pause;
seg2 = 0;
pause;
seg3 = 1;
PORTB=chisla[2];
pause;
seg3 = 0;
pause;
seg4 = 1;
PORTB=chisla[1];
pause;
seg4=0;
pause;
};
}




















И сразу же несколько слов по коду:
#define seg1 PORTD.0 
#define seg2 PORTD.1
#define seg3 PORTD.2
#define seg4 PORTD.3
     Таким образом я присвоил ногам микроконтроллера управляющим транзисторами имена, в соответствии с тем какой транзистор управляет каким индикатором, по схеме выше seg1 это самый правый индикатор.
#define pause delay_ms(50)
     Время задержки в 50 миллисекунд я выставил только для того, чтобы убедится  что на индикаторы символы выводятся правильно, при меньшей задержке и, соответственно, большей частоте( желательно чтобы время задержки было не более 5мс) мой PROTEUS записывал в лог ошибку 

что говорит о том что мощностей моего процессора не хватает для симулляции в реальном времени, а потому неподвижной картинки о протеуса я не добился, но на практике все обстоит куда лучше.
    Если после сборки в железе заметно мерцание символов или то как они переключаются, то просто подберите время задержки.

Несколько слов напоследок.
     Я мельком упоминал, что есть два вида индикаторов: с общим катодом и с общим анодом. Все что написано выше относится к индикаторам с общим катодом, но если Вы в этом разобрались, то без труда сможете разобраться и с индикаторами с общим анодом. 
     Отличия будут заключаться в следующем: 
- анод нужно подключить к "+" питания, а не к земле как в случае с общим катодом,
- ноги микроконтроллера нужно установить как входы( для порта B DDRB=0x00),
- для зажигания сегментов на порт выставлять уровень "0" (изначально все ноги выставить в "1"                                                          PORTB=0xFF;),
- символы будут иметь другие коды, как это сделать думаю догадаетесь уже сами.





Нравится
Категория: Микроконтроллеры | Добавил: Naprisar (06.04.2012)
Просмотров: 15978 | Комментарии: 1 | Теги: attiny2313, микроконтроллер, семисигментный индикатор, подключение индикатора
Всего комментариев: 0
Добавлять комментарии могут только зарегистрированные пользователи.
[ Регистрация | Вход ]

Наверх