feat(image_decoder): add webp decoder (#9175)
Arduino Lint / lint (push) Has been cancelled
Build Examples with C++ Compiler / build-examples (push) Has been cancelled
MicroPython CI / Build esp32 port (push) Has been cancelled
MicroPython CI / Build rp2 port (push) Has been cancelled
MicroPython CI / Build stm32 port (push) Has been cancelled
MicroPython CI / Build unix port (push) Has been cancelled
C/C++ CI / Build OPTIONS_16BIT - Ubuntu (push) Has been cancelled
C/C++ CI / Build OPTIONS_24BIT - Ubuntu (push) Has been cancelled
C/C++ CI / Build OPTIONS_FULL_32BIT - Ubuntu (push) Has been cancelled
C/C++ CI / Build OPTIONS_NORMAL_8BIT - Ubuntu (push) Has been cancelled
C/C++ CI / Build OPTIONS_SDL - Ubuntu (push) Has been cancelled
C/C++ CI / Build OPTIONS_16BIT - cl - Windows (push) Has been cancelled
C/C++ CI / Build OPTIONS_16BIT - gcc - Windows (push) Has been cancelled
C/C++ CI / Build OPTIONS_24BIT - cl - Windows (push) Has been cancelled
C/C++ CI / Build OPTIONS_24BIT - gcc - Windows (push) Has been cancelled
C/C++ CI / Build OPTIONS_FULL_32BIT - cl - Windows (push) Has been cancelled
C/C++ CI / Build OPTIONS_FULL_32BIT - gcc - Windows (push) Has been cancelled
C/C++ CI / Build ESP IDF ESP32S3 (push) Has been cancelled
C/C++ CI / Run tests with 32bit build (push) Has been cancelled
C/C++ CI / Run tests with 64bit build (push) Has been cancelled
BOM Check / bom-check (push) Has been cancelled
Verify that lv_conf_internal.h matches repository state / verify-conf-internal (push) Has been cancelled
Verify the widget property name / verify-property-name (push) Has been cancelled
Verify code formatting / verify-formatting (push) Has been cancelled
Compare file templates with file names / template-check (push) Has been cancelled
Build docs / build-and-deploy (push) Has been cancelled
Test API JSON generator / Test API JSON (push) Has been cancelled
Install LVGL using CMake / build-examples (push) Has been cancelled
Check Makefile / Build using Makefile (push) Has been cancelled
Check Makefile for UEFI / Build using Makefile for UEFI (push) Has been cancelled
Emulated Performance Test / ARM Emulated Benchmark - Script Check (scripts/perf/tests/benchmark_results_comment/test.sh) (push) Has been cancelled
Emulated Performance Test / ARM Emulated Benchmark - Script Check (scripts/perf/tests/filter_docker_logs/test.sh) (push) Has been cancelled
Emulated Performance Test / ARM Emulated Benchmark - Script Check (scripts/perf/tests/serialize_results/test.sh) (push) Has been cancelled
Emulated Performance Test / ARM Emulated Benchmark 32b - lv_conf_perf32b (push) Has been cancelled
Emulated Performance Test / ARM Emulated Benchmark 64b - lv_conf_perf64b (push) Has been cancelled
Emulated Performance Test / ARM Emulated Benchmark - Save PR Number (push) Has been cancelled
Hardware Performance Test / Hardware Performance Benchmark (push) Has been cancelled
Hardware Performance Test / HW Benchmark - Save PR Number (push) Has been cancelled
Performance Tests CI / Perf Tests OPTIONS_TEST_PERF_32B - Ubuntu (push) Has been cancelled
Performance Tests CI / Perf Tests OPTIONS_TEST_PERF_64B - Ubuntu (push) Has been cancelled
Port repo release update / run-release-branch-updater (push) Has been cancelled
Verify Font License / verify-font-license (push) Has been cancelled
Verify Kconfig / verify-kconfig (push) Has been cancelled

Signed-off-by: rongyichang <rongyichang@xiaomi.com>
This commit is contained in:
terry.rong
2025-11-06 18:38:42 +08:00
committed by GitHub
parent cae6123799
commit 830c0b9319
27 changed files with 549 additions and 0 deletions
+3
View File
@@ -1433,6 +1433,9 @@ menu "LVGL configuration"
config LV_USE_LIBJPEG_TURBO config LV_USE_LIBJPEG_TURBO
bool "libjpeg-turbo decoder library" bool "libjpeg-turbo decoder library"
config LV_USE_LIBWEBP
bool "WebP decoder library"
config LV_USE_GIF config LV_USE_GIF
bool "GIF decoder library" bool "GIF decoder library"
+1
View File
@@ -549,6 +549,7 @@ redirects = {
"libs/libjpeg_turbo": "../details/libs/libjpeg_turbo.html" , "libs/libjpeg_turbo": "../details/libs/libjpeg_turbo.html" ,
"libs/libpng": "../details/libs/libpng.html" , "libs/libpng": "../details/libs/libpng.html" ,
"libs/lodepng": "../details/libs/lodepng.html" , "libs/lodepng": "../details/libs/lodepng.html" ,
"libs/libwebp": "../details/libs/libwebp.html" ,
"libs/qrcode": "../details/libs/qrcode.html" , "libs/qrcode": "../details/libs/qrcode.html" ,
"libs/rle": "../details/libs/rle.html" , "libs/rle": "../details/libs/rle.html" ,
"libs/rlottie": "../details/libs/rlottie.html" , "libs/rlottie": "../details/libs/rlottie.html" ,
@@ -13,6 +13,7 @@ Image Support
libjpeg_turbo libjpeg_turbo
libpng libpng
lodepng lodepng
libwebp
rle rle
rlottie rlottie
svg svg
@@ -0,0 +1,70 @@
.. _libwebp:
=================
WebP Decoder
=================
**libwebp** is an LVGL interface to the WebP image format --- a modern image format that provides superior lossless and lossy compression for images on the web. WebP offers:
- Smaller file sizes compared to JPEG and PNG
- Lossy compression with transparency
- Lossless compression
- Animation support (not yet supported in the LVGL integration)
For more information, see: https://developers.google.com/speed/webp
Library source: https://github.com/webmproject/libwebp
.. _libwebp_install:
Install
*******
.. code-block:: bash
# Linux
sudo apt install libwebp-dev
# macOS
brew install webp
.. _libwebp_integration:
Adding libwebp to Your Project
******************************
CMake configuration:
.. code-block:: cmake
find_package(PkgConfig REQUIRED)
pkg_check_modules(WebP REQUIRED libwebp)
include_directories(${WebP_INCLUDEDIR})
target_link_libraries(main ${WebP_LINK_LIBRARIES})
.. _libwebp_usage:
Usage
*****
Set :c:macro:`LV_USE_LIBWEBP` in ``lv_conf.h`` to ``1``.
Memory requirements for WebP images:
- Lossy WebP: width × height × 4 bytes (ARGB8888 format)
- Lossless WebP: width × height × 4 bytes (ARGB8888 format)
For optimal memory usage, combine with LVGL's :ref:`overview_image_caching` feature.
.. _libwebp_example:
Example
*******
.. include:: ../../../examples/libs/libwebp/index.rst
.. _libwebp_api:
API
***
.. API startswith: lv_libwebp_
+1
View File
@@ -125,6 +125,7 @@ Make sure `LV_MEM_SIZE` is no less than `(128*1024U)`.
- \#define LV_USE_RLE 0 - \#define LV_USE_RLE 0
- \#define LV_USE_TJPGD 0 - \#define LV_USE_TJPGD 0
- \#define LV_USE_LIBJPEG_TURBO 0 - \#define LV_USE_LIBJPEG_TURBO 0
- \#define LV_USE_LIBWEBP 0
- \#define LV_USE_GIF 0 - \#define LV_USE_GIF 0
- \#define LV_USE_BARCODE 0 - \#define LV_USE_BARCODE 0
- \#define LV_USE_QRCODE 0 - \#define LV_USE_QRCODE 0
+6
View File
@@ -0,0 +1,6 @@
Open a WEBP image from file and variable
----------------------------------------
.. lv_example:: libs/libwebp/lv_example_libwebp_1
:language: c
@@ -0,0 +1,38 @@
/**
* @file lv_example_libwebp.h
*
*/
#ifndef LV_EXAMPLE_LIBWEBP_H
#define LV_EXAMPLE_LIBWEBP_H
#ifdef __cplusplus
extern "C" {
#endif
/*********************
* INCLUDES
*********************/
/*********************
* DEFINES
*********************/
/**********************
* TYPEDEFS
**********************/
/**********************
* GLOBAL PROTOTYPES
**********************/
void lv_example_libwebp_1(void);
/**********************
* MACROS
**********************/
#ifdef __cplusplus
} /*extern "C"*/
#endif
#endif /*LV_EXAMPLE_LIBWEBP_H*/
@@ -0,0 +1,31 @@
#include "../../lv_examples.h"
#if LV_BUILD_EXAMPLES
#if LV_USE_LIBWEBP
/**
* Load a WEBP image
*/
void lv_example_libwebp_1(void)
{
lv_obj_t * img;
img = lv_image_create(lv_screen_active());
/* Assuming a File system is attached to letter 'A'
* E.g. set LV_USE_FS_STDIO 'A' in lv_conf.h */
lv_image_set_src(img, "A:lvgl/examples/libs/libwebp/rose.webp");
lv_obj_center(img);
}
#else
void lv_example_libwebp_1(void)
{
lv_obj_t * label = lv_label_create(lv_screen_active());
lv_label_set_text(label, "Libwebp is not installed");
lv_obj_center(label);
}
#endif
#endif
Binary file not shown.

After

Width:  |  Height:  |  Size: 18 KiB

+1
View File
@@ -26,6 +26,7 @@ extern "C" {
#include "rlottie/lv_example_rlottie.h" #include "rlottie/lv_example_rlottie.h"
#include "tjpgd/lv_example_tjpgd.h" #include "tjpgd/lv_example_tjpgd.h"
#include "libjpeg_turbo/lv_example_libjpeg_turbo.h" #include "libjpeg_turbo/lv_example_libjpeg_turbo.h"
#include "libwebp/lv_example_libwebp.h"
#include "tiny_ttf/lv_example_tiny_ttf.h" #include "tiny_ttf/lv_example_tiny_ttf.h"
#include "svg/lv_example_svg.h" #include "svg/lv_example_svg.h"
+3
View File
@@ -948,6 +948,9 @@
* - Supports complete JPEG specifications and high-performance JPEG decoding. */ * - Supports complete JPEG specifications and high-performance JPEG decoding. */
#define LV_USE_LIBJPEG_TURBO 0 #define LV_USE_LIBJPEG_TURBO 0
/** WebP decoder library */
#define LV_USE_LIBWEBP 0
/** GIF decoder library */ /** GIF decoder library */
#define LV_USE_GIF 0 #define LV_USE_GIF 0
#if LV_USE_GIF #if LV_USE_GIF
+1
View File
@@ -109,6 +109,7 @@ extern "C" {
#include "src/libs/fsdrv/lv_fsdrv.h" #include "src/libs/fsdrv/lv_fsdrv.h"
#include "src/libs/lodepng/lv_lodepng.h" #include "src/libs/lodepng/lv_lodepng.h"
#include "src/libs/libpng/lv_libpng.h" #include "src/libs/libpng/lv_libpng.h"
#include "src/libs/libwebp/lv_libwebp.h"
#include "src/libs/gltf/gltf_data/lv_gltf_model.h" #include "src/libs/gltf/gltf_data/lv_gltf_model.h"
#include "src/libs/gltf/gltf_view/lv_gltf.h" #include "src/libs/gltf/gltf_view/lv_gltf.h"
#include "src/libs/gif/lv_gif.h" #include "src/libs/gif/lv_gif.h"
+1
View File
@@ -64,6 +64,7 @@ def run(output_path, lv_conf_file, output_to_stdout, target_header, filter_priva
'LV_USE_BMP', 'LV_USE_BMP',
'LV_USE_TJPGD', 'LV_USE_TJPGD',
'LV_USE_LIBJPEG_TURBO', 'LV_USE_LIBJPEG_TURBO',
'LV_USE_LIBWEBP',
'LV_USE_GIF', 'LV_USE_GIF',
'LV_BIN_DECODER_RAM_LOAD', 'LV_BIN_DECODER_RAM_LOAD',
'LV_USE_RLE', 'LV_USE_RLE',
+2
View File
@@ -5,12 +5,14 @@ g++-multilib
ninja-build ninja-build
libpng-dev libpng-dev
libjpeg-turbo8-dev libjpeg-turbo8-dev
libwebp-dev
libfreetype-dev libfreetype-dev
libglew-dev libglew-dev
libglfw3-dev libglfw3-dev
libsdl2-dev libsdl2-dev
libpng-dev:i386 libpng-dev:i386
libjpeg-dev:i386 libjpeg-dev:i386
libwebp-dev:i386
libfreetype-dev:i386 libfreetype-dev:i386
libsdl2-dev:i386 libsdl2-dev:i386
ruby-full ruby-full
+240
View File
@@ -0,0 +1,240 @@
/**
* @file lv_libwebp.c
*
*/
/*********************
* INCLUDES
*********************/
#include "../../draw/lv_image_decoder_private.h"
#include "../../../lvgl.h"
#if LV_USE_LIBWEBP
#include "lv_libwebp.h"
#include <webp/decode.h>
#include "../../core/lv_global.h"
/*********************
* DEFINES
*********************/
#define DECODER_NAME "LIBWEBP"
#define image_cache_draw_buf_handlers &(LV_GLOBAL_DEFAULT()->image_cache_draw_buf_handlers)
#define WEBP_HEADER_SIZE 64
/**********************
* TYPEDEFS
**********************/
/**********************
* STATIC PROTOTYPES
**********************/
static lv_result_t decoder_info(lv_image_decoder_t * decoder, lv_image_decoder_dsc_t * dsc, lv_image_header_t * header);
static lv_result_t decoder_open(lv_image_decoder_t * decoder, lv_image_decoder_dsc_t * dsc);
static void decoder_close(lv_image_decoder_t * decoder, lv_image_decoder_dsc_t * dsc);
static lv_draw_buf_t * decode_webp_file(lv_image_decoder_dsc_t * dsc, const char * filename);
/**********************
* STATIC VARIABLES
**********************/
/**********************
* MACROS
**********************/
/**********************
* GLOBAL FUNCTIONS
**********************/
/**
* Register the WEBP decoder functions in LVGL
*/
void lv_libwebp_init(void)
{
lv_image_decoder_t * dec = lv_image_decoder_create();
lv_image_decoder_set_info_cb(dec, decoder_info);
lv_image_decoder_set_open_cb(dec, decoder_open);
lv_image_decoder_set_close_cb(dec, decoder_close);
dec->name = DECODER_NAME;
}
void lv_libwebp_deinit(void)
{
lv_image_decoder_t * dec = NULL;
while((dec = lv_image_decoder_get_next(dec)) != NULL) {
if(dec->info_cb == decoder_info) {
lv_image_decoder_delete(dec);
break;
}
}
}
/**********************
* STATIC FUNCTIONS
**********************/
/**
* Get info about a WEBP image
* @param dsc can be file name or pointer to a C array
* @param header store the info here
* @return LV_RESULT_OK: no error; LV_RESULT_INVALID: can't get the info
*/
static lv_result_t decoder_info(lv_image_decoder_t * decoder, lv_image_decoder_dsc_t * dsc, lv_image_header_t * header)
{
LV_UNUSED(decoder); /*Unused*/
lv_image_src_t src_type = dsc->src_type; /*Get the source type*/
/*If it's a webp file...*/
if(src_type == LV_IMAGE_SRC_FILE) {
uint8_t buf[WEBP_HEADER_SIZE];
int width;
int height;
uint32_t rn;
lv_fs_res_t res = lv_fs_read(&dsc->file, buf, sizeof(buf), &rn);
/* The max header size = RIFF + VP8X + (optional chunks) + VP8(L), 64 bytes is enough to get the width and height.
* If the file is smaller than 64 bytes, it's maybe a valid webp file,
* so we don't check the result length here.
* VP8X : RIFF(12) + VP8X(18) = 30bytes;
* VP8(L): RIFF(12) + VP8(L) chunk header(8) + VP8(L) frame header(5) = 23bytes;
* VP8: RIFF(12) + VP8(L) chunk header(8) + VP8(L) frame header(10) = 28bytes;
*/
if(res != LV_FS_RES_OK) return LV_RESULT_INVALID;
if(WebPGetInfo(buf, rn, &width, &height) == 0) {
return LV_RESULT_INVALID;
}
/*Default decoder color format is ARGB8888*/
header->cf = LV_COLOR_FORMAT_ARGB8888;
header->w = width;
header->h = height;
header->stride = width * sizeof(lv_color32_t);
return LV_RESULT_OK;
}
return LV_RESULT_INVALID; /*If it didn't succeed earlier then it's an error*/
}
/**
* Open a WEBP image and return the decoded image
* @param decoder pointer to the decoder
* @param dsc pointer to the decoder descriptor
* @return LV_RESULT_OK: no error; LV_RESULT_INVALID: can't open the image
*/
static lv_result_t decoder_open(lv_image_decoder_t * decoder, lv_image_decoder_dsc_t * dsc)
{
LV_UNUSED(decoder); /*Unused*/
/*If it's a webp file...*/
if(dsc->src_type == LV_IMAGE_SRC_FILE) {
const char * fn = dsc->src;
lv_draw_buf_t * decoded = decode_webp_file(dsc, fn);
if(decoded == NULL) {
return LV_RESULT_INVALID;
}
lv_draw_buf_t * adjusted = lv_image_decoder_post_process(dsc, decoded);
if(adjusted == NULL) {
lv_draw_buf_destroy(decoded);
return LV_RESULT_INVALID;
}
/*The adjusted draw buffer is newly allocated.*/
if(adjusted != decoded) {
lv_draw_buf_destroy(decoded);
decoded = adjusted;
}
dsc->decoded = decoded;
if(dsc->args.no_cache) {
return LV_RESULT_OK;
}
/*If the image cache is disabled, just return the decoded image*/
if(!lv_image_cache_is_enabled()) {
return LV_RESULT_OK;
}
lv_image_cache_data_t search_key;
search_key.src_type = dsc->src_type;
search_key.src = dsc->src;
search_key.slot.size = decoded->data_size;
lv_cache_entry_t * entry = lv_image_decoder_add_to_cache(decoder, &search_key, decoded, NULL);
if(entry == NULL) {
lv_draw_buf_destroy(decoded);
return LV_RESULT_INVALID;
}
dsc->cache_entry = entry;
return LV_RESULT_OK; /*The image is fully decoded. Return with its pointer*/
}
return LV_RESULT_INVALID; /*If not returned earlier then it failed*/
}
/**
* Free the allocated resources
*/
static void decoder_close(lv_image_decoder_t * decoder, lv_image_decoder_dsc_t * dsc)
{
LV_UNUSED(decoder); /*Unused*/
if(dsc->args.no_cache ||
!lv_image_cache_is_enabled()) lv_draw_buf_destroy((lv_draw_buf_t *)dsc->decoded);
}
static lv_draw_buf_t * decode_webp_file(lv_image_decoder_dsc_t * dsc, const char * filename)
{
LV_PROFILER_DECODER_BEGIN;
uint32_t data_size;
uint8_t * data = lv_fs_load_with_alloc(filename, &data_size);
if(data == NULL) {
LV_LOG_WARN("can't load file: %s", filename);
LV_PROFILER_DECODER_END;
return NULL;
}
/*Alloc image buffer*/
lv_draw_buf_t * decoded;
decoded = lv_draw_buf_create_ex(image_cache_draw_buf_handlers, dsc->header.w, dsc->header.h, dsc->header.cf,
LV_STRIDE_AUTO);
if(decoded == NULL) {
LV_LOG_ERROR("alloc draw buffer failed: %s", filename);
lv_free(data);
LV_PROFILER_DECODER_END;
return NULL;
}
WebPDecoderConfig config;
WebPInitDecoderConfig(&config);
config.output.colorspace = MODE_BGRA;
config.output.u.RGBA.rgba = (uint8_t *) decoded->data;
config.output.u.RGBA.stride = decoded->header.stride;
config.output.u.RGBA.size = decoded->data_size;
config.output.is_external_memory = 1;
LV_PROFILER_DECODER_BEGIN_TAG("WebPDecode");
int status = WebPDecode(data, data_size, &config);
LV_PROFILER_DECODER_END_TAG("WebPDecode");
if(status != VP8_STATUS_OK) {
LV_LOG_ERROR("decode webp failed: %s, status: %d", filename, status);
lv_draw_buf_destroy(decoded);
decoded = NULL;
}
lv_free(data);
LV_PROFILER_DECODER_END;
return decoded;
}
#endif /*LV_USE_LIBWEBP*/
+48
View File
@@ -0,0 +1,48 @@
/**
* @file lv_libwebp.h
*
*/
#ifndef LV_LIBWEBP_H
#define LV_LIBWEBP_H
#ifdef __cplusplus
extern "C" {
#endif
/*********************
* INCLUDES
*********************/
#include "../../lv_conf_internal.h"
#if LV_USE_LIBWEBP
/*********************
* DEFINES
*********************/
/**********************
* TYPEDEFS
**********************/
/**********************
* GLOBAL PROTOTYPES
**********************/
/**
* Register the WEBP decoder functions in LVGL
*/
void lv_libwebp_init(void);
void lv_libwebp_deinit(void);
/**********************
* MACROS
**********************/
#endif /*LV_USE_LIBWEBP*/
#ifdef __cplusplus
} /* extern "C" */
#endif
#endif /*LV_LIBWEBP_H*/
+9
View File
@@ -3035,6 +3035,15 @@
#endif #endif
#endif #endif
/** WebP decoder library */
#ifndef LV_USE_LIBWEBP
#ifdef CONFIG_LV_USE_LIBWEBP
#define LV_USE_LIBWEBP CONFIG_LV_USE_LIBWEBP
#else
#define LV_USE_LIBWEBP 0
#endif
#endif
/** GIF decoder library */ /** GIF decoder library */
#ifndef LV_USE_GIF #ifndef LV_USE_GIF
#ifdef CONFIG_LV_USE_GIF #ifdef CONFIG_LV_USE_GIF
+5
View File
@@ -30,6 +30,7 @@
#include "libs/libjpeg_turbo/lv_libjpeg_turbo.h" #include "libs/libjpeg_turbo/lv_libjpeg_turbo.h"
#include "libs/lodepng/lv_lodepng.h" #include "libs/lodepng/lv_lodepng.h"
#include "libs/libpng/lv_libpng.h" #include "libs/libpng/lv_libpng.h"
#include "libs/libwebp/lv_libwebp.h"
#include "libs/tiny_ttf/lv_tiny_ttf.h" #include "libs/tiny_ttf/lv_tiny_ttf.h"
#include "draw/lv_draw.h" #include "draw/lv_draw.h"
#include "misc/lv_async.h" #include "misc/lv_async.h"
@@ -398,6 +399,10 @@ void lv_init(void)
lv_libjpeg_turbo_init(); lv_libjpeg_turbo_init();
#endif #endif
#if LV_USE_LIBWEBP
lv_libwebp_init();
#endif
#if LV_USE_BMP #if LV_USE_BMP
lv_bmp_init(); lv_bmp_init();
#endif #endif
+12
View File
@@ -166,6 +166,7 @@ endif()
if ($ENV{NON_AMD64_BUILD}) if ($ENV{NON_AMD64_BUILD})
set(CMAKE_LIBRARY_PATH "/usr/lib/i386-linux-gnu" CACHE PATH "search 32bit lib path firstly") set(CMAKE_LIBRARY_PATH "/usr/lib/i386-linux-gnu" CACHE PATH "search 32bit lib path firstly")
set(ENV{PKG_CONFIG_PATH} "/usr/lib/i386-linux-gnu/pkgconfig:$ENV{PKG_CONFIG_PATH}")
endif() endif()
# Options lvgl and examples are compiled with. # Options lvgl and examples are compiled with.
@@ -349,6 +350,16 @@ if(NOT WIN32)
find_package(JPEG REQUIRED) find_package(JPEG REQUIRED)
include_directories(${JPEG_INCLUDE_DIR}) include_directories(${JPEG_INCLUDE_DIR})
find_package(PkgConfig)
pkg_check_modules(WebP libwebp)
if (WebP_FOUND)
include_directories(${WebP_INCLUDEDIR})
else()
message("WebP not found, defaulting to 0")
add_definitions(-DLV_USE_LIBWEBP=0)
endif()
# Wayland # Wayland
find_package(PkgConfig) find_package(PkgConfig)
pkg_check_modules(wayland_client wayland-client) pkg_check_modules(wayland_client wayland-client)
@@ -509,6 +520,7 @@ foreach( test_case_fname ${TEST_CASE_FILES} )
${LIBDRM_LIBRARIES} ${LIBDRM_LIBRARIES}
${LIBINPUT_LIBRARIES} ${LIBINPUT_LIBRARIES}
${JPEG_LIBRARIES} ${JPEG_LIBRARIES}
${WebP_LINK_LIBRARIES}
${FFMPEG_LIBRARIES} ${FFMPEG_LIBRARIES}
m m
pthread pthread
Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

+1
View File
@@ -80,6 +80,7 @@
#define LV_USE_TJPGD 1 #define LV_USE_TJPGD 1
#ifndef _WIN32 #ifndef _WIN32
#define LV_USE_LIBJPEG_TURBO 1 #define LV_USE_LIBJPEG_TURBO 1
#define LV_USE_LIBWEBP 1
#endif #endif
#ifndef LV_USE_FFMPEG #ifndef LV_USE_FFMPEG
#define LV_USE_FFMPEG 1 #define LV_USE_FFMPEG 1
Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 710 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

+75
View File
@@ -0,0 +1,75 @@
#if LV_BUILD_TEST
#include "../lvgl.h"
#include "../../lvgl_private.h"
#include "unity/unity.h"
void setUp(void)
{
/* Function run before every test */
}
void tearDown(void)
{
/* Function run after every test */
}
static void create_image_item(lv_obj_t * parent, const void * src, const char * text)
{
lv_obj_t * cont = lv_obj_create(parent);
lv_obj_remove_style_all(cont);
lv_obj_set_size(cont, 300, 200);
lv_obj_set_flex_flow(cont, LV_FLEX_FLOW_COLUMN);
lv_obj_set_flex_align(cont, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER);
lv_obj_t * img = lv_image_create(cont);
lv_image_set_src(img, src);
lv_obj_t * label = lv_label_create(cont);
lv_label_set_text(label, text);
}
static void create_webp_images(void)
{
lv_obj_t * screen = lv_screen_active();
lv_obj_clean(screen);
lv_obj_set_flex_flow(screen, LV_FLEX_FLOW_ROW_WRAP);
lv_obj_set_flex_align(screen, LV_FLEX_ALIGN_SPACE_AROUND, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER);
/* Lossy WebP file */
create_image_item(screen, "A:src/test_assets/test_img_lvgl_logo_lossy.webp", "Lossy WebP");
/* Lossless WebP file */
create_image_item(screen, "A:src/test_assets/test_img_lvgl_logo_lossless.webp", "Lossless WebP");
/* Transparent WebP file */
create_image_item(screen, "A:src/test_assets/test_img_lvgl_logo_transparent.webp", "Transparent WebP");
/* Corrupted WebP file : "WEBP" -> "WEDP" */
create_image_item(screen, "A:src/test_assets/test_img_lvgl_logo_corrupted.webp", "Corrupted WebP");
}
void test_libwebp_1(void)
{
create_webp_images();
/* Verify initial rendering */
TEST_ASSERT_EQUAL_SCREENSHOT("libs/webp_1.png");
/* Test memory stability */
size_t mem_before = lv_test_get_free_mem();
for(uint32_t i = 0; i < 20; i++) {
create_webp_images();
lv_obj_invalidate(lv_screen_active());
lv_refr_now(NULL);
}
/* Verify rendering after multiple refreshes */
TEST_ASSERT_EQUAL_SCREENSHOT("libs/webp_1.png");
/* Check for memory leaks */
TEST_ASSERT_MEM_LEAK_LESS_THAN(mem_before, 36);
}
#endif