Hello,
I am learning the arduino language from a book by Simon Monk. I have installed the bounce2 library and tested his code show below and it works.
//bounce program using the bounce2 library
#include <Bounce2.h>
const int inputPin = 5;
const int ledPin = 13;
int ledValue = LOW;
Bounce bouncer = Bounce();
void setup()
{
pinMode (inputPin, INPUT_PULLUP);
pinMode (ledPin, OUTPUT);
bouncer.attach (inputPin);
}
void loop()
{
if (bouncer.update() && bouncer.read() == LOW)
{
ledValue = ! ledValue;
digitalWrite (ledPin, ledValue);
}
However, in the examples which come with the bounce library is the following code
/*
DESCRIPTION
====================
Simple example of the Bounce library that switches a LED when
a state change (from HIGH to LOW) is triggered (for example when a button is pressed).
Set BOUNCE_PIN to the pin attached to the input (a button for example).
Set LED_PIN to the pin attached to a LED.
*/
// WE WILL attach() THE Bounce INSTANCE TO THE FOLLOWING PIN IN setup()
#define BOUNCE_PIN 2
// DEFINE THE PIN FOR THE LED :
// 1) SOME BOARDS HAVE A DEFAULT LED (LED_BUILTIN)
#define LED_PIN LED_BUILTIN
// 2) OTHERWISE SET YOUR OWN PIN
// #define LED_PIN 13
// Include the Bounce2 library found here :
// https://github.com/thomasfredericks/Bounce2
#include <Bounce2.h>
// INSTANTIATE A Bounce OBJECT
Bounce bounce = Bounce();
// SET A VARIABLE TO STORE THE LED STATE
int ledState = LOW;
void setup() {
// BOUNCE SETUP
// SELECT ONE OF THE FOLLOWING :
// 1) IF YOUR INPUT HAS AN INTERNAL PULL-UP
bounce.attach( BOUNCE_PIN , INPUT_PULLUP ); // USE INTERNAL PULL-UP
// 2) IF YOUR INPUT USES AN EXTERNAL PULL-UP
//bounce.attach( BOUNCE_PIN, INPUT ); // USE EXTERNAL PULL-UP
// DEBOUNCE INTERVAL IN MILLISECONDS
bounce.interval(5); // interval in ms
// LED SETUP
pinMode(LED_PIN, OUTPUT);
digitalWrite(LED_PIN, ledState);
}
void loop() {
// Update the Bounce instance (YOU MUST DO THIS EVERY LOOP)
bounce.update();
// <Bounce>.changed() RETURNS true IF THE STATE CHANGED (FROM HIGH TO LOW OR LOW TO HIGH)
if ( bounce.changed() ) {
// THE STATE OF THE INPUT CHANGED
// GET THE STATE
int deboucedInput = bounce.read();
// IF THE CHANGED VALUE IS LOW
if ( deboucedInput == LOW ) {
ledState = !ledState; // SET ledState TO THE OPPOSITE OF ledState
digitalWrite(LED_PIN,ledState); // WRITE THE NEW ledState
}
}
}
Which uses an interval timer which I understand is not the same as using delay which I want to avoid. My main question is this, in the first program which does not appear to use interval, why so? is a default interval value used instead whenever it is not specified?
Also any thoughts on what is better for debouncing, using bounce2 library or the millis function methods.
They both have their places, and Bounce2 uses millis() methods behind the scenes.
Learning how to use millis() for timing is an important skill to gain, but once you have that, using Bounce2 to simplify your code or because you are feeling "lazy" is not a problem to worry about. The .rose() and .fell() methods are useful.
Bounce2 is a very solid library and I frequently use it.
+1 for @alto777 recommendation to get into the habit of reading library source code.
In general, using Libarys is like cooking with instant soups. A soup comes out of the pot, but if the soup doesn't taste good, you don't know why it doesn't taste good.
I have started using an anti-anti-delay() debounce that will have me banned works for me
define a button on an interrupt pin
define an interrupt service routine that sets a flag on the interrupt
if the flag is set (not a pressed button) use delay(x) to debounce residual button-press oscillations.
These steps allow a button to be pressed during blocking code (for(), while(), do()) without being lost to polling, as long as interrupts are not turned off. Once the blocking code is finished, the button-press will be acted upon. Like this:
volatile bool buttonFlag; // type volatile for interrupt handler
int buttonPin = 2; // interrupt pin INT0
.
.
void setup() {
.
.
attachInterrupt(digitalPinToInterrupt(buttonPin), buttonISR, FALLING); // INT#, ISR, TRIGGER
.
.
}
void loop() {
.
.
if (buttonFlag) { // button flag is returned from ISR
delay(150); // debounce
buttonFlag = 0; // reset ISR flag
.
.
}
int buttonISR() {
noInterrupts(); // disable interrupts while in the ISR
buttonFlag = 1; // set a flag indicating the button was pressed
interrupts(); // enable interrupts when leaving the ISR
}