找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 5755|回复: 2
收起左侧

51单片机电子制作DIY---交通灯控制器

  [复制链接]
ID:350579 发表于 2019-7-3 15:56 | 显示全部楼层 |阅读模式
> 作者:李剀
> 出处:https://www.cnblogs.com/kevin-nancy
>  或者
>
https://blog.csdn.net/Kevin_8_Lee/article/details/91351632
>未经本人允许禁止转载。谢谢!(上面两个都是我的博客,只是在不同平台)



首先说一下背景吧 :


最近在帮别人做一些小东西,是用51做的,主要给他们提供单片机课设的思路。     且由于时间问题,我也没有将程序进行优化,只是拿来分享一下,大家可以参考。 有思路之后可以稍微花点时间去优化一下代码,是代码更简洁。


马丁·福勒 的一句名言与君共勉:

任何一个傻瓜都会写能够让机器理解的代码,只有好的程序员才能写出人类可以理解的代码。—Martin Fowler

ok, 废话不多说,下面是设计要求及制作过程,proteus仿真以及代码流程的介绍




1)  题目及设计要求
题目:交通灯控制器
要求:
1、红灯和绿灯相互转换时经过黄灯,黄灯闪烁三次(6秒);

2、主干道方向通行30秒,辅干道方向通行20秒,单独左转信号15秒;先直行信号,后左转信号。

3、设手动、自动、特殊情况三种方式。

4、特殊情况时所有路口红灯都亮,给120、110等通行。


5、自动时显示各种状态倒计时。

2) C51编程以及电路仿真软件
编程


51单片机的C语言编程一般都是keil3或者keil4,我一直以来用的keil3,这次使用的keil4,其实都一样的。


注:关于keil3/4/5的资料和安装教程,在我的另一篇博客讲过了,可以参考一下  点击蓝字-->>


keil软件图标.jpg




keil4打开的界面如下:
keil软件打开演示.jpg



( PS:: 不过这次做这些东西的过程中,keil4经常自己卡死,害得我只能任务管理器关闭它,超级烦,不知道什么原因,有了解的可以评论一下告诉我,感激不尽 .............但是老版本的keil3却很稳定)  


仿真:
proteus仿真软件

我用的7版本的
proteus图标.jpg



proteus打开界面如下:
proteus软件界面.jpg    这个界面里面的电路图与这个交通灯无关,是我以前做的一个,只是给大家演示




3)解决思路
硬件部分:
交通灯显示部分分为6个部分

- [ 1] 首先:主干道通行30秒  其中单独左转15秒  黄灯6秒
1)主干道--------绿灯                                辅干道--------红灯                0-15s                 // 单独直行
2)主干道--------蓝灯                                辅干道--------红灯                15-24s                // 单独左转
3)主干道--------黄灯                                辅干道--------红灯                24-30s                // 黄灯减速

---------------------------------------------------------------------------------------------------------------------------------------
- [ 2] 辅干道通行20秒   单独左转15秒  黄灯6秒
4)主干道--------红灯                                辅干道--------绿灯                0-5s
5)主干道--------红灯                                辅干道--------蓝灯                5-14s
6)主干道--------红灯                                辅干道--------黄灯                14-20s


模拟交通的灯的几个led灯的显示在程序中就是按照上面的流程显示的,由 1)--->2)--->.....--->6)--->1)->.....   一直循环


仿真电路图各个部分展示:

(1)单片机 & 复位电路 & 晶振
单片机及复位电路.jpg



(2)交通灯部分
交通灯部分仿真图.jpg


上图标注了每个灯对应的引脚   以及每个灯的颜色


分别在上面和右面放置了一排  用来表示道路的方向



D1-D4指示的是主干道                        D5-D8指示的是辅干道


(3)数码管显示部分

这部分是和交通灯部分一起的  为了方便看到我写的标注,我把交通灯抹去了,抹去的部分就是上面交通灯的部分
数码管显示部分.jpg

数码管驱动.jpg

(该芯片使用方法这里不多说,网上很多资料。。。本质就是一个锁存器)


软件部分

首先代码流程图如下,对这个画图软件不是很熟,画的很垃圾,不过大致能体现出来
程序流程图.jpg



4)部分代码展示及解释


