⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 project._c

📁 AVRkaifashili.rar
💻 _C
📖 第 1 页 / 共 3 页
字号:
//***************************FileName:Project.c**********************//
//***************************ICCAVR6.30编译**************************//
#include <io8535v.h>	     //AT90S8535寄存器定义;
#include <macros.h>	         //AT90S8535宏定义;
#include "zimo.h"            //点阵LED字模
#define uchar unsigned char  //数据类型定义
#define uint unsigned int    //数据类型定义

uchar Key_Value;		     //按键键值;
uchar State_Flag;		     //站点标志;
uchar Ack_Flag;		         //确认标志;
uchar Pre_Flag;		         //预报标志;
uchar Move_Flag;		     //滚动标志;
uchar Spec_Flag;		     //特殊信息标志;
uchar EOM_Flag=1;	         //信息结束标志;
uchar Pst_Flag;		         //上、下行标志;
uchar State=1;			     //站数;
uchar Spec;			         //特殊信息数;
uchar Speed=20;		         //文字滚动速度;
uchar Word_Number;	         //显示字数;

//语音芯片第1~16段分别保存16站的站名信息
//第17段保存报站信息“到了,请要下车的乘客依次从后门下车”
//第18、19段分别保存预报信息“前方到站”、“请要下车的乘客做好下车准备”
//第20段保存欢迎信息及公交车线路说明
//第21、22段保存特殊提示信息
uchar Snd_Info[]={0,17};			   //报站声音信息
uchar Snd_Pre_Info[]={18,0,19};		   //预报声音信息
uchar Snd_Spec[]={21,22};			   //特殊声音信息
uchar Snd_Welc=20;				       //欢迎声音信息

//本例公交车语音报站系统包含16站
//所有的站名都以“第n站”代替,其中n为当前站数,n<16
//报站时显示屏滚动显示“第n站到了”
//预报站时显示屏显示“前方到站第n站”
//其中“第n站”字模存放在二维数组State n[3][32]中
//“到了”字模存放在二维数组DL[2][32]中
//“前方到站”字模存放在二维数组QFDZ[4][32]中
uchar text[32];				           //当前显示文字
uchar next[32];			               //下一个显示文字

#pragma interrupt_handler Key_Scan:2   //定义按键中断INT0的中断服务程序
#pragma interrupt_handler Receive_EOM:3//定义语音中断INT1的中断服务程序

//****************************延时程序*******************************//
void delay(int t)
{while(t--) ;}

//****************************语音芯片驱动程序***********************//
void Set_CE(uchar level)               //定义ISD2560使能线为PA^4
{if(level==1) PORTA |=0x10;           
 else         PORTA &=0xef;
}

void Set_PD(uchar level)               //定义ISD2560的PD线为PA^3      
{if(level)    PORTA |=0x08;
 else         PORTA &=0xf7;
}

void Set_PR(uchar level)               //定义ISD2560的PR线为PA^2
{if(level)    PORTA |=0x04;
 else         PORTA &=0xfb;
}

void Set_A6(uchar level)               //定义ISD2560的A6/8/9线为PA^1
{if(level)    PORTA |=0x02;
 else         PORTA &=0xfd;
}

void Set_A0(uchar level)               //定义ISD2560的A6/8/9线为PA^1
{if(level)    PORTA |=0x01;
 else         PORTA &=0xfe;
}

//****************************语音搜索和播放程序****************************//
void Seek_Segment(uchar s)             //语音搜索程序
{Set_PD(1);				               //语音芯片复位
 delay(20000);
 Set_PD(0);
 Set_PR(1);				               //放音模式
 Set_A0(1);	 			               //M0模式
 while(s--)				               //快进s段
 {Set_CE(0);
  Set_CE(1);
  do NOP();
  while(EOM_Flag);		               //检测EOM标志位,为0时有效
  EOM_Flag=1;}
 Set_A0(0);	 			               //M6模式
}

void Play(void)                        //语音播放程序
{Set_CE(0);				               //CE线低电平触发芯片的放音操作
 Set_CE(1);
 do  NOP();
 while(EOM_Flag);		               //检测EOM标志位,为0时有效
 EOM_Flag=1;			               //重新赋EOM标志位为1
}

//****************************语音报站程序****************************//
void Inform(uchar m)                   //报站
{uchar i;
 if(Pst_Flag) Snd_Info[0]=m;           //若为上行方向,顺序报站
 else		  Snd_Info[0]=17-m;	       //若为下行方向,逆序报站
 Set_PD(1);				               //语音芯片复位
 delay(20000);
 Set_PD(0); 
 for(i=0;i<2;i++)
 {Seek_Segment(Snd_Info[i]);	       //搜索相应语音信息段
  Play();}						       //播放
}

void Pre_Inform(uchar m)               //报站 
{uchar i;
 if(Pst_Flag) Snd_Pre_Info[1]=m;       //若为上行方向,顺序预报站
 else		  Snd_Pre_Info[1]=17-m;	   //逆序预报站
 Set_PD(1);				               //语音芯片复位
 delay(20000);
 Set_PD(0); 
 for(i=0;i<3;i++)
 {Seek_Segment(Snd_Pre_Info[i]);	   //搜索相应语音信息段
  Play();}							   //播放
}

void Special(uchar m)                  //播放特殊信息
{Set_PD(1);				               //语音芯片复位
 delay(20000);
 Set_PD(0);
 Seek_Segment(Snd_Spec[m]);		       //搜索相应语音信息段
 Play();							   //播放
}

void Welcome()                         //欢迎信息
{Set_PD(1);				               //语音芯片复位
 delay(20000);
 Set_PD(0); 
 Seek_Segment(Snd_Welc);		       //搜索相应语音信息段
 Play();						       //播放
}

//****************************I2C驱动程序****************************//
void Set_SCL(uchar i)                  //定义MAX6959时钟线为PA^7
{if(i)   PORTA |=0x80;
 else    PORTA &=0x7f;
}
 
void Set_SDA(uchar i)                  //定义MAX6959数据线为PA^6
{if(i)   PORTA |=0x40;
 else    PORTA &=0xbf;
}

void Start()                           //I2C总线的开始条件
{Set_SDA(1);	                       //SDA=1;
 Set_SCL(1);	                       //SCL=1;
 delay(100);	                       //等待时钟信号变高
 Set_SDA(0);	                       //SDA=0;
 delay(100);
 Set_SCL(0);	                       // SCL=0;
}

void Stop()                            //I2C总线结束条件
{Set_SDA(0);	                       //SDA=0;
 delay(100);
 Set_SCL(1);	                       //SCL=1;
 delay(100);	                       //等待时钟信号变低
 Set_SDA(1);	                       //SDA=1;
 delay(100);
 Set_SCL(0);	                       //SCL=0;
}

void Ack()                             //I2C总线应答
{Set_SDA(0);	                       //SDA=0;
 delay(50);
 Set_SCL(1);	                       //SCL=1;
 delay(100);
 Set_SCL(0);	                       //SCL=0;
 delay(50);
 Set_SDA(1);	                       //SDA=1;
}

void Nack()                            //I2C总线应答非
{Set_SDA(1);	                       //SDA=1;
 delay(50);
 Set_SCL(1);	                       //SCL=1;
 delay(100);
 Set_SCL(0);	                       //SCL=0;
 delay(50);
 Set_SDA(0);	                       //SDA=0;
}

void Check_Ack()                       //I2C总线应答检查
{Set_SDA(1);	                       //SDA=1;
 Set_SCL(1);	                       //SCL=1;
 Ack_Flag=0;	                       //清除应答标志;
 DDRA&=0xbf; 	                       //设置SDA为输入
 if(!((PINA & 0x40)>>6))
   {delay(50);
    Set_SCL(0);	                       //SCL=0;
    delay(100);}
 else
   {Ack_Flag=1;	                       //收到应答;
    delay(50);
    Set_SCL(0);	                       //SCL=0;
    delay(100);}
 DDRA |=0xff; 	                       //重新设置SDA为输出	 
}

void Write_Bit0()                      //写1bit数据:0    
{Set_SDA(0);	                       //SDA=0;
 Set_SCL(1);	                       //SCL=1;
 delay(100);
 Set_SCL(0);	                       //SCL=0;
}

void Write_Bit1()                      //写1bit数据:1       
{Set_SDA(1);	                       //SDA=1;
 Set_SCL(1);	                       //SCL=1;
 delay(100);
 Set_SCL(0);	                       //SCL=0;
 Set_SDA(0);	                       //SDA=0;
}

void Write_Byte(uchar Data)            //写一字节数据Data  
{uchar i;
 for(i=0;i<8;i++)
  {if(Data & 0x80)  Write_Bit1();      //传输位从高位到低位,先传最高位 
   else             Write_Bit0();
   Data <<=1;}                         //数据左移             
}

uchar Read_Byte()                      //读一字节数据:返回值即读的数据           
{uchar Read_Data=0xff;		           // Read_Data为读入的数据,初始值为0xff
 uchar j;
 for (j=0;j<8;j++)
  {Set_SDA(1);	   
   Set_SCL(1);	   
   DDRA &=0xbf;	   
   if((PINA & 0x40)==0)
     {Read_Data <<=1;
      Read_Data=(Read_Data & 0xfe);                 
      Set_SCL(0);}
   else 
    {Read_Data <<=1;
     Read_Data =( Read_Data  | 0x01);
     Set_SCL(0);}}
 DDRA |=0x40;		              
 return(Read_Data);               
}

//***************************写一字节数据****************************//
//向从地址为Slave的IIC器件的Address地址写一字节数据Data
void Write_1byte(uchar Slave,uchar Address,uchar Data)
{Start();		                       //开始
 Write_Byte(Slave);		               //写I2C器件地址
 do Check_Ack();		               //检查应答位
 while(Ack_Flag==1);
 Write_Byte(Address);                  //送寄存器地址
 do Check_Ack();		               //检查应答位
 while(Ack_Flag==1);
 Write_Byte(Data);		               //写入一字节数据
 do Check_Ack();                       //检查应答位
 while(Ack_Flag==1);
 Stop();                               //停止
}

//***************************写两字节数据****************************//
//向从地址为Slave的IIC器件的Address地址开始写两字节数据Data0,Data1
void Write_2byte(uchar Slave,uchar Address,uchar Data0,uchar Data1)
{Start();		                       //开始
 Write_Byte(Slave);		               //写I2C器件地址
 do Check_Ack();		               //检查应答位
 while(Ack_Flag==1);                  
 Write_Byte(Address);                  //送寄存器地址
 do Check_Ack();		               //检查应答位
 while(Ack_Flag==1);
 Write_Byte(Data0);
 do Check_Ack();	     	           //检查应答位
 while(Ack_Flag==1);
 Write_Byte(Data1);
 do Check_Ack();		               //检查应答位
 while(Ack_Flag==1);
 Stop();		                       //停止信号
}

//***************************读一字节数据****************************//
//从从地址为Slave的IIC器件的Address地址处读一字节数据

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -