利用键盘开关控制液晶显示器进行十六进制数字显示.docx

上传人:b****6 文档编号:3642703 上传时间:2022-11-24 格式:DOCX 页数:24 大小:312.92KB
下载 相关 举报
利用键盘开关控制液晶显示器进行十六进制数字显示.docx_第1页
第1页 / 共24页
利用键盘开关控制液晶显示器进行十六进制数字显示.docx_第2页
第2页 / 共24页
利用键盘开关控制液晶显示器进行十六进制数字显示.docx_第3页
第3页 / 共24页
利用键盘开关控制液晶显示器进行十六进制数字显示.docx_第4页
第4页 / 共24页
利用键盘开关控制液晶显示器进行十六进制数字显示.docx_第5页
第5页 / 共24页
点击查看更多>>
下载资源
资源描述

利用键盘开关控制液晶显示器进行十六进制数字显示.docx

《利用键盘开关控制液晶显示器进行十六进制数字显示.docx》由会员分享,可在线阅读,更多相关《利用键盘开关控制液晶显示器进行十六进制数字显示.docx(24页珍藏版)》请在冰豆网上搜索。

利用键盘开关控制液晶显示器进行十六进制数字显示.docx

利用键盘开关控制液晶显示器进行十六进制数字显示

中北大学

课程设计说明书

 

 

 

学生姓名:

张彪

学号:

0706024146 

学院:

电子计算机科学与技术学院 

专业:

微电子学 

题目:

利用键盘开关控制液晶显示器进行十六进制数字显示

 

 

指导教师:

王红亮职称:

讲师

 

 

 

 

2010年6月25日

目录

1、课程设计的目的………………………………………………………2

2、课程设计内容和要求……………………………………………………2

2.1、课程设计内容………………………………………………………2

2.2、课程设计要求………………………………………………………2

3、设计方案及实现情况………………………………………………2

3.1、设计思路……………………………………………………………2

3.2、工作原理及框图……………………………………………………3

3.3、各模块功能描述……………………………………………………3

3.4、程序VHDL语言源代码………………………………………………………4

3.5、仿真结果…………………………………………………………………12

3.6、实验箱验证情况……………………………………………………13

4、课程设计总结………………………………………………………16

5、参考文献……………………………………………………………17

6、附录:

液晶显示器简介……………………………………………17

 

1、课程设计的目的

(1)学习操作数字电路设计实验开发系统,掌握液晶显示模块的工作原理及应用。

(2)掌握组合逻辑电路、时序逻辑电路的设计方法。

(3)学习掌握可编程器件设计的全过程。

2、课程设计的内容和要求

2.1、课程设计内容

(1)学习掌握键盘开关控制模块、液晶显示模块的工作原理及应用;

(2)熟练掌握VHDL编程语言,编写键盘开关控制模块的控制逻辑;

(3)仿真所编写的程序,模拟验证所编写的模块功能;

(4)下载程序到芯片中,硬件验证所设置的功能,能够实现十六进制数字的显示;

(5)整理设计内容,编写设计说明书。

2.2、课程设计要求

(1)本课程设计说明书。

(2)VHDL源程序及内部原理图。

(3)该设计可以在实验箱上正常工作并演示。

3、设计方案及实现情况

3.1、设计思路

本次设计要求利用VHDL语言编写源程序,利用键盘控制液晶显示十六进制数。

因此,本次设计的程序利用矩阵键盘模块产生的按键信号来控制OCMJ模块显示0~F十六进制数。

当程序被下载到FPGA中,首先进行上电自复位,接着检测是否有按键按下,并判读是否是一个干扰,如果确定是0~F中的某一按键按下,则程序将检测OCMJ的BUSY信号是否为高,若为高,则继续等待,否则将按键对应的地址送入OCMJ模块的存储单元中,而液晶模块也会置REQ信号为高电平,完成一次握手,同时FPGA向OCMJ发送一个四字的命令,分别是显示8*8ASCII码命令F1、显示坐标值XX\YY,以及按键的键值QQ。

(注:

第一次传送前会先发送一个清零命令F4)若再有按键按下则重复上述过程。

3.2、工作原理及框图

本实验采用的是OCMJ中文模块系列液晶显示器,内含GB231216*16点阵国标一级简体汉字和ASCII8*8(半高)及8*16(全高)点阵英文字库,用户输入区位码或ASCII码即可实现文本显示。

OCMJ中文模块系列液晶显示器也可用作一般的点阵图形显示器之用。

提供有位点阵和字节点阵两种图形显示功能,用户可在指定的屏幕位置上以点为单位或以字节为单位进行图形显示。

完全兼容一般的点阵模块。

OCMJ中文模块系列液晶显示器可以实现汉字、ASCII码、点阵图形和变化曲线的同屏显示,并可通过字节点阵图形方式造字。

引脚功能图和内部结构图分别如下图1所示。

图1液晶显示器

3.3、各功能模块作用描述

矩阵模块由四个子电路构成,对应于源程序的四个进程。

它们分别是时钟产生电路、键盘扫描电路、键盘消抖电路、以及键盘译码电路。

时钟产生电路时利用自由的计数器产生各种频率的时钟信号。

在设计中,用到了系统时钟信号、分频产生的键盘扫描信号、消抖信号。

键盘扫描电路的作用是用来提供键盘扫描信号的电路。

扫描时依序扫描八列按键,当扫描信号为000时,扫描0这一列按键......没扫描一列按键,就检查一次是否有按键按下,如果这排有按键按下,就马上停止扫描,立即进行按键编码动作,存储键码,如果没有按键按下,则继续扫描下一列。

键盘消抖电路的使用是因为按键大多是机械式的开关结构,在开关切换的瞬间会在接触点出现来回弹跳的现象,因此必须加上键盘消抖电路,避免误操作信号的发生。

相关信号定义:

在本次课程设计中,定义的主要输入输出信号有:

液晶模块的请求应答信号REQ\BUSY(主要用于OCMJ是否决定处理数据上的数据);键盘选通信号SEL/KEY(两者一起构成键盘行、列扫描信号结合后的信号dcc);数据输出信号DOUT。

同时还定义了重要的过程信号,其中counter为计数信号,用来确定REQ(本设计中是计3个数后,REQ才为1,否则为0)。

addrbegin用来定义存储器首地址,addr1用来存储地址变量(传送一个数据需要送4个字节,分别是写命令字节,横坐标字节,纵坐标字节,写的内容字节);addr用来定义数据地址(由addrbegin和addr1构成);DAT用来记录输入到lcd的数据,counter1用来分频计数(本设计是四分频);counte为键盘扫描辅助信号(类似于连接线的作用);counter2为弹跳消除信号(消抖的方法有三种:

加延时程序,需考虑不同器件的延时时间和温度;加触发器,需考虑时钟的同步性;本设计采用计数的方式来消除按键抖动的影响计三十次数之后数据稳定后才开始读入);dcc用来记录键盘行、列扫描信号结合后的信号,DCC1用来记录按下的为哪个键。

clk1,test,koff分别为时钟1信号,测试信号,按键消抖信号(test=’0‘时,表示有按键按下,koff='0'时,表示按键无抖动影响)。

3.4、程序VHDL语言源代码

LIBRARYieee;

USEieee.std_logic_1164.ALL;

USEieee.std_logic_unsigned.ALL;

USEieee.std_logic_arith.all;

ENTITYshixianis

PORT(clr,clk,BUSY:

INstd_logic;

REQ:

OUTstd_logic;

sel:

OUTSTD_LOGIC_VECTOR(2downto0);

key:

INSTD_LOGIC_VECTOR(3downto0);

dout:

outstd_logic_vector(7downto0));

ENDshixian;

ARCHITECTUREdoitOFshixianIS

signalcounter:

std_logic_vector(7downto0);

signaladdrbegin:

std_logic_vector(7downto0);

signaladdr1:

std_logic_vector(7downto0);

signaladdr:

std_logic_vector(7DOWNTO0);

signalDAT:

std_logic_vector(7downto0);

signalcounter1:

std_logic_vector(1downto0);

signalcounte:

std_logic_vector(2downto0);

signalcounter2:

std_logic_vector(4downto0);

signaldcc:

std_logic_vector(6downto0);

signalclk1,test,koff:

std_logic;

signalDCC1:

STD_LOGIC_VECTOR(3DOWNTO0);

BEGIN

test<=key(3)andkey

(2)andkey

(1)andkey(0);

P0:

process(clr,clk)

begin

if(clr='0')then

counter1<="00";

