您的当前位置:首页正文

交通灯控制系统设计与仿真毕业论文

2020-05-20 来源:V品旅游网
. . . .

交通灯控制系统设计与仿真

项目名称交通灯控制系统设计与仿真

摘要

1 / 27

. . . .

随着社会主义的建设,城市的规模在不断扩大,城市的交通也在不断的提高和改进,交通的顺畅已经成为制约社会主义建设的一个重要因素。目前,伴随着机动车辆的不断增加,尤其是十字路口的交通建设

颇为关键,严重的影响到城市交通安全。社会主义建设

以来,有许许多多的设计工作者投身于十字路口交通建设的研究之中,创造和设计出了很多新型的方案,把我国交通建设推向了更高的发展阶段。当前,十字路口都采用了信号灯来控制车辆和人的通行,不仅便于维护管理,而且有较强的自动化。大量的信号灯电路正向着数字化、小功率、多样化、方便人、车、路三者关系的协调,多值化方向发展随着社会经济的发展,城市交通问题越来越引起人们的关注。它的出现使交通得以有效管制,对于疏导交通流量、提高道路通行能力,减少交通事故有明显效果。十字路口车辆穿梭,行人熙攘,车行车道,人行人道,有条不紊。那么靠什么来实现这井然秩序呢?靠的就是交通信号灯的自动指挥系统。交通信号灯控制方式很多。本系统采用单片机AT89S52来设计交通灯控制器,实现了能根据实际车流量通过AT89S52芯片的P1口设置红、绿灯燃亮时间的功能;红绿灯循环点亮,倒计时剩5秒时黄灯闪烁警示。本系统实用性强、操作简单、扩展功能强。

关键词: AT89S52单片机;交通灯;倒计时;时间显示

2 / 27

. . . .

第一章 绪 论

1.1交通信号灯的发展与研究意义

当今,红绿灯安装在各个道口上,已经成为疏导交通车辆最常见和最有效的手段,这一技术已经有相当长的发展历史了。

红绿灯的起源可追溯到19世纪初的英国。那时,在英国的约克城,着红装的女人表示“已婚”,而着绿装的女人则是“未婚”。当时,伦敦议会大厦前经常发生马车轧人的事故。受红绿装启发,英国机械师德?哈特于1868年设计了红、绿两色的煤气交通信号灯,由一名手持长杆的警察通过牵动皮带来转换灯的颜色。可惜的是,这盏灯的历史只有23天,中断的原因是煤气灯突然爆炸使一位警察殉职。图为一1938年6月27日发布的照片显示,在英国伦敦,行人看着一群蜜蜂聚集在一个交通信号灯上。

电气启动的红绿灯出现在美国,这种红绿灯由红绿黄三色圆形的投光器组成,1914年始安装于纽约市5号大街的一座高塔上。红灯亮表示“停止”,绿灯亮表示“通行”。克里夫兰市率先在街道中恢复交通信号灯,随后纽约、芝加哥等城市也开始出现。这时的交通信号灯已从煤气进化为电气,这与现代的交通信号灯已经没有多少差距,除了信号灯本身,美国人还完善了信号控制系统。图为1931年6月23日,美国纽约第五大道竖起一盏新的青铜制造的红绿灯。

3 / 27

. . . .

1918年,又出现了带控制的红绿灯和红外线红绿灯。带控制的红绿灯,一种是把压力探测器安在地下,车辆一接近红灯便变为绿灯;另一种是用扩音器来启动红绿灯,司机遇红灯时按一下嗽叭,就使红灯变为绿灯。红外线红绿灯当行人踏上对压力敏感的路面时,它就能察觉到有人要过马路。红外光束能把信号灯的红灯延长一段时间,推迟汽车放行,以免发生交通事故。

中国最早的红绿灯出现在的英租界。有资料显示,早在1923年,公共租界开始在部分十字路口使用机械装置指示车辆停止和前进,该年4月13日,路两个重要十字路口,最先安装红绿灯交通信号装置。图为上世纪20年代,租界印度锡克族交警用手控制红绿交通信号灯。

4 / 27

. . . .

