=COUNT11+1;FULLSPKS<='1';
ELSIFCOUNT11=TONE1THENCOUNT11:
=1;FULLSPKS<='0';
ENDIF;
ENDIF;
ENDPROCESS;
DELAYSPS:
PROCESS(FULLSPKS)--此进程对FULLSPKS进行2分频
VARIABLECOUNT2:
STD_LOGIC:
='0';
BEGIN
IFFULLSPKS'EVENTANDFULLSPKS='1'THENCOUNT2:
=NOTCOUNT2;
IFCOUNT2='1'THENSPKS<='1';
ELSESPKS<='0';
ENDIF;
ENDIF;
ENDPROCESS;
ENDBEHAVIORAL;
仿真图:
2.音调发生模块(tone)
音调发生模块的作用是产生音阶的分频预置值。
当13位发声控制输入信号中的某一位为高电平时,则对应某一音阶的数值将输出,该数值即为该音阶的分频预置值,分频预置值控制数控分频模块进行分频,由此得到每个音阶对应的频率,根据频率的不同,从而能通过喇叭听到不同的声音,实现音乐的播放。
模块程序:
LIBRARYIEEE;
USEIEEE.STD_LOGIC_1164.ALL;
USEIEEE.STD_LOGIC_ARITH.ALL;
USEIEEE.STD_LOGIC_UNSIGNED.ALL;
ENTITYTONEIS
PORT(INDEX:
INSTD_LOGIC_VECTOR(7DOWNTO0);--音符输入信号
CODE:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);--音符显示信号
HIGH:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);--高低音显示信号
TONE0:
OUTINTEGERRANGE0TO669);--音符的分频系数
ENDTONE;
ARCHITECTUREARTOFTONEIS
BEGIN
SEARCH:
PROCESS(INDEX)
BEGIN
CASEINDEXIS
WHEN"00000001"=>TONE0<=669;CODE<="01101101";HIGH<="00001000";
--分频系数,音符显示01101101,显示低音
WHEN"00000010"=>TONE0<=596;CODE<="01111101";HIGH<="00001000";
WHEN"00000011"=>TONE0<=531;CODE<="00000111";HIGH<="00001000";
WHEN"00000100"=>TONE0<=501;CODE<="00000110";HIGH<="00000000";
WHEN"00000101"=>TONE0<=447;CODE<="01011011";HIGH<="00000000";
WHEN"00000110"=>TONE0<=398;CODE<="01001111";HIGH<="00000000";
WHEN"00000111"=>TONE0<=376;CODE<="01100110";HIGH<="00000000";
WHEN"00001000"=>TONE0<=335;CODE<="01101101";HIGH<="00000000";
WHEN"00001001"=>TONE0<=299;CODE<="01111101";HIGH<="00000000";
WHEN"00001010"=>TONE0<=266;CODE<="00000111";HIGH<="00000000";
WHEN"00001011"=>TONE0<=251;CODE<="00000110";HIGH<="01000000";
WHEN"00001100"=>TONE0<=224;CODE<="01011011";HIGH<="01000000";
WHEN"00001101"=>TONE0<=200;CODE<="01001111";HIGH<="01000000";
WHEN"00001110"=>TONE0<=189;CODE<="01100110";HIGH<="01000000";
WHEN"00001111"=>TONE0<=168;CODE<="01101101";HIGH<="01000000";
WHEN"00010000"=>TONE0<=150;CODE<="01111101";HIGH<="01000000";
WHEN"00010001"=>TONE0<=134;CODE<="00000111";HIGH<="01000000";
WHEN"00010010"=>TONE0<=126;CODE<="00000110";HIGH<="00000001";
WHEN"00010011"=>TONE0<=113;CODE<="01011011";HIGH<="00000001";
WHEN"00010100"=>TONE0<=101;CODE<="01001111";HIGH<="00000001";
WHENOTHERS=>TONE0<=0;CODE<="01000000";HIGH<="01000000";
ENDCASE;
ENDPROCESS;
ENDART;
仿真图:
3.数码显示模块(xianshi)
由于要显示0—F之外的字母,必须采用动态扫描显示,与实验三内容相似,分两个进程,不同的数据对应不同的状态和位码。
模块程序:
LIBRARYIEEE;
USEIEEE.STD_LOGIC_1164.ALL;
USEIEEE.STD_LOGIC_UNSIGNED.ALL;
ENTITYXIANSHIIS
PORT(CLK:
INSTD_LOGIC;
CODE1:
INSTD_LOGIC_VECTOR(7DOWNTO0);
HIGH1:
INSTD_LOGIC_VECTOR(7DOWNTO0);
SIGN:
INSTD_LOGIC_VECTOR(7DOWNTO0);
DATA:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);
TIME:
BUFFERSTD_LOGIC_VECTOR(2DOWNTO0));
ENDENTITYXIANSHI;
ARCHITECTURESIMPLEOFXIANSHIIS
SIGNALA:
STD_LOGIC_VECTOR(1DOWNTO0):
="00";
BEGIN
PRO1:
PROCESS(CLK)
BEGIN
IFCLK'EVENTANDCLK='1'THENA<=A+1;ENDIF;
ENDPROCESSPRO1;
PRO2:
PROCESS(A)
BEGIN
CASEAIS
WHEN"00"=>TIME<="001";DATA<=CODE1;
WHEN"01"=>TIME<="010";DATA<=HIGH1;
WHEN"10"=>TIME<="100";DATA<=SIGN;
WHENOTHERS=>NULL;
ENDCASE;
ENDPROCESSPRO2;
ENDARCHITECTURESIMPLE;
仿真图:
4.乐曲演奏模块(auto)
乐曲演奏模块的作用是产生13位发生控制输入信号并存储。
当进行回放时时,由存储在数组中的8位二进制数作为发声控制输入,从而回放乐曲。
同时还加入了扩展内容。
模块程序:
LIBRARYIEEE;
USEIEEE.STD_LOGIC_1164.ALL;
USEIEEE.STD_LOGIC_ARITH.ALL;
USEIEEE.STD_LOGIC_UNSIGNED.ALL;
ENTITYAUTOIS
PORT(CLK:
INSTD_LOGIC;--系统时钟信号
AUTO:
INSTD_LOGIC;--回放
BIANYIN:
INSTD_LOGIC;
BIANSU:
INSTD_LOGIC;
HAND:
INSTD_LOGIC;--键盘输入
WRITE:
INSTD_LOGIC;
INDEX0:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);--音符信号输出
D:
INSTD_LOGIC_VECTOR(7DOWNTO0);
SIGN0:
OUTSTD_LOGIC_VECTOR(7DOWNTO0));--功能信号输出
ENDAUTO;
ARCHITECTUREBEHAVIORALOFAUTOIS
SUBTYPEWORDIS
STD_LOGIC_VECTOR(7DOWNTO0);
TYPEMEMORYISARRAY(0TO49)OFWORD;
SIGNALSRAM:
MEMORY;
SIGNALSIGN1:
STD_LOGIC_VECTOR(7DOWNTO0);
SIGNALNT:
INTEGERRANGE0TO50:
=0;
SIGNALSONG:
STD_LOGIC_VECTOR(7DOWNTO0);
BEGIN
COM2:
PROCESS(CLK)--手动模式,变高音
BEGIN
IFHAND='1'ANDBIANYIN='1'THENINDEX0<=D+7;SIGN0<=SIGN1;ELSIFHAND='1'ANDBIANYIN='0'THENINDEX0<=D;SIGN0<=SIGN1;
ELSIFAUTO='1'THENSIGN0<="01110011";INDEX0<=SONG;
ELSESIGN0<="00000000";INDEX0<="00000000";
ENDIF;
ENDPROCESS;
COM3:
PROCESS(WRITE)--闪烁,0.5S
VARIABLECOUNT:
INTEGERRANGE0TO40;
BEGIN
IF(WRITE'EVENTANDWRITE='1')THEN
IF(COUNT=20)THEN
COUNT:
=COUNT+1;
SIGN1<="01110111";
ELSIF(COUNT=40)THEN
COUNT:
=0;
SIGN1<="00000000";
ELSECOUNT:
=COUNT+1;
ENDIF;
ENDIF;
ENDPROCESS;
COM4:
PROCESS(WRITE)--存储和扩展
VARIABLEADR:
STD_LOGIC_VECTOR(7DOWNTO0):
="00000000";
VARIABLEADR_IN:
INTEGERRANGE0TO49;
VARIABLECOUNT:
INTEGERRANGE0TO4;
BEGIN
IF(WRITE'EVENTANDWRITE='1')THENCOUNT:
=COUNT+1;
IF(NT<50)THENADR_IN:
=CONV_INTEGER(ADR);
IF(HAND='1')THENSRAM(ADR_IN)<=D;NT<=NT+1;ADR:
=CONV_STD_LOGIC_VECTOR(CONV_INTEGER(ADR)+1,8);
ELSIF(AUTO='1'ANDBIANYIN='1'ANDBIANSU='1'ANDCOUNT=4)THENSONG<=SRAM(ADR_IN)+7;NT<=NT+1;ADR:
=CONV_STD_LOGIC_VECTOR(CONV_INTEGER(ADR)+1,8);COUNT:
=0;
ELSIF(AUTO='1'ANDBIANYIN='0'ANDBIANSU='1'ANDCOUNT=4)THENSONG<=SRAM(ADR_IN);NT<=NT+1;ADR:
=CONV_STD_LOGIC_VECTOR(CONV_INTEGER(ADR)+1,8);COUNT:
=0;
ELSIF(AUTO='1'ANDBIANYIN='1'ANDBIANSU='0')THENSONG<=SRAM(ADR_IN)+7;NT<=NT+1;ADR:
=CONV_STD_LOGIC_VECTOR(CONV_INTEGER(ADR)+1,8);
ELSIF(AUTO='1'ANDBIANYIN='0'ANDBIANSU='0')THENSONG<=SRAM(ADR_IN);NT<=NT+1;ADR:
=CONV_STD_LOGIC_VECTOR(CONV_INTEGER(ADR)+1,8);
ENDIF;
ELSIF(AUTO='1')THENADR:
="00000000";NT<=0;
ENDIF;
ENDIF;
ENDPROCESS;
ENDBEHAVIORAL;
仿真图:
五、顶层模块设计
该dianziqin模块是整个电子琴设计的核心,也是vhdl程序的主程序,前面4个源程序都是作为子程序分别实现电子琴的某一功能,而dianziqin模块则通过调用子程序最终实现乐曲演奏的目的,奏出美妙的乐曲。
顶层模块程序:
LIBRARYIEEE;
USEIEEE.STD_LOGIC_1164.ALL;
USEIEEE.STD_LOGIC_ARITH.ALL;
USEIEEE.STD_LOGIC_UNSIGNED.ALL;
ENTITYDIANZIQINIS
PORT(CLOCK:
INSTD_LOGIC;--系统时钟信号
BIANSU:
INSTD_LOGIC_VECTOR(3DOWNTO0);
HANDTOAUTO:
INSTD_LOGIC;--回放信号
HANDTOAUTO1:
INSTD_LOGIC;--手动信号
DATA:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);
TIME:
BUFFERSTD_LOGIC_VECTOR(2DOWNTO0);
INDEX1:
INSTD_LOGIC_VECTOR(7DOWNTO0);--键盘输入信号
SPKOUT:
OUTSTD_LOGIC);--音频信号
END;
ARCHITECTUREARTOFDIANZIQINIS
COMPONENTXIANSHI
PORT(CLK:
INSTD_LOGIC;
CODE1:
INSTD_LOGIC_VECTOR(7DOWNTO0);
HIGH1:
INSTD_LOGIC_VECTOR(7DOWNTO0);
SIGN:
INSTD_LOGIC_VECTOR(7DOWNTO0);
DATA:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);
TIME:
BUFFERSTD_LOGIC_VECTOR(2DOWNTO0));
ENDCOMPONENT;
COMPONENTAUTO--引用AUTO元件
PORT(CLK:
INSTD_LOGIC;--系统时钟信号
BIANSU:
INSTD_LOGIC_VECTOR(3DOWNTO0);
AUTO:
INSTD_LOGIC;--回放
HAND:
INSTD_LOGIC;--键盘输入
INDEX0:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);--音符信号输出
D:
INSTD_LOGIC_VECTOR(7DOWNTO0);
SIGN0:
OUTSTD_LOGIC_VECTOR(7DOWNTO0));--功能信号输出
ENDCOMPONENT;
COMPONENTTONE--引用TONE元件
PORT(INDEX:
INSTD_LOGIC_VECTOR(7DOWNTO0);
CODE:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);
HIGH:
OUTSTD_LOGIC_VECTOR(7DOWNTO0);
TONE0:
OUTINTEGERRANGE0TO669);
ENDCOMPONENT;
COMPONENTFENPIN--引用FENPIN元件
PORT(CLK1:
INSTD_LOGIC;
TONE1:
ININTEGERRANGE0TO669;
SPKS:
OUTSTD_LOGIC);
ENDCOMPONENT;
SIGNALTONE2:
INTEGERRANGE0TO669;--定义主程序音调频率信号
SIGNALINDX:
STD_LOGIC_VECTOR(7DOWNTO0);--定义8位的音符信号
SIGNALDATA1:
STD_LOGIC_VECTOR(7DOWNTO0);
SIGNA