millis или прерывания.

AndreyD
AndreyD аватар
Offline
Зарегистрирован: 07.10.2018

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



#include <MsTimer2.h>
byte my_h=0, my_m=0, my_s=0, lmy_h=1, lmy_m=1, lmy_s=1; // внутренние часы, минуты, секунды
void mytime()
{
 my_s++;
 if (my_s > 59) {my_s = 0; my_m++;}
 if (my_m > 59) {my_m = 0; my_h++;}
 if (my_h > 23) my_h = 0;
}
void setup() {
  MsTimer2::set(1000, mytime); // прерывание каждую секунду 
  MsTimer2::start();
}
void loop() {
  if (my_s != lmy_s) { // каждую секунду
    lmy_s = my_s;

  }
  if (my_m != lmy_m) { // каждую минуту
    lmy_m = my_m; 
    
  }
  if (my_h != lmy_h) { // каждый час
     lmy_h = my_h;

  }


}

 

rkit
Offline
Зарегистрирован: 23.11.2016

Будут баги или нет - это только от тебя зависит.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

rkit абсолютно прав: пока неизвестно, что именно должен делать код, невозможно определить, делает ли он то, что должен.

Перефразируя: Программа всегда делает то, что написал программист, хотя это и не всегда совпадает с тем, что он хотел написать.

Morroc
Offline
Зарегистрирован: 24.10.2016

Вроде часики тикают. На данном этапе багов может и нет пока )

AndreyD
AndreyD аватар
Offline
Зарегистрирован: 07.10.2018

Вот пример кода одного из моих контроллеров на arduino nano. Вроде пашет, но может можно что-нибудь улучшить? Библиотеки гайвера использую т.к. только его нашёл урезанные, а полные не влезали. Контроллер получает данные с датчиков и управляет лампами и герляндой, идет обмен данных  с основным контроллером и управление от него по MQTT. Предусмотрено дублирование расчёта заката и рассвета при обрыве связи, ну и автономная работа при этом обрыве.

/* Начало блока подключения библиотек */
#include <SPI.h> //для SPI устройств
#include <Ethernet2.h> // для сетевого модуля
#include <EthernetUdp2.h> // для UDP протокола
#include <MsTimer2.h> // для внутреннего времени
#include <PubSubClient.h> // для MQTT
#include <DS1307RTC.h> //для модуля времени
#include <TimeLib.h> //для работы с датой и веменем
#include <microWire.h> // для I2C устройств
#include <GyverBME280.h> // для датчика температуры, влажности и давления
#include <BH1750FVI.h> // для датчика интенсивности света
/* Конец блока подключения библиотек */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
tmElements_t tm; // Время
byte l1_count=0; //таймер минут для включения света навес
byte l2_count=0; //таймер минут для включения света туалет
byte lmonth = -1,lday = -1,lhour = -1,lmin = -1,lsec = -1; // для отсчёта времени
unsigned int minutes=720, vos=360, zak=1080;  // какая сейчас минута в дне, минуты восхода и заката
// Макросы
#define B_TRUE(bp,bb) (bp) |= (bb)
#define B_FALSE(bp,bb) (bp) &= ~(bb)
#define B_READ(bp,bb) bool((bp) & (bb))
#define B_RAVNO(bp,bb,br) if (br) (bp) |= (bb); else (bp) &= ~(bb);
// Одиночные флаги
unsigned int booleans = 0; // byte - 8 флагов; unsigned int - 16 флага; unsigned long - 32 флага.
#define girl_activ 1 // флаг активации гирлянды
#define day_n      2 // день/ночь
#define lday_n     4
#define day_nus    8 // утренние сумерки
#define lday_nus   16
#define day_nvs    32 // вечерние сумерки
#define lday_nvs   64
#define lper       128 // переключатель
#define svet       256 // свет Навес
#define con_mqtt   512 // флаг связи с сервером MQTT
#define reg_l1_d1  1024 // режим работы лампа навес от датчика движения
#define reg_l2_d2  2048 // режим работы лампа туалет от датчика движения
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Начало блока сетевых настроек */
byte mac[] = {0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xEA}; // мак адрес этого модуля
IPAddress ip(192, 168, 0, 2); //ip этого модуля
IPAddress ipMQTT(192, 168, 0, 1); // ip MQTT сервера 
byte con_net=0; // счетчик минут дисконнекта сеть
/* Конец блока сетевых настроек */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
// пины ламп
#define PIN_L1 2 // пин свет навес
#define PIN_L2 3 // пин свет туалет
// пин на гирлянду
#define PIN_GIRL 5 // пин гирлянды
#define PIN_DATCH1 6 // пин датчик движения навес
#define ETH_RST 7 //перезагрузка W5500
#define ETH_INTN 8 //прерывания W5500
#define PIN_PER 9 // пин переключателя
#define PIN_DATCH2 15 //датчик движения забор A1
#define PIN_DATCHZ 16 // пин магнитного датчика A2
/* Конец блока выбора пинов */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Начало блока выбора датчика температура/влажность/давление/освещённость */
GyverBME280 bme;
BH1750FVI lightMeter;
float t=0,h=0; unsigned int pr=0,lux=0; //переменные температуры,влажности,давления и интенсивности света
/* Конец блока выбора датчика температура/влажность/давление/освещённость */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Начало блока настроек MQTT */
const char *Mqtt_Pub_Str[] = // максимум 32 топика на отправку в зависимости от размера Mqtt_Update_flag
  {"o/d/d1",  // 0 датчик движения навес
   "o/d/d2",  // 1 датчик движения забор
   "o/d/d3",  // 2 магнитный датчик
   "o/d/p",   // 3 переключатель
   "o/d/l2",  // 4 лампа навес
   "o/d/l3",  // 5 лампа туалет
   "o/d/g",   // 6 гирлянда
   "o/d/s",   // 7 датчик света
   "o/d/t",   // 8 температура
   "o/d/h",   // 9 влажность
   "o/d/pr",  // 10 давление
   "o/d/db"   // 11 строка отладки
  };
byte Mqtt_Update_flag_len = sizeof(Mqtt_Pub_Str) / sizeof(char *);
unsigned int Mqtt_Update_flag = 0; // byte - 8 флагов; unsigned int - 16 флага; unsigned long - 32 флага.
#define mqtt_d1_f    1 // датчик движения навес
#define mqtt_d2_f    2 // датчик движения забор
#define mqtt_d3_f    4 // магнитный датчик
#define mqtt_p_f     8 // переключатель
#define mqtt_l2_f    16 // лампа навес
#define mqtt_l3_f    32 // лампа туалет
#define mqtt_g_f     64 // гирлянда
#define mqtt_s_f     128 // датчик света
#define mqtt_t_f     256 // температура
#define mqtt_h_f     512 // влажность
#define mqtt_pr_f    1024 // давление
#define mqtt_db_f    2048 // строка отладки
byte Mqtt_Data1=0; // byte - 8 флагов; unsigned int - 16 флага; unsigned long - 32 флага. 
#define mqtt_d1    1 // датчик движения навес
#define mqtt_d2    2 // датчик движения забор
#define mqtt_d3    4 // магнитный датчик
#define mqtt_p     8 // переключатель
#define mqtt_l2    16 // лампа навес
#define mqtt_l3    32 // лампа туалет
#define mqtt_g     64 // гирлянда
#define mqtt_s     128 // датчик света
float Mqtt_Data2[3]; // температура, влажность и давление
char Mqtt_debug[20]; // строка отладки
EthernetClient ethClient;
PubSubClient client(ethClient);

