这些小活动你都参加了吗?快来围观一下吧!>>
电子产品世界 » 论坛首页 » DIY与开源设计 » 电子DIY » STM32H7S78-DK运行LVGLDemo:外部Flash+触摸屏实战

共1条 1/1 1 跳转至页

STM32H7S78-DK运行LVGLDemo:外部Flash+触摸屏实战

高工
2026-11-10 23:52:00     打赏
STM32H7S78-DK 运行 LVGL Demo:外部 Flash + 触摸屏实战

本文记录在 STM32H7S78-DK 开发板(STM32H7S7L8,Cortex-M7 @600MHz,800×480 RGB 屏 + GT911 触摸)上运行 LVGL 图形界面的完整流程。由于 LVGL 应用远超片内 64KB Flash,采用「MCUboot + 外部 Octo-SPI Flash」方式运行,帧缓冲放在板载 32MB PSRAM。

环境基于上一篇《STM32H7S78-DK上跑通Zephyr:从Blinky到外部Flash启动-电子产品世界论坛》搭建的 Windows + Zephyr 4.5 工作区(D:\luglZephyrproject)。

image.png

1. Demo 源码解析

工程放在 app/lvgl_demo,只有三个文件。

prj.conf —— 打开显示、输入和 LVGL;触摸通过板级 DTS 的 zephyr,touch chosen 节点自动接管;色深必须与 LTDC 面板一致(RGB888,24bit),否则花屏:

CONFIG_MAIN_STACK_SIZE=4096
CONFIG_LOG=y

CONFIG_DISPLAY=y
CONFIG_INPUT=y

CONFIG_LVGL=y
CONFIG_LV_Z_MEM_POOL_SIZE=58368
CONFIG_LV_Z_POINTER_FROM_CHOSEN_TOUCH=y

# LTDC 面板为 RGB888(24bit)
CONFIG_LV_COLOR_DEPTH_24=y

CONFIG_LV_FONT_MONTSERRAT_24=y
CONFIG_LV_FONT_MONTSERRAT_32=y

CMakeLists.txt —— 与所有 Zephyr 应用同构:

cmake_minimum_required(VERSION 3.20.0)
find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE})
project(lvgl_demo)

target_sources(app PRIVATE src/main.c)

src/main.c —— 创建一个标题、一个触摸计数按钮和一个滑动条。要点:所有 LVGL API 调用必须包在 lvgl_lock() / lvgl_unlock() 之间,主循环周期调用 lv_timer_handler():

#include <stdio.h>

#include <zephyr/kernel.h>
#include <zephyr/drivers/display.h>
#include <zephyr/logging/log.h>

#include <lvgl.h>
#include <lvgl_zephyr.h>

LOG_MODULE_REGISTER(app, LOG_LEVEL_INF);

static lv_obj_t *count_label;
static lv_obj_t *slider_label;

static void count_btn_event_cb(lv_event_t *e)
{
    static uint32_t count;
    char buf[32];

    count++;
    snprintf(buf, sizeof(buf), "Count: %u", count);
    lv_label_set_text(count_label, buf);
}

static void slider_event_cb(lv_event_t *e)
{
    lv_obj_t *slider = lv_event_get_target(e);
    char buf[32];

    snprintf(buf, sizeof(buf), "Slider: %d", (int)lv_slider_get_value(slider));
    lv_label_set_text(slider_label, buf);
}

int main(void)
{
    const struct device *display_dev = DEVICE_DT_GET(DT_CHOSEN(zephyr_display));
    lv_obj_t *btn;
    lv_obj_t *btn_label;
    lv_obj_t *slider;

    if (!device_is_ready(display_dev)) {
        LOG_ERR("display device not ready");
        return 0;
    }

    lvgl_lock();

    lv_obj_t *title = lv_label_create(lv_screen_active());
    lv_label_set_text(title, "STM32H7S78-DK LVGL Demo");
    lv_obj_set_style_text_font(title, &lv_font_montserrat_32, 0);
    lv_obj_align(title, LV_ALIGN_TOP_MID, 0, 40);

    count_label = lv_label_create(lv_screen_active());
    lv_label_set_text(count_label, "Count: 0");
    lv_obj_set_style_text_font(count_label, &lv_font_montserrat_24, 0);
    lv_obj_align(count_label, LV_ALIGN_CENTER, 0, -60);

    btn = lv_button_create(lv_screen_active());
    lv_obj_set_size(btn, 200, 60);
    lv_obj_align(btn, LV_ALIGN_CENTER, 0, 20);
    lv_obj_add_event_cb(btn, count_btn_event_cb, LV_EVENT_CLICKED, NULL);
    btn_label = lv_label_create(btn);
    lv_label_set_text(btn_label, "Click me!");
    lv_obj_set_style_text_font(btn_label, &lv_font_montserrat_24, 0);
    lv_obj_center(btn_label);

    slider_label = lv_label_create(lv_screen_active());
    lv_label_set_text(slider_label, "Slider: 0");
    lv_obj_set_style_text_font(slider_label, &lv_font_montserrat_24, 0);
    lv_obj_align(slider_label, LV_ALIGN_CENTER, 0, 100);

    slider = lv_slider_create(lv_screen_active());
    lv_obj_set_size(slider, 400, 20);
    lv_obj_align(slider, LV_ALIGN_CENTER, 0, 150);
    lv_obj_add_event_cb(slider, slider_event_cb, LV_EVENT_VALUE_CHANGED, NULL);

    lv_timer_handler();
    lvgl_unlock();

    display_blanking_off(display_dev);
    LOG_INF("lvgl demo started");

    while (1) {
        lvgl_lock();
        lv_timer_handler();
        lvgl_unlock();
        k_msleep(10);
    }
    return 0;
}

板子的显示能力全部由板级 DTS 描述:LTDC 控制器(800×480 RGB888,ext-sdram = <&psram> 指定帧缓冲在 PSRAM)、GT911 触摸、背光/使能 GPIO,应用代码无需任何板级修改。

2. 编译与烧录(外部 Flash 方式)

在 CMD 中执行:

cd /d D:\luglZephyrproject
set ZEPHYR_SDK_INSTALL_DIR=D:\luglZephyrproject\zephyr-sdk-1.0.1\zephyr-sdk-1.0.1
set ZEPHYR_TOOLCHAIN_VARIANT=zephyr

:: Sysbuild 一次构建 MCUboot + 签名应用(LVGL 镜像约 400KB,放不进片内 64KB)
west build -b stm32h7s78_dk/stm32h7s7xx/ext_flash_app --sysbuild -s D:\STM32\stm32H7S78-dk\app\lvgl_demo -d D:\STM32\stm32H7S78-dk\app\lvgl_demo\build

:: 首次烧录:MCUboot + 应用两个镜像一起烧
west flash -d D:\STM32\stm32H7S78-dk\app\lvgl_demo\build

:: 以后改代码只重烧应用(引导器不动):
west flash -d D:\STM32\stm32H7S78-dk\app\lvgl_demo\build --domain lvgl_demo

烧录后复位,屏幕显示标题、按钮和滑动条,触摸点击按钮计数递增,拖动滑动条数值实时更新;串口(ST-LINK VCP,115200)可见启动链:

I: Starting bootloader
I: Jumping to the first image slot
*** Booting Zephyr OS build v4.5.0 ***
[00:00:00.xxx] <inf> app: lvgl demo started

3. 踩坑记录

  • 色深必须匹配面板:LTDC 是 RGB888,CONFIG_LV_COLOR_DEPTH_24=y 不能少,否则画面异常。

  • 镜像放不下就换变体:普通 stm32h7s78_dk 目标只有 64KB Flash,LVGL 必须用 ext_flash_app 变体 + --sysbuild。

  • 签名依赖:sysbuild 构建用 imgtool 给应用签名,需要提前 pip install -r bootloader\mcuboot\scripts\requirements.txt。

  • 切变体要清缓存:同一 build 目录换板级变体时加 -p,否则 CMake 报 board 不匹配。

  • 触摸开箱即用:LV_Z_POINTER_FROM_CHOSEN_TOUCH=y 直接把板级 zephyr,touch 节点注册为 LVGL 指针输入,无需手写触摸驱动对接代码。





关键词: STM32H7S78-DK     Zephyr     LVGL    

共1条 1/1 1 跳转至页

回复

匿名不能发帖!请先 [ 登陆 注册 ]