美文网首页程序员
单片机实现秒表计时

单片机实现秒表计时

作者: ERROR505 | 来源:发表于2019-11-10 13:35 被阅读0次

要求:

用stc89c51,数码管,锁存器实现秒表功能

实验仿真图:

1.png

加入两个锁存器使单片机能够分时进行位选和段选,这样做的目的是为了节省单片机的端口数量。P0口控制位选和段选,实现动态数码管的显示,P2口连接了矩阵键盘,可以进行功能的拓展。

注意,关于锁存器和数码管无法正常工作的问题,在图1中P0口接了8个上拉电阻,原因是P0口内部没有上拉电阻或电阻不够,如果不外接一个上拉电阻,P0口有可能只能输出低电平和悬空状态,无法输出高电平,而实验中所选用的数码管是共阴极的数码管,会导致数码管不能工作,如果有类似问题出现,可尝试接上上拉电阻。

接有锁存器的动态数码管显示:

动态显示原理图.png

动态显示电路如图,共8个共阴极数码管,采用两片74LS573进行驱动,74LS573与74LS373都是8D锁存器,只是573引脚排列更易于布线。其引脚功能为:D1-D8为数据输入端;Q1-Q8为数据输出端;LE为数据输入锁存端,LE=1数据输入D锁存器,LE=0数据不能输入D锁存器,即LE下降沿锁存当前输入数据;地址输出允许端,-OE=0输出锁存数据,-OE=1输出高阻。
电路中,U1输出段码a b c d e f g db,控制显示的字形与小数点,U2输出位选码,控制第几个数码管显示。单片机P1.4、P1.5分别连接到U1、U2的LE,P1.3连接U1和U2的-OE。根据硬件电路,动态显示编程时,应:① P1.3=1,U1、U2输出高阻;② P1.4=1,P0口输出段码,P1.4=0,U1锁存输入的段码;③ P1.5=1,P0口输出位选码,P1.5=0,U2锁存输入的位选码;④ P1.3=0,U1、U2同时输出段码和位选码,进行显示,经过一段时间后,再对另一个数码管做同样的操作。

矩阵键盘

矩阵键盘原理图.png

程序源代码

#include"reg51.h"
#include"intrins.h"
#define uchar unsigned  char
#define uint unsigned int
sbit OE = P1^3;
sbit LE1 = P1^4;
sbit LE2 = P1^5;
data uchar h,m,i,s;
uchar code dis_code[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};
uchar code reg[8]={0x80,0x40,0x20,0x10,0x08,0x04,0x02,0x01};
void show();
void delay(uint t){
    uchar i;
    while(t--)
        for(i=0;i<200;i++);
}

void main(){

while(1){
    TMOD=0x01;                  // 设置定时器T0为方式1定时
    TH0=(65536-50000)/256;      // 给T0装入初值
    TL0=(65536-50000)%256;      // 给T0装入初值
    ET0=1;                      // 允许T0中断
    TR0=1;
    EA=1;
    show();
}                       //CPU开中断        
}
void  T0_int(void)  interrupt 1 
  { 
    TH0=(65536-50000)/256;
    TL0=(65536-50000)%256;
    i++;
    if(i==20)                       //1s时间
    { i=0;
      s++; 
    }
    if(s==60)                       //1s时间
    { s=0;
      m++; 
    }
    if(m==60)                       //1s时间
    { m=0;
      h++; 
    }
  }


