VHDL程序之交通灯控制系统设计
前言
本次实验所用软件为Quartus||9.0
,所用板载为EPF10K20T144-4
。
注意事项
(1)创建VHDL工程时选择板载系列一定要按照板载芯片上的系列选中。
(2)目前使用的Quartus || 9.0
不支持输入汉字的功能,只支持显示汉字的功能,所以想要在上面显示汉字,得先在记事本中写好自己要写的汉字内容,然后再复制粘贴到Quartus || 9.0
上的文件中。
(3)安装驱动程序前一定要记得禁止驱动程序签名。
(4)配置完引脚以后一定要记得要再编译一次。
实验题目
1、实验要求。
要求一:交叉路口为十字路口;
要求二:每路口设直行、左转、右转的方向指示灯;
要求三:每个方向指示灯有三种颜色,即红、绿、黄三色。为简化设计,右转指示灯常绿;
要求四:为应用实验板上的资源,每个方向用一个指示灯表示(灯亮表示停车等候,灯灭表示绿灯通行,闪烁表示黄灯警示)。
要求五:每路口需用两个数码管显示允许通行或禁止通行的时间。
代码实现
1、实现思路如下。
(注:代码如下)
LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.ALL;
USE IEEE.STD_LOGIC_UNSIGNED.ALL;
ENTITY traffic_light IS
port( clk :in std_logic;
L1 : out std_logic_vector(2 downto 0);--北方向灯
L2 : out std_logic_vector(2 downto 0);--南方向灯
L3 : out std_logic_vector(2 downto 0);--西方向灯
L4 : out std_logic_vector(2 downto 0);--东方向灯
DS : out std_logic_vector(6 downto 0);--段选
WS : out std_logic_vector(7 downto 0)--位选
);
end traffic_light;
architecture one of traffic_light is
type FSM is (s0,s1,s2,s3,s4,s5,s6,s7,s8,s9,s10,s11,s12); --自定义数据类型
signal cst,next_state : FSM;
signal count,count1 : integer range 0 to 999;--输入1KHz,时钟为1MS,则通过计数将时钟转为1S
signal clk1,clk2 : std_logic; --分频所用代替时钟
signal cnt : integer := 0 ;
signal tmp,tmp1 ,data : std_logic_vector(7 downto 0);
signal sum : integer range 0 to 199;
begin
--计时进程
process(CLK)
begin
if clk'event and clk ='1' then
if count1 =4 then --用来给数码管扫描4ms
count1 <= 0;
clk2 <= '1';
else
count1 <= count1 + 1;
clk2 <= '0';
end if;
if count = 999 then --用来计时1S
count <= 0;
sum <= sum +1;
if sum = 179 then
sum <= 0;
end if;
clk1 <= '1';--时钟频率为1Hz
else
count <= count + 1;
clk1 <= '0';
end if;
end if;
end process;
--每一秒执行一次REG进程
REG:process (clk1,sum)
begin
if clk1'event and clk1 = '1' then
cst <= next_state;
end if;
end process REG;
--红绿灯状态控制
COM:process (cst,sum)
variable t1,t2,t3 : std_logic_vector(7 downto 0);
begin
case cst is
when s0 => L1 <= "110";
L2 <= "110";
L3 <= "110";
L4 <= "110";
if sum < 20 then next_state <= s0;
else next_state <= s9;
end if;
when s9 => L1 <= "110";
L2 <= "110";
L3 <= "100";
L4 <= "100";
if sum < 40 then
next_state <= s9;
else
next_state <= s1;
end if;
when s1 => L1 <= "110";
L2 <= "110";
L3 <= "100";
L4 <= "100";
if sum < 60 then
next_state <= s7;
else
next_state <= s10;
end if;
when s10 =>L1 <= "100";
L2 <= "100";
L3 <= "110";
L4 <= "110";
if sum < 80 then
next_state <= s10;
else
next_state <= s2;
end if;
when s2 => L1 <= "100";
L2 <= "100";
L3 <= "110";
L4 <= "110";
if sum > 80 and sum < 100 then next_state <= s5;
else next_state <= s11;
end if;
when s11 => L1 <= "110";
L2 <= "110";
L3 <= "010";
L4 <= "010";
if sum > 100 and sum < 120 then next_state <= s11;
else next_state <= s3;
end if;
when s3 => L1 <= "110";
L2 <= "110";
L3 <= "010";
L4 <= "010";
if sum > 120 and sum < 140 then next_state <= s8;
else next_state <= s12;
end if;
when s12 =>L1 <= "010";
L2 <= "010";
L3 <= "110";
L4 <= "110";
if sum > 140 and sum < 160 then next_state <= s12;
else next_state <= s4;
end if;
when s4 => L1 <= "010";
L2 <= "010";
L3 <= "110";
L4 <= "110";
if sum > 160 and sum < 180 then next_state <= s6;
else next_state <= s9;
end if;
when s5 => L1 <= "110";
L2 <= "110";
L3 <= "110";
L4 <= "110";
if sum > 80 and sum < 100 then
next_state <= s2;
else next_state <= s11;
end if;
when s6 => L1 <= "110";
L2 <= "110";
L3 <= "110";
L4 <= "110";
if sum > 160 and sum < 180 then
next_state <= s4;
else next_state <= s9;
end if;
when s7 => L1 <= "110";
L2 <= "110";
L3 <= "110";
L4 <= "110";
if sum > 40 and sum < 60 then
next_state <= s1;
else next_state <= s10;
end if;
when s8 => L1 <= "110";
L2 <= "110";
L3 <= "110";
L4 <= "110";
if sum > 120 and sum < 140 then
next_state <= s3;
else next_state <= s12;
end if;
end case;
end process COM;
--每一秒执行一次计数
process(clk1)
begin
if clk1'event and clk1 = '1' then
if tmp = 0 then
tmp <= "00001001";--十位赋值9
if tmp1 = 2 or tmp1 = 1 then
tmp1 <= tmp1 - 1;
else
tmp1 <= "00000001";
end if;
else
tmp <= tmp - 1;
end if;
end if;
end process;
process(clk2)--该进程的目的就是为了达到一种动态交替的效果
begin
if clk2'event and clk2 = '1' then
cnt <= cnt+1;------每1/1000秒的时间cnt+1,主要用于扫描数码管
if cnt = 2 then
cnt <= 0;
end if;
end if;
end process;
-------------------------------------------------------------
process(cnt)
begin
case cnt is
when 0 => WS <= "11111101";data <= tmp1;--当cnt为0时亮倒数第二个数码管,来完成一个动态扫描的目的
when 1 => WS <= "11111110";data <= tmp;
when others => null;
end case;
end process;
process (data)
begin
case data is
when "00000000" => DS <="1111110";--显示0
when "00000001" => DS <="0110000";--显示1
when "00000010" => DS <="1101101";--显示2
when "00000011" => DS <="1111001";--显示3
when "00000100" => DS <="0110011";--显示4
when "00000101" => DS <="1011011";--显示5
when "00000110" => DS <="1011111";--显示6
when "00000111" => DS <="1110000";--显示7
when "00001000" => DS <="1111111";--显示8
when "00001001" => DS <="1111011";--显示9
when others =>DS<="0000000";
end case;
end process;
end one;
烧入板载实现
(注:东西左转实现图如下)
(注:南北左转实现图如下)
转载:https://blog.csdn.net/APPDREAMER/article/details/116030150
查看评论