/* Click and Press+Hold Test Sketch
By Jeff Saltzman
To keep input interfaces simple, I want to use a single button to:
1) click (fast press and release) for regular button use, and
2) press and hold to enter a configuration mode.
*/
#define ledPin1 9 // digital output pin for LED 1 indicator
#define ledPin2 8 // digital output pin for LED 2 indicator
#define debounce 20 // ms debounce period to prevent flickering when pressing or releasing the button
#define holdTime 1000 // ms hold period: how long to wait for press+hold event
const int buttonPin = 6;
// Button variables
int b = 0; // value read from button
int blast = 0; // buffered value of the button's previous state
long bdown; // time the button was pressed down
long bup; // time the button was released
boolean ignoreUp = false; // whether to ignore the button release because the click+hold was triggered
// LED variables
boolean ledVal1 = false; // state of LED 1
boolean ledVal2 = false; // state of LED 2
//=================================================
void setup() {
// Set button input pin
pinMode(buttonPin, INPUT);
digitalWrite(buttonPin, HIGH); // pull-up 20k
// Set LED output pins
pinMode(ledPin1, OUTPUT);
digitalWrite(ledPin1, ledVal1);
pinMode(ledPin2, OUTPUT);
digitalWrite(ledPin2, ledVal2);
}
//=================================================
void loop() {
checkButton();
}
//=================================================
// Events to trigger by click and press+hold
void checkButton() {
// Read the state of the button
b = digitalRead(buttonPin);
// Test for button pressed and store the down time
if (b == LOW && blast == HIGH && (millis() - bup) > long(debounce)) {
bdown = millis();
}
// Test for button release and store the up time
if (b == HIGH && blast == LOW && (millis() - bdown) > long(debounce)) {
if (ignoreUp == false) {
changeMode();
} else {
ignoreUp = false;
}
bup = millis();
}
// Test for button held down for longer than the hold time
if (b == LOW && (millis() - bdown) > long(holdTime)) {
discharge();
ignoreUp = true;
bdown = millis();
}
blast = b;
}
void changeMode() {
ledVal1 = !ledVal1;
digitalWrite(ledPin1, ledVal1);
}
void discharge() {
ledVal2 = !ledVal2;
digitalWrite(ledPin2, ledVal2);
}