void mqtt_publish_changes() { // отправка топиков
  char buff[20];
  if (Mqtt_Update_flag){
   delay (50);
   unsigned long j = 1;
   for (byte i = 0; i < Mqtt_Update_flag_len; i++, j = 2*j) {
     if (B_READ(Mqtt_Update_flag,j)){
       if (i < 8) dtostrf(B_READ(Mqtt_Data1,j),1,0,buff);
       if (i == 8 || i == 9) dtostrf(Mqtt_Data2[i-8],3,1,buff);
       if (i == 10) dtostrf(Mqtt_Data2[2],3,0,buff);
       if (i == 11) for (byte a = 0; a < 20; a++) buff[a] = Mqtt_debug[a];
       client.publish(Mqtt_Pub_Str[i], buff);
       B_FALSE(Mqtt_Update_flag,j);
       return;
     }
   }
  }
}
void callback(char* topic, byte* payload, unsigned int length) { //здесь обрабатываем входящие топики
  String strTopic = String(topic);
  if (strTopic == "i/d/l2") {
    if ((char)payload[0] == '0') {digitalWrite(PIN_L1, HIGH); l1_count=0; B_FALSE(booleans,reg_l1_d1);}
    if ((char)payload[0] == '1') {digitalWrite(PIN_L1, LOW); B_TRUE(booleans,reg_l1_d1);}}
  if (strTopic == "i/d/l3") {
    if ((char)payload[0] == '0') {digitalWrite(PIN_L2, HIGH); l2_count=0; B_FALSE(booleans,reg_l2_d2);}
    if ((char)payload[0] == '1') {digitalWrite(PIN_L2, LOW); B_TRUE(booleans,reg_l2_d2);}}
  if (strTopic == "i/d/g") {
    if ((char)payload[0] == '0') B_FALSE(booleans, girl_activ); 
    if ((char)payload[0] == '1') B_TRUE(booleans, girl_activ);}
  if (strTopic == "i/d/c") {
    if ((char)payload[0] == '1') {
      unsigned long j = 1;
      for (byte i = 0; i < Mqtt_Update_flag_len; i++, j = 2*j) B_TRUE(Mqtt_Update_flag,j);
    }
    if ((char)payload[0] == '2') {
      B_TRUE(Mqtt_Update_flag,mqtt_db_f);
      if (RTC.read(tm)) {
        int years = tm.Year + 1970;
        sprintf(Mqtt_debug,"%02d:%02d:%02d %02d/%02d/%04d",tm.Hour, tm.Minute, tm.Second, tm.Day, tm.Month, years); 
      } else sprintf(Mqtt_debug,"Time error %d",0);
    }
  }
  if (strTopic == "i/a/m") { minutes = 0;
    for (byte i=1; i <= length; i++) minutes = minutes + (((char)payload[i-1]-'0')*pow(10,length-i));
    if (length > 1) minutes++;
    con_net=241;
  }
  if (strTopic == "i/a/v") { vos = 0;
    for (byte i=1; i <= length; i++) vos = vos + (((char)payload[i-1]-'0')*pow(10,length-i));
    if (length > 1) vos++;
  }  
  if (strTopic == "i/a/z") { zak = 0;
    for (byte i=1; i <= length; i++) zak = zak + (((char)payload[i-1]-'0')*pow(10,length-i));
    if (length > 1) zak++;
  }  
 }
