|
要想成功讀取DS18B20的溫度,那么時(shí)序很重要,因?yàn)镾TC12C5A60是1T的單片機(jī),跟STC89C52的延時(shí)是不一樣的,所以在程序處理時(shí),一定要特別注意延時(shí)是否正確,我在DS18B20身上研究了很久,一開(kāi)始還以為是接線的問(wèn)題或者是元件壞了,溫度一直顯示-0.006,后面查了很多資料才發(fā)現(xiàn)是時(shí)序不對(duì),導(dǎo)致初始化不成功,如果看到我的帖子,希望對(duì)大家有所幫助- /*-----------------------------------------------
- 名稱(chēng):18B20溫度傳感器
- ------------------------------------------------*/
- #include"delay.h"
- #include"18b20.h"
- #include"LCD1602.h"
- uchar fu;
- /*------------------------------------------------
- 端口定義
- ------------------------------------------------*/
- sbit DQ=P1^3;//ds18b20 端口
- sbit beep=P2^3;
- /*------------------------------------------------
- 18b20初始化
- ------------------------------------------------*/
- unsigned char ds18b20_init(void)
- {
- unsigned char presence;
- DQ = 1;
- delay_us(2);
- DQ = 0;
- delay_us(500);
- DQ = 1;
- delay_us(70);
- presence = DQ;
- delay_us(500);
- return presence;
- }
- /*------------------------------------------------
- 讀一位
- ------------------------------------------------*/
- bit tmpreadbit(void)
- {
- unsigned char a;
- DQ = 0;
- delay_us(5);
- DQ = 1;
- delay_us(5);
- a = DQ;
- delay_us(50);
- return a;
- }
- /*------------------------------------------------
- 讀一個(gè)字節(jié)
- ------------------------------------------------*/
- unsigned char ReadOneChar(void) //read a byte date
- {
- uchar i,j,dat;
- dat=0;
- for(i=1;i<=8;i++)
- {
- j=tmpreadbit();
- dat=(j<<7)|(dat>>1); //讀出的數(shù)據(jù)最低位在最前面,這樣剛好一個(gè)字節(jié)在DAT里
- }
- return(dat);
- }
- /*------------------------------------------------
- 寫(xiě)入一位
- ------------------------------------------------*/
- void ds18b20_writebit(unsigned char a)
- {
- DQ = 0;
- delay_us(10);
- DQ = a;
- delay_us(50);
- DQ = 1;
- }
- /*------------------------------------------------
- 寫(xiě)入一個(gè)字節(jié)
- ------------------------------------------------*/
- void WriteOneChar(unsigned char dat)
- {
- unsigned char j;
- bit testb;
- for(j=1;j<=8;j++)
- {
- testb=dat&0x01;
- dat=dat>>1;
- ds18b20_writebit(testb);
- }
- }
- void tmpchange(void) //DS18B20開(kāi)始獲取溫度并轉(zhuǎn)換
- {
- ds18b20_init();
- DelayMs(1);
- WriteOneChar(0xcc); // address all drivers on bus
- WriteOneChar(0x44); // initiates a single temperature conversion
- }
- /*------------------------------------------------
- 讀取溫度
- ------------------------------------------------*/
- unsigned int ReadTemperature(void)
- {
- unsigned char a,b;
- unsigned int g,c,d,e;
- ds18b20_init();
- DelayMs(1);
- WriteOneChar(0xCC); //跳過(guò)讀序號(hào)列號(hào)的操作
- WriteOneChar(0xBE); //讀取溫度寄存器等(共可讀9個(gè)寄存器) 前兩個(gè)就是溫度
- a=ReadOneChar(); //先讀低位
- b=ReadOneChar(); //再讀高位
- if(!(b&0x08))
- {
- fu=1;
- g=b;
- c=((g<<8)|a)*6.25;
- }
- else
- {
- fu=0;
- d=((b<<8)|a);
- e=((~d)+1);
- c=e*6.25;
- }
- return(c);
- }
- void warn(uint s,uchar led)//蜂鳴器報(bào)警和燈閃爍 s控制音調(diào),led控制燈
- {
- uchar i;
- i=s;
- beep=0; //蜂鳴器響
- P1=~(led); //控制相應(yīng)的燈亮
- while(i--)
- {
- distemperature();//用溫度顯示函數(shù)起到延時(shí)的作用
- }
- beep=1; //蜂鳴器不響
- P1=0xff; //控制相應(yīng)的燈滅
- i=s;
- while(i--)
- {
- distemperature();//用溫度顯示函數(shù)起到延時(shí)的作用
- }
- }
- void deal(uint t) //溫度區(qū)間報(bào)警
- {
- uchar i;
- if((t>2700)&&(t<=2500)) //大于25度小于27度
- {
- warn(40,0x01); //第一個(gè)燈亮,蜂鳴器發(fā)出"滴"聲
- }
- else if(t<=2500) //小于25度
- {
- warn(10,0x03);//第一個(gè)和第二燈亮,蜂鳴器發(fā)出"滴"聲
- }
- else if((t<3200)&&(t>=3000)) //小于32度大于30度
- {
- warn(40,0x04);//第三個(gè)燈亮,蜂鳴器發(fā)出"滴"聲
- }
- else if(t>=3200)//大于32度
- {
- warn(10,0x0C);//第三個(gè)和第四個(gè)燈亮,蜂鳴器發(fā)出"滴"聲
- }
- else //在27度和30度之間時(shí)只是調(diào)用顯示函數(shù)延時(shí)
- {
- i=40;
- while(i--)
- {
- distemperature(); //用溫度顯示函數(shù)起到延時(shí)的作用
- }
- }
- }
- void distemperature(void)
- {
- unsigned int m1,m2,m3,m4,m5,temperature;
- tmpchange();
- temperature=ReadTemperature();//讀取溫度
- if(fu==0)
- {
- LCD_Write_Char(5,1,'-');//寫(xiě)入負(fù)號(hào)的位置,如果是負(fù)溫度就顯示
- }
- else
- {
- LCD_Write_Char(5,1,0x20);//是正溫度就顯示空格,0x20在ASCII字符表里表示空格
- }
- m1=temperature/10000+48; //1602字符顯示ASCII的地址位0X30,0~9,對(duì)應(yīng)的地址是48~57,所以計(jì)算出來(lái)的數(shù)要加48,48=0x30 /號(hào)是求整 %是求余
- m2=temperature%10000/1000+48;//為什么要除于10000呢,因?yàn)橐婚_(kāi)始溫度換算的時(shí)就已經(jīng)乘以100倍了,如果溫度是110度,此時(shí)得出來(lái)的數(shù)就是11000,所以要除于10000
- m3=temperature%1000/100+48;
- m4=temperature%100/10+48;
- m5=temperature%10+48;
- LCD_Write_Char(6,1,m1);
- LCD_Write_Char(7,1,m2);
- LCD_Write_Char(8,1,m3);
- LCD_Write_Char(9,1,'.');
- LCD_Write_Char(10,1,m4);
- LCD_Write_Char(11,1,m5);
- }
復(fù)制代碼 原理圖: 無(wú)
仿真: 無(wú)
代碼:
1602 18b20.zip
(58.15 KB, 下載次數(shù): 50)
2023-9-13 14:40 上傳
點(diǎn)擊文件名下載附件
下載積分: 黑幣 -5
|
評(píng)分
-
查看全部評(píng)分
|