ESP32-S3-RGB-Matrix 使用教程

产品特性

  • 采用 ESP32-S3-N32R16 芯片,搭载 Xtensa 32 位 LX7 双核处理器,主频高达 240MHz
  • 支持 2.4 GHz Wi-Fi 与 Bluetooth 5 (BLE) 双模通信
  • 内置 512KB SRAM、384KB ROM,叠封 32MB Flash 与 16MB PSRAM,满足多场景存储需求
  • 兼容微雪商店 Matrix-RGB 全系列尺寸,可流畅运行 LVGL 等图形界面程序
  • 板载 ES7210 回声消除芯片,提升语音处理效果
  • 板载 ES8311 低功耗音频编解码芯片,支持高质量音频输入输出
  • 配备双麦克风阵列,支持降噪与回声消除算法,适用于语音识别及唤醒等应用场景
  • 板载喇叭接口,支持音频播放输出,可直接连接喇叭使用
  • 集成 QMI8658 六轴惯性测量单元 (3 轴加速度计 + 3 轴陀螺仪),可实现姿态检测
  • 集成 SHTC3 温湿度传感器,可实现精准的温湿度检测
  • 板载 Micro SD 卡槽,支持图片、音频及各类文件数据存储,方便数据读写
  • 板载 PCF85063 RTC 实时时钟芯片,预留 SH1.0 电池接口,支持掉电持续计时
  • 预留 GPIO 扩展接口,便于外设扩展与功能定制,适配多样化开发需求
  • 双供电接口设计,最多支持 6 块 64 × 64 Matrix-RGB 屏幕稳定工作,支持级联扩展,满足大尺寸显示需求
  • 板载 USB Type-C 接口,支持供电、程序下载与调试,操作便捷
  • 板载 RST / BOOT 按钮,其中 BOOT 按钮支持自定义功能,提升开发灵活性

资源简介


接口展示


产品尺寸


使用说明

为了让用户能够快速了解产品的各个功能,我们提供了一系列的测试例程,方便客户了解各个接口的使用,为了能够运行例程,需要准备的器件如下:

器件准备

  • 1. ESP32-S3-RGB-Matrix ×1

  • 2. 任意型号的LED屏幕 x1 (如果有级联需求可以准备多个)

  • 3. VH4 2PIN 散头线(约 500mm) ×1 (如果有级联需求可以准备多个)

  • 4. 螺丝包 × 1

  • 5. 扁平线 16PIN 约 200mm × 1 (如果有级联需求可以准备多个)

  • 6. Micro SD卡 × 1

  • 7. 8Ω 5W 喇叭 × 1

  • 8. USB 线 Type-A 公口 → Type-C 公口 ×1

  • 9. PSU-27W-USB-C-EU-B x 1** USB Type-C接口充电器


注意事项

  • 如需要级联多个屏幕,需要准备多个屏幕和多个扁平线,每个屏幕连接到一个扁平线端,如果供电不足可以准备双USB Type-C接口充电器供电。

  • TF 卡仅支持 MMC 通信方式。

    USB 下载注意事项(重要)

    开发板使用 USB 下载程序

若出现 无法识别端口 的情况,请进入 Boot 模式

  1. 按住 BOOT 按键
  2. 连接 USB 至电脑
  3. 松开 BOOT 按键

下载完成后,按 RESET 按键运行程序。

编译前需在 menuconfig 中配置以下选项:


  • Panel Height = 64

  • Panel Width = 64

  • 根据具体像素大小配置,配错会显示错位。

  • Scan Wiring Pattern = Standard

  • 扫描接线方式,选最常见标准模式。

  • Shift Driver IC = Generic

  • 驱动芯片按通用模式初始化,适合大多数普通面板。

  • Bit Depth = 8-bit

  • 颜色精度中等,效果和性能比较平衡。

  • Output Clock Speed = 20MHz

  • 数据输出速度,20MHz 通常稳定且够用。

  • Minimum Refresh Rate = 60Hz

  • 设置最低刷新率 60Hz,减少肉眼闪烁。

  • Default Brightness = 128

  • 默认亮度一半,亮度和功耗折中。

  • Display Rotation = 0°

  • 不旋转,按默认方向显示。

Arduino 开发

本章节包含以下部分,请按需阅读:

Arduino 入门教程

初次接触 Arduino ESP32 开发,想要快速上手?我们为您准备了一套通用的 入门教程

请注意:该教程使用 ESP32-S3-Zero 作为教学示例,所有硬件代码均基于其引脚布局。在动手实践前,建议您对照手中的开发板引脚图,确认引脚配置无误。

