单片机照明灯智能控制器.docx
《单片机照明灯智能控制器.docx》由会员分享,可在线阅读,更多相关《单片机照明灯智能控制器.docx(14页珍藏版)》请在冰豆网上搜索。
单片机照明灯智能控制器
图7照明灯智能控制器原理图
附页1:
程序清单
//************************************
//**********1602-LEDorClock*********
//************************************
#include"at89x52.h"
#include"intrins.h"
//************************************************************
#defineucharunsignedchar
#defineuintunsignedint
#defineulongunsignedlong
ucharbdataflag;
sbitstart=flag^0;//设置时间标志位
sbitstart1=flag^1;
sbitstart2=flag^2;
sbitstart3=flag^3;
sbitstart4=flag^4;
sbitstart5=flag^5;
sbitstart6=flag^6;
sbitstart7=flag^7;
bitcasp;
sbitrs=P2^3;
sbitrw=P2^4;
sbite=P2^5;
ucharcodetable1[]={'M','C','U','','C','l','o','c',
'k','','S','y','s','t','e','m'};
ucharcodetable2[]={'','','','','',':
','','',
':
','','','.','','','',''};
ucharcodetable3[]={'0','1','2','3','4','5','6','7','8','9','S','e','t','','',''};
ucharsecond_l,second,minte,hour;
ucharcount,buffer[7],count1;
uchartempsecond,tempminte,temphour;
uchartempdaysecond,tempdayminte,tempdayhour;
voiddisplay(void);
voidscankey(void);
voiddelaysecond(void);
voiddelayfirst(void);
voidwrite(void);
voidenable(void);
voidsys_init2(void);
voidtemptime(void);
voidchecktime(void);
voidcheckdaytime(void);
voidtempdaytime(void);
voidcallmusic(void);
voidcheckled(ucharcheckled,ucharcheckled1,ucharjnz);
//*****************************************************
ucharT1count;
ucharT1minte;
ucharbdataTofirst1;
sbitTofirst=Tofirst1^0;
sbitfirstday=Tofirst1^1;
//***************************
//**********main*************
//***************************
voidmain(void)
{
uchari;//定义字符变量i
P0=0x01;enable();//
P0=0x38;enable();//
P0=0x0c;enable();//
P0=0x80;enable();//
for(i=0;i<16;i++)
{
P0=table1[i];//从液晶显示地址(0x80),开始逐步写入16个字符
write();//调用写数据子程序
}
P0=0xc0;enable();//液晶显示地址(0xc0)
for(i=0;i<16;i++)
{
P0=table2[i];//从液晶显示地址(0xc0),开始逐步写入16个字符
write();//调用写数据子程序
}
TMOD=0x11;//初始化定时器0/1的状态寄存器
TH0=(65536-50000)/256;//赋初值给定时器0TH0
TL0=(65536-50000)%256;//赋初值给定时器0TL0
TH1=(65536-50000)/256;//赋初值给定时器1TH1
TL1=(65536-50000)%256;//赋初值给定时器1TL1
sys_init2();//调用启动定时器2子程序
ET1=1;//允许定时器1中断
ET0=1;TR0=1;EA=1;//允许定时器0中断,启动定时器0,允许CPU中断
start2=0;start=0;start1=0;//位寻址区start2,start,start1为0
hour=12;minte=59;//时缓冲区赋初值为12,分缓冲区赋初值为59
while
(1)
{
if(Tofirst==0)
{
if(P3_7==0)
{
P3_6=0;//灯亮
temptime();//记录天黑后的时间,用于4个小时之后灯灭(P3_6=1)
TR1=1;
}
}
//if(P3_7==0){P1_7=0;TR1=1;Tofisrt=1;}只执行一次
if(P3_7==1)
{
P3_6=1;//灯灭
tempdaytime();
}
}
}
//************************
//******write*************
//************************
voidwrite(void)//液晶写数据子程序
{
rs=1;//rs=1;
rw=0;//rw=0;
e=0;//e=0;
delayfirst();//调用延时子程序
e=1;//e=1;
}
//**********************
//*******enable*********
//**********************
voidenable(void)//液晶使能子程序
{
rs=0;//rs=0;
rw=0;//rw=0;
e=0;//e=0;
delayfirst();//调用延时子程序
e=1;//e=1
}
//****************************
//*********timer**************
//****************************
voidtimer0()interrupt1using0
{
TH0=(65536-50000)/256;//赋初值定时器0给TH0
TL0=(65536-50000)%256;//赋初值定时器0给TL0
if((P1&0x0f)!
=0x0f)//判断P1.0-P1.4是否有键按下
{
delaysecond();//调用键盘延时子程序,用于消除干扰
if((P1&0x0f)!
=0x0f)//判断P1.0-P1.4是否有键按下
{
scankey();//调用键盘扫描子程序scankey()
}
}
count++;//计数单元count自加加
if(count==2)//如果计数单元count为2
{
count=0;//计数单元count清零
second_l++;//second_l缓冲区自加加
if(second_l==10)//如果second_l0缓冲区为10
{
second_l=0;//second_l秒缓冲区赋值为0
second++;//second缓冲区自加加
if(second==60)//如果second缓冲区的内容为24
{
second=0;///second缓冲区赋值为0
minte++;//minte缓冲区自加加
if(minte==60)//如果minte缓冲区内容为60
{
minte=0;//minte缓冲区赋值为0
hour++;//hour缓冲区自加加
if(hour==24)//如果hour缓冲区的内容为24
{
second=0;//把second缓冲区的内容赋值为0
minte=0;//把minte缓冲区的内容赋值为0
hour=0;//把hour缓冲区的内容赋值为0
}
}
}
}
}
}
//********************************
//***********display**************
//********************************
voiddisplay(void)
{
uchari;//定义字符型变量i
buffer[0]=second/10;//取出秒缓冲区(second)的高位,放入数组缓冲区buffer[0]
buffer[1]=second%10;//取出秒缓冲区(second)的高位,放入数组缓冲区buffer[1]
buffer[2]=minte/10;//取出分缓冲区(minte)的高位,放入数组缓冲区buffer[2]
buffer[3]=minte%10;//取出分缓冲区(minte)的高位,放入数组缓冲区buffer[3]
buffer[4]=hour/10;//取出时缓冲区(hour)的高位,放入数组缓冲区buffer[4]
buffer[5]=hour%10;//取出时缓冲区(hour)的高位,放入数组缓冲区buffer[5]
buffer[6]=second_l;//取出0.6秒,放入数组缓冲区buffer[6]
if(start==0)//判断是否为设置标志位,start==0为假
{
P0=0xc0;enable();//从液晶地址(0xc0)开始写数据
for(i=13;i<16;i++)
{
P0=table3[i];//P0口输出table3[]数组里面的数据
write();//调用写数据子程序
}
}
if(start==1)//判断是否为设置标志位,start==1为真
{
P0=0xc0;enable();//从液晶地址(0xc0)开始写数据
for(i=10;i<13;i++)
{
P0=table3[i];//P0口输出table3[]数组里面的数据
write();//调用写数据子程序
}
}
P0=0xc3;enable();//从液晶地址(0xc6)开始写数?
for(i=4;i<6;i++)
{
P0=table3[buffer[i]];//P0口输出table3[]数组里面的数据
write();//调用写数据子程序
}
P0=0xc6;enable();//从液晶地址(0xc6)开始写数据
for(i=2;i<4;i++)
{
P0=table3[buffer[i]];//P0口输出table3[]数组里面的数据
write();//调用写数据子程序
}
P0=0xc9;enable();//从液晶地址(0xc9)开始写数据
for(i=0;i<2;i++)
{
P0=table3[buffer[i]];//P0口输出table3[]数组里面的数据
write();//调用写数据子程序
}
P0=0xcc;enable();//从液晶地址(0xcc)开始写数据
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
P0=table3[buffer[6]];//P0口输出table3[]数组里面的数据
write();//调用写数据子程序
}
//********************************
//********************************
voidtimer1()interrupt3using1
{
TH1=(65536-50000)/256;//重新赋值给定时器1的TH1
TL1=(65536-50000)%256;//重新赋值给定时器1的TL1
checktime();
checkdaytime();
}
//***************************************************
voidsys_init2(void)//初始化定时器2
{
T2CON=0x04;//*加载定时器2的控制寄存器
T2MOD=0x00//*加载定时器2的模式寄存器*/
TH2=0xFC;//*加载定时器2的高位字节*/
RCAP2H=0xFC;//*加载定时器2的重装寄存器的高位字节*/
TL2=0x18;//*加载定时器2的低位字节*/
RCAP2L=0x18;//*加载定时2器2的重装寄存器的低位字节*/
ET2=1;//*使能定时2中断*/
TR2=1;//*启动定时器2*/
}
//****************************************************
voidtimer2(void)interrupt5using1
{
display();//调用显示子程序
}
//**********************************
voidtemptime(void)
{
tempsecond=second;//把此时秒(second)缓冲区的值赋给tempsecond
tempminte=minte;//把此时分(minte)缓冲区的值赋给tempminte
temphour=hour;//把此时时(hour)缓冲区的值赋给tempdayhour
temphour=temphour+4;//把此时时(temphour)缓冲区的值加4
}
//**********************************
voidtempdaytime(void)
{
tempdaysecond=second;//把此时秒(second)缓冲区的值赋给tempdaysecond
tempdayminte=minte;//把此时分(minute)缓冲区的值赋给tempdayminte
tempdayhour=hour;//把此时秒(hour)缓冲区的值赋给tempdayhour
tempdayminte=tempdayminte-1;//把此时秒(second)缓冲区的值赋给tempdaysecond
firstday=1;
}
//*********************************************************************
//********************************
voidcheckdaytime(void)//用于检测是否是天亮前1个小时到否
{
if(hour==temphour)//如果小时(hour)到,向下检测
{
if(minte==tempminte)//如果分钟(minute)到,再向下检测
{
if(second==tempsecond)//如果秒(second)到,执行下面指令(P3_6=0)
{
P3_6=0;//灯亮
Tofirst=0;
}
}
}
}
//***************************
voidchecktime(void)//用于检测是否是天亮前1个小时到否
{
if(hour==temphour)//如果小时(hour)到,向下检测
{
if(minte==tempminte)//如果分钟(minute)到,向下检测
{
if(second==tempsecond)//如果秒(second)到,执行下面指令(P3_6=1)
{
P3_6=1;//灯灭
Tofirst=1;
}
}
}
}
//***************************
voidscankey(void)//键盘扫描程序,用于调整标准时钟的时间
{
ucharkey;//定义一个字符变量,用于存放P1口的数据
key=P1;//把P1口的数据传送给key存储单元
switch(key)//应用switch语句,以便判断下面状态
{
case0xfe:
minte++;//当P1口等于0xfe时,minte++
callmusic();//同时调用callmusic()子程序,以便识别P1.0口按下
if(minte==60)//当minte等于60时,执行minte=0
{
minte=0;//执行minte=0语句
}
break;//退出switch语句
case0xfd:
hour++;//当P1口等于0xfd时,hour++
callmusic();//同时调用callmusic()子程序,以便识别P1.1口按下
if(hour==24)//当hour等于24时,执行hour=0
{
hour=0;//执行hour=0语句
}
break;//退出switch语句
case0xfb:
callmusic();
break;
}
}
//**********************
//*******delay**********
//**********************
voiddelayfirst(void)//延时子程序1,用于液晶显示
{
uchari,j;//定义两个字符变量i,j
for(i=1;i<30;i++)//用两个for循环语句来实现延时
for(j=1;j<19;j++);
}
//**********************
voiddelaysecond(void)//延时子程序2,用于键盘去抖动
{
uchari,j;//定义两个字符变量i,j
for(i=1;i<150;i++)
for(j=1;j<=110;j++);//用两个for循环语句来实现延时
}
voidcallmusic(void)//响铃子程序,用于驱动器BELL发声
{
uintkey;//定义一个整形变量
key=1;//初始化key=1
while(key)//当key值为真时,执行下面语句
{_nop_();//调用_nop_();函数
P1_7=~P1_7;//P1_7取反,使之高低电平变换
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
P1_7=~P1_7;//P1_7取反,使之高低电平变换
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
_nop_();//调用_nop_();函数
key++;//key值++
if(key==2400)//当key值等于2400时
{
key=0;//key值再赋于0
}
}
}