单片机论坛

 找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 328|回复: 1
收起左侧

AVR单片机Atmega16电子时钟程序+仿真,内部定时器实现

[复制链接]
哈哈151- 发表于 2019-5-14 16:34 | 显示全部楼层 |阅读模式
Atmega16电子时钟,内部定时器,有可调闹钟。

仿真原理图如下(proteus仿真工程文件可到本帖附件中下载)
0.png

单片机源程序如下:
  1. #include <iom16v.h>
  2. #include <macros.h>
  3. #define  key_bz    0b00000111
  4. char smg_zx[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d, 0x7d,0x07,0x7f,0x6f};// 全局变量
  5.   
  6. char hour=12;
  7. char min;
  8. char sec;
  9. char nz_hour=12;
  10. char nz_min=1;
  11. char mode=0;
  12. char set;

  13. void delay_ms(unsigned int k)                       
  14. {
  15.     unsigned int i,j;
  16.     for(i=0;i<k;i++)
  17.     {
  18.       for(j=0;j<570;j++);
  19.     }
  20. }
  21. // 用定时器实现定时
  22. void T0_init(void)// 端口初始化函数
  23. {
  24. TIFR=0XFF;
  25. TCCR0=0X0B; //64FENPIN, CTC MODE
  26. TCNT0=0;
  27. OCR0=250;
  28. TIMSK=0X02;

  29. }

  30. void port_init(void)// 端口初始化函数
  31. {
  32.   DDRC  |= 0b11110000;  // PC4 5 OUT PUT
  33.   PORTC |= 0b00111111; //m103 output only

  34. PORTD = 0x00; //  上电关闭数码管, 因为上电电压不稳
  35. DDRD  = 0xff;
  36. DDRB  |= 0b11100000;  // PC5 6 7OUT PUT
  37. }

  38. //call this routine to initialize all peripherals
  39. void init_devices(void)
  40. {
  41. //stop errant interrupts until set up
  42. CLI(); //disable all interrupts
  43. port_init();//smg_zx[0]=1;
  44.   T0_init();
  45. SEI(); //re-enable interrupts
  46. //all peripherals are now initialized
  47. }
  48. //miao=45;

  49. void key (void)
  50. {

  51. if(!(PINC&0X01))
  52. {
  53.    delay_ms(2);
  54.    if(!(PINC&0X01))
  55.    {
  56.     TIMSK=0X00;
  57.     mode++;
  58.         mode%=3;
  59.         set=0;
  60.         if(mode==0)TIMSK=0X02;
  61.         while(!(PINC&0X01));
  62.    }
  63. }


  64. if(!(PINC&0X02))
  65. {
  66.    delay_ms(2);
  67.    if(!(PINC&0X02))
  68.    {
  69.     if(mode==1)
  70.         {
  71.          set++;
  72.          set%=3;
  73.         }
  74.         if(mode==2)
  75.         {
  76.          set++;
  77.          set%=2;
  78.         }
  79.         while(!(PINC&0X02));
  80.    }
  81. }


  82. if(!(PINC&0X04))
  83. {
  84.    delay_ms(2);
  85.    if(!(PINC&0X04))
  86.    {

  87.     if(mode==1)
  88.         {
  89.          if(set==0)
  90.          {
  91.           hour++;
  92.           hour%=24;
  93.          }
  94.          if(set==1)
  95.          {
  96.           min++;
  97.           min%=60;
  98.          }
  99.          if(set==2)
  100.          {
  101.           sec++;
  102.           sec%=60;
  103.          }  

  104.         }
  105.         if(mode==2)
  106.         {
  107.          if(set==0)
  108.          {
  109.           nz_hour++;
  110.           nz_hour%=24;
  111.          }
  112.          if(set==1)
  113.          {
  114.           nz_min++;
  115.           nz_min%=60;
  116.          }
  117.         }
  118.         while(!(PINC&0X04));
  119.    }
  120. }
  121.   
  122. }

  123. //主函数
  124. void main()
  125. {/// 变量声明
  126.    
  127. char zz;  
  128.   // 调用初始化哈数
  129. //port_init();
  130. init_devices();
  131. // 特定代码
  132.    while(1)
  133.    {
  134.    
  135.    
  136. if(mode==0)  
  137. {
  138.    
  139.     PORTD=~smg_zx[hour/10];  // 给5的字形编码  
  140.     PORTB|=1<<PB6;//选中PC6
  141.         delay_ms(2);
  142.         PORTB&=0B00111111;//       
  143.                
  144.    
  145.     PORTD=~smg_zx[hour%10];  // 给5的字形编码  
  146.          PORTB|=1<<PB7;//选中PC7
  147.          delay_ms(2);
  148.      PORTB&=0B00111111;//
  149.    
  150.    
  151.    
  152.      PORTD=~smg_zx[min/10];  // 给5的字形编码  
  153.      PORTC|=1<<PC7;//选中PC7
  154.          delay_ms(2);
  155.          PORTC&=0B00001111;//       
  156.                
  157.    
  158.     PORTD=~smg_zx[min%10];  // 给5的字形编码  
  159.         PORTC|=1<<PC6;//选中PC6

  160.          delay_ms(2);
  161.     PORTC&=0B00001111;//
  162.    
  163.     PORTD=~smg_zx[sec/10];  // 给5的字形编码  
  164.     PORTC|=1<<PC5;//选中PC5
  165.         delay_ms(2);
  166.         PORTC&=0B00001111;//       
  167.                
  168.    
  169.      PORTD=~smg_zx[sec%10];  // 给5的字形编码  
  170.          PORTC|=1<<PC4;//选中PC4
  171.          delay_ms(2);
  172.      PORTC&=0B00001111;//
  173. }

  174. else if(mode==1)  
  175. {
  176.    
  177.     PORTD=~smg_zx[hour/10];  // 给5的字形编码  
  178.     PORTB|=1<<PB6;//选中PC6
  179.         delay_ms(2);
  180.         PORTB&=0B00111111;//       
  181.                
  182.    
  183.     PORTD=~smg_zx[hour%10];  // 给5的字形编码  
  184.         if(set==0)  PORTD&=0x7f;//控制小数点亮
  185.          PORTB|=1<<PB7;//选中PC7
  186.          delay_ms(2);
  187.      PORTB&=0B00111111;//
  188.    
  189.    
  190.    
  191.      PORTD=~smg_zx[min/10];  // 给5的字形编码  
  192.      PORTC|=1<<PC7;//选中PC7
  193.          delay_ms(2);
  194.          PORTC&=0B00001111;//       
  195.                
  196.    
  197.     PORTD=~smg_zx[min%10];  // 给5的字形编码  
  198.          if(set==1)  PORTD&=0x7f;//控制小数点亮
  199.         PORTC|=1<<PC6;//选中PC6

  200.          delay_ms(2);
  201.     PORTC&=0B00001111;//
  202.    
  203.     PORTD=~smg_zx[sec/10];  // 给5的字形编码  
  204.     PORTC|=1<<PC5;//选中PC5
  205.         delay_ms(2);
  206.         PORTC&=0B00001111;//       
  207.                
  208.    
  209.      PORTD=~smg_zx[sec%10];  // 给5的字形编码  
  210.          if(set==2)  PORTD&=0x7f;//控制小数点亮
  211.          PORTC|=1<<PC4;//选中PC4
  212.          delay_ms(2);
  213.      PORTC&=0B00001111;//
  214. }
  215. else if(mode==2)
  216. {

  217.      PORTD=~smg_zx[nz_hour/10];  // 给5的字形编码  
  218.     PORTB|=1<<PB6;//选中PC6
  219.         delay_ms(2);
  220.         PORTB&=0B00111111;//       
  221.                
  222.    
  223.     PORTD=~smg_zx[nz_hour%10];  // 给5的字形编码  
  224.         if(set==0)  PORTD&=0x7f;//控制小数点亮
  225.          PORTB|=1<<PB7;//选中PC7
  226.          delay_ms(2);
  227.      PORTB&=0B00111111;//
  228.    
  229.    
  230.    
  231.      PORTD=~smg_zx[nz_min/10];  // 给5的字形编码  
  232.      PORTC|=1<<PC7;//选中PC7
  233.          delay_ms(2);
  234.          PORTC&=0B00001111;//       
  235.                
  236.    
  237.      PORTD=~smg_zx[nz_min%10];  // 给5的字形编码  
  238.          if(set==1)  PORTD&=0x7f;//控制小数点亮
  239.          PORTC|=1<<PC6;//选中PC6
  240.          delay_ms(2);
  241.      PORTC&=0B00001111;//
  242.    

  243. }


  244.    if((hour==nz_hour)&&(min==nz_min))//闹钟
  245.    {
  246.     if(zz++>20)
  247.         {
  248.      PORTB^=1<<PB5;//选中Pb5
  249.          zz=0;
  250.         }
  251.    }
  252.    else
  253.    PORTB|=1<<PB5;//选中Pb5
  254.        
  255.    
  256.          key ();
  257.        
  258.        
  259.    


  260.    }
  261.   }
  262.    //T0中断服务程序 //  2ms 进入中断
  263.    #pragma interrupt_handler timer0_ocf_isr:20
  264.   void timer0_ocf_isr(void)
  265.   {static int count=0;
  266.    if(++count>=500)
  267.    { count=0;
  268.      sec++;
  269.          if(sec>=60)
  270.          {
  271.          sec=0;
  272.          min++;
  273.           if(min>=60)
  274.          {
  275.          min=0;
  276.          hour++;
  277.          hour%=24;
  278.          }
  279.          }
  280.    }
  281. }
复制代码

所有资料51hei提供下载:
仿真测试.rar (30.95 KB, 下载次数: 5)

评分

参与人数 1黑币 +50 收起 理由
admin + 50 共享资料的黑币奖励!

查看全部评分

回复

使用道具 举报

无效楼层,该帖已经被删除
无效楼层,该帖已经被删除
春风十里吹死你 发表于 2019-5-15 00:29 | 显示全部楼层
正找算开始整这个了,现在出来先看看路数
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|手机版|小黑屋|单片机论坛 |51Hei单片机16群 联系QQ:125739409;技术交流QQ群7344883

Powered by 单片机教程网

快速回复 返回顶部 返回列表