找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 4060|回复: 2
打印 上一主题 下一主题
收起左侧

骨牌时钟制作

[复制链接]
跳转到指定楼层
楼主
视频1——简介:http://v.youku.com/v_show/id_XNDA5NTg4MjA4.html

视频2——工作介绍:http://v.youku.com/v_show/id_XNDA5NTk1MTg0.html
视频3——原理解说:http://v.youku.com/v_show/id_XNDA5NjI1MTIw.html
视频里会发现灯珠有闪动,那是程序扫描频率问题,用肉眼直接看是很完美的,不会闪动!
原理图:




程序等资料包: 骨牌时钟.zip (75.47 KB, 下载次数: 12)
2
年前,无意中进了51hei网站里面的东西给我留下了深刻的印象,那时候才开始学习单片机,看到里面的立方体之后,震撼之余,也想自己什么时候可以发个作品在这个网站里。可惜自己学艺不精,2年来只能是看网站里的作品,后来,终于觉得自己在专业课上有了点进步,做了个led金字塔。联系到站长之后,站长很乐意上传这些原创性的作品,也给我了很多鼓励。
因为面临毕业、参加各种比赛,这次上传作品距离上次做金字塔间隔很久了,不过我没有偷懒,一直在挤时间设计属于自己的立方体(之前也做过,金字塔就是改版),但这个立方体我想做成终极版的,即便是不懂单片机编程的朋友,都可以编辑动画,现在也已经有了很大的进展,估计在6月底,就可以和大家见面了!
这次的作品骨牌时钟,灵感源于爱折腾网站,里面有个国外的骨牌时钟,我那时候看了觉得很有意思,自己和工作室的朋友折腾了几天,也搞了出来。下面,我就毫无保留的把制作过程、程序、原理图拿出来供大家参考,希望读者能指出不足之处,
在开始之前,我想说,希望各位读者尊重原创,我所做的原创性、开源性的作品会上传到爱折腾网,因为我觉得这个网站干净,不带广告,非常适合做大家DIY交流的平台。如果您觉得我的作品好,觉得这个网站好,请把连接发给您的朋友,让更多的人欣赏里面妙趣横生的作品,但请不要不道德的转载,希望转载的读者,注明首发网站及作者。
作为单片机的初学者,最大的困难就是找资料,网络上很多资料都是不完整的,特别是程序。我们工作室,立志做开源设计,毫无保留,我相信,我们工作室第一个做开源,会吸引更多的人一起来开源,大家会共同进步!希望在大家共同的努力下,爱折腾网站上会出现更多有趣、开源资料的作品!
骨牌时钟图片效果:



当前显示的时间为  1229



显示时间为   626








显示时间为  333



显示时间为  222
这个家伙可是我们工作室的人纯手工制作的,这也是重庆市盛群杯单片机设计竞赛的复赛作品,虽然在最终的评审后没有取得奖项,但是得到了其他高校的赞赏和认可,算是有个安慰奖吧!
个人对DIY的理解:我觉得DIY就是一种折腾,折腾我们生活中一切可以折腾的东西。我呢,因为是学过单片机的,也喜欢动手制作,就把单片机技术和DIY结合起来,让单片机学习不在变的枯燥、呆板,而是让它改善我们的生活,就像爱折腾网站里说的那样:“让生活因折腾而与众不同”,如果你爱生活,就请和我一起来折腾这个时钟吧!
我这里粗略的说一下这个时钟的显示原理,和外壳设计方法,详细请结合视频。
大家在视频里看到的骨牌,其实就是用ABS板围成的,再盖上玻璃板或者塑料板(透明就可以啦)。至于这个颜色,就是木纹纸了,建材市场很多卖的,十几块一大张,各种颜色、纹理都有的,大家根据自己的喜好自行选择,现在图片和视频里白色的边框那是ABS板的颜色,朋友们也可以把这部分贴上木纹纸,个人觉得,和骨牌面一样的颜色比较好。
驱动部分:



