обратный отсчет на RTC

dimOnOff
Offline
Зарегистрирован: 21.04.2015

Доброго времени суток, уважаемые форумчане!

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

 

#include <Wire.h>
#include <DS1307new.h>

void countdown ()
{   
  byte seconds = ((17 - RTC.second)+60)%60; //17 - час сработки (здесь может быть любая цифра 0- 23)
  byte minutes = ((23 - RTC.minute)+60)%60; //23 - минута сработки (здесь может быть любая цифра 0- 59)
  byte hours   = ((45 - RTC.hour)+24)%24;   //45 - секунда сработки (здесь может быть любая цифра 0- 59)

  Serial.print(hours);
  Serial.print(':');
  Serial.print(minutes);
  Serial.print(':');
  Serial.println(seconds);
}

void setup(void)
{
    Serial.begin(9600);
    
}
void loop(void)
{  
    RTC.getTime();
    countdown ();         
}

T.Rook
Offline
Зарегистрирован: 05.03.2016

Ну все так и должно быть. Библиотеки тут ни при чем. На алгоритм разницы времени посмотрите внимательно. Вы ведь отдельно считаете разницу секунд, минут и часов совершенно не учитывая возникшую "нехватку" секунды в минуте. Вот и получается у вас -1сек=59 сек а на минуты влияния никакого. Один из простых способов: сигнальное_время.(часы*3600+минуты*60+секунды )- (тоже самое от RTC) и обратно выделить часы минуты и секунды.

dimOnOff
Offline
Зарегистрирован: 21.04.2015

Все понятно. Попробую так сделать. Спасибо.

Mr.Privet
Mr.Privet аватар
Offline
Зарегистрирован: 17.11.2015

я надеюсь это не для бо.... это для кухонного таймера?

dimOnOff
Offline
Зарегистрирован: 21.04.2015

БлииииН))) Ну конечно не для бо...) Для автополивалки) 

dimOnOff
Offline
Зарегистрирован: 21.04.2015

Способ перевода в секунды и обратно дает такой же результат. Вероятно, как-то нужно секунды научиться синхронизировать с модулем часов. 

 

 

 

NeiroN
NeiroN аватар
Offline
Зарегистрирован: 15.06.2013

Я когда делал таймер все сравнения выполнял в секундах и отчет вел в секундах и только перед выводом использовал деление и остаток от деления

количество_секунд=Часы.сейчас().количество_секунд()

время=(точка_старта+интервал)-количество_секунд

если время<0 тогда время = 0

если старое_время != время тогда {

секунды=время%60

минуты=(время/60)%60

часы=(время/3600)%24

Сериал.вывод(формат("%d:%d:%d",часы,минуты,секунды))

старое_время = время

}

dimOnOff
Offline
Зарегистрирован: 21.04.2015

На скорую руку соорудил по Вашей схеме , NeiroN. Вроде работает. Я так понял, что работает, когда точка_старта > часы_сейчас.  А что, если точка_старта < часы_сейчас? Т.е. точка старта перенеслась на завтра ? 

Andy
Andy аватар
Offline
Зарегистрирован: 01.01.2016

Цитата:
А что, если точка_старта < часы_сейчас? Т.е. точка старта перенеслась на завтра ?
точка_старта - часы_сейчас + 86400

Mr.Privet
Mr.Privet аватар
Offline
Зарегистрирован: 17.11.2015

Если тебе надо для автополировки я так понял что счет идет на минуты, так что бы не сделать через миллис?

NeiroN
NeiroN аватар
Offline
Зарегистрирован: 15.06.2013

ну если убрать "%24" (остаток от деления на 24) то можно хоть 100500 часов сделать. Вообще есть такая методика измерения времени как число секунд с определенной даты - unixtime считает секунды с первой версии unix

если используете тип unsigned long в переменной то сравнения лучше переписать - этот тип не может быть меньше 0.

Andy
Andy аватар
Offline
Зарегистрирован: 01.01.2016

Растениям важно знать, что с 1 января 1970 года прошло 1458691200 секунд, и что следующий полив состоится на 1458777600 секунде.

dimOnOff
Offline
Зарегистрирован: 21.04.2015

Добавление новых суток по условию  "если время<0 тогда время = время+ 86400" помогло)) Спасибо.  

Sindbad
Offline
Зарегистрирован: 08.12.2015

Andy пишет:

Растениям важно знать, что с 1 января 1970 года прошло 1458691200 секунд, и что следующий полив состоится на 1458777600 секунде.

Очень смешно. Через юникстайм имеет смысл делать не ради точности в секундах, а ради упрощения скетча. Велосипед давно изобретен и включен в расово верные библиотеки: http://playground.arduino.cc/Code/Time

 

dimOnOff
Offline
Зарегистрирован: 21.04.2015

В процессе возник еще вопрос : как в обратном отсчете задействовать дни? Как проверить в какой следующий из дней произойдет включение таймера? В том смысле, что дни, в которые будет включаться таймер, будут меняться: каждый день, через день, день через два ну или любые др. варианты. Не могу понять логику. Может есть какие идеи, подскажите, пожалуйста. 

NeiroN
NeiroN аватар
Offline
Зарегистрирован: 15.06.2013

1 день = 24 часа = 1440 минут = 86400 секунд

обратный отсчет всегда связан с моментом старта.

есть библиотека RTC с обьектом даты. Есть даже с timedelta: к обьекту даты можно прибавить обьект timedelta - размер обьекта задается в часах или минутах или днях 

Если нет то берем unixtime прибавляем секунды, создаем новый обьект даты из результирующего unixtime - готово - мы знаем когда в следующий раз включится реле.

dimOnOff
Offline
Зарегистрирован: 21.04.2015

Спасибо. Опробую.