找回密码
 注册会员
更新自动建库工具PCB Footprint Expert 2024.04 Pro / Library Expert 破解版

自学AVR单片机二十五(12864)

  [复制链接]
慧龙 发表于 2010-5-7 11:29:08 | 显示全部楼层 |阅读模式

本文包含原理图、PCB、源代码、封装库、中英文PDF等资源

您需要 登录 才可以下载或查看,没有账号?注册会员

×
本帖最后由 慧龙 于 2010-5-7 11:30 编辑

一、电路实现
本实例电路图如下
8160_1243303239JD25.jpg
二、控制流程

本实验采用TS12864-3型液晶,这种液晶自带汉字库,可直接显示汉字,采用的驱动电路是ST7290。其他兼容ST7290电路的12864液晶都可利用此方法进行控制。


液晶使用手册请查阅相关资料。


12864液晶的初始化设置与1602相似,在本实验中用到的160212864两种液晶的时序图是一致的,所以他们的清屏,显示设置操作是完全一样的。


12864液晶是指这种液晶有64行,每行有128个点。要显示一个完整的汉字,需要16*16的点阵,即要显示一个汉字需要16行,每行有16个点.而显示一个字符只需要8*8点阵(或者5*7点阵等)。这样12864液晶可以显示4行汉字,每行能显示8个汉字。如果显示字符的话,每行能显示16个字符。再上一个例子中,每显示一个字符需要向液晶数据端口发送一个8位的单字节字符,而一个汉字的字码有两个字节;也就是说显示一个汉字要比显示一个字符多传送一个字节。

需要特别注意的是12864液晶的第一二三四行的地址是不连续的,实际连续顺序是1324,第一行起始地址是0X80,结束地址是0X87,第二行起始地址是0X88,结束地址是0X8F,第三行起始地址是0X90,结束地址是0X97,第四行起始地址是0X98,结束地址是0X9F,编写程序的时候一定要弄清楚。


三、程序代码

