Last active
July 25, 2016 18:51
-
-
Save daniel-packard/8be666f9e67cb37b524a3131861a7673 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// pseudo-ish code for the simple on/off state machine | |
// define all possible states | |
enum State { | |
ON, | |
OFF | |
}; | |
// define all possible transitions (including NONE) | |
enum Transition { | |
STARTED_PEDALING, | |
STOPPED_PEDALING, | |
NONE | |
}; | |
// track current state, starting in the OFF state | |
State currentState = OFF; | |
// to detect transitions, we need to know if we ARE pedaling and if we WERE pedaling | |
boolean isPedaling = false; | |
boolean wasPedaling = false; | |
// function to detect transitions based on changes in pedaling state | |
Transition getTransition(boolean isPedaling, boolean wasPedaling) { | |
// if the two states are equal, there was no transition ==> return NONE; | |
if(isPedaling == wasPedaling) | |
return NONE; | |
// if the two states are _NOT_ equal, and we are currently pedaling ==> STARTED_PEDALING | |
if(isPedaling) | |
return STARTED_PEDALING; | |
// otherwise | |
return STOPPED_PEDALING; | |
} | |
void loop() { | |
// capture previous pedaling state | |
wasPedaling = isPedaling; | |
// update the current pedaling state | |
isPedaling = ( digitalRead(magSensor) == HIGH ); | |
Transition transition = getTransition(isPedaling, wasPedaling); | |
// initalize the _new_ state if there was a transition | |
switch(transition) { | |
case STARTED_PEDALING: | |
currentState = ON; | |
TurnEverythingOn(); // void function defined elsewhere | |
case STOPPED_PEDALING: | |
currentState = OFF; | |
TurnEverythingOff(); // void function defined elsewhere | |
case NONE: | |
// no transition ==> do nothing | |
break; | |
case default: | |
break; | |
} | |
// do anything required by the current state | |
switch(currentState) { | |
case ON: | |
updateLights(); // void function defined elsewhere | |
updateMusic(); // void function defined elsewhere | |
break; | |
case OFF: | |
// everything should have been turned off in the transition | |
// ==> we don't need to do anything here | |
break; | |
case default: | |
break; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// pseudo-ish code for the state machine with "wind down period" | |
// define all possible states | |
enum State { | |
ON, | |
OFF, | |
WINDING_DOWN | |
}; | |
// define all possible transitions (including NONE) | |
enum Transition { | |
START_PEDALING, | |
STOP_PEDALING, | |
FINISH_WINDING_DOWN, | |
NONE | |
}; | |
// track current state, starting in the OFF state | |
State currentState = OFF; | |
// to detect transitions, now we need to know: | |
// * if we ARE pedaling | |
boolean isPedaling = false; | |
// * if we WERE pedaling | |
boolean wasPedaling = false; | |
// * AND what the targetWindDownTime | |
int targetWindDownTime = 0; | |
// function to detect transitions based on changes in pedaling state or reaching the target windDownTime | |
Transition getTransition(boolean isPedaling, boolean wasPedaling, int targetWindDownTime) { | |
// if winding down, check for winding down finished | |
if(currentState == WINDING_DOWN) { | |
if(targetWindDownTime > millis(); | |
return NONE; // still winding down, so no transition | |
else | |
return WINDING_DOWN_FINISHED; | |
} | |
// else, check for changes in pedaling | |
// if the two pedaling states are equal, there was no pedaling transition ==> return NONE; | |
if(isPedaling == wasPedaling) | |
return NONE; | |
// if the two states are _NOT_ equal, and we are currently pedaling | |
if(isPedaling) | |
return STARTED_PEDALING; | |
// otherwise | |
return STOPPED_PEDALING; | |
} | |
void loop() { | |
// capture previous pedaling state | |
wasPedaling = isPedaling; | |
// update the current pedaling state | |
isPedaling = ( digitalRead(magSensor) == HIGH ); | |
Transition transition = getTransition(isPedaling, wasPedaling, targetWindDownTime); | |
// initalize the _new_ state if there was a state transition | |
switch(transition) { | |
case STARTED_PEDALING: | |
currentState = ON; | |
TurnEverythingOn(); // void function defined elsewhere | |
// stopping pedaling now transitions into WINDING_DOWN state (instead of OFF) | |
case STOPPED_PEDALING: | |
currentState = WINDING_DOWN; | |
targetWindDownTime = millis() + 5000; | |
// when winding down finished, transition to OFF state | |
case WINDING_DOWN_FINISHED: | |
currentState = OFF; | |
TurnEverythingOff(); // void function defined elsewhere | |
case NONE: | |
// no transition ==> do nothing | |
break; | |
case default: | |
break; | |
} | |
// do anything required by the current state | |
switch(currentState) { | |
case ON: | |
updateLights(); // void function defined elsewhere | |
updateMusic(); // void function defined elsewhere | |
break; | |
case OFF: | |
// everything should have been turned off in the transition | |
// ==> we don't need to do anything here | |
break; | |
case WINDING_DOWN: | |
// need to slowly dim lights? | |
// target end time was set in the transition, so nothing else to do here | |
break; | |
case default: | |
break; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment