#include // ----- Pin definitions ----- #define Hold1 0 #define Hold2 1 #define Hold3 2 #define Hold4 21 #define Hold5 22 #define Hold6 20 #define Battery_LED 17 #define NeoPixelPin 18 #define ButtonPin 19 // NEW: start button // ----- NeoPixel setup ----- #define NUMPIXELS 8 Adafruit_NeoPixel strip(NUMPIXELS, NeoPixelPin, NEO_GRB + NEO_KHZ800); // ----- Timing (in milliseconds) ----- const unsigned long workTimes[6] = { 10000, // Hold1 work time (10s) 10000, // Hold2 10000, // Hold3 10000, // Hold4 10000, // Hold5 10000 // Hold6 }; const unsigned long restTimes[6] = { 5000, // Hold1 rest time (5s) 5000, // Hold2 5000, // Hold3 5000, // Hold4 5000, // Hold5 5000 // Hold6 }; // Extra rest after button press (10 seconds) const unsigned long preStartRest = 10000; // Array of hold pins for easier looping const uint8_t holdPins[5] = {Hold1, Hold2, Hold3, Hold5, Hold6}; // ----- Helper functions ----- void allHoldsLow() { for (int i = 0; i < 6; i++) { digitalWrite(holdPins[i], LOW); } } void clearStrip() { for (int i = 0; i < NUMPIXELS; i++) { strip.setPixelColor(i, 0, 0, 0); // off } strip.show(); } void workPhase(unsigned long workTimeMs) { clearStrip(); if (workTimeMs < NUMPIXELS) workTimeMs = NUMPIXELS; // avoid 0 delays unsigned long stepDelay = workTimeMs / NUMPIXELS; // Fill bar one pixel at a time (green) for (int i = 0; i < NUMPIXELS; i++) { strip.setPixelColor(i, 0, 255, 0); // green strip.show(); delay(stepDelay); } // If any leftover time due to integer division, wait it out unsigned long usedTime = stepDelay * NUMPIXELS; if (workTimeMs > usedTime) { delay(workTimeMs - usedTime); } } void restPhase(unsigned long restTimeMs) { // All pixels red at start of rest for (int i = 0; i < NUMPIXELS; i++) { strip.setPixelColor(i, 255, 0, 0); // red } strip.show(); if (restTimeMs < NUMPIXELS) restTimeMs = NUMPIXELS; // avoid 0 delays unsigned long stepDelay = restTimeMs / NUMPIXELS; // Decrease bar one pixel at a time (turn off from the end) for (int i = NUMPIXELS - 1; i >= 0; i--) { strip.setPixelColor(i, 0, 0, 0); // off strip.show(); delay(stepDelay); if (i == 0) break; // avoid underflow } // Leftover time if any unsigned long usedTime = stepDelay * NUMPIXELS; if (restTimeMs > usedTime) { delay(restTimeMs - usedTime); } } void setup() { // Hold pins pinMode(Hold1, OUTPUT); pinMode(Hold2, OUTPUT); pinMode(Hold3, OUTPUT); pinMode(Hold4, OUTPUT); pinMode(Hold5, OUTPUT); pinMode(Hold6, OUTPUT); // Battery LED always on pinMode(Battery_LED, OUTPUT); digitalWrite(Battery_LED, HIGH); // Button input (using internal pull-up, active LOW) pinMode(ButtonPin, INPUT_PULLUP); // NeoPixel init strip.begin(); strip.setBrightness(80); // adjust 0–255 if you want brighter/dimmer clearStrip(); // Make sure holds are off at start allHoldsLow(); } void loop() { // ----- WAIT FOR BUTTON PRESS ----- allHoldsLow(); clearStrip(); // Wait until button is pressed (active LOW) while (digitalRead(ButtonPin) == HIGH) { //idle; //everything off except battery LED delay(10); } // Simple debounce delay(50); //Wait for button release while (digitalRead(ButtonPin) == LOW) { delay(10); } // ----- 10 SECOND REST BEFORE STARTING SEQUENCE ----- restPhase(preStartRest); // reuses the red-shrinking bar as the 10s rest // ----- RUN FULL HOLD SEQUENCE ONCE ----- for (int h = 0; h < 6; h++) { allHoldsLow(); digitalWrite(holdPins[h], HIGH); // activate current hold // Work phase: bar fills up workPhase(workTimes[h]); // Turn this hold off before moving to next digitalWrite(holdPins[h], LOW); // Rest phase: bar red then decreases restPhase(restTimes[h]); } // After this, loop() restarts, goes back to waiting for the button }