51单片机音乐播放程序设计

给大家分享下51单片机播放音乐简谱的函数库:
sound play for 51mcu
copyright (c) 2005 by jjj.
--all rights reserved--
file name: soundplay.h
author: jiang jian jun
created: 2005/5/16
modified:no
revision: 1.0
说明
曲谱存贮格式 unsigned char code musicname{音高,音长,音高,音长。..。, 0,0}; 末尾:0,0 表示结束(important)
音高由三位数字组成:
个位是表示 1~7 这七个音符
十位是表示音符所在的音区:1-低音,2-中音,3-高音;
百位表示这个音符是否要升半音: 0-不升,1-升半音。
音长最多由三位数字组成:
个位表示音符的时值,其对应关系是:
|数值(n):|0 |1 |2 |3 | 4 | 5 | 6
|几分音符: |1 |2 |4 |8 |16 |32 |64 音符=2^n
十位表示音符的演奏效果(0-2):0-普通,1-连音,2-顿音
百位是符点位: 0-无符点,1-有符点
调用演奏子程序的格式
play(乐曲名,调号,升降八度,演奏速度);
|乐曲名: 要播放的乐曲指针,结尾以(0,0)结束;
|调号(0-11) : 是指乐曲升多少个半音演奏;
|升降八度(1-3) : 1:降八度, 2:不升不降, 3:升八度;
|演奏速度(1-12000): 值越大速度越快;
***************************************************************************/
#ifndef __soundplay_h_revision_first__
#define __soundplay_h_revision_first__
#include
/**************************************************************************
#define system_osc 11059200/12000000 /定义晶振频率12000000hz
#define sound_space4/5 /定义普通音符演奏的长度分率,/每4分音符间隔
sbit beepio = p2^6;/定义输出管脚
unsigned intcode fretab[12]= { 262,277,294,311,330,349,369,392,415,440,466,494 }; /原始频率表
unsigned char code signtab[7]= { 0,2,4,5,7,9,11 }; /1~7在频率表中的位置
unsigned char code lengthtab[7]= { 1,2,4,8,16,32,64 };
unsigned char sound_temp_th0,sound_temp_tl0; /音符定时器初值暂存
unsigned char sound_temp_th1,sound_temp_tl1; /音长定时器初值暂存
/**************************************************************************
void initialsound(void)
{
beepio = 1;
sound_temp_th1 = (65535-(1/1200)*system_osc)/256; / 计算tl1应装入的初值(10ms的初装值)
sound_temp_tl1 = (65535-(1/1200)*system_osc)%6; / 计算th1应装入的初值
th1 = sound_temp_th1;
tl1 = sound_temp_tl1;
tmod|= 0x11;
et0 = 1;
et1 = 0;
tr0 = 0;
tr1 = 0;
ea = 1;
}
void beeptimer0(void) interrupt 1 /音符发生中断
{
beepio = !beepio;
th0 = sound_temp_th0;
tl0 = sound_temp_tl0;
}
/**************************************************************************
void play(unsigned char *sound,unsigned char signature,unsigned octachord,unsigned int speed)
{
unsigned int newfretab[12];/新的频率表
unsigned char i,j;
unsigned int point,ldiv,ldiv0,ldiv1,ldiv2,ldiv4,currentfre,temp_t,soundlength;
unsigned char tone,length,sl,sh,sm,slen,xg,fd;
for(i=0;i12;i) / 根据调号及升降八度来生成新的频率表
{
j = i signature;
if(j11)
{
j = j-12;
newfretab[i] = fretab[j]*2;
}
else
newfretab[i] = fretab[j];
if(octachord == 1)
newfretab[i]=2;
else if(octachord == 3)
newfretab[i]=2;
}
soundlength = 0;
while(sound[soundlength] != 0x00) /计算歌曲长度
{
soundlength =2;
}
point = 0;
tone = sound[point]; br / length = sound[point 1]; / 读出第一个音符和它时时值
ldiv0 = 12000/speed; / 算出1分音符的长度(几个10ms)
ldiv4 = ldiv0/4; / 算出4分音符的长度
ldiv4 = ldiv4-ldiv4*sound_space;/ 普通音最长间隔标准
tr0 = 0;
tr1 = 1;
while(pointsoundlength)
{
sl=tone; /计算出音符
sm=tone/10; /计算出高低音
sh=tone/100; /计算出是否升半
currentfre = newfretab[signtab[sl-1] sh];/查出对应音符的频率
if(sl!=0)
{
if (sm==1) currentfre = 2; /低音
if (sm==3) currentfre = 2; /高音
temp_t = 65536-(50000/currentfre)*10/(12000000/system_osc);/计算计数器初值
sound_temp_th0 = temp_t/256;
sound_temp_tl0 = temp_t%6;
th0 = sound_temp_th0;
tl0 = sound_temp_tl0 12; /加12是对中断延时的补偿
}
slen=lengthtab[length];/算出是几分音符
xg=length/10; /算出音符类型(0普通1连音2顿音)
fd=length/100;
ldiv=ldiv0/slen; /算出连音音符演奏的长度(多少个10ms)
if (fd==1)
ldiv=ldiv ldiv/2;
if(xg!=1)
if(xg==0) /算出普通音符的演奏长度
if (slen=4)
ldiv1=ldiv-ldiv4;
else
ldiv1=ldiv*sound_space;
else
ldiv1=ldiv/2; /算出顿音的演奏长度
else
ldiv1=ldiv;
if(sl==0) ldiv1=0;
ldiv2=ldiv-ldiv1; /算出不发音的长度
if (sl!=0)
{
tr0=1;
for(i=ldiv1;i0;i--)/发规定长度的音
{
while(tf1==0);
th1 = sound_temp_th1;
tl1 = sound_temp_tl1;
tf1=0;
}
}
if(ldiv2!=0)
{
tr0=0; beepio=1;
for(i=ldiv2;i0;i--)/音符间的间隔
{
while(tf1==0);
th1 = sound_temp_th1;
tl1 = sound_temp_tl1;
tf1=0;
}
}
point =2;
tone=sound[point];
length=sound[point 1];
}
beepio = 1;
}
/**************************************************************************
#endif
以下为曲谱编码文件,自己可以根据规则,对照简谱编写曲谱编码表,我已经做好了一个应用程序,只需将简谱输入进去,就可以直接输出曲谱编码表,省去人工编码的痛苦。此软件作为共享软件发布,此东东绝对是搞电子设计在校大学生泡mm的巨佳手段,呵呵。
▎附录:
/挥着翅膀的女孩
unsigned char code music_girl[]={ 0x17,0x02, 0x17,0x03, 0x18,0x03, 0x19,0x02, 0x15,0x03,
0x16,0x03, 0x17,0x03, 0x17,0x03, 0x17,0x03, 0x18,0x03,
0x19,0x02, 0x16,0x03, 0x17,0x03, 0x18,0x02, 0x18,0x03,
0x17,0x03, 0x15,0x02, 0x18,0x03, 0x17,0x03, 0x18,0x02,
0x10,0x03, 0x15,0x03, 0x16,0x02, 0x15,0x03, 0x16,0x03,
0x17,0x02, 0x17,0x03, 0x18,0x03, 0x19,0x02, 0x1a,0x03,
0x1b,0x03, 0x1f,0x03, 0x1f,0x03, 0x17,0x03, 0x18,0x03,
0x19,0x02, 0x16,0x03, 0x17,0x03, 0x18,0x03, 0x17,0x03,
0x18,0x03, 0x1f,0x03, 0x1f,0x02, 0x16,0x03, 0x17,0x03,
0x18,0x03, 0x17,0x03, 0x18,0x03, 0x20,0x03, 0x20,0x02,
0x1f,0x03, 0x1b,0x03, 0x1f,0x66, 0x20,0x03, 0x21,0x03,
0x20,0x03, 0x1f,0x03, 0x1b,0x03, 0x1f,0x66, 0x1f,0x03,
0x1b,0x03, 0x19,0x03, 0x19,0x03, 0x15,0x03, 0x1a,0x66,
0x1a,0x03, 0x19,0x03, 0x15,0x03, 0x15,0x03, 0x17,0x03,
0x16,0x66, 0x17,0x04, 0x18,0x04, 0x18,0x03, 0x19,0x03,
0x1f,0x03, 0x1b,0x03, 0x1f,0x66, 0x20,0x03, 0x21,0x03,
0x20,0x03, 0x1f,0x03, 0x1b,0x03, 0x1f,0x66, 0x1f,0x03,
0x1b,0x03, 0x19,0x03, 0x19,0x03, 0x15,0x03, 0x1a,0x66,
bsp; 0x1a,0x03, 0x19,0x03, 0x19,0x03, 0x1f,0x03, 0x1b,0x03,
0x1f,0x00, 0x1a,0x03, 0x1a,0x03, 0x1a,0x03, 0x1b,0x03,
0x1b,0x03, 0x1a,0x03, 0x19,0x03, 0x19,0x02, 0x17,0x03,
0x15,0x17, 0x15,0x03, 0x16,0x03, 0x17,0x03, 0x18,0x03,
0x17,0x04, 0x18,0x0e, 0x18,0x03, 0x17,0x04, 0x18,0x0e,
0x18,0x66, 0x17,0x03, 0x18,0x03, 0x17,0x03, 0x18,0x03,
0x20,0x03, 0x20,0x02, 0x1f,0x03, 0x1b,0x03, 0x1f,0x66,
0x20,0x03, 0x21,0x03, 0x20,0x03, 0x1f,0x03, 0x1b,0x03,
0x1f,0x66, 0x1f,0x04, 0x1b,0x0e, 0x1b,0x03, 0x19,0x03,
0x19,0x03, 0x15,0x03, 0x1a,0x66, 0x1a,0x03, 0x19,0x03,
0x15,0x03, 0x15,0x03, 0x17,0x03, 0x16,0x66, 0x17,0x04,
0x18,0x04, 0x18,0x03, 0x19,0x03, 0x1f,0x03, 0x1b,0x03,
0x1f,0x66, 0x20,0x03, 0x21,0x03, 0x20,0x03, 0x1f,0x03,
0x1b,0x03, 0x1f,0x66, 0x1f,0x03, 0x1b,0x03, 0x19,0x03,
0x19,0x03, 0x15,0x03, 0x1a,0x66, 0x1a,0x03, 0x19,0x03,
0x19,0x03, 0x1f,0x03, 0x1b,0x03, 0x1f,0x00, 0x18,0x02,
0x18,0x03, 0x1a,0x03, 0x19,0x0d, 0x15,0x03, 0x15,0x02,
0x18,0x66, 0x16,0x02, 0x17,0x02, 0x15,0x00, 0x00,0x00};

关于行业首款双摄儿童手表的性能分析和应用
成都高新减灾研究所与百度签署战略合作协议
图像增强三大类别介绍
智能涡街流量计的错误安装方式有哪些
基于一种多功能设计的Coosno智能咖啡桌介绍
51单片机音乐播放程序设计
如何看懂继电器控制电路图
LDO线性稳压器的并联-什么是LDO线性稳压器的并联
连接技术的发展对工业连接器提出了新要求
ACM官网公布了2018 ACM博士论文奖
百个为什么—什么时候该用片上稳压器?片内稳压器呢?
Nordic:nRF51422多协议ANT SoC简介
2016年全球VR设备出货将达291万台 明年预估增长75%
企业申请USB VID具有哪些重要意义
骁龙888已成为了2021年旗舰智能手机树立的全新标杆
华为云构建知识计算平台,助力实现行业的智能化转型
Apple Pay日本上线为何只有iPhone7能用?
钳形电流表的优点_钳形电流表测三相电流
高通获得苹果支付的45亿美元和解金,库克:感觉良好
百度Apollo获IATF 16949认证 为自动驾驶的车规级量产奠定了基础