В маломощных системах одновременное включение всей группы светодиодов для достижения максимальной яркости может быть невозможно из-за ограниченного тока питания. Для обеспечения оптимальной яркости необходимо эффективно управлять рассеиваемой мощностью каждого светодиода от маломощного источника. Это требует применения метода управления питанием, при котором в группе светодиодов в течение определенного периода времени питается только одна группа светодиодов. Другие группы светодиодов будут невидимы визуально, пока достигается требуемая яркость.
Для расчета необходимого количества светодиодов на заданный интервал времени необходимо определить доступную мощность и требуемую светоотдачу для данного применения. Следует сравнить характеристики светоотдачи и постоянного тока, чтобы выбрать светодиоды с требуемым уровнем интенсивности. После определения необходимого количества светодиодов, их можно питать в течение интервала времени, определяемого соотношением общего тока, потребляемого светодиодами, и доступного тока, следующим образом:
Количество светодиодов в блоке = Общий ток, потребляемый светодиодами / Общий ток, доступный от источника.
Частота переключения блока светодиодов должна быть отрегулирована таким образом, чтобы время включения было достаточно долгим для полного освещения блока, а время выключения ограничивалось временем, необходимым до того, как блок начнет заметно тускнеть. Время выключения ограничивает количество дополнительных блоков светодиодов, которыми можно управлять, регулируя временной интервал.
Этот метод можно реализовать с низкими затратами, используя источник тактового сигнала, цифровые триггеры для управления светодиодными блоками и логический элемент ИЛИ для определения состояния запуска с помощью простого выключателя. На рисунке 1 показана блок-схема конфигурации D-триггеров для управления четырьмя светодиодными блоками.
Изначально триггер находится в статическом состоянии и требует запускающего импульса, длительностью не менее одного такта. Этот импульс может быть обнаружен первым триггером по восходящему фронту тактового сигнала. Запусковой сигнал должен быть кратковременным и не может длиться дольше одного такта; в противном случае первые два выхода триггера будут установлены одновременно. Поскольку подаваемый ток ограничен, система освещения не будет работать корректно. При такой конфигурации блок светодиодов полностью загорается по восходящему фронту каждого такта, и для человеческого глаза кажется, что все светодиоды загораются одновременно.
Однако такая реализация монотонна и не обеспечивает гибкости проектирования. Она имеет только состояние «включено/выключено». Эта схема может подойти для таких приложений, как подсветка ЖК-дисплеев, но если вам нужно регулировать яркость или генерировать последовательности, схема на основе микроконтроллера обеспечит максимальную гибкость при минимальном влиянии на общую стоимость решения. Конструкция схемы проще, требуется меньше компонентов, поскольку микроконтроллер управляет каждым блоком светодиодов и может также распознавать пользовательские входные данные для управления яркостью и выбора последовательности.
Недорогой 8-битный микроконтроллер с малым количеством выводов, например, семейство PIC10F или PIC12F от Microchip, в сочетании с расширителем портов ввода-вывода, таким как MCP23018 от Microchip, предложил бы экономичное решение. Расширение портов ввода-вывода также может быть полезно для управления светодиодами, когда схема освещения расположена удаленно от микроконтроллера.
Расширители портов ввода/вывода увеличивают количество портов ввода/вывода микроконтроллера. В данном случае микроконтроллер управляет расширителем портов ввода/вывода, используя протокол I2C™, для включения/выключения светодиодов. Контакты ввода/вывода микроконтроллера могут использоваться для считывания пользовательского ввода через кнопку или встроенный АЦП для считывания уровня потенциометра для управления яркостью.
Расширители ввода-вывода доступны в конфигурациях с открытым стоком или двухтактным выходом. Микроконтроллеры могут работать при напряжении 3,3 В или ниже, поэтому расширитель ввода-вывода с открытым стоком хорошо подходит для этого применения. Преимущество заключается в том, что это позволяет светодиодам работать при напряжении 5 В или выше, при условии, что микроконтроллер и расширитель ввода-вывода питаются от более низкого напряжения. MCP23018 — это 16-битный расширитель портов ввода-вывода с открытым стоком и интерфейсом I2C. На рисунке 2 показана принципиальная схема расширителя ввода-вывода с открытым стоком, напряжение которого повышается до уровня выше напряжения питания микроконтроллера.
Когда входной/выходной порт установлен в низкое состояние, напряжение на усилителе ввода/вывода равно 0 В, и по нему протекает ток, обеспечивая прямое смещение и переключение светодиода в проводящее состояние. Резистор смещения светодиода ограничивает ток, протекающий через светодиод, в соответствии с требуемой яркостью, а также выступает в качестве подтягивающего резистора для выхода с открытым стоком.
Когда выходной порт усилителя ввода-вывода установлен в высокое состояние, выход с открытым стоком переходит в режим отсечки или высокого импеданса, и напряжение на порту усилителя ввода-вывода повышается до 5 В с помощью подтягивающего резистора. Светодиод находится в режиме отсечки, поскольку ток не будет протекать. Конфигурация с открытым стоком также имеет преимущество в том, что при высоком импедансе порта требуется больше времени для выключения светодиода из-за паразитной емкости. Это позволяет следующему блоку светодиодов работать немного дольше по сравнению с аналогичными двухтактными схемами вывода.
Микросхема MCP23018 имеет 16 портов ввода/вывода и может управлять до 16 светодиодами. Величина тока, подаваемого на порт ввода/вывода при полном включении светодиода, может быть ограничена путем управления выходным сигналом усилителя ввода/вывода. Минимальное напряжение на порту ввода/вывода составляет 0,6 В при токе 8,5 мА. Если ток превышает 8,5 мА, напряжение на порту будет экспоненциально возрастать. Абсолютный максимальный ток составляет 25 мА.
Если, например, подаваемый ток ограничен 5 В/50 мА, и 2 мА выделено на микроконтроллер, расширитель ввода/вывода и резисторы для определения пользовательского ввода, то оставшийся доступный ток можно использовать для подсветки светодиодов. Можно управлять четырьмя светодиодами на блок, если интенсивность свечения светодиода при токе приблизительно 10 мА достаточна. В этом примере токоограничивающий резистор будет иметь номинальное сопротивление приблизительно 440 Ом.
void main (Void){
initialize(); //инициализация периферийных устройств PICmicro, включая таймер 0 и расширитель ввода-вывода
bank_counter = 0; //Очистка переменной счетчика банка
while(1){} //бесконечный цикл while
}
Void Interrupt int_service(void){
TurnOffAll_LEDs(); //подпрограмма для выключения всех ранее загоревшихся светодиодов
I2C_start(); //подпрограмма запуска сигнала протокола I2C
I2C_send(Comand_byte); //подпрограмма отправки байта протокола I2C
Если (bank_counter == bank1) { // bank1 — константа, определенная как 0
I2C_send(Address_pionter_bank1n2); // Отправить указатель адреса регистра периферийного устройства
I2C_send('0000 1111'); // Протокол I2C — отправить состояние банка (банк 1 включен и банк 2 выключен)
bank_counter = bank_counter + 1;
}
Если (bank_counter == bank2) { // bank1 — константа, определенная как 1
I2C_send(Address_pionter_bank1n2); // Отправить указатель адреса регистра периферийного устройства
I2C_send('1111 0000'); // Протокол I2C — отправить состояние банка (банк 2 включен и банк 1 выключен)
bank_counter = bank_counter + 1;
}
If(bank_counter == bank3){ // bank1 — константа, определенная как 2
I2C_send(Address_pionter_bank3n4); //Отправить указатель адреса регистра периферийного устройства
I2C_send('0000 1111'); //Протокол I2C — отправка состояния банка (банк 3 включен и банк 4 выключен)
bank_counter = bank_counter + 1;
}
If(bank_counter == bank4){ // bank1 — константа, определенная как 3
I2C_send(Address_pionter_bank3n4); //Отправить указатель адреса регистра периферийного устройства
I2C_send('1111 0000'); //Протокол I2C — отправка состояния банка (банк 4 включен и банк 3 выключен)
bank_counter = 0;
}
I2C_stop(); //Протокол I2C — подпрограмма сигнала остановки
}
Псевдокод 1: Код подпрограммы обработки прерывания микроконтроллера
*
*
*
Если (bank_counter == bank1) { // bank1 — константа, определенная как 0
I2C_send(Address_pionter_bank1n2); // Отправляем указатель адреса регистра периферийного устройства
Bank1n2_pattern = ~Bank1n2_pattern; // Дополняем переменную символом '~'
I2C_send((Bank1n2_pattern | '0000 1111')); // Протокол I2C — отправляем статус банка
// (используйте ИЛИ '|' для включения банка 1 и выключения банка 2)
bank_counter = bank_counter + 1;
}
*
*
*
Псевдокод 2: Генерация последовательности.
*
*
*
Void Interrupt int_service(void){
TurnOffAll_LEDs(); //подпрограмма для выключения всех ранее загоревшихся светодиодов
If (Delay_ON == ON){ // ON — константа, определенная как 1
Update_Timer0_Counter(Timer0delay_interval); //подпрограмма для обновления Timer0
// Timer0delay_interval — константа для установки минимальной задержки
Delay_Counter = Delay_Counter – 1; //обратный отсчет количества прерываний для задержки
If(Delay_Counter == 0){
Delay_ON = OFF; // Очистить флаг задержки для следующего прерывания
Delay_Counter = Get_Delay_Counter(); //подпрограмма для обнаружения ввода пользователя
//и установки переменной счетчика задержки
}else{
Delay_ON = ON; // оставить флаг задержки включенным
Return; //выход из подпрограммы обработки прерывания
}
}
I2C_start(); // Подпрограмма запуска протокола I2C
I2C_send(Comand_byte); // Подпрограмма отправки байта протокола I2C
If(bank_counter == bank1){ // bank1 — константа, определенная как 0
I2C_send(Address_pionter_bank1n2); // Отправка указателя адреса регистра периферийного устройства
Bank1n2_pattern = ~Bank1n2_pattern; // Дополнение переменной с помощью '~'
I2C_send((Bank1n2_pattern | '0000 1111')); // Протокол I2C — отправка статуса банка
// (используйте ИЛИ '|' для включения банка 1 и выключения банка 2)
bank_counter = bank_counter + 1;
delay_ON = ON; // Включить флаг задержки
}
*
*
*
Псевдокод 3: Реализация кода задержки для визуализации последовательности освещения.
Временную диаграмму, показанную на рисунке 1, можно воспроизвести с помощью короткого кода инструкций микроконтроллера. Например, для псевдокода 1 основная подпрограмма может представлять собой бесконечный цикл while. Для каждого временного интервала микроконтроллера (таймер 0) подпрограмма обработки прерывания отправляет инструкцию I2C на расширитель ввода-вывода для управления только одним блоком светодиодов. Подпрограмма обработки прерывания подсчитывает или отслеживает состояние блока светодиодов, например, находится ли блок в текущем состоянии, и конфигурацию соответствующего порта расширителя ввода-вывода как высокого или низкого уровня. Первоначально, или после перезагрузки микроконтроллера, блок 1 включается при первом прерывании таймера 0. При втором прерывании блок 1 выключается, а блок 2 включается. Затем, при третьем прерывании, блок 2 выключается, а блок 3 включается. Наконец, при четвертом прерывании блок 1 деактивируется, а блок 4 активируется, и переменная счетчика блоков сбрасывается в ноль. При следующем прерывании цикл повторяется, активируя банк 1 и деактивируя банк 4. Другие переменные, такие как Command_byte, Address_pointer_bank1n2 и Address_pointer_bank3n4, являются константами, определенными в файле запуска. В такой реализации схема генерирует необходимую интенсивность света, и создается впечатление, что все светодиоды активируются одновременно от имеющегося источника питания.
Void get_PWM_ratio(void) {
Double PotScale; // локальная переменная для хранения масштаба выходного сигнала АЦП
Double PWM_Percentage; // локальная переменная для хранения процента изменения ШИМ
PotScale = (ADRESH)/16 + 1; // Масштабирование старшего байта выхода АЦП
PWM_Percentage = 1/16 * PotScale; // Масштабирование выхода от 0 до 1, что эквивалентно 100%
PWM_High = Frequency_counter * PWM_Percentage; // Установка высокого значения ШИМ на таймере
0 PWM_Low = Frequency_counter * (1 – PWM_Percentage); // Установка низкого значения ШИМ на таймере 0
// PWM_High и PWM_Low — глобальные переменные,
// а Frequency_counter — постоянное значение таймера 0 для установки частоты.
}
Псевдокод 4: Подпрограмма для расчета коэффициента ШИМ
*
*
*
If(bank_counter == bank1){ // bank1 — константа, определенная как 0
If (PWM_High_Low_flag == OFF){ //проверка флага состояния ШИМ
get_PWM_ratio(); //Обнаружение пользовательского ввода для коэффициента ШИМ
Timer0_counter = 65535 – PWM_High; //установка переменной счетчика Timer0
Update_Timer0_Counter(Timer0_counter); //подпрограмма для обновления Timer0
I2C_send(Address_pionter_bank1n2); //Отправка указателя адреса регистра периферийного устройства
Bank1n2_pattern = ~Bank1n2_pattern; //дополнение переменной с помощью '~'
I2C_send((Bank1n2_pattern | '0000 1111')); // Протокол I2C – отправка состояния банков
// (используйте оператор ИЛИ '|' для включения банка 1 и выключения банка 2)
PWM_High_Low_flag = ON; // Установка флага
Delay_ON = OFF;
}else{
Timer0_counter = 65535 – PWM_Low; // установить переменную счетчика Timer0
Update_Timer0_Counter(Timer0_counter); // подпрограмма для обновления Timer0
I2C_send(Address_pionter_bank1n2); // отправить указатель адреса регистра периферийного устройства
I2C_send('1111 1111')); // протокол I2C – выключить все светодиоды
bank_counter = bank_counter + 1;
PWM_High_Low_flag = OFF; // очистить флаг
Delay_ON = ON;
}
}
*
*
*
Псевдокод 5: Последовательность выполнения кода для регулировки коэффициента ШИМ.
Регулировка яркости и генерация последовательностей светодиодов.
С помощью приложения на базе микроконтроллера можно создавать интересные световые последовательности. Выходные состояния расширителя портов ввода-вывода загружаются из
В оперативной памяти хранятся 2 байта переменных с именами Bank1n2_pattern и Bank3n4_pattern. Полбайта соответствует каждому банку. Предопределенная таблица поиска содержит несколько последовательностей единиц и нулей для каждого банка.
Для непрерывного мониторинга состояния кнопки включения/выключения в код микроконтроллера добавлена инструкция IF THEN: бесконечный цикл while основной подпрограммы. При кратковременном нажатии кнопки в два байта ОЗУ, названные Bank1n2_pattern и Bank3n4_pattern, загружается последовательность из таблицы поиска. При возникновении прерывания таймера 0 новая последовательность отправляется на расширитель ввода-вывода, и светодиоды загораются в соответствии с последовательностью. Основная подпрограмма перебирает значения из таблицы поиска до тех пор, пока пользователь кратковременно нажимает кнопку. Для отображения другой последовательности загорания достаточно отправить дополнение предыдущей последовательности. Например, если последовательность в банке 1 равна '0101', то дополнение будет '1010', как показано в псевдокоде 2, который является фрагментом псевдокода 1.
Однако перед тем, как инструкции IF THEN для включения/выключения банка визуально проверят чередующиеся последовательности, в подпрограмму прерывания необходимо добавить задержку. Она генерируется флагом Delay_ON, так что в следующем прерывании вычитается только счетчик задержки для подсчета количества прерываний для данной задержки. Пользователь также может выбрать значение задержки с помощью потенциометра, вывод которого подключается к входу АЦП, встроенного в микроконтроллер. Цифровые данные с АЦП масштабируются от минимальной до максимальной задержки путем определения четырех старших битов, которые обеспечивают 16 уровней. Более точная настройка может быть выполнена путем определения пяти старших битов, т.е. 32 уровней. Максимальная задержка — это самая низкая частота мигания светодиодов, а при минимальной задержке создается впечатление, что все светодиоды включены. На рисунке 3 показано положение задержки, tDELAY.
Для управления длительностью временного интервала для каждого банка используется широтно-импульсная модуляция (ШИМ). Длительность прерывания таймера 0 имеет два значения: длительное и короткое, пропорциональное проценту ШИМ, регулируемому поворотным потенциометром, центральный вывод которого подключен к входу АЦП. Уровень разрешения можно регулировать, выбирая верхние 4 или 5 бит АЦП. Положение счетчика таймера 0 регулируется пропорционально и по шкале данных АЦП, где 100% ШИМ соответствует максимальному положению счетчика (полностью освещенный), а 0% — минимальному или самому низкому уровню затемнения. Псевдокод 4 показывает уравнение шкалы ШИМ для 16 уровней, а на рисунке 3 показана временная диаграмма во время ШИМ, tPWM_LOW и tPWM_HIGH. Подпрограмма обработки прерывания
должна обновлять положение счетчика таймера 0 для следующего прерывания. Она также должна определять, является ли сигнал ШИМ длинным или коротким. Следовательно, необходимо добавить несколько инструкций для определения уровня потенциометра для управления затемнением и пропорционального масштабирования положения счетчика Timer0 с использованием значений PWM_High и PWM_Low, показанных в псевдокоде 4. Псевдокод 5 показывает код для регулировки ШИМ; для определения состояния ШИМ используется инструкция IF THEN.
Этот метод также может быть реализован на 8-битном микроконтроллере среднего уровня с дополнительной программной памятью, например, на семействе PIC16F от Microchip. Модернизация позволит основной подпрограмме обрабатывать сложные последовательности освещения, такие как непрерывное движение света. Модуль Timer1 микроконтроллера может использоваться для изменения длительности, а два байта ОЗУ обновляются для последовательности непрерывного движения.
Разработчики постоянно ищут новые способы снижения затрат без ущерба для производительности. Существует множество методов эффективного управления светодиодными блоками, используемыми в подсветке ЖК-дисплеев или в системах последовательного освещения для обеспечения эффективного освещения. В маломощных приложениях светодиодами можно управлять, регулируя временной интервал для каждого блока светодиодов. Кроме того, микроконтроллеры с малым количеством выводов и расширители портов ввода-вывода предлагают недорогую альтернативу для решений в области освещения с большей гибкостью проектирования.
Автор:
Эзана Хайле, главный инженер по применению аналоговых и интерфейсных продуктов, Microchip Technology Inc.