配置开发环境

1. 安装和配置 Arduino IDE

请参考 安装和配置 Arduino IDE 教程 下载安装 Arduino IDE 并添加 ESP32 支持。

板名称板安装要求版本号要求
esp32 by Espressif Systems“离线”安装/“在线”安装3.3.7

Arduino 设置:


2. 运行示例

Arduino 示例程序:ESP32-S3-RGB-Matrix 示例程序-GitHub Arduino 示例程序:ESP32-S3-RGB-Matrix 示例程序-Gitee

下面给出每个示例的目的、要点说明与运行效果(以便快速上手)。

示例程序基础例程说明
01_SimpleTestShapes简单形状绘画
02_PatternPlasma等离子特效
03_DoubleBuffer双缓冲测试,绘制动态图形
04_OtherShiftDriverPanel使用驱动芯片驱动屏幕
05_AnimatedGIFPanel_SD读取 SD 卡中的 GIF 图片并显示
06_BitmapIcons显示bmp 图片
07_Pixel_Mapping_Test展示HUB75基本控制逻辑

提示

注意:

  • 若驱动P4系列的屏幕,注意在代码中添加mxconfig.driver = HUB75_I2S_CFG::SHIFTREG;,否则会导致显示异常。

01_SimpleTestShapes

【代码分析】

  • loop():按顺序执行文字绘制、纯色填充与清屏操作,用于快速验证面板的基础显示功能。
  • drawText(wheelval):根据 wheelval 绘制文字并改变颜色效果,用于检查字符渲染与颜色变化是否正常。
  • dma_display->fillScreen():依次将屏幕填充为黑、红、绿、蓝、白等纯色,便于观察整屏刷新与颜色显示效果。
  • delay(2000):每个显示步骤停留 2 秒,方便肉眼确认画面是否正确。
  • dma_display->clearScreen():在测试结束后清空画面,避免上一帧内容残留。

void loop() {

// animate by going through the colour wheel for the first two lines
drawText(wheelval);
wheelval +=1;
delay(2000);
dma_display->clearScreen();
dma_display->fillScreen(myBLACK);
delay(2000);
dma_display->fillScreen( myRED);
delay(2000);
dma_display->fillScreen(myGREEN);
delay(2000);
dma_display->fillScreen(myBLUE);
delay(2000);
dma_display->fillScreen(myWHITE);
delay(2000);
dma_display->clearScreen();

}

【运行效果】


02_PatternPlasma

【代码分析】

  • loop():通过逐像素计算与调色板映射生成动态等离子特效。
  • for (int x ...) / for (int y ...):遍历整块面板的每个像素,逐点计算并绘制颜色。
  • sin8()sin16()cos16():结合坐标和 time_counter 生成动态变化的中间值 v,构造流动波纹效果。
  • ColorFromPalette(currentPalette, (v >> 8)):根据计算结果从当前调色板中取色。
  • dma_display->drawPixelRGB888():将计算出的 RGB 颜色写入当前像素。
  • time_countercyclesfps:分别用于驱动动画变化、统计循环次数和计算绘制帧率。
  • if (cycles >= 1024):重置计数器并随机切换调色板,实现不同色系自动轮换。
  • Serial.printf_P():每 5 秒输出一次 Effect fps,用于观察特效绘制速度。

void loop() {

for (int x = 0; x < PANE_WIDTH; x++) {
for (int y = 0; y < PANE_HEIGHT; y++) {
int16_t v = 128;
uint8_t wibble = sin8(time_counter);
v += sin16(x * wibble * 3 + time_counter);
v += cos16(y * (128 - wibble) + time_counter);
v += sin16(y * x * cos8(-time_counter) / 8);

currentColor = ColorFromPalette(currentPalette, (v >> 8)); //, brightness, currentBlendType);
dma_display->drawPixelRGB888(x, y, currentColor.r, currentColor.g, currentColor.b);
}
}

++time_counter;
++cycles;
++fps;

if (cycles >= 1024) {
time_counter = 0;
cycles = 0;
currentPalette = palettes[random(0,sizeof(palettes)/sizeof(palettes[0]))];
}

// print FPS rate every 5 seconds
// Note: this is NOT a matrix refresh rate, it's the number of data frames being drawn to the DMA buffer per second
if (fps_timer + 5000 < millis()){
Serial.printf_P(PSTR("Effect fps: %d\n"), fps/5);
fps_timer = millis();
fps = 0;
}
} // end loop


【运行效果】


03_DoubleBuffer

