SPI 接口是 Motorola 首先提出的全双工三线同步串行外围接口,采用主从模式(Master Slave)架构;支持多 slave 模式应用,一 般仅支持单 Master。 时钟由 Master 控制,在时钟移位脉冲下,数据按位传输,高位在前,低位在后(MSB first);SPI 接口有 2 根单向数据线,为全双工通信,目前应用中的数据速率可达几 Mbps 的水平。
提示:以下是本篇文章正文内容,下面案例可供参考
相关资料:0.96inch SPI OLED Module(下载原始代码)
单片机实验的第一步当然是接线了
这里我们打开上面链接资料里面下载好的源码
Demo文件夹里面找到Stm32相关部分
这里我选择的是与我板子对应的F103RCT6的4线制SPI模式
打开后可以看到代码里面很清楚的给出了接线怎么接
SSD1306(OLED驱动芯片)指令详解
通过查阅资料和其他博客,发现滚动的代码如下
void roll_v(void)
{
OLED_WR_Byte(0x2e,OLED_CMD);
OLED_WR_Byte(0x29,OLED_CMD);
OLED_WR_Byte(0x00,OLED_CMD);
OLED_WR_Byte(0x00,OLED_CMD);
OLED_WR_Byte(0x07,OLED_CMD);
OLED_WR_Byte(0x07,OLED_CMD);
OLED_WR_Byte(0x01,OLED_CMD);
OLED_WR_Byte(0x2F,OLED_CMD);
}
void roll_h(void)
{
OLED_WR_Byte(0x2E,OLED_CMD); //关闭滚动
OLED_WR_Byte(0x26,OLED_CMD); //水平向左或者右滚动 26/27
OLED_WR_Byte(0x00,OLED_CMD); //虚拟字节
OLED_WR_Byte(0x00,OLED_CMD); //起始页 0
OLED_WR_Byte(0x07,OLED_CMD); //滚动时间间隔
OLED_WR_Byte(0x07,OLED_CMD); //终止页 7
OLED_WR_Byte(0x00,OLED_CMD); //虚拟字节
OLED_WR_Byte(0xFF,OLED_CMD); //虚拟字节
OLED_WR_Byte(0x2F,OLED_CMD); //开启滚动
}
写一个测试函数在main里面循环
void TEST_Menu(void)
{
GUI_ShowString(0,0,"631707060324",16,1);
GUI_ShowCHinese(0,20,16,"肖思睿",1);
roll_h();
}
结果如下
上面屏幕滚动的视频里面可以看到我显示了自己的名字和学号
但是如果你试过就会发现
在资料里面下载下来的代码改动后不能直接显示中文
这是因为代码里面没有相关的字模
在嵌入式设备 LCD 上显示的汉字大多数都属于点阵汉字。常用的点阵字库来自 UCDOS。
"肖",0x01,0x00,0x21,0x08,0x11,0x10,0x09,0x20,0x01,0x00,0x3F,0xF8,0x20,0x08,0x20,0x08,
0x3F,0xF8,0x20,0x08,0x20,0x08,0x3F,0xF8,0x20,0x08,0x20,0x08,0x20,0x28,0x20,0x20,
"思",0x00,0x00,0x3F,0xF8,0x21,0x10,0x21,0x10,0x3F,0xF8,0x21,0x10,0x21,0x10,0x3F,0xF8,
0x20,0x08,0x01,0x00,0x08,0x88,0x48,0x84,0x48,0x12,0x48,0x12,0x87,0xF0,0x00,0x00,
"睿",0x01,0x00,0x01,0xF8,0x01,0x00,0x7F,0xFE,0x40,0x02,0x9F,0xF4,0x09,0x20,0x32,0x90,
0x0C,0x60,0x3F,0xF8,0xD0,0x16,0x1F,0xF0,0x10,0x10,0x1F,0xF0,0x10,0x00,0x1F,0xF0,
代码的提取可以通过字模提取软件提取
也可以通过计算手动添加(不推荐,虽然我没找到软件就是手动添加的)
比如肖字
第一行就是:0x01,0x00,即:0000 0001 0000 0000
依次类推,就可以得到相关代码
添加到oledfont.h文件里面就可以直接调用了
要同时实现OLED和AHT20的工作,我们第一个要修改的是GPIO_Init
因为他们所接的引脚不同
OLED.c文件里面的初始化函数
添加AHT20连接的PB6和PB7
void OLED_Init_GPIO(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); //使能B端口时钟
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10|GPIO_Pin_11|GPIO_Pin_12|GPIO_Pin_6|GPIO_Pin_7; //GPIOB10,11,12,6,7
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; //推挽输出
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;//速度50MHz
GPIO_Init(GPIOB, &GPIO_InitStructure); //初始化GPIOB10、11、12,6,7
GPIO_SetBits(GPIOB,GPIO_Pin_10|GPIO_Pin_11|GPIO_Pin_12|GPIO_Pin_6|GPIO_Pin_7);
}
GUI_DrawLine(WIDTH/2-1,10+(HEIGHT-10)/2-1,WIDTH/2-1,HEIGHT-1,1);
GUI_DrawLine(0,10+(HEIGHT-10)/2-1,WIDTH-1,10+(HEIGHT-10)/2-1,1);
GUI_ShowString(0,1,"631707060324",16,1);
GUI_ShowCHinese(0,20,16,"肖思睿",1);
GUI_ShowString(0,39,"TEMP",8,1);
GUI_DrawCircle(WIDTH/2-1-19, 51, 1,2);
GUI_ShowString(WIDTH/2-1-14,46,"C",16,1);
GUI_ShowString(WIDTH/2-1+2,39,"hum",8,1);
GUI_ShowString(WIDTH/2-1+40,46,"%",16,1);
GUI_ShowNum(WIDTH/2-1-50,46,(tem/10),3,16,1);
GUI_ShowNum(WIDTH/2-1+5,46,(hum/10),3,16,1);
可以看到,由于手给温湿度测量带来的变化清晰的显示在了屏幕上