请教学习型遥控器,波形拷贝式,发射和接收的问题。

2020-01-21 21:36发布

本帖最后由 yihui184 于 2012-10-12 09:35 编辑

做遥控器做了三个月来了,
还没有做到让自己满意的地步!特地来这里请教高人,
帮助帮助我,鳖的急了,真是有点恨自己了,
怎么就做不出来,在网上找资料感觉没有什么收获,这么久了,
现在我就想快点把这个学习型遥控器做出来,
尽快,我再也等不了,再拖,我自己都原谅不了我自己,
很郁闷,真的.现在确实是碰到了瓶颈了!

我做的第一个遥控器程序是专门解NEC的,参考了本论坛楼主BXAK的程序.





第二个做的是看到51hei论坛上的一个学习型遥控器,我把它该造成了存入eeprom中去,但是感觉这个路波型的学习型遥控器,感觉时间不是很准确,不是用定时器录波的,感觉不可靠,但是试了试所有的身边的电视都可以实现
接收码,再发射码都能控制电视。代码如下:有遇到点问题,里面都有注释:

学习型遥控器.rar (40.29 KB, 下载次数: 88) 2012-10-11 23:10 上传 点击文件名下载附件

第三个是我现在做的,根据百度文库上面的一个文章写的,文章如下:

学习型遥控器设计.pdf (121.82 KB, 下载次数: 125) 2012-10-11 23:12 上传 点击文件名下载附件


我写的程序如下:

  1. /*
  2.    时间:2012.10.10
  3.    功能:学习型遥控器
  4. */

  5. #include <reg52.h>

  6. #define uchar unsigned char   
  7. #define uint  unsigned int
  8. #define ulong unsigned long

  9. sbit  study_key=P1^0;                      //学习按键
  10. sbit  studylamp=P2^1;                             //学习状态指示灯
  11. sbit  send_key=P1^1;                      //发射键
  12. sbit  remotein=P2^0;                      //遥控信号输入口
  13. sbit  remoteout= P3^4;                  // 遥控信号输出口
  14. sbit  txkey=P1^1;                         //待定
  15. bit   flag=0;

  16. uchar dat[80];                            //用于记录高低电平的记时值!80个.一的电平要2个字节.


  17. void Delay1ms(uint t)
  18. {
  19.                 uint x,y;
  20.         for(x=0;x<t;x++)
  21.            for(y=0;y<120;y++);
  22. }

  23. void delete_dat()
  24. {
  25.                uchar t;
  26.         for(t=0;t<80;t++)
  27.         {
  28.             dat[t]=0;
  29.         }
  30. }

  31. void init_io()
  32. {
  33.                TMOD=0x21;
  34.         TH1=0xF3;                              
  35.         TL1=0xF3;
  36.         remotein=1;
  37.         remoteout=1;
  38.         studylamp=0;       
  39.         EA=1;
  40. }


  41. void main()
  42. {
  43.    uchar i=0;
  44.    init_io();
  45.    delete_dat();
  46.    while(1)
  47.    {

  48.            if(!study_key)                                                                            //学习键按下,开始接收红外码.用于记录整个码的高低电平.
  49.            {
  50.                           Delay1ms(10);
  51.                   if(!study_key)
  52.                   {
  53.                                  while(!study_key);
  54.                                     while( remotein );                   //当红外接收端为 1 时一直等待,为 0 跳入循环.开始接收程序.
  55.                                       while(1)
  56.                                 {                       
  57.                                   TH0=0;                                
  58.                                   TL0=0;
  59.                                   TR0=1;
  60.                                   while(!remotein);                         //当为 1 时 跳出循环.
  61.                                   TR0=0;
  62.                                   dat[i++]=TH0;                           //保存 0  的记时时间.
  63.                                   dat[i++]=TL0;
  64.                                   TH0=0;                                    //重新赋初值.
  65.                                   TL0=0;                 
  66.                                   TR0=1;
  67.                                   while(remotein)                      //当接收的时候,1 的值是否有溢出,有的话,跳出当前循环,给一个标志位,用于跳出大循环,不再接收.
  68.                                   if(TF0)
  69.                                   {
  70.                                             TF0=0;
  71.                                             TR0=0;
  72.                                               flag=1;
  73.                                               dat[i++]=0;
  74.                                             studylamp=1;
  75.                                             break;
  76.                                  }
  77.                                  if(flag)
  78.                                       break;
  79.                                  TR0=0;
  80.                                  dat[i++]=TH0;
  81.                                          dat[i++]=TL0;                  
  82.                         }
  83.                   }
  84.            }
  85.        
  86.            if(!send_key)                                                  //发射键按下,用于发射接收到的码的高低电平.
  87.            {
  88.                           Delay1ms(10);
  89.                   if(!send_key)
  90.                   {
  91.                           while(!send_key);
  92.                           if(flag)
  93.                           {          
  94.                                           i=0;                                                                                               
  95.                                           ET1=1;                                                                                   //把发送载波的中断开启.
  96.                                           while(1)
  97.                                   {                         
  98.                                                TH0=256-dat[i++];                                                       //先发 1 ,给定时器赋初值,取反,                                          
  99.                                                TL0=256-dat[i++];
  100.                                                TR0=1;
  101.                                                TR1=1;                                                                     //启动载波
  102.                                           while(!TF0);                                                               //溢出后,发下一组.
  103.                                                TF0=0;
  104.                                                TR0=0;
  105.                                                TR1=0;
  106.                                         remoteout=0;                                                        //发送 低 电平
  107.                                         TH0=256-dat[i++];                                                 //发 0  
  108.                                         TL0=256-dat[i++];
  109.                                          if( dat[i] == 0 )                                                     //当发的数据中没有植,为0时,停止发送.
  110.                                          {
  111.                                                       delete_dat();
  112.                                               flag=0;
  113.                                                       studylamp=0;
  114.                                                ET1=0;
  115.                                                break;
  116.                                         }
  117.                                         TR0=1;
  118.                                         while(!TF0);
  119.                                         TF0=0;       
  120.                                         TR0=0;                                                                                 
  121.                                 }
  122.                           }
  123.                   }
  124.            }

  125.    }
  126.         
  127. }

  128. //40KHz发生器      
  129. void time_intt1(void) interrupt 3
  130. {
  131.      remoteout=~remoteout;
  132. }
复制代码请问一下:

我上面的这个程序,我根据PDF那份文档,写的程序:

看了这么多程序,我觉得要做学习型遥控器,我现在是要做记录波形的这种,我觉得只要把高低电平保存起来就可以了嘛,
我上面的这个程序,根据上面那份PDF文档写的,我感觉逻辑上没有错,可是就是控制不了,硬件上面没有问题,希望有经验的
大侠能教教我。

帮我看下我上面写的那个接收码和发射码,哪里是不是有问题呢?还是思路有问题呢?
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
该问题目前已经被作者或者管理员关闭, 无法添加新回复
61条回答
Xlt123gO
1楼-- · 2020-01-27 09:31
标记一下
chenjian198722
2楼-- · 2020-01-27 09:44
liujinhan 发表于 2012-10-12 11:14
之前也是用51的方案做了一个遥控学习,载波不准是肯定的,而且延时也不会很准。后来改用M32了,效果好很多 ...

前辈 我是一个学生,我也在学习红外这部分 ,能不能给我份您写的捕获脉冲长度复制红外波形的例程 ,非常感谢
chenjian198722
3楼-- · 2020-01-27 15:03
liujinhan 发表于 2012-10-12 11:14
之前也是用51的方案做了一个遥控学习,载波不准是肯定的,而且延时也不会很准。后来改用M32了,效果好很多 ...

1130160836@qq.com
liujinhan
4楼-- · 2020-01-27 16:19
 精彩回答 2  元偷偷看……
chenjian198722
5楼-- · 2020-01-27 18:04
liujinhan 发表于 2013-4-5 08:23
搜索下 输入捕获的相关主题吧。。

我已经弄了好长时间了 我用学习了原子例程里面的捕获高脉冲,可是我测遥控同一个按键 得到的两次数据不同 ,希望前辈给个思路,我不会把您的代码用作商用,仅学习
chenjian198722
6楼-- · 2020-01-27 20:44
liujinhan 发表于 2013-4-5 08:23
搜索下 输入捕获的相关主题吧。。

