標(biāo)題: 充電寶時(shí)鐘DIY 附單片機(jī)源程序 [打印本頁]

作者: bxyyhan    時(shí)間: 2020-1-14 21:02
標(biāo)題: 充電寶時(shí)鐘DIY 附單片機(jī)源程序
手里有幾個(gè)買東西送的充電寶,電池都老化了,于是就用充電寶的外殼做了個(gè)電子鐘。使用15單片機(jī)加DS1302,用單片機(jī)推挽直接驅(qū)動(dòng)數(shù)碼管。只用了不幾個(gè)元件。

制作出來的實(shí)物圖如下:


單片機(jī)源程序如下:
  1. ///***使用15W408AS單片機(jī),使用IO口直接驅(qū)動(dòng)共陽數(shù)碼管顯示



  2. #include <STC15F2K.h>
  3. #include <DS1302.h>
  4. #define uchar unsigned char
  5. /********************************************************/
  6. unsigned char code shumg[]={
  7.         0x3F,/*0*/
  8.         0x06,/*1*/
  9.         0x5B,/*2*/
  10.         0x4F,/*3*/
  11.         0x66,/*4*/
  12.         0x6D,/*5*/
  13.         0x7D,/*6*/
  14.         0x07,/*7*/
  15.         0x7F,/*8*/
  16.         0x6F,/*9*/



  17. 0x00};
  18. /********************************************************/                                            

  19. sbit LED1=P1^5;        //時(shí)間指示燈
  20. sbit LED2=P1^6;        //年月指示燈
  21. sbit LED3=P1^7; //日周指示燈
  22. sbit LED4=P1^0;        //冒號(hào)閃爍

  23. sbit S1=P3^0;   //定義按鍵
  24. sbit S2=P3^1;
  25. sbit S3=P3^2;     //切換
  26. sbit S4=P3^3;

  27. sbit DIG1=P3^7; //數(shù)碼管位選
  28. sbit DIG2=P3^6;
  29. sbit DIG3=P3^5;
  30. sbit DIG4=P3^4;

  31. char miao_num;                                   //冒號(hào)標(biāo)志
  32. /********************************************************/
  33. unsigned char Time[]={0,0,0,0};//用來儲(chǔ)存,時(shí)間
  34. unsigned char Dime[]={0,0,0,0};//用來儲(chǔ)存,年月
  35. unsigned char Bime[]={0,0,0,0};//用來儲(chǔ)存,日期
  36. unsigned char flag;                       //鍵盤入口
  37. /********************************************************/
  38. SYSTEMTIME  time1;   
  39. /********************************************************/
  40. void keyscan();                       //按鍵掃描程序
  41. void mao_hao();                                         //冒號(hào)聲明
  42. /********************************************************/
  43. void delay(unsigned char i)

  44.      //延時(shí)子程序  
  45. {
  46.   unsigned char j;
  47.   while((i--)!=0)
  48.   {
  49.     for(j=123;j>0;j--);
  50.   }
  51. }
  52. /********************************************************/
  53. void t0_init()                        //定時(shí)50ms一個(gè)中斷
  54. {
  55.   TMOD=0x11;                                                  //總中斷初始化
  56.   TH0=0x3c;                                          //定時(shí)50ms一個(gè)中斷
  57.   TL0=0xb0;                                          //定時(shí)50ms一個(gè)中斷
  58.   EA=1;                                                                  //開啟總中斷
  59.   ET0=1;                                                       
  60.   TR0=1;                                                          //開啟定時(shí)器0
  61. }
  62. /********************************************************/
  63. unsigned char button_time(n,x,y)        //時(shí)鐘調(diào)整子程序
  64. unsigned char n,x,y;
  65. {
  66. if(S1==0)                                                        //加
  67.   {
  68.   delay(50);
  69. if(S1==0)
  70. {
  71. n++;
  72. if(n==x)
  73.   n=0;
  74. while(S1==0);
  75.    }
  76. }
  77. /********************************************************/
  78. if(S2==0)                                                //減
  79.     {
  80.    delay(50);
  81. if(S2==0)
  82.     {
  83. if(n==0)
  84.    n=y;
  85. else
  86.     n--;                                               
  87.   while(S2==0);
  88.     }
  89. }
  90. return n;                                                   //函數(shù)返回
  91. }
  92. /********************************************************/



  93. void display(shi10,shi1,fen10,fen1)//顯示子程序
  94. {         P2M1 = 0x00; P2M0 = 0xFF; //設(shè)置P3.4-7推挽模式,就不用數(shù)碼管驅(qū)動(dòng)了
  95.          P1M1 = 0x00; P1M0 = 0x01; //P1(00000000B,00000001B)

  96.   DIG1=0;
  97. P2=shumg[shi10];   //顯示時(shí)的十位
  98.   delay(1);                        //延時(shí)
  99. P2=0x00;                        //消隱
  100.   DIG1=1;                         //消隱

  101.   DIG2=0;
  102. P2=shumg[shi1];        //顯示時(shí)的個(gè)位
  103.   delay(1);                        //延時(shí)
  104.   DIG2=1;                        //消隱
  105. P2=0x00;                        //消隱                                                         
  106.   
  107.   DIG3=0;
  108. P2=shumg[fen10];  //顯示分的十位
  109.   delay(1);                        //延時(shí)
  110.   DIG3=1;                        //消隱
  111. P2=0x00;                        //消隱
  112.   
  113.   DIG4=0;
  114. P2=shumg[fen1];        //顯示分的個(gè)位
  115.   delay(1);                        //延時(shí)
  116.   DIG4=1;                        //消隱
  117. P2=0x00;                    //消隱
  118. }
  119. /********************************************************/
  120. void main()                                                        //主程序
  121. {  
  122.    Initial_DS1302();                                 //初始化DS1302這個(gè)時(shí)鐘芯片,   
  123.    t0_init();                                                 //中斷初始化
  124.    while(1)                                                         //大循環(huán)   
  125.    {                                                                 
  126.    mao_hao();                                                 //冒號(hào)初始化
  127.           keyscan();                                         //鍵盤初始化

  128.   DS1302_GetTime(&time1);                       //讀取時(shí)間參數(shù)            
  129.   
  130.   Bime[3]=(time1.Week)%10;                   //把時(shí)的個(gè)位數(shù)據(jù)存入Bime[3]
  131.   Bime[2]=(time1.Week)/10;                         //把時(shí)的個(gè)位數(shù)據(jù)存入Bime[2]
  132.   Bime[1]=(time1.Day)%10;                       //把時(shí)的個(gè)位數(shù)據(jù)存入Bime[1]
  133.   Bime[0]=(time1.Day)/10;                     //把時(shí)的個(gè)位數(shù)據(jù)存入Bime[0]
  134.   
  135.   Dime[3]=(time1.Month)%10;                   //把時(shí)的個(gè)位數(shù)據(jù)存入Dime[3]
  136.   Dime[2]=(time1.Month)/10;                         //把時(shí)的個(gè)位數(shù)據(jù)存入Dime[2]
  137.   Dime[1]=(time1.Year)%10;                   //把時(shí)的個(gè)位數(shù)據(jù)存入Dime[1]
  138.   Dime[0]=(time1.Year)/10;                         //把時(shí)的個(gè)位數(shù)據(jù)存入Dime[0]
  139.   
  140.   Time[3]=(time1.Minute)%10;                 //把分的個(gè)位數(shù)據(jù)存入Time[3]
  141.   Time[2]=(time1.Minute)/10;                 //把分的十位數(shù)據(jù)存入Time[2]
  142.   Time[1]=(time1.Hour)%10;                   //把時(shí)的個(gè)位數(shù)據(jù)存入Time[1]
  143.   Time[0]=(time1.Hour)/10;                         //把時(shí)的十位數(shù)據(jù)存入Time[0]
  144. }
  145. }
  146. /*******************************************************/
  147. void keyscan()                                //按鍵掃描程序
  148. {
  149.     if(S3==0)                                    //切換程序
  150.         {
  151.          delay(50);
  152.         if(S3==0)
  153.            {
  154.            TR0=0;                                                        //有按鍵按下關(guān)閉定時(shí)器0
  155.                 miao_num=0;                                         //冒號(hào)常亮
  156.                  flag++;
  157.                 if(flag>2)                                                //翻頁年月日周按兩次后啟動(dòng)定時(shí)器
  158.                         {
  159.                  flag=0;
  160.                    TR0=1;                                                //啟動(dòng)定時(shí)器0
  161.                         }
  162.                 }
  163.         while(S3==0);
  164.         }
  165. /*******************************************************/
  166.         if(S4==0)                                    //設(shè)置程序
  167.         {
  168.          delay(50);
  169.         if(S4==0)
  170.            {
  171.           TR0=0;                                                        //有按鍵按下關(guān)閉定時(shí)器0
  172.            miao_num=0;                                                //冒號(hào)常亮
  173.                 flag++;                                                       
  174.             if(flag>2)                                                //按兩次后啟動(dòng)定時(shí)器
  175.            {
  176.            TR0=1;                                                        //啟動(dòng)定時(shí)器0
  177.                 }
  178.           if(flag>4)                                                //按四次后關(guān)閉定時(shí)器
  179.            {
  180.            TR0=0;                                                        //關(guān)閉定時(shí)器0
  181.                 miao_num=0;                                                //冒號(hào)常亮
  182.                 }
  183.         if(flag>8)                                                        //顯示多少位和翻頁按八次啟動(dòng)定時(shí)器
  184.                         {
  185.                  flag=0;
  186.                   TR0=1;                                                //啟動(dòng)定時(shí)器0
  187.                         }
  188.                 }
  189.         while(S4==0);
  190.         }
  191. switch(flag)
  192.         {
  193. /*******************************************************/
  194.                        
  195.         case 0:display(Time[0],Time[1],Time[2],Time[3]);                //調(diào)用子函數(shù)display,把存入數(shù)組time的數(shù)據(jù)給顯示出來
  196.                         LED1=0;
  197.                         LED3=1;
  198.                         break;
  199.         case 1:display(Dime[0],Dime[1],Dime[2],Dime[3]);                //調(diào)用子函數(shù)display,把存入數(shù)組Dime的數(shù)據(jù)給顯示出來
  200.                         LED1=1;
  201.                         LED2=0;
  202.                         break;
  203.         case 2:display(Bime[0],Bime[1],Bime[2],Bime[3]);                //調(diào)用子函數(shù)display,把存入數(shù)組Bime的數(shù)據(jù)給顯示出來
  204.                         LED2=1;
  205.                         LED3=0;
  206.                         break;
  207. /*******************************************************/       
  208.         case 3:time1.Hour=button_time(time1.Hour,24,23);                //調(diào)整時(shí)                          
  209.                         DS1302_SetTime(0x84,time1.Hour);
  210.                         display(Time[0],Time[1],10,10);
  211.                         LED1=0;
  212.                         LED3=1;
  213.                         break;

  214.     case 4:time1.Minute=button_time(time1.Minute,60,59);        //調(diào)整分                            
  215.                         DS1302_SetTime(0x82,time1.Minute);
  216.                         display(10,10,Time[2],Time[3]);
  217.                         LED1=0;
  218.                         LED3=1;
  219.                         break;
  220. /*******************************************************/
  221.                
  222.         case 5:time1.Year=button_time(time1.Year,100,99);                //調(diào)整年                            
  223.                         DS1302_SetTime(0x8c,time1.Year);
  224.                         display(Dime[0],Dime[1],10,10);
  225.                         LED1=1;
  226.                         LED2=0;
  227.                         break;
  228.        
  229.         case 6:time1.Month=button_time(time1.Month,13,12);                //調(diào)整月                          
  230.                         DS1302_SetTime(0x88,time1.Month);
  231.                         display(10,10,Dime[2],Dime[3]);
  232.                         LED1=1;
  233.                         LED2=0;
  234.                         break;
  235. /********************************************************/       
  236.                                          
  237.            case 7:time1.Day=button_time(time1.Day,32,31);                        //調(diào)整日
  238.                         DS1302_SetTime(0x86,time1.Day);
  239.                         display(Bime[0],Bime[1],10,10);
  240.                         LED2=1;
  241.                         LED3=0;
  242.                         break;
  243.        
  244.         case 8:time1.Week=button_time(time1.Week,8,7);                        //調(diào)整周
  245.                         DS1302_SetTime(0x8a,time1.Week);
  246.                         display(10,10,Bime[2],Bime[3]);
  247.                         LED2=1;
  248.                         LED3=0;
  249.                         break;
  250.     }
  251. }
  252. /*******************************************************/
  253. void t0_timer() interrupt 1                                //冒號(hào)中斷賦值
  254. {
  255.       TH0=0x3c;
  256.       TL0=0xb0;
  257.       miao_num++;
  258. }
  259. /*******************************************************/
  260. void mao_hao()                                        //冒號(hào)子程序
  261. {
  262. if(miao_num>=20)
  263.    {
  264.    miao_num=0;
  265.    }
  266.    if(miao_num<10)
  267.      LED4=0;
  268.          if(miao_num>=10)
  269.           LED4=1;
  270. }
復(fù)制代碼

所有資料51hei提供下載:
15共陰.rar (31.37 KB, 下載次數(shù): 53)

截圖01.jpg (30.81 KB, 下載次數(shù): 104)

截圖01.jpg

作者: brave_ruan    時(shí)間: 2020-1-15 08:40
不錯(cuò)不錯(cuò)
作者: man1234567    時(shí)間: 2020-1-15 14:44
程序里寫共陽文件名供陰,共陽還是供陰 ?
作者: bxyyhan    時(shí)間: 2020-1-26 13:14
man1234567 發(fā)表于 2020-1-15 14:44
程序里寫共陽文件名供陰,共陽還是供陰 ?

共陰共陽都可以,改一下數(shù)碼管的段碼就行了,手里有什么就用什么,
作者: 趙洋    時(shí)間: 2020-1-26 15:52
man1234567 發(fā)表于 2020-1-15 14:44
程序里寫共陽文件名供陰,共陽還是供陰 ?

自己不會(huì)看嗎
作者: wbwcf13e    時(shí)間: 2020-1-27 08:34
把DS1302換成DS3231就好了,它的精度更高更準(zhǔn)。
作者: bxyyhan    時(shí)間: 2020-1-27 15:54
wbwcf13e 發(fā)表于 2020-1-27 08:34
把DS1302換成DS3231就好了,它的精度更高更準(zhǔn)。

