mirror of
https://github.com/lvgl/lvgl.git
synced 2026-05-31 07:56:23 +08:00
fix(anim): fix the crash caused by delete anim in cb (#7926)
Signed-off-by: yushuailong <yushuailong1@xiaomi.com> Signed-off-by: yushuailong1 <yushuailong1@xiaomi.com> Co-authored-by: yushuailong <yushuailong1@xiaomi.com>
This commit is contained in:
+7
-5
@@ -46,7 +46,7 @@ static int32_t lv_anim_path_cubic_bezier(const lv_anim_t * a, int32_t x1,
|
|||||||
int32_t y1, int32_t x2, int32_t y2);
|
int32_t y1, int32_t x2, int32_t y2);
|
||||||
static void lv_anim_pause_for_internal(lv_anim_t * a, uint32_t ms);
|
static void lv_anim_pause_for_internal(lv_anim_t * a, uint32_t ms);
|
||||||
static void resolve_time(lv_anim_t * a);
|
static void resolve_time(lv_anim_t * a);
|
||||||
static bool remove_concurrent_anims(lv_anim_t * a_current);
|
static bool remove_concurrent_anims(const lv_anim_t * a_current);
|
||||||
static void remove_anim(void * a);
|
static void remove_anim(void * a);
|
||||||
|
|
||||||
/**********************
|
/**********************
|
||||||
@@ -95,6 +95,11 @@ lv_anim_t * lv_anim_start(const lv_anim_t * a)
|
|||||||
{
|
{
|
||||||
LV_TRACE_ANIM("begin");
|
LV_TRACE_ANIM("begin");
|
||||||
|
|
||||||
|
/*Do not let two animations for the same 'var' with the same 'exec_cb'*/
|
||||||
|
if(a->early_apply && (a->exec_cb || a->custom_exec_cb)) {
|
||||||
|
remove_concurrent_anims(a);
|
||||||
|
}
|
||||||
|
|
||||||
/*Add the new animation to the animation linked list*/
|
/*Add the new animation to the animation linked list*/
|
||||||
lv_anim_t * new_anim = lv_ll_ins_head(anim_ll_p);
|
lv_anim_t * new_anim = lv_ll_ins_head(anim_ll_p);
|
||||||
LV_ASSERT_MALLOC(new_anim);
|
LV_ASSERT_MALLOC(new_anim);
|
||||||
@@ -118,9 +123,6 @@ lv_anim_t * lv_anim_start(const lv_anim_t * a)
|
|||||||
|
|
||||||
resolve_time(new_anim);
|
resolve_time(new_anim);
|
||||||
|
|
||||||
/*Do not let two animations for the same 'var' with the same 'exec_cb'*/
|
|
||||||
if(a->exec_cb || a->custom_exec_cb) remove_concurrent_anims(new_anim);
|
|
||||||
|
|
||||||
new_anim->current_value = new_anim->path_cb(new_anim);
|
new_anim->current_value = new_anim->path_cb(new_anim);
|
||||||
if(new_anim->exec_cb) {
|
if(new_anim->exec_cb) {
|
||||||
new_anim->exec_cb(new_anim->var, new_anim->current_value);
|
new_anim->exec_cb(new_anim->var, new_anim->current_value);
|
||||||
@@ -725,7 +727,7 @@ static void resolve_time(lv_anim_t * a)
|
|||||||
* @param a_current the current animation, use its var and exec_cb as reference to know what to remove
|
* @param a_current the current animation, use its var and exec_cb as reference to know what to remove
|
||||||
* @return true: at least one animation was delete
|
* @return true: at least one animation was delete
|
||||||
*/
|
*/
|
||||||
static bool remove_concurrent_anims(lv_anim_t * a_current)
|
static bool remove_concurrent_anims(const lv_anim_t * a_current)
|
||||||
{
|
{
|
||||||
if(a_current->exec_cb == NULL && a_current->custom_exec_cb == NULL) return false;
|
if(a_current->exec_cb == NULL && a_current->custom_exec_cb == NULL) return false;
|
||||||
|
|
||||||
|
|||||||
@@ -13,6 +13,8 @@ void setUp(void)
|
|||||||
void tearDown(void)
|
void tearDown(void)
|
||||||
{
|
{
|
||||||
/* Function run after every test */
|
/* Function run after every test */
|
||||||
|
lv_obj_clean(lv_screen_active());
|
||||||
|
lv_anim_delete_all();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void exec_cb(void * var, int32_t v)
|
static void exec_cb(void * var, int32_t v)
|
||||||
@@ -170,4 +172,25 @@ void test_anim_pause_for_resume(void)
|
|||||||
lv_test_wait(20);
|
lv_test_wait(20);
|
||||||
TEST_ASSERT_EQUAL(19, var);
|
TEST_ASSERT_EQUAL(19, var);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void event_cb(lv_event_t * e)
|
||||||
|
{
|
||||||
|
lv_obj_t * obj = lv_event_get_target_obj(e);
|
||||||
|
int * var = lv_event_get_user_data(e);
|
||||||
|
lv_anim_delete(obj, NULL);
|
||||||
|
*var += 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void test_scroll_anim_delete(void)
|
||||||
|
{
|
||||||
|
int var = 0;
|
||||||
|
lv_obj_t * obj = lv_obj_create(lv_screen_active());
|
||||||
|
lv_obj_add_event_cb(obj, event_cb, LV_EVENT_SCROLL_END, &var);
|
||||||
|
lv_obj_scroll_by(obj, 0, 100, LV_ANIM_ON);
|
||||||
|
lv_test_wait(20);
|
||||||
|
lv_obj_scroll_by(obj, 0, 100, LV_ANIM_ON);
|
||||||
|
|
||||||
|
TEST_ASSERT_EQUAL(1, var);
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
Reference in New Issue
Block a user