Pull to refresh

Паяем «умный» автомобильный БП на 5v с USB-зарядкой и автоматическим включением/выключением

Reading time 9 min
Views 469K
Я человек ленивый и люблю комфорт, поэтому люблю всяческого рода автоматизацию. В машине у меня есть видеорегистратор, иногда использую навигатор, часто нужно зарядить телефон или планшет себе или семье/знакомым. Как результат указанных потребностей — вся машина окутана проводами и зарядками, при этом всегда надо думать, что выдернуть из тройника прикуривателя и не потеряла ли контакт в прикуривателе очередная зарядка. Конечно, потихоньку в машине образовался клубок проводов и зарядок, а это мало того, что не эстетично, так еще и может привлечь наркоманов.

В один прекрасный момент это всё достало и было принято решение сделать что-то универсальное.

Задача:

  • Выходное напряжение 5.1V
  • Ток не менее 3A (телефон, 0.6А, видеорегистратор — 0.3А, iPad — 2A)
  • Автоматическое включение БП при запуске двигателя
  • Ручное включение БП
  • Автоматическое отключение БП через 15-30 минут после выключения двигателя (с возможностью продлить это время). Чтобы можно было оставить регистратор в машине без необходимости каждый раз его выключать/включать.
  • Автоматическое отключение БП при сильном разряде аккумулятора
  • Ручное выключение БП
  • Свистелки и перделкиСветовая и звуковая сигнализация
  • Достаточное количество USB-разъемов (хотя бы 4 шт.) в легкодоступном месте но без извращения над салоном
  • Нормальный (как родной зарядкой) заряд устройств Samsung и Apple
  • Без занимания прикуривателя.


Решение:

Решение вполне очевидное. Микроконтроллер для автоматизации и какой-нибудь преобразователь напряжения, но у преобразователя должна быть возможность включения/выключения работы логическими уровнями.

С размещением в машине было немного сложнее, сначала хотел вставить USB в подстаканник, но потом откинул эту идею, т.к. не эстетично плюс стакан будет не поставить да и очередные мотки проводов не радовали. Потом я обратил внимание на подлокотник и ящичек находящий в нём. Это было то, что нужно! Сам ящичек вытаскивается — значит можно легко обслуживать, в самом подлокотнике много места — значит спокойно влезет электроника. USB разъемы легко врезать в боковину ящичка и не нужные провода зарядок можно не вытаскивая из разъемов прятать в ящик.

Помимо USB разъемов для зарядок, требовалось питание для видеорегистратора. Для этого был протянут провод от подлокотника до зеркала заднего вида, на зеркале был наклеен еще один USB-разъем и выведен разъем для видеорегистратора.

Если с размещением разъемов, всё было довольно понятно, то с электроникой возникли небольшие проблемы.

Сначала была LM2596.


Это не твой бро
Чуть ранее я заказал на eBay несколько платок регулируемых блоков питания, собранных на микросхеме LM2596. Мне нужно было сделать зарядку для iPad, чтобы заряжала большим током (как родная — 10W). Зарядку я сделал, всё прекрасно работало, зарядка выдавала что-то около 2.1A на 5.1V (при входном напряжении около 12-13V — аккумулятор ИБП), но был один минус — она жутко грелась! Вся плата грелась так, что расплавила пластиковую коробочку, в которой была и сама плата потемнела (несмотря на то, что туда был приколхожен радиатор). После замеров КПД выяснилось, что при большом токе КПД около 60%, что нам совершенно не подходило.
Дополнительным нехорошим моментом было то, что у таких китайских платок не выведена отдельно ножка управления и пришлось бы отпаивать одну ножку микросхемы от платы и подпаивать к ней проводки.
Что делать с модулями на LM2596 не ясно.



KIS-3R33S — чудо китайских «конверсионных» технологий.


Шерстя eBay, я часто встречал некие модули KIS-3R33S, в описании которых указывалось, что они выдают 3A. Стоимость модулей тоже внушала — при покупке 10 штук, каждый модуль обходится около 50-90 центов с бесплатной доставкой. Почитав Яндекс стало ясно, что это довольно хороший модуль на микросхеме MP2307, который можно переделать в регулируемый преобразователь, а из навесных элементов нужно только два конденсатора — на вход и на выход.
И что важно — даже при нагрузке 2A он совершенно не греется!
Все продающиеся модули — паянные. Откуда они их берут в таком количестве совершенно непонятно ;)
Тех. параметры микросхемы MP2307
Входное напряжение — 4,75-23V
Выходное напряжение — 0,925-20V
Максимальный продолжительный выходной ток (кратковременный) — 3A (4A)
Частота преобразования — 340kHz
КПД — до 95%
Встроенная защита от короткого замыкания и перегрева
Вход управления
Вообщем за какие-то пять копеек кучка модулей была приобретена и работа закипела.