【代码分析】

  • loop():演示双缓冲动画的完整流程,包括切换缓冲区、后台绘制和更新运动状态。
  • display->flipDMABuffer():将后续绘图切换到未显示的后台缓冲区,用于减少动态图形闪烁。
  • delay(1000/display->calculated_refresh_rate):等待当前帧完成显示,避免过早翻转缓冲区导致撕裂或闪烁。
  • display->clearScreen():清空后台缓冲区,为新一帧绘制做准备。
  • delay(25):模拟耗时绘图过程,用于更直观地观察启用双缓冲后的平滑效果。
  • display->fillRect():绘制多个运动方块,形成动态测试画面。
  • velocityx / velocityy 判断逻辑:当方块碰到屏幕边界时反转运动方向,实现反弹效果。
  • Squares[i].xpos / Squares[i].ypos 更新:根据速度更新方块坐标,推动下一帧动画。

void loop()
{

// Flip all future drawPixel calls to write to the back buffer which is NOT being displayed.
display->flipDMABuffer();

// SUPER IMPORTANT: Wait at least long enough to ensure that a "frame" has been displayed on the LED Matrix Panel before the next flip!
delay(1000/display->calculated_refresh_rate);

// Now clear the back-buffer we are drawing to.
display->clearScreen();

// This is here to demonstrate flicker if double buffering is disabled. Emulates a long draw routine that would typically occur after a 'clearscreen'.
delay(25);


for (int i = 0; i < numSquares; i++)
{
// Draw rect and then calculate
display->fillRect(Squares[i].xpos, Squares[i].ypos, Squares[i].square_size, Squares[i].square_size, Squares[i].colour);

if (Squares[i].square_size + Squares[i].xpos >= display->width()) {
Squares[i].velocityx *= -1;
} else if (Squares[i].xpos <= 0) {
Squares[i].velocityx = abs (Squares[i].velocityx);
}

if (Squares[i].square_size + Squares[i].ypos >= display->height()) {
Squares[i].velocityy *= -1;
} else if (Squares[i].ypos <= 0) {
Squares[i].velocityy = abs (Squares[i].velocityy);
}

Squares[i].xpos += Squares[i].velocityx;
Squares[i].ypos += Squares[i].velocityy;
}
}

【运行效果】


04_OtherShiftDriverPanel

【代码分析】

  • loop():持续生成整屏动态特效,用于验证带移位寄存器驱动芯片面板的显示兼容性。
  • for (int x ...) / for (int y ...):遍历整块屏幕,对每个像素分别计算颜色值。
  • sin8()sin16()cos16():结合坐标和 time_counter 生成连续变化的颜色索引。
  • ColorFromPalette(currentPalette, (v >> 8) + 127):根据中间值从调色板中映射出最终颜色。
  • dma_display->drawPixelRGB888():将 RGB 颜色逐点写入 DMA 显示缓冲区。
  • time_countercyclesfps:分别用于驱动动画变化、控制换色周期和统计绘制帧率。
  • if (cycles >= 1024):定期重置动画参数并随机切换调色板,便于观察不同色彩下的显示效果。
  • Serial.printf_P():周期输出 FPS 信息,用于评估当前图案绘制速度。
void loop(){
for (int x = 0; x < dma_display->width(); x++) {
for (int y = 0; y < dma_display->height(); y++) {
int16_t v = 0;
uint8_t wibble = sin8(time_counter);
v += sin16(x * wibble * 3 + time_counter);
v += cos16(y * (128 - wibble) + time_counter);
v += sin16(y * x * cos8(-time_counter) / 8);

currentColor = ColorFromPalette(currentPalette, (v >> 8) + 127); //, brightness, currentBlendType);
dma_display->drawPixelRGB888(x, y, currentColor.r, currentColor.g, currentColor.b);
}
}

++time_counter;
++cycles;
++fps;

if (cycles >= 1024) {
time_counter = 0;
cycles = 0;
currentPalette = palettes[random(0,sizeof(palettes)/sizeof(palettes[0]))];
}

// print FPS rate every 5 seconds
// Note: this is NOT a matrix refresh rate, it's the number of data frames being drawn to the DMA buffer per second
if (fps_timer + 5000 < millis()){
Serial.printf_P(PSTR("Effect fps: %d\n"), fps/5);
fps_timer = millis();
fps = 0;
}
}

【运行效果】


05_AnimatedGIFPanel_SD

