So I'm building a macro game controller, my intent is that I push a button and the Arduino will run through a macro sequence, ideally I'd like to be able to push the button a 2nd time to immediately stop the macro even if it hasn't completed. pushing it a 3rd time would start the macro sequence back at the beginning again.
I've got the hardware side complete and confirmed working.
I wrote a small program that turns an LED on and off via an interrupt and then I wrote another one that runs through my sequence as part of the main loop, both of those worked great (and confirmed that my hardware is setup properly) but I'm having problems now that I'm trying to combine them.
Initially when I tried running my macro sequence via an interrupt it would just skip over the calls to "delay" so I swapped that out for a manual calculation of delay using millis() but I can't seem to get that working and I don't know why. I would appreciate any help or advice.
Here is my sketch:
/*
SNES Controller Test
presses each of the buttons on the controller when the go button is pushed
should also stop the sequence if the go button is pushed a second time
*/
//set names for the output pins
int A = 4;
int B = 0;
int X = 1;
int Y = 2;
int R = 12;
int L = 7;
int Select = 13;
int Up = 11;
int Down = 10;
int Left = 9;
int Right = 8;
int Go = 1; //interrupt 1 pin #3
volatile int state = HIGH; // The go button state toggle
unsigned long lastInterruptTime = 0; //set the interrupt counter
// the setup routine runs once when you press reset:
void setup() {
// initialize the digital pins as an output.
pinMode(A, OUTPUT);
pinMode(B, OUTPUT);
pinMode(X, OUTPUT);
pinMode(Y, OUTPUT);
pinMode(L, OUTPUT);
pinMode(R, OUTPUT);
pinMode(Select, OUTPUT);
pinMode(Up, OUTPUT);
pinMode(Down, OUTPUT);
pinMode(Left, OUTPUT);
pinMode(Right, OUTPUT);
//setup interrupt
attachInterrupt(Go, buttonPushed, LOW);
//make sure everything is in the starting state that we want
allClear();
}
//sets all outputs to off (high)
void allClear(){
digitalWrite(Up, HIGH);
digitalWrite(Down, HIGH);
digitalWrite(Left, HIGH);
digitalWrite(Right, HIGH);
digitalWrite(A, HIGH);
digitalWrite(B, HIGH);
digitalWrite(X, HIGH);
digitalWrite(Y, HIGH);
digitalWrite(L, HIGH);
digitalWrite(R, HIGH);
digitalWrite(Select, HIGH);
}
// the loop routine runs over and over again forever:
void loop() {
wait();
}
// the interrupt routine run with the go button is pushed
void buttonPushed(){
unsigned long interruptTime = millis(); //check the interrupt time
// If interrupts come faster than 50ms, assume it's a bounce and ignore
if (interruptTime - lastInterruptTime > 50){
state = !state; //change state
if (state){
doStuff(); //run the sequence
} else {
allClear(); //clear the outputs
}
lastInterruptTime = interruptTime; //set the last interrupt time
}
}
// my non "delay" delay routine
void myDelay(int interval){
unsigned long previousMillis = millis(); //get the start time
unsigned long currentMillis = millis(); //get the current time
while (previousMillis + interval < currentMillis){ //loop until the start time plus the desired delay is reached
currentMillis = millis(); //get the current time
}
}
void wait(){
myDelay(1000); // wait for 1 second
}
// the output sequence routine
void doStuff(){
digitalWrite(Up, LOW);
myDelay(1000);
digitalWrite(Up, HIGH);
digitalWrite(Down, LOW);
myDelay(1000);
digitalWrite(Down, HIGH);
digitalWrite(Left, LOW);
myDelay(1000);
digitalWrite(Left, HIGH);
digitalWrite(Right, LOW);
myDelay(1000);
digitalWrite(Right, HIGH);
digitalWrite(A, LOW);
myDelay(1000);
digitalWrite(A, HIGH);
digitalWrite(B, LOW);
myDelay(1000);
digitalWrite(B, HIGH);
digitalWrite(X, LOW);
myDelay(1000);
digitalWrite(X, HIGH);
digitalWrite(Y, LOW);
myDelay(1000);
digitalWrite(Y, HIGH);
digitalWrite(L, LOW);
myDelay(1000);
digitalWrite(L, HIGH);
digitalWrite(R, LOW);
myDelay(1000);
digitalWrite(R, HIGH);
digitalWrite(Select, LOW);
myDelay(1000);
digitalWrite(Select, HIGH);
}