/* Конец блока настроек MQTT */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Начало блока настройки внутренних часов */
byte my_h=0, my_m=0, my_s=0, lmy_h=1, lmy_m=1, lmy_s=1; // внутренние часы, минуты, секунды
void mytime() // функция внутренниех часов
{
 my_s++;
 if (my_s > 59) {my_s = 0; my_m++;}
 if (my_m > 59) {my_m = 0; my_h++;}
 if (my_h > 23) my_h = 0;
}
void secundesF() { // выполняется каждую секунду
      lux = lightMeter.GetLux();
      if (lux > 4) B_TRUE(booleans,svet); else if (lux < 1) B_FALSE(booleans,svet);
      if (B_READ(booleans,svet) != B_READ(Mqtt_Data1,mqtt_s)) {B_TRUE(Mqtt_Update_flag,mqtt_s_f); B_RAVNO(Mqtt_Data1,mqtt_s,B_READ(booleans,svet));} 
}
void minutesF() { // выполняется каждую минуту
      day_nf(); // день или ночь
      t = (int)(bme.readTemperature()*10); t = (float)(t/10);
      if (t != Mqtt_Data2[0]) {B_TRUE(Mqtt_Update_flag,mqtt_t_f); Mqtt_Data2[0]=t;} // если изменилась, то флаг на отправку  
      h = (int)(bme.readHumidity()*10); h = (float)(h/10);
      if (h != Mqtt_Data2[1]) {B_TRUE(Mqtt_Update_flag,mqtt_h_f); Mqtt_Data2[1]=h;} // если изменилась, то флаг на отправку
      pr = pressureToMmHg(bme.readPressure());
      if (pr != Mqtt_Data2[2]) {B_TRUE(Mqtt_Update_flag,mqtt_pr_f); Mqtt_Data2[2]=pr;} // если изменилась, то флаг на отправку 
      if (l1_count == 1) digitalWrite(PIN_L1, HIGH); // отключение лампы навес
      if (l2_count == 1) digitalWrite(PIN_L2, HIGH); // отключение лампы туалет
      if ((l1_count > 0) && !B_READ(booleans,reg_l1_d1)) l1_count--; if ((l2_count > 0) && !B_READ(booleans,reg_l2_d2)) l2_count--;

      if (con_net > 0) con_net--;
      B_TRUE(booleans, con_mqtt);
}
void hoursF() { // выполняется каждый час
     unsigned long j = 1;
     for (byte i = 0; i < Mqtt_Update_flag_len; i++, j = 2*j) B_TRUE(Mqtt_Update_flag,j);
}
/* Конец блока настройки внутренних часов */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
void setup() {
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Начало блока установки режимов пинов */
  pinMode(PIN_L1,OUTPUT); digitalWrite(PIN_L1, HIGH);
  pinMode(PIN_L2,OUTPUT); digitalWrite(PIN_L2, HIGH);
  pinMode(PIN_GIRL,OUTPUT); digitalWrite(PIN_GIRL, LOW);
  pinMode(ETH_RST, OUTPUT); digitalWrite(ETH_RST, HIGH); // перезагрузка W5500 
  pinMode(ETH_INTN,INPUT); // прерывание W5500
  pinMode(PIN_DATCH1,INPUT); 
  pinMode(PIN_DATCH2,INPUT); 
  pinMode(PIN_DATCHZ,INPUT);
  pinMode(PIN_PER,INPUT_PULLUP);

/* Конец блока установки режимов пинов */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
  Ethernet.begin(mac, ip); // запуск сетевого модуля
  ntpInit(); // Запуск udp для приема времени
  //Активация внутреннего времени
  MsTimer2::set(1000, mytime); // прерывание каждую секунду 
  MsTimer2::start();
  
  bme.begin(); // запуск датчика температура/влажность/давление
  lightMeter.Begin(Addr_LOW, Continuous_H); // запуск датчика интенсивности света

  day_nf();
  
  if (Mqtt_Update_flag_len > 32) Mqtt_Update_flag_len = 32; // защита переменной Mqtt_Update_flag от переполнения
  client.setServer(ipMQTT, 1883);
  client.setCallback(callback);
  delay(1500);
  B_TRUE(booleans, con_mqtt);
  
}
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
void loop() {
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Начало блока работы с временем */
  if (RTC.read(tm)) {
    if (lsec != tm.Second) { //каждую секунду и при запуске
        lsec = tm.Second; 
        secundesF();
    }
    if (lmin != tm.Minute) { //каждую минуту и при запуске
      lmin = tm.Minute; 
      if (tm.Year < 47) { 
        time_t t = getNtpTime(); if (t != 0) RTC.set(t);
      } 
      minutesF();
    }
    if (lhour != tm.Hour) { // каждый час и при запуске
      lhour = tm.Hour;
      hoursF();
    }
    if (lday != tm.Day) { //каждый день и при запуске
      lday = tm.Day;
      time_t t = getNtpTime(); if (t != 0) RTC.set(t); //синхронизация времени модуля с NTP сервером 
      
    }
    if (lmonth != tm.Month) {
      lmonth = tm.Month;

    }
 } else {
    if (my_s != lmy_s) { // каждую секунду
    lmy_s = my_s;
    secundesF();
  }
  if (my_m != lmy_m) { // каждую минуту
    lmy_m = my_m; 
    minutesF();
  }
  if (my_h != lmy_h) { // каждый час
     lmy_h = my_h;
     hoursF();
  }
 } 
 /* Конец блока работы со временем */
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Место для кода "условий" и др.*/
  // лампы
  if (B_READ(booleans, day_n) && !B_READ(booleans, lday_n)) { // отключение лампы навес и туалет на рассвете
    digitalWrite(PIN_L1, HIGH); B_FALSE(booleans,reg_l1_d1); l1_count = 0;
    digitalWrite(PIN_L2, HIGH); B_FALSE(booleans,reg_l2_d2); l2_count = 0;} 
  if (!B_READ(booleans, day_n) && !B_READ(booleans, day_nus) && !B_READ(booleans, day_nvs) && digitalRead(PIN_DATCH1)) { //включение света под навесом на 4+ минуты по датчику ночью.
    l1_count = 6; digitalWrite(PIN_L1, LOW);}
  if (!B_READ(booleans, day_n) && !B_READ(booleans, day_nus)) { //включение света у туалета на 5+ минуты по датчику ночью и от выключателя.
    if (digitalRead(PIN_DATCH2)) {l2_count = 7; digitalWrite(PIN_L2, LOW);}
    if (!digitalRead(PIN_PER)) {l2_count=0; digitalWrite(PIN_L2, LOW);}
    if (digitalRead(PIN_PER) != B_READ(booleans, lper)) {
      if (digitalRead(PIN_PER) && !B_READ(booleans, lper)) {l2_count=0; digitalWrite(PIN_L2, HIGH);}
      B_RAVNO(booleans, lper, digitalRead(PIN_PER));
    }
  } 
  //гирлянда
  if (!B_READ(booleans, day_n) && !B_READ(booleans, day_nus) && !B_READ(booleans, day_nvs) && B_READ(booleans,girl_activ)) //включение гирлянды ночью по активации
    digitalWrite(PIN_GIRL, HIGH); else digitalWrite(PIN_GIRL, LOW);

   if (!B_READ(booleans, day_n)) { // только ночью    
    if (digitalRead(PIN_DATCH1) != B_READ(Mqtt_Data1,mqtt_d1)) {B_TRUE(Mqtt_Update_flag,mqtt_d1_f); B_RAVNO(Mqtt_Data1,mqtt_d1,digitalRead(PIN_DATCH1));}
    if (digitalRead(PIN_DATCH2) != B_READ(Mqtt_Data1,mqtt_d2)) {B_TRUE(Mqtt_Update_flag,mqtt_d2_f); B_RAVNO(Mqtt_Data1,mqtt_d2,digitalRead(PIN_DATCH2));}
  }
    if (digitalRead(PIN_DATCHZ) != B_READ(Mqtt_Data1,mqtt_d3)) {B_TRUE(Mqtt_Update_flag,mqtt_d3_f); B_RAVNO(Mqtt_Data1,mqtt_d3,digitalRead(PIN_DATCHZ));}
    if (digitalRead(PIN_PER) != B_READ(Mqtt_Data1,mqtt_p)) {B_TRUE(Mqtt_Update_flag,mqtt_p_f); B_RAVNO(Mqtt_Data1,mqtt_p,digitalRead(PIN_PER));}
    if (digitalRead(PIN_L1) != B_READ(Mqtt_Data1,mqtt_l2)) {B_TRUE(Mqtt_Update_flag,mqtt_l2_f); B_RAVNO(Mqtt_Data1,mqtt_l2,digitalRead(PIN_L1));}
    if (digitalRead(PIN_L2) != B_READ(Mqtt_Data1,mqtt_l3)) {B_TRUE(Mqtt_Update_flag,mqtt_l3_f); B_RAVNO(Mqtt_Data1,mqtt_l3,digitalRead(PIN_L2));}
    if (digitalRead(PIN_GIRL) != B_READ(Mqtt_Data1,mqtt_g)) {B_TRUE(Mqtt_Update_flag,mqtt_g_f); B_RAVNO(Mqtt_Data1,mqtt_g,digitalRead(PIN_GIRL));} 

  if (B_READ(booleans, day_n) != B_READ(booleans, lday_n)) B_RAVNO(booleans, lday_n, B_READ(booleans, day_n));
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
/* Блок отправки и приёма MQTT*/ 
  if (B_READ(booleans, con_mqtt)) { 
    if (!client.connected()) { //проверка соединения с брокером MQTT
      B_FALSE(booleans, con_mqtt);
      if (client.connect("dvor")) {B_TRUE(booleans, con_mqtt); client.subscribe("i/a/#"); client.subscribe("i/d/#");}
    } else { //получение и отправка MQTT топиков
      client.loop();
      mqtt_publish_changes();
    }
  }
/* Конец блока отправки и приёма MQTT*/  
/*---------------------------------------------------------------------------------------------------------------------------------------------------*/
  delay(100); // задержка от "дребезга".
}

