Beware that this post is related to an SDK in maintenance mode
More Info: Consider nRF Connect SDK for new designs

Button Press detected twice when pushed once

Hi,

I'm using a custom board to record i2s data to a sd card. The recording starts and stops on a button press (Pin 25), which basically works. My problem is that the button press is always detected twice (once on pushing the button, once on release). The button is pulled to high by hardware, so I'm sensing when there is a transition to low. I'm using the app button handler library, nRF5 SDK 17.1.0 and Segger emStudio 5.42a.

Here are the related functions.

main()

int main(void) {
    uint32_t err_code;
    uint8_t sample_data;
    uint8_t response;
    bool detected_device = false;

    log_init();

    init_clock();

    bsp_board_init(BSP_INIT_LEDS);
    bsp_board_led_on(BSP_BOARD_LED_0);

    // init buttons
    timers_init();
    buttons_init();
    
    ...
}

init_clock()

void init_clock()
{
    NRF_CLOCK->LFCLKSRC            = (CLOCK_LFCLKSRC_SRC_Xtal << CLOCK_LFCLKSRC_SRC_Pos);
    NRF_CLOCK->EVENTS_LFCLKSTARTED = 0;
    NRF_CLOCK->TASKS_LFCLKSTART    = 1;
    while (NRF_CLOCK->EVENTS_LFCLKSTARTED == 0); // Wait for clock to start
}

buttons_init()

static void buttons_init(void)
{
    ret_code_t err_code;

    //The array must be static because a pointer to it will be saved in the button handler module.
    static app_button_cfg_t buttons[] =
    {
        {25, false, NRF_GPIO_PIN_PULLUP, button_event_handler}
    };

    err_code = app_button_init(buttons, ARRAY_SIZE(buttons),
                               BUTTON_DETECTION_DELAY);
    APP_ERROR_CHECK(err_code);

    err_code = app_button_enable();
    APP_ERROR_CHECK(err_code);

    NRF_LOG_INFO("Button enabled");
}

I also changed the configuration in app_button.c in app_button_init(), which was

nrf_drv_gpiote_in_config_t config = GPIOTE_CONFIG_IN_SENSE_TOGGLE(false);

and I changed it to:

nrf_drv_gpiote_in_config_t config = GPIOTE_CONFIG_IN_SENSE_HITOLO(false);

Is there an error in my configuration or do you think this is a hardware issue?

I appreciate any help, thanks!

Parents
  • Hi

    It sounds like you're not having a debounce implemented in your application. The button handler lib uses the GPIOTE handler to detect a button that has been pushed, and should start a timer in the GPIOTE event handler to handle this. The button will only be reported as pushed if the corresponding pin is still active when the timer expires. If there is a new GPIOTE event while the timer is running, the timer is restarted.

    For the hardware side of things, as long as there is a pull-up on the pin (internal or external) and there is a physical switch or button that connect the input to ground when pressed, then it can be used as a button. Are you using a Development Kit or a custom board for your application?

    Best regards,

    Simon

Reply
  • Hi

    It sounds like you're not having a debounce implemented in your application. The button handler lib uses the GPIOTE handler to detect a button that has been pushed, and should start a timer in the GPIOTE event handler to handle this. The button will only be reported as pushed if the corresponding pin is still active when the timer expires. If there is a new GPIOTE event while the timer is running, the timer is restarted.

    For the hardware side of things, as long as there is a pull-up on the pin (internal or external) and there is a physical switch or button that connect the input to ground when pressed, then it can be used as a button. Are you using a Development Kit or a custom board for your application?

    Best regards,

    Simon

Children
No Data
Related