與普通溫度計相比,以單片機為核心的數字溫度計具有數字顯示、超溫報警、記錄存儲、數據上傳等優點,因而得到了廣泛應用。根據性能要求和器件選型的不同,數字溫度計可有多種不同的實現方案。 溫度傳感器是數字溫度計中的關鍵器件。傳統的溫度傳感器有熱電阻、熱電偶、PN結等類型,這些傳感器的輸出均為微弱的模擬信號,必須經過放大、濾波、A/D轉換等電路處理,才能得到可為單片機接受的數字量。相比之下,新型數字溫度傳感器將溫度傳感元件、數字量轉換電路、數據存儲器、通信接口等部件集成在一塊芯片上,可通過幾根(最少只要一根)串行通信線直接輸出數字形式的溫度值,大大簡化了數字溫度計的硬件設計。
捕獲.PNG (82.17 KB, 下載次數: 62)
下載附件
2020-5-9 10:00 上傳
DS18B20是DALLAS公司生產的單總線(1-Wire)接口的數字溫度傳感器,數據傳輸僅需一根信號線。溫度測量范圍為-55~+125℃,在-10~+85℃范圍內,精度可達±0.5℃,有效數據位數可通過程序設置為9~12位,12位時分辨率可達0.0625℃。每個DS18B20具有唯一64位序列碼,多個器件可并聯在一根數據線上,實現多點測溫。 C語言源程序如下: //*****************************頭文件聲明**************************** #include <reg51.h> //****************************數據類型定義*************************** typedef unsigned char uint8; typedef unsigned int uint16; //****************************I/O口線聲明**************************** #define SEG_CODE_PORT P0 #define BIT_CODE_PORT P2 sbit DS18B20_DATA=P3^7; sbit BUZZ= P1^0; //************************常量數組(段碼表)聲明********************* uint8 code SegCodeTable[]= { 0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90 }; //****************************全局變量聲明*************************** int Temperature; uint8 t=27; //****************************函數原型聲明*************************** void DS18B20Init(); void DS18B20BitWrite(bit Bit); bit DS18B20BitRead(); void DS18B20ByteWrite(uint8 Byte); uint8 DS18B20ByteRead(); void GetTemperature(); void DispTemperature(); void Delay(uint16 ms); void AlarmCheck(); void UartInit(); void UartSendByte(uint8 Byte); //*******************************主函數****************************** void main() { uint8 Temp; UartInit(); while(1) { GetTemperature(); //采集當前溫度 DispTemperature(); //顯示當前溫度 AlarmCheck(); Temp=Temperature>>4; UartSendByte((Temp/10)*16+Temp%10); } } //*************************DS18B20初始化函數************************* void DS18B20Init() { uint16 i; while(1) { DS18B20_DATA=0; i=640; while(--i); //延時800us(STC12C5A60S2,11.0592MHz,代碼5級優化) DS18B20_DATA=1; i=56; while(--i); //延時70us if(DS18B20_DATA==1) continue; //無響應則重發復位脈沖 i=224; while(--i); //延時280us if(DS18B20_DATA==1) break; //復位成功 } i=160; while(--i); //延時200us } //***********************DS18B20位寫操作函數************************* void DS18B20BitWrite(bit Bit) { uint16 i; DS18B20_DATA=0; i=4; while(--i); //延時5us DS18B20_DATA=Bit; //發送1位數到DS18B20 i=48; while(--i); //延時60us DS18B20_DATA=1; } //**********************DS18B20位讀操作函數************************** bit DS18B20BitRead() { bit temp; uint16 i; DS18B20_DATA=0; i=4; while(--i); //延時5us DS18B20_DATA=1; i=4; while(--i); //延時5us temp=DS18B20_DATA; //讀來自DS18B20的1位數 i=48; while(--i); //延時60us return temp; } //**********************DS18B20字節寫操作函數************************ void DS18B20ByteWrite(uint8 Byte) { uint8 i; for(i=0;i<8;i++) //一共發送8位 { if(Byte&0x01==1 ) //先發最低位 DS18B20BitWrite(1); //發送1 else DS18B20BitWrite(0); //發送0 Byte>>=1; } } //**********************DS18B20字節讀操作函數************************ uint8 DS18B20ByteRead() { uint8 i,temp=0; for(i=0;i<8;i++) //一共讀8位 { temp>>=1; //字節變量右移 if(DS18B20BitRead()==1) //讀取1位數據并存入臨時變量temp中 temp|=0x80; //temp最高位置1 } return temp; //返回讀到的8位數 } //*****************************溫度采集函數************************** void GetTemperature() { uint8 Buff[2],i; DS18B20Init(); //DS18B20初始化 DS18B20ByteWrite(0xCC); //跳過ROM匹配(因為只有一個DS18B20) DS18B20ByteWrite(0x44); //啟動溫度轉換 for(i=0;i<250;i++) DispTemperature(); //等待750ms,期間不斷刷新LED顯示 DS18B20Init(); //DS18B20初始化 DS18B20ByteWrite(0xCC); //跳過ROM匹配(因為只有一個DS18B20) DS18B20ByteWrite(0xBE); //準備讀轉換結果 Buff[0]=DS18B20ByteRead(); //讀溫度值低字節 Buff[1]=DS18B20ByteRead(); //讀溫度值高字節 Temperature= (Buff[1]<<8)+Buff[0]; //拼成16位溫度值 } //******************************溫度顯示函數************************* void DispTemperature() { uint8 temp; SEG_CODE_PORT=SegCodeTable[t/10]; //顯示十位 BIT_CODE_PORT=0xF2; //選擇顯示位置 Delay(1); BIT_CODE_PORT=0xFF; SEG_CODE_PORT=SegCodeTable[t%10]; //顯示個位 BIT_CODE_PORT=0xF3; //選擇顯示位置 Delay(1); BIT_CODE_PORT=0xFF; temp=(Temperature>>4)/10; //顯示十位 if(temp==0) SEG_CODE_PORT=0xFF ; //十位為0則隱去 else SEG_CODE_PORT=SegCodeTable[temp]; BIT_CODE_PORT=0xF5; //選擇顯示位置 Delay(1); BIT_CODE_PORT=0xFF; SEG_CODE_PORT=SegCodeTable[(Temperature>>4)%10]&0x7F; //顯示個位(帶點) BIT_CODE_PORT=0xF6; //選擇顯示位置 Delay(1); BIT_CODE_PORT=0xFF; SEG_CODE_PORT=SegCodeTable[(Temperature&0x0F)*10/16]; //顯示十分位 BIT_CODE_PORT=0xF7; //選擇顯示位置 Delay(1); BIT_CODE_PORT=0xFF; } //******************************軟件延時函數************************* void Delay(uint16 ms) { uint16 i; do{ i=790; while(--i); //延時1ms(STC12C5A60S2,11.0592MHz,代碼5級優化) } while(--ms); } /********************************超溫報警函數***************************/ void AlarmCheck() { uint8 i; if(Temperature>0x1C8) //判斷溫度是否超過28.5℃ { for(i=0;i<50;i++) { BUZZ= ~BUZZ; Delay(1); //控制無源蜂鳴器發聲50ms } BUZZ=1; Delay(100); } } void UartInit() { TMOD=0x20; TH1=TL1=0xFD; TR1=1; SCON=0x50; PCON=0x00; ES=1; EA=1; TR1=1; } void UartISR() interrupt 4 { if(RI==0) return; RI=0; t=SBUF; } void UartSendByte(uint8 Byte) { SBUF=Byte; while(TI==0); TI=0; } //********************************程序結束***************************
|