//Восход +294 минут
const byte vosa[12][31] PROGMEM ={{217,217,216,216,216,216,216,216,215,215,214,214,213,213,212,212,211,210,210,209,208,207,206,205,204,203,202,201,200,199,198},
                  {197,195,194,193,191,190,189,187,186,184,183,181,180,178,177,175,173,172,170,168,167,165,163,162,160,158,156,154,153},
                  {151,149,147,145,143,141,140,138,136,134,132,130,128,126,124,122,120,118,116,114,113,111,109,107,105,103,101,99,97,95,93},
                  {91,89,87,85,83,81,80,78,76,74,72,70,68,67,65,63,61,59,58,56,54,52,51,49,47,46,44,43,41,39},
                  {38,36,35,33,32,30,29,28,26,25,24,22,21,20,19,18,17,16,14,13,12,12,11,10,9,8,7,7,6,5,5},
                  {4,4,3,3,2,2,2,1,1,1,1,1,0,0,0,0,1,1,1,1,1,2,2,2,3,3,3,4,4,5},
                  {6,6,7,8,8,9,10,11,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,27,28,29,30,31,32,33,35},
                  {36,37,38,40,41,42,43,44,46,47,48,49,51,52,53,55,56,57,58,60,61,62,63,65,66,67,68,70,71,72,74},
                  {75,76,77,79,80,81,82,84,85,86,87,89,90,91,92,94,95,96,98,99,100,101,103,104,105,107,108,109,110,112},
                  {113,114,116,117,118,120,121,122,124,125,126,128,129,130,132,133,135,136,137,139,140,142,143,144,146,147,149,150,152,153,154},
                  {156,157,159,160,162,163,165,166,167,169,170,172,173,175,176,177,179,180,182,183,184,186,187,188,190,191,192,193,195,196},
                  {197,198,199,200,201,202,203,204,205,206,207,208,209,210,210,211,212,212,213,213,214,214,215,215,215,216,216,216,216,216,217}};
