⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 infrared.c

📁 基于MSP430F14X单片机的红外接收程序
💻 C
字号:
/*****************************************************************************
* 文件名:   Infrared.c
* Copyright (c) 2008 *********武汉理工大学信息工程学院电信系
* 创建人:   王康
* 日 期:   2008.8.14
* 修改人:   王康
* 日 期:
* 描 述:   本文件包含了有关红外解码的所有模块函数,可供外部调用
* 接口定义: 在系统板上,红外接收头的输出接在msp430f149的P1.2口.
* 版 本:   IAR V4.11
******************************************************************************/


/*******************************************************************************
*红外说明: 红外的编码芯片和解码芯片的输出电平刚好相反,在没有接收码时,接收头的
*           输出一直时高电平,开始接收码,首先是9.5ms的低电平和4.5ms的高电平组成的
*           引导码,然后才是数据位."0"和"1"均以0.56ms的低电平开始,它们的高电平的
*           宽度不同,"0"的为0.565ms,"1"为1.685ms.         
*解码方法: 从0.56ms低电平过后,开始延时,0.565ms以后,若读到的为低电平,则说明该位
*           为"0",反之,则为"1".为了可靠起见,延时稍大于0.56ms一点,但应该小于1.12ms,
*	    否则如果该位为"0",读到的已是下一位的高电平,因此取(1.12+0.56)/2=0.84ms
*           最可靠.解码后得到8位系统识别码及其反码,8位数据码及其反码.本程序中的
*           解码主要利用了外部中断和定时计数器定时.
*******************************************************************************/


//头文件
#include "config.h"


/*****************************************************************************
* 文件名:   Infrared_Init
* 输 入:   无
* 输 出:   无
* 功能描述: 本函数为红外接收初始化子函数
* 全局变量: 无 
* 作 者:   王康
* 日 期:   2008.8.14
* 修改人:   王康
* 日 期:
* 版  本:   IAR V4.11
******************************************************************************/
void Infrared_Init(void)
{ 
    IRDIR = 0xfb;                           //P1.2口设置为输入    
    IRIE |= IRDA;                           //使能P1.2口中断
    IRIES |= IRDA;                          //P1.2口为下降沿中断
    IRIFG = 0x00;    
    
    //定时器TA的初始化,TA工作在定时器工作模式,计数模为连续计数模式
    TACTL = TACLR;                          //清除TAR
    TACTL = TASSEL_2 + ID_1;                //时钟源选择SMCLK,并且2分频,4MHz
    TACTL |= MC_2;                          //TA工作在连续计数模式,开启计数
    
    _EINT();                                //打开总中断 
}


/*****************************************************************************
* 文件名:   PORT1_ISR
* 输 入:   无
* 输 出:   无
* 功能描述: 本函数为端口P1的中断函数,因为P1每个口都有中断功能,所以在进入该中断
*           子函数后需要对P1IFG进行判断,从而来确定中断来自那个端口.
* 全局变量: 无 
* 作 者:   王康
* 日 期:   2008.8.14
* 修改人:   王康
* 日 期:   
* 版  本:   IAR V4.11
******************************************************************************/
#pragma vector = PORT1_VECTOR
__interrupt void PORT1_ISR(void)
{
    if((IRIFG & IRDA) == 1)                //红外接收中断子函数
    {
        //此处说明一下static:
        //1.变量会被放在程序的全局存储区中,这样可以在下一次调用的时候还可以保持原来的赋值
        //2.变量用static告知编译器,自己仅仅在变量的作用范围内可见
        //3.若全局变量仅在单个C文件中访问,则可以将这个变量修改为静态全局变量,以降低模块间的耦合度
        //4.若全局变量仅由单个函数访问,则可以将这个变量改为该函数的静态局部变量,以降低模块间的耦合度
        static  uint    time;                   //寄存器TAR时间缓存
        static  uchar   st_flg;                 //开始接收标志位,当接收到引导码后置位
        static  uchar   rcv_bit;                //接收位值缓存
        static  uchar   rcv_val;                //接收的数据值
        static  uchar   byt_num = 0;            //接收的字节的个数       
        static  uchar   bit_num = 0;            //接收的位的个数    
        static  uchar   ir_keyval_buf[4];       //红外键值缓存
        
        TACTL |= MC_0;                          //停TA计数
        time = TAR;                             //将TAR中的值存入time
        IRIFG = 0x00;                           //清IR中断标志
        TACTL |= TACLR;                         //清TAR
        TACTL |= MC_2;                          //开始计数
        
        if(st_flg == 0)                         //若st_flg为0标志还没接收到引导码  
        {
            if((time > 52000) && (time < 56000))//若time=54000,则表示定时时间为13.5ms
            {
                st_flg = 1;                     //表示开始接收引导码
            }                          
        }
        //以下程序开始按位接收数据码,位"0"时长1.125ms,位"1"时长2.25ms
        //1.125ms对应TAR中的值为4500,2.25ms对应TAR中的值为9000.
        else if(st_flg == 1)
        {
            if((time > 4000) && (time < 5000))  //接收的为位"0"           
            {
                rcv_bit = 0x00;
            }
            else if((time > 8500) && (time < 9500)) //接收的为位"1"         
            {
                rcv_bit = 0x80;
            }
            else                                //既不是位"0"又不是位"1",说明接收错误
            {
                st_flg = 0;
                bit_num = 0;
                byt_num = 0;
            }
            
            bit_num++;
            //先接收到的是系统识别码,先接收低位,再接收高位
            if(bit_num < 8)
            {
                rcv_val = rcv_val >> 1;
                rcv_val |= rcv_bit;
            }
           
            if(bit_num == 8)
            {
                bit_num = 0;
                ir_keyval_buf[byt_num] = rcv_val;
                byt_num++;
                if(byt_num == 4)
                {
                    byt_num = 0;
                    st_flg = 0;
                    if((ir_keyval_buf[0] == IRCODE_H) && (ir_keyval_buf[1] == IRCODE_L) && (ir_keyval_buf[2] + ir_keyval_buf[3] == 0xff))
                    {
                        g_IR_KeyFlg = 1;
                        g_IR_KeyVal = ir_keyval_buf[2];
                    }
                }              
            }
        }    
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -