refact(binfont): unified font creation API (#5333)
Co-authored-by: pengyiqiang <pengyiqiang@xiaomi.com>
This commit is contained in:
@@ -290,7 +290,7 @@ The built-in symbols are created from the `FontAwesome <https://fontawesome.com/
|
|||||||
Load a font at run-time
|
Load a font at run-time
|
||||||
***********************
|
***********************
|
||||||
|
|
||||||
:cpp:func:`lv_binfont_load` can be used to load a font from a file. The font needs
|
:cpp:func:`lv_binfont_create` can be used to load a font from a file. The font needs
|
||||||
to have a special binary format. (Not TTF or WOFF). Use
|
to have a special binary format. (Not TTF or WOFF). Use
|
||||||
`lv_font_conv <https://github.com/lvgl/lv_font_conv/>`__ with the
|
`lv_font_conv <https://github.com/lvgl/lv_font_conv/>`__ with the
|
||||||
``--format bin`` option to generate an LVGL compatible font file.
|
``--format bin`` option to generate an LVGL compatible font file.
|
||||||
@@ -302,19 +302,18 @@ Example
|
|||||||
|
|
||||||
.. code:: c
|
.. code:: c
|
||||||
|
|
||||||
static lv_font_t my_font;
|
lv_font_t *my_font = lv_binfont_create("X:/path/to/my_font.bin");
|
||||||
lv_result_t res = lv_binfont_load(&my_font, "X:/path/to/my_font.bin");
|
if(my_font == NULL) return;
|
||||||
if(res != LV_RESULT_OK) return;
|
|
||||||
|
|
||||||
/*Use the font*/
|
/*Use the font*/
|
||||||
|
|
||||||
/*Free the font if not required anymore*/
|
/*Free the font if not required anymore*/
|
||||||
lv_font_free(&my_font);
|
lv_binfont_destroy(my_font);
|
||||||
|
|
||||||
Load a font from a memory buffer at run-time
|
Load a font from a memory buffer at run-time
|
||||||
******************************************
|
******************************************
|
||||||
|
|
||||||
:cpp:func:`lv_binfont_load_from_buffer` can be used to load a font from a memory buffer.
|
:cpp:func:`lv_binfont_create_from_buffer` can be used to load a font from a memory buffer.
|
||||||
This function may be useful to load a font from an external file system, which is not
|
This function may be useful to load a font from an external file system, which is not
|
||||||
supported by LVGL. The font needs to be in the same format as if it were loaded from a file.
|
supported by LVGL. The font needs to be in the same format as if it were loaded from a file.
|
||||||
|
|
||||||
@@ -325,7 +324,7 @@ Example
|
|||||||
|
|
||||||
.. code:: c
|
.. code:: c
|
||||||
|
|
||||||
static lv_font_t my_font;
|
lv_font_t *my_font;
|
||||||
uint8_t *buf;
|
uint8_t *buf;
|
||||||
uint32_t bufsize;
|
uint32_t bufsize;
|
||||||
|
|
||||||
@@ -333,12 +332,12 @@ Example
|
|||||||
...
|
...
|
||||||
|
|
||||||
/*Load font from the buffer*/
|
/*Load font from the buffer*/
|
||||||
lv_result_t res = lv_binfont_load_from_buffer(&my_font, (void *)buf, buf));
|
my_font = lv_binfont_create_from_buffer((void *)buf, buf));
|
||||||
if(res != LV_RESULT_OK) return;
|
if(my_font == NULL) return;
|
||||||
/*Use the font*/
|
/*Use the font*/
|
||||||
|
|
||||||
/*Free the font if not required anymore*/
|
/*Free the font if not required anymore*/
|
||||||
lv_font_free(&my_font);
|
lv_binfont_destroy(my_font);
|
||||||
|
|
||||||
Add a new font engine
|
Add a new font engine
|
||||||
*********************
|
*********************
|
||||||
|
|||||||
@@ -78,47 +78,44 @@ static unsigned int read_bits(bit_iterator_t * it, int n_bits, lv_fs_res_t * res
|
|||||||
* GLOBAL FUNCTIONS
|
* GLOBAL FUNCTIONS
|
||||||
**********************/
|
**********************/
|
||||||
|
|
||||||
lv_result_t lv_binfont_load(lv_font_t * font, const char * path)
|
lv_font_t * lv_binfont_create(const char * path)
|
||||||
{
|
{
|
||||||
LV_ASSERT_NULL(font);
|
|
||||||
LV_ASSERT_NULL(path);
|
LV_ASSERT_NULL(path);
|
||||||
|
|
||||||
lv_result_t result = LV_RESULT_INVALID;
|
|
||||||
|
|
||||||
lv_fs_file_t file;
|
lv_fs_file_t file;
|
||||||
lv_fs_res_t fs_res = lv_fs_open(&file, path, LV_FS_MODE_RD);
|
lv_fs_res_t fs_res = lv_fs_open(&file, path, LV_FS_MODE_RD);
|
||||||
if(fs_res != LV_FS_RES_OK) return result;
|
if(fs_res != LV_FS_RES_OK) return NULL;
|
||||||
|
|
||||||
lv_memzero(font, sizeof(lv_font_t));
|
lv_font_t * font = lv_malloc_zeroed(sizeof(lv_font_t));
|
||||||
if(lvgl_load_font(&file, font)) {
|
LV_ASSERT_MALLOC(font);
|
||||||
result = LV_RESULT_OK;
|
|
||||||
}
|
if(!lvgl_load_font(&file, font)) {
|
||||||
else {
|
LV_LOG_WARN("Error loading font file: %s", path);
|
||||||
LV_LOG_WARN("Error loading font file: %s\n", path);
|
|
||||||
/*
|
/*
|
||||||
* When `lvgl_load_font` fails it can leak some pointers.
|
* When `lvgl_load_font` fails it can leak some pointers.
|
||||||
* All non-null pointers can be assumed as allocated and
|
* All non-null pointers can be assumed as allocated and
|
||||||
* `lv_font_free` should free them correctly.
|
* `lv_binfont_destroy` should free them correctly.
|
||||||
*/
|
*/
|
||||||
lv_font_free(font);
|
lv_binfont_destroy(font);
|
||||||
|
font = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
lv_fs_close(&file);
|
lv_fs_close(&file);
|
||||||
|
|
||||||
return result;
|
return font;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if LV_USE_FS_MEMFS
|
#if LV_USE_FS_MEMFS
|
||||||
lv_result_t lv_binfont_load_from_buffer(lv_font_t * font, void * buffer, uint32_t size)
|
lv_font_t * lv_binfont_create_from_buffer(void * buffer, uint32_t size)
|
||||||
{
|
{
|
||||||
lv_fs_path_ex_t mempath;
|
lv_fs_path_ex_t mempath;
|
||||||
|
|
||||||
lv_fs_make_path_from_buffer(&mempath, LV_FS_MEMFS_LETTER, buffer, size);
|
lv_fs_make_path_from_buffer(&mempath, LV_FS_MEMFS_LETTER, buffer, size);
|
||||||
return lv_binfont_load(font, (const char *)&mempath);
|
return lv_binfont_create((const char *)&mempath);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void lv_font_free(lv_font_t * font)
|
void lv_binfont_destroy(lv_font_t * font)
|
||||||
{
|
{
|
||||||
if(font == NULL) return;
|
if(font == NULL) return;
|
||||||
|
|
||||||
@@ -155,6 +152,7 @@ void lv_font_free(lv_font_t * font)
|
|||||||
lv_free((void *)dsc->glyph_bitmap);
|
lv_free((void *)dsc->glyph_bitmap);
|
||||||
lv_free((void *)dsc->glyph_dsc);
|
lv_free((void *)dsc->glyph_dsc);
|
||||||
lv_free((void *)dsc);
|
lv_free((void *)dsc);
|
||||||
|
lv_free(font);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**********************
|
/**********************
|
||||||
@@ -454,9 +452,9 @@ static int32_t load_glyph(lv_fs_file_t * fp, lv_font_fmt_txt_dsc_t * font_dsc,
|
|||||||
* the pointer should be set on the `lv_font_t` data before any possible return.
|
* the pointer should be set on the `lv_font_t` data before any possible return.
|
||||||
*
|
*
|
||||||
* When something fails, it returns `false` and the memory on the `lv_font_t`
|
* When something fails, it returns `false` and the memory on the `lv_font_t`
|
||||||
* still needs to be freed using `lv_font_free`.
|
* still needs to be freed using `lv_binfont_destroy`.
|
||||||
*
|
*
|
||||||
* `lv_font_free` will assume that all non-null pointers are allocated and
|
* `lv_binfont_destroy` will assume that all non-null pointers are allocated and
|
||||||
* should be freed.
|
* should be freed.
|
||||||
*/
|
*/
|
||||||
static bool lvgl_load_font(lv_fs_file_t * fp, lv_font_t * font)
|
static bool lvgl_load_font(lv_fs_file_t * fp, lv_font_t * font)
|
||||||
|
|||||||
@@ -28,29 +28,27 @@ extern "C" {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Loads a `lv_font_t` object from a binary font file
|
* Loads a `lv_font_t` object from a binary font file
|
||||||
* @param font pointer to font where to load
|
|
||||||
* @param path path where the font file is located
|
* @param path path where the font file is located
|
||||||
* @return LV_RESULT_OK on success; LV_RESULT_INVALID on error
|
* @return pointer to font where to load
|
||||||
*/
|
*/
|
||||||
lv_result_t lv_binfont_load(lv_font_t * font, const char * font_name);
|
lv_font_t * lv_binfont_create(const char * font_name);
|
||||||
|
|
||||||
#if LV_USE_FS_MEMFS
|
#if LV_USE_FS_MEMFS
|
||||||
/**
|
/**
|
||||||
* Loads a `lv_font_t` object from a memory buffer containing the binary font file.
|
* Loads a `lv_font_t` object from a memory buffer containing the binary font file.
|
||||||
* Requires LV_USE_FS_MEMFS
|
* Requires LV_USE_FS_MEMFS
|
||||||
* @param font pointer to font where to load
|
|
||||||
* @param buffer address of the font file in the memory
|
* @param buffer address of the font file in the memory
|
||||||
* @param size size of the font file buffer
|
* @param size size of the font file buffer
|
||||||
* @return LV_RESULT_OK on success; LV_RESULT_INVALID on error
|
* @return pointer to font where to load
|
||||||
*/
|
*/
|
||||||
lv_result_t lv_binfont_load_from_buffer(lv_font_t * font, void * buffer, uint32_t size);
|
lv_font_t * lv_binfont_create_from_buffer(void * buffer, uint32_t size);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Frees the memory allocated by the `lv_binfont_load()` function
|
* Frees the memory allocated by the `lv_binfont_create()` function
|
||||||
* @param font lv_font_t object created by the lv_binfont_load function
|
* @param font lv_font_t object created by the lv_binfont_create function
|
||||||
*/
|
*/
|
||||||
void lv_font_free(lv_font_t * font);
|
void lv_binfont_destroy(lv_font_t * font);
|
||||||
|
|
||||||
/**********************
|
/**********************
|
||||||
* MACROS
|
* MACROS
|
||||||
|
|||||||
@@ -33,7 +33,7 @@
|
|||||||
*
|
*
|
||||||
* The path object can be used at any place where a file path is required, e.g.:
|
* The path object can be used at any place where a file path is required, e.g.:
|
||||||
*
|
*
|
||||||
* lv_font_t* my_font = lv_binfont_load((const char *) & mempath);
|
* lv_font_t* my_font = lv_binfont_create((const char *) & mempath);
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|||||||
@@ -51,9 +51,9 @@ extern uint8_t const font_1_buf[6876];
|
|||||||
extern uint8_t const font_2_buf[7252];
|
extern uint8_t const font_2_buf[7252];
|
||||||
extern uint8_t const font_3_buf[4892];
|
extern uint8_t const font_3_buf[4892];
|
||||||
|
|
||||||
static lv_font_t font_1_bin;
|
static lv_font_t * font_1_bin = NULL;
|
||||||
static lv_font_t font_2_bin;
|
static lv_font_t * font_2_bin = NULL;
|
||||||
static lv_font_t font_3_bin;
|
static lv_font_t * font_3_bin = NULL;
|
||||||
|
|
||||||
void setUp(void)
|
void setUp(void)
|
||||||
{
|
{
|
||||||
@@ -68,9 +68,9 @@ void tearDown(void)
|
|||||||
|
|
||||||
static void common(void)
|
static void common(void)
|
||||||
{
|
{
|
||||||
compare_fonts(&font_1, &font_1_bin);
|
compare_fonts(&font_1, font_1_bin);
|
||||||
compare_fonts(&font_2, &font_2_bin);
|
compare_fonts(&font_2, font_2_bin);
|
||||||
compare_fonts(&font_3, &font_3_bin);
|
compare_fonts(&font_3, font_3_bin);
|
||||||
|
|
||||||
/* create labels for testing */
|
/* create labels for testing */
|
||||||
lv_obj_t * scr = lv_screen_active();
|
lv_obj_t * scr = lv_screen_active();
|
||||||
@@ -82,34 +82,33 @@ static void common(void)
|
|||||||
lv_obj_set_flex_align(scr, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER);
|
lv_obj_set_flex_align(scr, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER);
|
||||||
|
|
||||||
lv_label_set_text(label1, "The quick brown fox jumped over the lazy dog");
|
lv_label_set_text(label1, "The quick brown fox jumped over the lazy dog");
|
||||||
lv_obj_set_style_text_font(label1, &font_1_bin, 0);
|
lv_obj_set_style_text_font(label1, font_1_bin, 0);
|
||||||
lv_label_set_text(label2, "The quick brown fox jumped over the lazy dog");
|
lv_label_set_text(label2, "The quick brown fox jumped over the lazy dog");
|
||||||
lv_obj_set_style_text_font(label2, &font_2_bin, 0);
|
lv_obj_set_style_text_font(label2, font_2_bin, 0);
|
||||||
lv_label_set_text(label3, "The quick brown fox jumped over the lazy dog");
|
lv_label_set_text(label3, "The quick brown fox jumped over the lazy dog");
|
||||||
lv_obj_set_style_text_font(label3, &font_3_bin, 0);
|
lv_obj_set_style_text_font(label3, font_3_bin, 0);
|
||||||
|
|
||||||
TEST_ASSERT_EQUAL_SCREENSHOT("font_loader_1.png");
|
TEST_ASSERT_EQUAL_SCREENSHOT("font_loader_1.png");
|
||||||
|
|
||||||
lv_obj_clean(lv_screen_active());
|
lv_obj_clean(lv_screen_active());
|
||||||
|
|
||||||
lv_font_free(&font_1_bin);
|
lv_binfont_destroy(font_1_bin);
|
||||||
lv_font_free(&font_2_bin);
|
lv_binfont_destroy(font_2_bin);
|
||||||
lv_font_free(&font_3_bin);
|
lv_binfont_destroy(font_3_bin);
|
||||||
}
|
}
|
||||||
|
|
||||||
void test_font_loader_with_cache(void)
|
void test_font_loader_with_cache(void)
|
||||||
{
|
{
|
||||||
/*Test with cache ('A' has cache)*/
|
/*Test with cache ('A' has cache)*/
|
||||||
lv_result_t res;
|
|
||||||
|
|
||||||
res = lv_binfont_load(&font_1_bin, "A:src/test_assets/font_1.fnt");
|
font_1_bin = lv_binfont_create("A:src/test_assets/font_1.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_1_bin);
|
||||||
|
|
||||||
res = lv_binfont_load(&font_2_bin, "A:src/test_assets/font_2.fnt");
|
font_2_bin = lv_binfont_create("A:src/test_assets/font_2.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_2_bin);
|
||||||
|
|
||||||
res = lv_binfont_load(&font_3_bin, "A:src/test_assets/font_3.fnt");
|
font_3_bin = lv_binfont_create("A:src/test_assets/font_3.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_3_bin);
|
||||||
|
|
||||||
common();
|
common();
|
||||||
}
|
}
|
||||||
@@ -117,16 +116,15 @@ void test_font_loader_with_cache(void)
|
|||||||
void test_font_loader_no_cache(void)
|
void test_font_loader_no_cache(void)
|
||||||
{
|
{
|
||||||
/*Test without cache ('B' has NO cache)*/
|
/*Test without cache ('B' has NO cache)*/
|
||||||
lv_result_t res;
|
|
||||||
|
|
||||||
res = lv_binfont_load(&font_1_bin, "B:src/test_assets/font_1.fnt");
|
font_1_bin = lv_binfont_create("B:src/test_assets/font_1.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_1_bin);
|
||||||
|
|
||||||
res = lv_binfont_load(&font_2_bin, "B:src/test_assets/font_2.fnt");
|
font_2_bin = lv_binfont_create("B:src/test_assets/font_2.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_2_bin);
|
||||||
|
|
||||||
res = lv_binfont_load(&font_3_bin, "B:src/test_assets/font_3.fnt");
|
font_3_bin = lv_binfont_create("B:src/test_assets/font_3.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_3_bin);
|
||||||
|
|
||||||
common();
|
common();
|
||||||
}
|
}
|
||||||
@@ -134,16 +132,15 @@ void test_font_loader_no_cache(void)
|
|||||||
void test_font_loader_from_buffer(void)
|
void test_font_loader_from_buffer(void)
|
||||||
{
|
{
|
||||||
/*Test with memfs*/
|
/*Test with memfs*/
|
||||||
lv_result_t res;
|
|
||||||
|
|
||||||
res = lv_binfont_load_from_buffer(&font_1_bin, (void *)&font_1_buf, sizeof(font_1_buf));
|
font_1_bin = lv_binfont_create_from_buffer((void *)&font_1_buf, sizeof(font_1_buf));
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_1_bin);
|
||||||
|
|
||||||
res = lv_binfont_load_from_buffer(&font_2_bin, (void *)&font_2_buf, sizeof(font_2_buf));
|
font_2_bin = lv_binfont_create_from_buffer((void *)&font_2_buf, sizeof(font_2_buf));
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_2_bin);
|
||||||
|
|
||||||
res = lv_binfont_load_from_buffer(&font_3_bin, (void *)&font_3_buf, sizeof(font_3_buf));
|
font_3_bin = lv_binfont_create_from_buffer((void *)&font_3_buf, sizeof(font_3_buf));
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font_3_bin);
|
||||||
|
|
||||||
common();
|
common();
|
||||||
}
|
}
|
||||||
@@ -156,19 +153,21 @@ void test_font_loader_reload(void)
|
|||||||
lv_obj_center(label);
|
lv_obj_center(label);
|
||||||
lv_label_set_text(label, "The quick brown fox jumped over the lazy dog");
|
lv_label_set_text(label, "The quick brown fox jumped over the lazy dog");
|
||||||
|
|
||||||
lv_font_t font;
|
lv_font_t style_font;
|
||||||
lv_result_t res;
|
lv_font_t * font;
|
||||||
res = lv_binfont_load(&font, "A:src/test_assets/font_2.fnt");
|
font = lv_binfont_create("A:src/test_assets/font_2.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font);
|
||||||
|
lv_memcpy(&style_font, font, sizeof(lv_font_t));
|
||||||
|
|
||||||
lv_obj_set_style_text_font(label, &font, 0);
|
lv_obj_set_style_text_font(label, &style_font, 0);
|
||||||
|
|
||||||
TEST_ASSERT_EQUAL_SCREENSHOT("font_loader_2.png");
|
TEST_ASSERT_EQUAL_SCREENSHOT("font_loader_2.png");
|
||||||
|
|
||||||
lv_font_free(&font);
|
lv_binfont_destroy(font);
|
||||||
|
|
||||||
res = lv_binfont_load(&font, "A:src/test_assets/font_3.fnt");
|
font = lv_binfont_create("A:src/test_assets/font_3.fnt");
|
||||||
TEST_ASSERT_EQUAL(LV_RESULT_OK, res);
|
TEST_ASSERT_NOT_NULL(font);
|
||||||
|
lv_memcpy(&style_font, font, sizeof(lv_font_t));
|
||||||
|
|
||||||
lv_obj_report_style_change(NULL);
|
lv_obj_report_style_change(NULL);
|
||||||
|
|
||||||
@@ -176,7 +175,7 @@ void test_font_loader_reload(void)
|
|||||||
|
|
||||||
lv_obj_delete(label);
|
lv_obj_delete(label);
|
||||||
|
|
||||||
lv_font_free(&font);
|
lv_binfont_destroy(font);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int compare_fonts(lv_font_t * f1, lv_font_t * f2)
|
static int compare_fonts(lv_font_t * f1, lv_font_t * f2)
|
||||||
|
|||||||
Reference in New Issue
Block a user