你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

STM32接收红外遥控数据

[复制链接]
STMCU小助手 发布时间:2022-8-20 17:00
一. 简介
最近在做项目的过程中,由于使用的是核心板,没有按键,尝试通过串口进行数据发送,进行控制,但是太麻烦了。于是想到了通过红外遥控进行控制。经济又实惠,还可以隔空远程操作,且只有一个数据线,YYDS。

二. 红外遥控数据传输协议
不做过多的理论知识的简介,主要是为了教大家怎么使用。传输过程如下

1.空闲态 为 高电平
2.引导码 : 9ms的低电平 和 4.5ms的高电平
3.数据码: 数据码包括四个部分依次是用户码、用户反码、键码和键码反码,每个8位,共32位,560us的低电平加560us的高电平表示数据0,560us的低电平加1.68ms的高电平表示数据1
4.停止位:可以忽略,软件中可以不用管
依次按照对应的时间来检测就可以。

本次设计通过外部IO中断来进行红外数据的读取,低电平触发(空闲为高电平)。

三. 程序设计
1.定义好相关变量,RCC和GPIO
  1. //红外遥控控制
  2. #define InfraredGPIOPort        GPIOB
  3. #define InfraredGPIOPin         GPIO_Pin_0   
  4. #define InfraredRCC_APB         RCC_APB2Periph_GPIOB
复制代码

2.GPIO初始化
  1. void InfraredGPIOInit(void)//GPIO口初始化
  2. {
  3.     GPIO_InitTypeDef GPIOInitStruct;
  4.     RCC_APB2PeriphClockCmd(InfraredRCC_APB | RCC_APB2Periph_AFIO ,ENABLE); //开启时钟  RCC_APB2Periph_AFIO
  5.     GPIOInitStruct.GPIO_Pin = InfraredGPIOPin;
  6.     GPIOInitStruct.GPIO_Speed = GPIO_Speed_50MHz;
  7.     GPIOInitStruct.GPIO_Mode = GPIO_Mode_IPU;
  8.     GPIO_Init(InfraredGPIOPort,&GPIOInitStruct);
  9. }
复制代码

3.开启中断
中断控制线可以根据自己的Pin来确定,如果是GPIO_Pin_8,那么这里就是EXTI_Line8.
  1. void InfraredEXTIInit(void)//中断初始化
  2. {
  3.     EXTI_InitTypeDef EXTI_InitStructure;
  4.     NVIC_InitTypeDef NVIC_InitStructure;//定义中断结构体变量

  5.         //中断配置
  6.         EXTI_ClearITPendingBit(EXTI_Line0);
  7.         GPIO_EXTILineConfig(GPIO_PortSourceGPIOB, GPIO_PinSource0);  

  8.         EXTI_InitStructure.EXTI_Line = EXTI_Line0;
  9.         EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;
  10.         EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;  
  11.         EXTI_InitStructure.EXTI_LineCmd = ENABLE;
  12.         EXTI_Init(&EXTI_InitStructure);
  13.         
  14.            NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn;//EXTI0中断通道
  15.         NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0;//抢占优先级
  16.         NVIC_InitStructure.NVIC_IRQChannelSubPriority =1;                //子优先级
  17.         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;                //使能
  18.         NVIC_Init(&NVIC_InitStructure);        //根据指定的参数初始化VIC寄存器
复制代码

4.电平持续时间计数
这里主要是对电平的出现时间进行一个计数
  1. //计算低电平的持续时间
  2. uint16_t InfraredRecvLowTime(void)
  3. {
  4.     uint16_t time = 0;
  5.     while(GPIO_ReadInputDataBit(InfraredGPIOPort,GPIO_Pin_0) == 0)
  6.     {
  7.         if(time >= 500)
  8.             break;
  9.         time +=1;
  10.         delay_us(17);
  11.     }
  12.     return time;
  13. }   
  14. //计算高电平的持续时间
  15. uint16_t InfraredRecvHighTime(void)
  16. {
  17.     uint16_t time = 0;
  18.     while(GPIO_ReadInputDataBit(InfraredGPIOPort,GPIO_Pin_0) == 1)
  19.     {
  20.         if(time >= 250)
  21.             break;
  22.         time +=1;
  23.         delay_us(17);
  24.     }
  25.     return time;
  26. }

复制代码

5.编写中断控制函数
通过数据的参数过程进行判断,就可以了。持续时间需要在一个范围内,可以自己测试后设置。

  1. uint8_t InfraredDataRecv() //获取红外遥控数据
  2. {
  3.     uint16_t time;
  4.     uint8_t i,j;
  5.     uint8_t data[4] = {0};
  6.     //获取引导码
  7.     time = InfraredRecvLowTime();
  8.     if(time < 400 || time >= 500)
  9.         return 0x00;
  10.     time = InfraredRecvHighTime();
  11.     if(time < 150 || time > 250)
  12.         return 0x00;
  13.     //获取数据
  14.     for(i = 0; i < 4 ; i++)
  15.     {
  16.         for(j = 0 ; j < 8 ;j ++)
  17.         {
  18.             time = InfraredRecvLowTime();
  19.             if(time < 20 || time > 35)
  20.                 return 0x00;
  21.             time = InfraredRecvHighTime();   //通过高电平的时间长短来判断数据0,1
  22.             if(time < 35)   //数据0
  23.             {
  24.                 data<i> <<= 1;
  25.                 data<i> |=0x0;
  26.             }
  27.             else
  28.             {
  29.                 data<i> <<= 1;
  30.                 data<i> |= 0x1;
  31.             }
  32.         }
  33.     }
  34.     return data[2];
  35. }
  36. void EXTI0_IRQHandler(void)
  37. {
  38.   if(EXTI_GetITStatus(EXTI_Line0) != RESET)
  39.   {
  40.     uint8_t data;
  41.     data = InfraredDataRecv();
  42.     if(data == InfraredLeft)
  43.         KEYState = KEYLEFT;
  44.     else if(data == InfraredRight)
  45.         KEYState = KEYRIGHT;
  46.     else if(data == InfraredUp)
  47.         KEYState = KEYUP;
  48.     else if(data == InfraredDown)
  49.         KEYState = KEYDOWN;
  50.     else if(data == InfraredReturn)
  51.         KEYState = KEYRETURN;
  52.     delay_ms(10);
  53.     /*清除标志位 */
  54.     EXTI_ClearITPendingBit(EXTI_Line0);
  55.   }

  56. }


  57. </i></i></i></i>
复制代码


收藏 评论0 发布时间:2022-8-20 17:00

举报

0个回答

所属标签

相似分享

官网相关资源

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版