[Howto] How to get event when an animation is running?


I create 2 lv_img,
the first for a background img, the second for an image.
And set animation for the second image with the first image set event_cb.
However when the second image is animation-running,
the first image can’t receive any event from event_cb.

How to receive some events for the first image
between the second image is animation-running?

Thank you.

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

  • ESP32

What do you want to achieve?

I want to receive events between the animation is running.

What have you tried so far?

Code to reproduce

  lv_obj_t* first_img = lv_img_create(lv_scr_act(), NULL);
  lv_img_set_src(first_img, "S:/background.bin");

  lv_obj_set_click(first_img, true);
  lv_obj_set_event_cb(first_img, [](lv_obj_t* room, lv_event_t event){
    if(event != LV_EVENT_PRESSED) return;
    Serial.println("Pressed");  // ---> can't receive LV_EVENT_PRESSED for displaying this info.

  lv_obj_t* second_img = lv_img_create(lv_scr_act(),NULL);
  lv_img_set_src(second_img, "S:/image.bin");
  lv_obj_set_y(second_img, 120);

  lv_anim_t a;
  lv_anim_set_exec_cb(&a, second_img, (lv_anim_exec_xcb_t) lv_obj_set_x);
  lv_anim_set_time(&a, 10000, 0);
  lv_anim_set_values(&a, 0, 250);
  lv_anim_set_path_cb(&a, lv_anim_path_linear);
  lv_anim_set_repeat(&a, 1000);
  lv_anim_set_playback(&a, 1000);

Screenshot and/or video

Interesting. You are still using 6.1, right? Does it work again when the animation finishes?

I’m using on Dev7.0.

First Image can receive event when before playpack and repeat is begin
because of 1000ms by

  lv_anim_set_repeat(&a, 1000);
  lv_anim_set_playback(&a, 1000);

but between animation is running , first Image can not receive any event.


I’ve tested it in simulator and it worked well there.

Not that, the API of animations is slightly updated. Most importantly you should call lv_anim_init(&a) before other set functions.

I’ve tested with this code (buttons instead of images + the new animation API):

  lv_obj_t* first_img = lv_btn_create(lv_scr_act(), NULL);

   lv_obj_set_click(first_img, true);
   lv_obj_set_event_cb(first_img, event_cb);

   lv_obj_t* second_img = lv_btn_create(lv_scr_act(),NULL);
   lv_obj_set_y(second_img, 120);

   lv_anim_t a;
   lv_anim_set_var(&a, second_img);
   lv_anim_set_exec_cb(&a,  (lv_anim_exec_xcb_t) lv_obj_set_x);
   lv_anim_set_time(&a, 10000);
   lv_anim_set_values(&a, 0, 250);
   lv_anim_set_path_cb(&a, lv_anim_path_linear);
   lv_anim_set_repeat_delay(&a, 1000);
   lv_anim_set_playback_time(&a, 1000);

Could you update to the latest version and try again?

For possible bugs like this feel free to open an issue on GitHub!

1 Like

Thank you for the update.

However, the latest dev7.0 seems has some changing
about the lvgl-object’s style to new structure.
I have created my cpp libraries for covering lvgl dev7.0
based on the old object’s style,
it can’t use the latest dev7.0 with new object’s style.

Is there any document about new object’s style ?
Or can i replace only the lastest lv_anim.h /.c directly?
or do you mind to suggest for the best way
that can use with the old objlect’s style?

Thank you very much.

I see.
If you tell which commit do you use now, I can try your code with it and send a patch. I think it’d be the most simple way.

Sorry for late reply.

I’m not sure which commit,
I use lvgl dev7.0 downloaded on Jan24 maybe commit d108b2e.

No problem :slight_smile:
I’ve tried it an it still works in the simulator. However I have an idea what can cause the problem. If you load the images from the SD card and animate the image the CPU load can be 100% which could prevent indev_read from running. To fix this, in a later commit I’ve increased indev_read_task's priority. You can do the same by changing the priority in line 95 in lv_hal_indev.c to LV_TASK_PRIO_HIGH:

   indev->driver.read_task = lv_task_create(lv_indev_read_task, LV_INDEV_DEF_READ_PERIOD, LV_TASK_PRIO_HIGH, indev);

1 Like

It’ worked!

Thank you very much. Master Kisvegabor!

:smiley: My pleasure!

1 Like