【WCH】CH32F203硬件I2C驱动SSD1306 OLED
- 《关于CH32F203程序下载方式说明》
- 本驱动例程基于:
CH32F203C8
- 驱动显示效果
I2C接口
I2C1_SCL(PB8)
I2C1_SDA(PB9).
实现对 I2C SSD1306读写操作函数
void I2C_WriteByte(uint8_t addr, uint8_t data)
{
while(I2C_GetFlagStatus(I2C1, I2C_FLAG_BUSY));
I2C_GenerateSTART(I2C1, ENABLE);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_MODE_SELECT));
I2C_Send7bitAddress(I2C1, OLED_ADDRESS, I2C_Direction_Transmitter);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED));
I2C_SendData(I2C1, addr);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_BYTE_TRANSMITTING));
I2C_SendData(I2C1, data);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_BYTE_TRANSMITTED));
I2C_GenerateSTOP(I2C1, ENABLE);
}
static void OLED_Write_Cmd(uint8_t cmd)
{
I2C_WriteByte(0x00, cmd);
}
static void OLED_Write_Dat(uint8_t dat)
{
I2C_WriteByte(0x40, dat);
}
OLED驱动内容
#include "oled.h"
#include "oledfont.h"
void I2C_WriteByte(uint8_t addr, uint8_t data)
{
while(I2C_GetFlagStatus(I2C1, I2C_FLAG_BUSY));
I2C_GenerateSTART(I2C1, ENABLE);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_MODE_SELECT));
I2C_Send7bitAddress(I2C1, OLED_ADDRESS, I2C_Direction_Transmitter);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED));
I2C_SendData(I2C1, addr);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_BYTE_TRANSMITTING));
I2C_SendData(I2C1, data);
while(!I2C_CheckEvent(I2C1, I2C_EVENT_MASTER_BYTE_TRANSMITTED));
I2C_GenerateSTOP(I2C1, ENABLE);
}
static void OLED_Write_Cmd(uint8_t cmd)
{
I2C_WriteByte(0x00, cmd);
}
static void OLED_Write_Dat(uint8_t dat)
{
I2C_WriteByte(0x40, dat);
}
void OLED_Set_Pos(uint8_t x, uint8_t y)
{
OLED_Write_Cmd(0xb0 + y);
OLED_Write_Cmd(((x & 0xf0) >> 4) | 0x10);
OLED_Write_Cmd((x & 0x0f) | 0x01);
}
void OLED_Display_On(void)
{
OLED_Write_Cmd(0X8D);
OLED_Write_Cmd(0X14);
OLED_Write_Cmd(0XAF);
}
void OLED_Display_Off(void)
{
OLED_Write_Cmd(0X8D);
OLED_Write_Cmd(0X10);
OLED_Write_Cmd(0XAE);
}
void OLED_Clear(void)
{
uint8_t i, n;
for(i = 0; i < 8; i++)
{
OLED_Write_Cmd(0xb0 + i);
OLED_Write_Cmd(0x00);
OLED_Write_Cmd(0x10);
for(n = 0; n < 128; n++)
{
OLED_Write_Dat(0);
}
}
}
void OLED_On(void)
{
uint8_t i, n;
for(i = 0; i < 8; i++)
{
OLED_Write_Cmd(0xb0 + i);
OLED_Write_Cmd(0x00);
OLED_Write_Cmd(0x10);
for(n = 0; n < 128; n++)
{
OLED_Write_Dat(1);
}
}
}
void OLED_ShowChar(uint8_t x, uint8_t y, uint8_t chr, uint8_t size)
{
uint8_t c = 0, i = 0;
c = chr - ' ';
if(x > 128 - 1)
{
x = 0;
y++;
}
if(size == 16)
{
OLED_Set_Pos(x, y);
for(i = 0; i < 8; i++)
{
OLED_Write_Dat(F8X16[c * 16 + i]);
}
OLED_Set_Pos(x, y + 1);
for(i = 0; i < 8; i++)
{
OLED_Write_Dat(F8X16[c * 16 + i + 8]);
}
}
else
{
OLED_Set_Pos(x, y);
for(i = 0; i < 6; i++)
{
OLED_Write_Dat(F6x8[c][i]);
}
}
}
static uint32_t oled_pow(uint8_t m, uint8_t n)
{
uint32_t result = 1;
while(n--)result *= m;
return result;
}
void OLED_ShowNum(uint8_t x, uint8_t y, uint32_t num, uint8_t len, uint8_t size)
{
uint8_t t, temp;
uint8_t enshow = 0;
for(t = 0; t < len; t++)
{
temp = (num / oled_pow(10, len - t - 1)) % 10;
if(enshow == 0 && t < (len - 1))
{
if(temp == 0)
{
OLED_ShowChar(x + (size / 2)*t, y, ' ', size);
continue;
}
else enshow = 1;
}
OLED_ShowChar(x + (size / 2)*t, y, temp + '0', size);
}
}
void OLED_ShowString(uint8_t x, uint8_t y, char* chr, uint8_t size)
{
uint8_t j = 0;
while(chr[j] != '\0')
{
OLED_ShowChar(x, y, chr[j], size);
x += 8;
if(x > 120)
{
x = 0;
y += 2;
}
j++;
}
}
void OLED_ShowCHinese(uint8_t x, uint8_t y, uint8_t no)
{
uint8_t t, adder = 0;
OLED_Set_Pos(x, y);
for(t = 0; t < 16; t++)
{
OLED_Write_Dat(Hzk[2 * no][t]);
adder += 1;
}
OLED_Set_Pos(x, y + 1);
for(t = 0; t < 16; t++)
{
OLED_Write_Dat(Hzk[2 * no + 1][t]);
adder += 1;
}
}
void OLED_DrawBMP(uint8_t x0, uint8_t y0, uint8_t x1, uint8_t y1, uint8_t BMP[])
{
uint16_t j = 0;
uint8_t x, y;
if(y1 % 8 == 0)
{
y = y1 / 8;
}
else
{
y = y1 / 8 + 1;
}
for(y = y0; y < y1; y++)
{
OLED_Set_Pos(x0, y);
for(x = x0; x < x1; x++)
{
OLED_Write_Dat(BMP[j++]);
}
}
}
void OLED_Init(void)
{
Delay_Ms(100);
OLED_Write_Cmd(0xAE);
OLED_Write_Cmd(0x00);
OLED_Write_Cmd(0x10);
OLED_Write_Cmd(0x40);
OLED_Write_Cmd(0x81);
OLED_Write_Cmd(0xFF);
OLED_Write_Cmd(0xA1);
OLED_Write_Cmd(0xC8);
OLED_Write_Cmd(0xA6);
OLED_Write_Cmd(0xA8);
OLED_Write_Cmd(0x3F);
OLED_Write_Cmd(0xD3);
OLED_Write_Cmd(0x00);
OLED_Write_Cmd(0xD5);
OLED_Write_Cmd(0x80);
OLED_Write_Cmd(0xD9);
OLED_Write_Cmd(0xF1);
OLED_Write_Cmd(0xDA);
OLED_Write_Cmd(0x12);
OLED_Write_Cmd(0xDB);
OLED_Write_Cmd(0x40);
OLED_Write_Cmd(0x20);
OLED_Write_Cmd(0x02);
OLED_Write_Cmd(0x8D);
OLED_Write_Cmd(0x14);
OLED_Write_Cmd(0xA4);
OLED_Write_Cmd(0xA6);
OLED_Write_Cmd(0xAF);
OLED_Clear();
OLED_Set_Pos(0, 0);
}
#ifndef __OLED_H
#define __OLED_H
#include "debug.h"
#define OLED_ADDRESS 0x78
void OLED_Set_Pos(uint8_t x, uint8_t y);
void OLED_Display_On(void);
void OLED_Display_Off(void);
void OLED_Clear(void);
void OLED_On(void);
void OLED_ShowChar(uint8_t x,uint8_t y,uint8_t chr,uint8_t size);
void OLED_ShowNum(uint8_t x,uint8_t y,uint32_t num,uint8_t len,uint8_t size);
void OLED_ShowString(uint8_t x,uint8_t y, char *chr,uint8_t size);
void OLED_ShowCHinese(uint8_t x,uint8_t y,uint8_t no);
void OLED_DrawBMP(uint8_t x0, uint8_t y0,uint8_t x1, uint8_t y1,uint8_t BMP[]);
void OLED_Init(void);
#endif
main主程序
#include "debug.h"
#include
#include "oled.h"
#include "bmp.h"
void IIC_Init(u32 bound, u16 address)
{
GPIO_InitTypeDef GPIO_InitStructure = {0};
I2C_InitTypeDef I2C_InitTSturcture = {0};
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB | RCC_APB2Periph_AFIO, ENABLE);
GPIO_PinRemapConfig(GPIO_Remap_I2C1, ENABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_I2C1, ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_OD;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_OD;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
I2C_InitTSturcture.I2C_ClockSpeed = bound;
I2C_InitTSturcture.I2C_Mode = I2C_Mode_I2C;
I2C_InitTSturcture.I2C_DutyCycle = I2C_DutyCycle_16_9;
I2C_InitTSturcture.I2C_OwnAddress1 = address;
I2C_InitTSturcture.I2C_Ack = I2C_Ack_Enable;
I2C_InitTSturcture.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit;
I2C_Init(I2C1, &I2C_InitTSturcture);
I2C_Cmd(I2C1, ENABLE);
I2C_AcknowledgeConfig(I2C1, ENABLE);
}
int main(void)
{
Delay_Init();
USART_Printf_Init(115200);
printf("SystemClk:%d\r\n", SystemCoreClock);
IIC_Init(400000, 0x30);
OLED_Init();
printf("Init \r\n");
while(1)
{
OLED_Clear();
OLED_ShowChar(0, 0, 'A', 16);
OLED_ShowChar(0, 2, 'B', 16);
OLED_ShowChar(0, 4, 'C', 16);
OLED_ShowChar(0, 6, 'D', 16);
OLED_ShowChar(15, 0, 'A', 12);
OLED_ShowChar(15, 1, 'B', 12);
OLED_ShowChar(15, 2, 'C', 12);
OLED_ShowChar(15, 3, 'D', 12);
OLED_ShowChar(15, 4, 'E', 12);
OLED_ShowChar(15, 5, 'F', 12);
OLED_ShowChar(15, 6, 'G', 12);
OLED_ShowChar(15, 7, 'H', 12);
OLED_ShowString(30, 0, "Perseverance", 12);
OLED_ShowCHinese(35, 2, 0);
OLED_ShowCHinese(65, 2, 1);
OLED_ShowCHinese(95, 2, 2);
OLED_ShowString(36, 6, "Hello World", 16);
Delay_Ms(3000);
OLED_DrawBMP(0, 0, 128, 8, BMP1);
Delay_Ms(3000);
}
}
程序源码
链接: https:
提取码: up2m