1961年,心理学家卡尔?佩格劳为东德交通部设计了一种新的行人信号灯,1969年在东柏林首次投入使用。在卡尔。佩格劳的设计中,原本单调的图案,不但变成了一个站立的和一个行走的行人形象,而且两人体型肥胖,带着帽子,动作略显夸,这样传递的视觉信号更为明显,形象也更可爱。这个信号灯受到政府的认可和民众的喜爱,并很快推广。

在今天,红绿灯安装在城市各个道口上,已经成为疏导交通车辆最常见和最有效的手段。信号灯的出现,使交通得以有效管制,对于疏导交通流量、提高道路通行能力,减少交通事故有明显效果。

交通信号灯的出现,使交通得以有效管制,对于疏导交通流量、提高道路通行能力,减少交通事故有明显效果,更改变了交警轮流指挥和疏散交通拥挤的现状,实现了人,车,路三者的同步协调。现阶段,许多设计工作者又设计出许多智能化,自动化,数字化等更先进的交通灯控制方案,这更方便于维护管理,给人们提供了更加便利的交通环境。

目前,城市规模还在不断的扩大,人们对交通信号灯的控制也越来越高,我们需要更高层次的去了解交通信号灯,结合城市十字路口交通的需要,不断地去创新,才能达到发展的需求,所以研究交通信号灯的极为重要。

1.2方案的设计与论证

本设计以单片机为核心,以LED数码管作为倒计时指示,根据设计的要求我们考虑了各功能模块的几种设计方案,以求最佳方案,实现实时显示系统各种状态,系统还增设了根据交通拥挤情况可分别设置主干道和次干道的通行时间,以提高效率,缓减交通拥挤。系统总体设计框图如图所示。

交通灯控制的框图如下图所示,主要有控制电路、按键电路、晶振电路、复位电路、显示电路、电源电路等电路组成。 电源电路 单 时钟电路 片 机 复位电路 数码管显示电路

按键电路 5 / 27 Led信号灯控制电路 . . . .

1.2.1电源提供方案

方案:采用单片机控制模块提供电源。该方案的优点是系统简明扼要,节约成本;缺点是输出功率不高。

1.2.2显示界面方案

该系统要求完成倒计时功能。基于上述原因,本次设计考虑了两种方案:

方案一:完全采用点阵式LED显示。这种方案功能强大,可方便的显示各种英文字符,汉字,图形等,但实现复杂,且须完成大量的软件工作。

方案二:完全采用数码管显示。这种方案优点是实现简单,可以完成倒计时功能。缺点是功能较少,只能显示有限的符号和数码字符。根据本设计的要求,方案二已经满足了要求,所以本次设计采用方案二以实现系统的显示功能。

1.2.3输入方案

这里同样讨论了两种方案:

方案一:采用8155扩展I/O口、键盘与显示等。该方案的优点是使用灵活可编程,并且有RAM与计数器。若用该方案,可提供较多I/O口,但操作起来稍显复杂。

方案二:直接在I/O口线上接上按键开关。因为设计时精简和优化了电路,所以剩余的端口资源还比较多。

由于该系统是对交通灯与数码管的控制,只需用单片机本身的I/O口就可实现,且本身的计数器与RAM已经够用,故选择方案二。

第二章 系统硬件设计

2.1总体设计

本设计以单片机为控制核心,采用模块化设计,共分以下几个功能模块:单片机控制系统、键盘与状态显示、倒计时模块等。

6 / 27

. . . .

单片机作为整个硬件系统的核心,它由单片机振荡电路、复位电路等组成。 系统采用双数码管倒计时计数功能,最大显示数字99。

2.2 单片机的基本结构

AT89S52单片机是一款低功耗、低电压、高性能CMOS8位单片机,片含8KB(可经受1000次擦写周期)的FLASH可编程可反复擦写的只读程序存储器(EPROM),器件采用CMOS工艺和ATMEL公司的高密度,非易失性存储器(NURAM)技术制造,其输出引脚和指令系统都与MCS-51兼容,片的FLASH存储器允许在系统可改编程序或用常规的非易失性存储编程器来编程。因此,AT89C52是一种功能强,灵活性高且价格合理的单片机,可方便的应用在各个控制领域[1]。 AT89S52具有以下主要性能: 1.8KB可改编程序FLASH存储器; 2.全表态工作 :0~24HZ; 3.256X8字节部RAM;

4.32个外部双向输入,输出(I、O)口; 引脚说明如图2-2。

图2-2 AT89S52引脚说明

7 / 27

