|
--*****************************************************************
--文件名: watch.vhd
--文件描述:本文件为电子设计而开发的多功能数字钟VHDL语言完整源代码
--该数字钟实现的功能有时间,秒表,闹钟,年月日的显示设置等
--开发小组:信科04-3班 吴喆 张力文 王腾腾
--时间:2007年7月
--*********************************************************************
LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.ALL;
USE IEEE.STD_LOGIC_ARITH.ALL;
USE IEEE.STD_LOGIC_UNSIGNED.ALL;
USE IEEE.STD_LOGIC_UNSIGNED;
ENTITY watch IS
PORT(clk,scanclk,clr,clock,sclock,data,pause,m_add,h_add,mclock,hclock:IN STD_LOGIC;
music:OUT STD_LOGIC;
row:OUT STD_LOGIC_VECTOR(7 DOWNTO 0);
led:OUT STD_LOGIC_VECTOR(7 DOWNTO 0);
leda:OUT STD_LOGIC_VECTOR(7 DOWNTO 0));
END watch;
ARCHITECTURE Behavioral OF watch IS
SIGNAL clk_div2,clk_div1:STD_LOGIC_VECTOR(9 DOWNTO 0);
SIGNAL clk_div3:STD_LOGIC_VECTOR(4 DOWNTO 0);
SIGNAL clk0,clk1,nomusic,year:STD_LOGIC;
SIGNAL month:STD_LOGIC_VECTOR(1 DOWNTO 0);
SIGNAL hh,hl,mh,ml,sh,sl:STD_LOGIC_VECTOR(3 DOWNTO 0);--时分秒
SIGNAL shh,shl,smh,sml,ss:STD_LOGIC_VECTOR(3 DOWNTO 0);--闹钟时分秒
SIGNAL ssh,ssl,fs,msh,msl:STD_LOGIC_VECTOR(3 DOWNTO 0);--秒表时分秒
SIGNAL nhh,nhl,nlh,nll,yh,yl,dh,dl:STD_LOGIC_VECTOR(3 DOWNTO 0);--年月日
SIGNAL dispcnt:STD_LOGIC_VECTOR(2 DOWNTO 0);
SIGNAL num:STD_LOGIC_VECTOR(3 DOWNTO 0);
SIGNAL numh:STD_LOGIC_VECTOR(3 DOWNTO 0);
SIGNAL a,b,c,d:INTEGER range 0 to 9;
BEGIN
P1 ROCESS(clk) ----产生脉冲信号
BEGIN
IF rising_edge(clk) THEN
clk_div1<=clk_div1+'1';
IF ( clk_div1 = "1111101000")THEN
clk_div1 <= (others=>'0');
clk_div3<=clk_div3+'1';
END IF;
IF( clk_div3 = "10100") THEN
clk0 <= NOT clk0; ----产生1ms脉冲信号
clk_div3 <= (others=>'0');
clk_div2<=clk_div2+'1';
END IF;
IF( clk_div2 = "1111101000") THEN
clk_div2 <= (others=>'0');
clk1 <= NOT clk1; ----产生1s脉冲信号
END IF;
END IF;
END PROCESS P1;
P2 ROCESS(clk1,clr) ---60秒计数器
BEGIN
IF(clr='1')AND(sclock = '0')AND(data='0') THEN
sl<="0000";
sh<="0000";
ELSIF rising_edge(clk1)THEN
IF sl="1001"THEN
IF(sh="0101")THEN
sh<="0000";
ELSE
sh<=sh+'1';
END IF;
sl<="0000";
ELSE
sl<=sl+'1';
END IF;
END IF;
END PROCESS P2;
P3 ROCESS(clk1,clr,sh,sl,m_add) --60分计数器
BEGIN
IF (clr='1')AND(sclock = '0')AND(data='0')THEN
ml<="0000";
mh<="0000";
ELSIF rising_edge(clk1)THEN
IF(((sh="0101")AND(sl="1001"))OR(m_add='1'))THEN
IF((mh="0101")AND(ml="1001"))THEN
mh<="0000";ml<="0000";
ELSIF ml="1001" THEN
mh <= mh+'1';
ml <= "0000";
ELSE
ml<=ml+'1';
END IF;
END IF;
END IF;
END PROCESS P3;
P4 ROCESS(clk1,clr,mh,ml,sh,sl,h_add) --24 时计数器
BEGIN
IF (clr='1')AND(sclock = '0')AND(data='0')THEN
hl<="0000";
hh<="0000";
ELSIF rising_edge(clk1)THEN
IF(((sh="0101")AND(sl="1001")AND(mh="0101")AND(ml="1001"))OR(h_add='1'))THEN
IF((hh="0010")AND(hl="0011"))THEN
hh<="0000";hl<="0000";
ELSIF(hl="1001")THEN
hh <= hh +'1';
hl <= "0000";
ELSE
hl<=hl+'1';
END IF;
END IF;
END IF;
END PROCESS P4;
P5 ROCESS(clk0,clr,sclock) ---毫秒计数器
BEGIN
IF (clr='1')AND(sclock='1') THEN
msl<="0000";
msh<="0000";
fs <="0000";
ELSIF rising_edge(clk0) THEN
IF sclock = '1' THEN
IF (msl="1001")AND(pause='0') THEN
IF(msh="1001")THEN
if(fs="1001")THEN
fs<="0000";
ELSE
fs<=fs+'1';
END IF;
msh<="0000";
ELSE
msh<=msh+'1';
END IF;
msl<="0000";
ELSE
msl<=msl+'1';
END IF;
END IF;
END IF;
END PROCESS P5;
P6 ROCESS(clk0,clr,msh,msl,fs,sclock) --s 计数器
BEGIN
IF (clr='1')AND(sclock='1')THEN
ssl<="0000";
ssh<="0000";
ELSIF rising_edge(clk0)THEN
IF (sclock = '1')AND(pause='0')THEN
IF((fs="1001")AND(msh="1001")AND(msl="1001"))THEN
IF((ssh="0101")AND(ssl="1001"))THEN
ssh<="0000";ssl<="0000";
ELSIF(ssl="1001")THEN
ssh <= ssh +'1';
ssl <= "0000";
ELSE
ssl<=ssl+'1';
END IF;
END IF;
END IF;
END IF;
END PROCESS P6;
P7 ROCESS(clock,clk1) ---设置闹钟时间
BEGIN
IF rising_edge( clk1 ) THEN
IF ( ( clock = '1')AND(mclock = '1')) THEN
IF( sml = "1001" ) THEN
IF(smh="0101") THEN
smh <="0000";
ELSE
smh <= smh+'1';
END IF;
sml <= "0000";
ELSE
sml <= sml + '1';--nomusic <= '1';
END IF;
END IF;
IF (( clock = '1') AND (hclock = '1'))THEN
IF( (shh="0010")AND(shl ="0011") ) THEN
shh <= "0000";shl <= "0000";
ELSIF(shl="1001") THEN
shh <= shh+'1';
shl <= "0000";
ELSE
shl <= shl + '1';
END IF;
END IF;
END IF;
END PROCESS P7;
P8 ROCESS(clk1) --闹钟音乐
BEGIN
IF rising_edge( clk1 ) THEN
IF((shl = hl )AND(shh = hh)AND(sml = ml )AND(smh = mh)AND(nomusic = '0')) THEN
music <= '1';
ss <= sml + "0001";
IF (clock = '1') THEN
music <= '0';
nomusic <= '1';
END IF;
END IF;
IF(ml = ss) THEN
music <= '0';
nomusic <= '0';
END IF;
END IF;
END PROCESS P8;
P9 ROCESS(clk1,yh,yl,a,b,c,d) ---闰年,月份判断
VARIABLE q,w:INTEGER range 0 to 30 := 0 ;
VARIABLE count:INTEGER range 0 to 100 :=0;
BEGIN
IF((yh="0000")AND(yl="0010"))THEN
month<="00";
ELSIF((yh="0000")AND(yl="0100"))OR((yh="0000")AND(yl="0110"))OR((yh="0000")AND(yl="1001"))OR((yh="0001")AND(yl="0001"))THEN
month<="01";
ELSE
month<="10";
END IF;
IF (c=0)AND(d=0) THEN
count := INTEGER(10*a+ 1*b);
q:=INTEGER(count / 4 );
w:=INTEGER(4*q);
IF(count = w) THEN
year <= '0';
ELSE
year <= '1';
END IF;
ELSE
count := INTEGER(10*c+ 1*d);
q:=INTEGER(count / 4 );
w:=INTEGER(4*q);
IF(count = w)THEN
year <= '0';
ELSE
year <= '1';
END IF;
END IF;
END PROCESS P9;
P10 ROCESS(clk1,clr,hh,hl,data,month,year) ---年月日
BEGIN
IF(clr='1')AND(data ='1') THEN
yh<="0000";yl<="0001";
dh<="0000";dl<="0001";
nhh<="0010";nhl<="0000";
nlh<="0000";nll<="0000";
ELSIF rising_edge(clk1) THEN
IF ((data='1')AND(pause='1')) THEN
IF (month="00") THEN
IF(year='0')THEN
IF(dh="0010")AND(dl="1001")THEN
dl<="0001";dh<="0000";
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
ELSE
IF(dh="0010")AND(dl="1000")THEN
dl<="0001";dh<="0000";
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
END IF;
ELSIF(month="01")THEN
IF(dh="0011")AND(dl="0000")THEN
dh<="0000";dl<="0001";
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
ELSIF(month="10") THEN
IF(dh="0011")AND(dl="0001")THEN
dh<="0000";dl<="0001";
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
END IF;
END IF;
IF(data='1')AND(mclock='1')THEN
IF(yh="0001")AND(yl="0010")THEN
yh<="0000";yl<="0001";
ELSIF(yl="1001") THEN
yl<="0000";yh<=yh+'1';
ELSE
yl<=yl+'1';
END IF;
END IF;
IF(data='1')AND(hclock='1')THEN
IF(nll="1001") THEN
IF(nlh="1001")THEN
IF(nhl="1001")THEN
nhl<="0000";nhh<=nhh+'1';
ELSE
nlh<="0000";nhl<=nhl+'1';
END IF;
ELSE
nll<="0000";nlh<=nlh+'1';
END IF;
ELSE
nll<=nll+'1';
END IF;
END IF;
IF ((hh="0010")AND(hl="0011")AND(mh="0101")AND(ml="1001")AND(sh="0101")AND(sl="1001")) THEN
IF (month="00") THEN
IF(year='0')THEN
IF(dh="0010")AND(dl="1001")THEN
dl<="0001";dh<="0000";
yl<=yl+'1';
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
ELSE
IF(dh="0010")AND(dl="1000")THEN
dl<="0001";dh<="0000";
yl<=yl+'1';
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
END IF;
ELSIF(month="01")THEN
IF(dh="0011")AND(dl="0000")THEN
dh<="0000";dl<="0001";
IF(yl="1001")THEN
yl<="0000";yh<="0001";
ELSE
yl<=yl+'1';
END IF;
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
ELSIF(month="10") THEN
IF(dh="0011")AND(dl="0001")THEN
dh<="0000";dl<="0001";
IF(yh="0001")AND(yl="0010")THEN
yl<="0001";yh<="0000";
IF(nll="1001")THEN
nll<="0000";
IF(nlh="1001")THEN
IF(nhl="1001")THEN
nhl<="0000";nhh<=nhh+'1';
ELSE
nhl<=nhl+'1';
END IF;
nlh<="0000";
ELSE
nlh<=nlh+'1';
END IF;
ELSE
nll<=nll+'1';
END IF;
ELSE
yl<=yl+'1';
END IF;
ELSIF(dl="1001")THEN
dl<="0000";dh<=dh+'1';
ELSE
dl<=dl+'1';
END IF;
END IF;
END IF;
END IF;
END PROCESS P10;
P11:PROCESS(scanclk) --- 动态扫描时钟
BEGIN
IF rising_edge(scanclk)THEN
IF dispcnt="111"THEN
dispcnt<="000";
ELSE
dispcnt<=dispcnt+'1';
END IF;
END IF;
END PROCESS P11;
P12:PROCESS(dispcnt,clock) ---选择对应位BCD码
BEGIN
IF ( clock='1') THEN
IF dispcnt="000"THEN
row<="00100000";numh<=shh;
ELSIF dispcnt="001"THEN
row<="00010000";numh<=shl;
ELSIF dispcnt="010"THEN
row<="00001000";num<=smh;
ELSIF dispcnt="011"THEN
row<="00000100";num<=sml;
ELSE
row<="00000000";num<="0000";
END IF;
ELSIF (sclock = '1')THEN
IF dispcnt="000"THEN
row<="00100000";numh<=ssh;
ELSIF dispcnt="001"THEN
row<="00010000";numh<=ssl;
--ELSIF dispcnt="010"THEN
--row<="00001000";num<=fsh;
ELSIF dispcnt="011"THEN
row<="00000100";num<=fs;
ELSIF dispcnt="100"THEN
row<="00000010";num<=msh;
ELSIF dispcnt="101"THEN
row<="00000001";num<=msl;
END IF;
ELSIF(data='1')THEN
IF dispcnt="000"THEN
row<="10000000";numh<=nhh;
ELSIF dispcnt="001"THEN
row<="01000000";numh<=nhl;
ELSIF dispcnt="010"THEN
row<="00100000";numh<=nlh;
ELSIF dispcnt="011"THEN
row<="00010000";numh<=nll;
ELSIF dispcnt="100"THEN
row<="00001000";num<=yh;
ELSIF dispcnt="101"THEN
row<="00000100";num<=yl;
ELSIF dispcnt="110"THEN
row<="00000010";num<=dh;
ELSIF dispcnt="111"THEN
row<="00000001";num<=dl;
END IF;
ELSE
IF dispcnt="000"THEN
row<="00100000";numh<=hh;
ELSIF dispcnt="001"THEN
row<="00010000";numh<=hl;
ELSIF dispcnt="010"THEN
row<="00001000";num<=mh;
ELSIF dispcnt="011"THEN
row<="00000100";num<=ml;
ELSIF dispcnt="100"THEN
row<="00000010";num<=sh;
ELSIF dispcnt="101"THEN
row<="00000001";num<=sl;
END IF;
END IF;
END PROCESS P12;
WITH nhh SELECT --年译码
a<= 1 WHEN"0001", --1
2 WHEN"0010", --2
3 WHEN"0011", --3
4 WHEN"0100", --4
5 WHEN"0101", --5
6 WHEN"0110", --6
7 WHEN"0111", --7
8 WHEN"1000", --8
9 WHEN"1001", --9
0 WHEN OTHERS; --0
WITH nhl SELECT --年译码
b<= 1 WHEN"0001", --1
2 WHEN"0010", --2
3 WHEN"0011", --3
4 WHEN"0100", --4
5 WHEN"0101", --5
6 WHEN"0110", --6
7 WHEN"0111", --7
8 WHEN"1000", --8
9 WHEN"1001", --9
0 WHEN OTHERS; --0
WITH nlh SELECT --年译码
c<= 1 WHEN"0001", --1
2 WHEN"0010", --2
3 WHEN"0011", --3
4 WHEN"0100", --4
5 WHEN"0101", --5
6 WHEN"0110", --6
7 WHEN"0111", --7
8 WHEN"1000", --8
9 WHEN"1001", --9
0 WHEN OTHERS; --0
WITH nll SELECT --年译码
d<= 1 WHEN"0001", --1
2 WHEN"0010", --2
3 WHEN"0011", --3
4 WHEN"0100", --4
5 WHEN"0101", --5
6 WHEN"0110", --6
7 WHEN"0111", --7
8 WHEN"1000", --8
9 WHEN"1001", --9
0 WHEN OTHERS; --0
--dp,g,f,e,d,c,b,a
WITH num SELECT --SEG3--SEG6段7段译码器
led<="00000110"WHEN"0001", --1
"01011011"WHEN"0010", --2
"01001111"WHEN"0011", --3
"01100110"WHEN"0100", --4
"01101101"WHEN"0101", --5
"01111101"WHEN"0110", --6
"00000111"WHEN"0111", --7
"01111111"WHEN"1000", --8
"01101111"WHEN"1001", --9
"00111111"WHEN OTHERS; --0
WITH numh SELECT --SEG7--SEG10段7段译码器
leda<="00000110"WHEN"0001", --1
"01011011"WHEN"0010", --2
"01001111"WHEN"0011", --3
"01100110"WHEN"0100", --4
"01101101"WHEN"0101", --5
"01111101"WHEN"0110", --6
"00000111"WHEN"0111", --7
"01111111"WHEN"1000", --8
"01101111"WHEN"1001", --9
"00111111"WHEN OTHERS; --0
END behavioral; |
|