一、系统设计的任务和要求
1.实验目的
通过设计一个简易拔河比赛游戏机
(1) 熟练掌握EDA软件QUARTUS II的使用方法;
(2) 能利用EDA软件QUARTUS II进行一个电子技术综合问题的设计;
(3) 掌握FPGA系统各种外围接口的灵活运用,培养实验的仿真及下载技能。
(4) 掌握按键分配、CLOCK调用、LED数码管等外围接口的Verilog HDL语言编程;
(5) 通过软件编程和仿真理解并体会VHDL语言的常用编写语言和语法规 ;
(6) 培养分析、寻找和排除电子电路中常见故障的能力;
2. 题目功能分析
1) 设计拔河游戏电路,用按键与LED表示输入与输出。
2) 初始时,24个LED中间的两个点亮(引脚编号是100和99),然后游戏双方不停按动按键(K7和K0),点亮的两个LED向按动按键慢的一方移动;
3) 每按动一下按键,LED向对方移动一格;
4) 只要LED移动到头,游戏结束;
5) 游戏结束时让胜利一方的LED灯(K7方:118-110,K0方:86-98)循环点亮。
6) 设置复位键,按下复位键游戏重新开始。
7) 工作时钟100Hz即可;
二、总体模块划分
1. 设计思路
(1) 24个LED成一排,设置三个按键(复位键、游戏键K0、K7),游戏键每按一次就会产生一个有效低电平,哪边按得快灯就向对方按键移动一位;
(2) 无论何时按下复位键,24个LED立即恢复初始状态,即中间两个亮,其他灭;
(3) 当中间两个LED灯移到任一边终端时,两边选手按键均无效,而获胜一方的LED灯将循环点亮,直到按下复位键,开始下一轮游戏;
2. 按键比较与亮点移位
K0、K7是按键的输入变量,24位BUFF是亮点当前位置的状态变量,初值为000000000001100000000000。配合时钟脉冲,并且游戏使能端开启的情况下,当K7先按下时,BUFF进行逻辑移位,SRL右移,当K0先按下时,BUFF进行逻辑移位,SLL左移。其他情况,BUFF保持不变。
3. 游戏锁定
在任意一方将亮点按动到对方那边的终点后,游戏结束,此时按动游戏键无效。亮点到达终点时即BUFF中第0、1位为1(右端终点)或者第23、22位为1(左端终点)。故设定一个标志变量FLAG,在FLAG=0时按键有效,每当BUFF变化一次就进行一次判断,当BUFF=110000000000000000000000或BUFF=000000000000000000000011时FLAG=1,此时按键无效。
4. 获胜庆祝
8位BUFF2是K7方获胜,需要循环点亮的8个灯的状态变量,有初始值“10000000”,通过BUFF(23 DOWNTO 16)<=BUFF2对BUFF的第23位至第16位进行初始赋值,再通过循环移位,ROR循环右移,实现K7方的8个灯循环点亮,庆祝胜利;同理,11位BUFF3是K0方获胜,需要循环点亮的11个灯的状态变量,有初始值“00000000001”,通过BUFF(10 DOWNTO 10)<=BUFF3对BUFF的第10位至第0位进行初始赋值,再通过循环移位,ROL循环左移,实现K0方的11个灯循环点亮,庆祝胜利。
5. 游戏复位
CLR有初始值为1,按键按下则赋值为零,此时使BUFF恢复初始值,FLAG恢复初始值,实现游戏复位。
三、代码实现
1.定义实体定义输入输出端口
ENTITY VHDL1 IS PORT(CLR,CLK,K7,K0: IN STD_LOGIC; LED: OUT STD_LOGIC_VECTOR(23 DOWNTO 0) ); END VHDL1;
2. 在该实体的一个结构体中定义三个信号量和一个标志变量
SIGNAL BUFF :BIT_VECTOR(23 DOWNTO 0):="000000000001100000000000"; SIGNAL BUFF2 :BIT_VECTOR(7 DOWNTO 0):="10000000"; SIGNAL BUFF3 :BIT_VECTOR(10 DOWNTO 0):="00000000001"; SHARED VARIABLE FLAG :STD_LOGIC:='0';
3. 产生胜利一方,标志位变化,按键失效
IF BUFF = "000000000000000000000011" OR BUFF = "110000000000000000000000" THEN FLAG := '1'; END IF;
4. 按键比较和亮点移动
IF K7 = '0' THEN BUFF <= BUFF SRL 1; ELSIF K0= '0' THEN BUFF <= BUFF SLL 1; END IF;
5. 循环点亮庆祝胜利
IF BUFF(1 downto 0) = "11" THEN BUFF2<=BUFF2 ROR 1 ; BUFF(23 DOWNTO 16)<=BUFF2; ELSIF BUFF(23 DOWNTO 22) = "11" THEN BUFF3<=BUFF3 ROL 1 ; BUFF(10 DOWNTO 0)<=BUFF3; END IF;
6. 游戏重置
ELSIF CLR='0' THEN BUFF<="000000000001100000000000"; FLAG := '0';
7. 源代码
LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY VHDL1 IS PORT(CLR,CLK,K7,K0: IN STD_LOGIC; LED: OUT STD_LOGIC_VECTOR(23 DOWNTO 0) ); END VHDL1; ARCHITECTURE BEHAVIOR OF VHDL1 IS SIGNAL BUFF :BIT_VECTOR(23 DOWNTO 0):="000000000001100000000000"; SIGNAL BUFF2 :BIT_VECTOR(7 DOWNTO 0):="10000000"; SIGNAL BUFF3 :BIT_VECTOR(10 DOWNTO 0):="00000000001"; SHARED VARIABLE FLAG :STD_LOGIC:='0'; BEGIN PROCESS(K0,K7,CLK,CLR) BEGIN IF BUFF = "000000000000000000000011" OR BUFF = "110000000000000000000000" THEN FLAG := '1'; END IF; IF CLR='1' THEN IF CLK'EVENT AND CLK='1' THEN IF FLAG='0' THEN IF K7 = '0' THEN BUFF <= BUFF SRL 1; ELSIF K0= '0' THEN BUFF <= BUFF SLL 1; END IF; ELSIF FLAG='1' THEN IF BUFF(1 downto 0) = "11" THEN BUFF2<=BUFF2 ROR 1 ; BUFF(23 DOWNTO 16)<=BUFF2; ELSIF BUFF(23 DOWNTO 22) = "11" THEN BUFF3<=BUFF3 ROL 1 ; BUFF(10 DOWNTO 0)<=BUFF3; END IF; END IF; END IF; ELSIF CLR='0' THEN BUFF<="000000000001100000000000"; FLAG := '0'; END IF; LED <= TO_STDLOGICVECTOR(BUFF); END PROCESS; END ARCHITECTURE;
四、仿真结果
仿真波形
实现了24个灯的初始状态
K7方获胜之后,开始循环点亮23-16位的灯
K7按键快,实现逻辑右移