编写普中c51程序,蜂鸣器管脚为P2^5,通过控制按钮实现可以切换《两只老虎》、《世上只有妈妈好》、《烟花易冷》三首曲子播放,
时间: 2023-08-31 10:32:36 浏览: 183
### 回答1:
以下是普中c51程序,其中使用了定时器和外部中断实现按钮控制和播放曲子功能:
```
#include <reg52.h> // 引入 8051 系列的头文件
sbit beep = P2^5; // 定义蜂鸣器管脚为P2^5
sbit button = P3^2; // 定义按钮管脚为P3^2
unsigned char music[] = {0x95, 0x95, 0x96, 0x94, 0x94, 0x96, 0x97, 0x95, 0x93, 0x93, 0x95, 0x95, 0x95, 0x0, 0x95, 0x95, 0x96, 0x94, 0x94, 0x96, 0x97, 0x95, 0x93, 0x93, 0x95, 0x95, 0x95, 0x0, 0x97, 0x97, 0x98, 0x97, 0x95, 0x93, 0x91, 0x91, 0x93, 0x95, 0x95, 0x0}; // 两只老虎曲子
unsigned char music_index = 0; // 当前播放曲子的位置
unsigned char music2[] = {0x91, 0x91, 0x92, 0x94, 0x94, 0x92, 0x91, 0x91, 0x92, 0x94, 0x94, 0x92, 0x92, 0x0, 0x91, 0x91, 0x92, 0x94, 0x94, 0x92, 0x91, 0x91, 0x91, 0x92, 0x91, 0x0}; // 世上只有妈妈好曲子
unsigned char music2_index = 0; // 当前播放曲子的位置
unsigned char music3[] = {0x92, 0x92, 0x93, 0x91, 0x91, 0x93, 0x94, 0x92, 0x90, 0x90, 0x92, 0x92, 0x92, 0x0, 0x92, 0x92, 0x93, 0x91, 0x91, 0x93, 0x94, 0x92, 0x90, 0x90, 0x92, 0x92, 0x92, 0x0, 0x94, 0x94, 0x95, 0x94, 0x92, 0x90, 0x8e, 0x8e, 0x90, 0x92, 0x92, 0x0}; // 烟花易冷曲子
unsigned char music3_index = 0; // 当前播放曲子的位置
void delay(unsigned int i) // 延时函数
{
unsigned int j,k;
for(j=0;j<i;j++)
for(k=0;k<125;k++);
}
void init_timer() // 初始化定时器
{
TMOD |= 0x01; // 设置为模式1
TH0 = 0xFC; // 定时器初值
TL0 = 0x66;
ET0 = 1; // 允许定时器中断
TR0 = 1; // 启动定时器
}
void play_music(unsigned char *music, unsigned char *music_index) // 播放曲子函数
{
if (*music_index == 0) { // 如果是曲子的第一个音符,先延时一段时间
delay(2000);
}
if (*music_index < sizeof(music)-1) { // 如果还没有播放完整首曲子
unsigned char note = music[(*music_index)++]; // 获取当前音符
if (note != 0x0) { // 如果不是休止符
TH0 = 65536 - note * 100; // 计算定时器初值
TL0 = TH0;
beep = 1; // 发出声音
} else { // 如果是休止符
beep = 0; // 停止声音
}
} else { // 如果已经播放完整首曲子
*music_index = 0; // 重置当前播放曲子的位置
}
}
void main()
{
EA = 1; // 打开总中断
IT0 = 1; // 设定为下降沿触发
EX0 = 1; // 允许外部中断
init_timer(); // 初始化定时器
while(1) {
if (button == 0) { // 如果按钮按下
delay(10); // 延时去抖动
if (button == 0) { // 如果按钮还是按下状态
play_music(music, &music_index); // 播放两只老虎曲子
while(button == 0); // 等待按钮松开
}
}
}
}
void timer0() interrupt 1 // 定时器中断处理函数
{
beep = ~beep; // 反转蜂鸣器管脚
}
void external0() interrupt 0 // 外部中断0处理函数
{
static unsigned char music_id = 1;
music_id++;
if (music_id > 3) {
music_id = 1;
}
switch(music_id) {
case 1:
play_music(music, &music_index); // 播放两只老虎曲子
break;
case 2:
play_music(music2, &music2_index); // 播放世上只有妈妈好曲子
break;
case 3:
play_music(music3, &music3_index); // 播放烟花易冷曲子
break;
}
}
```
注意事项:
1. 程序中使用了定时器和外部中断,请确保单片机的时钟频率为12MHz,否则需要修改程序中的定时器初值和音符对应的计数值。
2. 程序中使用了延时函数,延时时间需要根据实际情况进行调整。
3. 程序中定义了三首曲子的音符序列和当前播放曲子的位置,需要在程序中添加新的曲子时,按照相同的格式添加音符序列和当前播放曲子的位置,并在外部中断0处理函数中添加曲子的选择逻辑。
### 回答2:
编写C51程序实现蜂鸣器的控制,其中蜂鸣器的管脚为P2^5。通过控制按钮,可以实现三首曲子《两只老虎》、《世上只有妈妈好》、《烟花易冷》的切换播放。
首先,我们需要定义曲谱数据以表示每首曲子的音符和节奏。假设每个音符用一个数字表示,0代表休止符,1-7分别代表音阶的1-7音,音符与音符之间以逗号分隔。节奏以音符的1/8为单位,数字表示节拍数,如4代表四分之一拍,8代表八分之一拍。我们可以定义三个全局数组来分别表示三首曲子的乐谱。
然后,使用定时器来实现音符和节奏的控制。我们可以选择一个合适的定时周期,比如在10ms的定时中断中更新蜂鸣器的管脚输出电平。根据当前曲谱数据的音符和节奏,通过改变蜂鸣器管脚的输出电平来产生音乐。
接着,我们使用一个外部按钮来切换曲子的播放。在按下按钮时,通过改变一个全局变量的值来记录当前是播放哪首曲子。同时,在定时器的中断中,根据全局变量的值来选择当前播放的曲谱数据。
最后,循环执行程序,在每次按下按钮时切换曲子的播放。
总结起来,我们需要完成以下几个步骤来编写C51程序实现蜂鸣器的控制:
1. 定义三个全局数组用于存储三首曲子的乐谱数据;
2. 使用定时器中断来控制蜂鸣器音符和节奏的切换;
3. 使用外部按钮来切换曲子的播放;
4. 循环执行程序,在每次按下按钮时切换曲子的播放。
通过以上步骤,我们可以实现蜂鸣器的控制,通过控制按钮切换曲子的播放。
### 回答3:
要编写普通C51程序,实现蜂鸣器管脚P2^5的控制,以及通过按钮切换不同的曲子播放的功能,可以按照以下步骤进行编写:
1.首先,需要定义蜂鸣器管脚和按钮的引脚,可以通过宏定义的方式进行,如下所示:
#define BEEP_PIN P2^5 // 蜂鸣器管脚为P2^5
#define BUTTON_PIN P1^0 // 控制按钮管脚为P1^0
2.接下来,需要定义每首歌曲对应的频率,可以使用数组的方式进行,如下所示:
unsigned int song1[] = { /* 两只老虎的频率数组 */ };
unsigned int song2[] = { /* 世上只有妈妈好的频率数组 */ };
unsigned int song3[] = { /* 烟花易冷的频率数组 */ };
3.然后,需要定义一个变量来表示当前播放的曲子编号,初始值为1,表示初始播放第一首曲子。同时,还需要定义一个变量用于保存按钮的状态,用于判断按钮是否按下,如下所示:
unsigned int currentSong = 1; // 当前播放的曲子编号,默认为1
unsigned int buttonState = 0; // 按钮状态变量,默认为0,表示未按下
4.接下来,需要编写一个函数用于播放指定曲子的频率数组,如下所示:
void playSong(unsigned int* song)
{
// 遍历频率数组,依次播放每个音符
for(int i = 0; i < sizeof(song)/sizeof(unsigned int); i++)
{
// 设置蜂鸣器管脚为高电平
BEEP_PIN = 1;
// 延时一定时间,即音符的持续时间
delay(song[i]);
// 设置蜂鸣器管脚为低电平
BEEP_PIN = 0;
// 延时一定时间,即音符之间的间隔时间
delay(10);
}
}
5.最后,需要在主程序中实现控制按钮的检测和曲子的切换逻辑,如下所示:
void main()
{
while(1)
{
// 检测按钮状态
buttonState = BUTTON_PIN;
// 如果按钮被按下,则切换曲子
if(buttonState == 1)
{
// 切换曲子编号
currentSong++;
// 如果曲子编号超过3,则重置为1
if(currentSong > 3)
{
currentSong = 1;
}
}
// 根据当前曲子编号播放对应曲子
switch(currentSong)
{
case 1:
playSong(song1);
break;
case 2:
playSong(song2);
break;
case 3:
playSong(song3);
break;
default:
break;
}
}
}
阅读全文