概念

SPI

SPI(Serial Peripheral Interface) 协议是由摩托罗拉公司提出的通讯协议,即串行外围设备接口,是一种同步、全双工、主从式接口,但并不是所有的 SPI 都是全双工。来自主机或从机的数据在时钟上升沿或下降沿同步。主机和从机可以同时传输数据。SPI 接口可以是 1 线、2 线 3 线式或 4 线式

产生时钟信号的器件称为 主机。主机和从机之间传输的数据与主机产生的时钟同步。同 I2C 接口相比,SPI 器件支持更高的时钟频率。用户应查阅产品数据手册以了解 SPI 接口的时钟频率规格。

标准 4 线 SPI 芯片的管脚上只占用四根线。

  • MOSI: 主器件数据输出,从器件数据输入。
  • MISO:主器件数据输入,从器件数据输出。
  • SCK: 时钟信号,由主设备控制发出。
  • CS(NSS): 从机设备选择信号,由主设备控制。当 CS 为低电平则选中从器件。

3 线 SPI 没有 MISO,或者 MISOMOSI 共线。

SPI 接口只能有一个主机,但可以有一个或多个从机。下图显示了主机和从机之间的 SPI 连接。来自主机的片选信号用于选择从机。这通常是一个低电平有效信号,拉高时从机与 SPI 总线断开连接。当使用多个从机时,主机需要为每个从机提供单独的片选信号。MOSI 和 MISO 是数据线。MOSI 将数据从主机发送到从机,MISO将数据从从机发送到主机。

2025-01-14T12:44:21.png

ESP32 集成了 4 个 SPI 外设。

  • 其中两个在内部用于访问 ESP32 所连接的闪存。两个控制器共享相同的 SPI 总线信号,并且有一个仲裁器来确定哪个可以访问该总线。
  • 另外两个是通用 SPI 控制器,分别称为 HSPI 和 VSPI。它们向用户开放,具有独立的总线信号,分别具有相同的名称。每条总线具有 3 条 CS 线,最多能控制 6 个 SPI 从设备。

I2C 与 SPI 区别

I2C 只需两根信号线,而标准 SPI 至少四根信号,如果有多个从设备,信号需要更多。一些 SPI 变种虽然只使用三根线—— SCK、CS 和双向的 MISO/MOSI,但 CS 线还是要和从设备一对一根。另外,如果 SPI 要实现多主设备结构,总线系统需额外的逻辑和线路。用 I2C 构建系统总线唯一的问题是有限的 7 位地址空间,但这个问题新标准已经解决 --- 使用 10 位地址。

如果应用中必须使用高速数据传输,那么 SPI 是必然的选择。因为 SPI 是全双工,IIC 的不是。SPI 没有定义速度限制,一般的实现通常能达到甚至超过 10Mbps。IIC 最高的速度也就快速+模式(1Mbps)和高速模式(3.4Mbps),后面的模式还需要额外的 I/O 缓冲区,还并不是总是容易实现的。SPI 适合数据流应用,而 IIC 更适合“字节设备”的多主设备应用。

SPI 有一个非常大的缺陷,主要是没有标准的协议,SPI 比较混乱,主要是没有标准的协议,只有moto的事实标准。所以衍生出多个版本,但没有本质的差异。

OLED 屏幕

OLED,即有机发光二极管(Organic Light Emitting Diode)。OLED 由于同时具备自发光,不需背光源、对比度高、厚度薄、视角广、反应速度快、可用于挠曲性面板、使用温度范围广、构造及制程较简单等优异之特性,被称为是第三代显示技术。

LCD 都需要背光,而 OLED 不需要,因为它是自发光的。这样同样的显示 OLED 效果要来得好一些。以目前的技术,OLED 的尺寸还难以大型化,但是分辨率确可以做到很高。


今天用到的屏幕是 0.96 寸的 SSD1306 芯片驱动的 OLED 屏幕。他的分辨率是 128*64,意思就是横向有 128 个像素点,纵向有 64 个

OLED 显示屏模块接口定义:

  1. GND:电源地。
  2. VCC:电源正(3.3~5V)。
  3. D0:OLED 的 D0 脚,在 SPI 通信中为时钟管脚。
  4. D1:OLED 的 D1 脚,在 SPI 通信中为数据管脚。
  5. RES:OLED 的 RES 脚,用来复位(低电平复位)。
  6. DC:数据和命令控制管脚。
  7. CS:片选管脚。

2025-01-14T12:46:59.png

电路图

2025-01-14T12:56:32.png

程序设计

