基于51单片机的24小时定时控制系统
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
姓名:余明永学号:E01214308 专业:网络工程
完成时间:2014/12/31
基于51单片机的24小时定时控制系统
E01214308 余明永
安徽大学计算机科学与技术学院,安徽合肥230061
摘要:定时开关控制器在工业方面的自动控制,办公场所的电器控制等有着极为广泛的用途;本文利用89C51单片机的定时器计数器时钟电路设计一套24小时范围内的定时控制系统;可方便的实现对家庭电器和工业方面的自动控制;该定时开关控制器具有简单易制、价格低廉、控制时间可精确到秒等优点,还可以实时显示时间,具有较高的应用价值。
关键字:单片机时钟定时控制开关
Timing Control System of 24h Designing Based on 51MCU
E01214308 YU Ming-yong
Department of Computer Science and Technology, Anhui University, Hefei 230601, China Abstract: Automatic control timing controller has a very wide range of uses in the industry and office applicant control. In this paper, we designed the timing control system including a set of 24 hours within the scope of using the timer counter clock circuit based on mcs-51; It can realize the automatic control of household appliances and industrial aspects very conveniently; the timing switch controller has the very simple and easy preparation, and it is also very cheap, It can control the time very accurately to seconds. Also show the time on time. This application is of great value.
Keywords: MCU; Clock; Timing; Control; Switch
0引言
电子定时器在家用电器中经常用于延时自动关机、定时。
延时自动关机可用于:收音机、电视机、录音机、催眠器、门灯、路灯、汽车头灯、转弯灯以及其他电器的延时断电及延时自停电源等。
定时可用于:照相定时曝光、定时闪光、定时放大、定时调速、定时烘箱、冰箱门开定时报警、水位定时报警、延时催眠器、延时电铃、延时电子锁、触摸定时开关等。
例如:空调中的定时器,在工作一段时间之后便能自动切断电源停止工作。
夏季夜间使用,入睡前先顶好时间,等睡熟后到了预定时间,空调自动关机。
方便节能。
定时器除了应用于家用电器外,还广泛地用于工业农业生产和服务设施,甚至军事等。
单片机的定时器是单片机里最“活跃”的部件之一,很多程序、应用系统都离不开定时器。
由于定时器的应用与单片机的其他硬件相关,存在着一定的复杂性。
而定时器也是单片机应用中解决某类复杂问题的最为有效的方法,应用非常广泛。
本文设计了基于单片机系统的一个简单的定时开关
控制系统。
可以灵活的承载多方面有定时控
制需求的设备的控制。
1整体方案设计
整个系统由51单片机,时钟电路,复位电路,独立按键,显示电路,报警器以及继电器等部分组成[1](结构图如图一)。
定时开关控制系统设计主要以STC89C51单片机为核心[2],通过DS1302进行精准的时间控制[3],独立按键控制设置实时时间以及定时开、关时间,由8个8段LED数码管显示实时的系统时间,并实现交互的设置开关定时时间。
报警器用蜂鸣器当到定时时间时蜂鸣器发出十秒左右报警声以提示用户。
继电器、受控电器插座及受控电器组成一个执行机构,当定时时间到时,单片机向继电器输出一个高电平使继电器工作,继电器常开触点闭合接通受控电器插座,使受控电器通电加以工作,从而完成定时开关电器的功能。
[4]
图一定时开关系统构成图
2硬件系统设计
硬件系统设计采用所学习单片机开发板的设计电路做些简要的修改,并添加继电器电路,电路原理图见图二。
独立按键与单片机K1,K2,K3,K4分别与51单片机的P3^0,P3^1,P3^2,P3^3口相接。
K3采用中断方式按下切换实时时间的设置状态和运行状态;K4切换选择显示实时时间,定时开时间点,定时关时间点,在定时时间点
图二定时开关系统硬件结构图
可进行设置改变定时时间;K1在设置状态下起作用,进行选择设置时分秒;K2在设置状态下起作用对设置项的值进行加一。
显示时间的八个LED八段数码管通过一个74138
译码器进行选择,数码管输入口通过
74573与单片机P0口相连;138译码器的输入口为P2^2,P2^3,P2^4。
本系统采用了两个LED灯区分设置选项,两灯都不亮数码管显示为实时时间,两灯亮一灯为开关关闭定时时间,两灯全亮为开关开启定时时间,占用P2^0,P2^1两个接口。
蜂鸣器报警装置接单片机P1^5口,通过P1^5口的高低电平不断变化产生交流信号使蜂鸣器发声。
继电器与单片机的P1^0口相接,输出1时继电器使电源接通控制电器正常工作,输出0时继电器使电源断开控制电器停止工作。
3软件系统设计
定时开关控制软件实现较为简单,主程序主要是在单片机的控制下,对键盘的输入信息进行存储分析,驱动LED数码管显示出相关信息,并通过对比分析定时时间与时钟,控制继电器的通、断,从而达到控制电器通断电。
在这个过程中,单片机首先进行初始化,显示值初始化、继电器断开、以及单片机振荡频率的校准等。
单片机每执行一次循环对定时时间和时钟进行一次比较。
[5]为了实现时钟走时与所在地时间一致和满足要求,设定了时钟设置和定时设置的功能。
时钟设置和定时设置都在主函数里的while循环中实现,对于设置的按键采用扫面检测的方法,而进入设置状态是用中断方法进入设置状态。
程序设计的流程图如图三。
图三定时开关系统设计流程图
程序初始化后,设置定时器T0工作在方式1用于计时,同时设置开关定时时间,执行显示程序。
当定时时间设置好后,系统不断的查询定时时间到否,定时开关开时间到时P1^0=1,继电器闭合,受控电器工作,同时是控制蜂鸣器报警变量设置时间值,使蜂鸣器控制P1^5电平高低不断交替变化产生交流信号使蜂鸣器报警。
在程序执行过程中中断0控制着定时器的启动和暂停,当暂停时可修改实时时钟的时间,程序查询检查K1和K2按键是否按下,K1选择设定位“时、分、秒”,K2设置当前选择的设定位数值加一。
K4切换显示模式:实时时钟,定时关
时间,定时开时间。
在模式切换时对应LED1,LED0显示灯改变,实时时钟两灯都灭,定时关时间显示一个灯,定时开时间显示两个灯。
在定时开关状态下即可由K1,K2键设置定时的时间值,K1,K2的功能与实时时钟设置相同。
具体软件实现代码如下:
#include<reg51.h>
sbit K1=P3^0;
sbit K2=P3^1;
sbit K3=P3^2;
sbit K4=P3^3;
unsigned char Time=0;
//用来计时间的值
#define DIG P0
sbit LSA=P2^2;
sbit LSB=P2^3;
sbit LSC=P2^4;
sbit LED0=P2^0;
sbit LED1=P2^1;
sbit Beep=P1^5;
sbit Switch=P1^0;
unsigned char code
DIG_CODE[10]={0x3f,0x06,0x5b,0x4f,0x66,0x 6d,0x7d,0x07,0x7f,0x6f};//0123456789 unsigned char Num=0;
unsigned int
disp[8]={0x3f,0x3f,0x3f,0x3f,0x3f,0x3f,0x 3f,0x3f};
unsigned char hour=0,minit=0,second=0; unsigned char
Thour[2]={0,0},Tminit[2]={0,0},Tsecond[2] ={0,0};
unsigned char Count=0;//设定选择设置项unsigned char SetPlace;//设置位选择unsigned int CT=0;//设定值闪烁控制
void Delay1ms(unsigned int c);
void TimerConfiguration();
void Int0Configuration();
void Int1Configuration(); unsigned char ReSet=1;
/**************************************** * 函数名 : main
* 函数功能 : 主函数
* 输入 : 无
* 输出 : 无
**************************************/ void main(void)
{
unsigned char i=0;
unsigned char m;
unsigned BCT=0;//报警时长设定
Switch=0;
TimerConfiguration();
Int0Configuration();
Int1Configuration();
while(1)
{
if(Count==0)
{
if(TR0==0)
{
CT++;
if(CT>2000)CT=0;
if(K1==0) //检测按键K2是否按下
{
Delay1ms(10); //消除抖动
if(K1==0)
{
SetPlace++;
if(SetPlace>=3)
SetPlace=0;
}
while((i<50)&&(K1==0)) //检测按键是否松开
{
Delay1ms(10);
i++;
}
i=0;
}
if(K2==0) //检测按键K3是否按下
{
Delay1ms(10); //消除抖动
if(K2==0)
{
if(SetPlace==0)
{
second++;
if(second>=60)
second=0;
}
else
if(SetPlace==1)
{
minit++;
if(minit>=60)
minit=0;
}
else
{
hour++;
if(hour>=24)
hour=0;
}
}
while((i<50)&&(K2==0)) //检测按键是否松开
{
Delay1ms(10);
i++;
}
i=0;
}
}
//数值转换为LED数码管显示
if(SetPlace==0&&CT>1000)
{
disp[7] = 0;
disp[6] = 0;
}
else
{
disp[7] =
DIG_CODE[second%10];
disp[6] =
DIG_CODE[second/10];
}
disp[5] = 0X40;
if(SetPlace==1&&CT>1000)
{
disp[4] = 0;
disp[3] = 0;
}
else
{
disp[4] =
DIG_CODE[minit%10];
disp[3] =
DIG_CODE[minit/10];
}
disp[2] = 0X40;
if(SetPlace==2&&CT>1000)
{
disp[1] = 0;
disp[0] = 0;
}
else
{
disp[1] =
DIG_CODE[hour%10];
disp[0] =
DIG_CODE[hour/10];
}
}
else//设定定时时间
{ //设置定时点
m=Count-1;
CT++;
if(CT>2000)CT=0;
if(K1==0) //检测按键K2是否按下
{
Delay1ms(10); //消除抖动
if(K1==0)
{
SetPlace++;
if(SetPlace>=3)
SetPlace=0;
}
while((i<50)&&(K1==0)) //检测按键是否松开
{
Delay1ms(10);
i++;
}
i=0;
}
if(K2==0) //检测按键K3是否按下
{
Delay1ms(10); //消除抖动
if(K2==0)
{
if(SetPlace==0)
{
Tsecond[m]=Tsecond[m]+1;
if(Tsecond[m]>=60)
Tsecond[m]=0;
}
else
if(SetPlace==1)
{
Tminit[m]=Tminit[m]+1;
if(Tminit[m]>=60)
Tminit[m]=0;
}
else
{
Thour[m]=Thour[m]+1;
if(Thour[m]>=24)
Thour[m]=0;
}
}
while((i<50)&&(K2==0)) //检测按键是否松开
{
Delay1ms(10);
i++;
}
i=0;
}
//数值转换为LED数码管显示
if(SetPlace==0&&CT>1000)
{
disp[7] = 0;
disp[6] = 0;
}
else
{
disp[7] =
DIG_CODE[Tsecond[m]%10];
disp[6] =
DIG_CODE[Tsecond[m]/10];
}
disp[5] = 0X40;
if(SetPlace==1&&CT>1000)
{
disp[4] = 0;
disp[3] = 0;
}
else
{
disp[4] =
DIG_CODE[Tminit[m]%10];
disp[3] =
DIG_CODE[Tminit[m]/10];
}
disp[2] = 0X40;
if(SetPlace==2&&CT>1000)
{
disp[1] = 0;
disp[0] = 0;
}
else
{
disp[1] =
DIG_CODE[Thour[m]%10];
disp[0] =
DIG_CODE[Thour[m]/10];
}
}
//检测是否到设定的时间
if(TR0==1)
{
if(hour==Thour[1])
if(minit==Tminit[1])
if(second==Tsecond[1])
{
Switch=1;
BCT=4000; //值为4000报警时长十秒钟左右
}
if(hour==Thour[0])
if(minit==Tminit[0])
if(second==Tsecond[0])
{
Switch=0;
BCT=2000;
}
if(BCT>0)
{
BCT--;
Beep= 1;
Delay1ms(1);
Beep= 0;
Delay1ms(1);
}
}
//--显示时钟--//
DIG=0; //消隐
switch(Num) //位选,选择点亮的数码管,
{
case(7):
LSA=0;LSB=0;LSC=0; break;
case(6):
LSA=1;LSB=0;LSC=0; break;
case(5):
LSA=0;LSB=1;LSC=0; break;
case(4):
LSA=1;LSB=1;LSC=0; break;
case(3):
LSA=0;LSB=0;LSC=1; break;
case(2):
LSA=1;LSB=0;LSC=1; break;
case(1):
LSA=0;LSB=1;LSC=1; break;
case(0):
LSA=1;LSB=1;LSC=1; break;
}
DIG=disp[Num]; //段选,选择显示的数字。
Num++;
if(Num>7)
Num=0;
}
}
/**************************************** * 函数名 : Delay1ms()
* 函数功能 : 延时1ms
* 输入 : c
* 输出 : 无
**************************************/
void Delay1ms(unsigned int c) //误差 0us {
unsigned char a,b;
for (; c>0; c--)
{
for(b=199;b>0;b--)
{
for(a=1;a>0;a--);
}
}
}
/**************************************** * 函数名 : TimerConfiguration() * 函数功能 : 配置定时器值
* 输入 : 无
* 输出 : 无
**************************************/
void TimerConfiguration()
{
TMOD = 0x01; //选择工作方式1
TH0 = 0x3c; //设置初始值
TL0 = 0x0b0;
EA = 1; //打开总中断
ET0 = 1; //打开定时器0中断
TR0 = 0; //启动定时器0
}
/**************************************** * 函数名 : Timer0()
* 函数功能 : 定时器0中断函数
* 输入 : 无
* 输出 : 无
**************************************/
void Timer0() interrupt 1
{
TH0 = 0x3c; //设置初始值
TL0 = 0xb0;
Time++;
if(Time>=20&&TR0==1) //一秒钟来到改变数值
{
Time=0;
second++;
if(second==60)
{
second=0;
minit++;
if(minit==60)
{
minit=0;
hour++;
if(hour==24)
{
hour=0;
}
}
}
}
}
/**************************************** * 函数名 : Int0Configuration() * 函数功能 : 配置外部中断0
* 输入 : 无
* 输出 : 无
***************************************/
void Int0Configuration()
{
//设置INT0
IT0=1;//跳变沿出发方式(下降沿)
EX0=1;//打开INT0的中断允许。
EA=1;//打开总中断
}
/**************************************** * 函数名 : Int0() interrupt 0 * 函数功能 : 外部中断0的中断函数
* 输入 : 无
* 输出 : 无
****************************************/ void Int0() interrupt 0
{
Delay1ms(10);
if(K3==0)
{
TR0=~TR0;
Time=0;
CT=0;
}
}
/**************************************** * 函数名 : Int1Configuration() * 函数功能 : 配置外部中断1
* 输入 : 无
* 输出 : 无
****************************************/ void Int1Configuration()
{
//设置INT0
IT1=1;//跳变沿出发方式(下降沿)
EX1=1;//打开INT0的中断允许。
EA=1;//打开总中断
}
/**************************************** * 函数名 : Int1() interrupt 2 * 函数功能 : 外部中断0的中断函数
* 输入 : 无
* 输出 : 无
****************************************/ void Int1() interrupt 2
{
Delay1ms(10);
if(K4==0)
{
CT=0;
Count++;
if(Count>2)
Count=0;
switch(Count)
{
case 0:
LED0=1;LED1=1;break;//实时时钟模式
case 1: LED0=0;LED1=1;break;//定时关闭模式
case 2:
LED0=0;LED1=0;break;//定时开启模式
}
}
}
4结语
使用此系统要设置好定时开启时间,和定时关闭时间,然后需要对系统的实时时钟进行设置以便与当地时间一致。
最后方可按K3键启动实时时钟。
当时间到预设定时时间报警器变会发出警报,并开启或关闭控制电路。
该智能定时开关采用C语言编写,以STC89C52和DS1302为核心,具备时间准确,功耗低,增加功能方便。
能较好的满足用户要求。
【参考文献】
[1] 万隆,巴奉丽. 单片机原理及应用技术[M] 北京:清华大学出版社,2010.3.[2] 刘焕平,李娟.基于51单片机的智能定时控制系统设计[J].石家庄职业技术学院学报,2010 (6):26⁃28.
[3] 张宁丹,金桂. 基于STC89C52单片机DS1302时钟芯片定时开关的设计与仿真[J].现代电子技术,2013 36(8):4-6.[4] 雷道仲,李书成,罗政球. 基于单片机定时开关的设计[J].贵州教育学院学报,2005 (4):224⁃225.
[5] 张红燕,何膳君. 基于单片机的定时开关插座的设计与制作[J].电子世界2014 (05).。