#include "oled.h"

#include "stdlib.h"

#include "oledfont.h"

#include "delay.h"

#include "usart.h"

//SSD1306 OLED 驱动IC驱动代码

//驱动方式:IIC

//OLED的显存

//存放格式如下.

//[0]0 1 2 3 ... 127

//[1]0 1 2 3 ... 127

//[2]0 1 2 3 ... 127

//[3]0 1 2 3 ... 127

//[4]0 1 2 3 ... 127

//[5]0 1 2 3 ... 127

//[6]0 1 2 3 ... 127

//[7]0 1 2 3 ... 127

u8 OLED_GRAM[128][8];

//更新显存到LCD

void OLED_Refresh_Gram(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(OLED_GRAM[n][i],OLED_DATA);

}

}

void OLED_IIC_START(void)

{

SDA_OUT();   //SDA线输出

OLED_SDIN=1;

OLED_SCLK=1;

delay_us(4);

OLED_SDIN=0;//START:when CLK is high,DATA change form high to low

delay_us(4);

OLED_SCLK=0;//钳住IIC总线,准备发送或者接收数据

}

void OLED_IIC_STOP(void)

{

SDA_OUT();  //SDA线输出

OLED_SCLK=0;

OLED_SDIN=0;//STOP:when CLK is high DATA change form low to high

delay_us(4);

OLED_SCLK=1;

OLED_SDIN=1;//发送I2C总线结束信号

delay_us(4);

}

//等待应答信号到来

//返回值: 1,接收应答失败,停止IIC总线

// 0,接收应答成功

//单片机作为主设备等待从设备的应答信号

u8 OLED_IIC_WAITACK(void)

{

u8 timer=0;

OLED_SDIN=1;delay_us(1);//和开发教程IIC顺序不同

OLED_SCLK=1;delay_us(1);

SDA_IN();      //SDA设置为输入和开发教程IIC顺序不同

while(OLED_SDIN_IN)

{

timer++;

if(timer++>250)

{

OLED_IIC_STOP();

return 1;

}

}

OLED_SCLK=0;//时钟输出0

return 0;

}

//IIC发送一个字节

void MCU_Send_Byte(u8 txd)

{

u8 t;

SDA_OUT();

OLED_SCLK=0;//拉低时钟开始数据传输

for(t=0;t<8;t++)

{

OLED_SDIN=(txd&0x80)>>7;

txd<<=1;

delay_us(4);   //8位二进制依次发送出去

OLED_SCLK=1;

delay_us(4);

OLED_SCLK=0;

delay_us(4);

}

}

//oled中写命令

u8 OLED_WR_CMD(u8 cmd)//

{

OLED_IIC_START();

MCU_Send_Byte(0X78);//发送器件地址0X78, R/W# = 0 写模式

if(OLED_IIC_WAITACK())

return 1;

MCU_Send_Byte(0X00);//0x00代表写命令  0x40带表写数据

if(OLED_IIC_WAITACK())

return 2;

MCU_Send_Byte(cmd);

if(OLED_IIC_WAITACK())

return 3;

OLED_IIC_STOP();

return 0;

}

void OLED_WR_DAT(u8 dat)//

{

OLED_IIC_START();

MCU_Send_Byte(0X78);//发送器件地址0X78, R/W# = 0 写模式

OLED_IIC_WAITACK();

MCU_Send_Byte(0X40);//0x00代表写命令  0x40带表写数据

OLED_IIC_WAITACK();

MCU_Send_Byte(dat);

OLED_IIC_WAITACK();

OLED_IIC_STOP();        //

}

void OLED_WR_Byte(u8 dat,u8 cmd)

{

if(cmd) OLED_WR_DAT(dat);

else OLED_WR_CMD(dat);

}

//开启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++)for(n=0;n<128;n++)OLED_GRAM[n][i]=0X00;

OLED_Refresh_Gram();//更新显示

}

//画点

//x:0~127

//y:0~63

//t:1 填充 0,清空

void OLED_DrawPoint(u8 x,u8 y,u8 t)

