//зададим исходные данные для счета millis()
uint32_t tmr1, tmr2, tmr3, tmr4;
uint32_t per1 = 3000;
uint32_t per2 = 500;
uint32_t per3 = 1500;
// инициализируем пины светодиода
const int RLED = 11;
const int YLED = 10;
const int GLED = 9;
// пин кнопки
const int BUT = 2;
boolean lastBUT = LOW; //переменная хранит предыдущее состояние кнопки
boolean currentBUT = LOW; //переменная хранит текущее состояние кнопки
int ledin = 0; //состояние светодиода (вкл, выкл)
//задаем флажки
boolean GLEDflag = false;
void setup()
{
pinMode(BUT, INPUT);
pinMode(RLED, OUTPUT);
pinMode(YLED, OUTPUT);
pinMode(GLED, OUTPUT);
}
/*
* Функция сглаживания дребезга
* принимает в качестве аргумента предыдущее состояние конпки
* и выдает фактическое
*/
boolean debounce(boolean last) //задаем функцию, которая принимает только логическую переменную boolean last (последнее состояние кнопки)
{
boolean current = digitalRead(BUT); //читаем конпку
if (last != current) //сравниваем состояние, если отличаются, то...
{
delay(10); //ждем 10 мс
current = digitalRead(BUT); //читаем кнопку еще раз
return current; //возвращаем состояние кнопки
}
}
void trLight(int mode)
{
if (mode == 1)
{
digitalWrite(GLED, HIGH);
if (millis() - tmr1 >= per1)
{
tmr1 = millis();
digitalWrite(GLED, LOW);
}
for (int i = 0; i < 4; i++)
{
if (millis() - tmr2 >= per2)
{
tmr2 = millis();
digitalWrite(GLED, GLEDflag);
GLEDflag =! GLEDflag;
}
}
digitalWrite(GLED, LOW);
digitalWrite(RLED, HIGH);
if (millis() - tmr3 >= per1)
{
tmr3 = millis();
digitalWrite(YLED, HIGH);
}
digitalWrite(YLED, HIGH);
if (millis() - tmr4 >= per3)
{
digitalWrite(RLED, LOW);
digitalWrite(YLED, LOW);
}
}
else
{
digitalWrite(RLED, LOW);
digitalWrite(YLED, LOW);
digitalWrite(GLED, LOW);
}
}
void loop()
{
currentBUT = debounce(lastBUT); //вызываем функцию антидребезга кнопки
if (lastBUT == LOW && currentBUT == HIGH)
{
ledin =! ledin;
}
lastBUT = currentBUT;
trLight(ledin);
}
// инициализируем пины светодиода
const int RLED = 11;
const int YLED = 10;
const int GLED = 9;
// пин кнопки
const int BUT = 2;
//режим работы светофора
int trmode = 0; //будет использоваться в switch case для переключения режима
uint32_t time0 = 5000; //время горения красного сигнала
uint32_t time1 = 1500; //время горения красного и желтого сигнала
uint32_t time2 = 3000; //время горения зеленого сигнала
uint32_t interval = time0; //присвоим по умолчанию интервал зеленого света
uint32_t prev = 0; //изначальное время, присвоим 0. Нужно для вычисления разницы
boolean lastBUT = LOW; //переменная хранит предыдущее состояние кнопки
boolean currentBUT = LOW; //переменная хранит текущее состояние кнопки
//для мигания зеленым светом
//boolean gFlag = false;
uint32_t timeblk = 500; //период мигания светодиодом
//int counter = 0;
int ledin = 1; //состояние светодиода (вкл, выкл)
void setup()
{
pinMode(BUT, INPUT);
pinMode(RLED, OUTPUT);
pinMode(YLED, OUTPUT);
pinMode(GLED, OUTPUT);
digitalWrite(RLED, HIGH); //красный по умолчанию
}
/*
* Функция сглаживания дребезга
* принимает в качестве аргумента предыдущее состояние конпки
* и выдает фактическое
*/
boolean debounce(boolean last) //задаем функцию, которая принимает только логическую переменную boolean last (последнее состояние кнопки)
{
boolean current = digitalRead(BUT); //читаем конпку
if (last != current) //сравниваем состояние, если отличаются, то...
{
delay(10); //ждем 10 мс
current = digitalRead(BUT); //читаем кнопку еще раз
return current; //возвращаем состояние кнопки
}
}
void trLight(int mode)
{
if (ledin == 1)
{
if (millis() - prev >= interval) //вычисляем разницу и сравниваем с заданным интервалом
{
prev = millis();
switch(trmode)
{
case 0: //выключаем зеленый, включаем красный
digitalWrite(GLED, LOW);
digitalWrite(RLED, HIGH);
interval = time0;
trmode = 1; //смотрим случай 1
break;
case 1: //подключаем желтый
digitalWrite(YLED, HIGH);
interval = time1;
trmode = 2; //смотрим случай 2
break;
case 2: //включаем зеленый
digitalWrite(YLED, LOW);
digitalWrite(RLED, LOW);
digitalWrite(GLED, HIGH);
interval = time2;
trmode = 3; //смотрим случай 3
break;
case 3: //гасим на время переменной timeblk
digitalWrite(GLED, LOW);
interval = timeblk;
trmode = 4;
break;
case 4: //включаем на время переменной timeblk
digitalWrite(GLED, HIGH);
interval = timeblk;
trmode = 5;
break;
case 5: //гасим на время переменной timeblk
digitalWrite(GLED, LOW);
interval = timeblk;
trmode = 6;
break;
case 6: //включаем на время переменной timeblk
digitalWrite(GLED, HIGH);
interval = timeblk;
trmode = 7;
break;
case 7: //включаем на время переменной timeblk
digitalWrite(GLED, LOW);
interval = timeblk;
trmode = 0;
break;
}
}
}
else
{
digitalWrite(RLED, LOW);
digitalWrite(GLED, LOW);
digitalWrite(YLED, LOW);
}
}
void loop()
{
currentBUT = debounce(lastBUT); //вызываем функцию антидребезга кнопки
if (lastBUT == LOW && currentBUT == HIGH)
{
ledin =! ledin;
}
lastBUT = currentBUT;
trLight(ledin);
}