From 943262294831375a2e5c7c0d6f83f140c89f1e00 Mon Sep 17 00:00:00 2001 From: Themba Dube Date: Sat, 4 Jan 2020 08:48:37 -0500 Subject: [PATCH] Allow objects to override bounding-box hit-testing --- src/lv_core/lv_obj.c | 27 +++++++++++++++++++-------- src/lv_core/lv_obj.h | 16 ++++++++++++++++ src/lv_objx/lv_cpicker.c | 5 +++++ 3 files changed, 40 insertions(+), 8 deletions(-) diff --git a/src/lv_core/lv_obj.c b/src/lv_core/lv_obj.c index c84ee346d..c05380603 100644 --- a/src/lv_core/lv_obj.c +++ b/src/lv_core/lv_obj.c @@ -2412,12 +2412,14 @@ bool lv_obj_is_focused(const lv_obj_t * obj) *------------------*/ /** - * Hit-test an object given a particular point in screen space. - * @param obj object to hit-test + * Check if a given screen-space point is on an object's coordinates. + * + * This method is intended to be used mainly by advanced hit testing algorithms to check + * whether the point is even within the object (as an optimization). + * @param obj object to check * @param point screen-space point - * @return true if the object is considered under the point */ -bool lv_obj_hittest(lv_obj_t * obj, lv_point_t * point) { +bool lv_obj_is_point_on_coords(lv_obj_t * obj, lv_point_t * point) { #if LV_USE_EXT_CLICK_AREA == LV_EXT_CLICK_AREA_TINY lv_area_t ext_area; ext_area.x1 = obj->coords.x1 - obj->ext_click_pad_hor; @@ -2439,15 +2441,24 @@ bool lv_obj_hittest(lv_obj_t * obj, lv_point_t * point) { #endif return false; } + return true; +} + +/** + * Hit-test an object given a particular point in screen space. + * @param obj object to hit-test + * @param point screen-space point + * @return true if the object is considered under the point + */ +bool lv_obj_hittest(lv_obj_t * obj, lv_point_t * point) { if(obj->adv_hittest) { lv_hit_test_info_t hit_info; hit_info.point = point; hit_info.result = true; obj->signal_cb(obj, LV_SIGNAL_HIT_TEST, &hit_info); - if(!hit_info.result) - return false; - } - return true; + return hit_info.result; + } else + return lv_obj_is_point_on_coords(obj, point); } /** diff --git a/src/lv_core/lv_obj.h b/src/lv_core/lv_obj.h index cd99382e6..d4886be47 100644 --- a/src/lv_core/lv_obj.h +++ b/src/lv_core/lv_obj.h @@ -940,6 +940,22 @@ lv_event_cb_t lv_obj_get_event_cb(const lv_obj_t * obj); * Other get *-----------------*/ +/** + * Check if a given screen-space point is on an object's coordinates. + * + * This method is intended to be used mainly by advanced hit testing algorithms to check + * whether the point is even within the object (as an optimization). + * @param obj object to check + * @param point screen-space point + */ +bool lv_obj_is_point_on_coords(lv_obj_t * obj, lv_point_t * point); + +/** + * Hit-test an object given a particular point in screen space. + * @param obj object to hit-test + * @param point screen-space point + * @return true if the object is considered under the point + */ bool lv_obj_hittest(lv_obj_t * obj, lv_point_t * point); /** diff --git a/src/lv_objx/lv_cpicker.c b/src/lv_objx/lv_cpicker.c index 4f6be702c..95c6d26aa 100644 --- a/src/lv_objx/lv_cpicker.c +++ b/src/lv_objx/lv_cpicker.c @@ -900,9 +900,14 @@ static lv_res_t lv_cpicker_signal(lv_obj_t * cpicker, lv_signal_t sign, void * p static bool lv_cpicker_hit(lv_obj_t * cpicker, const lv_point_t * p) { + bool is_point_on_coords = lv_obj_is_point_on_coords(cpicker, p); + if(!is_point_on_coords) + return false; + lv_cpicker_ext_t * ext = (lv_cpicker_ext_t *)lv_obj_get_ext_attr(cpicker); if(ext->type != LV_CPICKER_TYPE_DISC || ext->preview) return true; + const lv_style_t * style_main = lv_cpicker_get_style(cpicker, LV_CPICKER_STYLE_MAIN); lv_area_t area_mid; lv_area_copy(&area_mid, &cpicker->coords);