. . . .

引脚功能说明如下[2]: VCC:电源电压。 GND:地。

P0口:P0口是一组8位漏极开路型双向I/O口,也即地址/数据线复用口。作为输出口时,每位能吸收电流的方式驱动8个TTL逻辑门电路,对端口写“1”可作为高阻抗输入端。

在访问外部数据储存器或程序储存器时,这组口线分时转换地址(低8位)和数据总线复用,在访问期间激活部上拉电阻。FLASH编程时,P0口接收指令字节,而在程序校验时,输出指令字节,校验时,要求外接上拉电阻。

P1口:P1是一个带部上拉电阻的8位双向I/O口,P1的输出缓冲级可驱动(吸收或输出电流)4个TTL逻辑门电路。对端口写“1”,通过部的上拉电阻把端口拉到高电平,此时可作为输入口。作为输入口使用时,因为部存在上拉电阻,某个引脚被外部信号拉低时会输出一个电流。FLASH编程和程序校验期间,P1接收低8位地址。

P2口:P2是一个带部上拉电阻的8位双向I/O口,P2的输出缓冲级可驱动(吸收或输出电流)4个TTL逻辑门电路。对端口写“1”,通过部的上拉电阻把端口拉到高电平,此时可作为输入口。作为输入口使用时,因为部存在上拉电阻,某个引脚被外部信号拉低时会输出一个电流。在访问外部程序储存器或16位地址的外部数据储存器(例如执行MOVXDPTR指令)时,P2口送出高8位地址数据。在访问8位地址的外部数据储存器(例如执行MOVXRI指令)时,P2口线上的容(也即特殊功能寄存器(SFR)区中R2寄存器的容),在整个访问期间不改变。P3口:P3是一个带部上拉电阻的8位双向I/O口,P3的输出缓冲级可驱动(吸收或输出电流)4个TTL逻辑门电路。对端口写“1”,通过部的上拉电阻把端口拉到高电平,此时可作为输入口。作为输入口使用时,因为部存在上拉电阻,某个引脚被外部信号拉低时会输出一个电流。

P3除了作为一般的I/O口线外,更重要的用途是它的第二功能,具体功能说明如表2-1。

P3口还接收一些用于FLASH闪速存储器编程和程序校的控制信号。

RST:复位输入。当振荡器工作时,RST引脚出现两个机器周期以上高电平将使单片机复位

ALE/PROG:当访问外部程序存储器或数据存储器时,ALE(地址锁存允许)输出脉冲

8 / 27

. . . .

用于锁存地址的低8位字节。 表2-1 P3口的第二功能表

即 P3.1 P3.2 P3.3 P3.4 P3.5 P3.6 P3.7 TXD(穿行输入口) INT0(外部中断0) INT1(外部中断1) T0(定时/计数器0) T1(定时/计数器0) WR(外部数据写选通) RD(外部数据读选通) P3.0 RXD(穿行输出口) 端口引脚 第二功能 使不访问外部存储器,ALE仍以时钟振荡频率的1/6输出固定的正脉冲信号,因此它可对外输出时钟或用于定时目的。要注意的是:每当访问外部数据存储器时将跳过一个ALE脉冲。对FLASH存储器编程期间,该引脚还用于输入编程脉冲(PROG)。

如有必要,可通过对特殊功能寄存器(SFR)区中的8EH单元的D0位置位,可禁止ALE操作。该位置位后,只有一条MOVX和MOVC指令ALE才会被激活。此外,该引脚会被微弱拉高,单片机执行外部程序时,应设置ALE无效。

PSEN:程序储存允许(PSEN)输出是外部程序存储器的读选通信号,当AT80C51由外部程序存储器取指令(或数据)时,每个机器周期两次PSEN有效,即输出两个脉冲。在此期间,当访问外部数据存储器,这两次有效的PSEN信号不出现。

EA/VPP:外部访问允许。欲使CPU仅访问外部程序储存器(地址为0000H-FFFFH),EA端必须保持低电平(接地)。需要注意的是:如果加密位LB1被编程,复位时部会锁存EA端状态。如EA端为高电平(Vcc端),CPU则执行部程序储存器中的指令。

FLASH储存器编程时,该引脚加上+12V的编程允许电源Vpp,当然这必须是该器件是使用12v编程电压。

XTAL1:振荡器反相放大器的与部时钟发生器的输入端。 XTAL2:振荡器反相放大器的输出端

9 / 27

. . . .

2.3其他电路设计 2.3.1复位电路设计

MCS-51的复位输入引脚RST为MCS-51提供了初始化的手段,可以使程序从指定处开始执行,在MCS-51的时钟电路工作后,只要RST引脚上出现超过两个机器周期以上的高电平时,即可产生复位的操作,只要RST保持高电平,则MCS-51循环复位,只有单RET由高电平变成低电平以后,MCS-51才从0000H地址开始执行程序,本系统采用按键复位方式的复位电路。

2.3.2外部晶振时钟电路设计

MCS-51的时钟可以由两种方式产生,一种是部方式,利用芯片部的振荡电路;另外一

10 / 27

. . . .

种为外部方式,本论文根据实际需要和简便,采用部振荡方式,MCS-51部有一个用于构成振荡器的高增益反相放大器,引脚XTAL1和XTAL2分别是此放大器的输入端和输出端,这个放大器与作为反馈元件的片外晶体或瓷谐振器一起构成了一个自激振荡器。

MCS-51虽然有部振荡电路,但要形成时钟,必须外接元件,所以实际构成的振荡时钟电路,外接晶振以与电容C1和C2构成了并联谐振电路接在放大器的反馈回路中,对接电容的值虽然没有严格的要求,但电容的大小会影响振荡频率的高低,振荡器的稳定性,起振的快速性和温度的稳定性。晶振的频率可在1.2MHZ~12MHZ之间任选,电容C1和C2的典型值在20pf~100pf之间选择,由于本系统用到定时器,为了方便计算,采用了12MHZ的晶振,采用电容选择30pf。

2.3.3 显示模块电路设计

该模块由共阳LED数码管组成,利用数码管的动态扫描原理,由三极管进行锁存,当控制数码管的IO口P20和P21为低电平时(与三极管基极为低电平),则三极管导通,VCC通三极管给数码管供电,则数码管被点亮,利用数码管点亮的余辉和人眼的视觉暂留原理,则看起来数码管是同时被点亮的。

11 / 27

. . . .

从设计完成的任务与要求来看,显示通行时间必须用二位数码管,从节省硬件资源的角度考虑,可采用扫描的方式来处理,对于7段数码管,占用7个单片机的I/O口,另外设置2个电子开关对2位显示进行配合,占用2个I/O端口,十字路口共需4组红绿灯,加上转换黄灯,一共是12只灯,须用12个端口进行控制,加上两个方向的紧急通行按钮,占2个I/O端口和一个蜂鸣器端口,因此实际占用的单片机I/O口为24个,为此,我们可以选用51系列单片机中的ATAT89S52来作为中央处理器。这款单片机的I/O口作为输出时,具有较大的吸收电流能力,因此我们可以选用共阳型数码管,这样由单片机的I/O口就可以直接驱动,能简化硬件电路的设计。

12 / 27

. . . .

2.4原理图

2.5仿真图

我们用proteus软件对此原理图进行仿真。仿真图如下:

13 / 27

. . . .

2.4pcb图

经过布线工作后我们得到以下的pcb图:

14 / 27

. . . .

第三章 交通信号灯控制系统的设计与程序编写

3.1十字路口交通信号灯具体的控制要求

(1) 交通信号灯分布于东南西北,每个路口均有三个。南北方向绿灯和东西方向的绿灯不能同时亮;如果同时亮,则应自动立即关闭信号灯系统,并立即发出报警信号。系统工作后,首先南北红灯亮并维持30s;与此同时,东西绿灯亮,并维持25s时间,到25s时,东西绿灯熄灭。在东西绿灯熄灭时,东西黄灯亮并维持5s,然后东西黄灯熄灭,东西红灯亮,同时南北红灯熄灭,南北绿灯亮;东西红灯亮并维持30s;与此同时,南北绿灯亮并维持15s;然后,南北绿灯熄灭南北绿灯熄灭时,南北黄灯亮维持5s后熄灭;同时南北红灯亮,东西绿灯亮。至此,结束一个工作循环,如下交通信号灯变化表:

交通信号灯变化表 绿灯亮 东西 25S 红灯亮 南北 30S 15S 5S 5S 绿灯亮 20S 黄灯亮 黄灯亮 红灯亮

