51单片机学习——非标协议外设——LCD1602液晶显示屏
一、LCD1602液晶显示模块学习
1、概述
2、引脚接口说明
3、指令说明
4、操作时序图
5、LCD内部显示和地址
5.1、写入地址(或指令)
5.2、写入数据
6、LCD1602初始化及注意事项
6.1、初始化
6.2、注意事项
7、开发液晶显示屏实例
7.1、初始化液晶显示屏
7.2、写入指令操作
7.3、写入数据操作
7.4、每次写入操作之前的忙检测
7.5、建立字符串
7.6、显示屏第二行不亮BUG原因
检测忙的函数中,databuffer过定义导致,databuffer在头文件下已经定义为P0端口8根数据线
8、总代码
#include "reg52.h"
#include "intrins.h"#define databuffer P0 //定义P0数据总线
sbit RS = P1^0;
sbit RW = P1^1;
sbit E = P1^4;void Delay15ms() //@11.0592MHz
{unsigned char i, j;i = 27;j = 226;do{while (--j);} while (--i);
}void Delay5ms() //@11.0592MHz
{unsigned char i, j;i = 9;j = 244;do{while (--j);} while (--i);
}void Check_Busy() //检测是否忙
{char temp = 0x80; databuffer = 0xFF; //端口全部置1为了防止单片机读取数据出错 while(temp & 0x80){ //为忙则一直卡住,忙只关心BF为高电平RW = 1; //高电平进行读操作RS = 0;E = 0;_nop_();E = 1;_nop_();_nop_();temp = databuffer;E = 0;_nop_();}
}void Writ_Cmd_Fun(char cmd)
{Check_Busy();RW = 0; //R/W寄存器低电平为写操作RS = 0; //RS为低电平时选择指令寄存器E = 0;_nop_();databuffer = cmd; //指令建立_nop_();E = 1;_nop_();_nop_();E = 0;_nop_();
}void Writ_Data_Fun(char Data)
{Check_Busy();RW = 0; //R/W寄存器低电平为写操作RS = 1; //RS为高电平是选择数据寄存器E = 0;_nop_();databuffer = Data;_nop_();E = 1;_nop_();_nop_();E = 0;_nop_();
}void LCD1602_INIT() //查LCD手册初始化过程步骤
{//(1)延时 15msDelay15ms();//(2)写指令 38H(不检测忙信号)Writ_Cmd_Fun(0x38);//(3)延时 5msDelay5ms();//(4)以后每次写指令,读/写数据操作均需要检测忙信号//(5)写指令 38H:显示模式设置Writ_Cmd_Fun(0x38);//(6)写指令 08H:显示关闭Writ_Cmd_Fun(0x08);//(7)写指令 01H:显示清屏Writ_Cmd_Fun(0x01);//(8)写指令 06H:显示光标移动设置Writ_Cmd_Fun(0x06);//(9)写指令 0CH:显示开及光标设置Writ_Cmd_Fun(0x0C);
}void LCD1602_showLine(int row , int col , char *str)
{switch(row){case 1:Writ_Cmd_Fun(0x80 + col);while(*str){Writ_Data_Fun(*str);str++;}break;case 2:Writ_Cmd_Fun(0x80 + 0x40 + col);while(*str){Writ_Data_Fun(*str);str++;}break;}}void main()
{Delay15ms();LCD1602_INIT(); //初始化LCD1602模块LCD1602_showLine(1,5,"No.1"); //第一排05显示,N0.1LCD1602_showLine(2,0,"You Look handsome");
}