这个程序实现显示的效果是在液晶屏幕上显示4行汉字和字符:第一行显示" AVR单片机学习板";第二行显示" 12864液晶显示";第三行显示"程序设计: 慧龙";第四行显示" WWW.MCUZX.COM";

  1. #include <avr/io.h> //io端口寄存器配置文件,必须包含
  2. #include <util/delay.h> //GCC中的延时函数头文件

  3. //端口位定义
  4. #define RS PG0 //数据/命令控制端 0命令,1数据
  5. #define RW PG1 //读/写选择控制端 0写,1读
  6. #define E PG2 //使能端 下降沿读,高电平写
  7. #define PSB PA0 //数据传输方式选择端,H,8位或4位并口方式;L,串口方式

  8. //全局变量声明
  9. //unsigned char LCD_DispBuff1[]="Let's study AVR";
  10. unsigned char LCD_DispBuff1[]=" AVR单片机学习板";
  11. unsigned char LCD_DispBuff2[]=" 12864液晶显示";
  12. unsigned char LCD_DispBuff3[]="程序设计: 慧龙";
  13. unsigned char LCD_DispBuff4[]=" MCUZX-AVR ";


  14. //函数声明
  15. void Port_Init(void); //端口初始化
  16. void LCD_Init(void); //LCD初始化
  17. void Write_Com(unsigned char LCD_Com); //LCD写指令
  18. void Write_Data(unsigned char LCD_Data); //LCD写数据
  19. void Check_Busy(void); //读写检测函数,每次对液晶操作前都要进行读写检测

  20. int main(void)
  21. {
  22. unsigned char Disp_Number;


  23. Port_Init(); //端口初始化

  24. LCD_Init(); //LCD初始化


  25. //下面这段程序演示在LCD上显市字符
  26. Write_Com(0X80+0X00);
  27. for(Disp_Number = 0;Disp_Number < 16;Disp_Number++)
  28. {
  29. Write_Data(LCD_DispBuff1[Disp_Number]);
  30. _delay_ms(15);
  31. }
  32. Write_Com(0X90+0X00);
  33. for(Disp_Number = 0;Disp_Number < 14;Disp_Number++)
  34. {
  35. Write_Data(LCD_DispBuff2[Disp_Number]);
  36. _delay_ms(15);
  37. }
  38. Write_Com(0X88+0X00);
  39. for(Disp_Number = 0;Disp_Number < 16;Disp_Number++)
  40. {
  41. Write_Data(LCD_DispBuff3[Disp_Number]);
  42. _delay_ms(15);
  43. }
  44. Write_Com(0X98+0X00);
  45. for(Disp_Number = 0;Disp_Number < 14;Disp_Number++)
  46. {
  47. Write_Data(LCD_DispBuff4[Disp_Number]);
  48. _delay_ms(15);
  49. }

  50. //PORTB = 0xff; //
  51. //DDRB = 0xff; //配置端口PB全部为输出口,LCD数据端口
  52. while(1)
  53. {

  54. }
  55. }

  56. void Port_Init()
  57. {
  58. //LCD数据端口设置
  59. PORTB = 0x00; //
  60. DDRB = 0xff; //配置端口PB全部为输出口,LCD数据端口

  61. //LCD控制端口设置
  62. //
  63. DDRA |= (1 << PSB) | (1 << PA2);

  64. PORTG = 0X00;
  65. DDRG |= (1 << RS) | (1 << RW) | (1 << E);
  66. _delay_ms(15);
  67. }

  68. void LCD_Init()
  69. {
  70. PORTA |= (1 << PSB) | (1 << PA2);

  71. Write_Com(0x01); //清屏
  72. _delay_ms(15);
  73. Write_Com(0x38); //显示模式设置 16x2显示,5x7点阵,8位数据接口
  74. _delay_ms(15);
  75. //Write_Com(0x0f); //显示开关控制,开显示,光标显示,光标闪烁
  76. Write_Com(0x0c); //显示开关控制,开显示,光标不显示,光标不闪烁
  77. _delay_ms(15);
  78. Write_Com(0x06); //光标设置,读或写一个字符后,地址指针加一,光标加一,整屏不移动
  79. _delay_ms(15);
  80. }

  81. void Write_Com(unsigned char LCD_Com)
  82. {
  83. //Check_Busy();

  84. PORTG &= ~(1 << RS); //RS=0,写命令
  85. PORTG &= ~(1 << RW); //RW=0,写指令
  86. PORTG |= (1 << E); //E=1,写操作
  87. _delay_ms(15);
  88. PORTB = LCD_Com; //指令送数据端口
  89. PORTG &= ~(1 << E); //E=0,停止写操作
  90. _delay_ms(15);

  91. }

  92. void Write_Data(unsigned char LCD_Data)
  93. {
  94. //Check_Busy();

  95. PORTG |= (1 << RS); //RS=1,写数据
  96. PORTG &= ~(1 << RW); //RW=0,写指令
  97. PORTG |= (1 << E); //E=1,写操作
  98. _delay_ms(15);
  99. PORTB = LCD_Data; // 数据送数据端口
  100. PORTG &= ~(1 << E); //E=0,停止写操作
  101. _delay_ms(15);

  102. }

  103. void Check_Busy()
  104. {

  105. DDRB = 0x00; //PB口置为输入口,准备读取数据
  106. PORTG &= ~(1 << RS); //RS=0,读命令
  107. PORTG |= (1 << RW); //RW=1,读指令
  108. PORTG |= (1 << E); //E=1,使能

  109. while(0X80 & PINB); //监测忙信号,直到忙信号为0,才能进行读写操作
  110. PORTG &= ~(1 << E); //E=0
  111. DDRB = 0xff; //PB口置为输出口,准备向端口发送数据

  112. }

复制代码

*滑块验证:
您需要登录后才可以回帖 登录 | 注册会员

本版积分规则

QQ|手机版|MCU资讯论坛 ( 京ICP备18035221号-2 )|网站地图

GMT+8, 2024-12-23 12:20 , Processed in 0.063948 second(s), 10 queries , Redis On.

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

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