世纪电源网社区logo
社区
Datasheet
标题
返回顶部
讨论

电子琴单片机源码

[复制链接]
查看: 453 |回复: 0
1
yuangungun
  • 积分:1621
  • |
  • 主题:108
  • |
  • 帖子:197
积分:1621
LV6
高级工程师
  • 2018-10-17 10:01:55
#include<AT89X52.h>

#define KeyPort P1


unsigned char High,Low; //定时器预装值的高8位和低8位

sbit SPK=P3^7;          //定义蜂鸣器接口
sbit playSongKey=P0^0;          //功能键

sbit RS=P2^0;//液晶数据命令选择
sbit RW=P2^1;//液晶读写选择
sbit EN=P2^2;//液晶使能端

unsigned char code freq[][2]={
  0xD8,0xF7,//00440HZ 1   
  0xBD,0xF8,//00494HZ 2  
  0x87,0xF9,//00554HZ 3  
  0xE4,0xF9,//00587HZ 4   
  0x90,0xFA,//00659HZ 5     
  0x29,0xFB,//00740HZ 6     
  0xB1,0xFB,//00831HZ 7      
  0xEF,0xFB,//00880HZ `1
};

unsigned char Time;
unsigned char code YINFU[9][1]={{' '},{'1'},{'2'},{'3'},{'4'},{'5'},{'6'},{'7'},{'8'}};
                          //世上只有****好数据表
unsigned char code MUSIC[]={ 6,2,3,      5,2,1,      3,2,2,    5,2,2,    1,3,2,    6,2,1,    5,2,1,
                     6,2,4,      3,2,2,      5,2,1,    6,2,1,           5,2,2,         3,2,2,           1,2,1,
                     6,1,1,      5,2,1,      3,2,1,         2,2,4,           2,2,3,         3,2,1,    5,2,2,
                     5,2,1,      6,2,1,      3,2,2,         2,2,2,    1,2,4,         5,2,3,           3,2,1,
                     2,2,1,      1,2,1,      6,1,1,         1,2,1,           5,1,6,         0,0,0
                                      };
                         // 音阶频率表 高八位
unsigned char code FREQH[]={
                         0xF2,0xF3,0xF5,0xF5,0xF6,0xF7,0xF8,
                         0xF9,0xF9,0xFA,0xFA,0xFB,0xFB,0xFC,0xFC, //1,2,3,4,5,6,7,8,i
                         0xFC,0xFD,0xFD,0xFD,0xFD,0xFE,
                         0xFE,0xFE,0xFE,0xFE,0xFE,0xFE,0xFF,
                               } ;
                         // 音阶频率表 低八位
unsigned char code FREQL[]={
                         0x42,0xC1,0x17,0xB6,0xD0,0xD1,0xB6,
                         0x21,0xE1,0x8C,0xD8,0x68,0xE9,0x5B,0x8F, //1,2,3,4,5,6,7,8,i
                         0xEE,0x44, 0x6B,0xB4,0xF4,0x2D,
                         0x47,0x77,0xA2,0xB6,0xDA,0xFA,0x16,
                                };

void Init_Timer0(void);//定时器初始化

//延时函数大约约2*z+5us
void delay2xus(unsigned char z)
{
   while(z--);
}
// 延时函数大约约1ms
void delayms(unsigned char x)
{
   while(x--)
   {
     delay2xus(245);
     delay2xus(245);
   }
}


/*------------------------------------------------
                节拍延时函数
各调1/4节拍时间:
调4/4  125ms
调2/4  250ms
调3/4  187ms
------------------------------------------------*/
void delayTips(unsigned char t)
{
    unsigned char i;
          for(i=0;i<t;i++)
    {
            delayms(250);
    }
    TR0=0;
}
//播放音乐的函数
void PlaySong()
{
   TH0=High;//赋值定时器时间,决定频率
   TL0=Low;
   TR0=1;      //打开定时器
   delayTips(Time); //延时所需要的节拍                     
}

//定时器T0初始化子程序
void Init_Timer0(void)
{
TMOD |= 0x01;          //使用模式1,16位定时器,使用"|"符号可以在使用多个定时器时不受影响                     
EA=1;            //总中断打开
ET0=1;           //定时器中断打开
}
//定时器T0中断子程序
void Timer0_isr(void) interrupt 1
{
TH0=High;
TL0=Low;
SPK=!SPK;
}
//主函数
void main (void)
{
  unsigned char num,k,i;                 
  Init_Timer0();    //初始化定时器0,主要用于数码管动态扫描
  SPK=0;                        //在未按键时,喇叭低电平,防止长期高电平损坏喇叭         
  while (1)
  {
   switch(KeyPort)          //对按键进行处理
                {
                 case 0xfe:num= 1;break;
                 case 0xfd:num= 2;break;
                 case 0xfb:num= 3;break;
                 case 0xf7:num= 4;break;
                 case 0xef:num= 5;break;
                 case 0xdf:num= 6;break;
                 case 0xbf:num= 7;break;
                 case 0x7f:num= 8;break;      //分别对应不用的音调
                 default:num= 0;break;
                }
    P2 = KeyPort;
    if(num==0)
    {
       TR0=0;
       SPK=0;   //在未按键时,喇叭低电平,防止长期高电平损坏喇叭
          }
    else
    {
            High=freq[num-1][1];
                   Low =freq[num-1][0];
                  TR0=1;
          }
   if(playSongKey==0)        //如果播放音乐按键被按下
   {
     delayms(10);
     if(playSongKey==0)
     {
       i=0;  
       while(i<100)
            {         
            k=MUSIC+7*MUSIC[i+1]-1;//去音符振荡频率所需数据
            High=FREQH[k];
            Low=FREQL[k];
            Time=MUSIC[i+2];          //节拍时长
            i=i+3;
                        if(P1!=0xff)//长按任意8音键退出播放
                        {
               delayms(10);
               if(P1!=0xff)
                                 i=101;
                        }
            PlaySong();  
            }
                   TR0=0;
     }
   }

  }
}


声明:以上资源来源于网络,如侵删
热门技术、经典电源设计资源推荐

世纪电源网总部

地 址:天津市南开区黄河道大通大厦8层

电 话:400-022-5587

传 真:(022)27690960

邮 编:300110

E-mail:21dy#21dianyuan.com(#换成@)

世纪电源网分部

广 东:(0755)82437996 /(138 2356 2357)

北 京:(010)69525295 /(15901552591)

上 海:(021)24200688 /(13585599008)

香 港:HK(852)92121212

China(86)15220029145

网站简介 | 网站帮助 | 意见反馈 | 联系我们 | 广告服务 | 法律声明 | 友情链接 | 清除Cookie | 小黑屋 | 不良信息举报 | 网站举报

Copyright 2008-2024 21dianyuan.com All Rights Reserved    备案许可证号为:津ICP备10002348号-2   津公网安备 12010402000296号