Проблема с питанием - неадекватные символы на экране при питании от батарейки
- Войдите на сайт для отправки комментариев
Добрый день! Недавно вспомнил о своём старом проекте (его суть изложена в теме по ссылке: http://arduino.ru/forum/programmirovanie/spidometr-rabotayushchii-s-pomo...). Довёл, кстати говоря, до ума, и вопросов по вычислению скорости больше нет (использовал округление числа, функция ceil, надеюсь, здесь всё правильно, но если нет, прошу поправить). И всё работает прекрасно, но только тогда, когда arduino uno подключена к компьютеру через провод USB. Как только я пытаюсь её подключить от батарейки через VIN-вход, она вроде бы работает, но при этом на экран, во-первых, вместо чисел и фразы "km/h" (кстати, дисплей почему-то отказался поддерживать любые знаки, даже пробел, и мне пришлось функцией char самостоятельно рисовать все знаки - это очень странно, поскольку такой же дисплей в прошлых проектах хорошо работал с любыми знаками, но это не самое главное в моём вопросе), выводятся бессмысленные хаотичные символы.
А во-вторых, они выводятся не в том месте, где должна была выводиться скорость (с помощью предварительной настройки курсора функцией setCursor()), а в любом месте, иногда эти символы заполняют весь экран.
---
Предоставляю изменённый код скетча, если нужно (хотя вряд ли проблема кроется в нём):
P. S. Пробовал включить, используя 9 V-крону, 4 батарейки AA а также через понижающий преобразователь lm2596 и круглый вход вместо входа vin. Все разы arduino запускалась и работала, но выводила на экране неадекватные символы.
#include <Wire.h>
#include <LiquidCrystal_I2C.h> //библиотека для экрана
int gerkontime1 = 0; //эти две переменные нужны для того, чтобы оберечься от дребезга геркона
int gerkontime2 = 0;
int sekundi = 0; //эта переменная впоследствии будет являться количеством секунд с последнего сброса переменной gerkon при подсчёте скорости (знаю, не так назвал, но лень было менять название во всём коде, поэтому оставил)
int gerkon = 0; // собственно, количество полных оборотов колеса
int time24 = 0; //переменная для подсчёта миллисекунд с последнего сброса количества оборотов
int dlina = (3, 14) * 65; //радиус = 1/2 диаметра 26 дюймов (1 дюйм=2,5 см)
int mvsekundu = 0; //в этой переменной будет скорость в м/с
int realskorost = 0; // в этой переменной будет новая скорость, а в следующей - старая
int starayaskorost = 0;
LiquidCrystal_I2C lcd(0x3F,16,2);
byte simvol[8] = {
0b00001,
0b00010,
0b00010,
0b00100,
0b00100,
0b01000,
0b01000,
0b10000
};
void setup() {
Serial.begin(9600); //использовалось для проверок переменных, для отладки
pinMode(2, INPUT); //контакт геркона
pinMode(13, OUTPUT); //второй контакт геркона
digitalWrite(13, HIGH);
lcd.init();
lcd.backlight();
lcd.createChar(1, simvol);
lcd.setCursor(7,1);
lcd.print("km");
lcd.setCursor(9,1);
lcd.print(char(1));
lcd.print("h");
delay(500);
lcd.clear();
}
void contact () {
int time1 = millis() - time24; // постоянно мониторим, сколько времени прошло с момента последнего сброса
gerkontime2 = millis() - gerkontime1;
if (gerkontime2 <= 200) {
// если с момента срабатывания геркона прошло менее 500 миллисекунд, значит это дребезг и ничего не надо делать
}
else {
if (time1 < 4000) {
++gerkon;
//ещё один полный оборот колеса
}
if (time1 >= 4000) {
//если прошло более 4 секунд, делаем вычисления
starayaskorost = realskorost; // бывшая realskorost теперь уже starayaskorost))
sekundi = ceil(time1) / 1000; // поскольку здесь более 4 секунд, не факт, что велосипедист едет очень медленно и после срабатывания геркона на 3 секунде, не может следующее срабатывание быть не на 4, а на 5 или 6.
int dlina4 = (dlina / 100)*gerkon; //2,041*gerkon
//длина окружности была указана в сантиметрах, переводим в метры и умножаем на количество оборотов
mvsekundu = dlina4 / sekundi; //9,16
//теперь находим скорость в метрах в секунду
realskorost = mvsekundu * 3, 6; //переводим в км/ч
lcd.setCursor(3,1);
lcd.print(ceil(realskorost));
lcd.createChar(1, simvol);
lcd.setCursor(7,1);
lcd.print("km");
lcd.setCursor(9,1);
lcd.print(char(1));
lcd.print("h");
time24 = millis();
gerkon = 0;
//обнуляем переменную gerkon и обновляем переменную time24
}
gerkontime1 = millis(); //это всё для той же защиты от дребезга, при первом срабатывании геркона записывается текущее время
}
}
void loop() {
int time1 = millis() - time24; //на всякий случай, постоянно обновляем переменную time1
if (digitalRead(2)==LOW) {
contact();
}
Serial.println(realskorost); //использовалось для проверки, закомментировано)
// Serial.println(realskorost);
// Serial.println(" km/h");
}
P. P. S. - цифры 9,16 и 2,041 в комментариях - здесь ни к чему, эти цифры я писал в комментарии во время проверки, и забыл удалить
Я думаю, не надо быть семи пядей во лбу, чтобы сообразить, что проблема в питании.
Крона - очень маломощный источник. Максимум, на что ее может хватить - на кратковременное (максимум - десятки секунд) включение самой Ардуины и экономичного экрана. Подсветка экрана способна сразу убить крону. Измерьте напряжение на кроне при работе Ардуино. Лучше - осциллографом. Если есть провалы ниже 7 В, питания явно не хватает.
4 батарейки - это около 6 Вольт. На прямую на 5В такое напряжение подавать страшновато, а для стабилизатора все, что ниже 7 В - мало. Добавьте пятую батарейку.
Более или менее вменяемое питание - от двух элементов 18650.