通过开发板的蜂鸣器播放歌曲在实际产品设计中可能用处不大,但是在一些开发板中非常常见,其实看似简单的功能涉及到的知识点还比较多。
本文对蜂鸣器播放音乐涉及到的知识点进行重点说明。
一:硬件电路
如上图所示,是非常常用的三极管驱动蜂鸣器的电路:
当P12输出低电平时,三极管Q1不导通,此时无电流流过蜂鸣器,蜂鸣器不发声。当P12输出高电平时,Q1导通,此时有电流流过蜂鸣器,蜂鸣器发声。
R26是限流电阻,保证流过蜂鸣器的电流不会超过允许值。
关于三极管驱动电路的原理讲解及更多的优化设计,可在本公众号内搜索相关文章自行学习。
注意:想要进行音乐播放需要使用无源蜂鸣器;关于无源蜂鸣器与有源蜂鸣器的区别,可在本公众号内搜索蜂鸣器相关的文章进行学习。
二:有源蜂鸣器与无源蜂鸣器
注意:这里的“源”不是指电源,而是指震荡源。也就是说,有源蜂鸣器内部带震荡源,所以只要一通电就会叫; 而无源内部不带震荡源,所以如果用直流信号无法令其鸣叫。必须用 2K-5K 的方波去驱动它。
有源蜂鸣器往往比无源的贵,就是因为里面多个震荡电路。
无源蜂鸣器的优点是:
便宜
声音频率可控,可以做出“多来米发索拉西”的效果
在一些特例中,可以和 LED 复用一个控制口
有源蜂鸣器的优点是:
程序控制方便。
三:蜂鸣器发声原理
单片机驱动无源蜂鸣器的方式有两种:一种是 PWM 输出口直接驱动,另一种是利用 I/O 定时翻转电平产生驱动波形对蜂鸣器进行驱动。
PWM 输出口直接驱动是利用PWM输出口本身可以输出一定的方波来直接驱动蜂鸣器。在单片机的软件设置中有几个系统寄存器是用来设置 PWM 口的输出的,可以设置占空比、周期等等,通过设置这些寄存器产生符合蜂鸣器要求的频率的波形之后,只要打开 PWM 输出, PWM 输出口就能输出该频率的方波,这个时候利用这个波形就可以驱动蜂鸣器了。
比如频率为 2000Hz 的蜂鸣器的驱动,可以知道周期为 500μs,这样只需要把 PWM 的周期设置为 500μs,占空比电平设置为 250μs,就能产生一个频率为 2000Hz 的方波,通过这个方波再利用三极管就可以去驱动这个蜂鸣器了。
而利用 I/O 定时翻转电平来产生驱动波形的方式会比较麻烦一点,必须利用定时器来做定时,通过定时翻转电平产生符合蜂鸣器要求的频率的波形,这个波形就可以用来驱动蜂鸣器了。
比如为 2500Hz 的蜂鸣器的驱动,可以知道周期为 400μs,这样只需要驱动蜂鸣器的 I/O 口每 200μs 翻转一次电平就可以产生一个频率为 2500Hz,占空比为/2 的方波,再通过三极管放大就可以驱动这个蜂鸣器了。
其实两种驱动方式本质上都是给蜂鸣器一定频率的信号,蜂鸣器的发声频率等于驱动方波的频率。
下面贴出来蜂鸣器发声的相关函数。
// Buzzer初始化 void buzzerInit(void) { TR0 = 0; TF0 = 0; TMOD |= 0x01; // 设置新模式:16位定时模式 BUZZ = 1; ET0 = 1; EA = 1; } // Buzzer发出指定频率的声音 // uiFreq是发声频率,单位:Hz void buzzerSound(unsigned int uiFreq) { // 限定频率范围在20~20000Hz之间 if (uiFreq < 20) { buzzerQuiet(); return; } if (uiFreq > 20000) uiFreq = 20000; // 计算Timer0装载值 TL0_Load = LOW_BYTE(65536UL - CPUCLK / (uiFreq * 2)); TH0_Load = HIGH_BYTE(65536UL - CPUCLK / (uiFreq * 2)); // 启动Timer TL0 = 0xF0; TH0 = 0xFF; TR0 = 1; } // 蜂鸣器停止发声 void buzzerQuiet(void) { TR0 = 0; TF0 = 0; BUZZ = 1; }
四:蜂鸣器演奏乐曲
上图是《化蝶》的乐谱。
简谱是大众化的音乐记谱方式,比较容易理解和掌握。我们可以把一首乐谱(score)看成是由若干个基本的音符(note)单元组成。
一个音符由音名和时值组成。音名就是低音、中音、高音的 1234567(唱作 do re mi fa sol la si),其本质是音符的发声频率。
可以在程序中用 L1~L7、M1~M7、H1~H7 定义低音、中音、高音所对应的发声频率。
时值是音符的发声时间长短,有全音符、二分音符、四分音符……等等。
音符可以后缀一个“符点”,表示时值增加 1/2,特殊地,二分音符加符点时用“-”代替圆点。参见下表的描述。
在程序中定义一个音符结构体tNote,有两个数据成员:音名mName和时值mTime。
再使用该结构体定义一个tNote型常量数表MyScore[ ],用来保存实际乐谱转换成tNote格式的数据。
有了上述一点点乐谱基础知识,我们就可以很方便地编辑这个数表了。比如音符“3-”转换为“{L3, T/2}”,音符“3.”转换为“{M3, T/4+T/8}”,等等。感兴趣的同学可以自行补充上面简谱中的内容。
审核编辑:刘清
全部0条评论
快来发表一下你的评论吧 !