微波EDA网,见证研发工程师的成长!
首页 > 研发问答 > 嵌入式设计讨论 > MCU和单片机设计讨论 > 机友帮忙看看这个程序 8位数码管显示时分秒 51的片子

机友帮忙看看这个程序 8位数码管显示时分秒 51的片子

时间:10-02 整理:3721RD 点击:
#include <reg52.h>
#define uint unsigned int
#define uchar unsigned char
uint h=0,m=0,s=0,t0=0,i=0,t1=0;
uchar d[8];                                                                                                                                  //段显示
uchar code n[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0xbf};  //数码管码段
uchar code w[]={0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f};                                          //位扫描
/*************************端口初始化*************************/
void init()
{
        TMOD=0X11;                           //选择定时器1和0,工作方式1,内部控制定时器开关
        TH0=47104/256;                   //定时器0初值高8位   定时10ms
        TL0=47104%256;             //       初值低8位
        TH1=65036/256;                 //定时器1初值
        TL1=65036%256;                 //
        EA=1;                                   //打开总中断
        ET0=1;                              //允许定时器0中断
        ET1=1;
        TR1=1;
        TR0=1;                                     //打开定时器
}
/*************************处理显示数据*************************/
void led_display()
{
        d[0]=n[s%10];                  //显示秒
        d[1]=n[s/10];
        d[2]=n[10];                          //显示"-"
        d[3]=n[m%10];                  //显示分钟
        d[4]=n[m/10];
        d[5]=n[10];                          //显示"-"
        d[6]=n[h%10];                  //显示小时
        d[7]=n[h/10];
}
/*************************数码管扫描*************************/
void scan()
{
        if(t1>10)                                         //数码管扫描 1ms多一次
            {
                        t1=0;
                        for (i=0;i<8;i++)         
                        {
                                P2=w[i];
                                P0=d[i];
                        }
                }
}
/*************************定时器0中断*************************/
void time0() interrupt 1
{
        TH0=47104/256;                   //初值高8位   定时10ms
        TL0=47104%256;             //初值低8位
        t0++;               
}
/*************************定时器1中断*************************/
void time1() interrupt 3
{
        TH1=65036/256;                 
        TL1=65036%256;
        t1++;                        
}
/*************************时间处理*************************/
void time()
{
        if(t0==100)                         //时间进制处理
        {
                t0=0;
                s++;
                if(s==60)
                {
                        s=0;
                        if(m<60)
                        m++;
                        else
                        {
                                m=0;
                                if(h==24)
                                h=0;
                                else
                                h++;
                        }
                }
        }
}
/*************************主程序*************************/
void main()
{
        init();
        while(1)
        {
                time();
                led_display();
                scan();
        }
}
/********************************************************/

这个程序本身思路倒是没什么问题,有一点需要测试的就是    led_display();   scan();这两个函数的运行时间,假设大于20毫秒的话就会出错了,如果定时器0中断了两次还没有进入time() 那么假设上一次检测时99,然后执行显示函数了,20毫秒内没完事儿的话 t0就等于101了  整个程序就出错了  
            

晶振22.1184的,定时整数的话最少应该是5ms吧?

我不知道你现在是什么情况呢 也没说  光说看看

程序有问题 ,调试时 t0 t1 从数值上没问题 ,至于时间 准不准除了下载到片子上 不知道还有什么方法能看。i的值是有问题的  持续是8 偶尔会变化 ,到了片子上估计就是 第8位常亮  其他位微亮了吧

下载到单片机,结果确实是我说的那样 ,为什么呢

数码管发暗 应该是延时不够  如果我不定义一个延时函数 怎么延时呢 在P0=d;P2=w;之后

#include <reg52.h>
#define uint unsigned int
#define uchar unsigned char
uint h=0,m=0,s=0,i=0,t1=0,t0=0;
uchar d[8];                                                                                     //段选
uchar code n[]={0xc0,0xf9,0xa4,0xb0,0x99,
                                0x92,0x82,0xf8,0x80,0x90,0xbf};          //共阳码段:0-9, "-"
uchar code w[]={0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f};//位选
                                          
/*************************端口初始化*************************/
void init()
{
        TMOD=0X11;                           //选择定时器1和0,工作方式1,内部控制定时器开关
        TH0=15536/256;                   //定时器0   50ms 12mhz
        TL0=15536%256;             
        TH1=65526/256;                 //定时器1   10us  12mhz
        TL1=65526%256;       
        EA=1;                                   //打开总中断               
        ET0=1;                              //允许定时器0中断
        ET1=1;
        TR1=1;
        TR0=1;                                     //打开定时器0
}
/*************************定时器0中断*************************/
void time0() interrupt 1
{
        TH0=15536/256;                   //定时50ms         12mhz
        TL0=15536%256;             
        t0++;               
}
/*************************定时器1中断*************************/
void time1() interrupt 3
{
        TH1=65526/256;                 //定时10us 12mhz
        TL1=65526%256;
        t1++;                        
}
/*************************时间处理*************************/
void time()
{
        if(t0==20)                         //时间进制处理
        {
                t0=0;
                s++;
                if(s==60)
                {
                        s=0;
                        if(m<60)
                        m++;
                        else
                        {
                                m=0;
                                if(h==24)
                                h=0;
                                else
                                h++;
                        }
                }
        }
}
/**************************显示处理***************************/
void led_display()
{
        d[0]=n[s%10];                  //显示秒
        d[1]=n[s/10];
        d[2]=n[10];                          //显示"-"
        d[3]=n[m%10];                  //显示分钟
        d[4]=n[m/10];
        d[5]=n[10];                          //显示"-"
        d[6]=n[h%10];                  //显示小时
        d[7]=n[h/10];
}
/*************************数码管扫描*************************/
void scan()
{
        if(t1>200)                                           //2ms扫描一次
            {
                        for (i=0;i<8;i++)         
                        {         
                                t1=0;
                                P0=d[i];
                                P2=w[i];
                                while (t1<100);          //送显一位后延时2ms
                                P2=0xff;                  //关闭显示
                                while (t1<100);          //关闭位选后延时2ms
                        }
                        t1=0;
                }
}
/*************************主程序*************************/
void main()
{
        init();
        while(1)
        {
                time();
                led_display();
                scan();
        }
}
/********************************************************/

已经搞定了,你说的地方确实也挺重要的,后来调试的时候遇到过,感觉数码管还是稍微有那么一点的阴影,不明显,不知道能不能完全消除。

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top