Button Matrix (btnm) second click

Description

Hi,
I am trying to find a way to click button matrix button’s only one time. I need no effect, no animation and no state change for second click to same button on button matrixs (btnm). I have written my code then realized to check tab view transition for how tab view transition but they(my call back and tabview transition ) are similar for translation.
There is another-way to set toggle press/button press styles same and toggle release/button release styles same but i do not want to change buttons native natures. So how can i do it to click only ones on same button on button matrix.

What MCU/Processor/Board and compiler are you using?

STM32F7 series

What do you want to achieve?

How can i do it to click only ones on same button on button matrix.

What have you tried so far?

Code to reproduce

Add a code snippet which can run in the simulator. It should contain only the relevant code that compiles without errors when separated from your main code base.

The code block(s) should be between ```c and ``` tags:

/*declarations are all above functions*/
static void btnm1_event_handler(lv_obj_t * obj, lv_event_t event)
{
// this part from tabview change
    if(event != LV_EVENT_CLICKED) return;
    uint16_t btn_id = lv_btnm_get_active_btn(obj);
    if(btn_id == LV_BTNM_BTN_NONE) return;
    lv_btnm_clear_btn_ctrl_all(obj, LV_BTNM_CTRL_TGL_STATE);
    lv_btnm_set_btn_ctrl_all(obj, LV_BTNM_CTRL_TGL_ENABLE);
    lv_btnm_set_one_toggle(obj, true);
    lv_btnm_set_btn_ctrl(obj, btn_id, LV_BTNM_CTRL_TGL_STATE);
    lv_btnm_clear_btn_ctrl(obj, btn_id, LV_BTNM_CTRL_TGL_ENABLE);
    
	/*
//this is my own code. both are working similar
	//printf("%d was pressed\n", event);
	lv_btnm_set_btn_ctrl_all(obj,LV_BTNM_CTRL_NO_REPEAT);
	if(event == LV_EVENT_RELEASED) {
		uint16_t btn_id = lv_btnm_get_active_btn(obj);
        //printf("btn id: %d \n", btn_id);
        lv_btnm_set_btn_ctrl_all(obj, LV_BTNM_CTRL_TGL_ENABLE);
        lv_btnm_set_one_toggle(obj, true);
        lv_btnm_set_btn_ctrl(obj,btn_id,LV_BTNM_CTRL_TGL_STATE);
    }
*/
}

Screenshot and/or video

If possible, add screenshots and/or videos about the current state.
simulator4buttonmatrix-2019-08-20_08.38.zip (2.6 MB)

Hi,

This trick should work:

static void event_handler(lv_obj_t * obj, lv_event_t event)
{
    static uint16_t btn_first = LV_BTNM_BTN_NONE;

    uint16_t id = lv_btnm_get_active_btn(obj);
    lv_btnm_ext_t * ext = lv_obj_get_ext_attr(obj);
    if(event == LV_EVENT_PRESSED) {
        if(id != btn_first) {   /*A new button or first click because `btn_first == LV_BTNM_BTN_NONE`*/
            lv_btnm_ext_t * ext = lv_obj_get_ext_attr(obj);
            ext->btn_id_pr = LV_BTNM_BTN_NONE;
            ext->btn_id_act = LV_BTNM_BTN_NONE;
            btn_first = id;
        }
        else {
            printf("Second click\n");
            btn_first = LV_BTNM_BTN_NONE;
        }
    } else if(event == LV_EVENT_PRESSING) {
        if(id == btn_first) { /*If still pressing the same button ignore it*/
            ext->btn_id_pr = LV_BTNM_BTN_NONE;
            ext->btn_id_act = LV_BTNM_BTN_NONE;
        }
    }
}

I have check your codes but not worked for me.
It kind of does something else before click/pressed or pressing to change state.
I need to keep same state and visual when same button is clicked/pressed until different button is clicked/pressed.
Please check my short screen cast.
buttonmatrix-2019-08-21_10.29.zip (3.9 MB)
thanks

