C51控制OLED12864 倒计时程序
时间: 2024-05-14 21:19:13 浏览: 81
以下是使用C51控制OLED12864显示倒计时的示例程序。
```c
#include <reg51.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
// OLED控制端口定义
sbit OLED_SCL = P2^0; // 时钟线
sbit OLED_SDA = P2^1; // 数据线
sbit OLED_CS = P2^2; // 片选线
sbit OLED_RST = P2^3; // 复位线
// OLED显示缓存
uchar code F6x8[][6] = {
{0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // 空格
{0x00, 0x00, 0x5f, 0x00, 0x00, 0x00}, // !
{0x00, 0x07, 0x00, 0x07, 0x00, 0x00}, // "
// ... 其他字符的字模数据
};
uchar dis_buf[16]; // 显示缓冲区
uchar sec = 60; // 倒计时秒数
// 延时函数
void DelayMs(uint ms)
{
uint i, j;
for (i = 0; i < ms; i++) {
for (j = 0; j < 120; j++)
_nop_();
}
}
// OLED控制函数
void OLED_WrDat(uchar dat)
{
uchar i;
OLED_CS = 0; // 片选使能
for (i = 0; i < 8; i++) {
OLED_SCL = 0;
OLED_SDA = (dat & 0x80) >> 7;
dat <<= 1;
OLED_SCL = 1;
}
OLED_CS = 1; // 片选禁止
}
void OLED_WrCmd(uchar cmd)
{
uchar i;
OLED_CS = 0; // 片选使能
OLED_SCL = 0;
OLED_SDA = 0;
OLED_SCL = 1;
OLED_SDA = 1;
for (i = 0; i < 8; i++) {
OLED_SCL = 0;
OLED_SDA = (cmd & 0x80) >> 7;
cmd <<= 1;
OLED_SCL = 1;
}
OLED_CS = 1; // 片选禁止
}
void OLED_Init()
{
OLED_RST = 1; // 复位
DelayMs(100);
OLED_RST = 0;
DelayMs(100);
OLED_RST = 1;
OLED_WrCmd(0xae); // 关闭显示
OLED_WrCmd(0x00); // 列地址低4位
OLED_WrCmd(0x10); // 列地址高4位
OLED_WrCmd(0x40); // 起始行
OLED_WrCmd(0x81); // 对比度设置
OLED_WrCmd(0xcf); // 对比度
OLED_WrCmd(0xa1); // 左右反置
OLED_WrCmd(0xc8); // 上下反置
OLED_WrCmd(0xa6); // 正常显示
OLED_WrCmd(0xa8); // 多路复用设置
OLED_WrCmd(0x3f); // 多路复用比率
OLED_WrCmd(0xd3); // 显示偏移
OLED_WrCmd(0x00); // 偏移量
OLED_WrCmd(0xd5); // 显示时钟分频
OLED_WrCmd(0x80); // 分频设置
OLED_WrCmd(0xd9); // 预充电周期
OLED_WrCmd(0xf1); // 周期设置
OLED_WrCmd(0xda); // 通道选择
OLED_WrCmd(0x12); // 通道设置
OLED_WrCmd(0xdb); // Vcomh电压倍率
OLED_WrCmd(0x40); // 倍率设置
OLED_WrCmd(0x8d); // 充电泵设置
OLED_WrCmd(0x14); // 开启充电泵
OLED_WrCmd(0xaf); // 开启显示
}
void OLED_PutChar(uchar x, uchar y, uchar ch)
{
uchar i, j;
for (i = 0; i < 6; i++) {
dis_buf[y * 128 + x + i] = F6x8[ch][i];
}
for (i = 0; i < 8; i++) {
OLED_WrCmd(0xb0 + y + i);
OLED_WrCmd(x & 0x0f);
OLED_WrCmd(((x & 0xf0) >> 4) | 0x10);
for (j = 0; j < 6; j++) {
OLED_WrDat(dis_buf[y * 128 + x + j]);
}
}
}
void OLED_PutString(uchar x, uchar y, uchar *str)
{
while (*str) {
OLED_PutChar(x, y, *str++);
x += 6;
}
}
void main()
{
OLED_Init();
while (1) {
sprintf(dis_buf, "Countdown: %02d", sec);
OLED_PutString(0, 0, dis_buf);
DelayMs(1000);
sec--;
if (sec == 0) {
break;
}
}
OLED_PutString(0, 2, "Time's up!");
while (1)
;
}
```
该程序使用了OLED12864的标准控制方式,通过OLED_WrCmd()和OLED_WrDat()函数向OLED模块写入控制命令和数据。在倒计时过程中,程序使用sprintf()函数将倒计时秒数格式化为字符串,并通过OLED_PutString()函数将其显示在OLED屏幕上。
需要注意的是,该程序还需要使用到一个6x8字体的字模数组F6x8,可以在其他地方定义或引用。另外,程序中使用了一些基本的C语言语法,如sprintf()函数和while循环等,需要具备一定的C语言编程基础。
阅读全文