Arduino has a nice online reference. The documentation for attachInterrupt includes a short example for creating a circuit that toggles an LED on or off.
There are two interrupts on the Duemilanove, pin 2 and 3. Pin 2 is interrupt 0, pin 3 is interrupt 1. The example uses pin 2. When pin 2 transitions from high to low, or low to high the interrupt service routine is called. The example has the LED turn on when the button is pressed, and off when released.
/* The pin the LED is attached to. */ #define LED_PIN 13 /* The initial state of the LED */ volatile int state = LOW; void setup() { pinMode(LED_PIN, OUTPUT); attachInterrupt(0, blink, CHANGE); } void loop() { digitalWrite(LED_PIN, state); } void blink() { state = !state; }
But that's not what happened! After pressing the button several times the LED would be on when the button was released.
Insert video here
After double checking the wiring, and the project source several times I went looking for other interrupt examples. When I stumbled across my problem, which is the well known problem of bouncing. It turns out that physical switches give dirty signals. A switch will turn on and off very quickly many times for even a single action. Something an electrical engineer is well aware of, something I had no idea about.
So well known that Arduino even has a debouncing library.
I had some difficulties with getting the library to work; it's more my fault than anything else. Instead the interrupt service routine debounces.
#define BOUNCE_MIN 250 voidstatic unsigned long int last; unsigned long int now; now = millis(); if ((now - last) <= BOUNCE_MIN) { /* do nothing */ return; } last = now; state = !state; }
Which limits the frequency of state changes to 250ms.
It works!
No comments:
Post a Comment