极客工坊

 找回密码
 注册

QQ登录

只需一步,快速开始

查看: 32645|回复: 16

Arduino ATmega328P 裸奔的小钟

[复制链接]
发表于 2014-4-4 12:19:32 | 显示全部楼层 |阅读模式
本帖最后由 弘毅 于 2016-9-7 21:04 编辑

都在极客工坊逛了快半年了,没注册过用户,更没发过帖子.是不是太说不过去了.

昨天注册了, 各位前辈们请拍板砖吧!


花费了近两个小时才焊上





arduino 库 DigSegTime 下载(这是我第一次写 arduino 库)
https://github.com/pamisisi/arduino-DigSegTime/archive/master.zip

(为啥我不能直接上传png的图片, 也不能上链接呢,)


  1. // myClock.ino

  2. /* 4位数码管引脚
  3. 1   a   f     2   3   b
  4. 12 11 10  9   8   7

  5. D4 D5 D6 D7 D8 D9
  6. 2   9 10 11 12 13

  7. 28 27 26 25 24 23
  8. A5 A4 A3 A2 A1 A0

  9. 1   2   3   4   5   6
  10. e   d   dp c   g   4
  11. */

  12. #include <EEPROM.h>
  13. #include <DigSegTime.h>
  14. #include <DS1302.h>
  15. #include <IRremote.h>
  16. #include <OneWire.h>
  17. #include <DallasTemperature.h>

  18. /***************************************************/
  19. /* 数码管引脚 首个参数 true 代表共阳, false 代表共阴      */
  20. /***************************************************/
  21. DigSegTime dst(false, 4,7,8,A0, 5,9,A2,A4,A5,6,A1,A3);

  22. /***************************************************/
  23. /* DS1302引脚                                       */
  24. /***************************************************/
  25. DS1302 rtc(10, 11, 12);

  26. /***************************************************/
  27. /* DS18B20引脚                                      */
  28. /***************************************************/
  29. OneWire oneWire(2);
  30. DallasTemperature sensors(&oneWire);

  31. /***************************************************/
  32. /* IR引脚                                           */
  33. /***************************************************/
  34. IRrecv irrecv(3);
  35. decode_results results;

  36. /***************************************************/
  37. /* 临时变量                                        */
  38. /***************************************************/
  39. // 系统运行时间
  40. unsigned long timer, mils;
  41. // 一秒标记
  42. boolean oneSec;
  43. // 临时的秒从 DS1302 读取 一分钟读取一次 用于刷新时间
  44. uint8_t tmpSec;
  45. // 数码管亮度  &  数码管亮度EEPROM地址
  46. uint8_t dstBrightness = 1, dstBrightness_add = 0;
  47. // 温度
  48. uint8_t temperatures;
  49. // date & time
  50. int rtc_year;
  51. byte rtc_month, rtc_date, rtc_day, rtc_hour, rtc_min, rtc_sec;

  52. // 好复杂的组合菜单 一项伟大的工程
  53. uint8_t menu, clockModel = 1, clockModel_add = 1, setting = 1;
  54. const uint8_t menuShowClock = 0, menuShowTemperature = 1, menuShowSetting = 2;
  55. const uint8_t settingShowModel = 1, settingDstBrightness = 2, settingDSyear =3,
  56. settingDSmonth = 4, settingDSdate = 5, settingDSday = 6, settingDShour = 7,
  57. settingDSmin = 8, settingDSsec = 9;

  58. // 我开机啦
  59. void setup() {
  60.   // Serial.begin(9600);
  61.   // 从 EEPROM 读取亮度
  62.   dstBrightness = EEPROM.read(dstBrightness_add);
  63.   // 如果EEPROM 亮度值大于10 代表着 不是本程序想要的值
  64.   if(dstBrightness > 10){
  65.     // 写个1 再保存吧
  66.     dstBrightness = 1;
  67.     EEPROM.write(dstBrightness_add,dstBrightness);
  68.   }
  69.   // 设置数码管亮度 (1 to 10);
  70.   dst.brightness(dstBrightness);

  71.   // 从 EEPROM 读取时钟模式
  72.   clockModel = EEPROM.read(clockModel_add);
  73.   if(clockModel > 10){
  74.     clockModel = 1;
  75.     EEPROM.write(clockModel_add, clockModel);
  76.   }

  77.   // 读取 DS1302 时间
  78.   Time t =rtc.time();
  79.   //Serial.println(t.yr);

  80.   // 当年为 2000 时,代表着DS1302还没有设置过时间喔 设置本程序的出厂日期吧!
  81.   if(t.yr == 2000){
  82.     rtc.writeProtect(false);                // 写保护 关
  83.     rtc.halt(false);                                // 时间停止 关
  84.     Time t(2014, 3, 7, 00, 38, 00, Time::kWednesday);
  85.     rtc.time(t);
  86.     rtc.writeProtect(true);                        // 写保护 开
  87.   }
  88.   //t =rtc.time();
  89.   //Serial.println(t.yr);

  90.   irrecv.enableIRIn();                        //开启红外
  91.   timer=millis();
  92. }

  93. // 我拼命的干活
  94. void loop() {

  95.   dst.scan();                        // 我拼命的扫描
  96.   scanIR();                        // 没事你可以玩玩遥控器上的扫雷,命中就从此发生

  97.   mils=millis();

  98.   // 你是想要显示时间呢,还是显示度度呢, 还是想要设置我
  99.   switch (menu) {
  100.   case menuShowClock:
  101.     showClock();
  102.     break;
  103.   case menuShowTemperature:
  104.     showTemperature();
  105.     break;
  106.   case menuShowSetting:
  107.     showSetting();
  108.     break;
  109.   }
  110. }

  111. // 时间其时有很多种花样的 1 HH:MM , 2 时间+度度 (交替显示),  3, 只显示分:秒 (用于检验DS1302过快或者快慢)
  112. void showClock() {
  113.   if(mils - timer >= 500) {
  114.     timer = mils;
  115.     oneSec = !oneSec;
  116.     switch (clockModel) {
  117.     case 1:                        // 只有时间
  118.       if(oneSec) {
  119.         if(tmpSec == 0 || tmpSec >= 59){
  120.           Time t =rtc.time();
  121.           tmpSec = t.sec;
  122.           dst.printTime(t.hr, t.min);
  123.         }
  124.         tmpSec++;
  125.         dst.printDp(0);                // 灭掉点点
  126.       }
  127.       else{
  128.         dst.printDp(2);                // 点点亮
  129.       }
  130.       break;
  131.     case 2:                // 时间 + 温度
  132.       if(oneSec) {
  133.         if(tmpSec == 0 || tmpSec > 8){ // 每8秒后显示一下温度
  134.           Time t =rtc.time();
  135.           rtc_hour = t.hr;
  136.           rtc_min = t.min;
  137.           tmpSec = 1;
  138.           //获取温度
  139.           sensors.requestTemperatures();
  140.           temperatures = sensors.getTempCByIndex(0);
  141.           //显示温度
  142.           dst.printTime(temperatures,"C ");
  143.           dst.printDp(1);
  144.         }
  145.         else{
  146.           dst.printTime(rtc_hour, rtc_min);
  147.         }
  148.         dst.printDp(2);
  149.         tmpSec++;
  150.       }
  151.       else{
  152.         dst.printDp(0);
  153.       }
  154.       break;
  155.     case 3:        // MM:SS
  156.       if(oneSec) {
  157.         Time t =rtc.time();
  158.         dst.printTime(t.min, t.sec);
  159.         dst.printDp(0);
  160.       }
  161.       else{
  162.         dst.printDp(2);
  163.       }
  164.       break;

  165.     }
  166.   }
  167. }
  168. // 显示温度 3秒后 自动回到时间模式
  169. void showTemperature() {
  170.   if(mils - timer >= 1000) {
  171.     timer = mils;
  172.     if(tmpSec == 0){
  173.       sensors.requestTemperatures();
  174.       temperatures = sensors.getTempCByIndex(0);
  175.       dst.printHr(temperatures);
  176.       dst.printMin("C ");
  177.       dst.printDp(1);
  178.     }
  179.     tmpSec++;
  180.     if(tmpSec >= 3) {
  181.       menu = menuShowClock;
  182.       tmpSec = 0;
  183.     }

  184.   }
  185. }

  186. // 设置
  187. void showSetting() {
  188.   // 500 ms 时
  189.   if(mils - timer >= 500) {
  190.     timer = mils;
  191.     oneSec = !oneSec;
  192.     // 1秒时
  193.     if(oneSec) {
  194.       switch (setting) {
  195.       case settingShowModel:
  196.         dst.printTime("C-", clockModel);
  197.         break;
  198.       case settingDstBrightness:
  199.         dst.printTime("B-", dstBrightness);
  200.         break;
  201.       case settingDSyear:
  202.         dst.print(rtc_year);
  203.         break;
  204.       case settingDSmonth:
  205.         dst.printTime(rtc_month, rtc_date);
  206.         dst.printDp(1);
  207.         break;
  208.       case settingDSdate:
  209.         dst.printTime(rtc_month, rtc_date);
  210.         dst.printDp(1);
  211.         break;
  212.       case settingDSday:
  213.         dst.printTime("D-", rtc_day);
  214.         dst.printDp(0);
  215.         break;
  216.       case settingDShour:
  217.         dst.printTime(rtc_hour, rtc_min);
  218.         dst.printDp(2);
  219.         break;
  220.       case settingDSmin:
  221.         dst.printTime(rtc_hour, rtc_min);
  222.         dst.printDp(2);
  223.         break;
  224.       case settingDSsec:
  225.         dst.printTime(rtc_min,rtc_sec);
  226.         dst.printDp(3);
  227.         break;
  228.       }
  229.       // 500 ms 时
  230.     }
  231.     else {
  232.       switch (setting) {
  233.       case settingShowModel:
  234.         dst.printTime("C-", "  ");
  235.         break;
  236.       case settingDstBrightness:
  237.         dst.print("B-  ");
  238.         break;
  239.       case settingDSyear:
  240.         dst.printTime("  ", "  ");
  241.         break;
  242.       case settingDSmonth:
  243.         dst.printTime("  ", rtc_date);
  244.         break;
  245.       case settingDSdate:
  246.         dst.printTime(rtc_month, "  ");
  247.         break;
  248.       case settingDSday:
  249.         dst.printTime("D-", "  ");
  250.         break;
  251.       case settingDShour:
  252.         dst.printTime("  ", rtc_min);
  253.         break;
  254.       case settingDSmin:
  255.         dst.printTime(rtc_hour, "  ");
  256.         break;
  257.       case settingDSsec:
  258.         dst.printTime(rtc_min, "  ");
  259.         break;
  260.       }
  261.     }
  262.   }
  263. }

  264. // 红外判断
  265. void scanIR() {
  266.   if (irrecv.decode(&results)) {
  267.     //Serial.println(results.value,HEX);
  268.     switch (results.value) {
  269.     case 0xFF629D:        // CH 进入菜单红外编码
  270.       if(++menu >= 3) menu = 0;
  271.       // 进入调时模式
  272.       if(menu == 2){
  273.         Time t =rtc.time();
  274.         rtc_year = t.yr;
  275.         rtc_month = t.mon;
  276.         rtc_date = t.date;
  277.         rtc_day = t.day;
  278.         rtc_hour = t.hr;
  279.         rtc_min = t.min;
  280.         rtc_sec = t.sec;
  281.       }
  282.       dst.print("    ");
  283.       dst.printDp(0);
  284.       tmpSec = 0;
  285.       break;
  286.     case 0xFF02FD:        // >>| 下一项 红外编码
  287.       switch (menu) {
  288.       case menuShowSetting:
  289.         if(++setting == 10){
  290.           setting = 1;
  291.           menu = 0;
  292.           tmpSec = 0;
  293.           rtc.writeProtect(false);
  294.           rtc.year(rtc_year);
  295.           rtc.month(rtc_month);
  296.           rtc.date(rtc_date);
  297.           rtc.hour(rtc_hour);
  298.           rtc.minutes(rtc_min);
  299.           rtc.seconds(rtc_sec);
  300.           switch (rtc_day) {
  301.           case 1:
  302.             rtc.day(Time::kSunday);
  303.             break;
  304.           case 2:
  305.             rtc.day(Time::kMonday);
  306.             break;
  307.           case 3:
  308.             rtc.day(Time::kTuesday);
  309.             break;
  310.           case 4:
  311.             rtc.day(Time::kWednesday);
  312.             break;
  313.           case 5:
  314.             rtc.day(Time::kThursday);
  315.             break;
  316.           case 6:
  317.             rtc.day(Time::kFriday);
  318.             break;
  319.           case 7:
  320.             rtc.day(Time::kSaturday);
  321.             break;
  322.           }
  323.           rtc.halt(false);
  324.           rtc.writeProtect(true);

  325.         }
  326.         break;
  327.       }
  328.       break;
  329.     case 0xFF22DD:        // |<< 上一项 红外编码
  330.       switch (menu) {
  331.       case menuShowSetting:
  332.         if(--setting == 0) setting = 9;
  333.         break;
  334.       }
  335.       break;

  336.     case 0xFFA857:        // + 红外编码
  337.       switch (menu) {
  338.       case menuShowSetting:
  339.         switch (setting) {
  340.         case settingShowModel:
  341.           clockModel++;
  342.           if(clockModel > 3)
  343.             clockModel = 1;
  344.           EEPROM.write(clockModel_add,clockModel);
  345.           break;
  346.         case settingDstBrightness:
  347.           dstBrightness++;
  348.           if(dstBrightness > 10) {
  349.             dstBrightness = 1;
  350.           }
  351.           dst.brightness(dstBrightness);
  352.           EEPROM.write(dstBrightness_add,dstBrightness);
  353.           break;
  354.         case settingDSyear:
  355.           if(++rtc_year > 2090) rtc_year = 2014;
  356.           break;
  357.         case settingDSmonth:
  358.           if(++rtc_month > 12) rtc_month = 1;
  359.           break;
  360.         case settingDSdate:
  361.           if(++rtc_date > 31) rtc_date = 1;
  362.           break;
  363.         case settingDSday:
  364.           if(++rtc_day > 7) rtc_day = 1;
  365.           break;
  366.         case settingDShour:
  367.           if(++rtc_hour > 23) rtc_hour = 0;
  368.           break;
  369.         case settingDSmin:
  370.           if(++rtc_min > 59) rtc_min = 0;
  371.           break;
  372.         case settingDSsec:
  373.           if(++rtc_sec > 59) rtc_sec = 0;
  374.           break;
  375.         }
  376.         break;
  377.       }
  378.       break;
  379.     case 0xFFE01F:        // - 红外编码
  380.       switch (menu) {
  381.       case menuShowSetting:
  382.         switch (setting) {
  383.         case settingShowModel:
  384.           clockModel--;
  385.           if(clockModel == 0)
  386.             clockModel = 3;
  387.           EEPROM.write(clockModel_add,clockModel);
  388.           break;
  389.         case settingDstBrightness:
  390.           dstBrightness--;
  391.           if(dstBrightness == 0) {
  392.             dstBrightness = 10;
  393.           }
  394.           dst.brightness(dstBrightness);
  395.           EEPROM.write(dstBrightness_add,dstBrightness);
  396.           break;
  397.         case settingDSyear:
  398.           if(--rtc_year < 2014) rtc_year = 2090;
  399.           break;
  400.         case settingDSmonth:
  401.           if(--rtc_month < 1) rtc_month = 12;
  402.           break;
  403.         case settingDSdate:
  404.           if(--rtc_date < 1) rtc_date = 31;
  405.           break;
  406.         case settingDSday:
  407.           if(--rtc_day < 1) rtc_day = 7;
  408.           break;
  409.         case settingDShour:
  410.           if(--rtc_hour == 255) rtc_hour = 23;
  411.           break;
  412.         case settingDSmin:
  413.           if(--rtc_min == 255) rtc_min = 59;
  414.           break;
  415.         case settingDSsec:
  416.           if(--rtc_sec == 255) rtc_sec = 59;
  417.           break;
  418.         }
  419.         break;
  420.       }
  421.       break;
  422.     }
  423.     irrecv.resume(); // Receive the next value
  424.   }
  425. }

复制代码
回复

使用道具 举报

发表于 2014-4-4 15:35:24 | 显示全部楼层
{:soso_e179:}
回复 支持 反对

使用道具 举报

发表于 2014-4-4 15:37:12 | 显示全部楼层
谢谢分享啦。。。。
回复 支持 反对

使用道具 举报

发表于 2014-4-4 16:17:51 | 显示全部楼层
贴片飞线,这手工真心不错。
话说锂电池是充电的吗?充电用的是IC吗
回复 支持 反对

使用道具 举报

发表于 2014-4-4 16:33:12 | 显示全部楼层
代码注释很霸气,可见功底深厚,赞一个。
回复 支持 反对

使用道具 举报

发表于 2014-4-11 14:28:13 | 显示全部楼层
好友创意啊。顶楼主
回复 支持 反对

使用道具 举报

发表于 2014-4-23 10:05:28 | 显示全部楼层
{:soso_e179:}
回复 支持 反对

使用道具 举报

发表于 2014-4-24 12:38:05 | 显示全部楼层
如果能够把焊接过程也拍摄出来,就更棒了!对大家有很大帮助啊!
回复 支持 反对

使用道具 举报

发表于 2014-5-31 20:30:27 | 显示全部楼层
做的很好,能共享下DigSegTime.h库吗?
回复 支持 反对

