#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <Encoder.h>
#include <Adafruit_NeoPixel.h>
#include <SD.h>
#include <SPI.h>
#define CLK_PIN 2
#define DT_PIN 3
#define SW_PIN 4
#define VOLTAGE_PIN 9 // PWM pin for analog output
#define LED_PIN 6 // Pin for WS2812 data signal
#define NUM_LEDS 16 // Number of LEDs in the ring
#define SD_CS_PIN 10 // Chip select pin for the SD card
Encoder myEnc(CLK_PIN, DT_PIN);
LiquidCrystal_I2C lcd(0x27, 16, 2);
Adafruit_NeoPixel strip(NUM_LEDS, LED_PIN, NEO_GRB + NEO_KHZ800);
volatile bool buttonPressed = false;
int voltageValue = 0;
File dataFile;
void handleButtonPress() {
buttonPressed = true;
}
void setup() {
// Initialize Serial for debugging
Serial.begin(9600);
// Initialize LCD
lcd.begin(16, 2);
lcd.backlight();
lcd.setCursor(0, 0);
lcd.print("Voltage Control");
// Initialize encoder
pinMode(SW_PIN, INPUT_PULLUP);
attachInterrupt(digitalPinToInterrupt(SW_PIN), handleButtonPress, FALLING);
// Initialize PWM pin
pinMode(VOLTAGE_PIN, OUTPUT);
// Initialize WS2812 LED ring
strip.begin();
strip.show(); // Initialize all pixels to 'off'
// Initialize SD card
if (!SD.begin(SD_CS_PIN)) {
lcd.setCursor(0, 1);
lcd.print("SD Init Failed!");
Serial.println("SD card initialization failed!");
while (1);
}
lcd.setCursor(0, 1);
lcd.print("SD Init Success");
Serial.println("SD card initialized successfully.");
}
void loop() {
// Read encoder value
long newValue = myEnc.read() / 1; // Adjust scaling if needed
if (newValue != voltageValue) {
voltageValue = newValue;
if (voltageValue < 0) voltageValue = 0;
if (voltageValue > 255) voltageValue = 255;
// Update PWM output
analogWrite(VOLTAGE_PIN, voltageValue);
// Update LCD display
lcd.setCursor(0, 1);
lcd.print("Voltage: ");
lcd.print(voltageValue * (5.0 / 255.0), 2);
lcd.print(" V ");
// Update WS2812 LED ring brightness
uint8_t brightness = map(voltageValue, 0, 255, 0, 255);
for (int i = 0; i < NUM_LEDS; i++) {
strip.setPixelColor(i, strip.Color(brightness, 0, 0)); // Red color with variable brightness
}
strip.show();
// Save voltage and time to SD card
dataFile = SD.open("datalog.txt", FILE_WRITE);
if (dataFile) {
dataFile.print("Time: ");
dataFile.print(millis() / 1000);
dataFile.print("s, Voltage: ");
dataFile.print(voltageValue * (5.0 / 255.0), 2);
dataFile.println(" V");
dataFile.close();
Serial.println("Data written to SD card.");
} else {
lcd.setCursor(0, 1);
lcd.print("SD Write Failed");
Serial.println("Failed to write to SD card.");
}
}
// Handle button press
if (buttonPressed) {
buttonPressed = false;
myEnc.write(0);
voltageValue = 0;
analogWrite(VOLTAGE_PIN, voltageValue);
lcd.setCursor(0, 1);
lcd.print("Voltage: 0.00 V ");
// Turn off WS2812 LED ring
for (int i = 0; i < NUM_LEDS; i++) {
strip.setPixelColor(i, strip.Color(0, 0, 0)); // Turn off all LEDs
}
strip.show();
}
}
FPS: 0
Power: 0.00W
Power: 0.00W