×
单片机 > 单片机程序设计 > 详情

TEA5767的简单收音机设计

发布时间:2020-08-28 发布时间:
|
TEA5767是飞利浦公司生产的一款收音机芯片,很多手机,MP3、MP4里的收音机功能都是于他实现的。

  TEA5767HN 基本资料:
   高灵敏、低噪声高频放大器,
   收音频率:87.6MHz~108MHz,(支持频率范围在76MHz~87.5MHz 之间的校园收音频道),
   LC 调谐振荡器使成本更低,RF AGC 电路
   内置调频中频选择 ,I2C 总线控制
   内置FM 立体声解调器 ,PLL 合成调谐解码器
   两个可编程端口 ,软静音,SNC(立体声噪声消除)
   自适应立体声解码,自动搜索功能
   等待模式,需要一个32.768KHz 晶体
   40 脚LQFP 封装


CPU:STC89C54RD+
晶震:40M


#include
#include
#include

sbit SDA_5767=P1^0;     //数据
sbit SCL_5767=P1^1;    // 时钟
sbit BUS_MODE=P1^2;    // 总线选择
sbit BUS_ENABLE=P1^3;  // 总线使能

#define max_freq 108000     //108Mhz
#define min_freq 87500        //87.5Mhz
#define max_pll 0x339b       //108MHz时的pll.
#define min_pll 0x299d        //87.5MHz时的pll.
#define KEY  P2           //P2口作为按键


#define WADDR   0XC0  //写地址
#define RADDR   0XC1  //读地址

unsigned char write_data[5]={0x2b,0x05,0x61,0x11,0x40};  //每次写入5字节 注释如下(感觉有用的注下 详细了解看手册)
//write_data[0] 第二位为1为搜索模式 后6为表示收音机频率的高6位
//write_data[1] 表示收音机频率的低8位
//write_data[2] 最高位表示搜索模式是向上还是向下 后两位表示搜索的灵敏度 第四位立体声和单声道选择位后四为左右声道设置
//write_data[3] 第三位表示日本频率和国际频率选择位 第四位 震荡频率选择位(与第五字节最高位共同决定)第七为数字降噪功能选择
//write_data[4] 最高位决定内部震荡频率
unsigned char read_data[5];   //读取5字节 读以上各寄存器的状态 主要是频率读取

unsigned long frequencry=0;  //32位读取频率数据
unsigned int pll;            //16位转换数据

 


void delay(void) //延时函数
{
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
}

void start_5767(void)//起始
{
BUS_ENABLE=1;
SDA_5767=1;
SCL_5767=1;
delay();
SDA_5767=0;
delay();
SCL_5767=0;
}

void stop_5767(void)//停止
{
SDA_5767=0;
SCL_5767=1;
delay();
SDA_5767=1;
delay();
SCL_5767=0;
BUS_ENABLE=0;
}

void Check_Ack(void) //检查应答信号
{
SDA_5767=1;
SCL_5767=1;
F0=0;
delay();
if(SDA_5767) //如果数据为高 置位非应答标志FO
F0=1;        //通用标志位 PSW状态寄存器
SCL_5767=0;  //准备下一变化数据
}

void Ack(void) //发响应信号
{
SDA_5767=0;
delay();
SCL_5767=1;
delay();
SCL_5767=0;
}

void no_Ack(void) //发非响应信号
{
SDA_5767=1;
SCL_5767=0;
delay();
SCL_5767=1; //迫使数据传输结束
delay();
}

void send_byte(unsigned char temp) //发送一字节数据
{
unsigned char i=8;
while(i--)
{
  SDA_5767=(bit)(temp&0x80);
  SCL_5767=1;
  delay();
  SCL_5767=0;
  temp<<=1;
}
SCL_5767=0;
delay();
SDA_5767=1; //释放SDA数据线
}

unsigned char read_byte(void) //读一字节数据
{
unsigned char i=8;
unsigned char temp;
while(i--)
{
  temp<<=1;
  if(SDA_5767)
  temp++;
  SCL_5767=1;
  delay();
  SCL_5767=0;
}
SCL_5767=0;
delay();
SDA_5767=1; //释放SDA数据线
return (temp);
}

void write_radio()
{
unsigned char i;
start_5767();
send_byte(WADDR);
Check_Ack();
if(F0)
{
  no_Ack();
  return;
}
Ack();
for(i=0;i<5;i++)
{
send_byte(write_data[i]);
Check_Ack();
if(F0)
{
  no_Ack();
  return;
}
Ack();
}
stop_5767();
}


void  read_radio()
{
unsigned char i;
start_5767();
send_byte(RADDR);
Check_Ack();
if(F0)
{
  no_Ack();
  return;
}
Ack();
for(i=0;i<5;i++)
{
read_data[i]=read_byte();
Check_Ack();
if(F0)
{
  no_Ack();
  return;
}
Ack();
}
stop_5767();
}

unsigned int get_radio()  //获得频率数据
{
 unsigned char tmp_h,tmp_l;
 read_radio();
 tmp_h=read_data[0]&0x3f;
 tmp_l=read_data[1];
 return (tmp_h<<8|tmp_l);
}

