一 背景
最近在调试红外通信功能的时候遇到了很多问题,在此总结一下,希望能帮到未来对此有疑问的自己,如果有幸能帮到其他人也算是做了一件有意义的事情了。
二 红外发射头与红外接收头
2.1 发射头
发射管也属于二极管,只有两个脚,通过控制二极管的导通来发射信号
2.2 接收头
接收管一般有三个脚,一个vcc,一个gnd,还有一个信号脚。
2.3 起始信号、逻辑0、逻辑1的定义
通常在控制发射端时,以38khz的频率来发送方波,此时发送端需要以高低电平来控制,接收头收到的是一个低电平,其他情况下为高电平。
2.3.1 起始信号
参考红外遥控器中引导码
-发送端波形
9ms发送方波,4.5ms不发送方波
-接收端波形
9ms是低电平,4.5ms是高电平
2.3.2 逻辑1
2.3.3 逻辑0
三 发送与接收处理
3.1 延时api
rtthread官方提供了一个微妙延时函数rt_hw_us_delay,在延时低于1000us时会有延时不准的问题,这里稍作一些修改,如果想要更准确的延时可能要用定时器的方式了。
void rt_hw_us_delay_2(rt_uint32_t us){ rt_uint32_t ticks; rt_uint32_t told, tnow, tcnt = 0; rt_uint32_t reload = systick- >load; ticks = us * reload / (1000000ul / rt_tick_per_second); told = systick- >val; while (1) { tnow = systick- >val; if (tnow != told) { if (tnow = ticks) { break; } } }}void rt_hw_us_delay(rt_uint32_t us){ if (us val; /* number of ticks per millisecond */ const uint32_t tickperms = systick- >load + 1; /* number of ticks to count */ const uint32_t nbticks = ((us - ((us > 0) ? 1 : 0)) * tickperms) / 1000; /* number of elapsed ticks */ uint32_t elapsedticks = 0; __io uint32_t oldticks = currentticks; do { currentticks = systick- >val; elapsedticks += (oldticks elapsedticks); } else { rt_hw_us_delay_2(us); }}3.2 时间相关的宏定义
#define config_ir_frequency_hz ((uint32_t)38000) #define config_ir_frequency_us ((uint32_t)(1000000ul*1/config_ir_frequency_hz)) #define config_ir_delay_us (config_ir_frequency_us/2) #define round_up(m,n) (((m*10/n)+5)/10)#define config_ir_time_error_percent (30) #define time_get_error_min(t) (t-((t*config_ir_time_error_percent)/100))#define time_get_error_max(t) (t+((t*config_ir_time_error_percent)/100))#define config_ir_start_low_us ((uint32_t)9000) #define config_ir_start_high_us ((uint32_t)4500) #define config_ir_start_high_us_min time_get_error_min(config_ir_start_high_us)#define config_ir_start_high_us_max time_get_error_max(config_ir_start_high_us)#define config_ir_common_low_us ((uint32_t)500) #define config_ir_common_low_us_min time_get_error_min(config_ir_common_low_us)#define config_ir_common_low_us_max time_get_error_max(config_ir_common_low_us)#define config_ir_logic_0_high_us ((uint32_t)800) #define config_ir_logic_0_high_us_min time_get_error_min(config_ir_logic_0_high_us)#define config_ir_logic_0_high_us_max time_get_error_max(config_ir_logic_0_high_us)#define config_ir_logic_1_high_us ((uint32_t)1500) #define config_ir_logic_1_high_us_min time_get_error_min(config_ir_logic_1_high_us)#define config_ir_logic_1_high_us_max time_get_error_max(config_ir_logic_1_high_us)3.3 信号发送api
#define ir_h() {gpioe- >bsrr = gpio_pin_0;}#define ir_l() {gpioe- >brr = gpio_pin_0;}void ir_send_signal(uint16_t wave_us,uint16_t high_us){ if (wave_us) { wave_us = round_up(wave_us,config_ir_frequency_us); while (wave_us--) { ir_h(); rt_hw_us_delay(config_ir_delay_us); ir_l(); rt_hw_us_delay(config_ir_delay_us); } } if (high_us) { high_us = round_up(high_us,config_ir_frequency_us); while (high_us--) { rt_hw_us_delay(config_ir_frequency_us); } }}3.4 红外通信指令的定义
3.4.1 指令组成
起始信号+cmd+data+sum
3.4.2 高位先发
3.5 发送指令api
void ir_send_data(uint8_t set_type,uint8_t set_data){ unsigned char i; for (i = 0; i < 8; i++) { if (set_data & 0x80)//先发送高位 { ir_send_signal(config_ir_common_low_us,config_ir_logic_1_high_us); } else { ir_send_signal(config_ir_common_low_us,config_ir_logic_0_high_us); } set_data < instance==tim3) { __hal_rcc_tim3_clk_enable(); __hal_rcc_gpioa_clk_enable(); gpio_initstruct.pin = gpio_pin_6; gpio_initstruct.mode = gpio_mode_input; gpio_initstruct.pull = gpio_nopull; gpio_initstruct.speed = gpio_speed_freq_high; hal_gpio_init(gpioa, &gpio_initstruct); hal_nvic_setpriority(tim3_irqn,1,3); //设置中断优先级,抢占优先级1,子优先级3 hal_nvic_enableirq(tim3_irqn); //开启itm4中断 }}void tim3_irqhandler(void){ rt_interrupt_enter(); hal_tim_irqhandler(&htim3); rt_interrupt_leave(); } enum{ st_none = 0, st_start = 1, st_logic_0, st_logic_1, st_error,};typedef struct { uint8_t type:3;//0-2 uint8_t rising_capture_ok:1;//3 uint8_t start_capture_ok:1;//4-7 uint8_t reserve:3;//4-7}ir_signal_t;typedef struct { union { uint8_t byte; ir_signal_t ir_signal; }val;}status_val_t;volatile status_val_t ir_check = {0};void hal_tim_periodelapsedcallback(tim_handletypedef *htim){ if(htim- >instance==tim3) { static uint16_t count = 0; if (1 == ir_check.val.ir_signal.start_capture_ok) { ir_check.val.ir_signal.rising_capture_ok = 0; if (count >=30) { count = 0; ir_check.val.ir_signal.start_capture_ok = 0; } else { count++; } } } }volatile uint8_t temp_byte = 0;volatile uint8_t byte_length = 0;volatile uint8_t bit_cnt = 0;volatile uint8_t ir_data_buf[3] = {0};void hal_tim_ic_capturecallback(tim_handletypedef *htim) { if (htim- >instance==tim3) { if (hal_gpio_readpin(gpioa, gpio_pin_6)) { tim_reset_capturepolarity(&htim3,tim_channel_1); tim_set_capturepolarity(&htim3,tim_channel_1,tim_icpolarity_falling); __hal_tim_set_counter(&htim3,0); ir_check.val.ir_signal.rising_capture_ok = 1; } else // { uint32_t rising_time = hal_tim_readcapturedvalue(&htim3,tim_channel_1); tim_reset_capturepolarity(&htim3,tim_channel_1); tim_set_capturepolarity(&htim3,tim_channel_1,tim_icpolarity_rising); if (1 == ir_check.val.ir_signal.rising_capture_ok) { if (1 == ir_check.val.ir_signal.start_capture_ok) { if ((rising_time >=config_ir_logic_0_high_us_min) && (rising_time<=config_ir_logic_0_high_us_max)) { temp_byte < =config_ir_logic_1_high_us_min) && (rising_time<=config_ir_logic_1_high_us_max)) { temp_byte < =config_ir_start_high_us_min) && (rising_time<=config_ir_start_high_us_max)) { ir_check.val.ir_signal.start_capture_ok = 1; temp_byte = 0; byte_length = 0; bit_cnt = 0; } } if (8 == bit_cnt) { ir_data_buf[byte_length++] = temp_byte; temp_byte = 0; bit_cnt = 0; } ir_check.val.ir_signal.rising_capture_ok = 0; } }}int main(void){ while(1) { if (3 == byte_length) { uint8_t idx = 0; uint8_t check_sum = 0; for (idx = 0; idx < (length_of_array(ir_data_buf) - 1); idx++) { check_sum += ir_data_buf[idx]; } app_main_printf(trn); if (check_sum == ir_data_buf[byte_length - 1]) { for(idx = 0; idx ir aa 01tx:[aa] [01] [ab] msh >rx:{aa} {01} {ab}
三星新折叠屏手机设计专利曝光采用了向外折叠设计和双弧形显示屏
磁带库的最大存储容量
智能手机小厂的逆袭路:折叠屏手机?
直线模组助力的“工业设计+3D打印”技能竞赛
微软与TomTom携手,将OpenAI大语言模型和Azure云服务融入车载通信
红外通信协议功能调试
小米MIX2、iPhone8最新消息汇总:小米MIX2截胡iPhone8提前一天发布,可网友却担心的不是价格
有源低通滤波器(lpf)工作原理与作用详解
蘑菇车联成为第一家为联合国会议服务的中国自动驾驶公司
英飞凌高性能模拟/数字MEMS麦克风设计
日本发那科:每年可卖出50万台工业机器人
电力虚拟仿真实训系统提供丰富的实操内容,强化员工动手能力
通话质量好的蓝牙耳机有哪些?通话效果好的蓝牙耳机推荐!
基于红外遥控的简单灵敏测试仪电路图
工业物联网的发展在未来将会取代人类吗
德国3月电动车销量近万辆 市场所占份额攀升至2.8%
工信部专家韦乐平表示5G投资大约是4G的1.5倍
协作机器人与传统的机器人相比有什么区别
亿智电子亮相第三届硬核中国芯领袖峰会
若安卓开始收费,华米OV将受大多影响