ESP32S3IDF版本移植LVGL最详细教程100%成功,包括LCD移植,适合所有版本,有工程文件

此文章运行环境ESP-IDF5.3(5.2也可),lvgl8.3.10,lcd1.3寸ST7789驱动屏幕,ESP32S3
不想看此文章了解流程,可以直接到文章最下面下载工程文件,修改引脚即可,注意如果LCD驱动屏幕不显示可能是屏幕芯片驱动不同,此驱动适合ST7789和ST7789V,如果是此芯片还是无法显示,可能你的LCD屏幕没有带CS片选引脚可能是老版本的批次,屏幕无法点亮可以去网上看看,要飞线。建议是带CS引脚的LCD屏幕,有此引脚也可以不用接CS引脚

1、 准备好两个文件,LVGL(任意版本)源码,准备显示屏驱动。这边显示屏驱动使用的是正点原子官网的LCD屏幕ST7789驱动。LCD驱动源码地址 https://pan.baidu.com/s/1A19N218T66hs4PgRgdTqgQ 提取码:ixmr。LVGL源码地址:https://github.com/lvgl/lvgl/releases/tag/v8.3.10,这边移植的是8.3.10,方便使用GUI GUIder软件。在这里插入图片描述
2、 打开正点原子源码,修改引脚,增删文件。正点原子里的XL9555是用来拓展io的我们直接删除,还有IIC和LED的文件删除,并修改CMakeList文件,
在这里插入图片描述
3、 接下来修改LCD的引脚,记得修改图下函数,和引脚初始化
在这里插入图片描述4、 初始化代码如下放入lcd_init函数中,并在lcd.h中宏定义
在这里插入图片描述
5、 然后直接编译,因为删除了三个文件夹,可能有些头文件的引用或者函数调用不存在了可,看哪里编译错误删除即可,此屏幕是1.3寸屏幕,正点原子里的屏幕尺寸源码不用修改。(已改的LCD源码下载
链接: https://pan.baidu.com/s/1P-vsxNBkQpaAE4HfvvvSAg?pwd=4567 提取码: 4567 (在spi和LCD头文件中修改引脚即可))
在这里插入图片描述
6、 移植lvgl,将lvgl下载的源码文件改名为lvgl,直接移入components文件夹即可,因为LVGL里的CMakelist文件已经链接好了。文件结构如下
在这里插入图片描述
7、修改ESP-IDF的SDK配置(注意每次修改一定要保存),使其lv_conf.h生效,当然其实可以不用修改直接使用SDK配置文件的设置界面,但是每次修改测试文件界面就会所有重启编译构建比较耗时间,这边建议直接修改lv_conf.h文件。配置界面搜索uncheck(要先编译一下再搜索不然没有lvgl的配置界面),关闭Uncheck this to use custom lv_conf.h。使能此文件。
在这里插入图片描述
8、将lv_conf_template.h复制并重命名为lv_conf.h,移入scr文件里,并使能文件
在这里插入图片描述在这里插入图片描述
9、移植显示驱动,将components\lvgl\examples\porting里的以下几个文件复制,并到components/BSP文件里创建一个LV_Driver文件夹存放此文件并重命名两个文件为lv_port_disp。记住使能文件,两个文件里第一行的#if 0改为#if 1,并修改BSP里的CMakelist文件
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
10、导入LCD驱动的初始化到disp_init函数中,并在disp_flush初始化显示接口,以及缓冲区
lv_port_disp.c代码如下建议复制以下代码。记得修改屏幕尺寸


#if 1

/*********************
 *      INCLUDES
 *********************/
#include "lv_port_disp.h"
#include <stdbool.h>
#include "spi.h"
#include "lcd.h"

/*********************
 *      DEFINES
 *********************/
#ifndef MY_DISP_HOR_RES
    #warning Please define or replace the macro MY_DISP_HOR_RES with the actual screen width, default value 320 is used for now.
    #define MY_DISP_HOR_RES    240
#endif

#ifndef MY_DISP_VER_RES
    #warning Please define or replace the macro MY_DISP_HOR_RES with the actual screen height, default value 240 is used for now.
    #define MY_DISP_VER_RES    240
#endif


static void disp_init(void);

static void disp_flush(lv_disp_drv_t * disp_drv, const lv_area_t * area, lv_color_t * color_p);



void lv_port_disp_init(void)
{

    disp_init();

        //缓冲区开辟
        int DISP_BUF_SIZE =MY_DISP_HOR_RES * ((MY_DISP_VER_RES)/10);


        static lv_disp_draw_buf_t draw_buf_dsc;
        #if defined(CONFIG_GRAPHICS_USE_PSRAM)
        lv_color_t *buf_1 = heap_caps_malloc(DISP_BUF_SIZE*2, MALLOC_CAP_SPIRAM);
        lv_color_t *buf_2 = heap_caps_malloc(DISP_BUF_SIZE*2, MALLOC_CAP_SPIRAM);
        #else
        lv_color_t *buf_1 = heap_caps_malloc(DISP_BUF_SIZE*2, MALLOC_CAP_DMA);
        lv_color_t *buf_2 = heap_caps_malloc(DISP_BUF_SIZE*2, MALLOC_CAP_DMA);
        #endif
         lv_disp_draw_buf_init(&draw_buf_dsc, buf_1, buf_2,DISP_BUF_SIZE);


    //注册显示
    static lv_disp_drv_t disp_drv;
    lv_disp_drv_init(&disp_drv);
    disp_drv.hor_res = MY_DISP_HOR_RES;
    disp_drv.ver_res = MY_DISP_VER_RES;
    disp_drv.flush_cb = disp_flush;
    disp_drv.draw_buf = &draw_buf_dsc;
    lv_disp_drv_register(&disp_drv);
}


static void disp_init(void)
{
    spi2_init();
    lcd_init();
}

volatile bool disp_flush_enabled = true;


void disp_enable_update(void)
{
    disp_flush_enabled = true;
}


void disp_disable_update(void)
{
    disp_flush_enabled = false;
}


static void disp_flush(lv_disp_drv_t * disp_drv, const lv_area_t * area, lv_color_t * color_p)
{


    lcd_set_window(area->x1, area->y1, area->x2, area->y2);
    size_t size = (size_t)lv_area_get_width(area) * (size_t)lv_area_get_height(area);
    lcd_write_data(color_p, size * 2);
     //lcd_lvgl_flush(area->x1, area->y1, area->x2, area->y2,color_p, size);
    lv_disp_flush_ready(disp_drv);
}


#else

#endif

11、 修改lv_conf.h里的LV_TICK_CUSTOM,配置LVGL的TICK,和LV_COLOR_16_SWAP置为1(如果屏幕反色就修改)
在这里插入图片描述

12、 最后运行DEMO记得再lv_conf.h使能LV_USE_DEMO_BENCHMARK,,但是特殊的是再SDK配置界面里也要使能LV_USE_DEMO_BENCHMARK,这是为什么呢。因为在components\lvgl\env_support\cmake\esp.cmake文件中有SDK配置界面的DEMO开启定义,所以运行demo两个地方都要使能不然会编译错误。其他的配置修改lv_conf.h即可。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
13、 最后修改main.c文件,使其LVGL在ESP32S3的1号核上运行,并配置LVGL的刷新中断代码如下

main.c


#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/event_groups.h"
#include "lvgl.h"
#include "freertos/semphr.h"
#include "esp_system.h"
#include "lv_port_disp.h"
#include "nvs_flash.h"
#include "esp_system.h"
#include "esp_chip_info.h"
#include "esp_psram.h"
#include "esp_flash.h"
#include "esp_timer.h"
#include "demos/lv_demos.h"



static void lvgl_act(void *pvParameter);

void app_main(void)
{
    xTaskCreatePinnedToCore(lvgl_act, "gui_app", 4096 * 2, NULL, 0, NULL, 1);

}
static void lvgl_act(void *pvParameter)
{


    esp_err_t ret;
    ret = nvs_flash_init();              /* 初始化NVS */
    if (ret == ESP_ERR_NVS_NO_FREE_PAGES
    || ret == ESP_ERR_NVS_NEW_VERSION_FOUND)
    {
        ESP_ERROR_CHECK(nvs_flash_erase());
        ret = nvs_flash_init();
    }


    lv_init();
    lv_port_disp_init();
    lv_demo_benchmark();

    while (1)
    {
        /* Delay 1 tick (assumes FreeRTOS tick is 10ms */
        vTaskDelay(pdMS_TO_TICKS(10));
        lv_task_handler();
    }

}

14、最后编译运行结果。工程代码(改引脚直接运行即可)链接:: https://pan.baidu.com/s/117Lyi_Vw4iY-JK0AbTTx0g?pwd=4567 提取码: 4567

请添加图片描述

xecuting action: flash Serial port /dev/ttyACM0 Connecting.... Detecting chip type... ESP32-S3 Running ninja in directory /home/jichu/esp32/lvgl_display/build Executing "ninja flash"... [1/1] cd /home/jichu/esp32/lvgl_displa...isplay/build/bootloader/bootloader.bin Bootloader binary size 0x5240 bytes. 0x2dc0 bytes (36%) free. [2/5] Linking CXX executable lvgl_display.elf FAILED: lvgl_display.elf : && /home/jichu/.espressif/tools/xtensa-esp-elf/esp-13.2.0_20230928/xtensa-esp-elf/bin/xtensa-esp32s3-elf-g++ -mlongcalls -Wl,--cref -Wl,--defsym=IDF_TARGET_ESP32S3=0 -Wl,--Map=/home/jichu/esp32/lvgl_display/build/lvgl_display.map -Wl,--no-warn-rwx-segments -fno-rtti -fno-lto -Wl,--gc-sections -Wl,--warn-common -T esp32s3.peripherals.ld -T esp32s3.rom.ld -T esp32s3.rom.api.ld -T esp32s3.rom.libgcc.ld -T esp32s3.rom.newlib.ld -T esp32s3.rom.version.ld -T memory.ld -T sections.ld CMakeFiles/lvgl_display.elf.dir/project_elf_src_esp32s3.c.obj -o lvgl_display.elf -L/home/jichu/esp32/esp-idf/components/soc/esp32s3/ld -L/home/jichu/esp32/esp-idf/components/esp_rom/esp32s3/ld -L/home/jichu/esp32/lvgl_display/build/esp-idf/esp_system/ld -L/home/jichu/esp32/esp-idf/components/esp_phy/lib/esp32s3 -L/home/jichu/esp32/esp-idf/components/esp_coex/lib/esp32s3 -L/home/jichu/esp32/esp-idf/components/esp_wifi/lib/esp32s3 -L/home/jichu/esp32/esp-idf/components/bt/controller/lib_esp32c3_family/esp32s3 esp-idf/xtensa/libxtensa.a esp-idf/esp_ringbuf/libesp_ringbuf.a esp-idf/efuse/libefuse.a esp-idf/esp_mm/libesp_mm.a esp-idf/driver/libdriver.a esp-idf/esp_pm/libesp_pm.a esp-idf/mbedtls/libmbedtls.a esp-idf/esp_bootloader_format/libesp_bootloader_format.a esp-idf/esp_app_format/libesp_app_format.a esp-idf/bootloader_support/libbootloader_support.a esp-idf/esp_partition/libesp_partition.a esp-idf/app_update/libapp_update.a esp-idf/spi_flash/libspi_flash.a esp-idf/pthread/libpthread.a esp-idf/esp_system/libesp_system.a esp-idf/esp_rom/libesp_rom.a esp-idf/hal/libhal.a esp-idf/log/liblog.a esp-idf/heap/libheap.a esp-idf/soc/libsoc.a esp-idf/esp_hw_support/libesp_hw_support.a esp-idf/freertos/libfreertos.a esp-idf/newlib/libnewlib.a esp-idf/cxx/libcxx.a esp-idf/esp_common/libesp_common.a esp-idf/esp_timer/libesp_timer.a esp-idf/app_trace/libapp_trace.a esp-idf/esp_event/libesp_event.a esp-idf/nvs_flash/libnvs_flash.a esp-idf/esp_phy/libesp_phy.a esp-idf/vfs/libvfs.a esp-idf/lwip/liblwip.a esp-idf/esp_netif/libesp_netif.a esp-idf/wpa_supplicant/libwpa_supplicant.a esp-idf/esp_coex/libesp_coex.a esp-idf/esp_wifi/libesp_wifi.a esp-idf/bt/libbt.a esp-idf/unity/libunity.a esp-idf/cmock/libcmock.a esp-idf/console/libconsole.a esp-idf/http_parser/libhttp_parser.a esp-idf/esp-tls/libesp-tls.a esp-idf/esp_adc/libesp_adc.a esp-idf/esp_eth/libesp_eth.a esp-idf/esp_gdbstub/libesp_gdbstub.a esp-idf/esp_hid/libesp_hid.a esp-idf/tcp_transport/libtcp_transport.a esp-idf/esp_http_client/libesp_http_client.a esp-idf/esp_http_server/libesp_http_server.a esp-idf/esp_https_ota/libesp_https_ota.a esp-idf/esp_lcd/libesp_lcd.a esp-idf/protobuf-c/libprotobuf-c.a esp-idf/protocomm/libprotocomm.a esp-idf/esp_local_ctrl/libesp_local_ctrl.a esp-idf/espcoredump/libespcoredump.a esp-idf/wear_levelling/libwear_levelling.a esp-idf/sdmmc/libsdmmc.a esp-idf/fatfs/libfatfs.a esp-idf/json/libjson.a esp-idf/mqtt/libmqtt.a esp-idf/nvs_sec_provider/libnvs_sec_provider.a esp-idf/perfmon/libperfmon.a esp-idf/spiffs/libspiffs.a esp-idf/touch_element/libtouch_element.a esp-idf/usb/libusb.a esp-idf/wifi_p
03-14
<think>好的,我现在要处理用户提供的关于ESP32-S3项目编译失败的日志。首先,我需要仔细阅读日志内容,找出关键错误信息。用户执行了`ninja flash`命令,但在链接阶段出现了问题,具体是`FAILED: lvgl_display.elf`,说明生成可执行文件时失败。 首先,我注意到链接器命令中使用了`xtensa-esp32s3-elf-g++`,这可能涉及到C++的链接问题。常见的失败原因可能包括内存不足、库缺失或版本不兼容、符号未定义等。用户的环境是ESP-IDF,可能使用了LVGL库,所以需要检查相关依赖是否正确配置。 日志中的错误没有直接显示具体的错误信息,这可能是因为输出被截断或者需要更详细的编译日志。因此,我应该建议用户增加编译的详细程度,例如运行`ninja -v flash`来获取更多信息。此外,检查是否有未定义的引用(undefined reference)或库路径问题。 另一个可能性是项目的sdkconfig配置不正确,特别是对于ESP32-S3的配置,例如PSRAM设置、分区表大小等。用户需要确认`sdkconfig`中是否选择了正确的芯片型号,以及LVGL相关配置是否适配ESP32-S3。 内存不足也是一个常见问题,尤其是在链接阶段。Bootloader的大小显示为0x5240字节,剩余36%的空间,这可能没问题,但主应用程序可能超出了可用内存。需要检查分区表是否合理,以及应用程序的代码量和内存需求。 还有可能是工具链的问题,比如xtensa-esp32s3-elf-g++的版本是否与ESP-IDF版本兼容。用户使用的ESP-IDF版本是否支持所选的LVGL版本?需要确认版本兼容性,并尝试重新安装或更新工具链。 此外,检查CMakeLists.txt和组件依赖是否正确,特别是LVGL组件是否被正确包含,路径是否正确。如果用户自定义了组件,可能存在路径错误或编译选项冲突。 后,建议用户清理构建目录(删除build文件夹)并重新编译,有时候旧的构建文件会导致链接错误。如果问题依旧,查看更详细的日志或尝试简化项目以隔离问题。</think>您在尝试通过 `ninja flash` 命令烧录 ESP32-S3 固件时遇到了链接阶段的编译错误。以下是问题分析和解决步骤: --- ### **错误定位** 日志显示关键错误: ```bash FAILED: lvgl_display.elf : && /home/jichu/.espressif/tools/.../xtensa-esp32s3-elf-g++ ... (链接命令) ``` 此错误表明在生成终可执行文件 `lvgl_display.elf` 时,链接器 (`xtensa-esp32s3-elf-g++`) 失败。 --- ### **可能原因** 1. **内存不足** - Bootloader 剩余空间:$$ 0x5240 \text{ bytes (总)} - 0x2dc0 \text{ bytes (剩余)} = 0x2480 \text{ bytes (已用)} $$ - 主程序 (`lvgl_display.elf`) 可能超出芯片 Flash 或 RAM 限制。 2. **依赖库缺失或冲突** - 检查是否缺少 LVGL 相关库(如 `lvgl/liblvgl.a`)。 - 确保所有组件(如 Wi-Fi、SPIFFS)在 `sdkconfig` 中正确配置。 3. **符号未定义 (Undefined Reference)** - 常见于未实现函数、头文件未包含或库未链接。 4. **工具链版本不兼容** - ESP-IDF 版本LVGL 组件或第三方库存在兼容性问题。 --- ### **解决步骤** #### 1. **启用详细日志** 重新编译并输出详细错误信息: ```bash ninja -v flash | tee build.log ``` 检查 `build.log` 中具体的未定义符号或路径错误。 --- #### 2. **检查内存配置** - **分区表**:确认 `partitions.csv` 中 `app` 分区大小是否足够。 - **sdkconfig**:通过 `idf.py menuconfig` 检查: - **Component config → LVGL → Memory settings**(调整 LVGL 缓冲区大小)。 - **Serial flasher config → Flash Size** 是否匹配硬件。 --- #### 3. **验证依赖关系** - **组件路径**:确保 LVGL 组件路径正确(`CMakeLists.txt` 中 `EXTRA_COMPONENT_DIRS`)。 - **库链接**:在 `CMakeLists.txt` 中添加缺失库: ```cmake target_link_libraries(${PROJECT_NAME} PRIVATE lvgl) ``` --- #### 4. **清理并重新编译** 清除旧构建文件: ```bash rm -rf build idf.py build ``` --- #### 5. **缩小问题范围** - **小化代码**:注释掉 LVGL 初始化代码,逐步排查功能模块。 - **更新工具链**:重新安装 ESP-IDF 或更新至稳定版本(如 v5.1)。 --- ### **扩展建议** - **使用官方例程**:从 `esp-idf/examples/peripherals/lcd/lvgl` 测试基础功能。 - **内存分析工具**:通过 `idf.py size-components` 查看各组件内存占用。 如果仍有问题,请提供 `build.log` 中的具体错误信息,以便进一步诊断!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值