• 蓝桥杯校赛


    2018年“蓝桥杯” 第九届全国软件和信息技术专业人才大赛个人赛
    单片机设计与开发项目
    河南大学民生学院预选赛试题
    “简易摄氏、华氏双显温度计”设计
    设计功能要求:
    1 上电自检,数码管LED全亮,3秒钟后黑屏,然后蜂鸣器响200mS;(25分)
    2 按键S4,显示学号后四位;(15分)
    3 按下S5,测温,即显示当前温度;【该代码段要求逐行注释】
    再次按下S5,将温度显示为华氏温度。(25分)
    4 按下S6,存储当前温度;(15分)
    5 按下S7,显示存储温度;再次按下S7,将温度显示为华氏温度。(20分)
    注:1温度显示保留小数点1位,显示格式位xx.xC 或xx.xF
    2 华氏与摄氏的换算公式位:οF = ℃ × 1.8 + 32
    3 自检阶段,按键无效
    4 完成程序设计任务,并将工程文件保存在学号+姓名命名的文件夹中上交
    拓展要求:断电重启后,存储温度值不丢失
    成绩分两部分:现场测试成绩(占70%)+代码成绩(占30%)

    程序:

    主程序

    #include "stc15f2k60s2.h"
    #include "onewire.h"
    #include "iic.h"
    
                             // 0    1    2    3    4    5    6    7    8    9
    unsigned char code tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,
                       // 灭    c    f    0.   1.   2.  3.    4.   5.   6.   7.   8.   9.
                         0xff,0xc6,0x8e,0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0x00,0x10};
    unsigned char dspbuf[8]={10,10,10,10,10,10,10,10};
    unsigned char dspcom;
    unsigned char key_v,flag0,flag1,flag2;
    int i;
    int temper0,temper1,temper2,temper3;
    
    unsigned char keyscan(void);
    void display(void);
    void delay10ms();    
    void cls_buzz()
    {
        P2=0xa0;
        P0=0x00;
        P2=0x1f;
    }
    void on_led() //led and shumaguan 
    {
        P2=0x80;
        P0=0x00;
        
        P2=0xe0;
        P0=0x00;
        P2=0xc0;
        P0=0xff;
    }
    void delay10ms()        //@11.0592MHz
    {
        unsigned char i, j;
    
        i = 108;
        j = 145;
        do
        {
            while (--j);
        } while (--i);
    }
    
    void main()
    {
        cls_buzz();
        on_led();
        
        AUXR |= 0x80;        //定时器时钟1T模式
        TMOD &= 0xF0;        //设置定时器模式
        TL0 = 0xCD;        //设置定时初值
        TH0 = 0xD4;        //设置定时初值
        TF0 = 0;        //清除TF0标志
    //    TR0 = 1;        //定时器0开始计时
        ET0 = 1;
        
        AUXR |= 0x40;        //定时器时钟1T模式
        TMOD &= 0x0F;        //设置定时器模式
        TL1 = 0xCD;        //设置定时初值
        TH1 = 0xD4;        //设置定时初值
        TF1 = 0;        //清除TF1标志
        TR1 = 1;        //定时器1开始计时
        ET1 = 1;
        EA  = 1;
        while(1)
        {
            while(flag2)
            {
            key_v=keyscan();
            if (key_v==4)
            {
                dspbuf[0]=3;
                dspbuf[1]=0;
                dspbuf[2]=6;
                dspbuf[3]=1;
            }
            if (key_v==5)
            {
                flag0++;
                if(flag0==3)
                {
                    flag0=1;
                }
            }
            if (flag0==1)
            {
                temper0=temper_read()*10;
                dspbuf[4]=temper0/100;
                dspbuf[5]=temper0%100/10+13;
                dspbuf[6]=temper0%100%10;
                dspbuf[7]=11;
            }
            if (flag0==2)
            {
                temper1=(temper_read()*1.8+32)*10;
                dspbuf[4]=temper1/100;
                dspbuf[5]=temper1%100/10+13;
                dspbuf[6]=temper1%100%10;
                dspbuf[7]=12;
            }
            if (key_v==6)
            {
                write_eeprom(0x00,dspbuf[4]);
                write_eeprom(0x01,dspbuf[5]);
                write_eeprom(0x02,dspbuf[6]);
                write_eeprom(0x03,temper_read());
            }
            if (key_v==7)
            {
                flag1++;
                if (flag1==3)
                {
                    flag1=1;
                }
                if (flag1==1)
                {
                    dspbuf[0]=3;
                dspbuf[1]=0;
                dspbuf[2]=6;
                dspbuf[3]=1;
    //                temper2=read_eeprom(0x00)*10;
                    dspbuf[0]=read_eeprom(0x00);
                  dspbuf[1]=read_eeprom(0x01);
                  dspbuf[2]=read_eeprom(0x02);
                  dspbuf[3]=11;
                }
                if (flag1==2)
                {
                    dspbuf[0]=3;
                dspbuf[1]=0;
                dspbuf[2]=6;
                dspbuf[3]=1;
                    temper3=(read_eeprom(0x03)*1.8+32)*10;
                    dspbuf[0]=temper3/100;
                  dspbuf[1]=temper3%100/10+13;
                  dspbuf[2]=temper3%100%10;
                  dspbuf[3]=12;
                }
            }
        }
    }
    }
    
    void timer0(void) interrupt 1
    {
        display();
    }
    void timer1(void) interrupt 3
    {
        i++;
        if (i==3000)
        {
            P2=0x80;
          P0=0xff;
            P2=0x1f;
            
            P2=0xa0;
          P0=0x40;
            P2=0x1f;
            
            TR0=1;
        }
        if (i==3200)
        {
            cls_buzz();
            TR1=0;
            flag2=1;
        }
    }
    void display(void)
    {
        P2=0xe0;
        P0=0xff;
        P2=0x1f;
        
        P0=1<<dspcom;    
        P2=0xc0;
        P2=0x1f;
        
        P2=0xe0;
        P0=tab[dspbuf[dspcom]];
        P2=0x1f;
        if (++dspcom==8)
        {
            dspcom=0;
        }
    }
    unsigned char keyscan(void)
    {
        unsigned char key=0;
        unsigned char GPIO;
        GPIO=P3;
        GPIO&=0x0f;
        if (GPIO!=0x0f)
        {
            delay10ms();
            GPIO=P3;
            GPIO&=0x0f;
            if (GPIO!=0x0f)
            {
                switch(GPIO)
                {
                    case 0x0e:key=7;break;
                    case 0x0d:key=6;break;
                    case 0x0b:key=5;break;
                    case 0x07:key=4;break;
                    default:break;
                }
                while(GPIO!=0x0f)
                {
                    GPIO=P3;
                GPIO&=0x0f;
                }
            }
        }
        return key;
    }

    IIC模块

    /*
      程序说明: IIC总线驱动程序
      软件环境: Keil uVision 4.10 
      硬件环境: CT107单片机综合实训平台(12MHz)
      日    期: 2011-8-9
    */
    
    #include "iic.h"
    
    //总线启动条件
    void IIC_Start(void)
    {
        SDA = 1;
        SCL = 1;
        somenop;
        SDA = 0;
        somenop;
        SCL = 0;    
    }
    
    //总线停止条件
    void IIC_Stop(void)
    {
        SDA = 0;
        SCL = 1;
        somenop;
        SDA = 1;
    }
    
    //应答位控制
    void IIC_Ack(unsigned char ackbit)
    {
        if(ackbit) 
        {    
            SDA = 0;
        }
        else 
        {
            SDA = 1;
        }
        somenop;
        SCL = 1;
        somenop;
        SCL = 0;
        SDA = 1; 
        somenop;
    }
    
    //等待应答
    bit IIC_WaitAck(void)
    {
        SDA = 1;
        somenop;
        SCL = 1;
        somenop;
        if(SDA)    
        {   
            SCL = 0;
            IIC_Stop();
            return 0;
        }
        else  
        { 
            SCL = 0;
            return 1;
        }
    }
    
    //通过I2C总线发送数据
    void IIC_SendByte(unsigned char byt)
    {
        unsigned char i;
        for(i=0;i<8;i++)
        {   
            if(byt&0x80) 
            {    
                SDA = 1;
            }
            else 
            {
                SDA = 0;
            }
            somenop;
            SCL = 1;
            byt <<= 1;
            somenop;
            SCL = 0;
        }
    }
    
    //从I2C总线上接收数据
    unsigned char IIC_RecByte(void)
    {
        unsigned char da;
        unsigned char i;
        
        for(i=0;i<8;i++)
        {   
            SCL = 1;
            somenop;
            da <<= 1;
            if(SDA) 
            da |= 0x01;
            SCL = 0;
            somenop;
        }
        return da;
    }
    
    
    //向EEPROM里写数据(地址)/
    void write_eeprom(unsigned char add,unsigned char date)
    {
        
        IIC_Start();
        IIC_SendByte(0xa0);//发送方式字 1010 0000 激活该器件写操作
        IIC_WaitAck();
        IIC_SendByte(add);
        IIC_WaitAck();
        IIC_SendByte(date);
        IIC_WaitAck();
        IIC_Stop();
        delay10ms();
    }
    //从EEPROM里读数据(地址)/
    unsigned char read_eeprom(unsigned char add)
    {
        unsigned char date;
        IIC_Start();
        IIC_SendByte(0xa0);//发送方式字 1010 0000 激活该器件写操作
        IIC_WaitAck();
        IIC_SendByte(add);
        IIC_WaitAck();
        IIC_Start();
        IIC_SendByte(0xa1);//发送方式字 1010 0001 激活该器件读操作
        IIC_WaitAck();
        date=IIC_RecByte();
        IIC_Ack(0);
        IIC_Stop();
        return date;
    }
  • 相关阅读:
    OCP-1Z0-053-V12.02-367题
    OCP-1Z0-053-V12.02-16题
    OCP-1Z0-053-V12.02-21题
    OCP-1Z0-053-V12.02-368题
    OCP-1Z0-053-V12.02-356题
    VC++ 线程池(h)
    OCP-1Z0-053-V12.02-361题
    OCP-1Z0-053-V12.02-355题
    OCP-1Z0-053-V12.02-289题
    OCP-1Z0-053-V12.02-100题
  • 原文地址:https://www.cnblogs.com/liushuizs/p/10334285.html
Copyright © 2020-2023  润新知