ESP32玩转1.3寸ST7789屏幕:从点亮到显示中文,一份避坑指南
ESP32玩转1.3寸ST7789屏幕:从点亮到显示中文的完整避坑指南
第一次拿到ESP32和那块小巧的1.3寸ST7789屏幕时,我像大多数初学者一样兴奋——直到真正开始动手才发现,从点亮屏幕到显示中文,每一步都暗藏玄机。这篇文章将带你避开我踩过的所有坑,用最短的时间让这块屏幕焕发生机。
1. 硬件连接:那些容易被忽略的细节
ESP32与ST7789的SPI连接看似简单,但魔鬼藏在细节里。我遇到过至少三种不同引脚定义的1.3寸ST7789模块,最坑的是某些厂商的"默认引脚"与文档完全不符。
1.1 确认你的屏幕版本
先观察屏幕背面,通常会有版本标识。最常见的两种配置:
| 屏幕版本 | SCLK引脚 | MOSI引脚 | RES引脚 | DC引脚 | BLK引脚 |
|---|---|---|---|---|---|
| V1.0 | GPIO18 | GPIO23 | GPIO17 | GPIO16 | GPIO4 |
| V2.0 | GPIO13 | GPIO11 | GPIO12 | GPIO10 | GPIO14 |
提示:如果屏幕完全不亮,先检查背光引脚(BLK)是否接对。有些模块需要持续高电平,有些则需要PWM控制亮度。
1.2 硬件SPI vs 软件SPI
ESP32的硬件SPI(HSPI和VSPI)性能更优,但引脚固定:
// 硬件SPI配置示例 (VSPI) #define TFT_SCLK 18 #define TFT_MOSI 23 #define TFT_MISO 19 // 实际显示可以不用 #define TFT_CS 5 // 如果使用片选 #define TFT_DC 16 #define TFT_RST 17如果这些引脚被占用,可以改用软件SPI,但刷新率会降低:
// 软件SPI配置示例 #define TFT_SCLK 25 #define TFT_MOSI 26 #define TFT_DC 27 #define TFT_RST 142. TFT_eSPI库配置:90%的问题出在这里
Bodmer的TFT_eSPI库功能强大但配置复杂,新手最容易在这里翻车。
2.1 正确安装库的姿势
不要直接从Arduino库管理器安装!这会导致缺少关键配置文件。正确做法:
cd ~/Arduino/libraries git clone --depth=1 https://github.com/Bodmer/TFT_eSPI.git然后必须修改这两个文件:
User_Setup.h- 驱动芯片和引脚定义User_Setup_Select.h- 启用自定义配置
2.2 典型配置陷阱
陷阱1:驱动芯片选错
// 正确选择ST7789驱动 #define ST7789_DRIVER陷阱2:分辨率设置错误
// 1.3寸屏通常是240x240 #define TFT_WIDTH 240 #define TFT_HEIGHT 240陷阱3:引脚定义与硬件不匹配
// 示例配置(根据实际连接修改) #define TFT_MOSI 23 #define TFT_SCLK 18 #define TFT_CS -1 // 未使用片选 #define TFT_DC 16 #define TFT_RST 17 #define TFT_BL 4 // 背光控制注意:
TFT_CS设为-1表示未使用片选引脚,这是很多新手忽略的点。
3. 基础显示测试:从点亮到图形绘制
3.1 最小测试代码
先来段最简单的测试,确认屏幕能正常工作:
#include <TFT_eSPI.h> TFT_eSPI tft = TFT_eSPI(); void setup() { tft.init(); tft.setRotation(1); // 尝试0-3不同旋转角度 tft.fillScreen(TFT_BLACK); tft.setTextColor(TFT_WHITE); tft.drawString("Hello ST7789!", 20, 50, 2); } void loop() {}常见问题排查:
- 如果屏幕全白:检查背光引脚和电压
- 如果显示乱码:检查SPI引脚定义
- 如果颜色异常:检查驱动芯片设置
3.2 图形API实战
TFT_eSPI提供了丰富的绘图功能:
// 绘制几何图形 tft.drawRect(10, 10, 100, 50, TFT_RED); // 矩形 tft.fillCircle(60, 60, 30, TFT_BLUE); // 实心圆 // 渐进色填充 for(int y=0; y<tft.height(); y++) { uint16_t color = tft.color565(y, y, 128); tft.drawFastHLine(0, y, tft.width(), color); }4. 中文显示:从字库制作到优化渲染
这是最让开发者头疼的部分,但掌握方法后其实很简单。
4.1 自定义字库制作全流程
准备工具:
- Processing IDE(https://processing.org/download/)
- 中文字体文件(如微软雅黑,注意版权)
修改Create_font工具: 在TFT_eSPI库的
Tools/Create_Smooth_Font目录下找到Processing项目,添加需要的中文字符:// 在specificUnicodes中添加汉字Unicode static final int[] specificUnicodes = { 0x4f60, 0x597d, // 你好 0x4e2d, 0x6587, // 中文 0x6d4b, 0x8bd5 // 测试 };生成字库文件:
- 运行Processing脚本生成
.vlw文件 - 使用Hex转换工具转为C数组
- 保存为
font_mycn.h头文件
- 运行Processing脚本生成
4.2 高效使用中文字库
#include "font_mycn.h" void showChinese() { tft.loadFont(font_mycn); // 加载自定义字库 tft.setTextColor(TFT_WHITE, TFT_BLACK); tft.drawString("中文测试", 10, 10); tft.unloadFont(); // 释放内存 }性能优化技巧:
- 只包含需要的汉字(减少字库体积)
- 使用
SPIFFS存储大字库(避免占用程序空间) - 预渲染静态文本为位图(减少实时渲染开销)
5. 高级技巧与性能优化
当基础功能实现后,这些技巧能让你的项目更专业。
5.1 双缓冲动画
避免屏幕闪烁的关键技术:
TFT_eSprite sprite = TFT_eSprite(&tft); void setup() { sprite.createSprite(240, 240); // 创建缓冲区 } void loop() { sprite.fillSprite(TFT_BLACK); sprite.drawString("流畅动画", 50, 50); sprite.pushSprite(0, 0); // 一次性刷新 delay(16); // 约60FPS }5.2 触摸屏集成
如果你的模块带触摸功能(XPT2046),可以这样初始化:
#include <XPT2046_Touchscreen.h> #define TOUCH_CS 21 XPT2046_Touchscreen touch(TOUCH_CS); void setup() { touch.begin(); while(!touch.tirqTouched()); // 等待触摸 }5.3 低功耗优化
电池供电项目的关键设置:
// 降低SPI频率 tft.initDMA(true); // 启用DMA SPI.beginTransaction(SPISettings(10000000, MSBFIRST, SPI_MODE0)); // 动态背光控制 digitalWrite(TFT_BL, brightness); // 0-255 PWM从第一次成功点亮屏幕的喜悦,到实现流畅中文显示的成就感,这块1.3寸的小屏幕带给我的远不止技术上的收获。记得在调试最困难的时候,一个简单的GPIO定义错误就让我折腾了整整两天——现在回头看,那些踩过的坑都成了最宝贵的经验。
