1. 硬件准备与环境搭建
第一次拿到合宙ESP32 C3开发板和0.96寸ST7735显示屏时,我花了半小时研究怎么把它们正确连接起来。这块开发板尺寸只有54mm×26mm,但集成了Wi-Fi和蓝牙功能,主频能达到160MHz,对于驱动小型显示屏来说性能绰绰有余。
核心硬件清单:
- 合宙ESP32 C3开发板(注意要确认是RISC-V架构版本)
- 0.96寸ST7735驱动IPS显示屏(分辨率80×160)
- 杜邦线若干(如果不用排针直接对接的话)
- Micro USB数据线(用于供电和程序烧录)
实际接线时最容易出错的是引脚对应关系。我刚开始就接反了SCK和MOSI线,导致屏幕一直白屏。正确的接线方式应该是:
| 开发板引脚 | 显示屏引脚 | 功能说明 |
|---|---|---|
| GPIO2 | SCK | 时钟信号 |
| GPIO3 | SDA | 数据输入 |
| GPIO10 | RES | 复位信号 |
| GPIO6 | DC | 数据/命令选择 |
| GPIO7 | CS | 片选信号 |
| GPIO11 | BL | 背光控制 |
提示:如果屏幕背光不亮,记得检查BL引脚是否接对,必要时可以单独接3.3V测试背光是否正常
开发环境我推荐使用Arduino IDE,需要先安装ESP32开发板支持包。在首选项的附加开发板管理器网址中添加:
https://raw.githubusercontent.com/espressif/arduino-esp32/gh-pages/package_esp32_index.json然后在开发板管理器中搜索安装"esp32"。
2. 库安装与配置技巧
驱动ST7735显示屏最方便的库是Arduino_GFX_Library,这个库支持多种显示控制器,而且性能优化得很好。我在GitHub上找到这个库时,发现它有超过100个star,说明社区认可度很高。
安装方法有两种:
- 通过Arduino库管理器直接搜索安装
- 手动下载ZIP包,在IDE中选择"项目"→"加载库"→"添加.ZIP库"
安装完成后,需要特别注意库的示例程序中有个关键配置容易出错。在Arduino_GFX_Library/examples/PDQ_graphicstest示例中,找到这两行关键代码:
Arduino_DataBus *bus = new Arduino_ESP32SPI(6 /* DC */, 7 /* CS */, 2 /* SCK */, 3 /* MOSI */, GFX_NOT_DEFINED /* MISO */); Arduino_GFX *gfx = new Arduino_ST7735(bus, 10 /*RST*/, 0 /* rotation */, false /* IPS */, 80 /* width */, 160 /* height */, 24 /* col offset 1 */, 0 /* row offset 1 */, 24 /* col offset 2 */, 0 /* row offset 2 */);这里有几个参数需要根据实际情况调整:
- 旋转角度(rotation):0-3分别对应0°、90°、180°、270°
- IPS面板:如果是IPS屏要设为true
- 偏移量:不同批次屏幕可能有差异,我的这块需要设置x偏移24像素
我遇到过屏幕显示内容偏移的问题,就是通过调整最后那几个偏移参数解决的。建议先用默认值测试,如果发现显示内容不在正中,再逐步调整这些偏移值。
3. 基础功能测试与优化
第一次成功点亮屏幕时,建议先运行库自带的graphicstest示例。这个测试程序会依次演示各种图形绘制功能,包括:
- 全屏填充测试(检查有无坏点)
- 文字显示(测试不同大小和颜色)
- 基本图形绘制(线、矩形、圆形等)
- 性能测试(显示每种操作的耗时)
测试时我发现一个有趣的现象:ESP32 C3的SPI时钟可以开到40MHz,但实际测试发现设置为27MHz时稳定性最好。修改方法是在代码中添加:
#define SPI_FREQUENCY 27000000如果遇到屏幕闪烁问题,可以尝试以下优化:
- 降低SPI频率
- 检查电源是否稳定(建议外接电源)
- 缩短接线长度(长线容易引入干扰)
- 在CS引脚上加10K上拉电阻
性能测试结果显示,这块开发板驱动0.96寸屏完全无压力:
- 全屏刷新:约18ms
- 文字显示:平均每个字符0.2ms
- 图形绘制:简单图形1-5ms,复杂图形10-15ms
4. 实战项目:打造天气信息显示屏
掌握了基础驱动后,我决定做个实用的天气显示屏。这个项目需要用到Wi-Fi功能获取网络数据,正好展示ESP32 C3的多任务处理能力。
首先需要安装必要的库:
#include <ArduinoJson.h> #include <WiFi.h> #include <HTTPClient.h>核心代码结构分为三部分:
- Wi-Fi连接模块
void connectWifi() { WiFi.begin("你的SSID", "密码"); while (WiFi.status() != WL_CONNECTED) { delay(500); Serial.print("."); } }- 天气数据获取
String getWeatherData() { HTTPClient http; http.begin("http://api.openweathermap.org/data/2.5/weather?q=Beijing&appid=你的API密钥"); int httpCode = http.GET(); if(httpCode > 0) { return http.getString(); } return ""; }- 显示界面设计
void drawWeatherUI(String jsonData) { DynamicJsonDocument doc(1024); deserializeJson(doc, jsonData); float temp = doc["main"]["temp"]; int humidity = doc["main"]["humidity"]; gfx->setTextSize(2); gfx->setCursor(10, 30); gfx->printf("Temp: %.1f C", temp - 273.15); gfx->drawRect(10, 60, 60, 10, WHITE); gfx->fillRect(10, 60, map(humidity, 0, 100, 0, 60), 10, BLUE); }这个项目我遇到了两个坑:
- 内存不足导致重启:解决方法是用
DynamicJsonDocument代替StaticJsonDocument,并根据实际数据大小调整缓冲区 - 屏幕刷新闪烁:通过双缓冲技术解决,先绘制到内存再一次性刷新到屏幕
最终效果很不错,屏幕每10分钟自动更新天气信息,待机电流只有15mA,用移动电源可以连续工作好几天。