【补档_C51单片机】基于C51的蜂鸣器音乐盒工程源码解析(可播放《打上花火》)

项目地址:https://gitee.com/daycen/c51-music-box
通过Keil uVision3打开即可使用
以前做的一些小硬件,现补档至博客

1 功能及总体方案

1.1 功能描述

​ 一个可通过无源蜂鸣器播放任意预先编码好的歌曲的基于51单片机设计的音乐盒。

​ 最小系统部分:由STC89S52单片机X接口连接晶振电路,RESET连接复位电路所构成的满足最简单应用的单片机系统。

​ 无源蜂鸣器驱动电路:由一个1K的分压电阻与无源蜂鸣器串联组成,作为系统的发声源。

​ 软件模块:由计算得出的每个声调的频率数据数组、歌曲编码数组、延时函数、定时器中断函数以及主循环函数构成,用于改变无源蜂鸣器的发声声调。

1.2 系统组成及工作过程

系统组成框图如下:

image-20210531191232675

2 硬件设计

2.1 硬件电路总体设计

image-20210531191222654

​ 单片机最小系统包括单片机、时钟电路、复位电路与5V电源构成,时钟电路提供的时钟信号给单片机提供了一个时间基准。复位电路则是让单片机回到原始状态重新执行程序。

实物图如下:

image-20210531191610728

image-20210531191623023

image-20210531191631723

image-20210531191641518

2.2 模块电路设计

​ 播放一段音乐需要的是两个元素,一个是音调,另一个是音符。首先要了解对应的音调,音调主要由声音的频率决定,同时也与声音强度有关。对一定强度的纯音,音调随频率的升降而升降;对一定频率的纯音、低频纯音的音调随声强增加而下降,高频纯音的音调却随强度增加而上升。另外,音符的频率有所不同。音符的发音主要靠不同的音频脉冲。利用单片机的内部定时器/计数器0,使其工作在模式1,定时中断,然后控制P2.0引脚的输出音乐。只要算出某一音频的周期(1/频率),然后将此周期除以2,即为半周期的时间,利用定时器计时这个半周期时间,每当计时到后就将输出脉冲的I/O反相,然后重复计时此半周期时间再对I/O反相,就可在I/O脚上得到此频率的脉冲。

​ 音乐盒的设计采用STC89C52作为主控芯片,利用单片机内部定时器产生特定的音符频率,控制节拍。

​ 音频模块选用无源蜂鸣器作为发声源,因为它制作成本低,声音频率范围宽,可高分贝的发出某些频率的超声波以及可以做出音符的效果。

PCB图:

image-20210531191724878

image-20210531191746945

3 软件设计

3.1 软件总体设计

软件的总流程图如下

image-20210531191349797

3.2 主程序设计

​ 主程序的设计思路就是将一首乐曲分成三个变量来控制,分别是曲调、所在音区、时长。而控制曲调的因素即频率又分成高八位和第八位两个表,每演奏一个曲调,就根据该曲调的三个变量来取值。此外,x变量用于定义休止符,控制歌曲的不演奏(间断)延时

3.3 各模块程序设计

①音调频率换算

​ 要想产生音频脉冲信号,需要算出某音频的周期(1/频率),然后将此周期除以2,即为半周期的时间。利用单片机定时器计时这个半周期的时间,每当计时到后就输出脉冲的I/O口反相,这样就在此I/O口上得到此脉冲的频率。

​ 例如,若要产生C大调中的Re(频率为587Hzs)的音频脉冲,其音频信号的脉冲周期T=1/587=1703.5775us,半周期时间为852us,因此总要令计时器计数=852us/1us=852,在每计数852时将I/O口反相,就可以得到Re这个音。按照这种方式可得到一张音符频率对应的半周期数值表,如下图

image-20210531191403281

②歌曲编码

​ 为了能够让程序按照乐谱调用相应的音调数据发声,于是这里我定义了一种编码方式对乐谱进行转换,每个音符的对应的编码包含四个数字:第一个数代表第几个音符(对应简谱中的1234567);第二个数代表第几个八度(音高);第三个数代表时长(以半拍为单位,在钢琴简谱中,音符的右边有一个点代表1.5倍时长);第四个数仅定义为1或0,1表示休止符,间断延时一个节拍而0则不进行任何操作(统一以1121编码代表休止符);

​ 在本程序中,我一共写入了两首歌,分别是《打上花火》和《aLIEz》,在第一首歌播放完毕后会间隔3个节拍的时间播放下一首。特别说明的是,由于编码参考的是钢琴简谱,故编码表中部分时长为3的音符调整为了2目的是让歌曲节奏快一些,且对我对双手谱的复弹做了一定删减以保证听感。

③休止符间断延时函数

​ 该函数由一组双重循环构成,当数组遍历到编码为1121的休止符时,程序会延时a个半拍,模拟出乐谱上休止符的功能。

image-20210531191421791

④主延时函数

与休止符函数类似,主延时函数也由一组双重循环构成,共延时t/2个节拍以控制蜂鸣器发声的时长。此处仅延时t/2个节拍是为了加快歌曲节奏。

image-20210531191430065

⑤定时器中断函数

该函数为T0中断函数。根据图3数值表找到的定时器的初始值被送入这里,无源蜂鸣器被驱动而发声

image-20210531191442411

⑥音乐播放函数

该函数启动T0, 由T0输出方波去发音,并传递参数给图5中的主延时函数,对节拍时长进行控制。

image-20210531191455882

⑦主函数

主程序流程图如下

image-20210531191515812

posted @ 2021-06-01 14:30  dayceng  阅读(3715)  评论(0编辑  收藏  举报