如果想要使用 Arduino 控制 SSD1306 驱动的 OLED 屏幕,有以下两种第三方库可以使用:

  1. Adafruit_SSD1306 库:专门针对 SSD1306 驱动 OLED 屏幕的显示图形库;
  2. U8G2 库:目前 Arduino 平台上使用最广泛的 OLED 库。

1. Adafruit_SSD1306 控制 OLED 屏幕

想要使用 Adafruit_SSD1306,还需要安装 Adafruit_GFX 第三方库。Arduino 的 Adafruit_GFX 库为我们所有的 LCD 和 OLED 显示器提供了通用语法和图形功能集,也就是说这是一个通用图形库,并不针对特定的显示器型号。

  • Adafruit_GFX 定义了一系列的绘画方法(线,矩形,圆等等),属于基础类,并且最重要的一点,drawPixel 方法由子类来实现;
  • Adafruit_SSD1306 定义了一系列跟 SSD1306 有关的方法,并且重写了 drawPixel 方法,属于扩展类。

首先,我们就需要先下载这两个第三方库,PlatformIO 已经为我们提供了方便的下载途径,我们可以直接在 PlatformIO 的 PIO HOME 页面中选择 Libraries 中分别搜索 Adafruit GFX LibraryAdafruit_SSD1306,然后添加到项目中即可。

SSD1306-12864 就是一个 128X64 像素点阵,这个点阵拥有自己的一套坐标系,在坐标系中,左上角是原点,向右是X轴,向下是Y轴。

在屏幕上显示一些图形和字符

#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // OLED 显示屏宽度
#define SCREEN_HEIGHT 64 // OLED 显示屏高度

// 软件SPI总线
#define OLED_MOSI 13
#define OLED_CLK 18
#define OLED_DC 2
#define OLED_CS 4
#define OLED_RESET 15
Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT,
                      OLED_MOSI, OLED_CLK, OLED_DC, OLED_RESET, OLED_CS);

void setup()
{
  oled.begin();
  oled.clearDisplay();                          // 清除显示
  oled.drawFastHLine(32, 5, 48, SSD1306_WHITE); // 绘制水平线
  oled.drawLine(32, 5, 48, 30, SSD1306_WHITE);  // 绘制线
  oled.drawRect(5, 5, 10, 25, SSD1306_WHITE);   // 绘制矩形
  oled.fillRect(75, 5, 10, 30, SSD1306_WHITE);  // 绘制实心矩形
  oled.setCursor(5, 50);                        // 设置光标位置
  oled.setTextSize(2);                          // 设置字体大小
  oled.setTextColor(WHITE);                     // 设置文本颜色
  oled.println("Hello, world!");                // 显示文字
  oled.display();                               // 显示内容
}

void loop()
{
}

在 OLED 上显示进度条

#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // OLED 显示屏宽度
#define SCREEN_HEIGHT 64 // OLED 显示屏高度

// 软件SPI总线
#define OLED_MOSI 13
#define OLED_CLK 18
#define OLED_DC 2
#define OLED_CS 4
#define OLED_RESET 15
Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT,
                      OLED_MOSI, OLED_CLK, OLED_DC, OLED_RESET, OLED_CS);

// 初始化进度条变量
int progress = 0;

void setup()
{
  oled.begin();
  oled.setTextSize(2);              // 设置字体大小
  oled.setTextColor(SSD1306_WHITE); // 设置文本颜色
  oled.display();                   // 显示内容
}

void loop()
{
  // 清空屏幕
  oled.clearDisplay();

  // 设置光标位置
  oled.setCursor(25, 40);
  // 显示文字
  oled.println("Process");

  // 显示进度条边框
  oled.drawRoundRect(0, 10, 128, 20, 5, SSD1306_WHITE);
  // 显示进度
  oled.fillRoundRect(5, 15, progress, 10, 2, SSD1306_WHITE);

  // 进度递增
  if (progress < 118)
  {
    progress++;
  }
  else
  {
    progress = 0;
  }

  // 刷新屏幕
  oled.display();

  delay(50); // 延迟一段时间后更新显示
}

如果要绘制图片,可以通过这个网站

https://javl.github.io/image2cpp/

2025-01-14T13:50:34.png

#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // OLED 显示屏宽度
#define SCREEN_HEIGHT 64 // OLED 显示屏高度

// 软件SPI总线
#define OLED_MOSI 13
#define OLED_CLK 18
#define OLED_DC 2
#define OLED_CS 4
#define OLED_RESET 15
Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT,
                      OLED_MOSI, OLED_CLK, OLED_DC, OLED_RESET, OLED_CS);

