基于51单片机控制的ISD4004语音模块引脚电平触发发音程序Word格式.docx
《基于51单片机控制的ISD4004语音模块引脚电平触发发音程序Word格式.docx》由会员分享,可在线阅读,更多相关《基于51单片机控制的ISD4004语音模块引脚电平触发发音程序Word格式.docx(19页珍藏版)》请在冰豆网上搜索。

sbitLCM_E=P2^2;
//使能信号输入端,LCD1602的第6脚
//***************函数声明************************************************
voidWriteDataLCM(ucharWDLCM);
//LCD模块写数据
voidWriteCommandLCM(ucharWCLCM,BuysC);
//LCD模块写指令
ucharReadStatusLCM(void);
//读LCD模块的忙标
voidDisplayOneChar(ucharX,ucharY,ucharASCII);
//在第X+1行的第Y+1位置显示一个字符
voidLCMInit(void);
voidDelayUs(uintus);
//微妙延时程序
voidDelayMs(uintMs);
//毫秒延时程序
voidinit_t0();
//定时器0初始化函数
voidsetkey_treat(void);
//录音键处理程序
voidupkey_treat(void);
//播放键处理程序
voiddisplay();
//显示处理程序
voidisd_setrec(ucharadl,ucharadh);
//发送setrec指令
voidisd_rec();
//发送rec指令
voidisd_stop();
//stop指令(停止当前操作)
voidisd_powerup();
//发送上电指令
voidisd_stopwrdn();
//发送掉电指令
voidisd_send(ucharisdx);
//spi串行发送子程序,8位数据
voidisd_setplay(ucharadl,ucharadh);
voidisd_play();
//程序中的一些常量定义
uinttime_total,st_add,end_add=0;
uintadds[25];
//25段语音的起始地址暂存
uintadde[25];
//25段语音的结束地址暂时
uchart0_crycle,count,count_flag,flag2,flag3,flag4;
ucharsecond_count=170,msecond_count=0;
//second_count为芯片录音的起始地址,起始地址本来是A0,也就是160,
//我们从170开始录音吧。
#defineBusy0x80//用于检测LCM状态字中的Busy标识
/*===========================================================================
主程序
=============================================================================*/
////////////////////////////////////////////////
sbitK0=P2^0;
//
sbitK1=P2^1;
sbitK2=P2^5;
//
sbitK3=P3^0;
sbitK4=P3^1;
sbitK5=P3^2;
sbitK6=P3^3;
sbitK7=P3^5;
sbitK8=P3^6;
sbitK9=P3^7;
////////////////////////////////////////////////
voidmain(void)
{
LED1=0;
//灭录音指示灯
flag3=0;
flag4=0;
time_total=340;
//录音地址从170开始,对应的单片机开始计时的时间就是340*0.1秒
adds[0]=170;
count=0;
LCMInit();
//1602初始化
init_t0();
//定时器初始化
DisplayOneChar(0,5,'
I'
);
//开机时显示000ISD4004-X
DisplayOneChar(0,6,'
S'
DisplayOneChar(0,7,'
D'
DisplayOneChar(0,8,'
4'
DisplayOneChar(0,9,'
0'
DisplayOneChar(0,10,'
DisplayOneChar(0,11,'
DisplayOneChar(0,12,'
-'
DisplayOneChar(0,13,'
X'
//////////////////////////////////////////////////
K0=P2^0;
K1=P2^1;
K2=P2^5;
K3=P3^0;
K4=P3^1;
K5=P3^2;
K6=P3^3;
K7=P3^5;
K8=P3^6;
K9=P3^7;
while
(1)
{
display();
//显示处理
/////////////////////////////////////////////
if(K0==0)
//你
{st_add=0x0170;
isd_setplay(st_add&
0x00ff,st_add>
>
8);
//发送setplay指令,从指定地址开始放音
isd_play();
//发送放音指令
DelayUs(20);
while(INT==1);
//等待放音完毕的EOM中断信号INT=P1^4
isd_stop();
//放音完毕,发送stop指令
}
if(K1==0)//好
{st_add=0x0181;
//等待放音完毕的EOM中断信号
if(K2==0)//对不起
{st_add=0x0194;
if(K3==0)//谢谢
{st_add=0x0211;
if(K4==0)//没关系
{st_add=0x0225;
if(K5==0)//什么
{st_add=0x0240;
if(K6==0)//真
{st_add=0x0254;
if(K7==0)//克服
{st_add=0x0267;
if(K8==0)//叫
{st_add=0x0281;
if(K9==0)//早上
{st_add=0x0293;
//////////////////////////////////////////////////////////////////////////////////////////////////////////
//upkey_treat();
//放音键处理
//setkey_treat();
//录音键处理
}
//*******************************************
//从指定地址开始录音的程序就是在这段里面
voidsetkey_treat(void)
set_key=1;
//置IO口为1,准备读入数据
DelayUs
(1);
if(set_key==0)
if(flag3==0)//录音键和放音键互锁,录音好后,禁止再次录音。
如果要再次录音,那就要复位单片机,重新开始录音
if(count==0)//判断是否为上电或复位以来第一次按录音键
st_add=170;
else
st_add=end_add+3;
}//每段语言间隔3个地址
adds[count]=st_add;
//每段语音的起始地址暂时
if(count>
=25)//判断语音段数时候超过25段,因为单片机内存的关系?
//本程序只录音25段,如果要录更多的语音,改为不可查询的即可
{//如果超过25段,则覆盖之前的语音,从新开始录音
isd_powerup();
//AN键按下,ISD上电并延迟50ms
isd_stopwrdn();
isd_powerup();
LED1=1;
//录音指示灯亮,表示录音模式
isd_setrec(st_add&
//从指定的地址
if(INT==1)//判定芯片有没有溢出
{
isd_rec();
//发送录音指令
time_total=st_add*2;
//计时初始值计算
TR0=1;
//开计时器
while(set_key==0);
//等待本次录音结束
TR0=0;
//录音结束后停止计时
isd_stop();
//发送4004停止命令
end_add=time_total/2+2;
//计算语音的结束地址
adde[count]=end_add;
//本段语音结束地址暂存
//录音完毕,LED熄灭
count++;
//录音段数自加
count_flag=count;
//录音段数寄存
flag2=1;
flag4=1;
//解锁放音键
//=================================================
//放音机处理程序
//从指定地址开始放本段语音就是这段程序
voidupkey_treat(void)
//ucharovflog;
AN=1;
//准备读入数据
if(AN==0)//判断放音键是否动作
if(flag4==1)//互锁录音键
//if(flag2==1)//判断是否为录音好后的第一次放音
//{
//从第0段开始播放
//}
/////////////////////////////////////////
//count=0;
///////////////////////////////////////////////////
//count=0;
st_add=adds[count];
//送当前语音的起始地址
isd_setplay(st_add&
isd_play();
//发送放音指令
DelayUs(20);
while(INT==1);
//等待放音完毕的EOM中断信号
isd_stop();
//放音完毕,发送stop指令
while(AN==0);
//语音段数自加
flag2=0;
flag3=1;
=count_flag)//如果播放到最后一段后还按加键,则从第一段重新播放
}
//************************************************?
voidisd_rec()
isd_send(0xb0);
SS=1;
//****************************************
voidisd_setrec(unsignedcharadl,unsignedcharadh)
DelayMs
(1);
isd_send(adl);
//发送放音起始地址低位
DelayUs
(2);
isd_send(adh);
//发送放音起始地址高位
isd_send(0xa0);
//发送setplay指令字节
//=============================================================================
//**********************************************
//定时器0中断程序
voidtimer0()interrupt1
TH0=(65536-50000)/256;
TL0=(65536-50000)%256;
t0_crycle++;
if(t0_crycle==2)//0.1秒
t0_crycle=0;
time_total++;
msecond_count++;
if(msecond_count==10)//1秒
{
msecond_count=0;
second_count++;
if(second_count==60)
second_count=0;
if(time_total==4800)time_total=0;
//********************************************************************************************
voidinit_t0()
TMOD=0x01;
//设定定时器工作方式1,定时器定时50毫秒
EA=1;
//开总中断
ET0=1;
//允许定时器0中断
//定时器中断次数计数单元
//******************************************
voiddisplay()
ucharx;
if(flag3==1||flag4==1)//判断是否有录音过或者放音过
x=count-1;
if(x==255){x=count_flag-1;
DisplayOneChar(0,0,x/100+0x30);
//显示当前语音是第几段
DisplayOneChar(0,1,x/10%10+0x30);
DisplayOneChar(0,2,x%10+0x30);
if(flag3==0)//录音时显示本段语音的起始和结束地址
DisplayOneChar(1,0,st_add/1000+0x30);
//计算并显示千位
DisplayOneChar(1,1,st_add/100%10+0x30);
DisplayOneChar(1,2,st_add/10%10+0x30);
DisplayOneChar(1,3,st_add%10+0x30);
DisplayOneChar(1,4,'
DisplayOneChar(1,5,'
DisplayOneChar(1,6,end_add/1000+0x30);
DisplayOneChar(1,7,end_add/100%10+0x30);
DisplayOneChar(1,8,end_add/10%10+0x30);
DisplayOneChar(1,9,end_add%10+0x30);
if(flag4==1)//放音时显示本段语音的起始和结束地址
DisplayOneChar(1,0,adds[x]/1000+0x30);
DisplayOneChar(1,1,adds[x]/100%10+0x30);
DisplayOneChar(1,2,adds[x]/10%10+0x30);
DisplayOneChar(1,3,adds[x]%10+0x30);
DisplayOneChar(1,6,adde[x]/1000+0x30);
DisplayOneChar(1,7,adde[x]/100%10+0x30);
DisplayOneChar(1,8,adde[x]/10%10+0x30);
DisplayOneChar(1,9,adde[x]%10+0x30);
//======================================================================
//LC