【代码分析】

  • setup():完成 SD 卡、HUB75 面板和 GIF 解码器的初始化,为后续播放 GIF 动画做准备。
  • SD_MMC.setPins():配置 SD 卡使用的时钟、命令和数据引脚。
  • SD_MMC.begin("/sdcard", true):以 1-bit 模式挂载 SD 卡文件系统。
  • SD_MMC.cardType()cardSize()totalBytes()usedBytes():读取卡类型、容量和空间占用信息,用于确认存储介质状态。
  • HUB75_I2S_CFG mxconfig(...):配置 HUB75 面板的宽度、高度和级联数量。
  • dma_display = new MatrixPanel_I2S_DMA(mxconfig):创建 DMA 显示对象。
  • dma_display->begin():启动 DMA 显示并分配显示缓冲区。
  • SD_MMC.open("/gifs"):打开 GIF 文件目录。
  • root.openNextFile():遍历 /gifs 目录中的文件。
  • GifFiles.push_back(filename):将找到的 GIF 文件路径保存到列表中,供后续循环播放使用。
  • gif.begin(LITTLE_ENDIAN_PIXELS):初始化 GIF 解码器,并设置像素字节序。
void setup()
{
Serial.begin(115200);

// **************************** Setup SD Card access via SD_MMC 1-bit ****************************
if (!SD_MMC.setPins(BSP_SD_CLK, BSP_SD_CMD, BSP_SD_D0)) {
Serial.println("SD_MMC setPins Failed");
return;
}

if(!SD_MMC.begin("/sdcard", true)){
Serial.println("Card Mount Failed");
return;
}
uint8_t cardType = SD_MMC.cardType();

if(cardType == CARD_NONE){
Serial.println("No SD card attached");
return;
}

Serial.print("SD Card Type: ");
if(cardType == CARD_MMC){
Serial.println("MMC");
} else if(cardType == CARD_SD){
Serial.println("SDSC");
} else if(cardType == CARD_SDHC){
Serial.println("SDHC");
} else {
Serial.println("UNKNOWN");
}

uint64_t cardSize = SD_MMC.cardSize() / (1024 * 1024);
Serial.printf("SD Card Size: %lluMB\n", cardSize);

//listDir(SD_MMC, "/", 1, false);

Serial.printf("Total space: %lluMB\n", SD_MMC.totalBytes() / (1024 * 1024));
Serial.printf("Used space: %lluMB\n", SD_MMC.usedBytes() / (1024 * 1024));



// **************************** Setup DMA Matrix ****************************
HUB75_I2S_CFG mxconfig(
PANEL_RES_X, // module width
PANEL_RES_Y, // module height
PANEL_CHAIN // Chain length
);

// Keep ESP32-S3 default HUB75 mapping to avoid Flash/PSRAM reserved pins.

//mxconfig.clkphase = false;
//mxconfig.driver = HUB75_I2S_CFG::FM6126A;

// Display Setup
dma_display = new MatrixPanel_I2S_DMA(mxconfig);

// Allocate memory and start DMA display
if( not dma_display->begin() )
Serial.println("****** !KABOOM! HUB75 memory allocation failed ***********");

dma_display->setBrightness8(128); //0-255
dma_display->clearScreen();


// **************************** Setup Sketch ****************************
Serial.println("Starting AnimatedGIFs Sketch");

// SD CARD STOPS WORKING WITH DMA DISPLAY ENABLED>...

File root = SD_MMC.open("/gifs");
if(!root){
Serial.println("Failed to open directory");
return;
}

File file = root.openNextFile();
while(file){
if(!file.isDirectory())
{
Serial.print(" FILE: ");
Serial.print(file.name());
Serial.print(" SIZE: ");
Serial.println(file.size());

std::string filename = "/gifs/" + std::string(file.name());
Serial.println(filename.c_str());

GifFiles.push_back( filename );
// Serial.println("Adding to gif list:" + String(filename));
totalFiles++;

}
file = root.openNextFile();
}

file.close();
Serial.printf("Found %d GIFs to play.", totalFiles);
//totalFiles = getGifInventory("/gifs");



// This is important - Set the right endianness.
gif.begin(LITTLE_ENDIAN_PIXELS);

}

【运行效果】


06_BitmapIcons