const unsigned char epd_bitmap_ [] PROGMEM = {
    0xff, 0xf0, 0x00, 0x00, 0x30, 0x00, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xd9, 0x20, 0x22, 0x4c, 0xfc, 0x00, 0x16, 0xd6, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xdf, 0x82, 0x08, 0x14, 0xfe, 0x49, 0x0d, 0xb6, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xe6, 0x08, 0x81, 0x8d, 0xfe, 0x08, 0x0b, 0x37, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xb8, 0x40, 0x24, 0x29, 0xff, 0x24, 0x82, 0xdd, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xd8, 0x12, 0x03, 0x19, 0xff, 0x0c, 0x22, 0xfb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x43, 0x00, 0x93, 0x1f, 0xff, 0x8c, 0x01, 0xae, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xee, 0x48, 0x07, 0x3b, 0xff, 0x86, 0x40, 0xed, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xba, 0x02, 0x47, 0x3b, 0xff, 0x12, 0x08, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xd8, 0x90, 0x14, 0x3b, 0xfd, 0x8e, 0x00, 0x53, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xdc, 0x01, 0x0f, 0x3b, 0xfd, 0x86, 0x42, 0xdd, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x64, 0x48, 0x4f, 0x7b, 0xff, 0x97, 0x08, 0x66, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xf9, 0x02, 0x4f, 0x3b, 0xff, 0xa7, 0x00, 0x7b, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xb1, 0x00, 0xcf, 0x3f, 0xff, 0xa6, 0x10, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xd2, 0x48, 0xcf, 0x7f, 0xfe, 0xb6, 0x42, 0xa6, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x72, 0x02, 0x4d, 0xbf, 0xff, 0xb7, 0x02, 0xfb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xa6, 0x20, 0xef, 0xef, 0xfd, 0x76, 0x01, 0x3b, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xdc, 0x08, 0xcf, 0xff, 0xff, 0x4e, 0xc9, 0x6e, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x74, 0x82, 0x6f, 0x7f, 0xff, 0x8f, 0x83, 0x5b, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xdc, 0x20, 0x7e, 0x3f, 0xff, 0xdf, 0x01, 0x9d, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xd9, 0x01, 0x7e, 0x7f, 0x7f, 0xff, 0x01, 0xe7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xed, 0x11, 0xff, 0xff, 0x7f, 0xfe, 0xc9, 0x7e, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xb7, 0x44, 0xff, 0xff, 0x7e, 0xfb, 0x82, 0xdb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xd3, 0x01, 0xff, 0xde, 0x7f, 0xcf, 0x83, 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xdc, 0xe0, 0xf6, 0xfe, 0xff, 0x79, 0x85, 0xed, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xef, 0x24, 0xff, 0xfe, 0xff, 0xff, 0x07, 0x7a, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x3b, 0xb7, 0xff, 0xff, 0xff, 0xff, 0x63, 0x9e, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xf4, 0xde, 0xff, 0xff, 0xff, 0xff, 0x7e, 0xe7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xb7, 0x6c, 0xff, 0xff, 0xfe, 0x7e, 0xf7, 0x7b, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xef, 0xad, 0xff, 0xfb, 0x2f, 0xfe, 0xd9, 0x9f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xf9, 0xbb, 0x7e, 0x4f, 0xff, 0xfe, 0x6f, 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xfc, 0xdb, 0x7f, 0xff, 0xff, 0xff, 0xac, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xbd, 0xff, 0xff, 0xff, 0xfc, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xe6, 0xff, 0xff, 0xff, 0xf9, 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xfd, 0x9f, 0xff, 0xff, 0xf6, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xff, 0xff, 0xdf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xf7, 0xff, 0xff, 0xdf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xfd, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xfe, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0x3f, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0x9f, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xc3, 0xe3, 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xf0, 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xfc, 0x0f, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0x7f, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xfb, 0xfd, 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xff, 0x77, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xfd, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xff, 0xff, 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xfc, 0xff, 0xff, 0x83, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xfb, 0xff, 0xff, 0xc9, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xf8, 0xff, 0xff, 0xcc, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xf6, 0xff, 0xff, 0x96, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0xe2, 0x7f, 0xff, 0x91, 0x87, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xff, 0x89, 0x3f, 0xff, 0xac, 0xd0, 0x2f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xff, 0xf8, 0x34, 0xcf, 0xff, 0x26, 0x36, 0x80, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0xfd, 0x03, 0x26, 0x4f, 0xff, 0x50, 0x89, 0xb6, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x81, 0x6c, 0xc9, 0x37, 0xfc, 0xcc, 0xc9, 0x29, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x32, 0x01, 0x11, 0x23, 0xfc, 0x23, 0x36, 0x4d, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x4c, 0xd9, 0x64, 0xc9, 0xf3, 0x30, 0x91, 0x94, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 
    0x45, 0x16, 0x18, 0x94, 0xf2, 0xcc, 0xcc, 0xb3, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
};