void show()
{
    uint i;

    for(i=0;i<8;i++)
    {   
           OE = 1;
           LE2 = 1;
           OE = 0;
            P0=~reg[i];
           LE2 = 0;
           OE=1;
           LE1 = 1;
           OE = 0;
            //OE =0;    
        if(i==2||i==5)
        {
        P0=0x40;//发送段码
        delay(4); //间隔一段时间扫描    

        }
        if(h<10)
        {
           if(i==7) 
        {
        P0=dis_code[0];//发送段码
        delay(4); //间隔一段时间扫描    

        }
         if(i==6) 
        {
        P0=dis_code[h];//发送段码
        delay(4); //间隔一段时间扫描    
    
        }

        }
        if(m<10)
        {
           if(i==4) 
        {
        P0=dis_code[0];//发送段码
        delay(4); //间隔一段时间扫描    

        }
         if(i==3) 
        {
        P0=dis_code[m];//发送段码
        delay(4); //间隔一段时间扫描    
    
        }

        }
        if(s<10)
        {
            if(i==1) 
        {
        P0=dis_code[0];//发送段码
        delay(4); //间隔一段时间扫描    
    
        }
         if(i==0) 
        {
        P0=dis_code[s];//发送段码
        delay(4); //间隔一段时间扫描    
    
        }
        }
        if(h>=10)
            {
               if(i==7) 
            {
            P0=dis_code[h/10];//发送段码
            delay(4); //间隔一段时间扫描    
    
            }
             if(i==6) 
            {
            P0=dis_code[h%10];//发送段码
            delay(4); //间隔一段时间扫描    
        
            }
            if(h>=24)h=0;
            }
    if(m>=10)
            {
            if(i==4) 
            {
            P0=dis_code[m/10];//发送段码
            delay(4); //间隔一段时间扫描    
    
            }
            if(i==3) 
            {
            P0=dis_code[m%10];//发送段码
            delay(4); //间隔一段时间扫描    
    
            }
            if(m>60)m=1;
            }
    if(s>=10)
            {
            if(i==1) 
            {
            P0=dis_code[s/10];//发送段码
            delay(4); //间隔一段时间扫描    

            }
            if(i==0) 
            {
            P0=dis_code[s%10];//发送段码
            delay(4); //间隔一段时间扫描    

            }
            if(s>60)s=1;
            }
        //  delay(100);
            OE=0;
        }
    }

注意:如果在仿真实验中数码管无法一起点亮,可能是延时需要改进,延时的总数在300-400之间合适,比如本实验的延时函数中是100个数,那么在外层自定义的数就定在4,共延时400个数,延时函数需要根据实验的不同进行调整。

程序相对简易,没有使用算法,主要思想就是将时、分、秒作为全局变量,在定时器中计时,通过单独的显示函数来显示,主函数只进行中断开关和调用显示函数,所以代码相对易懂,需要注意的是,在定时的过程中,当时间到达最大时需要及时归零,比如计时到达60s是要将秒的全局变量归零,另外,想要做闹钟或者定时器的朋友可以沿用本实验电路和代码,矩阵键盘已连接,只需在代码加入矩阵键盘的操作就能实现想要的功能。

相关文章

  • 单片机实现秒表计时

    要求: 用stc89c51,数码管,锁存器实现秒表功能 实验仿真图: 加入两个锁存器使单片机能够分时进行位选和段选...

  • Protopie进阶教程--动态时钟(中)

    导读秒表——常用的测时工具,从零开始进行计时。本案例中具体实现的秒表,用户点开始后即开始计时,在秒表运行的时候可以...

  • 22 旋转+弹窗

    该案例主要想实现以下功能: (一) (二)旋转功能(重点) 2.1 用到的节点 Timer是秒表计时器,秒表可以倒...

  • 单片机实现秒表,通过一个按键控制秒表的暂停、启动、复位

    最近学习到单片机,老师要求我们用单片机实现一个秒表。在求助了各种网上的资源后发现还是一脸mb,所以决定自己动手,丰...

  • 51单片机实现的秒表

    功能描述 使用6段数码管显示时间 分钟-秒-100毫秒 (十分钟以内,0.1秒一位) 记录8组数据 使用LED灯代...

  • JavaScript3.0作业

    1、实现点击按钮,滚动条走动和百分比走动 2、实现秒表 3、实现文字时钟 5、短信倒计时

  • 前端定时器

    1、实现点击按钮,滚动条走动和百分比走动 2、实现秒表 3、实现文字时钟 5、短信倒计时

  • 不拖延战术启动

    1.启动秒表计时。番茄钟也行。秒表计时功能更方便不用下载App…… 2.话说我在番茄钟上立的倒计时目标没有完成内心...

  • 程序员常用网址

    程序员常用网址 Iconfont-阿里巴巴矢量图标库 在线秒表在线计时器秒表计时器 - 多事通 RxJav...

  • Day7-作业

    滚动条 秒表 文字时间 微信倒计时 classname兼容

网友评论

    本文标题:单片机实现秒表计时

    本文链接:https://www.haomeiwen.com/subject/dcxabctx.html