Подготовка БП.


По умолчанию модуль KIS-3R33S настрое на 3.3V, поэтому надо модуль немного адаптировать. Есть разные варианты переделки этого модуля (например), но я решил обойтись минимальными переделками. Вооружившись даташитом и схемой KIS-3R33S я составил такой список переделок:

  1. Вскрываем модуль
  2. Удаляем резистор и стабилитрон отмеченные красным. (некоторые удаляют конденсатор, отмеченный жёлтым — я не стал)
  3. Припаиваем (прямо внутри, чтобы потом корпус можно было закрыть) «выводный» резистор (0,125 ваттный) R между минусом и входом ADJ модуля. Резистор фиолетовый. Резистор номиналом от 9.1ком до 10 ком, в зависимости от резистора будет и разное напряжение (от 5.28V до 5.15V соответственно). Этот резистор включается последовательно с уже установленным резистором на 3.3ком (т.е. общее сопротивление резисторов будет 3.3+9.1=12.4) и параллельно резистору R1, за счёт чего их общее сопротивление падает и напряжение на выходе микросхемы растёт.
  4. Собираем модуль обратно
  5. На вход и выход модуля подпаиваем электролитические конденсаторы примерно указанных ёмкостей. Напряжение конденсаторов меньше брать нельзя, а больше можно.

Я не хотел, чтобы преобразователь работал на полную нагрузку, поэтому решил использовать 2 преобразователя, на одном будет 2 USB + USB и питание видеорегистратора, а на втором только 2 USB.

В принципе, уже всё работает и может заряжать, если не нужна автоматика, то можно закончить читать :)

Микроконтроллер.


Блок питания это самое простое, дальше нужно реализовать логику работы. Как мне показалось, контролировать заведен ли двигатель проще всего по напряжению в бортовой сети авто. Посидев с тестером в машине, получил такие данные:
  • > 13.8V — машина заведена.
  • < 13.3V — машина заглушена.
  • < 11.8V — дальше аккумулятор лучше поберечь.

Можно было контроль напряжения сделать на дискретных элементах, но мне хотелось хардкора легкости изготовления, малых размеров и функционала. Так же и свистелки-перделки свето-звуковые эффекты были в списке задач, поэтому решил использовать МК Attiny13A.

Схема управления.


Схема вроде простая. Резистор RV2, обычный подстроечный, чтобы легче было задать нужное напряжение на входе МК. Биппер LS1 обычный компьютерный, светодиод и кнопка тоже компьютерные. Вся схема питается от КРЕНки (78L05). Выход МК подключается к управлению модулями KIS-3R33S — высокий уровень включает, а низкий выключает модули.

Программа

Программа оказалась самой трудной задачей. В ассемблере я не силён, да и Си знаю в основном по примерам. Программу несколько раз переписывал, чтобы добиться нужного функционала и влезть в доступную память, в итоге память МК занята на 100%.
Логика работы такая:
  • Режим 1. Если напряжение выше или равно 13.8V и БП должен включится. Так же должен гореть светодиод и при включении должен пикнуть биппер.
  • Режим 2. Если напряжение упало до 13.3V значит двигатель заглушен, пикнем биппером три раза и начнём отсчет времени (по умолчанию — около 30 минут). Если во время этого режима нажать на кнопку, то к времени ожидания прибавится 1 час, еще одно нажатие — еще час и т.д. Светодиодом начинаем мигать.
  • Если напряжение упало до 11.8V или истекло время предыдущего режима, то пикнем долго и выключим БП. Светодиод погасим.
  • Когда БП выключен, то можно нажать на кнопку и БП включится на 30 мин (во второй режим).
  • При включенном БП и заведенном двигателе можно выключить БП нажав кнопку и удерживая её (около 3-х секунд) до короткого сигнала. БП выключится. Обратного его включить можно коротким нажатием на кнопку либо он включится сам, если двигатель заглушить и снова завестись.

