#include <reg51.h>
#include <intrins.h>
#define uchar unsigned char
sbit sound = P3^0;
sbit kg= P2^0; //加湿器控制开关
sbit rs=P2^5; //LCD控制口
sbit rw=P2^6;
sbit ep=P2^7;
//ad转换控制口
sbit cs=P3^5;
sbit wr=P3^6;
sbit rd=P3^7;
sbit k1=P2^1; //按键控制口
sbit k3=P2^3;
typedef unsigned char BYTE;
scan_key(); //独立按键获取键值
void lcd_pos(uchar pos); //设定显示位置
void lcd_wdat(uchar dat); //写入字符显示数据到LCD
void lcd_init(void); //LCD初始化设定
//unsigned int datpro(); //ADC0804 读出的数据处理,取平均值
//{
//uchar a1,a2,a3,a4,a5,a;
//a1=adc0804();
//a2=adc0804();
//a3=adc0804();
//a4=adc0804();
//a5=adc0804();
//a=(a1+a2+a3+a4+a5)/5;
//
//}
void delayms(unsigned char ms);
unsigned int flag=0;
uchar shiduzhi,shedingzhi=30; // 湿度值、设定值
unsigned char SDZ_Tab[] = {3,0,10,0,0}; //设定值,显示与设定使用
unsigned char
code Disp_Tab[] = {0x80,0x81,0x82,0x83,0x84,0x85,0x86,0x87,0x88,0x89,0x78};
//1602字符'0~9'加'.'
unsigned char adc0804(void) //读AD0804子程序
{
uchar data1;
cs=0;
wr=0;
delayms(1);
wr=1;
cs=1;
cs=0;
rd=0;
data1=P1;
delayms(1);
rd=1;
cs=1;
return data1;
delayms(200);
}
void Init(void)
{
lcd_pos(0x03);
lcd_wdat('S');
lcd_wdat('D');
lcd_wdat('Z');
lcd_wdat(':');
lcd_wdat('3');
lcd_wdat('0');
lcd_wdat('.');
lcd_wdat('0');
lcd_wdat('0');
lcd_pos(0x40);
lcd_wdat('S');
lcd_wdat('D');
lcd_wdat(':');
lcd_pos(0x48);
}
void system_Ini()
{
TMOD|= 0x11;
TH1 = 0xD8; //10
TL1 = 0xF0;
IE = 0x8A;
TR1 = 1;
}
void delayms(unsigned char ms)
{
unsigned char i;
while(ms--)
{
for(i = 0; i < 120; i++);
}
}
void shuru(void) //光标位置 数值加 退出 操作
{
unsigned char key_n,m=0,n;
while(flag)
{
key_n=scan_key(); //获取键值
if(key_n==2) //K1按下,移位按键
{
delayms(10); //延时
key_n=scan_key(); //再次获取
if(key_n==2) //确认按下
{
m++; //指针加一
if(m>=5) m=0; //等于五归零,实现循环
n=m+9; //显示位置
lcd_pos(n); //移动光标到指定位置
}
}
if(key_n==4) //K2按下,加一按键
{
delayms(10);
key_n=scan_key();
if(key_n==4) //确认按键
{
SDZ_Tab[m]++; //数值加一
if(SDZ_Tab[m]>=10)
SDZ_Tab[m]=0; //等于十归零,实现循环
lcd_wdat(SDZ_Tab[m]); //送出显示
lcd_pos(n); //将光标移回该位
}
}
if(key_n==8) //K3按下,确定退出设置
{
delayms(10);
key_n=scan_key();
if(key_n==8) //确认按下
{
lcd_pos(0x0F); //移走光标
shedingzhi=SDZ_Tab[0]*10; //更新设定值
shedingzhi+=SDZ_Tab[1];
shedingzhi+=SDZ_Tab[3]*0.1;
shedingzhi+=SDZ_Tab[4]*0.01;
flag=0; //清标志位
}
}
}
}
void shidu(void) //湿度采集 值=值/1.58
{
shiduzhi=adc0804(); //读取AD转换值
shiduzhi/=1.58; //转换成实际湿度值
lcd_pos(0x43); //显示位置为第二行第4位
lcd_wdat(Disp_Tab[shiduzhi%100/10]); //显示十位
lcd_wdat(Disp_Tab[shiduzhi%10]); //显示个位
lcd_wdat(Disp_Tab[10]); //显示小数点
lcd_wdat(Disp_Tab[shiduzhi*10%10]); //显示小数点后一位
}
void chuli(void) //报警模块
{
if(shiduzhi>=shedingzhi) //湿度是否大于设定值
{
kg=1; //控制继电器停止加湿
if(shiduzhi>50) //湿度是否高于极限值
sound=1; //蜂鸣器报警
else //不高于极限值
sound=0;
}
else //不高于设定值
kg=0; //控制继电器启动加湿
}
void sheding(void)
{
unsigned char key_s;
key_s=scan_key();
if(key_s&&0x08==0x08)
{
delayms(10);
key_s=scan_key();
if(key_s&&0x08==0x08)
{
flag=1;
lcd_pos(0x09);
shuru();
} }}
scan_key()
{
P2=0xff;
while(1)
{
uchar a,key;
a=0x0e;;
if((P2&&0x0e)!=0x0e)
{
delayms(1);
if((P2&&0x0e)!=0x0e)
{
key=(P2&&0x0e);
switch(key)
{
case 0x0c: return 2; break;
case 0x08: return 4; break;
case 0x00: return 8; break;
}
}
}
}
}
uchar Busy_Check(void)
{
uchar LCD_Status;
rs=0;
rw=1;
ep=1;
_nop_();
_nop_();
_nop_();
_nop_();
LCD_Status=P0&0x80;
ep=0;
return LCD_Status;
}
void lcd_wcmd(uchar cmd)
{
while(Busy_Check());
rs=0;
rw=0;
ep=0;
_nop_();
_nop_();
P0=cmd;
_nop_();
_nop_();
_nop_();
_nop_();
ep=1;
_nop_();
_nop_();
_nop_();
_nop_();
ep=0;
}
void lcd_pos(uchar pos)
{
lcd_wcmd(pos|0x80);
}
void lcd_wdat(uchar dat)
{
while(Busy_Check());
rs=1;
rw=0;
ep=0;
P0=dat;
_nop_();
_nop_();
_nop_();
_nop_();
ep=1;
_nop_();
_nop_();
_nop_();
_nop_();
ep=0;
}
void lcd_init(void)
{
lcd_wcmd(0x38);
delayms(1);
lcd_wcmd(0x0c);
delayms(1);
lcd_wcmd(0x06);
delayms(1);
lcd_wcmd(0x01);
delayms(1);
}
void main(void)
{
system_Ini();
lcd_init();
Init();
while(1);
{
shidu(); //调用湿度子程序,进行湿度检测与显示
chuli(); //对检测湿度处理,控制加湿器工作
sheding(); //设定湿度值
}
}
|