51单片机+红外发射模块(38k+NEC),这代码对不对?有详细...

2020-01-27 11:34发布

哪位大神帮小弟看一下这段代码,是网上载的,我大概修改了一下几个数值,因为我觉得原来的错的,结果红外发射模块发射不了,用原来载下来的数值执行起来也是不行,小弟这里没示波器,这份代码小弟很详细的给它添加了很多注释,只求有心的前辈帮一下小弟,帮忙看一下哪里不对。。。。 38k + NEC协议。。。。作者没有使用循环去发送 用户码 用户反码 键码 键反码,所以代码看起来比较多,其实是很少的。。。
捣鼓了我好几天了一直不知道为什么不行,啊啊啊啊啊啊 拜托前辈了!帮了小弟这个忙,什么都好说
  1. //#include <AT89X51.h>
  2. #include <reg51.h>

  3. static bit OP;                                   //红外发射管的亮灭控制位
  4. static unsigned int count;                //延时计数器
  5. static unsigned int endcount;         //终止延时计数
  6. static unsigned char flag;                //红外发送标志
  7. sbit  P3_4=P3^4;
  8. char iraddr1; //十六位地址的第一个字节
  9. char iraddr2; //十六位地址的第二个字节
  10. void SendIRdata(char p_irdata);//发送子函数
  11. void delay();


  12. void main(void)                                 
  13. {
  14.         count = 0;
  15.         flag = 0;                //无载波
  16.         OP = 0;                        //不亮
  17.         P3_4 = 0;                //在后面会发现用OP赋值的
  18.         EA = 1;                 //允许CPU中断
  19.         TMOD = 0x11;         //设定时器0和1为16位模式1  
  20.         ET0 = 1;                 //定时器0中断允许
  21.         TH0 = 0xFF;  
  22.         TL0 = 0xE6;         //设定时值0为38K 也就是每隔26us中断一次
  23.         TR0 = 1;                //开始计数
  24.         iraddr1=3;                //自定义的一个地址
  25.         iraddr2=252;        //地址反码

  26.         do
  27.         {
  28.                 delay();                 //延时
  29.                 SendIRdata(221); //发送数据

  30.         }while(1);
  31. }

  32. //定时器0中断处理
  33. void timeint(void) interrupt 1
  34. {
  35.         TH0=0xFF;
  36.         TL0=0xE6;                 //设定时值为38K 也就是每隔26us中断一次
  37.         count++;
  38.        
  39.         if (flag==1)         //如果是待发送的有效数据flag=1,就在此产生载波(亮灭交变)
  40.         {
  41.                 OP=~OP;                //产生方波其实就是调制后的高电平哈
  42.         }
  43.         else
  44.         {
  45.                 OP = 0;                 //发送低电平
  46.         }
  47.        
  48.          P3_4 = OP;           //往发射模块的 IO口发送出去哈
  49. }

  50. void SendIRdata(char p_irdata)                //发送数据子函数
  51. {
  52.         int i;
  53.         char irdata=p_irdata;
  54.        
  55.         /***************************************************************/
  56.        
  57.         //发送9ms的起始码       
  58.         //引导码是9ms的高电平,9000us/26us = 346
  59.         endcount = 346;
  60.         flag=1;                                          //载波模式有效
  61.         count=0;
  62.         while(count<endcount);        //等待中断,在中断中发送载波,总时间为9ms


  63.         //发送4.5ms的结果码,并是载波模式无效,也就是发送4.5ms的低电平
  64.         //结果码是 4500us/26us = 173
  65.         endcount = 173;
  66.         flag=0;
  67.         count=0;
  68.         while(count<endcount);

  69.         /***************************************************************/
  70.         //发送十六位地址的前八位,iraddr存的是地址码
  71.         irdata=iraddr1;
  72.         for(i=0;i<8;i++)
  73.         {
  74.                 //一个周期里规定先以高电平开始,在以低电平结束。先发送0.56ms的38KHZ“1”的红外波(即编码中0.56ms的高电平)
  75.                 endcount = 21;                        //560us/26us = 21
  76.                  flag=1;
  77.                 count=0;
  78.                 while(count<endcount); //等待中断


  79.                   if(irdata-(irdata/2)*2)        //判断二进制数个位为1还是0
  80.                   {
  81.                         endcount=64; //如果是 1,修改 endcount = 64, 64*26us = 1680us
  82.                 }
  83.                   else                 
  84.                   {
  85.                         endcount=21;//如果是0,则低电平 21*26us = 560us;
  86.                 }
  87.                 flag=0; //因为发送的 0,所以调制后就是一连串连续的低电平,所以 flag=0,载波模式无效
  88.                 count=0;
  89.                
  90.                 while(count<endcount); //等待中断发送
  91.                
  92.                 irdata=irdata>>1;//依次取位
  93.                        
  94.         }

  95.         //发送十六位地址的后八位

  96.        
  97.         irdata=iraddr2;        //此处已经是地址的反码       
  98.         for(i=0;i<8;i++)
  99.         {
  100.                 endcount = 21;
  101.                 flag=1;
  102.                 count=0;
  103.                
  104.                 while(count<endcount);
  105.                
  106.                 if(irdata-(irdata/2)*2)
  107.                 {
  108.                         endcount = 64;

  109.                 }
  110.                 else
  111.                 {
  112.                         endcount = 21;
  113.                 }

  114.                 flag=0;
  115.                 count=0;
  116.                
  117.                 while(count<endcount);
  118.                
  119.                 irdata=irdata>>1;
  120.         }/***************************************************************/
  121.         //发送八位数据
  122.        
  123.         irdata=p_irdata;
  124.        
  125.         for(i=0;i<8;i++)
  126.         {
  127.                 endcount = 21;
  128.                 flag=1;
  129.                 count=0;
  130.                
  131.                 while(count<endcount);
  132.                
  133.                 if(irdata-(irdata/2)*2)
  134.                 {
  135.                         endcount=64;;
  136.                        
  137.                 }
  138.                 else
  139.                 {
  140.                         endcount = 21;
  141.                 }
  142.                
  143.                 flag=0;
  144.                 count=0;
  145.                
  146.                 while(count<endcount);
  147.                
  148.                 irdata=irdata>>1;               
  149.         }

  150.         //发送八位数据的反码
  151.         irdata=~p_irdata;                //要将数据位取反
  152.        
  153.         for(i=0;i<8;i++)
  154.         {
  155.                 endcount = 21;
  156.                 flag=1;
  157.                 count=0;
  158.                
  159.                 while(count<endcount);
  160.                
  161.                 if(irdata-(irdata/2)*2)
  162.                 {
  163.                         endcount = 64;
  164.                 }
  165.                 else
  166.                 {
  167.                         endcount = 21;
  168.                 }
  169.                
  170.                 flag=0;
  171.                 count=0;
  172.                
  173.                 while(count<endcount);
  174.                
  175.                 irdata=irdata>>1;
  176.         }
  177.        
  178.   //到这边一帧的数据已经按照 38K + NEC发送出去了
  179. }


  180. void delay()
  181. {
  182.         int i,j;
  183.        
  184.         for(i=0;i<400;i++)
  185.         {
  186.                 for(j=0;j<100;j++)
  187.                 {
  188.                 }
  189.         }
  190. }

