乐曲演奏硬件电路设计报告Word文档格式.docx
《乐曲演奏硬件电路设计报告Word文档格式.docx》由会员分享,可在线阅读,更多相关《乐曲演奏硬件电路设计报告Word文档格式.docx(19页珍藏版)》请在冰豆网上搜索。
音频的持续时间需根据乐曲的速度及每个音符的节拍数来确定,模块ToneTaba的功能首先是为Speakera提供决定所发音符的分频预置数,而次数在Speakera输入口停留的时间即为此音符的节拍值。
模块ToneTaba是乐曲简谱码对应的预置数,共13个,每一音符的停留时间由音乐节拍和音调发生器模块NoteTabs的clk的输入频率决定,在此喂4Hz。
这13个值的输出由对应于ToneTaba的4位输入值Index[3..0]确定,而Index[3..0]最多有16种可选值。
输向ToneTaba中的Index[3..0]的值ToneIndex[3..0]的输出值与持续时间由模块NoteTabs决定。
在NoteTabs中设置了一个8位二进制计数器计数最大值为138),作为音符数据ROM的地址发生器。
这个计数器的技术频率选为4Hz,即每一个计数值的停留时间为0.25秒,恰为当全音符设为1秒时,四四拍的4分音符持续时间。
顶层电路VHDL程序设计
LIBRARYIEEE;
--硬件演奏电路顶层设计
USEIEEE.STD_LOGIC_1164.ALL;
ENTITYSongerIS
PORT(CLK12MHZ:
INSTD_LOGIC;
--音调频率信号
CLK8HZ:
--节拍频率用于控制音长(节拍)的时钟频率;
CODE1:
OUTSTD_LOGIC_VECTOR(3DOWNTO0);
--简谱码输出显示
HIGH1:
OUTSTD_LOGIC;
--高8度指示
SPKOUT:
OUTSTD_LOGIC);
--声音输出
END;
ARCHITECTUREoneOFSongerIS
COMPONENTNoteTabs--元件u1例换化
PORT(clk:
ToneIndex:
OUTSTD_LOGIC_VECTOR(3DOWNTO0));
ENDCOMPONENT;
COMPONENTToneTaba--元件u2例换化
PORT(Index:
INSTD_LOGIC_VECTOR(3DOWNTO0);
CODE:
OUTSTD_LOGIC_VECTOR(3DOWNTO0);
HIGH:
Tone:
OUTSTD_LOGIC_VECTOR(10DOWNTO0));
COMPONENTSpeakera--元件u3例换化
INSTD_LOGIC_VECTOR(10DOWNTO0);
SpkS:
SIGNALTone:
STD_LOGIC_VECTOR(10DOWNTO0);
SIGNALToneIndex:
STD_LOGIC_VECTOR(3DOWNTO0);
BEGIN
u1:
NoteTabsPORTMAP(clk=>
CLK8HZ,ToneIndex=>
ToneIndex);
--参数传递映射语句
u2:
ToneTabaPORTMAP(Index=>
ToneIndex,Tone=>
Tone,CODE=>
CODE1,HIGH=>
HIGH1);
u3:
SpeakeraPORTMAP(clk=>
CLK12MHZ,Tone=>
Tone,SpkS=>
SPKOUT);
单元模块程序设计
共分为music模块、地址发生器模块、分频预置数模块、十六进制模块、数控分频模块这五个模块。
music模块存放乐曲中的音符数据,地址发生器模块作为music模块中所定制的音符数据ROM的地址发生器,分频预置数模块提供分频预置数即给数控分频模块提供计数初值,十六进制模块对12MHz的时钟脉冲进行16分频,得到750KHz的频率,给数控分频模块提供时钟脉冲。
数控分频模块根据分频预置数输出各个音符所对应的频率。
音符的频率由数控分频模块获得,这是一个数控分频电路。
它是由一个初值可变的加法计数器构成。
该计数器的模为2047,当计数器记满时,计数器产生一个溢出信号FULL,此溢出信号就是用作发音的频率信号。
在计数器的输入端给定不同的初值,而此预置数就是表1中的计数初值,就可得到不同音符的发音频率信号。
它计满时所需要的计数初值可由下式来表示。
计数初值(Tone)=2047-分频系数,而分频系数又可有下式来求:
分频系数=基准频率/音符的发生频率。
低音时Tone值小,分频系数大,溢出信号周期长,扬声器发出的声音低,Tone随音乐的乐谱变化大,自动控制分频比,实现了数控分频,发生信号的频率与音调Tone成正比。
这就是利用数控分频器自动演奏音乐的原理。
时钟(Clk)端输入的是在十六进制模块里对12MHz的信号进行16分频得到的750KHz,750KHz的信号根据分频预置数模块中所提供的计数初值,分别得出相应音符频率的两倍值。
此时从数控分频器中出来的输出信号是脉宽极窄的脉冲式信号,为了有利于驱动扬声器,需另加一个D触发器以均衡其占空比,这时的频率就变为原来的1/2,刚好就是相应音符的频率。
数控分频模块中对Clk输入信号的分频比由11位预置数tone[10..0]决定。
Fout的输出频率将决定每一个音符的音调,这样,分频计数器的预置值tone[10..0]与Fout的输出频率就有了对应关系。
例如在分频预置数模块中若取tone[10..0]=1036,将发出音符为“3”音的信号频率。
音符的频率由数控分频模块VHDL程序:
--音乐符数控分频电路模块
USEIEEE.STD_LOGIC_UNSIGNED.ALL;
ENTITYSpeakeraIS
PORT(clk:
--音调频率信号12MHZ
--音乐符对应分频11位
ARCHITECTUREoneOFSpeakeraIS
SIGNALPreCLK,FullSpkS:
STD_LOGIC;
DivideCLK:
PROCESS(clk)
VARIABLECount4:
STD_LOGIC_VECTOR(3DOWNTO0);
BEGIN
PreCLK<
='
0'
;
--将CLK进行16分频,PreCLK为CLK的16分频
IFCount4>
11THENPreCLK<
1'
Count4:
="
0000"
ELSIFclk'
EVENTANDclk='
THENCount4:
=Count4+1;
ENDIF;
ENDPROCESS;
GenSpkS:
PROCESS(PreCLK,Tone)--11位可预置计数器
VARIABLECount11:
IFPreCLK'
EVENTANDPreCLK='
THEN
IFCount11=16#7FF#THENCount11:
=Tone;
FullSpkS<
ELSECount11:
=Count11+1;
DelaySpkS:
PROCESS(FullSpkS)--将输出再2分频,展宽脉冲,使扬声器有足够功率发音
VARIABLECount2:
IFFullSpkS'
EVENTANDFullSpkS='
THENCount2:
=NOTCount2;
IFCount2='
THENSpkS<
ELSESpkS<
音乐谱对应分频预制数查表电路VHDL程序设计
音乐谱分频预置数模块是乐曲简谱码对应的分频预置数查表电路。
它提供了每个音符所对应的分频预置数,即给数控分频模块提供计数初值,这里以“梁祝”乐曲为例,列出了在这个乐曲中所用到的13个音符的分频预置数。
在这个模块的VHDL逻辑描述中设置了四四拍乐曲中全部音符所对应的分频预置数,共13个,每一音符的停留时间由音乐节拍和地址发生器模块的时钟(Clk)的输入频率决定,在此为4Hz。
这13个值的输出由程序[3]的4位输入值index[3..0]确定。
输向程序[4]中index[3..0]的值又由地址发生器模块的输出toneindex[3..0]的输出值和持续时间决定。
模块的功能是输出各个音符所对应的分频预置数,即当index是“0000”,tone输出为2047,即休止符的分频预置数;
当index是“0101”时,tone输出为1197即低音5的分频预置数;
当index是“1111”时,tone输出为1728即高音1的分频预置数等等其它状态时,tone分别输出相应音符的分频预置数。
分频预置数模块的VHDL设计程序:
--音乐谱对应分频预制数查表电路模块
ENTITYToneTabaIS
PORT(Index:
--4位预制数查表
--音乐高8度指示
ARCHITECTUREoneOFToneTabaIS
Search:
PROCESS(Index)
CASEIndexIS--译码电路,查表方式,控制音调的预置数13组频率
WHEN"
=>
Tone<
="
11111111111"
;
CODE<
HIGH<
='
--2047
0001"
01100000101"
--773;
0010"
01110010000"
--912;
0011"
10000001100"
--1036;
0101"
10010101101"
--1197;
0110"
10100001010"
--1290;
0111"
10101011100"
--1372;
1000"
10110000010"
--1410;
1001"
10111001000"
--1480;
1010"
11000000110"
--1542;
1100"
11001010110"
--1622;
1101"
11010000100"
--1668;
1111"
11011000000"
--1728;
WHENOTHERS=>
NULL;
ENDCASE;
音乐节拍和音调发生器模块VHDL程序设计
--音乐节拍和音调发生器模块
ENTITYNoteTabsIS
--音乐节拍时钟4HZ
ARCHITECTUREoneOFNoteTabsIS
COMPONENTmusic--音符数据ROM1
PORT(address:
INSTD_LOGIC_VECTOR(7DOWNTO0);
inclock:
INSTD_LOGIC;
q:
OUTSTD_LOGIC_VECTOR(3DOWNTO0));
SIGNALCounter:
STD_LOGIC_VECTOR(7DOWNTO0);
--8位二进制计数器
CNT8:
PROCESS(clk,Counter,sel,rst)
IF((clk'
)and(Counter=256orrst='
))thenCounter<
00000000"
Counter<
=Counter+1;
endif;
IF((clk'
)and(sel='
))THENCounter<
10010000"
MUSICPORTMAP(address=>
Counter,q=>
ToneIndex,inclock=>
clk);
ROM中的音符数据模块(music)程序为:
WIDTH=4;
--“梁祝“乐曲演奏数据
DEPTH=256;
ADDRESS_RADIX=DEC;
DATA_RADIX=DEC;
CONTENTBEGIN
00:
3;
01:
02:
03:
04:
5;
05:
06:
07:
6;
08:
8;
09:
10:
11:
9;
12:
13:
14:
15:
16:
12;
17:
18:
19:
15;
20:
13;
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
0;
32:
33:
34:
35:
10;
36:
7;
37:
38:
39:
40:
41:
42:
43:
44:
45:
46:
47:
48:
49:
50:
51:
52:
53:
54:
55:
56:
57:
58:
59:
60:
61:
62:
63:
64:
65:
66:
67:
68:
69:
70:
71:
72:
73:
74:
75:
76:
77:
78:
79:
80:
81:
82:
83:
84:
85:
86:
87:
88:
89:
90:
91:
92:
93:
94:
95:
96:
97:
98:
99:
100:
101:
102:
103:
104:
105:
106:
107:
108:
109:
110:
111:
112:
113:
114:
115:
4;
116:
117:
118:
119:
120:
121:
122:
123:
124:
125:
126:
127:
128:
129:
130:
131:
132:
133:
134:
135:
136:
137:
138:
End;
其中WIDTH=4,表示数据输出为宽为4;
DEPTH=256,表示共有256个4位数据点;
ADDRESS-RADIX=DEC,表示地址信号用十进制;
DATA-RADIX=DEC,表示输出数据是十进制数。
形成ROM中的配置数据(初始化数据)文件的方法是:
在QuartusII中编辑.mif文件。
首先在File菜单下的New菜单上选择TextEditorFile命令,进入文本编辑器,然后输入以上格式的数据文件。
文件中的关键词WIDTH设置ROM的数据宽度;
DEPTH设置ROM数据的深度,即4位数据的数量,文件中设置的256等效于8位地址线宽度;
ADDRESS-RADIX=DEC和DATA-RADIX=DEC表示设置地址和数据的表达式格式都是十进制;
地址/数据表以CONTENTBEGIN开始,以END结束;
其中的地址/数据表达方式是冒号左边写ROM地址值,冒号右边写对应此地址放置的十进制数据,如24:
9,表示24为地址,9为该地址中的数据。
这样每读到一个地址,即可输出其相应的数据。
文件编辑好后,保存时取文件名为“songer.mif”。
定制音符数据的ROM文件
定制的基本步骤如下:
(1)
进入QuartusII,选菜单TOOL->
megawizardplug-inmanager,选择“creatanew…”,然后按“next”键,选择LPM-ROM;
最后在browse下的栏中