1. OLED驱动芯片概述:SSD1306/SSH1106与显示原理
各位同学,咱们这门课要啃的硬骨头,就是怎么用SPI把OLED屏幕点亮、画图、显示文字。第一章,先把底层的芯片和原理搞清楚。我做了这么多年嵌入式,发现很多新手上来就抄代码,结果屏幕不亮、花屏、坐标算错,根本原因就是没搞懂驱动芯片在干什么。
说白了,OLED驱动芯片就是屏幕的“大脑”。你通过SPI发指令和数据给它,它负责把每个像素点亮或熄灭。今天咱们就聊聊市面上最常见的两款芯片:SSD1306和SSH1106。
1.1 常见驱动芯片:SSD1306 vs SSH1106
这两款芯片,我估计你至少听过其中一个。SSD1306是绝对的“街机”,淘宝上几块钱的0.96寸蓝屏、白屏,十有八九都是它。SSH1106则常见于1.3寸或更大尺寸的屏幕。
它们有什么区别?我整理了一个表格,你一看就明白:
| 特性 | SSD1306 | SSH1106 |
|---|---|---|
| 最大分辨率 | 128×64 | 132×64 |
| 内部GRAM | 128×64 bits | 132×64 bits |
| 页数 | 8页(每页8行) | 8页(每页8行) |
| 列地址范围 | 0~127 | 0~131 |
| 常见屏幕尺寸 | 0.96寸 | 1.3寸 |
| SPI时序 | Mode 0/3 兼容 | Mode 0/3 兼容 |
关键点:SSH1106的列地址比SSD1306多了4列(132 vs 128)。如果你用SSD1306的驱动去驱动SSH1106的屏幕,最右边4列像素会显示异常。我曾经在这个坑里爬了整整一个下午。
1.2 OLED显示原理:像素是怎么亮的?
OLED和LCD不一样。LCD需要背光,OLED是自发光。每个像素就是一个微小的有机发光二极管,电流通过它就亮,电流大小决定亮度。
你想想看,一个128×64的屏幕,总共有8192个像素点。驱动芯片不可能给每个像素单独拉一根线——那得8000多根引脚,谁也做不出来。
所以,芯片内部用了矩阵扫描的方式。它把屏幕分成行和列,每次只点亮一行,然后快速切换到下一行。只要切换速度够快(通常>60Hz),人眼就感觉整个屏幕都在亮。
我画了一张图,帮你理解这个结构:
我的经验:扫描频率低于50Hz时,人眼能明显感觉到闪烁。我建议你至少设置刷新率为70Hz。如果CPU负载高,可以降到60Hz,但不能再低了。
1.3 像素与分辨率:坐标映射的基础
分辨率就是屏幕上有多少个像素点。128×64,意思是有128列、64行。每个像素用1 bit表示——亮就是1,灭就是0。
但驱动芯片内部不是这么存的。它把64行分成了8个页(Page),每页8行。你发数据的时候,是按页发的,一次发8个像素(一列)。
我举个例子,你就懂了:
- 页0:第0~7行
- 页1:第8~15行
- 页2:第16~23行
- ……
- 页7:第56~63行
每个页有128列。所以,你要显示一个像素在(x, y)位置,得先算出它在哪一页,再算出这一页的第几行。
公式很简单:
page = y / 8; // 页号
bit = y % 8; // 该页内的行偏移(0~7)
column = x; // 列号(0~127)
然后你发命令设置页地址和列地址,再发一个字节的数据。这个字节的bit[bit]位就是你要点的像素。
注意:SSD1306的列地址是自动递增的。你发完一个字节后,列地址会自动加1。如果你连续发128个字节,就能填满一整页。这个特性在刷全屏时非常有用,但也容易出错——我曾经因为忘记重置列地址,导致数据写到下一页去了,屏幕显示全乱套。
1.4 三种接口模式:SPI、I2C、并行
SSD1306支持三种接口,通过BS0、BS1、BS2引脚配置。咱们这门课主要讲SPI,但我觉得有必要让你知道其他接口的存在:
| 接口模式 | 引脚数 | 速度 | 适用场景 |
|---|---|---|---|
| 4线SPI | 4(CS, DC, SCK, MOSI) | ~10MHz | 通用,引脚少,速度快 |
| 3线SPI | 3(CS, SCK, MOSI) | ~10MHz | 引脚更少,但需要9位数据格式 |
| I2C | 2(SCL, SDA) | ~400kHz | 引脚最少,但速度慢 |
| 6800/8080并行 | 8+ | ~20MHz | 速度快,但占用引脚多 |
我的建议:除非你引脚极度紧张(比如只有I2C总线可用),否则优先用4线SPI。它比I2C快一个数量级,刷动画不卡顿。我做过一个项目,用I2C刷128×64的图片,肉眼可见的从上到下刷新,体验很差。换成SPI后,流畅度完全不一样。
1.5 本章小结
好了,第一章的内容就这些。你只需要记住三件事:
- 芯片选型:SSD1306是128×64,SSH1106是132×64,别搞混。
- 显示原理:矩阵扫描,按页存储,每页8行。
- 坐标映射:先算页号,再算位偏移,最后发数据。