diff --git a/code/esp32c3_espidf/CMakeLists.txt b/code/esp32c3_espidf/CMakeLists.txt index 05fe49d..a034070 100644 --- a/code/esp32c3_espidf/CMakeLists.txt +++ b/code/esp32c3_espidf/CMakeLists.txt @@ -4,3 +4,4 @@ cmake_minimum_required(VERSION 3.16) include($ENV{IDF_PATH}/tools/cmake/project.cmake) project(demo1) + diff --git a/code/esp32c3_espidf/dependencies.lock b/code/esp32c3_espidf/dependencies.lock index 2a7d37e..89bb3a2 100644 --- a/code/esp32c3_espidf/dependencies.lock +++ b/code/esp32c3_espidf/dependencies.lock @@ -2,7 +2,7 @@ dependencies: idf: source: type: idf - version: 5.5.2 + version: 5.5.1 manifest_hash: a52a8cabe7f10f1636effa39e0be0f2d62531803ed5f518e7921b728e64c8752 target: esp32c3 version: 2.0.0 diff --git a/code/esp32c3_espidf/main/CMakeLists.txt b/code/esp32c3_espidf/main/CMakeLists.txt index 6287e94..6331096 100644 --- a/code/esp32c3_espidf/main/CMakeLists.txt +++ b/code/esp32c3_espidf/main/CMakeLists.txt @@ -1,6 +1,7 @@ # 收集当前目录下所有 .c 文件 file(GLOB_RECURSE SRC_LIST "*.c") + idf_component_register( SRCS ${SRC_LIST} PRIV_REQUIRES spi_flash esp_driver_spi esp_driver_gpio esp_timer @@ -12,6 +13,9 @@ idf_component_register( PRIV_REQUIRES ) +# 在注册组件后添加 +target_compile_definitions(${COMPONENT_LIB} PRIVATE LV_LVGL_H_INCLUDE_SIMPLE) + set(SPIFFS_PARTITION_NAME "storage") # 如果分区名是 "storage" # 设置 SPIFFS 根目录路径 set(SPIFFS_IMAGE_DIR "${CMAKE_SOURCE_DIR}/spiffs_image") diff --git a/code/esp32c3_espidf/main/hello_world_main.c b/code/esp32c3_espidf/main/hello_world_main.c index 84e4395..daa5b13 100644 --- a/code/esp32c3_espidf/main/hello_world_main.c +++ b/code/esp32c3_espidf/main/hello_world_main.c @@ -3,11 +3,7 @@ * * SPDX-License-Identifier: CC0-1.0 */ -#define LV_LVGL_H_INCLUDE_SIMPLE -#include "lv_conf.h" -/* 然后包含 lvgl.h */ -#include "lvgl.h" #include #include @@ -36,9 +32,17 @@ #include "esp_timer.h" + +#include "lv_conf.h" + +/* 然后包含 lvgl.h */ +#include "lvgl.h" + #include "lv_port_disp.h" #include "lv_port_fs.h" +#include "lv_log_to_esp.h" + #include "lv_apps/helloworld/lv_helloworld.h" static const char *TAG = "SYS"; @@ -110,6 +114,7 @@ void app_main(void) lv_init(); lv_tick_set_cb(custom_tick_get); + lv_log_to_esp_init(); lv_port_disp_init(); lv_port_fs_init(); diff --git a/code/esp32c3_espidf/main/lv_apps/helloworld/lv_helloworld.c b/code/esp32c3_espidf/main/lv_apps/helloworld/lv_helloworld.c index 3d4a37a..9933f7e 100644 --- a/code/esp32c3_espidf/main/lv_apps/helloworld/lv_helloworld.c +++ b/code/esp32c3_espidf/main/lv_apps/helloworld/lv_helloworld.c @@ -12,7 +12,7 @@ void lv_example_get_started_1(void) { // 1. 加载中文字体 - lv_font_t* cn_font_16 = load_chinese_font_from_spiffs("/spiffs/cn_font.bin"); + lv_font_t* cn_font_16 = load_chinese_font_from_spiffs("S:/spiffs/cn_font.bin"); if (cn_font_16 == NULL) { ESP_LOGE(TAG, "无法加载中文字体,使用默认字体"); cn_font_16 = &my_cn_font; // 回退到默认字体 diff --git a/code/esp32c3_espidf/main/lv_conf.h b/code/esp32c3_espidf/main/lv_conf.h index f2bd8cb..5841be7 100644 --- a/code/esp32c3_espidf/main/lv_conf.h +++ b/code/esp32c3_espidf/main/lv_conf.h @@ -457,7 +457,7 @@ *-----------*/ /** Enable log module */ -#define LV_USE_LOG 0 +#define LV_USE_LOG 1 #if LV_USE_LOG /** Set value to one of the following levels of logging detail: * - LV_LOG_LEVEL_TRACE Log detailed information. @@ -466,7 +466,7 @@ * - LV_LOG_LEVEL_ERROR Log only critical issues, when system may fail. * - LV_LOG_LEVEL_USER Log only custom log messages added by the user. * - LV_LOG_LEVEL_NONE Do not log anything. */ - #define LV_LOG_LEVEL LV_LOG_LEVEL_WARN + #define LV_LOG_LEVEL LV_LOG_LEVEL_INFO /** - 1: Print log with 'printf'; * - 0: User needs to register a callback with `lv_log_register_print_cb()`. */ @@ -479,11 +479,11 @@ /** - 1: Enable printing timestamp; * - 0: Disable printing timestamp. */ - #define LV_LOG_USE_TIMESTAMP 1 + #define LV_LOG_USE_TIMESTAMP 0 /** - 1: Print file and line number of the log; * - 0: Do not print file and line number of the log. */ - #define LV_LOG_USE_FILE_LINE 1 + #define LV_LOG_USE_FILE_LINE 0 /* Enable/disable LV_LOG_TRACE in modules that produces a huge number of logs. */ #define LV_LOG_TRACE_MEM 1 /**< Enable/disable trace logs in memory operations. */ diff --git a/code/esp32c3_espidf/main/lv_load_font_from_spiffs.c b/code/esp32c3_espidf/main/lv_load_font_from_spiffs.c index fee4adc..9906fde 100644 --- a/code/esp32c3_espidf/main/lv_load_font_from_spiffs.c +++ b/code/esp32c3_espidf/main/lv_load_font_from_spiffs.c @@ -12,12 +12,14 @@ lv_font_t* load_chinese_font_from_spiffs(const char* font_path) ESP_LOGI(TAG, "尝试加载字体: %s", font_path); // 检查文件是否存在 - FILE* f = fopen(font_path, "rb"); - if (f == NULL) { - ESP_LOGE(TAG, "字体文件不存在: %s", font_path); - return NULL; - } - fclose(f); + // FILE* f = fopen(font_path, "rb"); + // if (f == NULL) { + // ESP_LOGE(TAG, "字体文件不存在: %s", font_path); + // return NULL; + // } + // fclose(f); + + //LV_LOG_USER("loadfile"); // LVGL V8/V9通用方法:使用lv_binfont_create lv_font_t* font = lv_binfont_create(font_path); diff --git a/code/esp32c3_espidf/main/lv_load_font_from_spiffs.h b/code/esp32c3_espidf/main/lv_load_font_from_spiffs.h index 6ca0a65..f78d2b4 100644 --- a/code/esp32c3_espidf/main/lv_load_font_from_spiffs.h +++ b/code/esp32c3_espidf/main/lv_load_font_from_spiffs.h @@ -24,6 +24,8 @@ #include "esp_spiffs.h" #include "esp_log.h" + + lv_font_t* load_chinese_font_from_spiffs(const char* font_path); void free_chinese_font(lv_font_t* font); diff --git a/code/esp32c3_espidf/main/lv_log_to_esp.c b/code/esp32c3_espidf/main/lv_log_to_esp.c new file mode 100644 index 0000000..5c8ce8a --- /dev/null +++ b/code/esp32c3_espidf/main/lv_log_to_esp.c @@ -0,0 +1,60 @@ +#include "lv_log_to_esp.h" + +static const char *TAG = "LVGL"; + +static void my_print(lv_log_level_t level, const char *buf) +{ + + // 1. 获取原始字符串长度 + size_t buf_len = strlen(buf); + + // 2. 动态分配内存(比原始字符串多分配1个字节,确保安全) + char *my_buf = (char *)malloc(buf_len + 1); + if (my_buf == NULL) { + // 内存分配失败的处理 + // 可以尝试使用备用方案,比如输出到备用缓冲区或直接返回 + return; + } + + // 3. 复制字符串 + strncpy(my_buf, buf, buf_len); + my_buf[buf_len] = '\0'; // 确保字符串终止 + + // 4. 移除末尾的换行符 + if (buf_len > 0 && my_buf[buf_len - 1] == '\n') { + my_buf[buf_len - 1] = '\0'; + buf_len--; // 更新长度 + + // 如果倒数第二个字符是 '\r'(Windows风格换行),也移除 + if (buf_len > 0 && my_buf[buf_len - 1] == '\r') { + my_buf[buf_len - 1] = '\0'; + buf_len--; + } + } + + switch (level) + { + case LV_LOG_LEVEL_WARN: + /* code */ + ESP_LOGW(TAG, "%s", my_buf); + break; + case LV_LOG_LEVEL_ERROR: + /* code */ + ESP_LOGE(TAG, "%s", my_buf); + break; + + default: + ESP_LOGI(TAG, "%s", my_buf); + break; + } + + // 6. 释放动态分配的内存 + free(my_buf); +} + + +void lv_log_to_esp_init() +{ + + lv_log_register_print_cb(my_print); +} \ No newline at end of file diff --git a/code/esp32c3_espidf/main/lv_log_to_esp.h b/code/esp32c3_espidf/main/lv_log_to_esp.h new file mode 100644 index 0000000..843f034 --- /dev/null +++ b/code/esp32c3_espidf/main/lv_log_to_esp.h @@ -0,0 +1,27 @@ +#ifndef LV_LOG_TO_ESP_H +#define LV_LOG_TO_ESP_H + +#if defined(LV_LVGL_H_INCLUDE_SIMPLE) +#include "lvgl.h" +#else +#include "lvgl/lvgl.h" +#endif + +#include +#include +#include "sdkconfig.h" +#include +#include +#include +#include // 关键:包含 DIR 相关定义 +#include // 错误码定义 +#include // 时间相关函数 + +#include "esp_system.h" +#include "esp_log.h" + +#include "lv_conf.h" + +void lv_log_to_esp_init(); + +#endif \ No newline at end of file diff --git a/code/esp32c3_espidf/main/lv_port_fs.c b/code/esp32c3_espidf/main/lv_port_fs.c index 861b6e8..ed9e333 100644 --- a/code/esp32c3_espidf/main/lv_port_fs.c +++ b/code/esp32c3_espidf/main/lv_port_fs.c @@ -12,7 +12,6 @@ #include "lv_port_fs.h" #include "lvgl.h" - static const char *TAG = "LVGL_FS"; /********************* * DEFINES @@ -27,17 +26,17 @@ static const char *TAG = "LVGL_FS"; **********************/ static void fs_init(void); -static void * fs_open(lv_fs_drv_t * drv, const char * path, lv_fs_mode_t mode); -static lv_fs_res_t fs_close(lv_fs_drv_t * drv, void * file_p); -static lv_fs_res_t fs_read(lv_fs_drv_t * drv, void * file_p, void * buf, uint32_t btr, uint32_t * br); -static lv_fs_res_t fs_write(lv_fs_drv_t * drv, void * file_p, const void * buf, uint32_t btw, uint32_t * bw); -static lv_fs_res_t fs_seek(lv_fs_drv_t * drv, void * file_p, uint32_t pos, lv_fs_whence_t whence); -static lv_fs_res_t fs_size(lv_fs_drv_t * drv, void * file_p, uint32_t * size_p); -static lv_fs_res_t fs_tell(lv_fs_drv_t * drv, void * file_p, uint32_t * pos_p); +static void *fs_open(lv_fs_drv_t *drv, const char *path, lv_fs_mode_t mode); +static lv_fs_res_t fs_close(lv_fs_drv_t *drv, void *file_p); +static lv_fs_res_t fs_read(lv_fs_drv_t *drv, void *file_p, void *buf, uint32_t btr, uint32_t *br); +static lv_fs_res_t fs_write(lv_fs_drv_t *drv, void *file_p, const void *buf, uint32_t btw, uint32_t *bw); +static lv_fs_res_t fs_seek(lv_fs_drv_t *drv, void *file_p, uint32_t pos, lv_fs_whence_t whence); +static lv_fs_res_t fs_size(lv_fs_drv_t *drv, void *file_p, uint32_t *size_p); +static lv_fs_res_t fs_tell(lv_fs_drv_t *drv, void *file_p, uint32_t *pos_p); -static void * fs_dir_open(lv_fs_drv_t * drv, const char * path); -static lv_fs_res_t fs_dir_read(lv_fs_drv_t * drv, void * rddir_p, char * fn, uint32_t fn_len); -static lv_fs_res_t fs_dir_close(lv_fs_drv_t * drv, void * rddir_p); +static void *fs_dir_open(lv_fs_drv_t *drv, const char *path); +static lv_fs_res_t fs_dir_read(lv_fs_drv_t *drv, void *rddir_p, char *fn, uint32_t fn_len); +static lv_fs_res_t fs_dir_close(lv_fs_drv_t *drv, void *rddir_p); /********************** * STATIC VARIABLES @@ -70,7 +69,7 @@ void lv_port_fs_init(void) lv_fs_drv_init(&fs_drv); /*Set up fields...*/ - fs_drv.letter = 'P'; + fs_drv.letter = 'S'; fs_drv.open_cb = fs_open; fs_drv.close_cb = fs_close; fs_drv.read_cb = fs_read; @@ -95,7 +94,7 @@ static void fs_init(void) /*E.g. for FatFS initialize the SD card and FatFS itself*/ /*You code here*/ - ESP_LOGE(TAG, "fs_init"); + ESP_LOGI(TAG, "fs_init"); } /** @@ -105,26 +104,42 @@ static void fs_init(void) * @param mode read: FS_MODE_RD, write: FS_MODE_WR, both: FS_MODE_RD | FS_MODE_WR * @return a file descriptor or NULL on error */ -static void * fs_open(lv_fs_drv_t * drv, const char * path, lv_fs_mode_t mode) +static void *fs_open(lv_fs_drv_t *drv, const char *path, lv_fs_mode_t mode) { - ESP_LOGE(TAG, "fs_open:%s", path); + ESP_LOGI(TAG, "fs_open:%s", path); lv_fs_res_t res = LV_FS_RES_NOT_IMP; - void * f = NULL; + void *f = NULL; - if(mode == LV_FS_MODE_WR) { + if (mode == LV_FS_MODE_WR) + { /*Open a file for write*/ - //f = ... /*Add your code here*/ + // f = ... /*Add your code here*/ + f = fopen(path, "wb"); } - else if(mode == LV_FS_MODE_RD) { + else if (mode == LV_FS_MODE_RD) + { /*Open a file for read*/ - //f = ... /*Add your code here*/ + // f = ... /*Add your code here*/ + f = fopen(path, "rb"); } - else if(mode == (LV_FS_MODE_WR | LV_FS_MODE_RD)) { + else if (mode == (LV_FS_MODE_WR | LV_FS_MODE_RD)) + { /*Open a file for read and write*/ - //f = ... /*Add your code here*/ + // f = ... /*Add your code here*/ + f = fopen(path, "wb+"); + } + + if (f == NULL) + { + res = LV_FS_RES_NOT_EX; + ESP_LOGW(TAG, "找不到文件:%s", path); + } + else + { + res = LV_FS_RES_OK; } return f; @@ -136,12 +151,24 @@ static void * fs_open(lv_fs_drv_t * drv, const char * path, lv_fs_mode_t mode) * @param file_p pointer to a file_t variable. (opened with fs_open) * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_close(lv_fs_drv_t * drv, void * file_p) +static lv_fs_res_t fs_close(lv_fs_drv_t *drv, void *file_p) { - ESP_LOGE(TAG, "fs_close"); + ESP_LOGI(TAG, "fs_close"); lv_fs_res_t res = LV_FS_RES_NOT_IMP; + int r = fclose(file_p); + + if (r != 0) + { + res = LV_FS_RES_UNKNOWN; + ESP_LOGE(TAG, "文件关闭失败"); + } + else + { + res = LV_FS_RES_OK; + } + /*Add your code here*/ return res; @@ -156,11 +183,29 @@ static lv_fs_res_t fs_close(lv_fs_drv_t * drv, void * file_p) * @param br the real number of read bytes (Byte Read) * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_read(lv_fs_drv_t * drv, void * file_p, void * buf, uint32_t btr, uint32_t * br) +static lv_fs_res_t fs_read(lv_fs_drv_t *drv, void *file_p, void *buf, uint32_t btr, uint32_t *br) { lv_fs_res_t res = LV_FS_RES_NOT_IMP; /*Add your code here*/ + ESP_LOGI(TAG, "fs_read"); + + FILE *f = (FILE *)file_p; + size_t bytes_read = fread(buf, 1, btr, f); + *br = (uint32_t)bytes_read; + + if (*br == btr) + { + res = LV_FS_RES_OK; + } + else + { + + ESP_LOGE(TAG, "文件读取字节数量错误需要读取%lu 已读取%lu", btr, *br); + res = LV_FS_RES_UNKNOWN; + } + + ESP_LOGI(TAG, "文件读取字节数量:读取%lu 已读取%lu", btr, *br); return res; } @@ -174,11 +219,27 @@ static lv_fs_res_t fs_read(lv_fs_drv_t * drv, void * file_p, void * buf, uint32_ * @param bw the number of real written bytes (Bytes Written). NULL if unused. * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_write(lv_fs_drv_t * drv, void * file_p, const void * buf, uint32_t btw, uint32_t * bw) +static lv_fs_res_t fs_write(lv_fs_drv_t *drv, void *file_p, const void *buf, uint32_t btw, uint32_t *bw) { lv_fs_res_t res = LV_FS_RES_NOT_IMP; /*Add your code here*/ + ESP_LOGI(TAG, "fs_write"); + + FILE *f = (FILE *)file_p; + size_t bytes_written = fwrite(buf, 1, btw, f); + *bw = (uint32_t)bytes_written; + + if (*bw == btw) + { + res = LV_FS_RES_OK; + } + else + { + + ESP_LOGE(TAG, "文件写入字节数量错误需要写入%lu 已写入%lu", btw, *bw); + res = LV_FS_RES_UNKNOWN; + } return res; } @@ -191,11 +252,40 @@ static lv_fs_res_t fs_write(lv_fs_drv_t * drv, void * file_p, const void * buf, * @param whence tells from where to interpret the `pos`. See @lv_fs_whence_t * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_seek(lv_fs_drv_t * drv, void * file_p, uint32_t pos, lv_fs_whence_t whence) +static lv_fs_res_t fs_seek(lv_fs_drv_t *drv, void *file_p, uint32_t pos, lv_fs_whence_t whence) { lv_fs_res_t res = LV_FS_RES_NOT_IMP; /*Add your code here*/ + ESP_LOGI(TAG, "fs_seek:pop%lu whence%d",pos,whence); + + FILE *f = (FILE *)file_p; + int std_whence; + switch (whence) + { + case LV_FS_SEEK_SET: + std_whence = SEEK_SET; + break; + case LV_FS_SEEK_CUR: + std_whence = SEEK_CUR; + break; + case LV_FS_SEEK_END: + std_whence = SEEK_END; + break; + default: + // 如果传入的 whence 值不合法 + ESP_LOGE(TAG, "whence 参数错误"); + return LV_FS_RES_INV_PARAM; + } + + if (fseek(f, (long)pos, std_whence) != 0) + { + // 定位失败,返回错误 + res = LV_FS_RES_UNKNOWN; // 或更具体的错误码 + ESP_LOGE(TAG, "seek定位失败"); + } + + res = LV_FS_RES_OK; return res; } @@ -206,11 +296,23 @@ static lv_fs_res_t fs_seek(lv_fs_drv_t * drv, void * file_p, uint32_t pos, lv_fs * @param pos_p pointer to store the result * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_tell(lv_fs_drv_t * drv, void * file_p, uint32_t * pos_p) +static lv_fs_res_t fs_tell(lv_fs_drv_t *drv, void *file_p, uint32_t *pos_p) { lv_fs_res_t res = LV_FS_RES_NOT_IMP; /*Add your code here*/ + ESP_LOGI(TAG, "fs_tell"); + + FILE *f = (FILE *)file_p; + long pos = ftell(f); + if (pos < 0) + { + ESP_LOGE(TAG, "tell定位失败"); + return LV_FS_RES_UNKNOWN; + } + *pos_p = (uint32_t)pos; + + return LV_FS_RES_OK; return res; } @@ -221,13 +323,14 @@ static lv_fs_res_t fs_tell(lv_fs_drv_t * drv, void * file_p, uint32_t * pos_p) * @param path path to a directory * @return pointer to the directory read descriptor or NULL on error */ -static void * fs_dir_open(lv_fs_drv_t * drv, const char * path) +static void *fs_dir_open(lv_fs_drv_t *drv, const char *path) { ESP_LOGE(TAG, "fs_dir_open:%s", path); - void * dir = NULL; + void *dir = NULL; /*Add your code here*/ - //dir = ... /*Add your code here*/ - return dir; + // dir = ... /*Add your code here*/ + + return dir; } /** @@ -239,10 +342,12 @@ static void * fs_dir_open(lv_fs_drv_t * drv, const char * path) * @param fn_len length of the buffer to store the filename * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_dir_read(lv_fs_drv_t * drv, void * rddir_p, char * fn, uint32_t fn_len) +static lv_fs_res_t fs_dir_read(lv_fs_drv_t *drv, void *rddir_p, char *fn, uint32_t fn_len) { lv_fs_res_t res = LV_FS_RES_NOT_IMP; + ESP_LOGI(TAG, "fs_dir_read"); + /*Add your code here*/ return res; @@ -254,11 +359,12 @@ static lv_fs_res_t fs_dir_read(lv_fs_drv_t * drv, void * rddir_p, char * fn, uin * @param rddir_p pointer to an initialized 'lv_fs_dir_t' variable * @return LV_FS_RES_OK: no error or any error from @lv_fs_res_t enum */ -static lv_fs_res_t fs_dir_close(lv_fs_drv_t * drv, void * rddir_p) +static lv_fs_res_t fs_dir_close(lv_fs_drv_t *drv, void *rddir_p) { lv_fs_res_t res = LV_FS_RES_NOT_IMP; /*Add your code here*/ + ESP_LOGI(TAG, "fs_dir_close"); return res; } diff --git a/readme.md b/readme.md index 2ef9ae5..32fd59f 100644 --- a/readme.md +++ b/readme.md @@ -1 +1,2 @@ -git submodule update --init --recursive \ No newline at end of file +git submodule update --init --recursive +