SSD1306 I2C 写入显存示例
以下是一个简单的示例,展示如何通过 I2C 向 SSD1306 写入显存数据:
- #include <avr/io.h>
- #include <util/delay.h>
- #define SSD1306_I2C_ADDRESS 0x3C // SSD1306 的 I2C 地址
- void I2C_Init() {
- // 初始化 I2C(根据你的单片机配置)
- TWSR = 0x00; // 预分频器 = 1
- TWBR = 0x48; // 设置比特率
- TWCR = (1 << TWEN); // 使能 I2C
- }
- void I2C_Start() {
- TWCR = (1 << TWINT) | (1 << TWSTA) | (1 << TWEN);
- while (!(TWCR & (1 << TWINT)));
- }
- void I2C_Stop() {
- TWCR = (1 << TWINT) | (1 << TWSTO) | (1 << TWEN);
- }
- void I2C_Write(uint8_t data) {
- TWDR = data;
- TWCR = (1 << TWINT) | (1 << TWEN);
- while (!(TWCR & (1 << TWINT)));
- }
- void SSD1306_Command(uint8_t cmd) {
- I2C_Start();
- I2C_Write(SSD1306_I2C_ADDRESS << 1); // 发送设备地址(写模式)
- I2C_Write(0x00); // 控制字节:命令
- I2C_Write(cmd); // 发送命令
- I2C_Stop();
- }
- void SSD1306_Data(uint8_t data) {
- I2C_Start();
- I2C_Write(SSD1306_I2C_ADDRESS << 1); // 发送设备地址(写模式)
- I2C_Write(0x40); // 控制字节:数据
- I2C_Write(data); // 发送数据
- I2C_Stop();
- }
- void SSD1306_Init() {
- // 初始化 SSD1306
- SSD1306_Command(0xAE); // 关闭显示
- SSD1306_Command(0xD5); // 设置显示时钟分频
- SSD1306_Command(0x80);
- SSD1306_Command(0xA8); // 设置多路复用率
- SSD1306_Command(0x3F);
- SSD1306_Command(0xD3); // 设置显示偏移
- SSD1306_Command(0x00);
- SSD1306_Command(0x40); // 设置显示起始行
- SSD1306_Command(0x8D); // 电荷泵设置
- SSD1306_Command(0x14);
- SSD1306_Command(0x20); // 内存地址模式
- SSD1306_Command(0x00);
- SSD1306_Command(0xA1); // 段重映射
- SSD1306_Command(0xC8); // COM 输出扫描方向
- SSD1306_Command(0xDA); // COM 引脚硬件配置
- SSD1306_Command(0x12);
- SSD1306_Command(0x81); // 对比度控制
- SSD1306_Command(0xCF);
- SSD1306_Command(0xD9); // 预充电周期
- SSD1306_Command(0xF1);
- SSD1306_Command(0xDB); // VCOMH 电压
- SSD1306_Command(0x40);
- SSD1306_Command(0xA4); // 显示内容从 RAM 中读取
- SSD1306_Command(0xA6); // 正常显示
- SSD1306_Command(0xAF); // 打开显示
- }
- int main(void) {
- I2C_Init();
- SSD1306_Init();
- // 写入显存数据
- for (uint8_t i = 0; i < 128; i++) {
- SSD1306_Data(0xFF); // 点亮所有像素
- }
- while (1) {
- // 主循环
- }
- }
SSD1306 在 I2C 模式下不支持读取显存。
如果需要读取显存,建议使用 SPI 接口,或者在单片机中维护一个显存缓冲区。
|