aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorcristian-stoica <cristianmarian.stoica@nxp.com>2024-03-17 07:42:33 +0200
committerGitHub <noreply@github.com>2024-03-17 13:42:33 +0800
commitf42be6a4da61f50f81b9226a8ef54a1d9590f3d2 (patch)
tree8246b1736cb87ef14ac922bd1925bda50a859593
parent5c018517894ccdb1cc349ef4d5cb472b4ef98ba9 (diff)
downloadlvgl-f42be6a4da61f50f81b9226a8ef54a1d9590f3d2.tar.gz
lvgl-f42be6a4da61f50f81b9226a8ef54a1d9590f3d2.zip
fix(vglite): update NXP's VGLite implementation (#5887)
Signed-off-by: Ana Grad <ana.grad@nxp.com> Co-authored-by: Ana Grad <ana.grad@nxp.com>
-rw-r--r--src/draw/nxp/vglite/lv_draw_vglite.c17
-rw-r--r--src/draw/nxp/vglite/lv_draw_vglite_arc.c3
-rw-r--r--src/draw/nxp/vglite/lv_draw_vglite_img.c160
-rw-r--r--src/draw/nxp/vglite/lv_vglite_matrix.c18
-rw-r--r--src/draw/nxp/vglite/lv_vglite_path.h8
5 files changed, 132 insertions, 74 deletions
diff --git a/src/draw/nxp/vglite/lv_draw_vglite.c b/src/draw/nxp/vglite/lv_draw_vglite.c
index fc36a3035..d4c951728 100644
--- a/src/draw/nxp/vglite/lv_draw_vglite.c
+++ b/src/draw/nxp/vglite/lv_draw_vglite.c
@@ -228,7 +228,15 @@ static int32_t _vglite_evaluate(lv_draw_unit_t * u, lv_draw_task_t * t)
const lv_draw_image_dsc_t * draw_dsc = (lv_draw_image_dsc_t *) t->draw_dsc;
lv_layer_t * layer_to_draw = (lv_layer_t *)draw_dsc->src;
- if(!_vglite_src_cf_supported(layer_to_draw->color_format))
+#if LV_USE_VGLITE_BLIT_SPLIT
+ bool has_transform = (draw_dsc->rotation != 0 || draw_dsc->scale_x != LV_SCALE_NONE ||
+ draw_dsc->scale_y != LV_SCALE_NONE);
+#endif
+ if(!_vglite_src_cf_supported(layer_to_draw->color_format)
+#if LV_USE_VGLITE_BLIT_SPLIT
+ || has_transform
+#endif
+ )
return 0;
if(t->preference_score > 80) {
@@ -354,8 +362,11 @@ static void _vglite_execute_drawing(lv_draw_vglite_unit_t * u)
/* Invalidate the drawing area */
lv_draw_buf_invalidate_cache(draw_buf, &draw_area);
- /* Set scissor area */
- vglite_set_scissor(&clip_area);
+ /* Set scissor area, excluding the split blit case */
+#if LV_USE_VGLITE_BLIT_SPLIT
+ if(t->type != LV_DRAW_TASK_TYPE_IMAGE || t->type != LV_DRAW_TASK_TYPE_LAYER)
+#endif
+ vglite_set_scissor(&clip_area);
switch(t->type) {
case LV_DRAW_TASK_TYPE_LABEL:
diff --git a/src/draw/nxp/vglite/lv_draw_vglite_arc.c b/src/draw/nxp/vglite/lv_draw_vglite_arc.c
index b35d2c74a..6b0d4fe55 100644
--- a/src/draw/nxp/vglite/lv_draw_vglite_arc.c
+++ b/src/draw/nxp/vglite/lv_draw_vglite_arc.c
@@ -573,8 +573,7 @@ static void _vglite_draw_arc(const lv_point_t * center, const lv_area_t * clip_a
bool donut = ((end_angle - start_angle) % 360 == 0) ? true : false;
vg_lite_buffer_t * vgbuf = vglite_get_dest_buf();
- /* path: max size = 16 cubic bezier (7 words each) */
- int32_t arc_path[16 * 7];
+ int32_t arc_path[ARC_PATH_DATA_MAX_SIZE];
lv_memzero(arc_path, sizeof(arc_path));
/*** Init path ***/
diff --git a/src/draw/nxp/vglite/lv_draw_vglite_img.c b/src/draw/nxp/vglite/lv_draw_vglite_img.c
index 6dacad88b..b7ee0560c 100644
--- a/src/draw/nxp/vglite/lv_draw_vglite_img.c
+++ b/src/draw/nxp/vglite/lv_draw_vglite_img.c
@@ -19,6 +19,7 @@
#include "lv_vglite_buf.h"
#include "lv_vglite_matrix.h"
#include "lv_vglite_utils.h"
+#include "lv_vglite_path.h"
#include "../../../misc/lv_log.h"
@@ -57,18 +58,6 @@
* STATIC PROTOTYPES
**********************/
-/**
- * BLock Image Transfer - copy rectangular image from src_buf to dst_buf with effects.
- * By default, image is copied directly, with optional opacity.
- *
- * @param[in] dest_area Destination area with relative coordinates to dest buffer
- * @param[in] src_area Source area with relative coordinates to src buffer
- * @param[in] dsc Image descriptor
- *
- */
-static void _vglite_blit_single(const lv_area_t * dest_area, const lv_area_t * src_area,
- const lv_draw_image_dsc_t * dsc);
-
#if LV_USE_VGLITE_BLIT_SPLIT
/**
* Move buffer pointer as close as possible to area, but with respect to alignment requirements.
@@ -98,19 +87,31 @@ static void _move_buf_close_to_area(void ** buf, lv_area_t * area, uint32_t stri
static void _vglite_blit_split(void * dest_buf, lv_area_t * dest_area, uint32_t dest_stride, lv_color_format_t dest_cf,
const void * src_buf, lv_area_t * src_area, uint32_t src_stride, lv_color_format_t src_cf,
const lv_draw_image_dsc_t * dsc);
-#else
+#endif /*LV_USE_VGLITE_BLIT_SPLIT*/
+
/**
- * BLock Image Transfer - copy rectangular image from src_buf to dst_buf with transformation.
- * By default, image is copied directly, with optional opacity.
+ * VGlite blit - fill a path with an image pattern
+ *
+ *
+ * @param[in] dest_area Destination area with relative coordinates to dest buffer
+ * @param[in] clip_area Clip area with relative coordinates to dest buff
+ * @param[in] coords Coordinates of the image (relative to dest buff)
+ * @param[in] dsc Image descriptor
+ *
+ */
+static void _vglite_draw_pattern(const lv_area_t * clip_area, const lv_area_t * coords,
+ const lv_draw_image_dsc_t * dsc);
+
+/**
+ * BLock Image Transfer - copy rectangular image from src_buf to dst_buf with or without effects.
*
- * @param[in] dest_area Area with relative coordinates to dest buffer
* @param[in] src_area Source area with relative coordinates to src buffer
* @param[in] dsc Image descriptor
*
*/
-static void _vglite_blit_transform(const lv_area_t * dest_area, const lv_area_t * src_area,
- const lv_draw_image_dsc_t * dsc);
-#endif /*LV_USE_VGLITE_BLIT_SPLIT*/
+static void _vglite_blit(const lv_area_t * src_area, const lv_draw_image_dsc_t * dsc);
+
+static vg_lite_color_t _vglite_recolor(const lv_draw_image_dsc_t * dsc);
/**********************
* STATIC VARIABLES
@@ -160,7 +161,7 @@ void lv_draw_vglite_img(lv_draw_unit_t * draw_unit, const lv_draw_image_dsc_t *
uint32_t src_stride = img_dsc->header.stride;
/* Set src_vgbuf structure. */
- vglite_set_src_buf(src_buf, lv_area_get_width(&src_area), lv_area_get_height(&src_area), src_stride, src_cf);
+ vglite_set_src_buf(src_buf, img_dsc->header.w, img_dsc->header.h, src_stride, src_cf);
#if LV_USE_VGLITE_BLIT_SPLIT
void * dest_buf = layer->draw_buf->data;
@@ -171,10 +172,12 @@ void lv_draw_vglite_img(lv_draw_unit_t * draw_unit, const lv_draw_image_dsc_t *
_vglite_blit_split(dest_buf, &blend_area, dest_stride, dest_cf,
src_buf, &src_area, src_stride, src_cf, dsc);
#else
- if(has_transform)
- _vglite_blit_transform(&blend_area, &src_area, dsc);
+ vglite_set_transformation_matrix(&blend_area, dsc);
+ bool is_tiled = dsc->tile;
+ if(is_tiled)
+ _vglite_draw_pattern(&clip_area, &relative_coords, dsc);
else
- _vglite_blit_single(&blend_area, &src_area, dsc);
+ _vglite_blit(&src_area, dsc);
#endif /*LV_USE_VGLITE_BLIT_SPLIT*/
}
@@ -196,23 +199,7 @@ static void _vglite_blit(const lv_area_t * src_area, const lv_draw_image_dsc_t *
src_vgbuf->image_mode = VG_LITE_MULTIPLY_IMAGE_MODE;
src_vgbuf->transparency_mode = VG_LITE_IMAGE_TRANSPARENT;
- lv_color_t color;
- lv_opa_t opa;
-
- bool has_recolor = (dsc->recolor_opa > LV_OPA_MIN);
- if(has_recolor) {
- color = dsc->recolor;
- opa = LV_OPA_MIX2(dsc->recolor_opa, dsc->opa);
- }
- else {
- color.red = 0xFF;
- color.green = 0xFF;
- color.blue = 0xFF;
- opa = dsc->opa;
- }
-
- lv_color32_t col32 = lv_color_to_32(color, opa);
- vg_lite_color_t vgcol = vglite_get_color(col32, false);
+ vg_lite_color_t vgcol = _vglite_recolor(dsc);
vg_lite_matrix_t * vgmatrix = vglite_get_matrix();
vg_lite_blend_t vgblend = vglite_get_blend_mode(dsc->blend_mode);
@@ -222,16 +209,6 @@ static void _vglite_blit(const lv_area_t * src_area, const lv_draw_image_dsc_t *
vglite_run();
}
-static void _vglite_blit_single(const lv_area_t * dest_area, const lv_area_t * src_area,
- const lv_draw_image_dsc_t * dsc)
-{
- /* Set vgmatrix. */
- vglite_set_translation_matrix(dest_area);
-
- /* Start blit. */
- _vglite_blit(src_area, dsc);
-}
-
#if LV_USE_VGLITE_BLIT_SPLIT
static void _move_buf_close_to_area(void ** buf, lv_area_t * area, uint32_t stride, lv_color_format_t cf)
{
@@ -276,6 +253,9 @@ static void _vglite_blit_split(void * dest_buf, lv_area_t * dest_area, uint32_t
_move_buf_close_to_area((void **)&src_buf, src_area, src_stride, src_cf);
_move_buf_close_to_area(&dest_buf, dest_area, dest_stride, dest_cf);
+ /* Set clip area */
+ vglite_set_scissor(dest_area);
+
/* If we're in limit, do a single BLIT */
if((src_area->x2 < VGLITE_BLIT_SPLIT_THR) &&
(src_area->y2 < VGLITE_BLIT_SPLIT_THR)) {
@@ -284,7 +264,8 @@ static void _vglite_blit_split(void * dest_buf, lv_area_t * dest_area, uint32_t
vglite_set_dest_buf_ptr(dest_buf);
vglite_set_src_buf_ptr(src_buf);
- _vglite_blit_single(dest_area, src_area, dsc);
+ vglite_set_transformation_matrix(dest_area, dsc);
+ _vglite_blit(src_area, dsc);
VGLITE_TRACE("Single "
"Area: ([%d,%d], [%d,%d]) -> ([%d,%d], [%d,%d]) | "
@@ -295,6 +276,8 @@ static void _vglite_blit_split(void * dest_buf, lv_area_t * dest_area, uint32_t
lv_area_get_width(src_area), lv_area_get_height(src_area),
lv_area_get_width(dest_area), lv_area_get_height(dest_area),
(uintptr_t)src_buf, (uintptr_t)dest_buf);
+
+ return;
};
/* Split the BLIT into multiple tiles */
@@ -371,7 +354,8 @@ static void _vglite_blit_split(void * dest_buf, lv_area_t * dest_area, uint32_t
vglite_set_dest_buf_ptr(tile_dest_buf);
vglite_set_src_buf_ptr(tile_src_buf);
- _vglite_blit_single(&tile_dest_area, &tile_src_area, dsc);
+ vglite_set_transformation_matrix(&tile_dest_area, dsc);
+ _vglite_blit(&tile_src_area, dsc);
VGLITE_TRACE("Tile [%d, %d] "
"Area: ([%d,%d], [%d,%d]) -> ([%d,%d], [%d,%d]) | "
@@ -386,16 +370,72 @@ static void _vglite_blit_split(void * dest_buf, lv_area_t * dest_area, uint32_t
}
}
}
-#else
-static void _vglite_blit_transform(const lv_area_t * dest_area, const lv_area_t * src_area,
- const lv_draw_image_dsc_t * dsc)
+#endif /*LV_USE_VGLITE_BLIT_SPLIT*/
+
+static void _vglite_draw_pattern(const lv_area_t * clip_area, const lv_area_t * coords,
+ const lv_draw_image_dsc_t * dsc)
{
- /* Set vgmatrix. */
- vglite_set_transformation_matrix(dest_area, dsc);
+ /* Target buffer */
+ vg_lite_buffer_t * dst_vgbuf = vglite_get_dest_buf();
+
+ /* Path to draw */
+ int32_t path_data[RECT_PATH_DATA_MAX_SIZE];
+ uint32_t path_data_size;
+ vglite_create_rect_path_data(path_data, &path_data_size, 0, coords);
+ vg_lite_quality_t path_quality = VG_LITE_MEDIUM;
+
+ vg_lite_path_t path;
+ VGLITE_CHECK_ERROR(vg_lite_init_path(&path, VG_LITE_S32, path_quality, path_data_size, path_data,
+ (vg_lite_float_t)clip_area->x1, (vg_lite_float_t)clip_area->y1,
+ ((vg_lite_float_t)clip_area->x2) + 1.0f, ((vg_lite_float_t)clip_area->y2) + 1.0f));
+
+ /* Path Matrix */
+ vg_lite_matrix_t path_matrix;
+ vg_lite_identity(&path_matrix);
+
+ /* Pattern Image */
+ vg_lite_buffer_t * src_vgbuf = vglite_get_src_buf();
+ src_vgbuf->image_mode = VG_LITE_MULTIPLY_IMAGE_MODE;
+ src_vgbuf->transparency_mode = VG_LITE_IMAGE_TRANSPARENT;
+
+ /* Pattern matrix */
+ vg_lite_matrix_t * vgmatrix = vglite_get_matrix();
+
+ /* Blend mode */
+ vg_lite_blend_t vgblend = vglite_get_blend_mode(dsc->blend_mode);
+
+ vg_lite_color_t vgcol = _vglite_recolor(dsc);
+
+ /* Filter */
+ bool has_trasform = (dsc->rotation != 0 || dsc->scale_x != LV_SCALE_NONE || dsc->scale_y != LV_SCALE_NONE);
+ vg_lite_filter_t filter = has_trasform ? VG_LITE_FILTER_BI_LINEAR : VG_LITE_FILTER_POINT;
- /* Start blit. */
- _vglite_blit(src_area, dsc);
+ /* Draw Pattern */
+ VGLITE_CHECK_ERROR(vg_lite_draw_pattern(dst_vgbuf, &path, VG_LITE_FILL_NON_ZERO, &path_matrix,
+ src_vgbuf, vgmatrix, vgblend, VG_LITE_PATTERN_REPEAT,
+ 0, vgcol, filter));
+}
+
+static vg_lite_color_t _vglite_recolor(const lv_draw_image_dsc_t * dsc)
+{
+ lv_color_t color;
+ lv_opa_t opa;
+
+ bool has_recolor = (dsc->recolor_opa > LV_OPA_MIN);
+ if(has_recolor) {
+ color = dsc->recolor;
+ opa = LV_OPA_MIX2(dsc->recolor_opa, dsc->opa);
+ }
+ else {
+ color.red = 0xFF;
+ color.green = 0xFF;
+ color.blue = 0xFF;
+ opa = dsc->opa;
+ }
+
+ lv_color32_t col32 = lv_color_to_32(color, opa);
+
+ return vglite_get_color(col32, false);
}
-#endif /*LV_USE_VGLITE_BLIT_SPLIT*/
#endif /*LV_USE_DRAW_VGLITE*/
diff --git a/src/draw/nxp/vglite/lv_vglite_matrix.c b/src/draw/nxp/vglite/lv_vglite_matrix.c
index 3076c6c91..0594b53dc 100644
--- a/src/draw/nxp/vglite/lv_vglite_matrix.c
+++ b/src/draw/nxp/vglite/lv_vglite_matrix.c
@@ -61,15 +61,17 @@ void vglite_set_transformation_matrix(const lv_area_t * dest_area, const lv_draw
bool has_scale = (dsc->scale_x != LV_SCALE_NONE || dsc->scale_y != LV_SCALE_NONE);
bool has_rotation = (dsc->rotation != 0);
- vg_lite_translate(dsc->pivot.x, dsc->pivot.y, &_vgmatrix);
- if(has_rotation)
- vg_lite_rotate(dsc->rotation / 10.0f, &_vgmatrix); /* angle is 1/10 degree */
- if(has_scale) {
- vg_lite_float_t scale_x = 1.0f * dsc->scale_x / LV_SCALE_NONE;
- vg_lite_float_t scale_y = 1.0f * dsc->scale_y / LV_SCALE_NONE;
- vg_lite_scale(scale_x, scale_y, &_vgmatrix);
+ if(has_scale || has_rotation) {
+ vg_lite_translate(dsc->pivot.x, dsc->pivot.y, &_vgmatrix);
+ if(has_rotation)
+ vg_lite_rotate(dsc->rotation / 10.0f, &_vgmatrix); /* angle is 1/10 degree */
+ if(has_scale) {
+ vg_lite_float_t scale_x = 1.0f * dsc->scale_x / LV_SCALE_NONE;
+ vg_lite_float_t scale_y = 1.0f * dsc->scale_y / LV_SCALE_NONE;
+ vg_lite_scale(scale_x, scale_y, &_vgmatrix);
+ }
+ vg_lite_translate(0.0f - dsc->pivot.x, 0.0f - dsc->pivot.y, &_vgmatrix);
}
- vg_lite_translate(0.0f - dsc->pivot.x, 0.0f - dsc->pivot.y, &_vgmatrix);
}
/**********************
diff --git a/src/draw/nxp/vglite/lv_vglite_path.h b/src/draw/nxp/vglite/lv_vglite_path.h
index 6c92e50e6..f38593aeb 100644
--- a/src/draw/nxp/vglite/lv_vglite_path.h
+++ b/src/draw/nxp/vglite/lv_vglite_path.h
@@ -47,8 +47,14 @@ extern "C" {
* - 4 cubics for the corners
* - 4 lines for the sides
* - 1 end for the path end */
-#define RECT_PATH_DATA_MAX_SIZE 1 * MOVE_PATH_DATA_SIZE + 4 * CUBIC_PATH_DATA_SIZE + 4 * LINE_PATH_DATA_SIZE + 1 * END_PATH_DATA_SIZE
+#define RECT_PATH_DATA_MAX_SIZE (1 * MOVE_PATH_DATA_SIZE + 4 * CUBIC_PATH_DATA_SIZE + 4 * LINE_PATH_DATA_SIZE + 1 * END_PATH_DATA_SIZE)
+/* Maximum possible arc path size
+ * is in the rounded arc case:
+ * - 1 move for the path start
+ * - 16 cubics for the arc (5 inner, 5 outer) and corners (3 per corner)
+ * - 1 end for the path end */
+#define ARC_PATH_DATA_MAX_SIZE (1 * MOVE_PATH_DATA_SIZE + 16 * CUBIC_PATH_DATA_SIZE + 1 * END_PATH_DATA_SIZE)
/**********************
* TYPEDEFS
**********************/