Адов код и фьюзы для PonyProg
/*****************************************************
This program was produced by the
CodeWizardAVR V2.05.0 Professional
Automatic Program Generator

Chip type               : ATtiny13a
AVR Core Clock frequency: 4,800000 MHz
Memory model            : Tiny
External RAM size       : 0
Data Stack size         : 16
*****************************************************/

#include <tiny13a.h>

#include <delay.h>

#define ADC_VREF_TYPE 0x00

      unsigned char iter3=10;
      unsigned char i,POFF, sec, nobeep;
      //POFF - запрещает включать БП при заведенном двигателе;
      

// Read the AD conversion result
unsigned int read_adc(unsigned char adc_input)
{
ADMUX=adc_input | (ADC_VREF_TYPE & 0xff);
// Delay needed for the stabilization of the ADC input voltage
delay_us(10);
// Start the AD conversion
ADCSRA|=0x40;
// Wait for the AD conversion to complete
while ((ADCSRA & 0x10)==0);
ADCSRA|=0x10;
return ADCW;
}

//пищалка
void beep(unsigned char on)
{
    //включим светодиод    
    PORTB.2=1;
    
    //включим пищалку, если не запрещено
    if(!nobeep)DDRB.0=1;      
    
    //пищим on*100 милисекунд
    while(on){on--; delay_ms(100);}
    
    //выключим светодиод и пищалку
    PORTB.2=0;
    DDRB.0=0;
}

//процедура включения БП
void on()
{    
    if(POFF!=0)return;
    //включаем БП
    PORTB.4=1;
    iter3=10;
    beep(5); 
    POFF=1;    
}


//процедуры выключения БП
void off()
{
    //выключение не из-за времени, а из-за напряжения
    if(iter3 > 1)
    {          
        //подождем пол минуты и если напряжение всё еще низкое будет, то выключится    
        delay_ms(30000);
        iter3=1;
        return;
    }            
            
    //пикнем о выключении            
    if(PORTB.4)beep(30);
            
    //отключаем БП
    PORTB.4=0;

    if(POFF)
        POFF--;
                        
    iter3=1;
}


// External Interrupt 0 service routine
//Отрабатываем нажатие на кнопки
interrupt [EXT_INT0] void ext_int0_isr(void)
{
// Place your code here
    
    //нажатие кнопки сопровождается пиканьем
    beep(1);          
            
    //если БП был выключен, то включим на час            
    if(!PINB.4)
    {              
        on(); 
        POFF=0;
    }
            
    //а если БП включен, то с каждым нажатием будем прибавлять +1 час к ожиданию до выключения
    //длинное нажатие (больше 2-х сек, выключит БП)
    else
    {
        //прибавляем +1 час к ожиданию
        iter3=iter3+20;
                
        //считаем сколько времени нажата кнопка            
        i=8;
        while(!PINB.1){
            i--;
            delay_ms(250);
            
            //кнопка нажата больше 2-х сек.? Вырубаем!
            if(i==0)
            {  
                //пикнем, чтобы было понятно, что дальше нажимать на кнопку смысла нет и всё готово к выключению
                beep(1);
                iter3=0;
                        
                //здесь стоит 2, чтобы даже при высоком напряжении БП заново не включился.
                //включится он после того, как двигатель будет заглушен и заново заведен.
                POFF=2;
            }
        }                
    }                        
            
}

// Declare your global variables here