(2)在交通信号灯亮和闪烁的同时,路口设有两位七段码的显示器倒数计时,让车辆行人能够清楚地知道再过多久信号灯就会发生变化。以便于司机和行人能够在有限的时间准确的通行。

3.2 软件设计流程

(1)软件总体设计主要完成各部分的软件控制和协调。本系统主程序模块主要完成的工作是对系统的初始化,发送显示数据,同时对键盘进行扫描,等待外部中断,以与根据所需要的功能进行相应的操作。

(2)交通灯根据其显示情况可以分为四个状态,可以通过定时来控制每个状态的时间;通过定时也可以向LED数码管中每隔1秒送一个数,显示该状态剩余的时间。其流程

15 / 27

. . . .

图如图所示。

开 始 设置定时,显示初南北绿灯亮,东西红灯亮,南北黄灯闪烁,东西红灯 南北红灯亮,东西绿灯亮,南北红灯亮,东西黄灯闪

图3-1 主程序框图

16 / 27

. . . .

3.3 软件设计 交通灯定时器模块

AT89S52单片机部有3个定时器T0,T1和T2,本次设计中使用T0工作在方式1,即16位定时器,定时50ms,20次中断产生秒信号,从而控制红绿灯的点亮时间。

工作方式寄存器TMOD用来设置T0、T1的工作方式。这次实习中设置TMOD=0x01,即T0工作于方式0(16位定时器)。

部定时器/计数器用作定时器时,是对机器周期计数,每个机器周期的长度是12个振荡周期。定时常数的设置可用一下方式计算:

机器周期=12/12MHz=1us (65536-定时常数)*1.0us=50ms 所以定时常数是50000。

第四章 调试

调试图:

17 / 27

. . . .

实物图:

第五章 体会

值此论文完成之际,谨向我们的导师老师表示衷心的感!我们六个同学分工合作,在整个项目中学会了multisim,keil等电路相关软件的使用,大致掌握了电路设计的基本方法。在项目进行中由于所学课程限制,遇到了诸多困难,通过自学也客服了许多。

总之,在整个项目中,学到的不仅仅是制作一个电子产品,更多的是对电子设计的兴趣和学到的创新精神。

附件一:源程序代码

#include //调用单片机头文件

18 / 27

. . . .

#define uchar unsigned char //宏定义\"uchar\"代替\"unsigned char\"。 #define uint unsigned int //宏定义\"uint\"用来定义无符号整型数。

#include \"eeprom52.h\"

//数码管段选定义 0 1 2 3 4 5 //

uchar dis_smg[8] = {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8}; uchar smg_i = 4; //显示数码管的个位数

//数码管位选定义 sbit smg_we1 = P2^0; sbit smg_we2 = P2^1; sbit smg_we3 = P3^6; sbit smg_we4 = P3^7;

char dx_s = 0; //东西 南北 倒计时变量 sbit dx_red = P2^4; //东西红灯 sbit dx_green = P2^3; sbit dx_yellow = P2^2;

sbit nb_red = P2^7; sbit nb_green = P2^6; sbit nb_yellow = P2^5;

uchar flag_jtd_mode; //交通灯的模式 根据时间 bit flag_1s = 0; bit flag_500ms; bit flag_dx_nb; uchar i;

uchar flag_alarm; //模式

uchar dx_time = 30,nb_time = 20; //东西、南北的时间 uchar flag_jdgz ; //交通管制

/***********************数码位选函数*****************************/ void smg_we_switch(uchar i)

19 / 27

//东西南北模式

uchar flag_5m_value;

//南北红灯 //南北绿灯 //南北黄灯 //东西绿灯 //东西黄灯 //数码管位选定义

A

6 7 8 9

不显示

uchar code smg_du[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,

B C D E F

0x88,0x83,0xc6,0xa1,0x86,0x8e,0xff}; //断码

. . . .

{ }

/******************把数据保存到单片机部eeprom中******************/ void write_eeprom() { }

/******************把数据从单片机部eeprom中读出来*****************/ void read_eeprom() { }

/**************开机自检eeprom初始化*****************/ void init_eeprom() ///开机自检eeprom初始化 { }

20 / 27