elsif(clk'eventandclk='1')then

counter1<=counter1+1;

endif;

endprocessP0;

clk1<='0'whencounter1<="01"else

'1';

P1:

process(clr,clk1,test)

begin

if(clr='0')then

counte<="000";

elsif(clk1'eventandclk1='1')then

if(test='0')or(koff='0')then

counte<=counte;

else

counte<=counte+1;

endif;

endif;

endprocessP1;

sel<=counte;

dcc<=counte&key;

P2:

process(clk,test)

begin

ifclr='0'then

dcc1<="0000";

elsif(clk'eventandclk='0')then

if(dcc="0001110")then

dcc1<="0000";

elsif(dcc="0011110")then

dcc1<="0001";

elsif(dcc="0101110")then

dcc1<="0010";

elsif(dcc="0111110")then

dcc1<="0011";

elsif(dcc="1101110")then

dcc1<="0100";

elsif(dcc="1111110")then

dcc1<="0101";

elsif(dcc="0001101")then

dcc1<="0110";

elsif(dcc="0011101")then

dcc1<="0111";

elsif(dcc="1001101")then

dcc1<="1000";

elsif(dcc="1011101")then

dcc1<="1001";

elsif(dcc="1101101")then

dcc1<="1010";

elsif(dcc="1111101")then

dcc1<="1011";

elsif(dcc="0101011")then

dcc1<="1100";

elsif(dcc="0111011")then

dcc1<="1101";

elsif(dcc="1001011")then

dcc1<="1110";

elsif(dcc="1011011")then

dcc1<="1111";

elsif(test='0')then

dcc1<="1111";

endif;

endif;

endprocessP2;

P3:

process(test,clk,clr)

begin

if(clr='0')then

counter2<="00000";

koff<='1';

elsif(clk'eventandclk='1')then

if(test='0')then

counter2<="00000";

koff<='0';

elsif(counter2<"11110")then

counter2<=counter2+1;

elsif(counter2="11110")then

koff<='1';

endif;

endif;

endprocessP3;

p4:

process(dcc1)

begin

casedcc1is

when"0000"=>addrbegin<="00000001";

when"0001"=>addrbegin<="00000101";

when"0010"=>addrbegin<="00001001";

when"0011"=>addrbegin<="00001101";

when"0100"=>addrbegin<="00010001";

when"0101"=>addrbegin<="00010101";

when"0110"=>addrbegin<="00011001";

when"0111"=>addrbegin<="00011101";

when"1000"=>addrbegin<="00100001";

when"1001"=>addrbegin<="00100101";

when"1010"=>addrbegin<="00101001";

when"1011"=>addrbegin<="00101101";

when"1100"=>addrbegin<="00110001";

when"1101"=>addrbegin<="00110101";

when"1110"=>addrbegin<="00111001";

when"1111"=>addrbegin<="00111101";

whenothers=>null;

endcase;

endprocessp4;

P5:

process(clr,busy)

begin

if(clr='0')then

addr<="00000000";

elsif(busy'eventandbusy='0')then

addr<=addrbegin+addr1;

endif;

endprocessP5;

P6:

process(clr,busy)

begin

if(clr='0')then

addr1<="00000000";

elsif(busy'eventandbusy='1')then

if(addr1="00000011")then

addr1<="00000000";

else

addr1<=addr1+1;

endif;

endif;

endprocessP6;

P7:

process(busy,clk)

begin

if(busy='1')then

counter<="00000000";

elsif(clk'eventandclk='1')then

counter<=counter+1;

endif;

endprocessP7;

dout<=DAT;

REQ<='1'whencounter>="00000011"else

'0';

P8:

PROCESS(addr)

BEGIN

CASEaddrIS

WHEN"00000000"=>DAT<="11110100";

WHEN"00000001"=>DAT<="11110001";

WHEN"00000010"=>DAT<="00001000";

WHEN"00000011"=>DAT<="00001000";

WHEN"00000100"=>DAT<="00110000";

WHEN"00000101"=>DAT<="11110001";

WHEN"00000110"=>DAT<="00001000";

WHEN"00000111"=>DAT<="00001000";

WHEN"00001000"=>DAT<="00110001";

WHEN"00001001"=>DAT<="11110011";

WHEN"00001010"=>DAT<="00001000";

WHEN"00001011"=>DAT<="00001000";

WHEN"00001100"=>DAT<="00110010";

WHEN"00001101"=>DAT<="11110001";

WHEN"00001110"=>DAT<="00001000";

WHEN"00001111"=>DAT<="00001001";

WHEN"00010000"=>DAT<="00110011";

WHEN"00010001"=>DAT<="11110001";

WHEN"00010010"=>DAT<="00001000";

WHEN"00010011"=>DAT<="00001000";

WHEN"00010100"=>DAT<="00110100";

WHEN"00010101"=>DAT<="11110001";

WHEN"00010110"=>DAT<="00001000";

WHEN"00010111"=>DAT<="00001000";

WHEN"00011000"=>DAT<="00110101";

WHEN"00011001"=>DAT<="11110001";

WHEN"00011010"=>DAT<="00001000";

WHEN"00011011"=>DAT<="00001000";

WHEN"00011100"=>DAT<="00110110";

WHEN"00011101"=>DAT<="11110001";

WHEN"00011110"=>DAT<="00001000";

WHEN"00011111"=>DAT<="00001000";

WHEN"00100000"=>DAT<="00110111";

WHEN"00100001"=>DAT<="11110001";

WHEN"00100010"=>DAT<="00001000";

WHEN"00100011"=>DAT<="00001000";

WHEN"00100100"=>DAT<="00111000";

WHEN"00100101"=>DAT<="11110001";

WHEN"00100110"=>DAT<="00001000";

WHEN"00100111"=>DAT<="00001000";

WHEN"00101000"=>DAT<="00111001";

WHEN"00101001"=>DAT<="11110001";

WHEN"00101010"=>DAT<="00001000";

WHEN"00101011"=>DAT<="00001000";

WHEN"00101100"=>DAT<="01000001";

WHEN"00101101"=>DAT<="11110001";

WHEN"00101110"=>DAT<="00001000";

WHEN"00101111"=>DAT<="00001000";

WHEN"00110000"=>DAT<="01000010";

WHEN"00110001"=>DAT<="11110001";

WHEN"00110010"=>DAT<="00001000";

WHEN"00110011"=>DAT<="00001000";

WHEN"00110100"=>DAT<="01000011";

WHEN"00110101"=>DAT<="11110001";

WHEN"00110110"=>DAT<="00001000";

WHEN"00110111"=>DAT<="00001000";

WHEN"00111000"=>DAT<="01000100";

WHEN"00111001"=>DAT<="11110011";

WHEN"00111010"=>DAT<="00001000";

WHEN"00111011"=>DAT<="00001000";

WHEN"00111100"=>DAT<="01000101";

WHEN"00111101"=>DAT<="11110001";

WHEN"00111110"=>DAT<="00001000";

WHEN"00111111"=>DAT<="00001000";

WHEN"01000000"=>DAT<="01000110";

WHENOTHERS=>DAT<="00000000";

ENDCASE;

ENDPROCESSP8;

ENDdoit;

 

3.5、仿真结果

图2仿真波形

3.6、实验箱验证情况

图3数字0图4数字1

图5数字2图6数字3

图7数字4图8数字5

图9数字6图10数字7

图11数字8图12数字9

图13字母A图14字母B

图15字母C图16字母D

图17字母E图18字母F

图19管脚分配图

图20连接图

4、课程设计总结

回顾起此次的利用键盘开关控制液晶显示器进行十六进制数字显示课程设计,至今我仍感慨颇多:

即便这是第二次做课程设计,但每次对我来说都是新的,都需要自己去构思,去熟悉以前的知识。

本次课程设计所应用的主要由矩阵键盘模块和液晶模块两部分构成,由于需要两个模块共同完成这次试验的,连接的部分显得尤为重要。

在源程序中使用的是信号来作为连接的,它的作用就是一个桥梁,就类似于连接线。

我查阅了相关矩阵键盘和液晶模块的书籍,了解了设计中所用到的模块的电气性能和参数(主要是液晶模块OCMJ)。

在设计的过程中遇到问题,可以说得是困难重重,即使是第二次做的,难免会遇到过各种各样的问题:

在仿真程序的时候能顺利通过,但在和机箱连接之后,当有些按下键时,会出现明显的延时,有的甚至不能显示出相应的数字。

后来查阅书籍才知道,当按键按下时,会出现抖动,数据有一段不稳定的时期,这就需要我们进行消抖。

消抖的方法有三种:

加延时程序,需考虑不同器件的延时时间和温度;加触发器,需考虑时钟的同步性;本设计采用计数的方式来消除按键抖动的影响计三十次数之后数据稳定后才开始读入。

但有时候电脑的发热等情况也会影响到仿真波形,出现抖动。

这次课程设计终于顺利完成了,我了解了液晶显示屏的逻辑和时序控制要求,掌握液晶显示器的工作原理及应用

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 高中教育 > 语文

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1