Skip to content
forked from lvgl/lvgl

Commit

Permalink
feat(vg_lite): add image clip corner support (lvgl#6121)
Browse files Browse the repository at this point in the history
Signed-off-by: pengyiqiang <pengyiqiang@xiaomi.com>
Co-authored-by: pengyiqiang <pengyiqiang@xiaomi.com>
  • Loading branch information
FASTSHIFT and pengyiqiang authored Jun 13, 2024
1 parent c129d97 commit f16a92a
Show file tree
Hide file tree
Showing 8 changed files with 46 additions and 6 deletions.
3 changes: 3 additions & 0 deletions src/draw/lv_draw_image.h
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,9 @@ typedef struct _lv_draw_image_dsc_t {
* 2. Tiled images, where the target draw area is larger than the image to be tiled.
*/
lv_area_t image_area;

int32_t clip_radius;

const lv_image_dsc_t * bitmap_mask_src;
} lv_draw_image_dsc_t;

Expand Down
32 changes: 26 additions & 6 deletions src/draw/vg_lite/lv_draw_vg_lite_img.c
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,7 @@ void lv_draw_vg_lite_img(lv_draw_unit_t * draw_unit, const lv_draw_image_dsc_t *
LV_VG_LITE_ASSERT_DEST_BUFFER(&u->target_buffer);

/* If clipping is not required, blit directly */
if(_lv_area_is_in(&image_tf_area, draw_unit->clip_area, false)) {
if(_lv_area_is_in(&image_tf_area, draw_unit->clip_area, false) && dsc->clip_radius <= 0) {
/* The image area is the coordinates relative to the image itself */
lv_area_t src_area = *coords;
lv_area_move(&src_area, -coords->x1, -coords->y1);
Expand All @@ -121,11 +121,31 @@ void lv_draw_vg_lite_img(lv_draw_unit_t * draw_unit, const lv_draw_image_dsc_t *
}
else {
lv_vg_lite_path_t * path = lv_vg_lite_path_get(u, VG_LITE_FP32);
lv_vg_lite_path_append_rect(
path,
clip_area.x1, clip_area.y1,
lv_area_get_width(&clip_area), lv_area_get_height(&clip_area),
0, 0);

if(dsc->clip_radius) {
int32_t width = lv_area_get_width(coords);
int32_t height = lv_area_get_height(coords);
float r_short = LV_MIN(width, height) / 2.0f;
float radius = LV_MIN(dsc->clip_radius, r_short);

/**
* When clip_radius is enabled, the clipping edges
* are aligned with the image edges
*/
lv_vg_lite_path_append_rect(
path,
coords->x1, coords->y1,
width, height,
radius, radius);
}
else {
lv_vg_lite_path_append_rect(
path,
clip_area.x1, clip_area.y1,
lv_area_get_width(&clip_area), lv_area_get_height(&clip_area),
0, 0);
}

lv_vg_lite_path_set_bonding_box_area(path, &clip_area);
lv_vg_lite_path_end(path);

Expand Down
3 changes: 3 additions & 0 deletions src/widgets/image/lv_image.c
Original file line number Diff line number Diff line change
Expand Up @@ -749,6 +749,9 @@ static void draw_image(lv_event_t * e)
obj->coords.y1,
obj->coords.x1 + img->w - 1,
obj->coords.y1 + img->h - 1);

draw_dsc.clip_radius = lv_obj_get_style_radius(obj, LV_PART_MAIN);

lv_area_t coords;
if(img->align < _LV_IMAGE_ALIGN_AUTO_TRANSFORM) {
lv_area_align(&obj->coords, &draw_dsc.image_area, img->align, img->offset.x, img->offset.y);
Expand Down
Binary file added tests/ref_imgs/widgets/image_clip_radius_10.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
14 changes: 14 additions & 0 deletions tests/src/test_cases/widgets/test_image.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include "unity/unity.h"

LV_IMAGE_DECLARE(test_img_lvgl_logo_png);
LV_IMAGE_DECLARE(test_arc_bg);

void setUp(void)
{
Expand Down Expand Up @@ -361,4 +362,17 @@ void test_image_ignore_transformation_settings_when_tiled(void)
TEST_ASSERT_EQUAL_INT(LV_SCALE_NONE, lv_image_get_scale_y(img));
}

void test_image_clip_radius(void)
{
lv_obj_t * img = lv_img_create(lv_screen_active());
lv_image_set_src(img, &test_arc_bg);
lv_obj_center(img);

lv_obj_set_style_radius(img, 10, 0);
TEST_ASSERT_EQUAL_SCREENSHOT("widgets/image_clip_radius_10.png");

lv_obj_set_style_radius(img, LV_RADIUS_CIRCLE, 0);
TEST_ASSERT_EQUAL_SCREENSHOT("widgets/image_clip_radius_circle.png");
}

#endif

0 comments on commit f16a92a

Please sign in to comment.