read_eeprom(); if(a_a != 1) {

a_a = 1; dx_time = 30;

nb_time = 20; //东西、南北的时间 write_eeprom(); //保存数据

//先读

//新的单片机初始单片机问eeprom

a_a = byte_read(0x2058); dx_time = byte_read(0x2000); nb_time = byte_read(0x2001); byte_write(0x2058, a_a);

SectorErase(0x2000); byte_write(0x2000, dx_time); byte_write(0x2001, nb_time); switch(i) {

case 0: smg_we1 = 0; smg_we2 = 1; smg_we3 = 1; smg_we4 = 1; break; case 1: smg_we1 = 1; smg_we2 = 0; smg_we3 = 1; smg_we4 = 1; break; case 2: smg_we1 = 1; smg_we2 = 1; smg_we3 = 0; smg_we4 = 1; break; case 3: smg_we1 = 1; smg_we2 = 1; smg_we3 = 1; smg_we4 = 0; break;

}

}

. . . .

/******************************************************************** * 名称 : delay_1ms() * 功能 : 延时1ms函数 * 输入 : q * 输出 : 无

***********************************************************************/ void delay_1ms(uint q) { }

/******************************************************************** * 名称 : display() * 功能 : 数码管显示 * 输入 : 无 * 输出 : 无

***********************************************************************/ void display() { }

/*********************定时器0、定时器1初始化******************/ void time0_init() {

EA = 1; ET0 = 1; TR0 = 1;

//开总中断

//定时器0、定时器1工作方式1 //开定时器0中断 //允许定时器0定时 //开定时器1中断 //允许定时器1定时

TMOD = 0X11; uchar i;

for(i=0;iP0 = 0xff; //消隐 smg_we_switch(i); //位选 P0 = dis_smg[i]; delay_1ms(3);

//段选

uint i,j; for(i=0;ifor(j=0;j<110;j++);

// ET1 = 1; // TR1 = 1; }

21 / 27

. . . .

/*********************交通灯处理函数*********************************/ void jiaotongdeng_dis() {

/***********************南北时间*********************************/

if(flag_dx_nb == 0) {

if(dx_s > 5) { {

dx_red = 1; //灭 dx_green = 1; //灭 nb_red = 0; //亮 nb_green = 1; //灭 nb_yellow = 1; //灭 if(flag_500ms == 0) {

dx_yellow = 0;//亮

22 / 27

dx_red = 1; //灭 dx_green = 0; //亮 dx_yellow = 1; //灭 nb_red = 0; //亮 nb_green = 1; //灭 nb_yellow = 1; //灭 flag_5m_value = 0;

//当小于5秒时 黄灯要闪了

if(flag_1s == 1) { }

dis_smg[0] = smg_du[dx_s % 10] ; dis_smg[1] = smg_du[dx_s / 10] ; dis_smg[2] = smg_du[dx_s % 10] ; dis_smg[3] = smg_du[dx_s / 10] ;

flag_1s = 0; if(dx_s == 0) { } dx_s --;

if(flag_dx_nb == 1)

dx_s = nb_time; //南北时间 dx_s = dx_time; //东西时间 else

flag_dx_nb = ~flag_dx_nb;

}else if(dx_s <= 5)

. . . .

}

}

} else { }

dx_yellow = 1;//灭

/***********************东西时间*********************************/

if(flag_dx_nb == 1) { if(dx_s > 5) { dx_red = 0; //亮 dx_green = 1; //灭 dx_yellow = 1; //灭 nb_red = 1; //灭 nb_green = 0; //亮 nb_yellow = 1; //灭 flag_5m_value = 0;

}else if(dx_s <= 5)

//当小于5秒时 { dx_red = 0; //灭 dx_green = 1; //灭 dx_yellow = 1; //灭 nb_red = 1; //灭 nb_green = 1; //灭

if(flag_500ms == 0) //黄灯闪烁 { nb_yellow = 0; //亮

} else { nb_yellow = 1; //灭

}

} }

}

/********************独立按键程序*****************/ uchar key_can; //按键值

void key() //独立按键程序 {

23 / 27

黄灯要闪了

. . . .

static uchar key_new;

key_can = 20; //按键值还原 P1 |= 0x1f;

