mirror of
https://github.com/lvgl/lvgl.git
synced 2025-01-28 07:03:00 +08:00
feat(draw): add layer memory allocation config support (#7038)
Co-authored-by: Gabor Kiss-Vamosi <kisvegabor@gmail.com> Co-authored-by: liamHowatt <liamjmh0@gmail.com> Co-authored-by: Liam <30486941+liamHowatt@users.noreply.github.com>
This commit is contained in:
parent
c022f0896a
commit
a7adce9d1a
9
Kconfig
9
Kconfig
@ -202,6 +202,15 @@ menu "LVGL configuration"
|
|||||||
it is buffered into a "simple" layer before rendering. The widget can be buffered in smaller chunks.
|
it is buffered into a "simple" layer before rendering. The widget can be buffered in smaller chunks.
|
||||||
"Transformed layers" (if `transform_angle/zoom` are set) use larger buffers and can't be drawn in chunks.
|
"Transformed layers" (if `transform_angle/zoom` are set) use larger buffers and can't be drawn in chunks.
|
||||||
|
|
||||||
|
config LV_DRAW_LAYER_MAX_MEMORY
|
||||||
|
int "The maximum amount of memory that can be used for layers"
|
||||||
|
default 0
|
||||||
|
help
|
||||||
|
Limit the max allocated memory for simple and transformed layers.
|
||||||
|
It should be at least `LV_DRAW_LAYER_SIMPLE_BUF_SIZE` sized but if transformed layers are also used
|
||||||
|
it should be enough to store the largest widget too (width x height x 4 area).
|
||||||
|
Set it to 0 to have no limit.
|
||||||
|
|
||||||
config LV_DRAW_THREAD_STACK_SIZE
|
config LV_DRAW_THREAD_STACK_SIZE
|
||||||
int "Stack size of draw thread in bytes"
|
int "Stack size of draw thread in bytes"
|
||||||
default 8192
|
default 8192
|
||||||
|
@ -144,6 +144,12 @@
|
|||||||
/** The target buffer size for simple layer chunks. */
|
/** The target buffer size for simple layer chunks. */
|
||||||
#define LV_DRAW_LAYER_SIMPLE_BUF_SIZE (24 * 1024) /**< [bytes]*/
|
#define LV_DRAW_LAYER_SIMPLE_BUF_SIZE (24 * 1024) /**< [bytes]*/
|
||||||
|
|
||||||
|
/* Limit the max allocated memory for simple and transformed layers.
|
||||||
|
* It should be at least `LV_DRAW_LAYER_SIMPLE_BUF_SIZE` sized but if transformed layers are also used
|
||||||
|
* it should be enough to store the largest widget too (width x height x 4 area).
|
||||||
|
* Set it to 0 to have no limit. */
|
||||||
|
#define LV_DRAW_LAYER_MAX_MEMORY 0 /**< No limit by default [bytes]*/
|
||||||
|
|
||||||
/** Stack size of drawing thread.
|
/** Stack size of drawing thread.
|
||||||
* NOTE: If FreeType or ThorVG is enabled, it is recommended to set it to 32KB or more.
|
* NOTE: If FreeType or ThorVG is enabled, it is recommended to set it to 32KB or more.
|
||||||
*/
|
*/
|
||||||
|
@ -36,7 +36,7 @@ static void lv_cleanup_task(lv_draw_task_t * t, lv_display_t * disp);
|
|||||||
|
|
||||||
static inline uint32_t get_layer_size_kb(uint32_t size_byte)
|
static inline uint32_t get_layer_size_kb(uint32_t size_byte)
|
||||||
{
|
{
|
||||||
return size_byte < 1024 ? 1 : size_byte >> 10;
|
return (size_byte + 1023) >> 10;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**********************
|
/**********************
|
||||||
@ -448,6 +448,15 @@ void * lv_draw_layer_alloc_buf(lv_layer_t * layer)
|
|||||||
int32_t h = lv_area_get_height(&layer->buf_area);
|
int32_t h = lv_area_get_height(&layer->buf_area);
|
||||||
uint32_t layer_size_byte = h * lv_draw_buf_width_to_stride(w, layer->color_format);
|
uint32_t layer_size_byte = h * lv_draw_buf_width_to_stride(w, layer->color_format);
|
||||||
|
|
||||||
|
#if LV_DRAW_LAYER_MAX_MEMORY > 0
|
||||||
|
/* Do not allocate the layer if the sum of allocated layer sizes
|
||||||
|
* will exceed `LV_DRAW_LAYER_MAX_MEMORY` */
|
||||||
|
if((_draw_info.used_memory_for_layers + layer_size_byte) > LV_DRAW_LAYER_MAX_MEMORY) {
|
||||||
|
LV_LOG_WARN("LV_DRAW_LAYER_MAX_MEMORY was reached when allocating the layer.");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
layer->draw_buf = lv_draw_buf_create(w, h, layer->color_format, 0);
|
layer->draw_buf = lv_draw_buf_create(w, h, layer->color_format, 0);
|
||||||
|
|
||||||
if(layer->draw_buf == NULL) {
|
if(layer->draw_buf == NULL) {
|
||||||
@ -456,8 +465,8 @@ void * lv_draw_layer_alloc_buf(lv_layer_t * layer)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
_draw_info.used_memory_for_layers_kb += get_layer_size_kb(layer_size_byte);
|
_draw_info.used_memory_for_layers += layer_size_byte;
|
||||||
LV_LOG_INFO("Layer memory used: %" LV_PRIu32 " kB\n", _draw_info.used_memory_for_layers_kb);
|
LV_LOG_INFO("Layer memory used: %" LV_PRIu32 " kB", get_layer_size_kb(_draw_info.used_memory_for_layers));
|
||||||
|
|
||||||
if(lv_color_format_has_alpha(layer->color_format)) {
|
if(lv_color_format_has_alpha(layer->color_format)) {
|
||||||
lv_draw_buf_clear(layer->draw_buf, NULL);
|
lv_draw_buf_clear(layer->draw_buf, NULL);
|
||||||
@ -535,8 +544,14 @@ static void lv_cleanup_task(lv_draw_task_t * t, lv_display_t * disp)
|
|||||||
int32_t h = lv_area_get_height(&layer_drawn->buf_area);
|
int32_t h = lv_area_get_height(&layer_drawn->buf_area);
|
||||||
uint32_t layer_size_byte = h * layer_drawn->draw_buf->header.stride;
|
uint32_t layer_size_byte = h * layer_drawn->draw_buf->header.stride;
|
||||||
|
|
||||||
_draw_info.used_memory_for_layers_kb -= get_layer_size_kb(layer_size_byte);
|
if(_draw_info.used_memory_for_layers >= layer_size_byte) {
|
||||||
LV_LOG_INFO("Layer memory used: %" LV_PRIu32 " kB\n", _draw_info.used_memory_for_layers_kb);
|
_draw_info.used_memory_for_layers -= layer_size_byte;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
_draw_info.used_memory_for_layers = 0;
|
||||||
|
LV_LOG_WARN("More layers were freed than allocated");
|
||||||
|
}
|
||||||
|
LV_LOG_INFO("Layer memory used: %" LV_PRIu32 " kB", get_layer_size_kb(_draw_info.used_memory_for_layers));
|
||||||
lv_draw_buf_destroy(layer_drawn->draw_buf);
|
lv_draw_buf_destroy(layer_drawn->draw_buf);
|
||||||
layer_drawn->draw_buf = NULL;
|
layer_drawn->draw_buf = NULL;
|
||||||
}
|
}
|
||||||
|
@ -178,7 +178,7 @@ struct _lv_draw_unit_t {
|
|||||||
typedef struct {
|
typedef struct {
|
||||||
lv_draw_unit_t * unit_head;
|
lv_draw_unit_t * unit_head;
|
||||||
uint32_t unit_cnt;
|
uint32_t unit_cnt;
|
||||||
uint32_t used_memory_for_layers_kb;
|
uint32_t used_memory_for_layers; /* measured as bytes */
|
||||||
#if LV_USE_OS
|
#if LV_USE_OS
|
||||||
lv_thread_sync_t sync;
|
lv_thread_sync_t sync;
|
||||||
#else
|
#else
|
||||||
|
@ -352,6 +352,18 @@
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Limit the max allocated memory for simple and transformed layers.
|
||||||
|
* It should be at least `LV_DRAW_LAYER_SIMPLE_BUF_SIZE` sized but if transformed layers are also used
|
||||||
|
* it should be enough to store the largest widget too (width x height x 4 area).
|
||||||
|
* Set it to 0 to have no limit. */
|
||||||
|
#ifndef LV_DRAW_LAYER_MAX_MEMORY
|
||||||
|
#ifdef CONFIG_LV_DRAW_LAYER_MAX_MEMORY
|
||||||
|
#define LV_DRAW_LAYER_MAX_MEMORY CONFIG_LV_DRAW_LAYER_MAX_MEMORY
|
||||||
|
#else
|
||||||
|
#define LV_DRAW_LAYER_MAX_MEMORY 0 /**< No limit by default [bytes]*/
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
/** Stack size of drawing thread.
|
/** Stack size of drawing thread.
|
||||||
* NOTE: If FreeType or ThorVG is enabled, it is recommended to set it to 32KB or more.
|
* NOTE: If FreeType or ThorVG is enabled, it is recommended to set it to 32KB or more.
|
||||||
*/
|
*/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user