#include <EEPROM.h> // Library for EEPROM usage
#include <Wire.h> // Library for I2C communication
#include <LiquidCrystal_I2C.h> // Library for LCD 2004 I2C
int CLK = 4; // Pin connected to the CLK of the rotary encoder
int DT = 3; // Pin connected to the DT of the rotary encoder
int SW = 2; // Pin connected to the SW of the rotary encoder
int RED_PIN = 5; // Pin number for the red LED
int GREEN_PIN = 6; // Pin number for the green LED
int BLUE_PIN = 9; // Pin number for the blue LED
int led_onoff = 1;
static int oldCLK = LOW; // Variable to store the value of the CLK pin
static int oldDT = LOW; // Variable to store the value of the DT pin
LiquidCrystal_I2C lcd(0x27, 20, 4); // Address: 0x3F or 0x27
int RED, GREEN, BLUE;
int INTERVAL, DURATION;
int mr, mg, mb, mi, md;
char buf[20];
int mode = 0; // 0=normal, 1=setup
int menu = 0; // 0=RED, 1=GREEN, 2=BLUE, 3=INTV, 4=DUR, 5=END
void setup() {
initsetting();
loadsetting();
lcd.init(); // Initialize LCD
lcd.backlight(); // Turn on backlight
pinMode(CLK, INPUT_PULLUP); // Set CLK as input with internal pull-up resistor
pinMode(DT, INPUT_PULLUP); // Set DT as input with internal pull-up resistor
pinMode(SW, INPUT_PULLUP); // Set SW as input with internal pull-up resistor
//attachInterrupt(digitalPinToInterrupt(SW), rotbutton, LOW);
attachInterrupt(digitalPinToInterrupt(DT), rotdial, CHANGE);
}
void loop() {
int currb = HIGH, lastb = HIGH;
if ((millis() / 100) % (INTERVAL + DURATION) < DURATION)
led_onoff = 1;
else
led_onoff = 0;
currb = digitalRead(SW);
if (mode == 1 && currb == LOW && lastb == HIGH) {
lcd.clear(); menu = menu + 1; delay(50);
}
if (mode == 0 && currb == LOW && lastb == HIGH) {
lcd.clear(); mode = 1; menu = 0; mr = RED; mg = GREEN; mb = BLUE; mi = INTERVAL; md = DURATION; delay(50);
}
lcdshow();
ledlight();
lastb = currb;
}
void ledlight() {
if (led_onoff == 1) {
analogWrite(RED_PIN, 255 - RED);
analogWrite(GREEN_PIN, 255 - GREEN);
analogWrite(BLUE_PIN, 255 - BLUE);
} else {
analogWrite(RED_PIN, 255);
analogWrite(GREEN_PIN, 255);
analogWrite(BLUE_PIN, 255);
}
}
void lcdshow() {
if (mode == 0) {
lcd.setCursor(0, 0);
sprintf(buf, "==RGB LED LIGHTING==");
lcd.print(buf);
lcd.setCursor(0, 1);
sprintf(buf, " R:%3d G:%3d B:%3d ", RED, GREEN, BLUE);
lcd.print(buf);
lcd.setCursor(0, 2);
sprintf(buf, " INTERVAL:%2d.%d(sec) ", INTERVAL / 10, INTERVAL % 10);
lcd.print(buf);
lcd.setCursor(0, 3);
sprintf(buf, " DURATION:%2d.%d(sec) ", DURATION / 10, DURATION % 10);
lcd.print(buf);
}
if (mode == 1) {
switch (menu) {
case 0:
lcd.setCursor(0, 0);
sprintf(buf, "<<<CHANGE SETTING>>>");
lcd.print(buf);
lcd.setCursor(0, 2);
sprintf(buf, " %3d", mr);
lcd.print(buf);
lcd.setCursor(0, 3);
sprintf(buf, " RED INTENSITY");
lcd.print(buf);
break;
case 1:
lcd.setCursor(0, 0);
sprintf(buf, "<<<CHANGE SETTING>>>");
lcd.print(buf);
lcd.setCursor(0, 2);
sprintf(buf, " %3d", mg);
lcd.print(buf);
lcd.setCursor(0, 3);
sprintf(buf, " GREEN INTENSITY");
lcd.print(buf);
break;
case 2:
lcd.setCursor(0, 0);
sprintf(buf, "<<<CHANGE SETTING>>>");
lcd.print(buf);
lcd.setCursor(0, 2);
sprintf(buf, " %3d", mb);
lcd.print(buf);
lcd.setCursor(0, 3);
sprintf(buf, " BLUE INTENSITY");
lcd.print(buf);
break;
case 3:
lcd.setCursor(0, 0);
sprintf(buf, "<<<CHANGE SETTING>>>");
lcd.print(buf);
lcd.setCursor(0, 2);
sprintf(buf, " %2d.%d", mi / 10, mi % 10);
lcd.print(buf);
lcd.setCursor(0, 3);
sprintf(buf, " BLINK INTERVAL");
lcd.print(buf);
break;
case 4:
lcd.setCursor(0, 0);
sprintf(buf, "<<<CHANGE SETTING>>>");
lcd.print(buf);
lcd.setCursor(0, 2);
sprintf(buf, " %2d.%d", md / 10, md % 10);
lcd.print(buf);
lcd.setCursor(0, 3);
sprintf(buf, " BLINK DURATION");
lcd.print(buf);
break;
case 5:
lcd.setCursor(0, 2);
sprintf(buf, "STORING SETTING .");
lcd.print(buf);
delay(500);
lcd.setCursor(0, 2);
sprintf(buf, "STORING SETTING ..");
lcd.print(buf);
delay(500);
lcd.setCursor(0, 2);
sprintf(buf, "STORING SETTING ...");
lcd.print(buf);
delay(500);
savesetting();
mode = 0;
break;
}
}
}
void loadsetting() {
RED = EEPROM.read(1);
GREEN = EEPROM.read(2);
BLUE = EEPROM.read(3);
INTERVAL = EEPROM.read(4);
DURATION = EEPROM.read(5);
}
void initsetting() {
EEPROM.update(1, 255);
EEPROM.update(2, 255);
EEPROM.update(3, 255);
EEPROM.update(4, 10);
EEPROM.update(5, 10);
}
void savesetting() {
RED = mr; EEPROM.update(1, RED);
GREEN = mg; EEPROM.update(2, GREEN);
BLUE = mb; EEPROM.update(3, BLUE);
INTERVAL = mi; EEPROM.update(4, INTERVAL);
DURATION = md; EEPROM.update(5, DURATION);
}
void rotdial() {
if (mode == 0) return;
int direct = 0; // Direction initialized to 0
int newCLK = digitalRead(CLK); // Variable to store the current CLK value
int newDT = digitalRead(DT); // Variable to store the current DT value
if (newCLK != oldCLK) { // CLK value has changed
if (oldCLK == LOW) { // Changed from LOW to HIGH
direct = -1 * (oldDT * 2 - 1); // Change direct value using DT
}
}
oldCLK = newCLK; // Update oldCLK
oldDT = newDT; // Update oldDT
switch (menu) {
case 0: mr += 5 * direct; if (mr > 255) mr = 0; if (mr < 0) mr = 255; break;
case 1: mg += 5 * direct; if (mg > 255) mg = 0; if (mg < 0) mg = 255; break;
case 2: mb += 5 * direct; if (mb > 255) mb = 0; if (mb < 0) mb = 255; break;
case 3: mi += direct; if (mi > 100) mi = 0; if (mi < 0) mi = 100; break;
case 4: md += direct; if (md > 100) md = 0; if (md < 0) md = 100; break;
}
}