Гуру
Регистрация: 16.04.2014
Возраст: 40
Город: Gdynia
Регион: другой - для добавления сообщить ab
Сообщений: 2,548
|
после 3 недель простоя здохла батарея. (или ушла в защиту - лень разбирать планшет).
Планшет стал забывать дату.
И самое неприятное - при старте перестал включаться режим отг. При этом масса на 4 конт юсб постоянно идёт.
Поэтому был поставлен долго ждущий сего радостного сообытия хаб.
Питание хаба взято с контакта +5v hub (Vout2), питание хаба через юсб перерезано. Это не помогло решить отваливание юсб, поэтому переписалась логика БП. ( при включении зажигания ждём 0,8 сек и подаём массу на 4 конт юсб, при выключении зажигания - убираем.
Заодно перекинул включение усилителя звука на REMout30.
Получившийся скетч. ( планшет без батареи)
PHP код:
//ver9.07.16.2111 ( чем больше цифра, тем новее) // для 5й версии блока питания ( для 4й тоже подходит, только нужно поменять местами в программе A0 и A1) //ТЕСТОВАЯ!!! /* _______Сделано__________________________________________________ вывод информации на внешний дисплей по I2C, активный вотчдог, программная защита its716G(statepin)-тестово, умное мигание встроенным светодиодом, усреднение завмеров по напряжению ACC и AKB. Оптимизирован для планшета без батареи. информация на дисплее обновляется не постоянно, а каждые 350мс ( 0,35 с). ________________________________________________________________ потребление блока по 12 вольтам, без планшета - при 10В +30 и +15 включены - 0,02 А - при 12В +30 и +15 включены - 0,092-0,1 А ________________________________________________________________
низкое напряжение АКБ авто - коротко моргает нормальное напряжение АКБ авто, ACC выключено. - быстро моргает нормальное напряжение, включено ACC, рабочий режим. - медленно моргает
*/ //*************************************************************************************************************************************************** // Массив режимов работы светодиода byte modes[] = { 0B00000000, //Светодиод выключен 0B11111111, //Горит постоянно 0B00111111, //Мигание по 0.8 сек 0B00000001, //Короткая вспышка раз в секунду 0B00000101, //Две короткие вспышки раз в секунду 0B00010101, //Три короткие вспышки раз в секунду 0B01010101 //Частые короткие вспышки (4 раза в секунду) };
uint32_t ms, ms1 = 0; uint8_t blink_loop = 0; uint8_t blink_mode = 0;
//*************************************************************************************************************************************************** #include <Wire.h> #include <LiquidCrystal_I2C.h> #include <avr/wdt.h> //Чтобы использовать функции Watchdog нужно подключить к проекту стандартную библиотеку ( https://geektimes.ru/post/255800/ )
LiquidCrystal_I2C lcd(0x27, 16, 2); // set the LCD address to 0x27 for a 16 chars and 2 line display float UakbONorOFF = 12.01;// в 155 строке == if ((15.5 > U_acc_real >= UaccONorOFF) && flagACC == 1) {UakbONorOFF = 11.5;} else {UakbONorOFF = 11.9;} float UaccONorOFF = 10;//11.1 // напряжение порога сработки асс
/*ноги ардуины*/ int SAMOZAPITKApin = 9; //управление самозапиткой блока питания IN4 //1 = есть самозапитка; 0 = нет самозапитки int PlanshBATpin = 6; // включить 1 канал KIW ..... управление питания БАТАРЕИ планшета через управляющую ногу IN2-5pin //0 = нет питания; 1 = есть питание ( БАТАРЕИ планшета) int II_KIW_pin_POGOpin = 2; // включить 2 канал KIW управление SS2 выходом питания +5V (2 канал kiw3312s) на пого пин(или USB), чтоб планшет думал, что идет зарядка //0 = нет 5V на POGO; 1 = есть 5V на POGO int OTGpin = 12; //управление транзюком OTG Q1 //1 = есть масса на OTG; 0 = нет массы на OTG int SLEEPpin = 10; //управление транзюком сна VT4 (на датчик холла)) //1 = потух экран(есть масса на пине сна); 0 = штатная работа планшета (нет массы на пине сна) int HUBpin = 11; //управление транзюком питания хаба // 0-есть питание, 1 - нет питания int REMpin = 7; // выход сигнала REM (+12v) (IN3), на плате распаяно. //0 = нет 12В на выходе REM; 1 = есть 12В на выходе REM int REGISTRATORpin = 4; //выход 12В для работы видеорегистратора (D4 -IN1) //пины состояния ITS int STATEpinI = 5; //логический вход для отслеживания аварийной ситуации ITS716G(724G)(питание KIW3312s-out2 и регистратор-out1) 0 = норма int STATEpinII = 8; //логический вход для отслеживания аварийной ситуации ITS716G(724G)(выход REM-out3 и самозапитка БП-out4 )1 = авар. сит.
/*логические переменные, используемые в коде*/ int flagACC = 0; //признак включенного зажигания int flagAKB = 0; // признак заряженной батареи int flagHALL = 0; //флаг отработки морга экрана при холодном старте( flagHALL = 1 экран можно включать и выключать, датчик холла на планшете инициализировался) /*счётчики времени*/ unsigned long eventTime = 0; unsigned long pauseTimeACC = 0; unsigned long pauseTimeAKB = 0; unsigned long pauseDisplay = 0; // таймер для обновления информации на дисплее, чтобы не мерцал unsigned long pauseTimeHALL = 120000; // время паузы перед морганием экрана (для датчика холла)(равен времени загрузки планшета плюс секунд 10-20)= 2мин int timeAfterACC = 5000; // время после выключения зажигания, после истечения которого вырубается экран, хаб, y-otg
void setup() //настройки { // Serial.begin(115200); //*************************test************* wdt_disable(); //Отключение таймера watchdog lcd.init(); // initialize the lcd занимает почти секунду pinMode(STATEpinI, INPUT); pinMode(STATEpinII, INPUT); pinMode(PlanshBATpin, OUTPUT); pinMode(SAMOZAPITKApin, OUTPUT); pinMode(OTGpin, OUTPUT); pinMode(SLEEPpin, OUTPUT); pinMode(II_KIW_pin_POGOpin, OUTPUT); pinMode(HUBpin, OUTPUT); pinMode(13, OUTPUT); //светодиодик на плате ардуины pinMode(REMpin, OUTPUT); pinMode(REGISTRATORpin, OUTPUT);
digitalWrite(PlanshBATpin, 0); //вЫключаем питание на батарею планшета digitalWrite(SAMOZAPITKApin, 0); //выключаем SAMOZAPITKApin, при этом пропадает управление на IN4, система ПОЛНОСТЬЮ обесточивается digitalWrite(OTGpin, 0); //вЫключаем минус на Y-OTG (8 pin PW1) digitalWrite(II_KIW_pin_POGOpin, 0); //вЫключаем +5V (POGO(USB)) digitalWrite(HUBpin, 1); // подаем + на управляющий транзюк хаба, тот закрывается и не пускает +5В с KIW (2вых)на хаб = ВЫключаем хаб digitalWrite(REMpin, 0); // // выключаем выход REM digitalWrite(REGISTRATORpin, 0); // выключаем питание на видеорегистратор pauseTimeACC = millis(); // сброс времени для отсчета отключения самозапитки pauseTimeAKB = millis(); wdt_enable (WDTO_8S); // Запуск таймера watchdog: Для тестов не рекомендуется устанавливать значение менее 8 сек. Таймер будет считать ровно столько, сколько указано в константе. По истечении этого времени произойдет перезагрузка. /* Возможные значения для константы WDTO_15MS WDTO_30MS WDTO_60MS WDTO_120MS WDTO_250MS WDTO_500MS WDTO_1S WDTO_2S WDTO_4S WDTO_8S */ }
void loop() {
//int Uacc = analogRead (A0); //Читаем напругу с делителя ACC R4-R5 //int Uakb = analogRead (A1); //Читаем напругу с делителя R2-R3 long Uacc = 0; //Читаем напругу с делителя ACC R4-R5 и вычисляем среднее арифметическое long Uakb = 0; ////Читаем напругу с делителя R2-R3 и вычисляем среднее арифметическое for (int i=0; i<100; ++i) { // делаем 100 замеров Uacc = Uacc + analogRead(A0); Uakb = Uakb + analogRead(A1); } Uacc = Uacc/100; Uakb = Uakb/100; //Serial.println(Uacc*0.01537); float U_acc_real = 0.0 + Uacc * 0.01537;//(5 / 1023.0 * 3.136); //Вычисляем реальное напряжение +ACC на входе делителя (A0) 3.1189=поправка делителя.(коэф деления) 0.2-падение на диоде float U_akb_real = Uakb * 0.015330;//(5 / 1023.0 * 3.145); //Вычисляем реальное напряжение +30 на входе делителя (A1) //Serial.println(U_akb_real); // вывод напруги АКБ в ком порт для калибровки.
// кусок кода ниже нужен для того, чтобы при включении и сразу выключении ACC при полностью выключенном планшете(холодный старт) экран мог тухнуть по сигналу датчика холла. if (millis() > pauseTimeHALL && flagHALL == 0 || millis() > 10000 && flagACC == 1) { flagHALL = 1; //проверка отсчета при холодном старте при включении и сразу выключении ACC } if ((U_akb_real - U_acc_real) >4 )//проверка, выключили ли мы зажигание или просто стартуем (1 - выключили заж, 0 - стартуем) {timeAfterACC = 500;} // 1 - выключили зажигание. ЕСЛИ +15 ПРОПАДАЕТ ВО ВРЕМЯ СТАРТА, ТО ВМЕСТО 500 НАДО 5000 или вообще убрать этот блок if-else. else {timeAfterACC = 5000;} // 0 - заводим машину (стартуем).
// ------------========================== блок ACC ========================-----------------------------------------------------------------------------
// -----------------=========ВКЛЮЧИЛИ ЗАЖИГАНИЕ=============---------------- if (15.5 > U_acc_real && U_acc_real >= UaccONorOFF && flagACC == 0 && flagAKB == 1 ) //проверка напруги АСС и АКБ при флаге ACC = 0 { flagACC = 1; pauseTimeACC = millis(); pauseTimeAKB = millis(); lcd.clear(); //очистка экрана }
if (millis() - pauseTimeACC >= 500 && flagACC == 1) // пауза 0,5c после включения ACC и потом делать следующ(пока включено ACC): { digitalWrite(PlanshBATpin, 1); //включаем питание на батарею планшета (in2) } if (millis() - pauseTimeACC >= 800 && flagACC == 1) // пауза 0.8c после включения ACC и потом делать следующ(пока включено ACC): //через 0,8с после включения ACC включаем экран, включаем питание на видеорегистратор. { digitalWrite(II_KIW_pin_POGOpin, 1); //включаем +5V (POGO(USB) нужно для распознавания планшетом признака зарядки. ( можно подавать на +5В USB кабеля (для тимуровской прошивки или если не используется датчик холла) digitalWrite(OTGpin, 1); //включаем минус на Y-OTG (включается звуковая карта) digitalWrite(REGISTRATORpin, 1); // включаем питание на видеорегистратор } if (millis() - pauseTimeACC >= 2000 && flagACC == 1)//через 1с после включения ACC включаем экран (вЫключаем минус на упр SLEEP), выход REM(если больше 12в), Включаем хаб (подаем минус на управляющий транзюк хаба, тот открывается и пускает +5В с KIW (2вых)на хаб) { digitalWrite(SLEEPpin, 0); //включаем экран = вЫключаем минус на упр SLEEP digitalWrite(HUBpin, 0); //Включаем хаб = подаем минус на управляющий транзюк хаба, тот открывается и пускает +5В с KIW (2вых)на хаб if (U_akb_real >= 12 && flagACC == 1)//если напруга батареи больше 12В, то включаем еще и усилитель звука (выход REM) { digitalWrite(REMpin, 1); // включаем выход REM } }
//-----------------=========ВЫКЛЮЧИЛИ ЗАЖИГАНИЕ=============----------------
if (U_acc_real < UaccONorOFF && flagACC == 1) { flagACC = 0; //Выключили зажигание digitalWrite(REMpin, 0); // выключаем выход REM pauseTimeACC = millis(); pauseTimeAKB = millis(); lcd.clear(); //очистка экрана\ } if (millis() - pauseTimeACC >= timeAfterACC && flagACC == 0) //пауза 5c или 0.5c после вЫключения ACC и потом делать следующ://через 5с после выключения зажигания вЫключаем минус на Y-OTG, ВЫключаем хаб, вЫключаем +5V (POGO(USB)), тушим экран (если прошло 2мин со старта БП) { digitalWrite(OTGpin, 0); //вЫключаем минус на Y-OTG (8 pin PW1) digitalWrite(II_KIW_pin_POGOpin, 0); //вЫключаем +5V (POGO(USB)) digitalWrite(HUBpin, 1); // ВЫключаем хаб = подаем + на управляющий транзюк хаба, тот закрывается и не пускает +5В с KIW (2вых)на хаб lcd.noBacklight(); // тушим подсветку экрана if (flagHALL == 1) { digitalWrite(SLEEPpin, 1); //включаем минус на SLEEP (7 pin PW1)при этом тухнет экран (если прошло 2 минуты с момента включения ардуины) } else { digitalWrite(SLEEPpin, 0); } }
// -------------------------========================= блок АКБ ==========================-------------------------------------------------------------------------------
if (U_acc_real >= UaccONorOFF) {UakbONorOFF = 11.5;} else {UakbONorOFF = 11.9;} //при включении зажигания напряжение самовырубания станет 11,5 вместо 11,9
if ((U_akb_real < UakbONorOFF && flagAKB == 1)||(U_akb_real >15.5))// ситуация, когда сел при работе ардуины аккумулятор, либо сел в процессе работы или простоя автомобиля, либо перезарядка > 15.5В { flagAKB = 0;//спустили флаг батареи flagACC = 0; pauseTimeACC = millis(); pauseTimeAKB = millis(); lcd.clear(); //очистка экрана }
if ((15.5 > U_akb_real) && ((U_akb_real >= UakbONorOFF) && flagAKB == 0)) //проверка +30 на перезаряд >15.5В, и больше заданного в 155 строке, и флага акб { if (millis() - pauseTimeACC >= 2000 && flagAKB == 0){ digitalWrite(SAMOZAPITKApin, 1); // включаем самозапитку через 2с flagAKB = 1;} //подняли флаг батареи }
if (millis() - pauseTimeAKB >= 20000 && flagAKB == 0) // если севший аккумулятор //через 20с вЫключаем питание на батарею планшета и вырубаем сам БП. { digitalWrite(PlanshBATpin, 0); //вЫключаем питание на батарею планшета (in2) digitalWrite(OTGpin, 0); //вЫключаем минус на Y-OTG (8 pin PW1) digitalWrite(II_KIW_pin_POGOpin, 0); //вЫключаем +5V (POGO(USB)) digitalWrite(HUBpin, 1); // подаем + на управляющий транзюк хаба, тот закрывается и не пускает +5В с KIW (2вых)на хаб = ВЫключаем хаб digitalWrite(REMpin, 0); // // выключаем выход REM digitalWrite(REGISTRATORpin, 0); // выключаем питание на видеорегистратор digitalWrite(SAMOZAPITKApin, 0); //выключаем SAMOZAPITKApin, при этом пропадает управление на IN4, система ПОЛНОСТЬЮ обесточивается delay (5000); // задержка для аппаратного выключения }
if (flagAKB == 1 && flagACC == 0) //ситуация, когда норм акб и выключено зажигание (ACC) { if ((millis() - pauseTimeAKB )>= 86400000 && flagAKB == 1) // если прошло 24 часа, как выключили ACC // пауза (3600000 - 60мин) (60000 - 1 мин)(10800000=3ч) (1800000=5ч) { digitalWrite(PlanshBATpin, 0); //вЫключаем питание на батарею планшета (in2)//(батарея планшета)) }
if ((millis() - pauseTimeAKB) >= 172800000 && flagAKB == 1) // если давно выключили ACC ) (2суток = 172800000)) //(самозапитка для регистратора) { digitalWrite(REGISTRATORpin, 0); // выключаем питание на видеорегистратор digitalWrite(SAMOZAPITKApin, 0); //выключаем SAMOZAPITKApin, при этом система ПОЛНОСТЬЮ обесточивается delay (5000); // задержка для аппаратного выключения } }
//* //******************************************отслеживания аварийной ситуации ITS716G******************************************************************************************************************************************************************************** //отслеживания аварийной ситуации ITS716G канал 1 (питание KIW3312s-out2 и регистратор-out1) 0 = норма 1 = авар. сит. //тогда моргаем 13 ногой код "1" //отслеживания аварийной ситуации ITS716G канал 2 (выход REM-out3 и самозапитка БП-out4 )0 = норма 1 = авар. сит. //тогда моргаем 13 ногой код "2" if(SAMOZAPITKApin==1 || PlanshBATpin==1 ||REMpin==1 || REGISTRATORpin ==1) // если проц включал любой канал ITS { if(STATEpinI == 0) { // и если пин защиты показал аварию for (int i=0; i <= 300; i++) { //тогда моргаем 13 ногой код "1" 10 минут, если они прошли и асс ВКЛ, тогда еще раз и еще по кругу, пока неисправность не уйдёт digitalWrite(13, 1); delay(500); digitalWrite(13, 0); delay(1493); digitalWrite(PlanshBATpin, 0); //вЫключаем питание на батарею планшета (in2) digitalWrite(OTGpin, 0); //вЫключаем минус на Y-OTG (8 pin PW1) digitalWrite(II_KIW_pin_POGOpin, 0); //вЫключаем +5V (POGO(USB)) digitalWrite(HUBpin, 1); // подаем + на управляющий транзюк хаба, тот закрывается и не пускает +5В с KIW (2вых)на хаб = ВЫключаем хаб digitalWrite(REMpin, 0); // // выключаем выход REM digitalWrite(REGISTRATORpin, 0); // выключаем питание на видеорегистратор digitalWrite(SAMOZAPITKApin, 0); //выключаем SAMOZAPITKApin, при этом пропадает управление на IN4, система ПОЛНОСТЬЮ обесточивается wdt_reset(); //Сброс таймера watchdog } } ; if(STATEpinII == 0) { // и если пин защиты показал аварию for (int i=0; i <= 150; i++) { //тогда моргаем 13 ногой ногой код "2" 10 минут, если они прошли и асс ВКЛ, тогда еще раз и еще по кругу, пока неисправность не уйдёт digitalWrite(13, 1); delay(500); digitalWrite(13, 0); delay(493); digitalWrite(13, 1); delay(500); digitalWrite(13, 0); delay(1493); digitalWrite(PlanshBATpin, 0); //вЫключаем питание на батарею планшета (in2) digitalWrite(OTGpin, 0); //вЫключаем минус на Y-OTG (8 pin PW1) digitalWrite(II_KIW_pin_POGOpin, 0); //вЫключаем +5V (POGO(USB)) digitalWrite(HUBpin, 1); // подаем + на управляющий транзюк хаба, тот закрывается и не пускает +5В с KIW (2вых)на хаб = ВЫключаем хаб digitalWrite(REMpin, 0); // // выключаем выход REM digitalWrite(REGISTRATORpin, 0); // выключаем питание на видеорегистратор digitalWrite(SAMOZAPITKApin, 0); //выключаем SAMOZAPITKApin, при этом пропадает управление на IN4, система ПОЛНОСТЬЮ обесточивается wdt_reset(); //Сброс таймера watchdog } } ; }
//*/ //**************************************************************************************************************************************************************************************************************************
//******************************************индикация светодиодом и задержка вывода на дисплей******************************************************************************************************************************************************************************** ms = millis(); // Событие срабатывающее каждые 125 мс if ( ( ms - ms1 ) > 125 || ms < ms1 ) { ms1 = ms; // Режим светодиода ищем по битовой маске if ( blink_mode & 1 << (blink_loop & 0x07) ) digitalWrite(13, HIGH); else digitalWrite(13, LOW); blink_loop++; } // Событие срабатывающее каждые 250 мс if ( ( ms - pauseDisplay ) > 350 || ms < pauseDisplay ) { pauseDisplay = ms; //_____________________________________________СООБЩЕНИЕ НА ДИСПЛЕЙ____________________________________________________________
int H = (millis()/3600000); int M = ((millis()-(H*3600000))/60000); //int S = (((millis()/1000)-(H*3600))- (M*60)); if ((((millis())-(H*3600000))- (M*60000)) < 200 ){lcd.clear(); }//очистка экрана
if (flagACC == 1){lcd.backlight();}//}else {lcd.noBacklight();} //lcd.backlight();
//вывод времени работы lcd.setCursor(0, 0); lcd.print((millis() )/60000); // вывод кол-ва минут работы блока ( 1 строка 1 символ) lcd.setCursor(9, 0); lcd.print(flagACC); // вывод флага АСС lcd.setCursor(11, 0); lcd.print(U_acc_real); // вывод напряжения АСС //lcd.setCursor(5,1); //-------------------2 строка--------------------------------- lcd.setCursor(0, 1); unsigned long TIMER = ( pauseTimeAKB + 172800000 - millis() )/60000; // вывод кол-ва минут, оставшиеся до выключения блока (когда выключено АСС) lcd.print(TIMER); lcd.setCursor(9, 1); lcd.print(flagAKB); // вывод флага АКБ lcd.setCursor(11, 1); lcd.print(U_akb_real); // вывод напряжения АКБ /* так выглядит индикация на дисплее ================ |1 0 0.00 | 1 строка * вывод кол-ва минут работы блока * флаг АСС * вывод напряжения АСС |616 1 14.50| ================ 2 строка * кол-во минут, оставшиеся до выключения блока * флаг АКБ * вывод напряжения АКБ *///__________________________________________________________________________________________________________________________ } // blink_mode = modes[3]; if (blink_mode != modes[5] || blink_mode != modes[5]) { if (flagAKB == 0 ){blink_mode = modes[3];} // индикация напруги батареи на ардуинине.- низкое напряжение АКБ авто - коротко моргает if (flagAKB == 1 && flagACC == 0) {blink_mode = modes[6];} //- нормальное напряжение АКБ авто, ACC выключено. - быстро моргает if (flagAKB == 1 && flagACC == 1) {blink_mode = modes[2];} //- нормальное напряжение, включено ACC, рабочий режим. - медленно моргает } /* ********************************************************************************************************** 0B00000000, //Светодиод выключен blink_mode = modes[0]; 0B11111111, //Горит постоянно blink_mode = modes[1]; 0B00111111, //Мигание по 0.8 сек blink_mode = modes[2]; - нормальное напряжение, включено ACC, рабочий режим. 0B00000001, //Короткая вспышка раз в секунду = modes[3]; - низкое напряжение АКБ авто 0B00000101, //Две короткие вспышки раз в секунду 0B00010101, //Три короткие вспышки раз в секунду 0B01010101 //Частые короткие вспышки (4 раза в секунду)= blink_mode = modes[6]; - нормальное напряжение АКБ авто, ACC выключено. */ //**********************************************************************************************************
wdt_reset(); //Сброс таймера watchdog
} //конец цикла void loop()
//
|