1602液晶屏主程序.docx
- 文档编号:23985503
- 上传时间:2023-05-23
- 格式:DOCX
- 页数:14
- 大小:838.60KB
1602液晶屏主程序.docx
《1602液晶屏主程序.docx》由会员分享,可在线阅读,更多相关《1602液晶屏主程序.docx(14页珍藏版)》请在冰豆网上搜索。
1602液晶屏主程序
第十二讲1602液晶显示
液晶(LiquidCrystal)是一种高分子材料,因为其特殊的物理、化学、光学特性,20世纪中叶开始广泛应用在轻薄型显示器上。
液晶显示器(LiquidCrystalDisplay,LCD)的主要原理是以电流刺激液晶分子产生点、线、面并配合背部灯管构成画面。
为叙述简便,通常把各种液晶显示器都直接叫做液晶。
各种型号的液晶通常是按照显示字符的行数或液晶点阵的行、列数来命名的。
比如:
1602的意思是每行显示16个字符,一共可以显示两行;类似的命名还有0801,0802,1601等,这类液晶通常都是字符型液晶,即只能显示ASCII码字符,如数字、大小写字母、各种符号等。
12232液晶属于图形型液晶,她的意思是液晶由122列、32行组成,即共有122X32个点来显示各种图形,我们可以通过程序控制这122X32个点中的任一个点显示或不显示。
类似的命名还有12864,19264,192128,320240等,根据客户需要,厂家可以设计出任意数组合的点阵液晶。
液晶显示的使用有多广泛我就不多说了,LCD1602好像10元左右就可以拿到了的,不算贵。
我们来看看现在市面都有哪些样子的1602,下面从网上搜罗了几个:
蓝白屏黄绿屏
其实显而易,见也就是背光和字体的颜色不一样罢,不过老实说,蓝色背光的1602看上去显得确实比较亮,也许是人眼视觉的关系。
接下来进入LCD1602使用的重点:
操作时序。
操作时序永远使用是任何一片IC芯片的最主要的内容。
一个芯片的所有使用细节都会在它的官方器件手册上包含。
所以使用一个器件事情,要充分做好的第一件事就是要把它的器件手册上有用的内容提取,掌握。
介于中国目前的芯片设计能力有限,所以大部分的器件都是外国几个IC巨头比如TI、AT、MAXIM这些公司生产的,器件资料自然也是英文的多,所以,英文的基础要在阅读这些数据手册时得到提高哦。
即便有中文翻译版本,还是建议看英文原版,看不懂时不妨再参考中文版,这样比较利于提高。
我们首先来看1602的引脚定义,1602的引脚是很整齐的SIP单列直插封装,所以器件手册只给出了引脚的功能数据表:
我们只需要关注以下几个管脚:
3脚:
VL,液晶显示偏压信号,用于调整LCD1602的显示对比度,一般会外接电位器用以调整偏压信号,注意此脚电压为0时可以得到最强的对比度。
4脚:
RS,数据/命令选择端,当此脚为高电平时,可以对1602进行数据字节的传输操作,而为电平时,则是进行命令字节的传输操作。
命令字节,即是用来对LCD1602的一些工作方式作设置的字节;数据字节,即使用以在1602上显示的字节。
值得一提的是,LCD1602的数据是8位的。
脚:
R/W,读写选择端。
当此脚为高电平可对LCD1602进行读数据操作,反之进行写数据操作。
笔者认为,此脚其实用处不大,直接接地永久置为低电平也不会影响其正常工作。
但是尚未经过复杂系统验证,保留此意见。
6脚:
E,使能信号,其实是LCD1602的数据控制时钟信号,利用该信号的上升沿实现对LCD1602的数据传输。
7~14脚:
8位并行数据口,使得对LCD1602的数据读写大为方便。
现在来看LCD1602的操作时序:
在此,我们不需要读出它的数据的状态或者数据本身。
所以只需要看两个写时序:
①当我们要写指令字,设置LCD1602的工作方式时:
需要把RS置为低电平,RW置为低电平,然后将数据送到数据口D0~D7,最后E引脚一个高脉冲将数据写入。
②当我们要写入数据字,在1602上实现显示时:
需要把RS置为高电平,RW置为低电平,然后将数据送到数据口D0~D7,最后E引脚一个高脉冲将数据写入。
发现了么,写指令和写数据,差别仅仅在于RS的电平不一样而已。
一下是LCD1602的时序图:
大家要慢慢学会看时序图,要知道操作一个器件的精华便蕴藏在其中,看懂看准了时序,你操控这个芯片就是非常容易的事了。
1602的时序是我见过的一个最简单的时序:
1.注意时间轴,如果没有标明(其实大部分也都是不标明的),那么从左往右的方向为时间正向轴,即时间在增长。
2.上图框出并注明了看懂此图的一些常识:
1)时序图最左边一般是某一根引脚的标识,表示此行图线体现该引脚的变化,上图分别标明了RS、R/W、E、DB0~DB7四类引脚的时序变化。
2)有线交叉状的部分,表示电平在变化,如上所标注。
3)应该比较容易理解,如上图右上角所示,两条平行线分别对应高低电平,也正好吻合
(2)中电平变化的说法。
4)上图下,密封的菱形部分,注意要密封,表示数据有效,ValidData这个词也显示了这点。
3.需要十分严重注意的是,时序图里各个引脚的电平变化,基于的时间轴是一致的。
一定要严格按照时间轴的增长方向来精确地观察时序图。
要让器件严格的遵守时序图的变化。
在类似于18B20这样的单总线器件对此要求尤为严格。
4.以上几点,并不是LCD1602的时序图所特有的,绝大部分的时序图都遵循着这样的一般规则,所以大家要慢慢的习惯于这样的规则。
也许你还注意到了上面有许多关于时间的标注,这也是个十分重要的信息,这些时间的标注表明了某些状态所要维持的最短或最长时间。
因为器件的工作速度也是有限的,一般都跟不上主控芯片的速度,所以它们直接之间要有时序配合。
话说现在各种处理器的主频也是疯狂增长,日后搞不好出现个双核单片机也不一定就是梦话。
下面是时序参数表:
大家要懂得估计主控芯片的指令时间,可以在官方数据手册上查到MCU的一些级别参数。
比如我们现在主控芯片,外部12MHz晶振,指令周期就是一个时钟周期为(1/12MHz)us,所以至少确定了它执行一条指令的时间是us级别的。
我们看到,以上给的时间参数全部是ns级别的,所以即便我们在程序里不加延时程序,也应该可以很好的配合LCD1602的时序要求了。
怎么看这个表呢?
很简单,我们在时序图里可以找到TR1,对应时序参数表,可以查到这个是E上升沿/下降沿时间,最大值为25ns,表示E引脚上的电平变化,必须在最大为25ns之内的时间完成。
大家看是不是这个意思?
现在我来解读我对这个时序图的理解:
当要写命令字节的时候,时间由左往右,RS变为低电平,R/W变为低电平,注意看是RS的状态先变化完成。
然后这时,DB0~DB7上数据进入有效阶段,接着E引脚有一个整脉冲的跳变,接着要维持时间最小值为tpw=400ns的E脉冲宽度。
然后E引脚负跳变,RS电平变化,R/W电平变化。
这样便是一个完整的LCD1602写命令的时序。
我们看一下开发板的电路图
下面看一下程序:
/**************************************************************************
*实验名:
矩阵键盘实验
*使用的IO:
数码管使用P0,键盘使用P3.0、P3.1、P3.2、P3.3
*实验效果:
按矩阵键盘分别显示在数码管上面显示十六进制的0到F。
*注意:
**************************************************************************/
#include
#defineGPIO_LCDP0
#defineGPIO_KEYP1
sbitLCDE=P2^7;
sbitRW=P2^5;
sbitRS=P2^6;
unsignedcharKeyValue;
//用来存放读取到的键值
unsignedcharKeyState;
//用来存放按键状态
unsignedcharPuZh[]="PechinScience";
voidDelay10ms();//延时50us
voidKeyDown();//检测按键函数
voidLcdWriteCom(unsignedchar);
voidLcdWriteData(unsignedchar);
voidLcdInit();
voidDelay1ms(unsignedint);
/**************************************************************************
*函数名:
main
*函数功能:
主函数
*输入:
无
*输出:
无
**************************************************************************/
voidmain(void)
{
unsignedchari;
LcdInit();
KeyState=0;
for(i=0;i<16;i++)
{
//LcdWriteCom(0x80);
LcdWriteData(PuZh[i]);
}
while
(1)
{
KeyDown();
if(KeyState)
{
KeyState=0;
LcdWriteCom(0x80+0x40);
LcdWriteData('0'+KeyValue);
}
}
}
/**************************************************************************
*函数名:
KeyDown
*函数功能:
检测有按键按下并读取键值
*输入:
无
*输出:
无
**************************************************************************/
voidKeyDown(void)
{
chara;
GPIO_KEY=0x0f;
if(GPIO_KEY!
=0x0f)
{
Delay10ms();
if(GPIO_KEY!
=0x0f)
{
KeyState=1;
//测试列
GPIO_KEY=0X0F;
//Delay10ms();
switch(GPIO_KEY)
{
case(0X07):
KeyValue=0;break;
case(0X0b):
KeyValue=1;break;
case(0X0d):
KeyValue=2;break;
case(0X0e):
KeyValue=3;break;
//default:
KeyValue=17;//检测出错回复17意思是把数码管全灭掉。
}
//测试行
GPIO_KEY=0XF0;
Delay10ms();
switch(GPIO_KEY)
{
case(0X70):
KeyValue=KeyValue;break;
case(0Xb0):
KeyValue=KeyValue+4;break;
case(0Xd0):
KeyValue=KeyValue+8;break;
case(0Xe0):
KeyValue=KeyValue+12;break;
//default:
KeyValue=17;
}
while((a<50)&&(GPIO_KEY!
=0xf0))//检测按键松手检测
{
Delay10ms();
a++;
}
a=0;
}
}
}
/*************************************************************************
*函数名:
Delay10ms
*函数功能:
延时函数,延时10ms
*输入:
无
*输出:
无
**************************************************************************/
voidDelay10ms(void)//误差0us
{
unsignedchara,b,c;
for(c=1;c>0;c--)
for(b=38;b>0;b--)
for(a=130;a>0;a--);
}
/**************************************************************************
*函数名:
Delay1ms
*函数功能:
延时函数,延时1us
*输入:
a
*输出:
无
**************************************************************************/
voidDelay1ms(unsignedinta)
{
unsignedintb,c;
for(c=a;c>0;c--)
for(b=110;b>0;b--);
}
/**************************************************************************
*函数名:
LcdWriteCom
*函数功能:
向LCD写入一个字节的命令
*输入:
com
*输出:
无
**************************************************************************/
voidLcdWriteCom(unsignedcharcom)//写入命令
{
RS=0;
RW=0;
GPIO_LCD=com;
Delay1ms(10);
LCDE=1;
Delay1ms(10);
LCDE=0;
}
/**************************************************************************
*函数名:
LcdWriteData
*函数功能:
向LCD写入一个字节的数据
*输入:
dat
*输出:
无
**************************************************************************/
voidLcdWriteData(unsignedchardat)//写入数据
{
RS=1;
RW=0;
GPIO_LCD=dat;
Delay1ms(10);
LCDE=1;
Delay1ms(10);
LCDE=0;
}
/**************************************************************************
*函数名:
LcdInit()
*函数功能:
初始化LCD屏
*输入:
无
*输出:
无
**************************************************************************/
voidLcdInit()//LCD初始化子程序
{
LcdWriteCom(0x3c);//开显示
LcdWriteCom(0x0c);//开显示不显示光标
LcdWriteCom(0x06);//写一个指针加1
LcdWriteCom(0x01);//清屏
LcdWriteCom(0x80);//设置数据指针起点
}
下载lcd.hex,观察实验结果,实验结果是LCD1602第一行显示PechinScinence,第二行显示按键值。
作几点说明:
1.LCD1602对写进去的数据字节呢是以ASCII码识别的,所以写进去用以显示的字符数据必须是某一个ADCII码,当然如果你不想查ASCII表的话,可以用字符来代替,即用单引号包含的字符常量。
所以,也由此推出,’0’和30H(0的ASCII码)是等价的。
2.操作1602,要先对1602进行初始化,数据手册里写的比较清楚,并且对各个命令字的写入并没有先后要求。
3.1602是有自定义字符的功能的,大家熟悉基本操作之后可以尝试自行拓展
4.在每次写完数据之后,应该要将E引脚置为低电平,为下一次E的高脉冲做准备。
延伸来说,这叫释放时钟线,要养成释放时钟线的好习惯。
对配合时序大有裨益。
5.可以将所要显示的字符一次定义在一个字符数组里,以调用字符数组的形式调用显示数据,这样程序会变得简洁而高效。
6.记住时序的要求,往往是对最小时间有要求,在你严格配合时序的情况下仍然的不到理想的结果时,可以尝试插入延时。
这个并不违反时序的要求。
况且相当多的器件手册并没有详细的讲述最小时间要求。
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 1602 液晶屏 主程序