1302便宜,我7分錢一個(gè)買了一堆,精度也可以接受,3231最便宜也得3塊錢。
作者: songxia8013    時(shí)間: 2020-2-13 09:06
缺少電路圖
作者: yan1516    時(shí)間: 2020-2-16 20:07
請(qǐng)問師傅有Keil模擬圖嗎?
作者: ak333    時(shí)間: 2020-4-2 13:15
謝謝分享,確實(shí),要很認(rèn)真找找在哪里改共陽才行,
作者: 太陽黑子1    時(shí)間: 2020-4-2 16:02
還以為是做了個(gè)充電寶呢!
作者: bxyyhan    時(shí)間: 2020-4-3 12:01
yan1516 發(fā)表于 2020-2-16 20:07
請(qǐng)問師傅有Keil模擬圖嗎?

15單片機(jī)沒法仿真,你可以用51單片機(jī)來代替仿真。
作者: bxyyhan    時(shí)間: 2020-4-3 12:06
ak333 發(fā)表于 2020-4-2 13:15
謝謝分享,確實(shí),要很認(rèn)真找找在哪里改共陽才行,

段碼改為共陽的,位碼DIG1~4改成反的,就行了。共陰極DIG=0,共陽極DIG=1,你想是不是這個(gè)道理。
作者: zhangleixbyl    時(shí)間: 2020-12-23 14:54
高手,小白來學(xué)習(xí)看看
作者: gpdt3209    時(shí)間: 2024-1-31 08:48
數(shù)碼管不用限流電阻嗎?
作者: gzgy    時(shí)間: 2024-3-26 08:52
這個(gè)思路不錯(cuò),物盡其用。




歡迎光臨 (http://www.torrancerestoration.com/bbs/) Powered by Discuz! X3.1