2011_11_7单片机(五)

 

今天做了一道动态数码管显示与定时器控制的综合编程题,目的在于复习之前所学的动态数码显示和定时器中断控制原理。

题目:利用动态扫描和定时器1在数码管上显示出从765432开始以1/10秒的速度往下递减直至765398并保持显示此数,与此同时利用定时器0以500MS速度进行流水灯从上至下移动,当数码管上数减到停止时,实验板上流水灯也停止然后全部开始闪烁,3秒后(用T0定时)流水灯全部关闭、数码管上显示出“HELLO”。到此保持住。

 

思路:1.在定时器0中断里设置好流水灯程序;

             2.在定时器1中设计好算数递减(765432递减到765398)程序;

             3.根据定时器1条件终止定时器0、1;

             4.根据题干设标记flag、flag1,分别标记流水灯流动开始到结束,流水灯全部闪烁到结束。

程序如下:

#include<reg52.h>

#include<intrins.h>

 

#define uchar unsigned char

#define uint unsigned long

 

void init();

void delay(uint a);

void display(uint num);

void display1();

 

uchar code table[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0x89,0x86,0xc7,0xc7,0xc0};//共阳

uchar code table_w[]={0x01,0x02,0x04,0x08,0x10,0x20};

 

uint num=765432; 

uchar j=0;

uchar flag=0;

uchar flag1=0;

uchar temp=0xfe;

 

sbit LE=P3^5;

 

uchar tt=0;

uchar t0=0;

 

void main()

{

       init();

       j=0;

       while(1)

       {                         

              if(flag1!=1)

              {

                     display(num);

              }

              else

              {

                     display1();

              }

       }           

}

 

void delay(uint a)

{

       uint i,j;

       for(i=a;i>0;i--)

              for(j=20;j>0;j--);

}

 

void display(uint num)

{

       uchar i=0;

       //uchar bai,shi,ge;

       P2=table_w[j];       //段选开关,负责给当前led灯加高电平(共阳极)

       //i=(i+1)%8;765432

       switch(j)

       {

              case 0:i=num/100000;break;

              case 1:i=num%100000/10000;break;

              case 2:i=num%10000/1000;break;

              case 3:i=num%1000/100;break;

              case 4:i=num%100/10;break;

              case 5:i=num%10;break;

              default:break; 

       }

       LE=1;            //段选加锁存器    

       P0=table[i];//位选开关,负责给led灯显示数字

       LE=0;

       j=j+1;

       if(6==j)

       {

              j=0;

       }

       delay(1);//5ms

}

 

void display1()

{

       uchar i=0;

       //uchar bai,shi,ge;

       P2=table_w[j];       //段选开关,负责给当前led灯加高电平(共阳极)

       //i=(i+1)%8;765432

       switch(j)

       {

              case 0:i=10;break;

              case 1:i=11;break;

              case 2:i=12;break;

              case 3:i=13;break;

              case 4:i=14;break;

              default:break; 

       }

       LE=1;            //段选加锁存器    

       P0=table[i];//位选开关,负责给led灯显示数字

       LE=0;

       j=j+1;

       if(5==j)

       {

              j=0;

       }

       delay(1);

}

 

void init()

{

       //设置定时器50ms中断一次,中断后,需将TH0、TL0置0

       TH0=(65536-50000)/256;     //高8位50ms产生溢出

       TL0=(65536-50000)%256;    //低8位50ms产生溢出

 

       //设置定时器50ms中断一次,中断后,需将TH0、TL0置0

       TH1=(65536-50000)/256;     //高8位50ms产生溢出

       TL1=(65536-50000)%256;    //低8位50ms产生溢出

 

       //设置中断工作方式为模式1(16位自加器)

       TMOD=0x11; //time0、time1

 

       EA=1;                   //开总中断控制开关

       ET0=1;                 //开定时器控制中断开关

       ET1=1;                 //开定时器控制中断开关

 

 

       //TR1=1;               //设置定时器1开启    

       TR0=1;

       TR1=1;

}

 

void timer0()interrupt 1

{

       if(flag!=1)

       {

              if(10==t0)

              {

                     t0=0;

                     P1=temp;

                     temp=_crol_(temp,1);

              }    

       }

       else

       {

              if(t0%4==0)

                     P1=~P1;

              if(t0==60)

              {

                     TR0=0;

                     P1=0xff;

                     flag1=1;

              }           

       }

       t0++;

      

       //将TH0、TH1置0

       TH0=(65536-50000)/256;

       TL0=(65536-50000)%256;          

}

 

void timer1()interrupt 3

{

       if(2==tt)

       {

              tt=0;

              if(765398==num)

              {

                     //将TH0、TH1置0

                     tt=0;

                     flag=1;

                     P1=0xff;

                     TR0=0;

                     TH0=(65536-50000)/256;

                     TL0=(65536-50000)%256;                        

                     TR1=0;

                     TR0=1;

              }

              else

              {

                     num--;                 

              }           

       }

       tt++;      

       //将TH0、TH1置0

       TH1=(65536-50000)/256;

       TL1=(65536-50000)%256;

}

//备注:实际应用时段选位选都需加锁存器,否则容易跳乱码

/*

duan=1;

P0=table_d[i];

duan=0;

wei=1;

P1=table_w[j];

wei=0;

*/

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值