# include <reg52.h>
# define uchar unsigned char
# define uint  unsigned int

sbit wela = P2^7;                  // 数码管位选
sbit dula = P2^6;                // 数码管段选

  1. // 按键位定义
  2. sbit        key_auto         = P3^0;        // 自动
  3. sbit        key_step         = P3^1;        // 手动
  4. sbit        key_emerg         = P3^2;        // 紧急情况 110/120通过
复制代码
  1. // 四位八段共阴极数码管数字显示编码
  2. uchar code table[]={
  3. //"0" "1"  "2"  "3"
  4. 0x3f,0x06,0x5b,0x4f,
  5. //"4" "5"  "6"  "7"
  6. 0x66,0x6d,0x7d,0x07,
  7. //"8" "9"  "A"  "B"
  8. 0x7f,0x6f,0x77,0x7c,
  9. //"C" "D"  "E"  "F"
  10. 0x39,0x5e,0x79,0x71
  11. };
复制代码
  1. // 交通灯编码  自动模式时,交通灯亮灯顺序 我编成了一个数组,方便使用

  2. uchar code light[]={
  3. // 主G辅R      主G辅R    主Y辅R
  4.     0xdb,       0xde,     0xd7,
  5. // 主R辅G      主R辅B    主R辅R
  6.     0xbd,       0xed,     0x7d,
  7. };
复制代码
  1. // 定时器0中断服务函数  用于计算时间过了几秒
  2. void timer0() interrupt 1
  3. {
  4.         TH0=0x4c;                // 定时器装初值 50ms(11.05926MHz  TH0=0x4c TL0=0x00)
  5.         TL0=0x00;            // (12MHz 的初值是 TH0=0x3c TL0=0xb0)
  6.     cnt++;
  7.         if(cnt == 20)
  8.         {
  9.                 cnt = 0;
  10.                 sec++;          // 记录1秒
  11.         }
  12. }
复制代码
  1. // 按键扫描函数
  2. void key_scan()
  3. {
  4.     //判断那个按键盘下
  5.    
  6.     /********************** 自动模式 *********************/
  7.     ///如果是自动模式,就让交通灯正常运行  并显示倒计时
  8.     // Display_C_time(15-sec);        // 主干道倒计时显示
  9.     // Display_R_time(30-sec);  // 辅干道倒计时显示
  10.     // P1 = light[0];                   // 交通灯编码显示
  11.     // 具体代码省略、、、、、、、、、、
  12.    
  13.      /********************** 手动模式 *********************/
  14.     //手动模式就让交通等步进变换
  15.     if(key_step == 0)
  16.         {
  17.                 delay_ms(5);
  18.                 if(key_step == 0)
  19.                 {
  20.                         if(light_num == 6)
  21.                         {
  22.                                 light_num = 0;
  23.                         }
  24.                         P1 = light[light_num];
  25.                         light_num++;
  26.                         while(!key_step);  // 松手检测
  27.                 }
  28.         }
  29.         
  30.          /********************** 紧急模式 *********************/
  31.         // 紧急模式  用于120/110紧急通行
  32.         // 让主干道和辅干道都是红灯即可
  33.         // 具体代码省略、、、、、、、、、、、
  34.    
  35. }
复制代码
// 最后在主函数里面初始化,然后循环扫描按键

  1. void main()
  2. {
  3.     system_Init();                        // 系统初始化  里面是对定时器中断以及数码管进行初始化

  4.     while(1)
  5.         {
  6.                 key_scan();
  7.         }
  8. }
复制代码

5)整体效果演示
仿真展示.gif


因为这个是帮别人设计的,所以完整源码和仿真工程文件不贴出。         如果需要完整的仿真以及源码,请私聊我或者评论留下联系方式


今天所有的懒惰都会换来明天的卑微                   加油吧!!!


评分

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

查看全部评分

回复

使用道具 举报

ID:498463 发表于 2019-11-8 13:45 | 显示全部楼层
求楼主分享
回复

使用道具 举报

ID:982564 发表于 2021-11-24 14:47 | 显示全部楼层
最近正在学习,摆脱分享一下,感谢!
回复

使用道具 举报

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

本版积分规则

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

Powered by 单片机教程网

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