复制代码
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
29条回答
xymbmcu
2020-01-31 01:01
/*┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈
函数功能:单帧发送程序
入口参数:1帧数据
┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈*/
void Z0(uchar temp)
{
  uchar v;
  for (v=0;v<8;v++)                     //循环8次移位
       {     
                 TT0(1,m_565);                        //高电平0.65mS         
                         if(temp&0x01) TT0(0,m1_685); //发送最低位
                         else          TT0(0,m_56);     
                         temp >>= 1;                //右移一位
       }   
}

void Z1(uchar temp)
{
  uchar v;
  for (v=0;v<3;v++)                     //循环8次移位
       {     
                 TT0(1,m_565);                        //高电平0.65mS         
                         if(temp&0x04) TT0(0,m1_685); //发送最低位
                         else          TT0(0,m_56);     
                         temp <<= 1;                //右移一位
       }   
}
/*┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈
函数功能:38KHz脉冲发射 + 延时程序
入口参数:(是否发射脉冲,延时约 x (uS))
┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈*/
void TT0(bit BT,uint x)
{

  TH1 = x>>8;                    //输入T0初始值
  TL1 = x;
  TF1=0;                                //清0
  TR1=1;                                //启动定时器0
  if(BT == 0) while(!TF1);        //BT=0时不发射38KHz脉冲只延时;BT=1发射38KHz脉冲且延时;
  else while(1)                            //38KHz脉冲,占空比5:26
         {
                    Ir_Out = 1;               
                    if(TF1)break;       
                    if(TF1)break;
                    if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;       
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;         
                        if(TF1)break;       
                        if(TF1)break;   
                        _nop_();                                                   
                    Ir_Out = 0;
                  if(TF1)break;       
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;       
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;       
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;       
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;       
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;       
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                                   if(TF1)break;
                        if(TF1)break;       
                        if(TF1)break;         
                        if(TF1)break;         
                        if(TF1)break;         
                        if(TF1)break;
                        if(TF1)break;
                        if(TF1)break;       
                        if(TF1)break;
                        _nop_();
                        _nop_();               
                 }
  TR1=0;                                //关闭定时器0
  TF1=0;                                //标志位溢出则清0               
  Ir_Out =0;                                //脉冲停止后,发射端口常态为高电平
}

一周热门 更多>