• 51单片机学习:红外遥控实验


    实验名称:红外遥控实验
    接线说明:    
    实验现象:下载程序后,数码管上显示数码管上显示红外解码遥控器键值
    注意事项:红外接收头凸起处要与PCB板接口凸起丝印处对应                                                                                  
    ***************************************************************************************/
    #include "public.h"
    #include "smg.h"
    #include "ired.h"


    /*******************************************************************************
    * 函 数 名       : main
    * 函数功能         : 主函数
    * 输    入       : 无
    * 输    出         : 无
    *******************************************************************************/
    void main()
    {    
        u8 ired_buf[3];

        ired_init();//红外初始化

        while(1)
        {                
            ired_buf[0]=gsmg_code[gired_data[2]/16];//将控制码高4位转换为数码管段码
            ired_buf[1]=gsmg_code[gired_data[2]%16];//将控制码低4位转换为数码管段码
            ired_buf[2]=0X76;//显示H的段码
            smg_display(ired_buf,6);    
        }        
    }

    #include "ired.h"

    u8 gired_data[4];//存储4个字节接收码(地址码+地址反码+控制码+控制反码)

    /*******************************************************************************
    * 函 数 名         : ired_init
    * 函数功能           : 红外端口初始化函数,外部中断0配置 
    * 输    入         : 无
    * 输    出         : 无
    *******************************************************************************/
    void ired_init(void)
    {
        IT0=1;    //下降沿触发
        EX0=1;    //打开中断0允许
        EA=1;    //打开总中断
        IRED=1;    //初始化端口
    }

    void ired() interrupt 0    //外部中断0服务函数
    {
        u8 ired_high_time=0;
        u16 time_cnt=0;
        u8 i=0,j=0;

        if(IRED==0)
        {
            time_cnt=1000;
            while((!IRED)&&(time_cnt))//等待引导信号9ms低电平结束,若超过10ms强制退出
            {
                delay_10us(1);//延时约10us
                time_cnt--;
                if(time_cnt==0)return;        
            }
            if(IRED)//引导信号9ms低电平已过,进入4.5ms高电平
            {
                time_cnt=500;
                while(IRED&&time_cnt)//等待引导信号4.5ms高电平结束,若超过5ms强制退出
                {
                    delay_10us(1);
                    time_cnt--;
                    if(time_cnt==0)return;    
                }
                for(i=0;i<4;i++)//循环4次,读取4个字节数据
                {
                    for(j=0;j<8;j++)//循环8次读取每位数据即一个字节
                    {
                        time_cnt=600;
                        while((IRED==0)&&time_cnt)//等待数据1或0前面的0.56ms结束,若超过6ms强制退出
                        {
                            delay_10us(1);
                            time_cnt--;
                            if(time_cnt==0)return;    
                        }
                        time_cnt=20;
                        while(IRED)//等待数据1或0后面的高电平结束,若超过2ms强制退出
                        {
                            delay_10us(10);//约0.1ms
                            ired_high_time++;
                            if(ired_high_time>20)return;    
                        }
                        gired_data[i]>>=1;//先读取的为低位,然后是高位
                        if(ired_high_time>=8)//如果高电平时间大于0.8ms,数据则为1,否则为0
                            gired_data[i]|=0x80;
                        ired_high_time=0;//重新清零,等待下一次计算时间
                    }
                }
            }
            if(gired_data[2]!=~gired_data[3])//校验控制码与反码,错误则返回
            {
                for(i=0;i<4;i++)
                    gired_data[i]=0;
                return;    
            }
        }        
    }

    #include "smg.h"

    //共阴极数码管显示0~F的段码数据
    u8 gsmg_code[17]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,
                    0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};

    /*******************************************************************************
    * 函 数 名       : smg_display
    * 函数功能         : 动态数码管显示
    * 输    入       : dat:要显示的数据
                       pos:从左开始第几个位置开始显示,范围1-8
    * 输    出         : 无
    *******************************************************************************/
    void smg_display(u8 dat[],u8 pos)
    {
        u8 i=0;
        u8 pos_temp=pos-1;

        for(i=pos_temp;i<8;i++)
        {
               switch(i)//位选
            {
                case 0: LSC=1;LSB=1;LSA=1;break;
                case 1: LSC=1;LSB=1;LSA=0;break;
                case 2: LSC=1;LSB=0;LSA=1;break;
                case 3: LSC=1;LSB=0;LSA=0;break;
                case 4: LSC=0;LSB=1;LSA=1;break;
                case 5: LSC=0;LSB=1;LSA=0;break;
                case 6: LSC=0;LSB=0;LSA=1;break;
                case 7: LSC=0;LSB=0;LSA=0;break;
            }
            SMG_A_DP_PORT=dat[i-pos_temp];//传送段选数据
            delay_10us(100);//延时一段时间,等待显示稳定
            SMG_A_DP_PORT=0x00;//消音
        }
    }
     

    #include "public.h"

    /*******************************************************************************
    * 函 数 名       : delay_10us
    * 函数功能         : 延时函数,ten_us=1时,大约延时10us
    * 输    入       : ten_us
    * 输    出         : 无
    *******************************************************************************/
    void delay_10us(u16 ten_us)
    {
        while(ten_us--);    
    }

    /*******************************************************************************
    * 函 数 名       : delay_ms
    * 函数功能         : ms延时函数,ms=1时,大约延时1ms
    * 输    入       : ms:ms延时时间
    * 输    出         : 无
    *******************************************************************************/
    void delay_ms(u16 ms)
    {
        u16 i,j;
        for(i=ms;i>0;i--)
            for(j=110;j>0;j--);
    }

    纷传单片机学习资料放在纷传小程序里了,需要的可以加入圈子有资料百度网盘下载地址及提取码。

  • 相关阅读:
    (完整版)英语常用词组大全(2000词以上)
    使用UiPath和AA构建的解决方案 3. CRM 自动化
    windows mysql安装卸载,多版本mysql方案
    MATLAB车牌是如何精准定位的???!!!【深度好文】
    尚好房 05_二手房管理
    基于 yolov5n6 和tkinker实现的检测模型的可视化界面
    《微信小程序案例8》实现聊天框下部分别人向我发消息
    1.docker的基本使用
    [软件工具][原创]yolov7快速训练助手使用教程傻瓜式训练不需要写代码配置参数
    [Js进阶]bind、call、apply三个方法
  • 原文地址:https://blog.csdn.net/qq_63964231/article/details/126917085