【代码分析】

  • setup():完成显示初始化,并通过渐变方式绘制 WiFi 图标,验证位图资源与绘制接口是否正常。
  • dma_display->begin():启动 HUB75 面板显示。
  • dma_display->setBrightness8(90):设置面板亮度。
  • dma_display->fillScreen() / dma_display->clearScreen():初始化和切换阶段清空画面,避免残影干扰。
  • for (int r = 0; r < 255; r++):逐步增加红色分量,用于生成淡入动画。
  • drawXbm565(0,0,64,32, wifi_image1bit, ...):将 WiFi 的 XBM 位图绘制到屏幕上。
  • loop():循环切换不同图标,实现图标轮播显示。
  • drawXbm565(5,0, 32, 32, icon_bits[current_icon]):绘制当前索引对应的图标数据。
  • icon_name[current_icon]:通过串口输出当前显示的图标名称,便于调试。
  • current_icon = (current_icon + 1) % num_icons:循环更新图标索引,确保轮播不会越界。
void setup() {

// put your setup code here, to run once:
delay(1000); Serial.begin(115200); delay(200);


/************** DISPLAY **************/
Sprintln("...Starting Display");
dma_display = new MatrixPanel_I2S_DMA(mxconfig);
dma_display->begin();
dma_display->setBrightness8(90); //0-255
dma_display->clearScreen();

dma_display->fillScreen(dma_display->color444(0, 0, 0));

// Fade a Red Wifi Logo In
for (int r=0; r < 255; r++ )
{
drawXbm565(0,0,64,32, wifi_image1bit, dma_display->color565(r,0,0));
delay(10);
}

delay(2000);
dma_display->clearScreen();
}


void loop() {

// Loop through Weather Icons
Serial.print("Showing icon ");
Serial.println(icon_name[current_icon]);
drawXbm565(5,0, 32, 32, icon_bits[current_icon]);

current_icon = (current_icon +1 ) % num_icons;
delay(2000);
dma_display->clearScreen();

}

【运行效果】


07_Pixel_Mapping_Test

【代码分析】

  • loop():按行列顺序逐点点亮像素,用于检查面板像素映射与软件配置是否一致。
  • for (int i ...) / for (int j ...):遍历 FourScanPanel 的全部像素坐标。
  • FourScanPanel->drawPixel(j, i, FourScanPanel->color565(255, 0, 0)):将当前像素点亮为红色,形成可观察的扫描轨迹。
  • delay(30):让扫描点以较慢速度移动,便于观察实际点亮顺序。
  • dma_display->clearScreen():整屏扫描完成后清空画面,开始下一轮测试。
  • delay(2000):在每轮扫描结束后停留 2 秒,方便确认映射结果是否正确。
void loop() {
for (int i = 0; i < FourScanPanel->height(); i++)
{
for (int j = 0; j < FourScanPanel->width(); j++)
{
FourScanPanel->drawPixel(j, i, FourScanPanel->color565(255, 0, 0));
delay(30);
}
}
delay(2000);
dma_display->clearScreen();
} // end loop

【运行效果】



ESP-IDF

本章节包含以下部分,请按需阅读:

ESP-IDF 入门教程

初次接触 ESP32 ESP-IDF 开发,想要快速上手?我们为您准备了一套通用的 入门教程

请注意:该教程使用 ESP32-S3-Zero 作为教学示例,所有硬件代码均基于其引脚布局。在动手实践前,建议您对照手中的开发板引脚图,确认引脚配置无误。

配置 ESP-IDF 开发环境

备注

以下内容以 Windows 系统为例,使用 VS Code + ESP-IDF 扩展 的方式进行开发。Mac/Linux 用户请参考 官方说明

版本选择

此部分图示以安装 ESP-IDF V5.2.2 为例示范,安装时请选用与您开发板示例匹配的 ESP-IDF 版本。

安装 ESP-IDF 开发环境

  1. 前往 ESP-IDF Installation Manager 下载 ESP-IDF 安装管理器。这是乐鑫最新推出的跨平台安装工具,下文将演示如何使用其离线安装功能。

    在页面中点击 Offline Installer 标签,然后在筛选栏中选择 Windows 操作系统和你需要的 ESP-IDF 版本(图示仅为参考,请以实际为准)。


    确认选择无误后,点击下载按钮。浏览器将自动同时下载两个文件:一个是 ESP-IDF 离线整合包(.zst),另一个是 ESP-IDF 安装器(.exe)


    请耐心等待两个文件下载完成。

  2. 下载完成后,双击运行 ESP-IDF 安装器(eim-gui-windows-x64.exe)

    启动后,可在右上角将界面语言切换为中文。


    安装工具会自动检测同一目录下是否存在离线整合包。点击 从存档安装


    接下来,选择安装路径。建议使用默认路径;若需自定义,请确保路径中不包含中文或空格。确认无误后,点击 开始安装


  3. 当看到如下界面时,表示 ESP-IDF 已安装成功。


  4. 建议同时安装驱动程序。点击 完成安装,然后点击 安装驱动程序


安装 Visual Studio Code 与 ESP-IDF 扩展

  1. 下载并安装 Visual Studio Code

  2. 安装时建议勾选 通过 Code 打开操作添加到 Windows 资源管理器文件上下文菜单,以便快速打开项目文件夹。

  3. 在 VS Code 中,点击侧边活动栏中的 扩展图标 扩展图标(或使用快捷键 Ctrl + Shift + X)打开 扩展 视图。

  4. 在搜索框中输入 ESP-IDF,找到 ESP-IDF 扩展并点击安装。


  5. 当 ESP-IDF 扩展版本 ≥ 2.0 时,扩展会自动检测并识别上述步骤中安装的 ESP-IDF 环境,无需手动配置。

示例程序

IDF 示例程序:ESP32-S3-RGB-Matrix 示例程序-GitHub IDF 示例程序:ESP32-S3-RGB-Matrix 示例程序-Gitee

下面给出每个示例的目的、要点说明与运行效果(以便快速上手)。

示例程序基础例程说明
01_Matrix_RGBW简单测试 RGBW 灯颜色切换
02_Matrix_Font_5x7测试 5x7 字体显示
03_Matrix_QMI测试 QMI 功能显示
04_Matrix_RTC测试 RTC 时间显示
05_Matrix_SDCard测试 SD 卡挂载与容量读取
06_Matrix_SHTC3测试 SHTC3 温湿度传感器
07_Matrix_WiFi测试 WiFi 连接
08_Matrix_Audio测试音频播放

注意
  • 03_Matrix_QMI,06_Matrix_SHTC3,08_Matrix_Audio 这个三个示例是针对64x64像素大小的屏幕设计的,如果使用其他像素大小的屏幕,会出现文字显示重叠或错位。

01_Matrix_RGBW


【代码分析】

  • rgbw_start():循环切换板载 RGBW 灯颜色,用于验证灯光驱动与日志输出是否正常。
  • sizeof(rgbw_colors) / sizeof(rgbw_colors[0]):计算预设颜色数组长度,供循环切换使用。
  • bsp_display_lock():加锁后操作显示界面,避免与其他显示任务冲突。
  • lv_obj_set_style_bg_color(screen, lv_color_hex(0x000000), 0):将当前屏幕背景设置为黑色,减少灯光测试时的界面干扰。
  • rgbw_set_color(rgbw_colors[color_index].hex_color):把当前颜色值输出到 RGBW 灯珠。
  • ESP_LOGI(TAG, "Current color: %s", ...):打印当前颜色名称,便于调试和观察切换顺序。
  • vTaskDelay(pdMS_TO_TICKS(2000)):每种颜色保持 2 秒,方便观察显示效果。
  • if (color_index >= num_colors):颜色索引到达末尾后回到起点,实现循环切换。
void rgbw_start(void) {
/* =======================
* 1. Basic Parameters
* ======================= */
int color_index = 0;
const int num_colors = sizeof(rgbw_colors) / sizeof(rgbw_colors[0]);

/* =======================
* 2. Init Screen
* ======================= */
bool locked = bsp_display_lock(1000);
if (locked) {
lv_obj_t *screen = lv_scr_act();
lv_obj_set_style_bg_color(screen, lv_color_hex(0x000000), 0);
bsp_display_unlock();
}
/* =======================
* 3. Loop Colors
* ======================= */
while (true) {
locked = bsp_display_lock(1000);
if (locked) {
rgbw_set_color(rgbw_colors[color_index].hex_color);
bsp_display_unlock();
}
ESP_LOGI(TAG, "Current color: %s", rgbw_colors[color_index].name);
vTaskDelay(pdMS_TO_TICKS(2000));
color_index++;
if (color_index >= num_colors) {
color_index = 0;
}
}
}

【运行效果】



02_Matrix_Font_5x7


【代码分析】

  • font_5x7_start():启动 5x7 字体示例界面,并保持任务常驻运行。
  • ESP_LOGI(TAG, "Matrix Font 5x7 start"):输出启动日志,便于确认示例已经进入运行状态。
  • bsp_display_lock(0):进入 LVGL 显示上下文前先加锁,确保界面初始化过程安全。
  • font_5x7_ui_init():创建 5x7 字体示例所需的界面对象。
  • font_5x7_ui_apply():将字体、布局和默认文本等配置应用到界面上。
  • while (true):保持任务持续存在,避免示例初始化后立即退出。
  • vTaskDelay(pdMS_TO_TICKS(1000)):空闲等待,降低任务空转占用。