原理图中我是用的ls245,我建议大家用HC系列的,视频演示的时候,我就全换成了HC系列的245HC系列发热小,功耗小,价格便宜,只不过一定要记得在输入上加上拉电阻10K,这样才能和TTL兼容,有朋友和我说hc系列的不稳定,我针对这个也是做了实验的,结论就是加了上拉电阻后,效果和ls系列完全一样!24519脚(使能端)就作为位码的选通脚,所有输入(段码)都是并联在一起的。原理图我画的比较详细了,请用proteus7.5以上版本打开。
DS1302部分:
这个我想,接触过一段时间单片机的朋友都会有所了解,DS1302是最常见的时钟芯片之一,其工作原理图我是画好了的,这里要说一下,为了保证1302可以稳定的工作,567脚一定要加10K上拉电阻,最好把晶振的金属壳部分接地。这样才能保证DS1302工作的持久稳定。希望大家不要在这个环节偷懒。
三显示原理:
骨牌时钟显示小时和分钟,最左边的显示小时(12小时制),中间的显示分钟的十位(0——5,其中0时不显示),右边的显示分钟的各位(0——9,其中0时不显示)。每个骨牌由上下两部分组成,上下两部分原理相同(参考原理图),只是查表的标值不一样,不管是左中右那个骨牌,都是先选中上面,再选中下面进行查表显示,等于是一个6位数码管,具体的看程序IO设置就可以了。大家看了原理图就知道,其实也是个数码管,只不过形状和传统的不一样,这也意味着表值不一样的,我已经做好了表值在程序里,大家自行参考。
发光器材选择
现在我选用的是8MM的高亮发光二极管,因为做的比较大。现在都强调低碳嘛,我希望大家做小的,这样就用一般的5MM二极管就可以了,根据实际情况缩放比例,我这有个做好的,就是试验版本,用的就是5mm发光二极管,现在把图拍下来,给大家做个参考:

这个我是没做外壳的,只有显示电路,主要是用来测试程序和硬件的。大家可以根据这个尺寸来设计自己的。细心的朋友可以发现,中间的显示部分不需要焊接那么多的灯珠






,但是考虑到以后可能需要显示日期、温度等扩展功能,就在大的制作上把所有灯珠就焊接了,各位朋友可以根据自己的实际功能情况选择灯珠的数量。
底板选择
视频和图片里的呢,都是真材实料做的,底板用的是木板,尺寸为80cmX60cm。之所以看不到线,是因为我们在每个骨牌后面都是挖了线槽的(没电锯的朋友就苦恼了),线就像我们家里装修一样,走的都是内线,这个还是很费时间和精力的,如果有朋友想做这么大的,那就不要怕幸苦,如果做小型的,直接焊接万能板就可以了,不费什么事情,就是跳线而已。个人觉得呢,我们应该不怕折腾,我鼓励大家都做大型的,即便是做大了,也可以用5mm的二极管,选择那种可以投射出光圈的就可以了,这样只要设置好面板与二极管的距离,就可以改变红点的大小,因为8mm不仅价格贵了,也不节能。不过,也不是说做小的就不行,觉得做个精简版的,放在书桌上,也还是蛮不错的。
边框
我用的是2mmABS板,很好用,弯成转角后,直角的木板或塑料。固定,其实呢,还是1mmABS板好用,我们当时是没怎么注意,赶时间了,建议大家用1mm的,白色的比较便宜。每个骨牌的尺寸为36cmX18cm。详细的制作方案大家请参考看视频。
控制电路:
追求的完美的朋友可以不必用40p单片机,用28p的就够了,STC公司的芯片程序都是兼容的,价格便宜,下载方式也都兼容,不二之选哦!不管做大做小,元件的布局都很重要,因为我们还有外壳的,所以说,布局不好,导致太多的跳线之类的,势必影响外壳的安装,希望大家在焊接直接多花心思布局电路,我的不一定是最佳方案,我也期待网友们做出更好的布局,给我参考!有条件的可以做PCB板子,我这次主要是为了给大家做视频演示,用的是杜邦线直插(这样也方便初期的程序调试),最后肯定是要用焊锡拖焊到一起的。
程序(请用keil  4版本)
这次的程序是c语言的,我对c语言不是很了解,这个程序是工作室别的朋友写的,而且是用在其他地方的程序,我只是拿来改了改,肯定有不足之处,