void TIM5_Cap_Init(u16 arr,u16 psc)
{                 
        RCC->APB1ENR|=1<<3;           //TIM5 时钟使能
        RCC->APB2ENR|=1<<2;            //使能PORTA时钟  
         
        GPIOA->CRL&=0XFFFFFFF0;        //PA0 清除之前设置  
        GPIOA->CRL|=0X00000008;        //PA0 输入   
        GPIOA->ODR|=0<<0;                //PA0 下拉
          
        TIM5->ARR=arr;                  //设定计数器自动重装值   
        TIM5->PSC=psc;                  //预分频器

        TIM5->CCMR1|=1<<0;                //CC1S=01         选择输入端 IC1映射到TI1上
        TIM5->CCMR1|=0<<4;                 //IC1F=0000 配置输入滤波器 不滤波
        TIM5->CCMR1|=0<<10;         //IC2PS=00         配置输入分频,不分频

        TIM5->CCER|=0<<1;                 //CC1P=0        上升沿捕获
        TIM5->CCER|=1<<0;                 //CC1E=1         允许捕获计数器的值到捕获寄存器中

        TIM5->DIER|=1<<1;           //允许捕获中断                               
        TIM5->DIER|=1<<0;           //允许更新中断       
        TIM5->CR1|=0x01;            //使能定时器2
        MY_NVIC_Init(2,0,TIM5_IRQChannel,2);//抢占2,子优先级0,组2          
}

//捕获状态
//[7]:0,没有成功的捕获;1,成功捕获到一次.
//[6]:0,还没捕获到高电平;1,已经捕获到高电平了.
//[5:0]:捕获高电平后溢出的次数
u8  TIM5CH1_CAPTURE_STA=0;        //输入捕获状态                                                   
u16        TIM5CH1_CAPTURE_VAL;        //输入捕获值
//定时器5中断服务程序         
void TIM5_IRQHandler(void)
{                     
        u16 tsr;
        tsr=TIM5->SR;
        if((TIM5CH1_CAPTURE_STA&0X80)==0)//还未成功捕获       
        {
                if(tsr&0X01)//溢出
                {            
                        if(TIM5CH1_CAPTURE_STA&0X40)//已经捕获到高电平了
                        {
                                if((TIM5CH1_CAPTURE_STA&0X3F)==0X3F)//高电平太长了
                                {
                                        TIM5CH1_CAPTURE_STA|=0X80;//标记成功捕获了一次
                                        TIM5CH1_CAPTURE_VAL=0XFFFF;
                                }else TIM5CH1_CAPTURE_STA++;
                        }         
                }
                if(tsr&0x02)//捕获1发生捕获事件
                {       
                        if(TIM5CH1_CAPTURE_STA&0X40)                //捕获到一个下降沿                
                        {                                 
                                TIM5CH1_CAPTURE_STA|=0X80;                //标记成功捕获到一次高电平脉宽
                            TIM5CH1_CAPTURE_VAL=TIM5->CCR1;        //获取当前的捕获值.
                                 TIM5->CCER&=~(1<<1);                        //CC1P=0 设置为上升沿捕获
                        }else                                                                  //还未开始,第一次捕获上升沿
                        {
                                TIM5CH1_CAPTURE_STA=0;                        //清空
                                TIM5CH1_CAPTURE_VAL=0;
                                TIM5CH1_CAPTURE_STA|=0X40;                //标记捕获到了上升沿
                                 TIM5->CNT=0;                                        //计数器清空
                                 TIM5->CCER|=1<<1;                                 //CC1P=1 设置为下降沿捕获
                        }                    
                }                                                                                   
        }
        TIM5->SR=0;//清除中断标志位             
}





第一次

HIGH:7604 us
HIGH:2302 us
HIGH:2250 us
HIGH:7604 us
HIGH:1192 us
HIGH:21423 us
HIGH:1185 us
HIGH:1248 us
HIGH:7611 us
HIGH:2304 us
HIGH:2304 us
第二次

HIGH:7658 us
HIGH:1257 us
HIGH:1202 us
HIGH:7625 us
HIGH:1208 us
HIGH:7605 us
HIGH:1156 us
HIGH:1183 us
HIGH:7605 us
HIGH:2192 us
HIGH:2209 us

一周热门 更多>