void get_frequencry() //将数据转换为标准频率
{
 unsigned char tmp_data;
 unsigned int pll_data;
 pll_data=get_radio();
 tmp_data=read_data[2]&0x10;
 if(tmp_data)
 frequencry= (pll_data*32768/4-225000)/1000;  //(单位KHZ)
 else
 frequencry= (pll_data*32768/4+225000)/1000; // (单位KHZ)
}

void get_pll() //将频率转换数据
{
 unsigned char tmp_data;
 unsigned int pll_data;
 unsigned long  tmp_pll;
 pll_data=get_radio();
 tmp_data=read_data[2]&0x10;
 if(tmp_data)
 tmp_pll=(frequencry+255000)*4/32768;// (单位HZ)
 else
 tmp_pll=(frequencry-255000)*4/32768; //(单位HZ)
 pll=(unsigned int)(tmp_pll/1000);    //(单位 KHZ)
}

void search(bit mode)   //手动搜台
{
  get_frequencry();
  if(mode)
  {
  frequencry+=100;
  if(frequencry>max_freq)
  frequencry=87500;
  }
  else
  {
  frequencry-=100;
  if(frequencry   frequencry=108000;
  }
  get_pll();
  write_data[0]=(pll>>8)&0x3f;
  write_data[1]=pll&0xff;
  write_data[2]=0x61;
  write_data[3]=0x11;
  write_data[4]=0x40;
  write_radio();
}

void auto_search(bit mode)  //自动搜台
{
 get_frequencry();
 get_pll();
 if(mode)
 {
  write_data[2]=0xe1;
  if(pll>max_pll)
  pll=min_pll;
 }
 else
 {
 write_data[2]=0x61;
 if(pll  pll=max_pll;
 }
  write_data[0]=(pll>>8)&0x3f+0x40; //自动搜台
  write_data[1]=pll&0xff;
  write_data[2]=0x61;
  write_data[3]=0x11;
  write_data[4]=0x40;
  write_radio();
  read_radio();
  while(!(read_data[0]&0x80)) //最高位为1 电台就绪 否则一直读
  {
   read_radio();
  }
}

 void delay_xms(unsigned int count) //1MS延时函数
{
 register unsigned char j;
 while (count --)
 {
  for (j=0;j<230;j++);
 }
}


unsigned char GetKey()          //键盘处理函数
{
        unsigned char m,n,e=0xff; 
       
        KEY = 0x0f;        //键盘口置00001111
        if (KEY != 0x0f)          //查寻键盘口的值是否变化
        {
                delay_xms(20);       //延时20毫秒
                if (KEY != 0x0f)         //有键按下处理
                {
                        m = KEY;         //键值放入寄存器m
                }
                KEY = 0xf0;       //将键盘口置为11110000
                n = KEY;          //将第二次取得值放入寄存器n
                m |= n;   
                switch(m)        
                {
                        case 0x7e: e = 0x00; break;
                        case 0xbe: e = 0x01; break;
                        case 0xde: e = 0x02; break;
                        case 0xee: e = 0x03; break;
                        case 0x7d: e = 0x04; break;
                        case 0xbd: e = 0x05; break;
                        case 0xdd: e = 0x06; break;
                        case 0xed: e = 0x07; break;
                        case 0x7b: e = 0x08; break;
                        case 0xbb: e = 0x09; break;
                        case 0xdb: e = 0x0a; break;
                        case 0xeb: e = 0x0b; break;
                        case 0x77: e = 0x0c; break;
                        case 0xb7: e = 0x0d; break;
                        case 0xd7: e = 0x0e; break;
                        case 0xe7: e = 0x0f; break;
                        default: break;   
                }
        }
       
        KEY = 0x0f;           
        while (KEY != 0x0f);       
             
        return (e);   
}


void main(void)
{
    unsigned char i;
    TMOD = 0x11;
    TH0 = 0x5d;
    TL0 = 0x3d;
    TR0 = 0;  
    TH1 = 0x5d;
    TL1 = 0x3d;
    TR1 = 0;  
    PCON = 0x00;
    SCON = 0xD0;
    IP = 0x14;
    EX0 = 1;
    IT0 = 1;
    ET0 = 1;
    EX1 = 1;
    IT1 = 1;
    ES = 0;
    EA = 0;
    BUS_MODE=0;
    write_radio();//初始写入 90M
    frequencry = 90000;

    while(1)
    {
     i = GetKey();
    
     switch (i)
     {
                case 0x00:
                    search(1);   
                break;


                case 0x01:
                    search(0);
                break;

         
                case 0x02:
                    auto_search(1);
                break;
               
                case 0x03:
                    auto_search(0);
                break;
               
                default: break;
         }
    }
}


关键字:TEA5767  收音机设计 

『本文转载自网络,版权归原作者所有,如有侵权请联系删除』

热门文章 更多
C51 特殊功能寄存器SFR的名称和地址