{

u8 pos,bx,temp=0;

if(x>127||y>63)return;//超出范围了.

pos=7-y/8;

bx=y%8;

temp=1<

if(t)OLED_GRAM[x][pos]|=temp;

else OLED_GRAM[x][pos]&=~temp;

}

//x1,y1,x2,y2 填充区域的对角坐标

//确保x1<=x2;y1<=y2 0<=x1<=127 0<=y1<=63

//dot:0,清空;1,填充

void OLED_Fill(u8 x1,u8 y1,u8 x2,u8 y2,u8 dot)

{

u8 x,y;

for(x=x1;x<=x2;x++)

{

for(y=y1;y<=y2;y++)OLED_DrawPoint(x,y,dot);

}

OLED_Refresh_Gram();//更新显示

}

//在指定位置显示一个字符,包括部分字符

//x:0~127

//y:0~63

//mode:0,反白显示;1,正常显示

//size:选择字体 12/16/24

void OLED_ShowChar(u8 x,u8 y,u8 chr,u8 size,u8 mode)

{

u8 temp,t,t1;

u8 y0=y;

u8 csize=(size/8+((size%8)?1:0))*(size/2);                //得到字体一个字符对应点阵集所占的字节数

chr=chr-' ';//得到偏移后的值

for(t=0;t

{

if(size==12)temp=asc2_1206[chr][t];                  //调用1206字体

else if(size==16)temp=asc2_1608[chr][t];        //调用1608字体

else if(size==24)temp=asc2_2412[chr][t];        //调用2412字体

else return;                                                                //没有的字库

for(t1=0;t1<8;t1++)

{

if(temp&0x80)OLED_DrawPoint(x,y,mode);

else OLED_DrawPoint(x,y,!mode);

temp<<=1;

y++;

if((y-y0)==size)

{

y=y0;

x++;

break;

}

}

}

}

//m^n函数

u32 mypow(u8 m,u8 n)

{

u32 result=1;

while(n--)result*=m;

return result;

}

//显示2个数字

//x,y :起点坐标

//len :数字的位数

//size:字体大小

//mode:模式        0,填充模式;1,叠加模式

//num:数值(0~4294967295);

void OLED_ShowNum(u8 x,u8 y,u32 num,u8 len,u8 size)

{

u8 t,temp;

u8 enshow=0;

for(t=0;t

{

temp=(num/mypow(10,len-t-1))%10;

if(enshow==0&&t

{

if(temp==0)

{

OLED_ShowChar(x+(size/2)*t,y,' ',size,1);

continue;

}else enshow=1;

}

OLED_ShowChar(x+(size/2)*t,y,temp+'0',size,1);

}

}

void OLED_ShowSmallNum(u8 x,u8 y,u32 num,u8 len,u8 size)

{

u8 t,temp;

for(t=0;t

{

temp=(num/mypow(10,len-t-1))%10;

OLED_ShowChar(x+(size/2)*t,y,temp+'0',size,1);

}

}

void OLED_ShowFloatNum(u8 x,u8 y,float num,u8 len,u8 size)

{

u16 temp_int=0;

u16 temp_float=0;

temp_int=num;  //temp_int保存num的整数部分

temp_float=(num-temp_int)*100;//temp_float保存num的小数部分2位

OLED_ShowNum(x,y,temp_int,4,size);//显示4位整数部分数字

OLED_ShowString(2*size+x,y,".",size);//显示.

OLED_ShowSmallNum((2*size+size/2)+x,y,temp_float,2,size);//显示小数部分

}

//显示字符串

//x,y:起点坐标

//size:字体大小

//*p:字符串起始地址

void OLED_ShowString(u8 x,u8 y,const char *p,u8 size)

{

while((*p<='~')&&(*p>=' '))//判断是不是非法字符!

{

if(x>(128-(size/2))){x=0;y+=size;}

if(y>(64-size)){y=x=0;OLED_Clear();}

OLED_ShowChar(x,y,*p,size,1);

x+=size/2;

p++;

}

}

u8 OLED_Init(void)

{

RCC->APB2ENR|=1<<4;    //使能PORTC时钟

RCC->APB2ENR|=1<<8;    //使能PORTG时钟

GPIOC->CRL&=0XFFFFFFF0; //PC0 OUT IIC模式

GPIOC->CRL|=0X00000003;         //

GPIOC->ODR|=1<<0;        //

GPIOG->CRH&=0X0FFFFFFF;        //RST

GPIOG->CRH|=0X30000000;

GPIOG->ODR|=1<<15;

OLED_RST=0;

delay_ms(100);

OLED_RST=1;

if(!OLED_WR_CMD(0XAE)) printf("1-ok\r\n");

else printf("1-no\r\n");

if(!OLED_WR_CMD(0Xd5)) printf("2-ok\r\n");

else printf("2-no\r\n");

if(!OLED_WR_CMD(80)) printf("3-ok\r\n");

else printf("3-no\r\n");

if(!OLED_WR_CMD(0XA8)) printf("4-ok\r\n");

else printf("4-no\r\n");

if(!OLED_WR_CMD(0X3F)) printf("5-ok\r\n");

else printf("5-no\r\n");

if(!OLED_WR_CMD(0XD3)) printf("6-ok\r\n");

else printf("6-no\r\n");

if(!OLED_WR_CMD(0X00)) printf("7-ok\r\n");

else printf("7-no\r\n");

if(!OLED_WR_CMD(0X40)) printf("8-ok\r\n");

else printf("8-no\r\n");

if(!OLED_WR_CMD(0X8D)) printf("9-ok\r\n");

else printf("9-no\r\n");

if(!OLED_WR_CMD(0X14)) printf("10-ok\r\n");

else printf("10-no\r\n");

if(!OLED_WR_CMD(0X20)) printf("11-ok\r\n");

else printf("11-no\r\n");

if(!OLED_WR_CMD(0X02)) printf("12-ok\r\n");

else printf("12-no\r\n");

if(!OLED_WR_CMD(0XA1)) printf("13-ok\r\n");

else printf("13-no\r\n");

if(!OLED_WR_CMD(0XC0)) printf("14-ok\r\n");

else printf("14-no\r\n");

if(!OLED_WR_CMD(0XDA)) printf("15-ok\r\n");

else printf("15-no\r\n");

if(!OLED_WR_CMD(0X12)) printf("16-ok\r\n");

else printf("16-no\r\n");

if(!OLED_WR_CMD(0X81)) printf("17-ok\r\n");

else printf("17-no\r\n");

if(!OLED_WR_CMD(0XEF)) printf("18-ok\r\n");

else printf("18-no\r\n");

if(!OLED_WR_CMD(0XD9)) printf("19-ok\r\n");

else printf("19-no\r\n");

if(!OLED_WR_CMD(0XF1)) printf("20-ok\r\n");

else printf("20-no\r\n");

if(!OLED_WR_CMD(0XDB)) printf("21-ok\r\n");

else printf("21-no\r\n");

if(!OLED_WR_CMD(0X30)) printf("22-ok\r\n");

else printf("22-no\r\n");

if(!OLED_WR_CMD(0XA4)) printf("23-ok\r\n");

else printf("23-no\r\n");

if(!OLED_WR_CMD(0XA6)) printf("24-ok\r\n");

else printf("24-no\r\n");

if(!OLED_WR_CMD(0XAF)) printf("25-ok\r\n");

else printf("25-no\r\n");

OLED_Clear();

return 0;

}

stm32驱动ssd1306配置_STM32 OLED 屏幕 驱动芯片SSD1306 IIC代码相关推荐

  1. STM32(基于HAL库)驱动0.96寸OLED屏幕(六脚)

    STM32驱动0.96寸OLED屏幕(六脚) 1 序言 2 如何利用STM32单片机驱动12864液晶屏 2.1*基本配置* 2.2 *0.96寸OLED端口含义* 2.3 *0.96寸OLED液晶屏 ...

  2. STM32(基于HAL库)驱动0.96寸OLED屏幕(四脚且中英文皆可显示)

    STM32驱动0.96寸OLED屏幕(四脚) 1 注意事项 2 如何利用STM32单片机驱动12864液晶屏 2.1*基本配置* 2.2 *0.96寸OLED端口含义* 2.3 *0.96寸OLED液 ...

  3. 串口接收 DMA FIFO 双缓冲区配置 + 单色OLED屏幕灰度图像显示的抖动算法

    适用于单色OLED屏幕图像显示的抖动算法 Visual studio c++ STM32F407 0.96寸单色IIC通信OLED 5级灰度 串口DMA.双缓冲 github 抖动算法原理 DITHE ...

  4. 用esp8266驱动0.96寸OLED屏幕 太空人动画

    昨天闲来没事玩了一下OLED屏幕 之前只是做过显示图片 还没弄过动画的 (其实差不多–) 用esp8266驱动0.96寸LED屏幕 太空人动画 入门esp8266 看这篇文章 参考https://bl ...

  5. 7脚spi OLED屏幕改造成IIC屏幕

    最近在折腾OLED显示,手上有7脚的1306的OLED显示屏,两个默认的都是spi接口的使用,都是可以改造成IIC接口: 7pin 0.96寸OLED模块支持SPI和IIC接口 默认是4-SPI接口; ...

  6. stm32驱动ssd1306配置_stm32 ssD1306 OLED驱动架构

    #include "oled.h" #include "stdlib.h" #include "oledfont.h" #include & ...

  7. STM32驱动0.96寸OLED液晶屏

    一.OLED简述 1.OLED模块简介 2.SSD1306控制芯片驱动 3.如何显示字符 4.字幕显示原理 二. 上下或左右的滑动显示长字符 三. 显示AHT20的温度和湿度 四.总结 一.OLED简 ...

  8. STM32 驱动 GY-302 光照传感器 BH1750 模块(软件IIC与硬件IIC驱动)

    1.特别说明 ​ 要是不想看原理和过程,直接下拉找代码吧,都是测试过的,很稳定,有硬件I2C驱动的,也有软件模拟I2C驱动的,基于STM32F103系列和STM32F4系列实现,基于标准库实现,条理清 ...

  9. STM32使用IIC总线通讯协议在OLED屏幕上显示字符串、汉字、图像(硬件IIC)

    参考:基于STM32-Oled(IIC)的使用 作者:奋斗的小殷 发布时间: 2021-05-07 13:09:26 网址:https://blog.csdn.net/boybs/article/de ...

最新文章

  1. cmakelist 定义变量
  2. VS2010 MFC exe独立系统环境运行
  3. USB转串口 FT232/PL2303/CH340 比较
  4. Protobuf使用规范分享
  5. java 保存 设置_java – 保存设置的实现
  6. 漫步最优化二十——下降函数
  7. 如何展开Linux Memory Management学习?
  8. “社区之星”(社区核心贡献者)成长故事征集
  9. 了解计算机中的信息编码教案,《信息编码》教学设计
  10. PHP判断手机号码是否正确
  11. phpyun怎么采集_phpyun采集
  12. Linux出现“E45: ‘readonly‘ option is set (add ! to override)”的解决方法。
  13. Maven打包 错误: 程序包org.junit不存在
  14. 使用 LinuxGSM 搭建饥荒联机服务器(带洞穴)
  15. 三线表里加小短线_LaTeX 第六课:图表的排版
  16. Python错误集锦:matplotlib legend提示:ValueError: Unrecognized location ‘upper’. Valid locations are
  17. leetcode报错:member access within null pointer of type struct ListNode
  18. 工地安全帽反光衣识别系统 yolov5
  19. 访问我在BLOGBUS的博客吧
  20. java实现mysql还原_java代码实现mysql的备份与还原

热门文章

  1. flex实现水平居中和两栏布局
  2. 使用display:none和visibility:hidden隐藏的区别
  3. SpringBoot 参数符号转义,用这个包下面的类
  4. 算法题解:动态规划解0-1背包问题
  5. java中值传递和引用传递
  6. HDU 2841 Visible Trees(容斥)题解
  7. pytest.7.常见套路
  8. linux常用命令大全(转)好东西要分享
  9. Linux下面的IO模型
  10. MySQL 5.7.10 免安装配置