集成电路技术分享

 找回密码
 我要注册

QQ登录

只需一步,快速开始

搜索
查看: 2339|回复: 0

我写的PS2键盘控制电子琴(VHDL)

[复制链接]
izhou0517 发表于 2011-1-30 23:35:22 | 显示全部楼层 |阅读模式
本人新手,还望高手多多指点。
共分为DIV1、DIV2分频模块,PS2键盘控制模块,music发音模块,tone音符分频模块,spk发声模块。
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity Div1 is
    PORT(clk_50mhz: IN STD_LOGIC;            --输入时钟为50MHZ;
     c0: OUT STD_LOGIC;
c1: OUT STD_LOGIC);      
END Div1;

architecture art of Div1 is

begin
D1: PROCESS(clk_50mhz)          --工作进程开始,将50MHZ时钟50分频,=1MHZ;
  VARIABLE count6:INTEGER RANGE 0 TO 50;   
BEGIN
  IF(clk_50mhz 'EVENT AND clk_50mhz ='1')THEN   
     count6:=count6+1;                  
  IF count6=25 THEN              
     c0 <='1';
   ELSIF count6=50 THEN
     c0 <='0'; count6:=0;
END IF;
END IF;
END PROCESS;
D2: PROCESS(clk_50mhz)                --将50MHZ时钟100分频,=0.5MHZ;
VARIABLE count7: INTEGER RANGE 0 TO 100;
BEGIN
IF(clk_50mhz 'EVENT AND clk_50mhz ='1')THEN   
     count7:=count7+1;                  
  IF count7=50 THEN              
     c1<='1';
   ELSIF count7=100 THEN
     c1 <='0'; count7:=0;
END IF;
END IF;
END PROCESS;
END art;

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity Div2 is
    PORT(clk4: IN STD_LOGIC;            --输入时钟为1MHZ;
     c2: OUT STD_LOGIC;           --输出100khz;
          c3ut std_logic);       --输出时钟为4HZ;
END Div2;
ARCHITECTURE art OF Div2 IS
begin
D1: PROCESS(clk4)          --工作进程开始,将1MHZ时钟10分频;
  VARIABLE count8:INTEGER RANGE 0 TO 10;   
BEGIN
  IF(clk4 'EVENT AND clk4 ='1')THEN   
     count8:=count8+1;                  
  IF count8=5 THEN              
     c2 <='1';
   ELSIF count8=10 THEN
     c2 <='0'; count8:=0;
END IF;
END IF;
END PROCESS;
D2: PROCESS(clk4)                --250000分频;
VARIABLE count9: INTEGER RANGE 0 TO 250000;
BEGIN
IF(clk4 'EVENT AND clk4 ='1')THEN   
     count9:=count9+1;                  
  IF count9=125000 THEN              
     c3<='1';
   ELSIF count9=250000 THEN
     c3 <='0'; count9:=0;
END IF;
END IF;
END PROCESS;
END art;

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity ps2 is
    Port ( sysclk: in std_logic;                              
       ps2clk: in std_logic;                              
       ps2data: in std_logic;                             
       reset: in std_logic;
       result: out std_logic_vector(7 downto 0));
end ps2;

architecture art of ps2 is
signal ps2clk_r : std_logic_vector(2 downto 0);            
signal ps2clkfall : std_logic;                           
signal q : std_logic_vector(11 downto 0);                  
signal ps2serialdata : std_logic_vector(10 downto 0) ;     
begin       
process(sysclk,reset)
begin
if reset='0' then
  ps2clk_r <= "000";
elsif rising_edge(sysclk) then
     ps2clk_r(2) <= ps2clk_r(1);
  ps2clk_r(1) <= ps2clk_r(0);
  ps2clk_r(0) <= ps2clk;
end if;
end process;
ps2clkfall<='1' when ps2clk_r="110" else '0';
process(sysclk)
begin
if rising_edge(sysclk) then                       
  if reset='0' then q <= (others =>'0');         
   elsif ps2clkfall='1' then               
    if q(0)='0' then                       
     q <= ps2data & "01111111111";      
    else
     q <= ps2data & q(11 downto 1);
            end if;
        end if;
    end if;
end process;
process(q)
begin
if q(0) = '0' then
  ps2serialdata <= q(11 downto 1);
  result <= not ps2serialdata(8 downto 1);
else
  result <="11111111";
end if;
end process;
end art;

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity music is
    PORT(clk2:   IN STD_LOGIC;                       --4HZ时钟信号
          index1: IN STD_LOGIC_VECTOR(7 DOWNTO 0);   --键盘输入信号
       index2: OUT STD_LOGIC_VECTOR(7 DOWNTO 0));  --音符信号输出
END music;
ARCHITECTURE art OF music IS
SIGNAL count3:INTEGER RANGE 0 TO 31;  --定义信号计数器,有32个元素

BEGIN

M1ROCESS(count3,clk2,index1)               --music工作进程开始
BEGIN
  IF(clk2 'EVENT AND clk2 ='1')THEN       --时钟信号2为1
    IF(count3=31)THEN                   --计数器值为31
      count3<=0;                        --计数器清0
ELSE
      count3<=count3+1;
END IF;
END IF;
END PROCESS;
M2ROCESS(count3,index1)--除去了敏感信号auto1
BEGIN
IF index1="01001101" THEN                        按下P键生效
CASE count3 IS          --由计数器从0到31的取??断音符信号?制? WHEN 0=>index2<="00000011";    --3
WHEN 1=> index2<="00000011";    --3
WHEN 2=> index2<="00000011";    --3
WHEN 3=> index2<="00000011";    --3
WHEN 4=> index2<="00000101";    --5
WHEN 5=> index2<="00000101";    --5
WHEN 6=> index2<="00000101";    --5
WHEN 7=> index2<="00000110";    --6
WHEN 8=> index2<="00001000";    --8
WHEN 9=> index2<="00001000";    --8
WHEN 10=> index2<="00001000";   --8
WHEN 11=> index2<="00000011";   --3
WHEN 12=> index2<="00000010";   --2
WHEN 13=> index2<="00000010";   --2
WHEN 14=> index2<="00000001";   --1
WHEN 15=> index2<="00000001";   --1
WHEN 16=> index2<="00000101";   --5
WHEN 17=> index2<="00000101";   --5
WHEN 18=> index2<="00000100";   --4
WHEN 19=> index2<="00000100";   --4
WHEN 20=> index2<="00000100";   --4
WHEN 21=> index2<="00000011";   --3
WHEN 22=> index2<="00000010";   --2
WHEN 23=> index2<="00000010";   --2
WHEN 24=> index2<="00000101";   --5
WHEN 25=> index2<="00000101";   --5
WHEN 26=> index2<="00000100";   --4
WHEN 27=> index2<="00000100";   --4
WHEN 28=> index2<="00000011";   --3
WHEN 29=> index2<="00000011";   --3
WHEN 30=> index2<="00000010";   --2
WHEN 31=> index2<="00000010";   --2
WHEN OTHERS=>NULL;
END CASE;
ELSE --index2<=index1;
case index1 is
when"00010101"=>index2<="00000001";--q
when"00011101"=>index2<="00000010";--w
when"00100100"=>index2<="00000011";--e
when"00101101"=>index2<="00000100";--r
when"00101100"=>index2<="00000101";--t
when"00110101"=>index2<="00000110";--y
when"00111100"=>index2<="00000111";--u

when"00011100"=>index2<="00001000";--a
when"00011011"=>index2<="00001001";--s
when"00100011"=>index2<="00001010";--d
when"00101011"=>index2<="00001011";--f
when"00110100"=>index2<="00001100";--g
when"00110011"=>index2<="00001101";--h
when"00111011"=>index2<="00001110";--j

when"00011010"=>index2<="00001111";--z
when"00100010"=>index2<="00010000";--x
when"00100001"=>index2<="00010001";--c
when"00101010"=>index2<="00010010";--v
when"00110010"=>index2<="00010011";--b
when"00110001"=>index2<="00010100";--n
when"00111010"=>index2<="00010101";--m
when         others=>index2<="11111111";
end case;                 
END IF;
END PROCESS;  
END art;

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity tone is
    Port (index3: IN STD_LOGIC_VECTOR(7 DOWNTO 0);   --音符输入信号
     code1:  OUT STD_LOGIC_VECTOR(6 DOWNTO 0);  --音符显示信号
     high1:  OUT STD_LOGIC_VECTOR(2 DOWNTO 0);   --高低音显示信号
     tone1:  OUT INTEGER RANGE 0 TO 2047);       --音符的分频系数
end tone;

architecture art of tone is

begin
T1:process(index3)
begin
case index3 is
when"00000001"=> tone1<=1191; code1<="1001111"; high1<="001";
WHEN"00000010"=> tone1<=1702; code1<="0010010"; high1<="001";
WHEN"00000011"=> tone1<=1517; code1<="0000110"; high1<="001";
WHEN"00000100"=> tone1<=1432; code1<="1001100"; high1<="001";
WHEN"00000101"=> tone1<=1276; code1<="0100100"; high1<="001";
WHEN"00000110"=> tone1<=1136; code1<="0100000"; high1<="001";
WHEN"00000111"=> tone1<=1012;  code1<="0001111"; high1<="001";

WHEN"00001000"=> tone1<=955;  code1<="1001111"; high1<="010";
WHEN"00001001"=> tone1<=851;  code1<="0010010"; high1<="010";  
WHEN"00001010"=> tone1<=758;  code1<="0000110"; high1<="010";
WHEN"00001011"=> tone1<=716;  code1<="1001100"; high1<="010";
WHEN"00001100"=> tone1<=638;  code1<="0100100"; high1<="010";
WHEN"00001101"=> tone1<=568;  code1<="0100000"; high1<="010";
WHEN"00001110"=> tone1<=506;  code1<="0001111"; high1<="010";

WHEN"00001111"=> tone1<=478;  code1<="1001111"; high1<="100";
WHEN"00010000"=> tone1<=426;  code1<="0010010"; high1<="100";
WHEN"00010001"=> tone1<=379;  code1<="0000110"; high1<="100";
WHEN"00010010"=> tone1<=358;  code1<="1001100"; high1<="100";
WHEN"00010011"=> tone1<=319;  code1<="0100100"; high1<="100";
WHEN"00010100"=> tone1<=284;  code1<="0100000"; high1<="100";
WHEN"00010101"=> tone1<=253;  code1<="0001111"; high1<="100";

WHEN  OTHERS  => tone1<=2047; code1<="0000000"; high1<="000";
END CASE;
END PROCESS;
END art;


library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity speaker is
    PORT(clk3:  IN STD_LOGIC;               --0.5MHZ时钟信号;
     tone2: IN INTEGER RANGE 0 TO 2047;  --音符分频系数
     spk: OUT STD_LOGIC);               --驱动扬声器的音频信号
END speaker;                       
ARCHITECTURE art OF speaker IS
    SIGNAL fullclk: STD_LOGIC;
BEGIN
S1ROCESS(clk3,tone2)
VARIABLE count4:INTEGER RANGE 0 TO 2047; --定义变量频率计数器2047Hz
BEGIN
  IF(clk3'EVENT AND clk3='1')THEN        --clk3脉冲上升沿触发
    IF count4<tone2 THEN                    --若计数器11值小于音符信1
        count4:=count4+1;fullclk<='1';    --计数器加1,音频信号为1
   ELSE
       count4:=0;fullclk<='0';
END IF;
END IF;
END PROCESS;
S2ROCESS(fullclk)                           --音频信号输出进程开始
VARIABLE count5:STD_LOGIC:='0';             --定义变量计数器2,初值0
BEGIN
IF(fullclk'EVENT AND fullclk='1')THEN    --音频信号输出上升沿有效时
count5:=NOT count5;
IF count5='1'THEN
spk<='1';
ELSE
spk<='0';
END IF;
END IF;
END PROCESS;
END art;
您需要登录后才可以回帖 登录 | 我要注册

本版积分规则

关闭

站长推荐上一条 /1 下一条

QQ|小黑屋|手机版|Archiver|fpga论坛|fpga设计论坛 ( 京ICP备20003123号-1 )

GMT+8, 2024-12-29 00:18 , Processed in 0.078860 second(s), 20 queries .

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表