#include<reg51.h>
#define uint unsigned int
#define uchar unsigned char
sbit lcdrs=P3^0;
sbit lcdrw=P3^1;
sbit lcden=P3^2;//LCD选通线
sbit DQ=P1^7;//18B20引脚
uint value;//温度值
sbit sound=P1^6;//蜂鸣器
sbit warning=P3^5;//LED报警灯
sbit greenled=P3^6;//LED报警灯
sbit k1=P1^0;//set
sbit k2=P1^1;//+
sbit k3=P1^2;//-
char max=40;//初始温度最大值
char min=10;//初始温度最小值
uchar change_flag;//按键次数
uchar code table1[]={0x28,0x30,0xc5,0xb8,0x00,0x00,0x00,0x8e};
uchar code table2[]={0x28,0x31,0xc5,0xb8,0x00,0x00,0x00,0xb9};
uchar code table3[]={0x28,0x32,0xc5,0xb8,0x00,0x00,0x00,0xe0};
uchar code table4[]={0x28,0x33,0xc5,0xb8,0x00,0x00,0x00,0xd7};
uchar LCD_LINE_ONE[16]="tp1: ";
uchar LCD_LINE_TWO[16]="tp2: ";
uchar LCD_LINE_THREE[16]="tp3: " ;
uchar LCD_LINE_FOUR[16]="tp4: ";
uchar code table6[]="max: min: ";
uint temper[5];
bit fg=0;
void delay(uint n)
{ uint x,y;
for(x=n;x>0;x--)
for(y=110;y>0;y--);
}
void write_com(uchar com)
{
lcdrs=0; //rs=0时输入指令
P2=com;
delay(5);
lcden=1; //en=1时读取信息
delay(5);
lcden=0; //1 -> 0 执行指令
}
void write_dat(uchar dat)
{
lcdrs=1; //rs=1时输入数据
P2=dat;
delay(5);
lcden=1;
delay(5);
lcden=0;
}
void init_lcd()
{
lcden=0;
lcdrw=0;
write_com(0x38); //8位数据,双列,5*7字形
write_com(0x0c); //开启显示屏,关光标,光标不闪烁
write_com(0x06); //显示地址递增,即写一个数据后,显示位置右移一位
write_com(0x01);
}
void delay_us(uchar t)//微妙延时
{
while(t--);
}
void init_ds18b20() //数据初始化
{
DQ=1;
delay_us(4);
DQ=0;
delay_us(80);
DQ=1;
delay_us(200);
}
void write_ds18b20(uchar dat) //写数据
{
uchar i;
for(i=0;i<8;i++)
{
DQ=0;
DQ=dat&0x01;
delay_us(15);
DQ=1;
dat=dat>>1;
}
delay_us(10);
}
uchar read_ds18b20() //读数据
{
uchar i=0,readat=0;
for(i=0;i<8;i++)
{
DQ=0;
readat=readat>>1; //八位全部都是0,向右移一位后,仍然全是0
DQ=1;
if(DQ) //如果DQ为1,readat进行或运算,如果为0,则子语句不执行,直接for循环此时采集的数据是0
readat=readat|0x80;//此时最高位为1 ,然后再进行for循环 最高位成为第七位,依次往复
delay_us(10);
}
return readat;
}
void check_rom(uchar a) //匹配序列号
{
uchar j;
write_ds18b20(0x55);
if(a==1)
{
for(j=0;j<8;j++)
{
write_ds18b20(table1[j]);
}
}
if(a==2)
{
for(j=0;j<8;j++)
{
write_ds18b20(table2[j]);
}
}
if(a==3)
{
for(j=0;j<8;j++)
{
write_ds18b20(table3[j]);
}
}
if(a==4)
{
for(j=0;j<8;j++)
{
write_ds18b20(table4[j]);
}
}
}
uint change_ds18b20(uchar z)//为DS18B20序号
{
uchar tl,th;
init_ds18b20(); //初始化
write_ds18b20(0xcc); //跳过
init_ds18b20();
if(z==1)
{
check_rom(1); // 匹配rom1
}
if(z==2)
{
check_rom(2); // 匹配rom2
}
if(z==3)
{
check_rom(3); // 匹配rom3
}
if(z==4)
{
check_rom(4); // 匹配rom4
}
write_ds18b20(0x44);
init_ds18b20();
write_ds18b20(0xcc);
init_ds18b20();
if(z==1)
{
check_rom(1); //
}
if(z==2)
{
check_rom(2); //
}
if(z==3)
{
check_rom(3); //
}
if(z==4)
{
check_rom(4); //
}
write_ds18b20(0xbe); //启动读暂存器。读内部ram中9字节温度数据
tl=read_ds18b20();
th=read_ds18b20();
value=th;
value=value<<8;
value=value|tl;
if(th < 0x80)
{ fg=0; }
if(th>= 0x80)
{ fg=1;
value=~value+1;
}
value=value*(0.0625*10);
return value;
}
void display_lcd1604(uchar z)//显示各个温度
{
uchar i;
if(z==1)
{
write_com(0x80);
for(i=0;i<6;i++)
{
write_dat(LCD_LINE_ONE);
delay(3);
}
if(fg==1)
{
write_dat(0xb0);
}
if(fg==0)
{
write_dat(0x20);
}
write_dat(value/100+0x30);
write_dat(value%100/10+0x30);
write_dat(0x2e);
write_dat(value%10+0x30);
write_dat(0xdf);
write_dat(0x43);
}
if(z==2)
{
write_com(0xC0);
for(i=0;i<6;i++)
{
write_dat(LCD_LINE_TWO);
delay(3);
}
if(fg==1)
{
write_dat(0xb0);
}
if(fg==0)
{
write_dat(LCD_LINE_TWO);
}
write_dat(value/100+0x30);
write_dat(value%100/10+0x30);
write_dat(0x2e);
write_dat(value%10+0x30);
write_dat(0xdf);
write_dat(0x43);
}
if(z==3)
{
write_com(0x90);
for(i=0;i<6;i++)
{
write_dat(LCD_LINE_THREE);
delay(3);
}
if(fg==1)
{
write_dat(0xb0);
}
if(fg==0)
{
write_dat(0x20);
}
write_dat(value/100+0x30);
write_dat(value%100/10+0x30);
write_dat(0x2e);
write_dat(value%10+0x30);
write_dat(0xdf);
write_dat(0x43);
}
if(z==4)
{
write_com(0xD0);
for(i=0;i<6;i++)
{
write_dat(LCD_LINE_FOUR);
delay(3);
}
if(fg==1)
{
write_dat(0xb0);
}
if(fg==0)
{
write_dat(0x20);
}
write_dat(value/100+0x30);
write_dat(value%100/10+0x30);
write_dat(0x2e);
write_dat(value%10+0x30);
write_dat(0xdf);
write_dat(0x43);
}
}
void lcd_set_mun()//显示设置菜单
{
uchar i;
write_com(0x80);
for(i=0;i<6;i++)
{
write_dat(table6);
delay(3);
}
}
void lcd_set(char max,char min)//显示最大最小值
{
uchar x1,x2,x3,x4;
uchar flag_max,flag_min;
if(max<0)
{
flag_max=1;
max=-max;
}
else
flag_max=0;
if(min<0)
{
flag_min=1;
min=-min;
}
else
flag_min=0;
x1=max/10;
x2=max%10;
x3=min/10;
x4=min%10;
write_com(0x80+0x40+0x03);
if(flag_max==1)write_dat('-');
else write_dat(' ');
write_dat(x1+0x30);
write_dat(x2+0x30);
write_com(0x80+0x40+0x0b);
if(flag_min==1)write_dat('-');
else write_dat(' ');
write_dat(x3+0x30);
write_dat(x4+0x30);
}
void key1()
{
if(k1==0)
{
change_flag++;
if(change_flag>2)
change_flag=0;
}
while(k1==0);
}
void key2()
{
if(k2==0)
{
if(change_flag==1)
max++;
if(change_flag==2)
min++;
}
while(k2==0);
}
void key3()
{
if(k3==0)
{
if(change_flag==1)
max--;
if(change_flag==2)
min--;
}
while(k3==0);
}
void key()
{
key2();
key1();
key3();
}
void alarm(uint t )
{
int tt;
t=t*0.1;
if(fg==0)
{
tt=t;
}
if(fg==1)
{
tt=~t+1;
}
if(tt>max)
{
sound=0;
warning=1;
greenled=0;
}
else
{
if(tt<min)
{
sound=0;
warning=1;
greenled=0;
}
else
{
sound=1;
warning=0;
greenled=1;
}
}
}
void main()
{
uchar m=1;
uchar i;
uchar a=1,b=1;
warning=0;
greenled=1;
init_lcd();
for(i=1;i<5;i++)
{
change_ds18b20(i);
}
while(1)
{
if(change_flag==0)
{
if(a==1)
{b=1;
a=0;
write_com(0x01);
}
for(i=0;i<6;i++)
{
key();
display_lcd1604(m);
temper[m]=change_ds18b20(m);
alarm(temper[m]);
}
m++;
if(m>4) m=1;
}
else
{
if(b==1)
{
a=1;
b=0;
write_com(0x01);
lcd_set_mun();
}
key();
lcd_set(max,min);
}
}
}
|