void font_5x7_start(void) {
/* =======================
* 1. Start Display
* ======================= */
ESP_LOGI(TAG, "Matrix Font 5x7 start");
/* =======================
* 2. Init UI (LVGL Locked)
* ======================= */
bool locked = bsp_display_lock(0);
if (locked) {
font_5x7_ui_init();
font_5x7_ui_apply();
bsp_display_unlock();
}

/* =======================
* 3. Idle Loop
* ======================= */
while (true) {
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】


03_Matrix_QMI


【代码分析】

  • qmi_start():完成 QMI8658 传感器界面初始化、驱动启动和定时刷新配置。
  • qmi_ui_init():创建 QMI8658 数据显示界面。
  • middle_init_qmi8658():初始化 QMI8658 传感器驱动。
  • qmi_state.qmi_init_ret:保存传感器初始化结果,供界面层判断状态并显示提示。
  • example_ui_install_timer(100, qmi_data_update):安装 100 ms 周期定时器,定时刷新姿态或加速度数据。
  • qmi_data_update:在定时回调中更新传感器数据与界面显示。
  • while (true):保持任务常驻运行。
  • vTaskDelay(pdMS_TO_TICKS(1000)):空闲等待,减少任务资源占用。
void qmi_start(void) {
/* =======================
* 1. Start Display & UI
* ======================= */
bool locked = bsp_display_lock(0);
if (locked) {
qmi_ui_init();
bsp_display_unlock();
}

/* =======================
* 2. Start Sensor & Timer
* ======================= */
qmi_state.qmi_init_ret = middle_init_qmi8658();
locked = bsp_display_lock(0);
if (locked) {
example_ui_install_timer(100, qmi_data_update);
bsp_display_unlock();
}

/* =======================
* 3. Idle Loop
* ======================= */
while (true) {
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】


04_Matrix_RTC


【代码分析】

  • rtc_start():完成 RTC 界面初始化、设时、闹钟配置和实时刷新。
  • rtc_ui_init():创建时间显示相关的界面元素。
  • middle_rtc_init():初始化 RTC 驱动与底层硬件接口。
  • middle_rtc_set_time(rtc_state.rtc_time):将状态结构体中的初始时间写入 RTC 芯片。
  • middle_rtc_alarm(3):配置 RTC 闹钟测试条件,用于验证闹钟功能是否正常。
  • example_ui_install_timer(1, rtc_data_update):安装高频刷新定时器,使界面实时同步当前时间。
  • rtc_data_update:在回调中读取 RTC 数据并更新显示内容。
  • while (true):保持 RTC 示例任务持续运行。
void rtc_start(void) {
bool locked = bsp_display_lock(0);
if (locked) {
rtc_ui_init();
bsp_display_unlock();
}
middle_rtc_init();
middle_rtc_set_time(rtc_state.rtc_time);
middle_rtc_alarm(3);
locked = bsp_display_lock(0);
if (locked) {
example_ui_install_timer(1, rtc_data_update);
bsp_display_unlock();
}
while (true) {
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】


05_Matrix_SDCard


【代码分析】

  • sdcard_start():完成 SD 卡界面初始化、底层驱动启动和状态定时刷新。
  • sdcard_ui_init():创建用于显示挂载状态、容量和存储信息的界面组件。
  • middle_sdcard_init():执行 SD 卡底层初始化,通常包括总线配置、卡识别和文件系统挂载。
  • example_ui_install_timer(1000, sdcard_data_update):安装 1 秒周期定时器,定时刷新 SD 卡状态与容量信息。
  • sdcard_data_update:在回调中更新 SD 卡显示内容。
  • while (true):保持示例任务持续运行。
  • vTaskDelay(pdMS_TO_TICKS(1000)):空闲等待,减少任务占用。
void sdcard_start(void) {
/* =======================
* 1. Start Display & UI
* ======================= */
bool locked = bsp_display_lock(0);
if (locked) {
sdcard_ui_init();
bsp_display_unlock();
}

/* =======================
* 2. Init SD Card
* ======================= */
middle_sdcard_init();

/* =======================
* 3. Periodic Refresh
* ======================= */
locked = bsp_display_lock(0);
if (locked) {
example_ui_install_timer(1000, sdcard_data_update);
bsp_display_unlock();
}

/* =======================
* 4. Idle Loop
* ======================= */
while (true) {
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】


06_Matrix_SHTC3


【代码分析】

  • shtc3_start():完成 SHTC3 界面初始化、驱动启动和温湿度数据周期刷新。
  • shtc3_ui_init():创建温度、湿度和状态提示等界面元素。
  • middle_init_shtc3():初始化 SHTC3 传感器驱动。
  • shtc3_state.shtc3_init_ret:保存初始化结果,供界面层判断是否正常显示数据。
  • example_ui_install_timer(500, shtc3_data_update):安装 500 ms 周期定时器,定时更新传感器数据。
  • shtc3_data_update:在回调中读取温湿度信息并刷新界面。
  • while (true):保持示例任务持续运行。
  • vTaskDelay(pdMS_TO_TICKS(1000)):空闲等待,降低任务占用。
void shtc3_start(void) {
/* =======================
* 1. Start Display & UI
* ======================= */
bool locked = bsp_display_lock(0);
if (locked) {
shtc3_ui_init();
bsp_display_unlock();
}
/* =======================
* 2. Init Sensor & Timer
* ======================= */
shtc3_state.shtc3_init_ret = middle_init_shtc3();
locked = bsp_display_lock(0);
if (locked) {
example_ui_install_timer(500, shtc3_data_update);
bsp_display_unlock();
}

/* =======================
* 3. Idle Loop
* ======================= */
while (true){
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】


07_Matrix_WiFi


【代码分析】

  • wifi_start():完成 WiFi 界面初始化、STA 参数配置、驱动启动和状态刷新。
  • wifi_ui_init():创建网络状态显示界面。
  • middle_wifi_set_sta_config(WIFI_STA_SSID, WIFI_STA_PASS):设置目标热点的 SSID 和密码。
  • middle_wifi_init():启动 WiFi 驱动并发起连接流程。
  • wifi_state.wifi_init_ret:保存 WiFi 初始化结果,供界面显示连接状态。
  • example_ui_install_timer(1000, wifi_data_update):安装 1 秒周期定时器,定时刷新连接状态和网络信息。
  • wifi_data_update:在回调中更新 WiFi 连接状态、IP 地址等界面内容。
  • while (true):保持示例任务持续运行。
void wifi_start(void) {
/* =======================
* 1. Start Display & UI
* ======================= */
bool locked = bsp_display_lock(0);
if (locked) {
wifi_ui_init();
bsp_display_unlock();
}

/* =======================
* 2. Configure & Enable WiFi
* ======================= */
middle_wifi_set_sta_config(WIFI_STA_SSID, WIFI_STA_PASS);
wifi_state.wifi_init_ret = middle_wifi_init();

/* =======================
* 3. Periodic Refresh
* ======================= */
locked = bsp_display_lock(0);
if (locked) {
example_ui_install_timer(1000, wifi_data_update);
bsp_display_unlock();
}

/* =======================
* 4. Idle Loop
* ======================= */
while (true) {
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】


08_Matrix_Audio


【代码分析】

  • audio_start():完成音频界面初始化、音频任务创建和状态定时刷新。
  • audio_ui_init():创建音量、播放状态或频谱相关的界面元素。
  • audio_state.audio_out_vol = VOLUME:设置默认音频输出音量。
  • xTaskCreate(audio_task, "aud", 4096, NULL, tskIDLE_PRIORITY + 4, NULL):创建独立音频任务,在后台处理音频业务逻辑。
  • example_ui_install_timer(100, audio_data_update):安装 100 ms 周期定时器,定时同步音频状态到界面。
  • audio_data_update:在回调中更新播放状态、音量或其他音频信息。
  • while (true):保持示例任务持续运行。
  • vTaskDelay(pdMS_TO_TICKS(1000)):空闲等待,降低主任务占用。
void audio_start(void) {
/* =======================
* 1. Start Display & UI
* ======================= */
bool locked = bsp_display_lock(0);
if (locked) {
audio_ui_init();
bsp_display_unlock();
}
/* =======================
* 2. Start Audio Task
* ======================= */
audio_state.audio_out_vol = VOLUME;
xTaskCreate(audio_task, "aud", 4096, NULL, tskIDLE_PRIORITY + 4, NULL);
/* =======================
* 3. Periodic UI Refresh
* ======================= */
locked = bsp_display_lock(0);
if (locked) {
example_ui_install_timer(100, audio_data_update);
bsp_display_unlock();
}
/* =======================
* 4. Idle Loop
* ======================= */
while (true) {
vTaskDelay(pdMS_TO_TICKS(1000));
}
}

【运行效果】



相关资料

1. 硬件资料

开发板设计文件

2. 技术手册

3. 示例程序

4. 软件工具