Nano播放音乐
本帖最后由 丄帝De咗臂 于 2015-7-5 13:05 编辑【简介】本项目中使用Nano控制压电陶瓷片和LED灯,制作具有视听效果的音乐编辑播放器,使其播放一首《传奇》。完成图如下
【器材】Arduino Nano,压电陶瓷片、LE×6(白、绿、蓝、黄、橙、红),面包板,面包线
【原理】电路原理图如下
【接线】接线示意图如下
【程序】代码如下
/*用简谱制作一首《传奇》
1=E,1=G两种调;采用了Excel表格函数将简谱的1、2、3、4、5、6、7变成频率,还把频率变成数组,统计出数组的个数
在这个基础上,做了一组音乐彩灯:用不同的频率,驱动不同的6种颜色的灯*/
//6个频率指示灯的频率界值:
int ledbd1=560;
int ledbd2=661;
int ledbd3=760;
int ledbd4=880;
int ledbd5=1000;
/***************曲子中各个音符的频率及节拍数组*****************/
//旋律的频率,按照E调,旋律中各个音符的频率值
int melody[]=
{
0,660,660,660,825,733,733,733,660,660,660,733,733,660,550,550,0,619,619,619,660,733,619,550,495,412,412,
0,825,733,825,825,733,733,733,660,660,733,550,550,550,733,660,0,619,619,619,660,733,733,550,495,412,
990,733,825,990,733,660,550,0,733,550,825,733,660,660,495,
990,733,825,990,733,660,550,0,733,550,825,733,660,660,733,733,
0,660,660,660,495,660,990,879,825,733,660,0,660,825,990,1100,990,1100,990,1100,990,825,825,733,825,
0,660,660,660,495,660,990,879,825,733,660,0,660,825,990,1100,990,1100,990,1100,990,825,990,990,
1188,990,879,990,1188,1320,660,879,990,1056,990,1056,990,879,879,990,
1188,990,879,990,1188,1320,1584,1320,879,990,1056,990,1056,990,879,879,990
};
// 各个音符的节拍,16:1/4拍;8:1/2拍;4:1拍;2:2拍;等等
int noteDurations[]=
{
8,16,16,8,8,8,16,16,16,8,16,8,8,16,16,2,8,16,16,8,16,5.3,8,16,8,16,2,
8,16,16,8,16,16,8,16,16,4,8,8,16,16,16,2,8,16,16,8,16,5.3,8,16,5.3,2,
5.3,5.3,8,5.3,5.3,8,2,8,5.3,5.3,8,5.3,5.3,8,2,
5.3,5.3,8,5.3,5.3,8,2,8,5.3,5.3,8,5.3,5.3,16,16,2,
8,16,16,8,16,5.3,8,8,8,5.3,2,16,16,16,16,8,16,8,5.3,8,16,16,16,8,2,
5.3,16,16,8,16,5.3,8,8,8,5.3,2,16,16,16,16,8,16,8,5.3,8,8,16,5.3,2,
3,8,8,8,8,8,1,2,8,4,16,16,16,16,16,2,
3,8,8,8,8,8,2,2,4,8,4,16,16,16,16,16,2
};
/************************初始化函数****************************/
void setup()
{
//设置数字口的输入/输出模式
for(int i=2; i<14;i++)
pinMode(i,OUTPUT); //设置数字口D2-D13为输出口
}
/**************************主函数******************************/
void loop()
{
for(int i=3; i<12;i=i+2)//6个频率指示灯的负极接点:GND、3、5、7、9、11
digitalWrite(i,LOW); //即熄灭所有灯
//用循环语句演奏整个旋律,要注意音符的数量(这个可以用excel表格统计出来)
for (int thisNote = 0; thisNote < 166; thisNote++)
{
//用除法计算演奏时间,
//用传奇录音校对节奏,采用3132毫秒,很接近
int noteDuration = 3132/noteDurations; //赋值
tone(14, melody,noteDuration);//D14口-A0口,用压电陶瓷片,也可用8欧姆喇叭
int pauseBetweenNotes = noteDuration *1.2;//两个音符之间应该以最短的间隔分开,从经验中得知,延迟时间是音符的1.1~1.3倍左右
delay(pauseBetweenNotes);
noTone(14);//停止演奏
//频率赋值给变量,控制相应的LED灯亮
int melodytN = melody;
//为了使灯与音乐保持同步,这里的melody[]必须+1
if (melodytN<ledbd1)
{ //最低的频率区间
for (int i=2;i<13;i=i+2)
{
digitalWrite(i,LOW); //其余灯熄灭
}
digitalWrite(2,HIGH); //最左边的灯亮
}
if (melodytN>ledbd1&&melodytN<ledbd2)
{ //第二个频率区间
for (int i=2;i<13;i=i+2)
digitalWrite(i,LOW); //其余灯熄灭
digitalWrite(4,HIGH); //从左往右第二个灯亮
}
if (melodytN>ledbd2&&melodytN<ledbd3)
{ //第三个频率区间
for (int i=2;i<13;i=i+2)
digitalWrite(i,LOW); //其余灯熄灭
digitalWrite(6,HIGH); //从左往右第三个灯亮
}
if (melodytN>ledbd3&&melodytN<ledbd4)
{ //第四个频率区间
for (int i=2;i<13;i=i+2)
digitalWrite(i,LOW); //其余灯熄灭
digitalWrite(8,HIGH); //从左往右第四个灯亮
}
if (melodytN>ledbd4&&melodytN<ledbd5)
{ //第五个频率区间
for (int i=2;i<13;i=i+2)
digitalWrite(i,LOW); //其余灯熄灭
digitalWrite(10,HIGH); //从左往右第五个灯亮
}
if (melodytN>ledbd5)
{ //最高的频率
for (int i=2;i<13;i=i+2)
digitalWrite(i,LOW); //其余灯熄灭
digitalWrite(12,HIGH); //最右边的灯亮
}
}
}【效果】最终效果如下
http://v.youku.com/v_show/id_XMTI3NzYzNjkwOA==.html
广告时间为啥是100秒?额 能收集齐如此之多的LED,楼主真是费了 不少功夫。 hnyzcj 发表于 2015-7-5 15:29
能收集齐如此之多的LED,楼主真是费了 不少功夫。
六个颜色还多 丄帝De咗臂 发表于 2015-7-5 15:59
六个颜色还多
不多不多 hnyzcj 发表于 2015-7-5 16:16
不多不多
:P 做一个流水哈哈或者连接cube呢 大连林海 发表于 2015-7-5 21:55
做一个流水哈哈或者连接cube呢
我用的是6个LED,音符不是1-7吗,共形成6个区间,分别是1-2、2-3、3-4、4-5、5-6、6-7,给压电陶瓷片的不同频率时,相应区间的 LED就会被点亮,所以这其实是声光互动、视听盛宴,而非流水灯:victory: 大连林海 发表于 2015-7-5 21:55
做一个流水哈哈或者连接cube呢
cube效果应该更好,不过手头木有 好创意赞一个
页:
[1]