主程序源程序:
  1. #include"MAIN.h"
  2. #include"DS1302.h"
  3. #include"DISPLED.h"
  4. //****制作显示数据****//
  5. uint8 mek_buf[4];
  6. //制作显示数据(正常)
  7. uint8 led_buf[4];
  8. //制作显示数据(修改时钟)
  9. uint8 timer_buf[4];
  10. //数据写入DS1302缓存数组
  11. uint8 tempsbuf[5] = {0,0,0,0,0};
  12. //按键手动修改时钟标志位
  13. bit faneg = 0;
  14. //按键手动修改时钟位选
  15. uint8 mak = 0;
  16. //统一修改时间数组
  17. uint8 tempfen = 0,tempshi = 0;
  18. //********************************************************************
  19. //* 名称  : void delay_key()
  20. //* 功能  : 按键消抖延时
  21. //* 输入  :        无
  22. //* 返回值: 无
  23. //***********************************************************************
  24. void delay_key()
  25. {
  26.         uint8 c = 200;
  27.         while(--c);       
  28. }
  29. //********************************************************************
  30. //* 名称  : mek_led
  31. //* 功能  : 制作正常显示数据
  32. //* 输入  :        无
  33. //* 返回值: 无
  34. //***********************************************************************
  35. void mek_led()
  36. {       
  37.         if(1 == faneg)    //主机
  38.         {
  39.                 timer_buf[0] = tempshi/10;
  40.                 timer_buf[1] = tempshi%10;
  41.                 timer_buf[2] = tempfen/10;
  42.                 timer_buf[3] = tempfen%10;                         
  43.         }
  44.         else if(0 == faneg)    //正常
  45.         {
  46.                 led_buf[0] = mek_buf[2]/10;
  47.                 led_buf[1] = mek_buf[2]%10;
  48.                 led_buf[2] = mek_buf[1]/10;
  49.                 led_buf[3] = mek_buf[1]%10;
  50.                 led_buf[4] = mek_buf[0]/10;
  51.                 led_buf[5] = mek_buf[0]%10;       
  52.         }
  53. }
  54. //********************************************************************
  55. //* 名称  : void key_refresh()
  56. //* 功能  : 功能选择(只包含所有分机同时修改)
  57. //* 输入  :        无
  58. //* 返回值: 无
  59. //***********************************************************************
  60. void key_refresh()
  61. {
  62.         if(!keydin1)       
  63.         {
  64.                 delay_key();
  65.                 if(!keydin1)
  66.                 {
  67.                         write_ds1302(0X80,0X80);    //停止DS1302计时
  68.                         faneg = 1;                                    //标志位置1
  69.                         mak = 1;                                        //选中第一位
  70.                 }       
  71.         }
  72.         while((!keydin1));       
  73. }
  74. //********************************************************************
  75. //* 名称  : void key_Modify()
  76. //* 功能  : 按键手动修改时间
  77. //* 输入  :        无
  78. //* 返回值: 无
  79. //***********************************************************************
  80. void key_Modify()
  81. {       
  82.         tempshi = 0;
  83.         tempfen = 0;
  84.         while(1)
  85.         {
  86.                 mek_led();                                                 //制作显示数据
  87.                 display_led(timer_buf);                     //显示按键修改预存时间
  88.                 if(mak > 2){mak = 1;}
  89.                 if(!keydin1)
  90.                 {
  91.                         delay_key();
  92.                         if(!keydin1)
  93.                         {
  94.                                 mak++;
  95.                                 while(!keydin1);       
  96.                         }       
  97.                 }
  98.                
  99.                 if(1 == mak)
  100.                 {
  101.                         if(!keydin2)
  102.                         {
  103.                                 delay_key();
  104.                                 if(!keydin2)
  105.                                 {
  106.                                         if(tempshi > 23)
  107.                                         {
  108.                                                 tempshi = 0;
  109.                                         }
  110.                                         else
  111.                                         {
  112.                                                 tempshi++;               
  113.                                         }
  114.                                 }       
  115.                         }       
  116.                         if(!keydin3)
  117.                         {
  118.                                 delay_key();
  119.                                 if(!keydin3)
  120.                                 {
  121.                                         if(tempshi < 0)
  122.                                         {
  123.                                                 tempshi = 23;
  124.                                         }
  125.                                         else
  126.                                         {
  127.                                                 tempshi--;               
  128.                                         }
  129.                                 }       
  130.                         }       
  131.                         while((!keydin2) || (!keydin3));
  132.                 }
  133.                
  134.                 if(2 == mak)
  135.                 {
  136.                         if(!keydin2)
  137.                         {
  138.                                 delay_key();
  139.                                 if(!keydin2)
  140.                                 {
  141.                                         if(tempfen > 59)
  142.                                         {
  143.                                                 tempfen = 0;
  144.                                         }
  145.                                         else
  146.                                         {
  147.                                                 tempfen++;               
  148.                                         }
  149.                                 }       
  150.                         }       
  151.                         if(!keydin3)
  152.                         {
  153.                                 delay_key();
  154.                                 if(!keydin3)
  155.                                 {
  156.                                         if(tempfen < 0)
  157.                                         {
  158.                                                 tempfen = 59;
  159.                                         }
  160.                                         else
  161.                                         {
  162.                                                 tempfen--;               
  163.                                         }
  164.                                 }       
  165.                         }       
  166.                         while((!keydin2) || (!keydin3));
  167.                 }
  168.                
  169.                 if(!keydin4)
  170.                 {
  171.                         delay_key();
  172.                         if(!keydin4)
  173.                         {
  174.                                 tempsbuf[0] = tempshi;       
  175.                                 tempsbuf[1] = tempfen;       
  176.                                
  177.                                 write_ds1302(0X84,tempsbuf[0]/10*16+tempsbuf[0]%10);        //写入修改好的时钟
  178.                                 write_ds1302(0X82,tempsbuf[1]/10*16+tempsbuf[1]%10);   
  179.                                 write_ds1302(0X80,0X00);                                //启动计时                                 
  180.                                 faneg = 0;
  181.                                 mak = 0;
  182.                                 return;                       
  183.                         }       
  184.                 }
  185.         }
  186. }
  187. //********************************************************************
  188. //* 名称  : main()
  189. //* 功能  : 主程序
  190. //* 输入  :        无
  191. //* 返回值: 无
  192. //***********************************************************************
  193. void main()
  194. {
  195.        
  196.         keydin1 = 1;keydin2 = 1;keydin3 = 1;keydin4 = 1;   //端口初始化
  197.         while(1)
  198.         {
  199.                 key_refresh();                   //功能选择
  200.                 read_time(&mek_buf);             //读出DS1302中的时间
  201.                 mek_led();                                             //制作显示数据
  202.                 display_led(led_buf);                     //显示正常时间               
  203.                 if(1 == faneg){key_Modify();}         //修改时间
  204.         //        shanshuo_led();                  //秒点闪烁
  205.         //        Automatic();           //单片机自动操作
  206.         }
  207. }

复制代码



分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 分享淘帖 顶 踩
回复

使用道具 举报

沙发
ID:113533 发表于 2016-4-18 21:56 | 只看该作者
学习一下,if(1 == faneg)    //主机              避免了1=faneg的错误
回复

使用道具 举报

板凳
ID:185829 发表于 2017-5-17 17:59 | 只看该作者
时钟数据罗马数字编码的方法,有意思
回复

使用道具 举报

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

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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