//Закат +1021 минут
const byte zaka[12][31] PROGMEM ={{10,11,12,13,14,15,16,17,19,20,21,22,24,25,26,27,29,30,31,33,34,36,37,39,40,41,43,44,46,47,49},
                  {50,52,53,55,56,58,59,61,62,64,65,67,68,70,71,73,74,76,77,79,80,82,83,85,86,88,89,90,92},
                  {93,95,96,98,99,100,102,103,105,106,107,109,110,111,113,114,116,117,118,120,121,122,124,125,126,128,129,131,132,133,135},
                  {136,137,139,140,141,143,144,145,147,148,149,151,152,153,155,156,157,159,160,161,163,164,165,167,168,169,171,172,173,175},
                  {176,177,179,180,181,182,184,185,186,187,189,190,191,192,194,195,196,197,198,199,201,202,203,204,205,206,207,208,209,210,211},
                  {212,212,213,214,215,216,216,217,218,218,219,219,220,220,221,221,221,222,222,222,222,223,223,223,223,223,223,223,223,222},
                  {222,222,222,221,221,221,220,220,219,218,218,217,216,216,215,214,213,212,211,211,210,208,207,206,205,204,203,202,200,199,198},
                  {196,195,194,192,191,189,188,186,185,183,182,180,178,177,175,173,172,170,168,167,165,163,161,159,158,156,154,152,150,148,146},
                  {144,143,141,139,137,135,133,131,129,127,125,123,121,119,117,115,113,111,109,107,105,103,101,99,97,95,93,91,89,87},
                  {85,84,82,80,78,76,74,72,70,68,66,65,63,61,59,57,56,54,52,50,49,47,45,44,42,40,39,37,36,34,32},
                  {31,30,28,27,25,24,23,21,20,19,18,17,15,14,13,12,11,10,9,8,8,7,6,5,5,4,3,3,2,2},
                  {2,1,1,1,0,0,0,0,0,0,0,0,0,0,0,1,1,1,2,2,3,3,4,5,5,6,7,7,8,9,10}};

