//
// Заика Денис Петрович БИСТ-22-ИТ-1
//
#include <LiquidCrystal_I2C.h> //библиотека для экрана
#include "iarduino_RTC.h"//библиотека для RTC
#include "Wire.h" // библиотека для работы с I2C
iarduino_RTC time(RTC_DS1307);//создание объекта time
float prev_lux = 0;//параметр для сохранения предыдущего значения люксов
long past1=0;//для реализации одного из таймеров
long past2=0;//для реализации одного из таймеров
long pastA=0;//для реализации таймера для кнопки (избегание дребезга)
int laststatA=0;//хранит предыдущее состояние кнопки
float lux = 0;//хранит значения лк освещенности
int flagL=0;//хранит состояние лампы 0 - не горит; 1 - горит
float analogValue=0;//принимает значение с аналоговых входов (зависит от выборанного датчика освещенности)
int previousAnalogValue1 = 0;//хранит предыдущие значения с аналогового выхода A0
int previousAnalogValue2 = 0;//хранит предыдущие значения с аналогового выхода A5
int Port = 0;//определяет как порт с какого датчика освещенности читает изменения лк
// LDR Characteristics
const float GAMMA = 0.7;
const float RL10 = 50;
LiquidCrystal_I2C lcd(0x27, 20, 4);//создаем объект lcd
void setup() {
delay(300);
time.begin();//запуск модуля часов
lcd.init();//инициализация дисплея
lcd.backlight();//включение дисплея
}
void loop() {
time.gettime();//получение текущего времени
if(millis()-past2>=50){//таймер, определяется, какой датчик пересекает человек (предполагается
// что датчики пересекаются поочередно или только один)
past2=millis();//сброc таймера
//получение текущих значений напряжения от датчиков с каждого аналогового порта
int currentAnalogValue1 = analogRead(A0);
int currentAnalogValue2= analogRead(A5);
//любое изменение напряжения на датчике определит порт (A0 или A5), который будет "прослушиваться" при расчетах
//если напряжение изменится на первом, то выбор аналогового порта A0
if (currentAnalogValue1 != previousAnalogValue1) {
analogValue = currentAnalogValue1;
Port = 0;
}
//если напряжение изменится на втором, то выбор аналогового порта A5
if (currentAnalogValue2 != previousAnalogValue2) {
analogValue = currentAnalogValue2;
Port = 5;
}
//сохранение предыдущих значений
previousAnalogValue1 = currentAnalogValue1;
previousAnalogValue2 = currentAnalogValue2;
}
//перевод напряжения в лк
float voltage = analogValue / 1024. * 5;
float resistance = 2000 * voltage / (1 - voltage / 5);
lux = pow(RL10 * 1e3 * pow(10, GAMMA) / resistance, (1 / GAMMA));
//срабатывание сигнализации
if (prev_lux >= 600 & lux < 600) {//при условии, что лк пошли на спад от 600 лк и ниже
long startTime = millis();//таймер, фиксация времени начала спада лк
while (lux > 200){//цикл, где считываются текущие значения лк
int analogValue = analogRead(Port);
float voltage = analogValue / 1024. * 5;
float resistance = 2000 * voltage / (1 - voltage / 5);
lux = pow(RL10 * 1e3 * pow(10, GAMMA) / resistance, (1 / GAMMA));
}
long fallTime = millis() - startTime;//при выходе из цикла, расчет общего времени спада лк от 600 до 200 лк
startTime = millis();//таймер фиксации времени начала роста лк от 200 до 600 лк
while (lux < 600){//цикл где считываются текущие значения лк
int analogValue = analogRead(Port);
float voltage = analogValue / 1024. * 5;
float resistance = 2000 * voltage / (1 - voltage / 5);
lux = pow(RL10 * 1e3 * pow(10, GAMMA) / resistance, (1 / GAMMA));
}
long riseTime = millis() - startTime;//при выходе из цикла расчет общего времени роста лк от 200 до 600
if (800000/(fallTime+riseTime)>=200){//проверка условия задачи (минимум 200 лк/c - резкое изменение освещенности )
flagL=1;//включение лампочки - сигнализации
lcd.setCursor(0,0);//установка курсора на экране
lcd.print(time.gettime("d/m, H:i:s"));//вывод на экран текущего времени и даты срабатывания сигнализации
}
}
prev_lux=lux;//сохранение предыдущего значения лк
if (flagL==1){// при условии - флаг активен - тогда реализуется мигание лампочки
if(millis()-past1>=500){// 1 раз в 500 мс, то есть 2 раза в сек (по условию)
past1=millis();
digitalWrite(11, HIGH);
delay(50);
digitalWrite(11,LOW);
}
}
else{
digitalWrite(11, LOW);
}
//отключение сигнализации (при этом время и дата срабатывания на экране сохраняется - по условию)
if (laststatA==0 & digitalRead(2))//нажали кнопку
{
laststatA = 1;//сменили состояние кнопки
}
long nowA = millis();//использование таймера с периодом 100
if (nowA - pastA >=100)
{
pastA = nowA;//сброс таймера
if (laststatA == 1 & !digitalRead(2))//отпустили кнопку
{
laststatA = 0;//сменили состояние кнопки - отпустили
flagL=0;//отпустил кнопку - флаг неактивен - лампочка погасла
}
}
}