void setup()
{
  oled.begin();
  oled.clearDisplay();
  delay(2000);
}

void loop()
{
  oled.drawBitmap(0, 0, epd_bitmap_, 128, 64, SSD1306_WHITE);
  oled.display();
}

配合进度条实现,进度条加载完显示位图(新年快乐文本)的效果

#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // OLED 显示屏宽度
#define SCREEN_HEIGHT 64 // OLED 显示屏高度

// 软件SPI总线
#define OLED_MOSI 13
#define OLED_CLK 18
#define OLED_DC 2
#define OLED_CS 4
#define OLED_RESET 15
Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT,
                      OLED_MOSI, OLED_CLK, OLED_DC, OLED_RESET, OLED_CS);

const unsigned char epd_bitmap_[] PROGMEM = {
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x80, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x7f, 0x01, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xf8, 0x00, 0x00,
    0x00, 0x00, 0x00, 0xfc, 0x03, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xfc, 0x00, 0x00,
    0x00, 0x00, 0x07, 0xfc, 0x0f, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0xff, 0xfc, 0x00, 0x00,
    0x00, 0x00, 0x03, 0xdc, 0xff, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xff, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x1c, 0xff, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xff, 0xc0, 0x00, 0x00,
    0x00, 0x00, 0x06, 0x3b, 0xff, 0x0c, 0x10, 0x00, 0x00, 0x81, 0x00, 0x1f, 0xff, 0x80, 0x00, 0x00,
    0x00, 0x00, 0x07, 0x7f, 0x9c, 0x3e, 0x1e, 0x3c, 0x01, 0x81, 0x80, 0x0f, 0xff, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x03, 0xff, 0x3c, 0x7e, 0x1f, 0xfe, 0x01, 0x80, 0x88, 0x01, 0xfe, 0xc0, 0x00, 0x00,
    0x00, 0x00, 0x01, 0xfc, 0x38, 0x7c, 0x3f, 0xfe, 0x03, 0xc0, 0xfc, 0x00, 0x3d, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x03, 0xf8, 0x78, 0x78, 0x70, 0x60, 0x03, 0xe1, 0xfc, 0x00, 0x79, 0xf8, 0x00, 0x00,
    0x00, 0x00, 0x07, 0xf8, 0x78, 0xf0, 0x40, 0xc0, 0x03, 0xe3, 0xf8, 0x00, 0x61, 0xff, 0x80, 0x00,
    0x00, 0x00, 0x3f, 0xfc, 0x79, 0xf0, 0x03, 0xf8, 0x17, 0xc7, 0xf0, 0x00, 0xc1, 0xff, 0x00, 0x00,
    0x00, 0x07, 0xff, 0xfe, 0x7b, 0xf0, 0x0f, 0xf0, 0x17, 0xcd, 0xe0, 0x01, 0xc1, 0xfc, 0x00, 0x00,
    0x00, 0x07, 0xff, 0xfc, 0xff, 0xf0, 0x7d, 0xe0, 0x17, 0x99, 0xcc, 0x01, 0x83, 0xf0, 0x00, 0x00,
    0x00, 0x03, 0xef, 0xf8, 0xfe, 0xf0, 0x03, 0xe0, 0x17, 0x13, 0x9e, 0x03, 0x0f, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x1f, 0xe0, 0xf8, 0xf0, 0x1f, 0xf0, 0x1f, 0x37, 0xfc, 0x07, 0x3f, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x3f, 0xe4, 0xf0, 0x70, 0x1e, 0x7c, 0x1f, 0x7f, 0xf0, 0x06, 0xff, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x3f, 0xe6, 0xf0, 0x70, 0x18, 0xfe, 0x1e, 0xff, 0x80, 0x07, 0xf1, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x1e, 0x7e, 0xf0, 0x60, 0x3f, 0xe0, 0x0f, 0xff, 0x00, 0x03, 0xc1, 0xef, 0x80, 0x00,
    0x00, 0x00, 0x00, 0x7f, 0xf0, 0x70, 0xf8, 0x60, 0x07, 0xce, 0x7c, 0x00, 0x61, 0xe1, 0xe0, 0x00,
    0x00, 0x00, 0x78, 0x6f, 0x00, 0x70, 0xe0, 0x60, 0x03, 0x8e, 0x1f, 0x00, 0xe1, 0xe0, 0xe0, 0x00,
    0x00, 0x00, 0x7f, 0xe0, 0x00, 0x70, 0x00, 0x60, 0x03, 0xb8, 0x07, 0x03, 0xe1, 0xe0, 0x70, 0x00,
    0x00, 0x00, 0xff, 0xf0, 0x00, 0xf0, 0x00, 0x60, 0x03, 0x80, 0x03, 0x07, 0xf9, 0xe0, 0x60, 0x00,
    0x00, 0x00, 0x78, 0x70, 0x00, 0x70, 0x00, 0x60, 0x01, 0xc0, 0x00, 0x03, 0x9f, 0xe0, 0x20, 0x00,
    0x00, 0x00, 0x00, 0x30, 0x00, 0x70, 0x00, 0x60, 0x00, 0x00, 0x00, 0x01, 0x0f, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x03, 0xe0, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x60, 0x01, 0x00, 0x00, 0x00, 0x01, 0xc0, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x60, 0x54, 0x01, 0x0c, 0x45, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};

