|
1、溫度可通過調(diào)整DS18B20“+”“-”進(jìn)行調(diào)整。
2、當(dāng)溫度超出范圍,會有聲光報(bào)警
3、因?yàn)樵趐roteus中找不到三極管8550,所以拿了NPN管MSP8098代替,其原理是相同的,但程序稍做修改,位選本來用低電平,現(xiàn)在高電平位選。
4、如何裝載程序?雙擊單片機(jī)—program file—找到相應(yīng)的hex文件。
1523791717856.jpg (26.1 KB, 下載次數(shù): 59)
下載附件
2018-5-31 21:46 上傳
仿真原理圖如下(proteus仿真工程文件可到本帖附件中下載)
0.png (20.47 KB, 下載次數(shù): 73)
下載附件
2018-6-1 03:57 上傳
0.png (9.77 KB, 下載次數(shù): 74)
下載附件
2018-6-1 03:57 上傳
單片機(jī)源程序如下:
- #include<reg52.h> //包含頭文件,一般情況不需要改動,頭文件包含特殊功能寄存器的定義
- #include<math.h>
- #include<INTRINS.H>
- #define uchar unsigned char
- #define uint unsigned int
- /******************************************************************/
- /* 定義端口 */
- /******************************************************************/
- sbit buzzer=P1^0;//蜂鳴器端口
- sbit led1=P1^1; //led指示燈,當(dāng)前溫度高于設(shè)置的最高溫度時點(diǎn)亮
- sbit led2=P1^2; //led指示燈,當(dāng)前溫度低于設(shè)置的最低溫度時點(diǎn)亮
- sbit DQ=P1^4; //ds18b20 端口
- sbit key1=P3^4; //按鍵
- sbit key2=P3^5;
- sbit key3=P3^6;
- sbit key4=P3^7;
- /******************************************************************/
- /* 全局變量 */
- /******************************************************************/
- uint temp;//當(dāng)前溫度值
- uchar TempH=0,TempL=0;
- int temp_max,temp_min;//設(shè)定溫度的最大值和最小值
- uchar flag_get,count,num;
- uchar tab[10]={0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90}; //0~~9段碼
- uchar str[4];//四位數(shù)碼管顯示字符
- uchar display_mod;//數(shù)碼管顯示模式
- /******************************************************************/
- /* 函數(shù)聲明 */
- /******************************************************************/
- unsigned int ReadTemperature(void);//讀取溫度函數(shù)
- void Init_DS18B20(void);//18b20初始化函數(shù)
- unsigned char ReadOneChar(void);//18B20讀一個字節(jié)
- void WriteOneChar(unsigned char dat);//18B20寫一個字節(jié)
- void delay(unsigned int i);//短延時
- void delay_ms(uint z);//長延時
- void alarm();//報(bào)警
- void keyscan();//鍵盤掃描
- /******************************************************************/
- /* 主函數(shù) */
- /******************************************************************/
- main()
- {
- uchar buzzer_delay=0;//蜂鳴器延時計(jì)數(shù)
- uchar buzzer_work=0;//蜂鳴器開始工作
- display_mod=0;//顯示當(dāng)前溫度
- temp_min=10;//設(shè)置最低溫
- temp_max=40;//設(shè)置最高溫
- TMOD|=0x01;//定時器設(shè)置
- TH0=0xef; //定時器初值
- TL0=0xf0;
- IE=0x82;//EA=1,ET0=1
- TR0=1; //開定時器
- P2=0xff;
- count=0;
- buzzer=0;
- while(1)
- {
- keyscan();//獨(dú)立按鍵掃描
-
- if(flag_get==1)
- { buzzer_delay++;
- flag_get=0;// 獲取溫度標(biāo)志清零
- temp=ReadTemperature();//讀溫度值
- }
- if(display_mod==0)
- {
- if(temp&0x8000)
- {
- str[0]=0xbf;//負(fù)號標(biāo)志
- temp=~temp; //取反加1
- temp +=1;
- }
- else
- {
- str[0]=0xff;
- }
- TempH=temp>>4;
- TempL=temp&0x0F;
- TempL=TempL*6/10;//小數(shù)近似處理
-
- str[1]=tab[(TempH%100)/10]; //十位溫度
- str[2]=tab[(TempH%100)%10]&0x7f; //個位溫度,帶小數(shù)點(diǎn)
- str[3]=tab[TempL];
- }
- else if(display_mod==1)//顯示最低溫
- {
- str[0]=0xc7;//顯示L
- str[1]=tab[temp_min/100]; //溫度百位
- str[2]=tab[(temp_min%100)/10]; //溫度十位
- str[3]=tab[temp_min%10];//溫度個位
- }
- else if(display_mod==2)//顯示最高溫
- {
- str[0]=0x89;//顯示H
- str[1]=tab[temp_max/100]; //溫度百位
- str[2]=tab[(temp_max%100)/10]; //溫度十位
- str[3]=tab[temp_max%10];//溫度個位
- }
- if(buzzer_delay>5)//為了防止溫度獲取前就會出現(xiàn)報(bào)警
- {
- buzzer_work=1;
- }
- if(buzzer_work==1)
- alarm();
- }
- }
- /******************************************************************/
- /* 定時器中斷 */
- /******************************************************************/
- void tim(void) interrupt 1 using 1//中斷,用于數(shù)碼管掃描和溫度檢測間隔
- {
- TH0=0xea;//定時器重裝值
- TL0=0xf0;
- num++;
- if (num==100)
- {
- num=0;
- flag_get=1;//獲取溫度標(biāo)志位有效
- }
- count++;
- if(count==1)
- {
- //P2=0Xfe;
- P2=0x01;
- P0=str[0];
- }//數(shù)碼管掃描
- if(count==2)
- {
- if(str[1]==tab[0])
- str[1]=0xff;//顯示為空
- //P2=0Xfd;
- P2=0x02;
- P0=str[1];
- }
- if(count==3)
- {
- //P2=0Xfb;
- P2=0x04;
- P0=str[2];
- }
- if(count==4)
- {
- //P2=0Xf7;
- P2=0x08;
- P0=str[3];
- count=0;
- }
- }
- /******************************************************************/
- /* 長延時函數(shù) */
- /******************************************************************/
- void delay_ms(uint z) //長延時函數(shù)
- {
- uint x,y;
- for(x=z;x>0;x--)
- for(y=110;y>0;y--);
- }
- /******************************************************************/
- /* 短延時函數(shù) */
- /******************************************************************/
- void delay(unsigned int i)//短延時函數(shù)
- {
- while(i--);
- }
- /******************************************************************/
- /* 初始化 */
- /******************************************************************/
- void Init_DS18B20(void)
- {
- /*unsigned char x=0;
- DQ = 1; //DQ復(fù)位
- delay(8); //稍做延時
- DQ = 0; //單片機(jī)將DQ拉低
- delay(80); //精確延時 大于 480us
- DQ = 1; //拉高總線
- delay(10);
- x=DQ; //稍做延時后 如果x=0則初始化成功 x=1則初始化失敗
- delay(5);*/
- unsigned char x=0;
- DQ = 1; //DQ復(fù)位
- delay(8); //稍做延時
- DQ = 0; //單片機(jī)將DQ拉低
- delay(80); //精確延時 大于 480us
- DQ = 1; //拉高總線
- delay(14);
- x=DQ; //稍做延時后 如果x=0則初始化成功 x=1則初始化失敗
- delay(20);
- }
- /******************************************************************/
- /* 讀一個字節(jié) */
- /******************************************************************/
- 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(5);
- }
- return(dat);
- }
- /******************************************************************/
- /* 寫一個字節(jié) */
- /******************************************************************/
- void WriteOneChar(unsigned char dat)
- {
- unsigned char i=0;
- for (i=8; i>0; i--)
- {
- DQ = 0;
- DQ = dat&0x01;
- delay(5);
- DQ = 1;
- dat>>=1;
- }
- delay(5);
- }
- /******************************************************************/
- /* 讀取溫度 */
- /******************************************************************/
- unsigned int ReadTemperature(void)
- {
- unsigned char a=0;
- unsigned int b=0;
- unsigned int t=0;
- Init_DS18B20();
- WriteOneChar(0xCC); // 跳過讀序號列號的操作
- WriteOneChar(0x44); // 啟動溫度轉(zhuǎn)換
- delay(200);
- Init_DS18B20();
- WriteOneChar(0xCC); //跳過讀序號列號的操作
- WriteOneChar(0xBE); //讀取溫度寄存器等(共可讀9個寄存器) 前兩個就是溫度
- a=ReadOneChar(); //低位
- b=ReadOneChar(); //高位
- b<<=8;
- t=a+b;
- return(t);
- }
- /******************************************************************/
- /* 獨(dú)立鍵盤掃描函數(shù)并顯示設(shè)定的溫度 */
- /******************************************************************/
- void keyscan()
- {
- static uchar keynum;//用于切換界面時按鍵計(jì)數(shù)
- P3=0xff;//拉高P3口,以讀取P3口的值
- if(key4==0)//設(shè)置鍵
- {
- delay_ms(5);//延時消抖
- if(key4==0)
- {
- keynum++;
- keynum%=2;//在0、1間變化
- if(keynum==1)
- {
- display_mod=1;
- }
- else
- {
- display_mod=2;
- }
- }
- while(!key4);//松手檢測
- }
- if(key3==0)//確定鍵
- {
- delay_ms(5);
- if(key3==0)
- {
- keynum=0;
- display_mod=0;
- }
- while(!key3);
- }
- if(key2==0)//加鍵
- {
- delay_ms(5);//延時消抖
- if(key2==0)
- {
- if(display_mod==2)
- {
- temp_max++;
- if(temp_max>=99)
- temp_max=99;
- }
- if(display_mod==1)
- {
- temp_min++;
- if(temp_min>=temp_max)
- temp_min=temp_max;
- }
-
- }
- while(!key2);//松手檢測
- }
- if(key1==0)//減鍵
- {
- delay_ms(5);
- if(key1==0)
- {
- if(display_mod==2)
- {
- temp_max--;
- if(temp_max<=temp_min)
- temp_max=temp_min;
- }
- if(display_mod==1)
- {
- temp_min--;
- if(temp_min<=0)
- temp_min=0;
- }
- }
- while(!key1);//松手檢測
- }
- }
- /******************************************************************/
- /* 蜂鳴器報(bào)警程序 */
- /******************************************************************/
- void alarm()
- {
- if(display_mod==0)//在顯示當(dāng)前溫度時報(bào)警才會動作
- {
- if(TempH<(temp_min))
- {
- led1=0;
- led2=1;
- buzzer=~buzzer;
- }
- else if(TempH>=(temp_max))
- {
- led1=1;
- led2=0;
- buzzer=~buzzer;
- }
- else
- {
- led1=1;
- led2=1;
- buzzer=0;
- }
- }
- }
復(fù)制代碼
所有資料51hei提供下載:
3 protues仿真.zip
(71.5 KB, 下載次數(shù): 308)
2018-5-31 21:48 上傳
點(diǎn)擊文件名下載附件
下載積分: 黑幣 -5
|
評分
-
查看全部評分
|