For Arch or Xadow M0, use on-board button to provide multifunction.

Dependencies:   mbed

main.cpp

Committer:
yihui
Date:
2015-01-13
Revision:
0:0d08d0b3c7ed

File content as of revision 0:0d08d0b3c7ed:

// For Arch and Xadow M0, use on-board button for normal input function rather than reset function
// single click - LED1 on
// double click - LED2 on
// long click - LED1 and LED2 on, and then the board will restart
//
// Note: To enter ISP mode, press the button and then power on (power-on reset)

#include "mbed.h"
#include "pinmap.h"

#define BUTTON_DOWN  0

InterruptIn button(P0_1);       // on-board button of Arch or Xadow M0
BusOut leds(LED1, LED2);

uint8_t button_down_event = 0;

void button_callback()
{
    button_down_event = 1;      // set button down event flag
}

int button_detect()
{
    int t = 0;
    
    while (1) {
        if (button.read() != BUTTON_DOWN) {
            if (t < 30) {
                return 0;     // for anti shake
            } else {
                break;
            }
        }
        
        if (t > 3000) {        // More than 3 seconds
            return -1;          // long click
        }
        
        t++;
        wait_ms(1);
    }
    
    if (t > 4000) {             // More than 0.4 seconds
        return 1;               // single click
    }
    
    while (true) {
        if (button.read() == BUTTON_DOWN) {
            wait_ms(1);
            if (button.read() == BUTTON_DOWN) {
                return 2;      // double click
            }
            
            t += 10;
        }
        
        if (t > 400) {
            return 1;          // The interval of double click supposes to be less than 0.4 seconds, so it's single click
        }
        
        t++;
        wait_ms(1);
    }
}


int main() {
    // start 
    leds = 1;
    wait(0.2);
    leds = 3;
    wait(0.2);
    leds = 2;
    wait(0.2);
    leds = 0;
    
    pin_function(P0_0, 1);      // use RESET pin as 
    button.fall(button_callback);
    
    while(1) {
        if (button_down_event != 0) {
            int clicks = button_detect();
            if (clicks == 1) {
                leds = 0x01;
            } else if (clicks == 2) {
                leds = 0x02;
            } else if (clicks == -1) {  // long press
                leds = 0x03;
                while (button.read() == BUTTON_DOWN) { } // wait until button is released. note: remove this line to boot into ISP mode after reset
                NVIC_SystemReset();                      // reset
            }
            
            wait(1);
            leds = 0;
            
            button_down_event = 0;      // clear button down event flag
        }
        
        // sleep();
        // or do something else
    }
}