if((P1 & 0x1f) != 0x1f) { delay_1ms(1); //按键消抖动 if(((P1 & 0x1f) != 0x1f) && (key_new == 1)) //按键按下

{

//确认是按键按下

key_new = 0; switch(P1 & 0x1f) { case 0x1e: key_can = 1; break; case 0x1d: key_can = 2; break; case 0x1b: key_can = 3; break; case 0x17: key_can = 4; break;

}

}

} else

key_new = 1;

}

uchar menu_1,flag_s;

/********************设置函数*****************/ void key_with() { if(key_can == 4) //交通管制按键 { flag_jdgz ++; if(flag_jdgz > 5) flag_jdgz = 0;

if(flag_jdgz == 1) // 全部亮红灯

{ dx_red = 0; //亮 dx_green = 1; //灭 dx_yellow = 1; //灭 nb_red = 0; //亮 nb_green = 1; //灭 nb_yellow = 1; //灭

}

if(flag_jdgz == 2) // 东西红灯 南北绿灯24 / 27

得到按键值 得到按键值 得到按键值 得到按键值

// // // //

. . . .

}

{ }

if(flag_jdgz == 3) // 南北红灯 东西绿灯 { }

if(flag_jdgz == 4) // 南北绿灯 东西绿灯 { }

if(flag_jdgz == 5) // 南北黄灯 东西黄灯 { }

//设置键

dx_red = 1; //灭 dx_green = 1; //灭 dx_yellow = 0; //亮 nb_red = 1; //灭 nb_green = 1; //灭 nb_yellow = 0; //亮

dx_red = 1; //灭 dx_green = 0; //亮 dx_yellow = 1; //灭 nb_red = 1; //灭 nb_green = 0; //亮 nb_yellow = 1; //灭

dx_red = 1; //灭 dx_green = 0; //亮 dx_yellow = 1; //灭 nb_red = 0; //亮 nb_green = 1; //灭 nb_yellow = 1; //灭

dx_red = 0; //亮 dx_green = 1; //灭 dx_yellow = 1; //灭 nb_red = 1; //灭 nb_green = 0; //亮 nb_yellow = 1; //灭

if(key_can == 1) {

menu_1 ++; if(menu_1 >= 3) { }

menu_1 = 0;

25 / 27

. . . .

}

}

if(menu_1 == 1) //设置东西的时间 {

if(key_can == 2) { }

if(key_can == 3) { }

dis_smg[0] = smg_du[10] ; //显示为A dis_smg[1] = smg_du[10] ; //显示为A dis_smg[2] = smg_du[dx_time % 10] ; dis_smg[3] = smg_du[dx_time / 10] ; write_eeprom(); //保存数据

//显示东西设置的时候

dx_time -- ;

//减1

if(dx_time <= 10)

dx_time = 10; dx_time ++ ;

//加1

if(dx_time > 99)

dx_time = 99;

}

if(menu_1 == 2) //设置南北的时间 { }

if(key_can == 2) { }

if(key_can == 3) { }

dis_smg[0] = smg_du[11] ; //显示为B dis_smg[1] = smg_du[11] ; //显示为B dis_smg[2] = smg_du[nb_time % 10] ; dis_smg[3] = smg_du[nb_time / 10] ; write_eeprom(); //保存数据

//显示东西设置的时候

nb_time -- ;

//减1

if(nb_time <= 10)

nb_time = 10; nb_time ++ ;

//加1

if(nb_time > 99)

nb_time = 99;

26 / 27

. . . .

/******************************************************************** * 名称 : main() * 功能 : 实现灯的闪烁 * 输入 : 无 * 输出 : 无

***********************************************************************/ void main() { }

/*********************定时器0中断服务程序************************/ void time0_int() interrupt 1 { }

27 / 27

//定时10ms中断一次

static uchar value; TH0 = 0x3c;

TL0 = 0xb0; //50ms value ++; flag_5m_value++;

if(flag_5m_value % 10 == 0) { }

value = 0; flag_1s = 1;

flag_500ms = ~flag_500ms; if(value >= 20)

P0 = P1 = P2 = P3 = 0XFF; //IO口全部输出为1 time0_init();

init_eeprom(); ///开机自检eeprom初始化 dx_s = nb_time; //东西时间 while(1) { }

key();

if(key_can < 20)

key_with(); menu_dis();

if((menu_1 == 0) && (flag_jdgz == 0))

jiaotongdeng_dis(); display();

//

因篇幅问题不能全部显示,请点此查看更多更全内容