找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1101|回复: 3
打印 上一主题 下一主题
收起左侧

单片机软件模拟IIC在OLED12864任意位置显示字符及汉字oled12864.h下载

[复制链接]
跳转到指定楼层
楼主
制作出来的电路实物图如下:


STC15F2K60S2单片机源程序如下:
oled12864.h
  1. /*********************************************************************************************************************
  2. *1.oled12864模块头文件( SSD1306驱动IC)
  3. *2.文件:oled12864.h
  4. *4.版本:  V1.0
  5. *************************************************说明事项*****************************************************************
  6. *  ssd1306本身支持多种总线驱动方式包括SPI以及并口等,通过芯片的相应IO口拉低拉高来选择哪一种接口,0x78为IIC接口,0x7A为SOI接口
  7. *使用I2C接口时,SSD1306允许有最多两个7位的I2C地址,同样通过相应的IO口拉低拉高来切换,一般默认是0x3c,在屏幕模块的背面,
  8. *可以看到一个I2C地址切换提示,需要改变模块I2C地址时,只需要把提示位置的电阻取下焊接到另外一端即可。
  9. *要注意的是板上的I2C地址是加上了第零位读写位后的数值,即0x78 = 0x3c<<1 0x7A = 0x3d<<1,

  10. *SSD1306支持多种控制方式,I2C、6800、8080、4线SPI、3线SPI,通过SSD1306的3个引脚 BS0、BS1、BS2接不同的电平来选择控制方式,
  11. *I2C控制:BS0=0、BS1=1、BS2=0;
  12. *6800控制:BS0=0、BS1=0、BS2=1;
  13. *8080控制:BS0=0、BS1=1、BS2=1;
  14. *4线SPI控制:BS0=0、BS1=0、BS2=0;
  15. *3线SPI控制:BS0=1、BS1=0、BS2=0;
  16. *从机地址是由七个位组成的,如上图框起来的高七位,这里说明了SSD1306的从地址高六位是固定的,只有第七位受SA0控制,
  17. *如果这个位为逻辑0,地址则是0x78,如果为逻辑1则是0x7A。一般情况下看一下背面就可以了,厂家一般会默认选择搞成0x78

  18. ***********************************************************************************************************************/
  19. #ifndef _OLED12864_H_
  20. #define _OLED12864_H_

  21. #include "IIC.h"
  22. #include "Font.h"
  23. #define BIRGTHNESS        //OLED的亮度  00~255,0xcf;

  24. #define X_WIDTH    128    //屏幕宽度
  25. #define Y_HIGH    (8*8)   //屏幕高度

  26. #define IIC_OLED_ADDR_W  0x78   //OLED器件地址,7位地址,高位为0表示写,为1表示读,//通过调整0R电阻,屏可以0x78和0x7A两个地址 -- 默认0x78
  27. #define        Brightness        0xCF
  28. //void OLED_Write_Command(unsigned char IIC_Command);
  29. //void OLED_Write_Data(unsigned char IIC_Data);
  30. void OLED_Init(void);
  31. void OLED_Clear(void);
  32. void OLED_ON(void);
  33. void OLED_OFF(void);
  34. //void OLED_ShowStr(unsigned char x, unsigned char y, unsigned char ch[]);
  35. void OLED_ShowChinese(unsigned char x, unsigned char y, unsigned char Num);
  36. void OLED_ShowStr(unsigned char x, unsigned char y, unsigned char ch[], unsigned char TextSize);

  37. /****************************************************************************
  38. *函数名称:void  OLED_Write_Command(unsigned char IIC_Command)
  39. *函数功能:写OLED命令;  此函数实测OK
  40. *输入:    unsigned char IIC_Command
  41. *输出:    无
  42. *****************************************************************************/
  43. /***************/

  44. void OLED_Write_Command(unsigned char IIC_Command)
  45. {

  46.           IIC_Start();                     //启动I2C
  47.     IIC_Send_Byte(IIC_OLED_ADDR_W);  //D/C #=0; R/W #=0;写IIC器件地址
  48.           IIC_Wait_Ack();
  49.                 IIC_Send_Byte(0x00);             //寄存器地址,告诉指令解析器,接下来的是一个指令
  50.                 IIC_Wait_Ack();
  51.                 IIC_Send_Byte(IIC_Command);      //写命令
  52.                 IIC_Wait_Ack();
  53.                 IIC_Stop();
  54.                  
  55. }        



  56. /****************************************************************************
  57. *函数名称:bit OLED12864_Write_Commmand(unsigned char cmd, bit start, bit stop)
  58. *函数功能:写指令函数,第一个参数为指令,第二、三个参数选择是否需要通信开始和结束函数,=1有,=0没有
  59. *输入:    unsigned char IIC_Command
  60. *输出:    无
  61. *****************************************************************************/
  62. /***************/
  63. /*****************************************************
  64. bit OLED12864_Write_Commmand(unsigned char cmd, bit start, bit stop)

  65. {
  66.      if(start)

  67.      {
  68.            IIC_Start();             //启动I2C

  69.            IIC_Send_Byte(IIC_OLED_ADDR_W);//写从机地址,并且加上读写标志位(最后一位)

  70.            if(!Test_ack())

  71.            {

  72.                  return 0;

  73.            }    //执行从机应答检测函数,如果从机发送了非应答信号,那么就退出数据发送函数

  74.       }
  75. }
  76. **********************************************************/
  77. /*********************************************************
  78. unsigned char OLED_Write_Command(unsigned char IIC_Command)
  79. {

  80.           I2C_Start();                     //启动I2C
  81.     IIC_Send_Byte(I2C_OLED_ADDR_W);  //D/C #=0; R/W #=0;写IIC器件地址
  82.           if(IIC_Wait_Ack())
  83.        return 1;
  84.                 IIC_Send_Byte(0x00);  // 告诉指令解析器,接下来的是一个指令
  85.                 if(IIC_Wait_Ack())
  86.        return 2;
  87.                 IIC_Send_Byte(IIC_Command);  //写命令
  88.                 if(IIC_Wait_Ack())
  89.        return 3;
  90.                 I2C_Stop();
  91.                    return 0;
  92. }        
  93. ***********************************************************/

  94. /****************************************************************************
  95. *函数名称:unsigned char OLED_Write_Data(unsigned char IIC_Data)
  96. *函数功能:写OLED数据;  此函数实测OK
  97. *输入:    unsigned char IIC_Data
  98. *输出:    无
  99. *****************************************************************************/
  100. /***************/

  101. void OLED_Write_Data(unsigned char IIC_Data)
  102. {

  103.           IIC_Start();                     //启动I2C
  104.     IIC_Send_Byte(IIC_OLED_ADDR_W);  //D/C #=0; R/W #=0;写IIC器件地址
  105.           IIC_Wait_Ack();
  106.                 IIC_Send_Byte(0x40);      //寄存器地址告诉指令解析器,接下来的是一个数据
  107.                 IIC_Wait_Ack();
  108.                 IIC_Send_Byte(IIC_Data);  //写数据
  109.                 IIC_Wait_Ack();
  110.                 IIC_Stop();
  111.                         
  112. }        

  113. /*****************************************************
  114. static unsigned char OLED_Write_Data(unsigned char IIC_Data)
  115. {
  116.     I2C_Start();                     //启动I2C
  117.     IIC_Send_Byte(I2C_OLED_ADDR_W);  //D/C #=0; R/W #=0;写IIC器件地址
  118.           if(IIC_Wait_Ack());
  119.        return 1;
  120.                 IIC_Send_Byte(0x40);      //告诉指令解析器,接下来的是一个指令
  121.                 if(IIC_Wait_Ack());
  122.        return 2;
  123.                 IIC_Send_Byte(IIC_Data);  //写数据
  124.                 if(IIC_Wait_Ack());
  125.        return 3;
  126.                 I2C_Stop();
  127.                    return 0;
  128. }        
  129. *******************************************************/

  130. /****************************************************************************
  131. *函数名称:void OLED_SetCursor(unsigned char x,unsigned char y)
  132. *函数功能:设置行列的起始地址位置;此函数实测OK
  133. *输入:    unsigned char x,unsigned char y;;// x列,y行
  134. *输出:    无
  135. *****************************************************************************/
  136. /***************/
  137. void OLED_SetCursor(unsigned char x,unsigned char y)// x列,y行
  138. {
  139.           //x += 4;
  140.           OLED_Write_Command(0xb0|y);             //y就是第y页,也就是第y行
  141.           OLED_Write_Command(((x&0xf0)>>4)|0x10); //x的高4位
  142.           OLED_Write_Command((x&0x0f));           //x的低4位
  143.          // OLED_Write_Command((x&0x0f)|0x01);  
  144.          //列起始地址由指令0x1m和0x0n来确定,m是高四位,n是低四位,使用12864,则m,n合起来的8位数数值范围在0-127之间
  145. }        

  146. /****************************************************************************
  147. *函数名称:void OLED_Clear(void)
  148. *函数功能:OLED清屏函数,复位清屏;;此函数实测OK
  149. *输入:    无
  150. *输出:    无
  151. *****************************************************************************/
  152. /***************/
  153. void OLED_Clear(void)
  154. {
  155.       unsigned char x,y;

  156.       for(y=0;y<Y_HIGH/8;y++)  //OLED_HIGH=8*8
  157.             {
  158.         OLED_Write_Command(0xb0+y); // 从0 ~ 7页依次写入
  159.         OLED_Write_Command(0x00);   // 低位列地址
  160.         OLED_Write_Command(0x10);   // 高位列地址
  161.         for(x=0; x<X_WIDTH; x++)    //OLED_WIDTH=128
  162.            OLED_Write_Data(0x00);
  163.      }
  164.                
  165. }


  166. /****************************************************************************
  167. *函数名称:void OLED_Fill(unsigned char bmp_dat)
  168. *函数功能:OLED全屏函数,         此函数实测OK
  169. *输入:    unsigned char bmp_dat,  0XFF为全屏亮,0X00为全屏灭
  170. *输出:    无
  171. *****************************************************************************/
  172. /***************/

  173. void OLED_Fill(unsigned char bmp_dat)
  174. {
  175.       unsigned char x,y;

  176.       for(y=0;y<Y_HIGH/8;y++)  //OLED_HIGH=8*8
  177.             {
  178.         OLED_Write_Command(0xb0+y);
  179.         OLED_Write_Command(0x00);
  180.         OLED_Write_Command(0x10);
  181.         for(x=0; x<X_WIDTH; x++)//OLED_WIDTH=128
  182.            OLED_Write_Data(bmp_dat);
  183.      }
  184.                
  185. }

  186. /****************************************************************************
  187. *函数名称:void OLED_ON(void)
  188. *函数功能:打开显示
  189. *输入:    无
  190. *输出:    无
  191. *****************************************************************************/
  192. /***************/
  193. /*********
  194. void OLED_ON(void)
  195. {
  196.     OLED_Write_Command(0x8D); //设置电荷泵
  197.     OLED_Write_Command(0x14); //开启电荷泵
  198.     OLED_Write_Command(0xAF); //oled唤醒
  199. }
  200. *****************/
  201. /****************************************************************************
  202. *函数名称:void OLED_OFF(void)
  203. *函数功能:打开显示
  204. *输入:    无
  205. *输出:    无
  206. *****************************************************************************/
  207. /***************/

  208. /*****************
  209. void OLED_OFF(void)
  210. {
  211.     OLED_Write_Command(0x8D);//设置电荷泵
  212.     OLED_Write_Command(0x10); //开启电荷泵
  213.     OLED_Write_Command(0xAE); //oled休眠
  214. }
  215. ********************/
  216. /****************************************************************************
  217. *函数名称:void OLED_Init(void)
  218. *函数功能:OLED12864初始化,此函数实测OK
  219. *输入:    无
  220. *输出:    无
  221. *****************************************************************************/
  222. /***************/
  223. void OLED_Init(void)
  224. {
  225.     //IIC_Init();      //iic初始化SDA,SCL的IO口的函数,可要可不要
  226.     delay_ms(100);  //从上电到下面开始初始化要有足够的时间,即等待RC复位完毕  
  227.     /* Init LCD */
  228.         
  229.           //A3H,垂直滚动区域,A是固定区域的顶行号,B是行数
  230.     OLED_Write_Command(0xAE); //0xAE为SSD1306关闭显示,
  231.         
  232.     OLED_Write_Command(0x20); //设置存储地址的模式,水平、竖直、页、[无效],四种,复位页模式
  233.     OLED_Write_Command(0x10); //00,Horizontal Addressing Mode;01,Vertical Addressing Mode;10,Page Addressing Mode (RESET);11,Invalid(无效)
  234.         
  235.     OLED_Write_Command(0xB0); //设置页地址,0-7
  236.     OLED_Write_Command(0x00); //设置起始列地址的低位,00H~0F,只在页地址模式有效
  237.     OLED_Write_Command(0x10); //设置起始列地址的高位,10H~1F,只在页地址模式有效
  238.     OLED_Write_Command(0x40); //设置显示的起始行,(0x00~0x3F),40H~7FH总共64行
  239.         
  240.     OLED_Write_Command(0x81); //设置对比度控制,实际取值是A[] + 1
  241.     OLED_Write_Command(Brightness); // 这里Brightness=0xcf,Set SEG Output Current Brightness,  256
  242.         
  243.     OLED_Write_Command(0xA1); //设置段(SEG)重映射,A0H/A1H,A1H是列翻转, 0xa0左右反置 0xa1正常
  244.           OLED_Write_Command(0xC8); //设置COM输出扫描方向C0H/C8H,C8H是行反转。 0xc0上下反置 0xc8正常,// 重映射模式,COM[N-1]~COM0扫描
  245.     OLED_Write_Command(0xA6); //设置反白显示,A6h --- “1”点亮像素点,//A7h --- “0”点亮像素点,A6H/A7H,0xa7逆显示,
  246.                
  247.                 OLED_Write_Command(0xA4); //A4/A5设置全局显示,A5H强制全局显示
  248.                
  249.     OLED_Write_Command(0xA8); //设置驱动路数,起始也就是命令为0xA8,参数取值16~63,效果是垂直方向显示的范围
  250.     OLED_Write_Command(0x3F); //// 64duty
  251.     OLED_Write_Command(0xD3); //设置显示偏移,图像竖直向上偏移,复位是00H,(0x00~0x3F)
  252.     OLED_Write_Command(0x00); // 无偏移
  253.                 OLED_Write_Command(0xD5); //设置震荡器分频,默认值80H
  254.     OLED_Write_Command(0xF0); //--set divide ratio
  255.                 OLED_Write_Command(0xD9); //设置预充电周期,同步亮度的,复位22H
  256.     OLED_Write_Command(0x22); //默认值22H,官方推荐值0xF1,/将预充电设置为15个时钟加上其放电设置为1个时钟
  257.     OLED_Write_Command(0xDA); //设置COM引脚硬件配置,复位是12H,加上重映射总共八种玩法,
  258.     OLED_Write_Command(0x12); //使用默认值
  259.                 OLED_Write_Command(0xDB); //设置Vcomh取消选择等级,可调节亮度(默认)
  260.     OLED_Write_Command(0x20); //默认值0x20,0x00:0.65*Vcc,0x10:0.71*Vcc,0x20:0.77*Vcc,0x30:0.83*Vcc
  261.                 OLED_Write_Command(0x8D); //电荷泵设置,复位是0B,启用电荷泵需要配置成1B
  262.     OLED_Write_Command(0x14); //开显示 set(0x10) disable
  263.     OLED_Write_Command(0xAF); //0xAF为SSD1306打开显示        
  264.                
  265.    
  266.                 //OLED_Fill(0x00);          //初始屏幕填充数据0
  267.                 //OLED_SetCursor(0,0);     //
  268.     OLED_Clear();//初始必须清屏
  269.                  
  270. }

  271. /****************************************************************************
  272. *函数名称:void OLED_P6x8Str(unsigned char x, y,unsigned char ch[]);此函数实测OK
  273. *函数功能:显示6*8一组标准宽度x高度=6x8,ASCII字符串        显示的坐标(x,y),x为列范围,y为页范围0~7*
  274. *输入:    unsigned char x, x为列,unsigned char y,y为行, unsigned char ch[]为字体数组
  275. *输出:    无
  276. *****************************************************************************/
  277. /***************/
  278. void OLED_P6x8Str(unsigned char x, y,unsigned char ch[])
  279. {
  280.         unsigned char c=0,i=0,j=0;
  281.         while (ch[j]!='\0')
  282.         {
  283.                 c =ch[j]-32;         //减去前面字符串有32个字符,第33个字符为A
  284.                 if(x>126){x=0;y++;}
  285.                   OLED_SetCursor(x,y);
  286.                 for(i=0;i<6;i++)       //写6列数据
  287.                   OLED_Write_Data(OLED_F6x8[c][i]);//如果要显示第1个6列,则为
  288.                 x+=6;   //列数+6
  289.                 j++;    //行数加1
  290.          }
  291. }

  292. //每行显示数据:生成数组的大小,字符的长(页)x字符的宽(如8*16字体,2页*8列 = 16;如12*24字体,3页*12列 = 36;如16*32字体,4页*16列 = 64)
  293. /****************************************************************************
  294. *函数名称:void OLED_Font8x16Str(unsigned char x, unsigned char y, unsigned char ch[])
  295. *函数功能:显示8*16一组标准ASCII字符串, 显示的坐标(x,y),y为页范围0~7;;此函数实测OK
  296. *输入:    unsigned char x, x为列,unsigned char y,y为行, unsigned char ch[]为字体数组
  297. *输出:    无
  298. *****************************************************************************/
  299. /***************/
  300. void OLED_P8x16Str(unsigned char x, unsigned char y, unsigned char ch[])
  301. {
  302.     unsigned char c=0,i=0,j=0;

  303.     while (ch[j] != '\0')
  304.                 {   
  305.         c = ch[j]-32;
  306.         if (x>120)
  307.                                 {
  308.               x = 0;
  309.               y++;
  310.         }
  311.         OLED_SetCursor(x,y);   
  312.         for(i=0;i<8;i++)     
  313.             OLED_Write_Data(OLED_F8x16[c*16+i]);
  314.                                 
  315.          OLED_SetCursor(x,y+1);   
  316.         for(i=0; i<8; i++)     
  317.             OLED_Write_Data(OLED_F8x16[c*16+i+8]);  
  318.         
  319.                                 x+=8;
  320.         j++;
  321.     }
  322. }


  323. /*****************************************************************************************************
  324. *函数名称:void OLED_ShowStr(unsigned char x,unsigned char y,unsigned char *chr,unsigned char TextSize)
  325. *函数功能:显示字符串函数,包括了OLED_P6x8Str(),OLED_P8x16Str()两个函数.

  326. *使用方法:只需更改后面的TextSize的值,字符大小(1:6*8 ; 2:8*16)

  327. *输入:    unsigned char x,unsigned char y,unsigned char *chr,unsigned char TextSize)
  328. *    :     x,y:起点坐标,x为0-127列,y为页0-7,*chr:为要显示的字符串
  329. *          TextSize为字号可以填入1与2,当填入1时,函数调用的为codetab.h中的6*8点阵数组,当填入2时调用的是8*16点阵数组。
  330. *          所谓6*8,8*16就是在oled上占格的大小,oled分辨率为64*128,所以在应用时要计算好格数,以免oled上显示不全

  331. *          如果 TextSize为1则为6*8,为2,则为8*16
  332. *输出:    无
  333. ********************************************************************************************************/
  334. /***************/        

  335. void OLED_ShowStr(unsigned char x, unsigned char y, unsigned char ch[], unsigned char TextSize)
  336. {
  337.     unsigned char c = 0,i = 0,j = 0;
  338.     switch(TextSize)
  339.     {
  340.         case 1:
  341.         {
  342.             while(ch[j] != '\0')
  343.             {
  344.                 c = ch[j] - 32;
  345.                 if(x > 126)
  346.                 {
  347.                     x = 0;
  348.                     y++;
  349.                 }
  350.                 OLED_SetCursor(x,y);
  351.                 for(i=0;i<6;i++)
  352.                     OLED_Write_Data(OLED_F6x8[c][i]);
  353.                 x += 6;
  354.                 j++;
  355.             }
  356.         }break;
  357.         case 2:
  358.         {
  359.             while(ch[j] != '\0')
  360.             {
  361.                 c = ch[j] - 32;
  362.                 if(x > 120)
  363.                 {
  364.                     x = 0;
  365.                     y++;
  366.                 }
  367.                 OLED_SetCursor(x,y);
  368.                 for(i=0;i<8;i++)
  369.                     OLED_Write_Data(OLED_F8x16[c*16+i]);
  370.                 OLED_SetCursor(x,y+1);
  371.                 for(i=0;i<8;i++)
  372.                     OLED_Write_Data(OLED_F8x16[c*16+i+8]);
  373.                 x += 8;
  374.                 j++;
  375.             }
  376.         }break;
  377.     }
  378. }


  379. /*****************************************************************************************************
  380. *函数名称:void OLED_ShowChinese(unsigned char x, unsigned char y, unsigned char Num)
  381. *函数功能:显示 bsp_font.h 中的16*16点阵汉字(宋体), 此函数实测OK
  382. *输入:   unsigned char Line, unsigned char Column, unsigned char Num
  383.           y:起始点行坐标:0 ~ 7,x:起始点列坐标:0 ~127,Num为第几个字
  384. *输出:    无
  385. ********************************************************************************************************/
  386. /***************/
  387. /****************************
  388. void  OLED_P16x16Ch(unsigned char x, unsigned char y, unsigned int Num)
  389. {
  390.         
  391.         unsigned char i=0;
  392.         unsigned int wide = 32*Num;      //字宽
  393.         
  394.         OLED_SetCursor(x,y);                //参数2:把光标设置在第几页. 参数1:把光标设置在第几列
  395.         
  396.         for (i = 0; i < 16; i++)
  397.         {
  398.                 OLED_Write_Data(OLED_F16x16[wide]);                        //显示上半部分内容
  399.                 wide+=1;
  400.         }
  401.         
  402.                 OLED_SetCursor(x,y+1);                //参数2:把光标设置在第几页. 参数1:把光标设置在第几列        
  403.         for (i = 0; i < 16 ; i++)
  404.         {
  405.                 OLED_Write_Data(OLED_F16x16[wide]);                //显示下半部分内容
  406.                 wide+=1;
  407.         }

  408. }
  409. ******************************

  410. /*****************************************************************************************************
  411. *函数名称:void  OLED_P16x16Ch(unsigned char x, unsigned char y, unsigned char Num)
  412. *函数功能:显示 bsp_font.h 中的汉字(宋体)
  413. *输入:   unsigned char Line, unsigned char Column, unsigned char Num
  414.           y:起始点行坐标:1 ~ 8, x:起始点列坐标:1 ~8,Num为第几个字
  415. *输出:    无
  416. ********************************************************************************************************/
  417. /***************/

  418. void  OLED_P16x16Ch(unsigned char x, unsigned char y, unsigned char Num)
  419. {
  420.         
  421.         unsigned char i=0;
  422.         unsigned char wide = 16; //字宽,如:16x16字体,32x32字体,
  423.         
  424.         OLED_SetCursor((x-1)*wide,(y-1));                   //参数1:把光标设置在第几列,参数2:把光标设置在第几页.
  425.         
  426.         for (i = 0; i < wide; i++)
  427.         {
  428.                   OLED_Write_Data(OLED_F16x16[Num][i]);    //显示上半部分内容
  429.                   
  430.         }
  431.         
  432.         OLED_SetCursor((x-1)*wide,(y-1)+1);                                 //参数2:把光标设置在第几页. 参数1:把光标设置在第几列        
  433.         
  434.         for (i = 0; i < wide ; i++)
  435.         {
  436.                   OLED_Write_Data(OLED_F16x16[Num][i+wide]); //显示下半部分内容
  437.                  
  438.         }

  439. }

  440. /****************************************************************************
  441. *函数名称:void OLED_ShowCHinese(unsigned char x,unsigned char y,unsigned char no,unsigned char font_width,unsigned char font_height)
  442. *函数功能: 显示任意大小汉字
  443. ********   x1,y1 -- 起点对角线(结束点)的坐标(x1:0~127,y1:0~7)
  444. *输入:    unsigned char x, x为列,unsigned char y,y为行, unsigned char ch[]为字体数组,
  445. *      :   *no: 表示要显示的汉字(模组)在hzk[][]数组中的行号,通过行号来确定在数组中要显示的汉字
  446. *          这里字体的宽font_width的值必须与用字模制作软件生成字模时的点阵值大小一致
  447. *         font_height的值为用字模制作软件生成字模时字体的高,由于我的屏像素为32*128-----0~7共8页,每页4个位
  448. *输出:    无
  449. *****************************************************************************/
  450. /***************/

  451. void OLED_ShowCHinese(unsigned char x,unsigned char y,unsigned char no,unsigned char font_width,unsigned char font_height)

  452. {                                 
  453.            unsigned char t, i;
  454.      for(i=0;i<(font_height/8);i++)                                /*font_height最大值为32,这张屏只有8个页(行),每页4个位*/
  455.            {
  456.                              OLED_SetCursor(x,y+i);        
  457.                         
  458.                              
  459.                              for(t=0;t<font_width;t++)                /*font_width最大值为128,屏幕只有这么大*/
  460.                              {        
  461.                                             //OLED_Write_Data(OLED_F32x32[(font_height/8)*no+i][t]);
  462.                                                          if((font_width==16)&(font_height==16))       //16x16字体
  463.                                                          {
  464.                                                             OLED_Write_Data(OLED_F16x16[no][font_width*i+t]);
  465.                                                          }
  466.                                                           else if((font_width==32)&(font_height==16))   //32x16字体
  467.                                                          {
  468.                                                             OLED_Write_Data(OLED_F32x16[no][font_width*i+t]);
  469.                                                          }
  470.                                                          
  471.                                                          
  472.                                                          else if((font_width==32)&(font_height==32))   //32x32字体
  473.                                                          {
  474.                                                             OLED_Write_Data(OLED_F32x32[no][font_width*i+t]);
  475.                                                          }
  476.                                                           else if((font_width==64)&(font_height==32))  //64x32字体
  477.                                                          {
  478.                                                             OLED_Write_Data(OLED_F64x32[no][font_width*i+t]);
  479.                                                          }
  480.                                                          
  481.                                                           else if((font_width==64)&(font_height==64))  //64x64字体
  482.                                                          {
  483.                                                             OLED_Write_Data(OLED_F64x64[no][font_width*i+t]);
  484.                                                          }
  485.                                                          
  486.                              }     
  487.            }               

  488. }

  489. /****************************************************************************
  490. *函数名称:void OLED_DrawBMP(unsigned char x0, unsigned char y0, unsigned char x1, unsigned char y1, unsigned char BMP[])
  491. *函数功能:显示显示BMP图片128×64起始点坐标(x0, y0),x的范围0~127,y为页的范围0~7
  492. ********   x1,y1 -- 起点对角线(结束点)的坐标(x1:0~127,y1:0~7)
  493. *输入:    unsigned char x, x为列,unsigned char y,y为行, unsigned char ch[]为字体数组
  494. *输出:    无
  495. *****************************************************************************/
  496. /***************/


  497. void OLED_DrawBMP(unsigned char x0, unsigned char y0, unsigned char x1, unsigned char y1, unsigned char BMP[])
  498. {   
  499.     unsigned int j=0;
  500.     unsigned char x, y;

  501.     if(y1%8 == 0)
  502.                         y = y1/8;      
  503.     else
  504.                         y = y1/8+1;
  505.     for (y=y0; y<y1; y++)
  506.     {
  507.          OLED_SetCursor(x0,y);               
  508.          for(x=x0; x<x1; x++)
  509.                            {      
  510.              OLED_Write_Data(BMP[j++]);            
  511.          }
  512.                 }
  513. }        

  514. /*****************************************************************************************************
  515. *函数名称:void OLED_ShowChinese(unsigned char Line, unsigned char Column, unsigned char Num)
  516. *函数功能:显示 bsp_font.h 中的汉字(宋体)
  517. *输入:   unsigned char Line, unsigned char Column, unsigned char Num
  518.           Line:起始点行坐标:0 ~ 7,Column:起始点列坐标:0 ~127
  519. *输出:    无
  520. ********************************************************************************************************/
  521. /***************/
  522. /***************************************
  523. void OLED_ShowChinese(unsigned char Line, unsigned char Column, unsigned char Num)
  524. {
  525.         
  526.         unsigned char i=0;
  527.         unsigned char wide = 32;      //字宽
  528.         
  529.         OLED_SetCursor(( Line - 1 ) * 2, ( Column - 1 )* wide);                //参数1:把光标设置在第几页. 参数2:把光标设置在第几列
  530.         
  531.         for (i = 0; i < wide; i++)
  532.         {
  533.                 OLED_Write_Data(OLED_F16x16[Num][i]);                        //显示上半部分内容
  534.         }
  535.         
  536.         OLED_SetCursor(( Line - 1 ) * 2 + 1,( Column - 1) * wide);               
  537.         for (i = 0; i < wide ; i++)
  538.         {
  539.                 OLED_Write_Data(OLED_F16x16[Num][i+wide]);                //显示下半部分内容
  540.         }

  541. }
  542. ****************************************/


  543. /**
  544. * 描述:显示6*8一组标准ASCII字符串,显示的坐标(x,y),y为页范围0~7
  545. */

  546. /****************************************************************************
  547. *函数名称:void OLED_Font6x8Str(unsigned char x, unsigned char y, unsigned char ch[])
  548. *函数功能:显示6*8一组标准ASCII字符串, 显示的坐标(x,y),y为页范围0~7
  549. *输入:    unsigned char x, x为列,unsigned char y,y为行, unsigned char ch[]为字体数组
  550. *输出:    无
  551. *****************************************************************************/
  552. /***************/
  553. /****************************
  554. void OLED_Font6x8Str(unsigned char x, unsigned char y, unsigned char ch[])
  555. {
  556.     unsigned char c=0, i=0, j=0;  

  557.     while (ch[j] != '\0')
  558.          {   
  559.         c = ch[j]-32;
  560.         if(x>126) {x=0; y++;}
  561.         OLED_SetCursor(x,y);   
  562.         for(i=0; i<6; i++)     
  563.           OLED_Write_Data(F6x8[c][i]);  
  564.         x += 6;
  565.         j++;
  566.     }
  567. }
  568. **************************/

  569. #endif

复制代码
原理图: 无
仿真: 无
STC15F2K60S2单片机完整Keil代码工程文件下载:
STC15F2K60S2 OLED12864任意位置显示字符和汉字.zip (93.21 KB, 下载次数: 47)

评分

参与人数 1黑币 +70 收起 理由
admin + 70 共享资料的黑币奖励!

查看全部评分

分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏4 分享淘帖 顶1 踩
回复

使用道具 举报

沙发
ID:259035 发表于 2024-8-23 09:48 | 只看该作者
谢谢楼主分享,我还在学习中
回复

使用道具 举报

板凳
ID:430492 发表于 2024-8-27 14:57 | 只看该作者
谢谢楼主分享
回复

使用道具 举报

地板
ID:433219 发表于 2024-8-30 16:51 | 只看该作者
注释很详细很重要!          ssd1306本身支持多种总线驱动方式
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表