当前位置:网站首页>STM32F103系列控制的OLED IIC 4针
STM32F103系列控制的OLED IIC 4针
2022-06-30 05:45:00 【文某9】
最近在研究四针的OLED 先上个效果图
总工程文件评论区留下邮箱我会发送
硬件部分
有开发板的直接用开发板就好 没有的去某宝买一块STM32F103C8T6(10元左右)
类似这种
接线部分
OLED一共有四个接口 本别是SCL(时钟),SDA(数据),GND(电源负),VCC3.3(注意是接3.3V, 5V会烧坏)
电源正负随便接是3.3V就OK SCL,SDA接单片机IO口 具体配置看原理图 我这个芯片的对应的是PB6,7用排线连接就好
硬件部分结束。
软件部分
源码是借鉴的 亲测能用 不得不说 站在巨人的肩膀上真的很舒服 现在分享主和OLED C文件 总工程文件评论区留下邮箱我会发送
//主c文件
#include "delay.h"
#include "sys.h"
#include "oled.h"
#include "bmp.h"
int main(void)
{ u8 t;
delay_init(); //延时函数初始化
NVIC_Configuration(); //设置NVIC中断
// delay_ms(8000);
OLED_Init();
OLED_Clear() ;
t=' ';
//显示汉字
OLED_ShowCHinese(18,0,0);//
OLED_ShowCHinese(36,0,1);//
OLED_ShowCHinese(72,0,2);//
OLED_ShowCHinese(90,0,3);//
while(1)
{
OLED_Clear();
OLED_ShowCHinese(18,0,0);
OLED_ShowCHinese(36,0,1);
OLED_ShowCHinese(72,0,2);
OLED_ShowCHinese(90,0,3);
OLED_ShowString(6,3,"0.96' OLED TEST",16);
OLED_ShowString(0,6,"ASCII:",16);
OLED_ShowString(63,6,"CODE:",16);
OLED_ShowChar(48,6,t,16);//显示字符
t++;
if(t>'~')t=' ';
OLED_ShowNum(103,6,t,3,16);
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
OLED_DrawBMP(0,0,128,8,BMP1); //显示图片
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
OLED_DrawBMP(0,0,128,8,BMP1);
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
delay_ms(8000);
}
}
//oled c文件
void IIC_Start()
{
OLED_SCLK_Set() ;
OLED_SDIN_Set();
OLED_SDIN_Clr();
OLED_SCLK_Clr();
}
/**********************************************
//IIC Stop
**********************************************/
void IIC_Stop()
{
OLED_SCLK_Set() ;
// OLED_SCLK_Clr();
OLED_SDIN_Clr();
OLED_SDIN_Set();
}
void IIC_Wait_Ack()
{
//GPIOB->CRH &= 0XFFF0FFFF; //设置PB12为上拉输入
//GPIOB->CRH |= 0x00080000;
// OLED_SDA = 1;
// delay_us(1);
//OLED_SCL = 1;
//delay_us(50000);
/* while(1)
{
if(!OLED_SDA) //判断是否接收到应答
{
//GPIOB->CRH &= 0XFFF0FFFF; //设置PB12为推挽输出
//GPIOB->CRH |= 0x00030000;
return;
}
}
*/
OLED_SCLK_Set() ;
OLED_SCLK_Clr();
}
/**********************************************
// IIC Write byte
**********************************************/
void Write_IIC_Byte(unsigned char IIC_Byte)
{
unsigned char i;
unsigned char m,da;
da=IIC_Byte;
OLED_SCLK_Clr();
for(i=0;i<8;i++)
{
m=da;
// OLED_SCLK_Clr();
m=m&0x80;
if(m==0x80)
{OLED_SDIN_Set();}
else OLED_SDIN_Clr();
da=da<<1;
OLED_SCLK_Set();
OLED_SCLK_Clr();
}
}
void Write_IIC_Command(unsigned char IIC_Command)
{
IIC_Start();
Write_IIC_Byte(0x78); //Slave address,SA0=0
IIC_Wait_Ack();
Write_IIC_Byte(0x00); //write command
IIC_Wait_Ack();
Write_IIC_Byte(IIC_Command);
IIC_Wait_Ack();
IIC_Stop();
}
/**********************************************
// IIC Write Data
**********************************************/
void Write_IIC_Data(unsigned char IIC_Data)
{
IIC_Start();
Write_IIC_Byte(0x78); //D/C#=0; R/W#=0
IIC_Wait_Ack();
Write_IIC_Byte(0x40); //write data
IIC_Wait_Ack();
Write_IIC_Byte(IIC_Data);
IIC_Wait_Ack();
IIC_Stop();
}
void OLED_WR_Byte(unsigned dat,unsigned cmd)
{
if(cmd)
{
Write_IIC_Data(dat);
}
else {
Write_IIC_Command(dat);
}
}
/********************************************
// fill_Picture
********************************************/
void fill_picture(unsigned char fill_Data)
{
unsigned char m,n;
for(m=0;m<8;m++)
{
OLED_WR_Byte(0xb0+m,0); //page0-page1
OLED_WR_Byte(0x00,0); //low column start address
OLED_WR_Byte(0x10,0); //high column start address
for(n=0;n<128;n++)
{
OLED_WR_Byte(fill_Data,1);
}
}
}
/***********************Delay****************************************/
void Delay_50ms(unsigned int Del_50ms)
{
unsigned int m;
for(;Del_50ms>0;Del_50ms--)
for(m=6245;m>0;m--);
}
void Delay_1ms(unsigned int Del_1ms)
{
unsigned char j;
while(Del_1ms--)
{
for(j=0;j<123;j++);
}
}
//坐标显示
void OLED_Set_Pos(unsigned char x, unsigned char y)
{ OLED_WR_Byte(0xb0+y,OLED_CMD);
OLED_WR_Byte(((x&0xf0)>>4)|0x10,OLED_CMD);
OLED_WR_Byte((x&0x0f),OLED_CMD);
}
//开启OLED显示
void OLED_Display_On(void)
{
OLED_WR_Byte(0X8D,OLED_CMD); //SET DCDCÃüÁî
OLED_WR_Byte(0X14,OLED_CMD); //DCDC ON
OLED_WR_Byte(0XAF,OLED_CMD); //DISPLAY ON
}
//关闭OLED显示
void OLED_Display_Off(void)
{
OLED_WR_Byte(0X8D,OLED_CMD); //SET DCDCÃüÁî
OLED_WR_Byte(0X10,OLED_CMD); //DCDC OFF
OLED_WR_Byte(0XAE,OLED_CMD); //DISPLAY OFF
}
//清屏函数
void OLED_Clear(void)
{
u8 i,n;
for(i=0;i<8;i++)
{
OLED_WR_Byte (0xb0+i,OLED_CMD); //ÉèÖÃÒ³µØÖ·£¨0~7£
OLED_WR_Byte (0x00,OLED_CMD); //ÉèÖÃÏÔʾλÖáªÁе͵ØÖ·
OLED_WR_Byte (0x10,OLED_CMD); //ÉèÖÃÏÔʾλÖáªÁиߵØÖ·
for(n=0;n<128;n++)OLED_WR_Byte(0,OLED_DATA);
} //更新显示
}
void OLED_On(void)
{
u8 i,n;
for(i=0;i<8;i++)
{
OLED_WR_Byte (0xb0+i,OLED_CMD); //ÉèÖÃÒ³µØÖ·£¨0~7£
OLED_WR_Byte (0x00,OLED_CMD); //ÉèÖÃÏÔʾλÖáªÁе͵ØÖ·
OLED_WR_Byte (0x10,OLED_CMD); //ÉèÖÃÏÔʾλÖáªÁиߵØÖ·
for(n=0;n<128;n++)OLED_WR_Byte(1,OLED_DATA);
} //更新显示
}
//在指定位置显示一个字符
//x:0~127
//y:0~63
//mode: 0反白显示 1正常显示
//size:选择字体16/12
void OLED_ShowChar(u8 x,u8 y,u8 chr,u8 Char_Size)
{
unsigned char c=0,i=0;
c=chr-' ';//得到偏移后的值
if(x>Max_Column-1){x=0;y=y+2;}
if(Char_Size ==16)
{
OLED_Set_Pos(x,y);
for(i=0;i<8;i++)
OLED_WR_Byte(F8X16[c*16+i],OLED_DATA);
OLED_Set_Pos(x,y+1);
for(i=0;i<8;i++)
OLED_WR_Byte(F8X16[c*16+i+8],OLED_DATA);
}
else {
OLED_Set_Pos(x,y);
for(i=0;i<6;i++)
OLED_WR_Byte(F6x8[c][i],OLED_DATA);
}
}
//m^n函数
u32 oled_pow(u8 m,u8 n)
{
u32 result=1;
while(n--)result*=m;
return result;
}
//显示两个数字
//x,y :起点坐标
//len :数字的位数
//size:字体的大小
//mode:0填充模式 1叠加模式
//num:数值(0~4294967295);
void OLED_ShowNum(u8 x,u8 y,u32 num,u8 len,u8 size2)
{
u8 t,temp;
u8 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+(size2/2)*t,y,' ',size2);
continue;
}else enshow=1;
}
OLED_ShowChar(x+(size2/2)*t,y,temp+'0',size2);
}
}
//显示一个字符
void OLED_ShowString(u8 x,u8 y,u8 *chr,u8 Char_Size)
{
unsigned char j=0;
while (chr[j]!='\0')
{ OLED_ShowChar(x,y,chr[j],Char_Size);
x+=8;
if(x>120){x=0;y+=2;}
j++;
}
}
//显示汉字
void OLED_ShowCHinese(u8 x,u8 y,u8 no)
{
u8 t,adder=0;
OLED_Set_Pos(x,y);
for(t=0;t<16;t++)
{
OLED_WR_Byte(Hzk[2*no][t],OLED_DATA);
adder+=1;
}
OLED_Set_Pos(x,y+1);
for(t=0;t<16;t++)
{
OLED_WR_Byte(Hzk[2*no+1][t],OLED_DATA);
adder+=1;
}
}
/***********显示BMP图片*****************/
void OLED_DrawBMP(unsigned char x0, unsigned char y0,unsigned char x1, unsigned char y1,unsigned char BMP[])
{
unsigned int j=0;
unsigned char 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_WR_Byte(BMP[j++],OLED_DATA);
}
}
}
//初始化SSD1306
void OLED_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB|RCC_APB2Periph_GPIOD|RCC_APB2Periph_GPIOG, ENABLE); //ʹÄÜPC,D,G¶Ë¿ÚʱÖÓ
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6|GPIO_Pin_7|GPIO_Pin_3|GPIO_Pin_8; //PD3,PD6ÍÆÍìÊä³ö
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; //推挽输出
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //速度50HZ
GPIO_Init(GPIOD, &GPIO_InitStructure); //初始化GPIOD3,6
GPIO_SetBits(GPIOD,GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6|GPIO_Pin_7|GPIO_Pin_3|GPIO_Pin_8); //PD3,PD6 Êä³ö¸ß
#if OLED_MODE==1
GPIO_InitStructure.GPIO_Pin =0xFF; //PC0~7 推挽输出
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_SetBits(GPIOC,0xFF); //PC0~7输出高
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_14|GPIO_Pin_15; //PG13,14,15 OUT推挽输出
GPIO_Init(GPIOG, &GPIO_InitStructure);
GPIO_SetBits(GPIOG,GPIO_Pin_13|GPIO_Pin_14|GPIO_Pin_15); //PG13,14,15 OUT 输出高
#else
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0|GPIO_Pin_1; //PC0,1 OUT推挽输出
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_SetBits(GPIOC,GPIO_Pin_0|GPIO_Pin_1); //PC0,1 OUT 输出高
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_15; //PG15 OUT 推挽输出 RST
GPIO_Init(GPIOG, &GPIO_InitStructure);
GPIO_SetBits(GPIOG,GPIO_Pin_15); //PG15 OUT 输出高
#endif
delay_ms(200);
OLED_WR_Byte(0xAE,OLED_CMD);//--display off
OLED_WR_Byte(0x00,OLED_CMD);//---set low column address
OLED_WR_Byte(0x10,OLED_CMD);//---set high column address
OLED_WR_Byte(0x40,OLED_CMD);//--set start line address
OLED_WR_Byte(0xB0,OLED_CMD);//--set page address
OLED_WR_Byte(0x81,OLED_CMD); // contract control
OLED_WR_Byte(0xFF,OLED_CMD);//--128
OLED_WR_Byte(0xA1,OLED_CMD);//set segment remap
OLED_WR_Byte(0xA6,OLED_CMD);//--normal / reverse
OLED_WR_Byte(0xA8,OLED_CMD);//--set multiplex ratio(1 to 64)
OLED_WR_Byte(0x3F,OLED_CMD);//--1/32 duty
OLED_WR_Byte(0xC8,OLED_CMD);//Com scan direction
OLED_WR_Byte(0xD3,OLED_CMD);//-set display offset
OLED_WR_Byte(0x00,OLED_CMD);//
OLED_WR_Byte(0xD5,OLED_CMD);//set osc division
OLED_WR_Byte(0x80,OLED_CMD);//
OLED_WR_Byte(0xD8,OLED_CMD);//set area color mode off
OLED_WR_Byte(0x05,OLED_CMD);//
OLED_WR_Byte(0xD9,OLED_CMD);//Set Pre-Charge Period
OLED_WR_Byte(0xF1,OLED_CMD);//
OLED_WR_Byte(0xDA,OLED_CMD);//set com pin configuartion
OLED_WR_Byte(0x12,OLED_CMD);//
OLED_WR_Byte(0xDB,OLED_CMD);//set Vcomh
OLED_WR_Byte(0x30,OLED_CMD);//
OLED_WR_Byte(0x8D,OLED_CMD);//set charge pump enable
OLED_WR_Byte(0x14,OLED_CMD);//
OLED_WR_Byte(0xAF,OLED_CMD);//--turn on oled panel
}
代码部分结束 总工程文件评论区留下邮箱我会发送
2020.12.3
又针对代码做出了一些改良 实现了通过按键实现翻页 按键部分是搬运的正点原子的代码 现贴出主函数
#include "delay.h"
#include "sys.h"
#include "oled.h"
#include "key.h"
int main(void)
{
u8 key=0;
delay_init(); //延时函数初始化
NVIC_Configuration(); //设置nvic中断
OLED_Init(); //oled初始化
OLED_Clear(); //清屏
KEY_Init(); //按键初始化
OLED_ShowCHinese(18,0,0);//
OLED_ShowCHinese(36,0,1);//
OLED_ShowCHinese(72,0,0);//
OLED_ShowCHinese(90,0,1);//
while(1)
{
key=KEY_Scan(0); //µÃµ½¼üÖµ
// if(key)
// {
switch(key)
{
case WKUP_PRES:
OLED_Init();
OLED_Clear();
OLED_ShowCHinese(18,0,2);
OLED_ShowCHinese(36,0,3);
OLED_ShowCHinese(72,0,4);
OLED_ShowCHinese(90,0,5);
break;
case KEY1_PRES:
OLED_Init();
OLED_Clear();
OLED_ShowCHinese(18,0,7);
OLED_ShowCHinese(36,0,8);
OLED_ShowCHinese(72,0,9);
OLED_ShowCHinese(90,0,10);
break;
case KEY0_PRES:
break;
}
// }else delay_ms(10);
}
}
效果如图
完结
边栏推荐
- AI大模型落地大考,浪潮交出了怎样的答卷?
- Xijiao 21 autumn "motor and drive" online homework answer sheet (III) [standard answer]
- Why can transformer break into the CV world and kill CNN?
- Qt之QListView的简单使用(含源码+注释)
- Sword finger offer 18 Delete the node of the linked list
- PKCs 12:personal information exchange syntax v1.1 translation part I
- Promise knowledge points
- [Motrix] download Baidu cloud files using Motrix
- Remote sensing image /uda:curriculum style local to global adaptation for cross domain remote sensing image segmentation
- D. Big Brush
猜你喜欢
OpenCL线程代数库ViennaCL的使用
86. 分隔链表
Solidity - 安全 - 重入攻击(Reentrancy)
14x1.5cm vertical label is a little difficult, VFP calls bartender to print
How to judge the quality of network transformer? What symptom is network filter transformer broken?
1380. lucky numbers in matrices
How to automatically renew a token after it expires?
Shenzhou ares tx6 boot logo modification tutorial
token 过期后,如何自动续期?
Xctf--Web--Challenge--area Wp
随机推荐
Promise知识点拾遗
Word frequency statistics (string, list)
Is it safe to open an account and trade with a compass?
Fifty years ago, the go code first submitted by the inventor of Hello world was as long as this
Codeforces C. Andrew and Stones
[typescript] experimentaldecorators of vscode stepping pit
如何写论文
Xi'an Jiaotong 21st autumn online expansion resources of online trade and marketing (III) [standard answer]
Database SQL language 05 SQL exercise
Online assignment of C language program design in the 22nd spring of Western Polytechnic University
How to prevent source code leakage in enterprises and institutions
Sound net, debout dans le "sol" de l'IOT
Expansion method of unity scanning circle
[typescript] cannot redeclare block range variables
声网,站在物联网的“土壤”里
图扑软件基于钻孔数据的三维地质模型可视化
Stack overflow caused by C # using protobuf stack overflow
Solidy - fallback function - 2 trigger execution modes
旋转框目标检测mmrotate v0.3.1 训练DOTA数据集(二)
Shopping list--