stm32f103c6t6 红外接收@TOC
前言
想要找份stm32f103c6t6红外接收代码,结果全是定时器中断,c6t6用不了的tim4,tim5,终于找到一个博主用外部中断解决了这个问题。感谢博主,好人,原文链接https://blog.csdn.net/jxnu_xiaobing/article/details/8693340
一、外部中断代码配置
代码如下:
#include "stm32f10x.h"
#include "stdio.h"
/*-------------------------协议--------------------------
开始拉低9ms,接着是一个4.5ms的高脉冲,通知器件开始传送数据了
接着是发送4个8位二进制码,第一二个是遥控识别码(REMOTE_ID),第一个为
正码(0),第二个为反码(255),接着两个数据是键值,第一个为正码
第二个为反码.发送完后40ms,遥控再发送一个9ms低,2ms高的脉冲,
表示按键的次数,出现一次则证明只按下了一次,如果出现多次,则可
以认为是持续按下该键.
---------------------------------------------------------*/
#include "remote.h"
#include "delay.h"
u32 Remote_Odr=0; //命令暂存处
u8 Remote_Cnt=0; //按键次数,此次按下键的次数
u8 Remote_Rdy=0; //红外接收到数据
/************************初始化红外接收引脚的设置**********************************/
/******************选择PA1脚作为外部中断,用于红外输入*****************************/
void Remote_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure; //GPIO
NVIC_InitTypeDef NVIC_InitStructure; //中断
EXTI_InitTypeDef EXTI_InitStructure; //外部中断线
RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOA|RCC_APB2Periph_AFIO, ENABLE );
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU ; //注意需要上拉输入
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource1); //选择PA1所在的GPIO管脚用作外部中断线路EXIT1
EXTI_InitStructure.EXTI_Line = EXTI_Line1; //外部线路EXIT1
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; //设外外部中断模式:EXTI线路为中断请求 EXTI_Mode_Event ;//设置 EXTI线路为事件请求
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling; //外部中断触发沿选择:设置输入线路下降沿为中断请求
EXTI_InitStructure.EXTI_LineCmd = ENABLE; //使能外部中断新状态
EXTI_Init(&EXTI_InitStructure); //根据EXTI_InitStruct中指定的参数初始化外设EXTI寄存器
NVIC_InitStructure.NVIC_IRQChannel = EXTI1_IRQn; //使能按键所在的外部中断通道
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2; //先占优先级2级
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //从优先级1级
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能外部中断通道
NVIC_Init(&NVIC_InitStructure); //根据NVIC_InitStruct中指定的参数初始化外设NVIC寄存器
}
/*功能 :检测脉冲宽度*****************************************/
/*说明 :最长脉宽为5ms
/*返回值: t代表脉宽为t*20us(T=1~250); *************************/
u8 Pulse_Width_Check(void)
{
u8 t=0;
while(RDATA)
{
t++;
delay_us(20);
if(t==250)
return t; //超时溢出
}
return t;
}
/*功能 : 中断函数*****************************************/
/*说明 :检测是否有中断
/*返回值: 无************************************************/
void EXTI1_IRQHandler(void)
{
u8 res=0;
u8 OK=0;
u8 RODATA=0;
EXTI_ClearITPendingBit(EXTI_Line1); //清除EXTI1线路挂起位
while(1)
{
if(RDATA)//有高脉冲出现
{
res=Pulse_Width_Check(); //获得此次高脉冲宽度
if(res==250)break; //非有用信号
if(res>=200&&res<250)OK=1; //获得前导位(4.5ms)
else if(res>=85&&res<200) //按键次数加一(2ms)
{
Remote_Rdy=1; //接受到数据
Remote_Cnt++; //按键次数增加
break;
}
else if(res>=50&&res<85)RODATA=1;//1.5ms
else if(res>=10&&res<50)RODATA=0;//500us
if(OK)
{
Remote_Odr<<=1;
Remote_Odr+=RODATA; //这里得到的是一个32位的码值, //地址码、地址反码、控制码、控制反码
Remote_Cnt=0; //按键次数清零
}
}
}
}
/*功能 : 处理红外键盘*****************************************/
/*说明 :无
/*返回值: 键值************************************************/
u8 Remote_Process(void)
{
u8 t1,t2;
t1 = ((Remote_Odr >> 8)&(0xff)); //得到控制码
t2=(Remote_Odr >> 0)&0xff; //得到控制反码
Remote_Rdy=0; //清除标记
// if(t1==(u8)~t2&&t1==REMOTE_ID) //检验遥控识别码(ID)及地址
// {
// t1=Remote_Odr>>8;
// t2=Remote_Odr;
// }
if(t1==(u8)~t2)
return t1; //处理键值
return 0xff;
}
2.主函数
代码如下:
#include "led.h"
#include "delay.h"
#include "sys.h"
#include "usart.h"
#include "lcd.h"
#include "remote.h"
//ALIENTEK Mini STM32开发板范例代码22
//红外遥控实验
//技术支持:www.openedv.com
//广州市星翼电子科技有限公司
int main(void)
{
u8 key;
u8 t=0;
u8 *str=0;
delay_init(); //延时函数初始�
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);// 设置中断优先级分组2
uart_init(115200); //串口初始化为9600
LED_Init(); //初始化与LED连接的硬件接口
//LCD_Init();
Remote_Init(); //红外接收初始化
printf("START\r\n");
//LCD_ShowString(60,50,200,16,16,"Mini STM32");
//LCD_ShowString(60,70,200,16,16,"REMOTE TEST");
//LCD_ShowString(60,90,200,16,16,"ATOM@ALIENTEK");
//LCD_ShowString(60,110,200,16,16,"2014/3/12");
//LCD_ShowString(60,130,200,16,16,"KEYVAL:");
//LCD_ShowString(60,150,200,16,16,"KEYCNT:");
//LCD_ShowString(60,170,200,16,16,"SYMBOL:");
while(1)
{
if(Remote_Rdy)
{
key=Remote_Process();
//if(key)
//{
//LCD_ShowNum(116,130,key,3,16); //显示键值
//LCD_ShowNum(116,150,RmtCnt,3,16); //显示按键次数
switch(key)
{
case 0:str="ERROR";break;
case 162:str="POWER";break;
case 98:str="UP";break;
case 2:str="PLAY";break;
case 226:str="ALIENTEK";break;
case 194:str="RIGHT";break;
case 34:str="LEFT";break;
case 224:str="VOL-";break;
case 168:str="DOWN";break;
case 144:str="VOL+";break;
case 104:str="1";break;
case 152:str="2";break;
case 176:str="3";break;
case 48:str="4";break;
case 24:str="5";break;
case 122:str="6";break;
case 16:str="7";break;
case 56:str="8";break;
case 90:str="9";break;
case 66:str="0";break;
case 82:str="DELETE";break;
}
printf("=== %d\n",key);
printf("=== %s\n",str);
//LCD_Fill(116,170,116+8*8,170+16,WHITE); //清楚之前的显示
//LCD_ShowString(116,170,200,16,16,str); //显示SYMBOL
//}
}else delay_ms(10);
t++;
if(t==20)
{
t=0;
LED0=!LED0;
}
}
}
工程链接:https://download.csdn.net/download/weixin_43653424/89561362
总结
提示:这里对文章进行总结:
例如:以上就是今天要讲的内容,本文仅仅简单介绍了pandas的使用,而pandas提供了大量能使我们快速便捷地处理数据的函数和方法。