Skip to content

Arduino: A new & improved Button library with some handy features

2012 August 2
by Tedb0t

By Ted Hayes, from code originally by Alexander Brevig & Tom Igoe

The Arduino Button library (Github Repo) makes it easy to do some very common but rather tedious tasks. Usually when you interact with a button (such as a momentary switch), you mainly want to detect the state change, not just the current state. You have to do something like:

int lastState = 0;
void loop(){
    int currentState = digitalRead(11);
    if(currentState != lastState){
        // do something
    }
    lastState = currentState;
}

It’s not hard, just tedious. This new and improved Button library makes this much simpler but adds so much more. Now you can do it this way:

Button button = Button(12);

void onPress(Button& b){
	Serial.print("onPress: ");
	Serial.println(b.pin);
	// will print out "onPress: 12"
}

void setup(){
  Serial.begin(9600);
  // Assign callback function
  button.pressHandler(onPress);
}

void loop(){
  // update the buttons' internals
  button.process();
}

Features

  • Object-oriented design
    Button myButton(11);
  • Automatic pull-up setting
    Button myButton(11, BUTTON_PULLUP_INTERNAL);
  • Simplified state-change detection:
    if(button.isPressed()) ...
  • Callback model
    button.pressHandler(onPress)
  • Built-in debouncing
    // Sets 50ms debounce duration
    Button button = Button(12, BUTTON_PULLUP_INTERNAL, true, 50);

Installing

To install, download the library, extract it to ~/Documents/Arduino/libraries and rename the folder “Button.” (Github generates a different name for the zip link.) Restart Arduino if it was already open.

I hope you find this useful! Please report any bugs using the Github issue tracker.

Related Posts:


3 Responses leave one →
  1. Ozan permalink
    September 11, 2012

    Thank you. It’s very useful.

  2. dinosaurGloop permalink
    October 11, 2013

    WOW! This is amazing. I’ve been searching for a button library with this level of ability and had given up to begin creating my own. I did one more search and found this— SoGOOD! thanks a bunch!

  3. TheRealGN permalink
    December 29, 2013

    Hey there, first off, thanks. I do have a couple comments/suggestions based on my particular use case. I am making a device that has a single button which will serve two purposes, first to change modes, switching between speed, time, and temperature. Second, on long press it will go into a time setting mode.

    One thing I noticed was that if I set both an click and a hold handler, I would get the click handler on the release of a hold. So for my use case anyway, I didn’t really want that and I changed the code by adding a test for triggerHoldEvent like this:

    else //the state changed to RELEASED
    {
    if ( !triggeredHoldEvent ) {
    if ( cb_onRelease ) { cb_onRelease( *this ); }
    if ( cb_onClick ) { cb_onClick( *this ); }
    }
    //reset states (for timing and for event triggering)
    pressedStartTime = -1;
    }
    I am curious if there is some use case where you want the click and the hold?
    Second, I mistakenly forgot to add a holdTime in my call to holdHandler(…) and then I would immediately get a call to the hold callback. I removed the default param so that I wouldn’t make the mistake again. As to the usefulness of a 0 for the hold time, I am not seeing one, and I would think that someone that wants that would use the press/release callbacks instead. Again, there could very well be a use case I am not seeing.
    Thanks again for sharing this.
    Regards, Guy

Leave a Reply

Note: You can use basic XHTML in your comments. Your email address will never be published.

Subscribe to this comment feed via RSS