code 1 (works, very basic). D1 Mini v4 with RED LED shield
// light show runs dim white when power on, button pushed once for 10 min each color and ends on bright white
//#include <ArduinoWiFiServer.h>
//#include <BearSSLHelpers.h>
//#include <CertStoreBearSSL.h>
//#include <ESP8266WiFi.h>
//#include <ESP8266WiFiAP.h>
//#include <ESP8266WiFiGeneric.h>
//#include <ESP8266WiFiGratuitous.h>
//#include <ESP8266WiFiMulti.h>
//#include <ESP8266WiFiScan.h>
//#include <ESP8266WiFiSTA.h>
//#include <ESP8266WiFiType.h>
//#include <WiFiClient.h>
//#include <WiFiClientSecure.h>
//#include <WiFiClientSecureBearSSL.h>
//#include <WiFiServer.h>
//#include <WiFiServerSecure.h>
//#include <WiFiServerSecureBearSSL.h>
//#include <WiFiUdp.h>
#include <Adafruit_NeoPixel.h>
#define BUTTON_PIN 16
#define PIXEL_PIN D4
#define PIXEL_COUNT 7
// When we setup the NeoPixel library, we tell it how many pixels, and which pin to use to send signals.
// Note that for older NeoPixel strips you might need to change the third parameter--see the strandtest
// example for more information on possible values.
Adafruit_NeoPixel strip = Adafruit_NeoPixel(PIXEL_COUNT, PIXEL_PIN, NEO_GRB + NEO_KHZ800);
boolean oldState = HIGH;
int mode = 0; // Currently-active animation mode, 0-9
void setup() {
// WiFi.mode(WIFI_OFF);
pinMode(BUTTON_PIN, INPUT_PULLUP);
strip.begin(); // Initialize NeoPixel strip object (REQUIRED)
strip.show(); // Initialize all pixels to 'off'
}
// Fill strip pixels one after another with a color. Strip is NOT cleared
// first; anything there will be covered pixel by pixel. Pass in color
// (as a single 'packed' 32-bit value, which you can get by calling
// strip.Color(red, green, blue) as shown in the loop() function above),
// and a delay time (in milliseconds) between pixels.
void colorWipe(uint32_t color, int wait) {
for (int i = 0; i < strip.numPixels(); i++) { // For each pixel in strip...
strip.setPixelColor(i, color); // Set pixel's color (in RAM)
strip.show(); // Update strip to match
delay(wait); // Pause for a moment
}
}
void loop() {
// Get current button state.
boolean newState = digitalRead(BUTTON_PIN);
// Check if state changed from high to low (button press).
if ((newState == LOW) && (oldState == HIGH)) {
// Short delay to debounce button.
delay(20);
// Check if button is still low after debounce.
newState = digitalRead(BUTTON_PIN);
if (newState == LOW) { // Yes, still low
colorWipe(strip.Color(255, 0, 0), 0); // Red
delay(600000) ;
colorWipe(strip.Color(255, 150, 0), 150); // Yellow
delay(600000) ;
colorWipe(strip.Color(0, 255, 0), 150); // Green
delay(600000) ;
colorWipe(strip.Color(0, 0, 255), 150); // Blue
delay(600000) ;
colorWipe(strip.Color(180, 0, 255), 150); // Purple
delay(600000) ;
strip.clear();
colorWipe(strip.Color(255, 255, 255), 0); // White
delay(0) ;
}
// Set the last-read button state to the old state.
oldState = newState;
}
}
Code 2 (Works when written for an Uno and does with a breadboard, but not when put on the D1 Mini v4 with RED LED shield). [On a seperate note, I'm looking for a way to make this code waaayyy less complex. It currently feels like it's way more complex than it needs to be and I'd also like to be able to easily change the colors and delay times much easier.]
// State Machine x 2 controlling 1 Neopixel unit with different patterns and working Abort
// D1 mini
#include <Adafruit_NeoPixel.h>
#define PIXEL_PIN D4
#define PIXEL_COUNT 7
#define BUTTON_PIN 16
#define BUTTON_PIN2 5
// When we setup the NeoPixel library, we tell it how many pixels, and which pin to use to send signals.
// Note that for older NeoPixel strips you might need to change the third parameter--see the strandtest
// example for more information on possible values.
Adafruit_NeoPixel strip = Adafruit_NeoPixel(PIXEL_COUNT, PIXEL_PIN, NEO_GRB + NEO_KHZ800);
//#define microsInOneSecond 1000000UL
//Top level variables:
int DEBUG = 1; //set to 1 to enable serial monitor debugging info
//Switch 1 variables:
int state_s1 = 0;
int state_prev_s1 = 0;
int pin_s1 = 16; //button 1
const int BUTTON1 = 16;
int val_s1 = 0;
unsigned long t_s1 = 0;
unsigned long t_led1 = 0;
unsigned long t_0_s1 = 0;
unsigned long bounce_delay_s1 = 10;
//unsigned long bounce_delay_s1a = 10;
unsigned long hold_delay_s1 = 1000;
//Switch 2 variables:
int state_s2 = 0;
int state_prev_s2 = 0;
int pin_s2 = 5; //button 2
const int BUTTON2 = 5;
int val_s2 = 0;
unsigned long t_s2 = 0;
unsigned long t_led2 = 0;
unsigned long t_0_s2 = 0;
unsigned long bounce_delay_s2 = 20;
unsigned long hold_delay_s2 = 1000;
//NEOPIXEL variables
int state_led1 = 0;//actual state of the state machine
int state_prev_led1 = 0; //remember the prev state
int val_led1 = 0; //LED value (on or off)
int pin_led1 = D4;
unsigned long current_t_led1 = 0; //current time of the LED state
unsigned long previous_t_led1 = 0; //previous time of the LED state
unsigned long t_0_led1 = 0; //The time that we last passed through a state of interest
unsigned long t_0_led1a = 0;
unsigned long on_delay_led1 = 5000; //on time for the LED as it beeps
unsigned long off_delay_led1 = 5000; //off time for the LED as it beeps
int beep_count_led1 = 0; //number of times we've light up on this journey
int beep_number_led1 = 1; //number of times we should light before resetting
//RED LED variables
int state_led2 = 0;//actual state of the state machine
int state_prev_led2 = 0; //remember the prev state
//int pin_led2 = 11; //LED pin
int val_led2 = 0; //LED value (on or off)
unsigned long current_t_led2 = 0; //current time of the LED state
unsigned long previous_t_led2 = 0; //previous time of the LED state
unsigned long t_0_led2 = 0; //The time that we last passed through a state of interest
unsigned long on_delay_led2 = 5000; //on time for the LED as it beeps
unsigned long off_delay_led2 = 5000; //off time for the LED as it beeps
int beep_count_led2 = 0; //number of times we've light up on this journey
int beep_number_led2 = 1; //number of times we should light before resetting
void setup()
{
pinMode(16, INPUT_PULLUP);
pinMode(pin_led1, OUTPUT);
pinMode(10, INPUT_PULLUP);
//pinMode(pin_led2, OUTPUT);
//if DEBUG is turned on, initialize serial connection
if (DEBUG) {
Serial.begin(9600);
//Serial.begin(115200);
Serial.println("Debugging is ON");
}
Serial.println( F( "\n\n\n Loop Counter, free by GoForSmoke\n" ));
Serial.println( F( "This sketch counts times that loop has run each second and prints it." ));
strip.begin(); // Initialize NeoPixel strip object (REQUIRED)
strip.show(); // Initialize all pixels to 'off'
}
// Fill strip pixels one after another with a color. Strip is NOT cleared
// first; anything there will be covered pixel by pixel. Pass in color
// (as a single 'packed' 32-bit value, which you can get by calling
// strip.Color(red, green, blue) as shown in the loop() function above),
// and a delay time (in milliseconds) between pixels.
void colorWipe(uint32_t color, int wait) {
for (int i = 0; i < strip.numPixels(); i++) { // For each pixel in strip...
strip.setPixelColor(i, color); // Set pixel's color (in RAM)
strip.show(); // Update strip to match
delay(wait); // Pause for a moment
}
}
void colorClear(uint32_t color, int wait) {
for (int i = 0; i < strip.numPixels(); i++) { // For each pixel in strip...
strip.setPixelColor(i, color); // Set pixel's color (in RAM)
strip.show(); // Update strip to match
delay(wait); // Pause for a moment
}
}
//----------------State Machine S1 ---------------------
//-------------------------------------------------------
void StateMachine_s1() {
//almost every state needs these lines, so I'll put it outside the State Machine
val_s1 = digitalRead(pin_s1);
state_prev_s1 = state_s1;
//State Machine Section
switch (state_s1) {
case 0: //RESET
// catch all 'home base' for the state machine
{
colorWipe(strip.Color(0, 0, 0), 0);
}
delay(2000);
state_s1 = 1;
break;
case 1: //WAIT
//wait for the switch to go low
if (val_s1 == LOW) {
state_s1 = 2;
}
break;
case 2: //ARMING!
//Record the time and proceed to ARMED
t_0_s1 = millis();
state_s1 = 3;
break;
case 3: //ARMED
//Check to see if the proper delay has passed. If a bounce occurs then RESET
t_s1 = millis();
if (t_s1 - t_0_s1 > bounce_delay_s1) {
state_s1 = 4;
}
if (val_s1 == HIGH) {
state_s1 = 5;
}
break;
case 4: //DRAWN
//if switch goes HIGH then trigger. Also check timer for a "long press"
if (val_s1 == HIGH) {
state_s1 = 5;
}
break;
case 5: //TRIGGERED!
//reset the state machine, start the LED state machine
if (DEBUG) {
Serial.println("TRIGGERED switch 1!!");
}
state_s1 = 6;
break;
case 6: //LED ON
t_0_led1 = millis();
{
colorWipe(strip.Color(255, 0, 0), 0);
state_s1 = 7;
}
if (DEBUG) {
Serial.println("LED1 ON RED");
}
break;
// ------------ AFTER LED TURNED ON -----REPEATING BUTTON CHECK --------------------------------------------------------------------------
case 7: //check position of button
if (val_s1 == LOW) {
state_s1 = 8; //proceed to starting time for debounce to check if real button press
}
if (val_s1 == HIGH) {
state_s1 = 11; //if no pressed button, proceed to state 11
}
break;
case 8: //set switch start time
t_0_s1 = millis();
state_s1 = 9;
break;
case 9: //check bounce delay
t_s1 = millis();
if (t_s1 - t_0_s1 > bounce_delay_s1) {
state_s1 = 10; //state 10 will ABORT
}
if (val_s1 == HIGH) {
state_s1 = 8;
} //if no pressed button, proceed to state 11 timed LED off
break;
case 10: //ABORT OPTION
if (val_s1 == HIGH)
{
colorWipe(strip.Color(0, 0, 0), 0);
}
Serial.println("ABORT");
{
state_s1 = 0;
}
//go back to very beginning RESET
break;
// ------------------- TURN LED OFF ----------------------------
case 11: //Check button
if (val_s1 == LOW) {
state_s1 = 8; //proceed to starting time for debounce
}
if (val_s1 == HIGH) {
state_s1 = 12;
}
break;
// --------------- Turn LED to BLUE ---------------------------------
case 12: //Timed LED TO BLUE
t_led1 = millis();
if ((t_led1 - t_0_led1) > off_delay_led1) (
colorWipe(strip.Color(0, 0, 255), 150));
previous_t_led1 = t_led1;
{
state_s1 = 13;
}
if ((t_led1 - t_0_led1) <= off_delay_led1) {
state_s1 = 11;
}
break;
case 13: //announce LED OFF
Serial.println("LED is Blue");
{
state_s1 = 14;
}
break;
//------------------ TURN LED to GREEN --------------
case 14: //Check button
if (val_s1 == LOW) {
state_s1 = 8; //proceed to starting time for debounce
}
if (val_s1 == HIGH) {
state_s1 = 15;
}
break;
case 15: //TIMED LED ON to green
t_led1 = millis();
if ((t_led1 - previous_t_led1) > on_delay_led1)
{
colorWipe(strip.Color(0, 255, 0), 150);
state_s1 = 16;
}
if ((t_led1 - previous_t_led1) <= on_delay_led1) {
state_s1 = 14;
}
break;
case 16: //announce LED ON again
Serial.println("LED is Green");
state_s1 = 17;
break;
// --------------- Turn LED to PURPLE ------------------
case 17: //Check button
if (val_s1 == LOW) {
state_s1 = 8; //proceed to starting time for debounce
}
if (val_s1 == HIGH) {
state_s1 = 18;
}
break;
case 18: //TIMED LED ON to Purple
t_led1 = millis();
if ((t_led1 - previous_t_led1) > on_delay_led1)
{
colorWipe(strip.Color(127, 0, 255), 150);
state_s1 = 19;
}
if ((t_led1 - previous_t_led1) <= on_delay_led1) {
state_s1 = 17;
}
break;
case 19: //announce LED ON again
Serial.println("LED is PURPLE");
state_s1 = 0;
break;
}
}
void loop()
{
//Instruct all the state machines to proceed one step (sometimes called a "cycle)
StateMachine_s1();
/////////////// StateMachine_s2(); - removed this code due to length. its the same just a different switch number switch_s2
//Provide events that can force the state machines to change state
//I like to program interactions between state machines here in the top level loop
//if (state_s1 == 5) {state_led1 = 2;} //short press
if (DEBUG) {
//Make a note whenever a state machine changes state
//("Is the current state different from the previous? Yes? OK well let's tell the world the new state")
if ((state_prev_s1 != state_s1) | (state_prev_led1 != state_led1)) {
Serial.print("Switch 1 State: "); Serial.print(state_s1);
Serial.print('\n');
}
if ((state_prev_s2 != state_s2) | (state_prev_led2 != state_led2)) {
Serial.print("Switch 2 State: "); Serial.print(state_s2);
Serial.print('\n');
}
}
}
I'll see if I can draw a diagram. I'm not good at that.
thanks