void day_nf() {
  if (con_net < 240) {
    tmElements_t t;
    if (RTC.read(t)) {
      vos = pgm_read_byte(&vosa[t.Month-1][t.Day-1])+294;
      zak = pgm_read_byte(zaka[t.Month-1][t.Day-1])+1021;
      minutes = int(t.Hour*60) + int(t.Minute);
    } else {
      vos=360; zak=1080;
      if (lux > 4) minutes=720; else if (lux < 1) minutes=0;
    }
  }
  // день или ночь
  if ((minutes < vos && minutes >=0) || (minutes > zak && minutes < 1440)) B_FALSE(booleans, day_n); else B_TRUE(booleans, day_n);
  // сумерки 
  if ((minutes >= (vos - 30)) && (minutes <= (vos + 30))) B_TRUE(booleans, day_nus); else B_FALSE(booleans, day_nus); //30 минут на сумерки
  if ((minutes >= (zak - 30)) && (minutes <= (zak + 30))) B_TRUE(booleans, day_nvs); else B_FALSE(booleans, day_nvs); //30 минут на сумерки 
}

//byte TIME_IP[] = {129, 6, 15, 30}; // time-c.nist.gov
//byte TIME_IP[] = {88, 147, 254, 235}; // ntp3.stratum2.ru
byte TIME_IP[] = {192, 168, 0, 1}; // Мой
unsigned int TIME_PORT = 123;
#define timeZone 4

IPAddress timeServer(TIME_IP);

EthernetUDP Udp; //udp объект для синхронизации времени.

#define NTP_PACKET_SIZE 48
byte packetBuffer[NTP_PACKET_SIZE];

void ntpInit() {
  Udp.begin(TIME_PORT);
}

time_t getNtpTime() {
  while (Udp.parsePacket() > 0) ; // discard any previously received packets
  sendNTPpacket(timeServer);
  uint32_t beginWait = millis();
  while (millis() - beginWait < 1500) {
    int size = Udp.parsePacket();
    if (size >= NTP_PACKET_SIZE) {
      Udp.read(packetBuffer, NTP_PACKET_SIZE);  // read packet into the buffer
      unsigned long secsSince1900;
      // convert four bytes starting at location 40 to a long integer
      secsSince1900 =  (unsigned long)packetBuffer[40] << 24;
      secsSince1900 |= (unsigned long)packetBuffer[41] << 16;
      secsSince1900 |= (unsigned long)packetBuffer[42] << 8;
      secsSince1900 |= (unsigned long)packetBuffer[43];
      setSyncInterval(3600);
      return secsSince1900 - 2208988800UL + timeZone * SECS_PER_HOUR;
      //Strtxt += String(secsSince1900 - 2208988800UL + timeZone * SECS_PER_HOUR);      
    }
  }
  setSyncInterval(18);
  return 0; // return 0 if unable to get the time
}

// send an NTP request to the time server at the given address
void sendNTPpacket(IPAddress &address) {
  // set all bytes in the buffer to 0
  memset(packetBuffer, 0, NTP_PACKET_SIZE);
  // Initialize values needed to form NTP request
  // (see URL above for details on the packets)
  packetBuffer[0] = 0b11100011;   // LI, Version, Mode
  packetBuffer[1] = 0;     // Stratum, or type of clock
  packetBuffer[2] = 6;     // Polling Interval
  packetBuffer[3] = 0xEC;  // Peer Clock Precision
  // 8 bytes of zero for Root Delay & Root Dispersion
  packetBuffer[12] = 49;
  packetBuffer[13] = 0x4E;
  packetBuffer[14] = 49;
  packetBuffer[15] = 52;
  // all NTP fields have been given values, now
  // you can send a packet requesting a timestamp:                 
  //for (byte i=0;i<16;i++) Strtxt += packetBuffer[i];
  Udp.beginPacket(address, 123); //NTP requests are to port 123
  Udp.write(packetBuffer, NTP_PACKET_SIZE);
  Udp.endPacket();
}

 

Morroc
Offline
Зарегистрирован: 24.10.2016

Что значит "что нибудь улучшить" ? Вы вообще о чем ? Что нибудь всегда можно улучшить вплоть до написания нового.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

"Улучшить" можно только при условии существования критерия, что лучше, а что хуже. 

Иначе - никак.

AndreyD
AndreyD аватар
Offline
Зарегистрирован: 07.10.2018

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

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Может быть.

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

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