void main(void)
{
// Declare your local variables here

// Crystal Oscillator division factor: 1
#pragma optsize-
CLKPR=0x80;
CLKPR=0x00;
#ifdef _OPTIMIZE_SIZE_
#pragma optsize+
#endif

// Input/Output Ports initialization
// Port B initialization
// Func5=In Func4=Out Func3=In Func2=Out Func1=In Func0=Out 
// State5=T State4=1 State3=T State2=0 State1=T State0=0 
PORTB=0x10;
DDRB=0x15;

// Timer/Counter 0 initialization
// Clock source: System Clock
// Clock value: 1,172 kHz
// Mode: Normal top=FFh
// OC0A output: Disconnected
// OC0B output: Disconnected
//TCCR0A=0x40;
//TCCR0B=0x02;//x05;     выключаем таймер
TCNT0=0x00;
OCR0A=0x00;
OCR0B=0x00;

// Timer/Counter 0 initialization
// Clock source: System Clock
// Clock value: 4,688 kHz
// Mode: CTC top=OCR0A
// OC0A output: Toggle on compare match
// OC0B output: Disconnected
TCCR0A=0x42;
TCCR0B=0x05;
TCNT0=0x00;
OCR0A=0x00;
OCR0B=0x00;

// External Interrupt(s) initialization
// INT0: On
// INT0 Mode: Low level
// Interrupt on any change on pins PCINT0-5: Off
GIMSK=0x40;
MCUCR=0x00;
GIFR=0x40;


// Timer/Counter 0 Interrupt(s) initialization
TIMSK0=0x00;


// Analog Comparator initialization
// Analog Comparator: Off
ACSR=0x80;
ADCSRB=0x00;
DIDR0=0x00;


// ADC initialization
// ADC Clock frequency: 600,000 kHz
// ADC Bandgap Voltage Reference: Off
// ADC Auto Trigger Source: ADC Stopped
// Digital input buffers on ADC0: On, ADC1: On, ADC2: On, ADC3: Off
DIDR0&=0x03;
DIDR0|=0x08;
ADMUX=ADC_VREF_TYPE & 0xff;
ADCSRA=0x83;

#asm("sei")

//выключим пищалку
DDRB.0=0;
while (1){    
    
    delay_ms(1000);
    
    //напряжение больше 13.8 - завелись
    if( (0.0048828125*read_adc(3)) >=3.42)
        on();
    
        
        
    //напряжение меньше 11.8 или время работы с заглушенным двигателем истекло
    if ( (0.0048828125*read_adc(3)) <3.23 || !iter3 )                                        
        off();                                  

      
    //напряжение ниже 13.3 - выключили двигатель
    else if( (0.0048828125*read_adc(3)) < 3.38)
    {     
        //БП включен? включим таймер
        if(PINB.4)
        {  
            nobeep=1;
            beep(1); 
            nobeep--;

            //осталось полчаса               
            if(iter3 == 10)
            {   
                if(sec==1)
                //пикнем 3 раза коротко
                for(; sec<4; sec++)
                {
                    beep(2);            
                    delay_ms(200);                        
                }                                                       
            }
            
            if(sec>=180)
            {
                iter3--;
                sec=0;
            }
            sec++;
        }
        
        //если выключили с заведенным двигателем, чтобы после повторной заводки БП включился
        POFF=0;       
      }
      //при заведенном двигателе светодиод постоянно горит      
      else if(iter3 > 1)
        PORTB.2=1;  
      
}//end while
      
}

Для программатора PonyProg фьюзы ставить так


«Правильные» зарядки.

USB используются двойные, при том у каждой пары у одного USB-выхода средние контакты закорочены (чтобы большинство устройств понимали, что они воткнуты не в USB, а в зарядку), а у второго поставлены резисторы подтяжки, чтобы Apple-устройства считали, что подключены к родной зарядке и заряжались быстро.
Как Apple-устройство узнает «родную» зарядку.
Способов масса. Как вариант:
Чтобы получить «родную» зарядку из неродной необходимо на data-контакты подать потенциалы в 2.00В и 2.70В
Простейший делитель на эти номиналы:

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

Для Samsung-устройств тоже существует "своя схема" зарядки, но даже с закороченными средними контактами, мой телефон SGS2 кушал 600mA, что считаю вполне достаточным для заряда.

Конструкция и размещение в машине.

Схематично всё выглядит так:


Плату я делал под имеющуюся коробочку, делал ЛУТом.
Кровь, кишки




4 USB хорошо разместились в ящике, рядом был выведен светодиод и проделана дырочка (1мм), чтобы лучше слышать биппер.

И обратная сторона «медали». В алюминиевой коробочке находится плата управления и 2 преобразователя. Коробочка приклеивается скотчем к днищу ящика, который вставляется в подлокотник.


А в машине всё выглядит культурно (кнопку ещё нормально не приделал :).


На зеркале чуть хуже.


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

Сейчас понимаю, что можно было всё сделать красивее, взяв провода потоньше. Наверно весной переделаю.

Архив со схемой, исходник программы, прошивка, поделки платы можно скачать в ZIP.

ПС. Уже две недели собирался написать этот пост и только появившиеся аналогичная статья мотивировала начать :)
Tags:
Hubs:
+75
Comments 71
Comments Comments 71

Articles