I also have tried to find out from btnm values for what effect make changes it’s state so print all btnm values on any events. I am not sure but it seems like something change before event happens.
buttonmatrix2-2019-08-21_11.06.zip (3.9 MB)

I don’t understand exactly what you mean, but are you looking to toggle the buttons and only allow one of them to be toggled at once? If so, you could try the “one toggle” feature:

https://docs.littlevgl.com/en/html/object-types/btnm.html#one-toggle

Be sure to have toggling enabled on all the relevant buttons (LV_BTNM_CTRL_TGL_ENABLE). It will ensure that when you toggle the next button the previous one is toggled back to the original unpressed state.

I need no changes(keep its states, and also no visual effects) When I pressed toggled button.

So you want to disable the ability to untoggle a button?

yes, until different btnm button is pressed.

I misunderstood your goal. How about this one?


static void event_handler(lv_obj_t * obj, lv_event_t event)
{
    static uint16_t prev_tgl_id = LV_BTNM_BTN_NONE;

    uint16_t id = lv_btnm_get_active_btn(obj);

    if(event == LV_EVENT_VALUE_CHANGED) {
        /*Untoggle previous*/
        lv_btnm_clear_btn_ctrl(obj, prev_tgl_id, LV_BTNM_CTRL_TGL_STATE);

        /*Be sure the current is toggled*/
        lv_btnm_set_btn_ctrl(obj, id, LV_BTNM_CTRL_TGL_STATE);

        prev_tgl_id = id;
    }
}

btm_tgl

Thanks. It works.
I have to mention one thing. If you have any toggled button on initial state, you have to clear all toggle states. So I just replace
lv_btnm_clear_btn_ctrl -> lv_btnm_clear_btn_ctrl_all


static void event_handler(lv_obj_t * obj, lv_event_t event)
{
    static uint16_t prev_tgl_id = LV_BTNM_BTN_NONE;

    uint16_t id = lv_btnm_get_active_btn(obj);

    if(event == LV_EVENT_VALUE_CHANGED) {
        /*Untoggle previous*/
        //lv_btnm_clear_btn_ctrl(obj, prev_tgl_id, LV_BTNM_CTRL_TGL_STATE);
        lv_btnm_clear_btn_ctrl_all(obj,LV_BTNM_CTRL_TGL_STATE);

        /*Be sure the current is toggled*/
        lv_btnm_set_btn_ctrl(obj, id, LV_BTNM_CTRL_TGL_STATE);

        prev_tgl_id = id;
    }
}

It works well, thanks again.

hello, i’m beginner, i’m working on the same topic but with LVGL 8.1 and i want to uncheck the pressed last button if i press a second time,
I need to have just one button checked and have the possibility to uncheck all buttons (as they are at first view of screen,

/*
lv_btnmatrix_set_btn_ctrl_all(btnm1 , LV_BTNMATRIX_CTRL_CHECKABLE);
lv_btnmatrix_set_one_checked(btnm1, true);
*/
first view (all buttons are unchecked)
image

here all time i have one button activated, i think it’s due to : ##lv_btnmatrix_set_one_checked()
image
is there a solution to uncheck all after ?

Hi,

It should work

  lv_obj_t * obj = lv_btnmatrix_create(lv_scr_act());
  lv_btnmatrix_set_btn_ctrl_all(obj, LV_BTNMATRIX_CTRL_CHECKABLE);
  lv_btnmatrix_set_one_checked(obj, true);

  /*Make a button checked manually*/
  lv_btnmatrix_set_btn_ctrl(obj, 3, LV_BTNMATRIX_CTRL_CHECKED);

  /*Uncheck all buttons*/
  lv_btnmatrix_clear_btn_ctrl_all(obj, LV_BTNMATRIX_CTRL_CHECKED);

1 Like

Hi @kisvegabor,

My issue is that i can’t know the state of my button (checked or not) all i get is focused and pressed
Could you have a look to my post here ? I hope you will understand my issue

Hi @Zebra067 ,

I have replied here. If you want to give that a try?

Cheers,

Pete

1 Like