单片机/MCU论坛
直播中

liangyuhc

13年用户 181经验值
擅长:EMC/EMI设计 处理器/DSP 控制/MCU
私信 关注
[文章]

简单电子表

`         最近学习51单片机,自己写了一个简单的电子表程序,但是总觉得还有些问题,是否还有更好的解决方案。由于目前才学到定时器这里,希望大虾能批评指正,通过仿真的时候,发现,有时候按键感觉处于失灵的状态,但是如果按的时间长一点,再松开就不不会出现,请问这应该是什么原因呢?代码如下:

/************************此文件已编译通过***************************************************************/
//1,可实现24小时计时
//2,可以通过按键手动校准当前时间
/******************************************************************************************************/
#include
#define uchar unsigned char
#define uint  unsigned int
***it K1=P3^4;
***it K2=P3^5;
***it K3=P3^6;
***it K4=P3^7;
***it LE1=P2^6;
***it LE2=P2^7;
/*函数声明*************************************************************/
void s_jian_z();
void xian_s();
void delay_xms(uchar);
void key_scan();
void chu_s();
/********************************************************************/
uchar code d_ma[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};
uchar num=0;f_num=0;s_num=0;
uchar num0;
uchar m_shi,m_ge,f_shi,f_ge,s_shi,s_ge;
uint s_f_k1=0;
/*初始化函数*********************************************************/
void chu_s()
{
TMOD=0x10;
EA=1;
ET1=1;
}
/*延时函数*************************************************************/
void delay_xms(uchar xms)
{   uchar i,j;
   for(i=xms;i>0;i--)
      for(j=110;j>0;j--);
}
/*时间附值函数*********************************************************/
void s_jian_z()
{
if( num0==20)  
      {
    num0=0;
       num++;
    }            
      if(num==60)
       {
    num=0;
     f_num++;
     }
     if(f_num==60)
       {
      f_num=0;
      s_num++;
      }
      if(s_num==24)
        s_num=0;
}
/*键盘扫描函数*********************************************************/
void key_scan()
{
   if(K1==0&&s_f_k1==2)    //按下三次k1时间设定完成
       {
      delay_xms(10);
        if(K1==0)
       s_f_k1=0;
    while (!K1);
    }
  if(K1==0&&s_f_k1==1)
    {
   delay_xms(10);
     if(K1==0)
    s_f_k1=2;     //表示k1按下两次 ,可以改变时间的分钟设定新值      
  while(!K1);  
}

if(K1==0)
    {
   delay_xms(10);
     if(K1==0)
    s_f_k1=1;     //表示k1按下一次 ,可以改变时间的小时设定新值     
  while(!K1);  
}
   
   if(s_f_k1==1)  
     {
  if(K2==0)      //表示k1按下之后,按下k2,小时加1
       {
      delay_xms(10);
        if(K2==0)
         {
      s_num++;
         if(s_num==24)
          s_num=0;
    }   
             while(!K2);
        }

      else if (K3==0)   //表示按下k1之后,按下k3,小时减1
      {
            delay_xms(10);
             if(K3==0)
          {
            if(s_num==0)
            s_num=24;
      s_num--;
     }
   
  while(!K3);
      }
      }
   if(s_f_k1==2)
    if(K2==0)     //表示按下k1两次,按下k2分钟加1
       {
      delay_xms(10);
       if(K2==0)
     {
       f_num++;
        if(f_num==60)
         f_num=0;
      while(!K2);
   
      }
     }
      else if (K3==0)    //表示k1按下两次,这次按下k3分钟减1
      {
            delay_xms(10);
             if(K3==0)
          {
      
         if(f_num==0)
           f_num=60;
     f_num--;
     
         while(!K3);
      }
      }

if(K4==0)                //按下k4,启动或者关闭定时器
    {
   delay_xms(10);
     if(K4==0)
    TR1=~TR1;
  while(!K4);
}
}
/*扫描显示函数**********************************************************/
void xian_s( )      
{   
    s_jian_z();
m_shi  = num/10;
    m_ge   =num%10;
f_shi  =f_num/10;
f_ge   =f_num%10;
s_shi  =s_num/10;
s_ge   =s_num%10;
/**间隔点的显示***************************************************************/
LE2=1;
P0=0xdb;
LE2=0;

P0=0xff;
delay_xms(5);
   
LE1=1;
P0=0x80;  
LE1=0;
P0=0xff;
delay_xms(5);

/**小时十位的显示************************************************/  
LE2=1;
P0=0xfe;
LE2=0;
delay_xms(5);
P0=0xff;

  
LE1=1;
P0=d_ma[s_shi];   
LE1=0;
delay_xms(5);
P0=0xff;

/***小时个位的显示***************************************************/   
LE2=1;
P0=0xfd;
LE2=0;
delay_xms(5);
P0=0xff;


LE1=1;
P0=d_ma[s_ge];     
LE1=0;
delay_xms(5);
P0=0xff;

/***分钟十位的显示****************************************************/
    LE2=1;
P0=0xf7;
LE2=0;
delay_xms(5);
P0=0xff;

LE1=1;
P0=d_ma[f_shi];     
LE1=0;
delay_xms(5);
P0=0xff;

/****分钟个位的显示*************************************************/
    LE2=1;
P0=0xef;
LE2=0;
delay_xms(5);
P0=0xff;

LE1=1;
P0=d_ma[f_ge];     
LE1=0;
    delay_xms(5);
P0=0xff;
/***秒十位的显示***********************************************/

   LE2=1;
P0=0xbf;
LE2=0;
delay_xms(5);
P0=0xff;

LE1=1;
P0=d_ma[m_shi];     
LE1=0;
delay_xms(5);
P0=0xff;

/****秒个位的显示****************************************/
    LE2=1;
P0=0x7f;
LE2=0;
delay_xms(5);
    P0=0xff;
LE1=1;
P0=d_ma[m_ge];     
LE1=0;
delay_xms(5);
    P0=0xff;
  
}
/****主函数*******************************************************/
void main()
{  
   chu_s();
   while(1)
   {
   key_scan();   //检测键盘
   if(!s_f_k1)   //当调节时间的时候数码管处于闪烁状态
      xian_s();   //显示内容
   

else
   while(1)
   {
    LE2=1;
    P0=0xff;
    LE2=0;
    delay_xms(200);
    delay_xms(200);
    delay_xms(200);
    delay_xms(200);
    delay_xms(200);
    delay_xms(200);
    xian_s();   //显示内容
    break;
  }

   }   
}
/*中断函数****************50ms中断一次**************************************/
void T1_time() interrupt 3
{
   TH1=0x3c;
   TL1=0xb0;
      num0++;
}

` 仿真图

