- #include<reg51.h>
- #include<absacc.h>
- #include<intrins.h>
- #define uint unsigned int
- #define uchar unsigned char
- #define ulint unsigned long int
- uchar code table0[]={ //歡迎界面
- 0xa0,0x57,0x65,0x6c,0x63,0x6f,0x6d,0x65,
- 0xa0,0x74,0x6f,0xa0,0x75,0x65,0x73,0xa0,
- 0xa0,0xa0,0x74,0x68,0x65,0x72,0x6d,0x6f,
- 0x6d,0x65,0x74,0x65,0x72,0x21,0xa0,0xa0};
- uchar table1[]={0x6d,0x61,0x78,0x3a,0x00,0x00,0x00,0xa0, //存儲報警值
- 0x6d,0x69,0x6e,0x3a,0x00,0x00,0x00,};
- uchar table2[]={ //存儲溫度
- 0x54,0x4d,0x50,0x54,0x3a,
- 0x00,0x00,0x00,0x00,0xa5,0x00,0x00,0x43};
- uchar code table3[]={ //提醒設定報警值
- 0xa0,0x50,0x6c,0x65,0x61,0x73,0x65,0xa0,
- 0xa0,0x63,0x68,0x61,0x72,0x67,0x65,0xa0,
- 0xa0,0xa0,0xa0,0x79,0x6f,0x75,0x72,0xa0,
- 0x63,0x61,0x72,0x64,0x21,0xa0,0xa0,0xa0};
- uchar table4[]={ //輸入界面
- 0x50,0x6c,0x65,0x61,0x73,0x65,0xa0,0x69,
- 0x6e,0x70,0x75,0x74,0x3a};
- sbit E=P3^7;
- sbit RW=P3^6;
- sbit RS=P3^5;
- sbit flag=P1^7;
- sbit dec=P3^0;
- sbit inc=P3^1;
- sbit ok_max=P3^2;
- sbit ok_min=P3^4;
- sbit out=P2^1;
- sbit DQ=P2^3;
- sbit beep=P2^2;
- uchar p,tflag;
- uint tvalue;
- /*****************延時函數**********************/
- void delay_18B20(unsigned int i)
- {
- while(i--);
- }
- /**********ds18b20初始化函數**********************/
- void Init_DS18B20(void)
- {
- unsigned char x=0;
- DQ = 1; //DQ復位
- delay_18B20(8); //稍做延時
- DQ = 0; //單片機將DQ拉低
- delay_18B20(80); //精確延時 大于 480us
- DQ = 1; //拉高總線
- delay_18B20(14);
- x=DQ; //稍做延時后 如果x=0則初始化成功 x=1則初始化失敗
- delay_18B20(20);
- }
- /***********ds18b20讀一個字節**************/
- unsigned char ReadOneChar(void)
- {
- unsigned char i=0;
- unsigned char dat = 0;
- for (i=8;i>0;i--)
- {
- DQ = 0; // 給脈沖信號
- dat>>=1;
- DQ = 1; // 給脈沖信號
- if(DQ)
- dat|=0x80;
- delay_18B20(4);
- }
- return(dat);
- }
- /*************ds18b20寫一個字節****************/
- void WriteOneChar(unsigned char dat)
- {
- unsigned char i=0;
- for (i=8; i>0; i--)
- {
- DQ = 0;
- DQ = dat&0x01;
- delay_18B20(5);
- DQ = 1;
- dat>>=1;
- }
- }
- /**************讀取ds18b20當前溫度************/
- unsigned int ReadTemperature(void)
- { unsigned char tl,th;
- float t;
- Init_DS18B20();
- WriteOneChar(0xCC); // 跳過讀序號列號的操作
- WriteOneChar(0x44); // 啟動溫度轉換
- delay_18B20(80); // 這個延時很重要
- Init_DS18B20();
- WriteOneChar(0xCC); //跳過讀序號列號的操作
- WriteOneChar(0xBE); //讀取溫度寄存器等(共可讀9個寄存器) 前兩個就是溫度
- delay_18B20(80);
- tl=ReadOneChar(); //讀取溫度值低位
- th=ReadOneChar(); //讀取溫度值高位
- tvalue=th;
- tvalue<<=8;
- tvalue=tvalue|tl;
- if(tvalue<0x0fff) //判斷正負
- {
- tflag=0; //符號標記位
- table2[5]=0xa0; //存儲'+'號
- }
- else
- {
- tvalue=~tvalue+1; //負數取反加一
- tflag=1;
- table2[5]=0x2d; //存儲'-'號
- }
- t=tvalue*(0.0625);
- tvalue=t*100; //溫度值擴大100倍,精確到2位小數
- return(tvalue);
- }
- /*************處理當前溫度******************/
- void show1(void);
- void DeelTemperatre(uint t)
- {
- table2[6]=t/10000+0x30;
- if(table2[6]==0x30) //百位為0,就消隱
- {
- table2[6]=0xa0;
- }
- table2[7]=t%10000/1000+0x30; //十位
- table2[8]=t%1000/100+0x30; //個位
- table2[10]=t%100/10+0x30; //小數位
- table2[11]=t%10+0x30;
- }
- /****************警告函數*******************/
- void warn(uchar s,uchar led)
- {
- uchar i,j,k;i=s;
- P2=~(led);
- for(k=0;k<20;k++)
- {for(j=0;j<200;j++)//喇叭發聲的時間循環,改變大小可以改變發聲時間長短
- {
- delay_18B20(i); //參數決定發聲的頻率,估算值,可以自行更改參數并
- beep=!beep;
- }
- }
- P2=0xff;
- beep=1;
- }
- /******************報警處理函數**************/
-
- void deal(uint fuzhi)
- {
- uchar t1,th,tl,i;
- char t1_c,th_c,tl_c,th_s,tl_s;
- t1=fuzhi/100;
- if(table2[5]==0x2d) //存儲實際溫度換成有符號數實際溫度
- { //符號位為'-'換成負數
- t1_c=t1;
- t1_c=~t1_c;
- }
- else
- {
- t1_c=t1;
- }
-
- th=(table1[5]-0x30)*10+(table1[6]-0x30); //存儲上限溫度換成有符號數溫度
- if(table1[4]==0x2d)
- {
- th_c=th;
- th_c=~th_c;
- th_s=th_c-2; //設置第二高溫度報警線
- }
- else
- {
- th_c=th;
- th_s=th_c-2;
- }
-
- tl=(table1[13]-0x30)*10+(table1[14]-0x30); //存儲下限溫度換成有符號數溫度
- if(table1[12]==0x2d)
- {
- tl_c=tl;
- tl_c=~tl_c;
- tl_s=tl_c+2;
- }
- else
- {
- tl_c=tl;
- tl_s=tl_c+2; //設置低二道報警線溫度
- }
- if(t1_c>=th_s&&t1_c<th_c) //大于第二高上限值小于最高上限,進行預報警
- {
- warn(20,0x80); //控制預報警聲音,點亮指示燈
- out=1;
- }
- else if(t1_c>=th_c) //高于最高上限
- {
- warn(40,0x40); //先報警
- out=0; //自動開發動機
- }
- else if(t1_c<=tl_s&&t1_c>tl_c) //進行預報警
- {
- warn(20,0x20);
- out=1;
- }
- else if(t1_c<=tl_c)
- {
- warn(40,0x10);
- out=0;
- }
- else
- {
- i=5; //利用顯示延時
- while(i--)
- {
- DeelTemperatre(ReadTemperature());
- show1();
- out=1;
- }
- }
- }
- /*************************LCD顯示****************************/
- /**********************延時函數***********************/
- void delay0()
- {
- uint a,b;
- for(a=0;a<600;a++)
- for(b=0;b<600;b++);
- }
- void delay1()
- {
- uint e;
- for(e=100;e>0;e--);
- }
- void delay2()
- {
- uint a,b;
- for(a=0;a<100;a++)
- for(b=0;b<100;b++);
- }
- /***********************判忙函數*********************/
- void busy()
- {
- do
- {
- P1=0xff;
- RS=0;
- RW=1;
- E=0;
- E=1;
- }while(flag);
- }
- /*************功能:寫函數**********************************/
- /*********入口參數:con=1代表寫指令,con=0代表寫數據,com代表數據
- /*********出口參數:無;
- **********************************************************/
- void write(uchar con,uchar com)
- {
- busy();
- RS=con;
- RW=0;
- E=1;
- P1=com;
- E=0;
- }
- /***********************lcd初始化**********************/
- void init()
- {
- write(0,0x01);
- write(0,0x38);
- write(0,0x0c);
- }
- /***********************顯示歡迎界面********************/
- void show0()
- {
- uint i;
- write(0,0x80);
- for(i=0;i<16;i++)
- write(1,table0[i]);
- busy();
- write(0,0xc0);
- for(i=16;i<32;i++)
- write(1,table0[i]);
- busy();
- delay0();
- }
- /***********************顯示溫度界面*********************/
- void show1()
- {
- uint i,j;
- write(0,0x01);
- write(0,0x80);
- for(i=0;i<15;i++)
- write(1,table1[i]);
- busy();
- write(0,0xc0);
- for(j=0;j<13;j++)
- write(1,table2[j]);
- busy();
- delay0();
- }
- /*************************改值函數******************************/
- void input()
- {
- uchar i,sign=0,k=0;
- char t=0,z=0;
- ok_max=1; //上限值確認鍵
- ok_min=1; //下限值確認鍵
- write(0,0x01); //清屏指令
- while(ok_max==1&&ok_min==1) //當確認鍵按下,結束循環
- {
- inc=1;
- dec=1;
- if(inc==0) //加一鍵按下
- {
- delay2(); //去抖動
- if(inc==0)
- {
- if(t<99) //設定最高上限為99
- {
- if(t>=0) //對符號數進行處理,大于0,保持不變
- {
- t++;
- sign=0xa0; //溫度顯示標志位
- }
- else{
- if(t==-1) //小于0,首先判斷是否等于-1,因為再加一為0,消‘-’符號位
- {
- t++;
- k--; //k為負數的絕對值
- sign=0xa0;
- }
- else{ //不為-1,前面要加符號位‘-’
- t++;
- k--;
- sign=0x2d;
- }
- }
- }
- else ; //大于99不再增加
- }
- }
- if(dec==0) //減一確認鍵按下
- {
- delay2(); //去抖動
- if(dec==0)
- {
- if(t<=-20); //設定下限為-20
- else{
- if(t<=0)
- {t--;
- k++;
- sign=0x2d;
- }
- else
- {
- t--;
- sign=0xa0;
- }
- }
- }
- }
- if(t<=0){z=t;t=k;} //t<=0,取絕對值
- write(0,0x80);
- for(i=0;i<13;i++)
- write(1,table4[i]); //顯示提醒輸入界面
- busy();
- write(0,0xc0);
- write(1,sign); //將設定的值顯示
- write(1,t/100%10+0x30);
- write(1,t/10%10+0x30);
- write(1,t%10+0x30);
- write(1,0x43);
- busy();
- if(z<0)t=z;
- delay1();
- }
- if(t<0)t=~t+1;
- p=t;
- if(ok_max==0) //存儲上限值
- {
- table1[6]=p%10+0x30;
- table1[5]=p/10%10+0x30;
- table1[4]=sign;}
- else{ //存儲下限值
- table1[14]=p%10+0x30;
- table1[13]=p/10%10+0x30;
- table1[12]=sign;
- }
- }
- /******************外部中斷0函數*******************/
- void Exter1(void) interrupt 2
- {
- EX1=0;
- input();
- EX1=1;
- }
- void main()
- {
- uchar l,i=5;
- init();
- show0();
- delay2();
- input();
- EA=1;
- EX1=1;
- IT1=1;
- while(1)
- {
- out=1; //電動機開關關閉
- DeelTemperatre(ReadTemperature()); //去溫度值
- show1();
- deal(ReadTemperature()); //溫度處理
- while(i--) //利用顯示延時
- {
- DeelTemperatre(ReadTemperature());
- show1();
- deal(ReadTemperature());
- }
- }
- }
復制代碼
|