// 初始化进度条变量
int progress = 0;

void setup()
{
  oled.begin();
  oled.setTextSize(2);              // 设置字体大小
  oled.setTextColor(SSD1306_WHITE); // 设置文本颜色
}

void loop()
{
  // 清空屏幕
  oled.clearDisplay();

  // 设置光标位置
  oled.setCursor(25, 40);
  // 显示文字
  oled.println("Process");

  // 显示进度条边框
  oled.drawRoundRect(0, 10, 128, 20, 5, SSD1306_WHITE);
  // 显示进度
  oled.fillRoundRect(5, 15, progress, 10, 2, SSD1306_WHITE);

  // 进度递增
  if (progress < 118)
  {
    progress += 5;
  }
  else
  {
    // 清空屏幕
    oled.clearDisplay();
    oled.drawBitmap(0, 0, epd_bitmap_, 128, 64, SSD1306_WHITE);
    oled.display();
    progress = 0;

    delay(5000);
  }

  // 刷新屏幕
  oled.display();

  delay(50); // 延迟一段时间后更新显示
}

演示视频:https://www.bilibili.com/video/BV196cbewEpy

U8G2 库控制 OLED

U8g2 是嵌入式设备的单色图形库,一句话简单明了。主要应用于嵌入式设备,包括我们常见的单片机。

安装方法与 Adafruit_SSD1306 一致,只需要在 PlatformIO 中的 libraries 中搜索u8g2,添加到项目中即可。

为什么要运用 U8g2 库?也就是说 U8g2 库能带给我们什么样的开发便利,主要考虑几个方面:

  • 平台支持性好,兼容多款开发板如 ESP32、ESP8266、Arduino Uno 等;
  • 显示控制器支持性好,基本上市面上的 OLED 都完美支持;
  • API 众多,特别支持了中文,支持了不同字体,这是一个对于开发者来说不小的福利。
#include <Arduino.h>
#include <U8g2lib.h>

// 构造对象
U8G2_SSD1306_128X64_NONAME_F_4W_SW_SPI u8g2(U8G2_R0, /* clock=*/18, /* data=*/13, 
                                             /* cs=*/4, /* dc=*/2, /* reset=*/15);

void setup(void)
{
  // 初始化 oled 对象
  u8g2.begin();
  // 开启中文字符集支持
  u8g2.enableUTF8Print();
}

void loop(void)
{
  // 设置字体
  u8g2.setFont(u8g2_font_unifont_t_chinese2);
  // 设置字体方向
  u8g2.setFontDirection(0);
  // 
  u8g2.clearBuffer();
  u8g2.setCursor(0, 15);
  u8g2.print("Hello GeeksMan!");
  u8g2.setCursor(0, 40);
  u8g2.print("你好, ESP32!");
  u8g2.sendBuffer();

  delay(1000);
}

U8G2 库的分页模式实现进度条效果

#include <Arduino.h>
#include <U8g2lib.h>

U8G2_SSD1306_128X64_NONAME_2_4W_SW_SPI u8g2(U8G2_R0, /* clock=*/18, /* data=*/13,
                                             /* cs=*/4, /* dc=*/2, /* reset=*/15);

int progress = 0;

void setup()
{
  // 初始化 OLED 对象
  u8g2.begin();
}

void loop()
{
  // 进入第一页
  u8g2.firstPage();
  do
  {
    // 显示进度条边框
    u8g2.drawFrame(0, 10, 128, 20);
    // 显示进度
    u8g2.drawBox(5, 15, progress, 10);

  } while (u8g2.nextPage());  // 进入下一页,如果还有下一页则返回true

  // 进度递增
  if (progress < 118)
  {
    progress++;
  }
  else
  {
    progress = 0;
  }
}

发表评论