回帖(12)

442528

2012-8-20 06:53:28
举报

oyl

2012-8-20 07:05:05
{:12:}
举报

翁现健

2012-8-20 09:51:30
因为你的按键程序没有去抖动,所以按键会失灵。你应该用2~10s的时间来去按键抖动,按键程序是
判断按键是否按下——延时8s——再判断按键是否被按下,判断按键是否按下后弹起也一样。
举报

张三

2012-8-20 11:55:01
按键失灵的原因是你的按键扫描调用延时过长。建议把键盘扫描程序同时放到第二个while(1)里面去
举报

lstcspring

2012-8-20 20:20:53
在哪一步失灵的,是哪个按键失灵?晶振是多少,延时程序延时量是多少?看了一下,像2楼分析的原因,不是失灵
举报

刘爱民

2012-8-20 20:25:35
举报

hellohaitong

2012-9-11 20:31:51
举报

sangwoo

2012-11-27 01:07:38
太感谢啦,很好用
举报

莫增星

2012-12-14 19:22:54
举报

管冬明

2012-12-14 19:25:37
举报

黄承伟

2012-12-15 00:25:46
消抖!!!
举报

枫中看落叶

2012-12-15 09:27:23
抖动消除木有,缺憾。
举报

更多回帖

发帖
×
20
完善资料,
赚取积分