使用道具 举报

发表于 2014-5-31 20:46:43 | 显示全部楼层
我的编译出错In file included from led_clk.ino:19:
E:\arduino-1.0.1-windows\arduino-1.0.1\libraries\DS1302/DS1302.h:31:22: error: WProgram.h: No such file or directory
led_clk.ino: In function 'void setup()':
led_clk:97: error: 'class DS1302' has no member named 'writeProtect'
led_clk:99: error: 'kWednesday' is not a member of 'Time'
led_clk:101: error: 'class DS1302' has no member named 'writeProtect'
led_clk.ino: In function 'void scanIR()':
led_clk:318: error: 'class DS1302' has no member named 'writeProtect'
led_clk:327: error: 'kSunday' is not a member of 'Time'
led_clk:330: error: 'kMonday' is not a member of 'Time'
led_clk:333: error: 'kTuesday' is not a member of 'Time'
led_clk:336: error: 'kWednesday' is not a member of 'Time'
led_clk:339: error: 'kThursday' is not a member of 'Time'
回复 支持 反对

使用道具 举报

发表于 2014-6-12 21:48:45 | 显示全部楼层
蒂张图是什么软件?
回复 支持 反对

使用道具 举报

发表于 2014-6-21 09:46:39 | 显示全部楼层
没看懂裸奔钟是神马,求科普资料
回复 支持 反对

使用道具 举报

发表于 2014-6-25 22:25:04 | 显示全部楼层
非常不错,感谢;
回复 支持 反对

使用道具 举报

发表于 2014-10-28 14:36:28 | 显示全部楼层
谢谢分享啦。。。。
回复 支持 反对

使用道具 举报

发表于 2014-11-9 13:31:10 | 显示全部楼层
挺好的。也要做一个。
回复 支持 反对

使用道具 举报

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

本版积分规则 需要先绑定手机号

Archiver|联系我们|极客工坊

GMT+8, 2024-4-24 17:05 , Processed in 0.061409 second(s), 29 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2021, Tencent Cloud.

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