?? ds18b20c.txt
字號:
//這是關于DS18B20的c讀寫程序,數據腳P1.0,晶振12MHZ
//采用的是啟東單片機開發板AY-MPU89S51E
//進行溫度顯示,這里我們考慮用四位數碼管來顯示溫度
//顯示范圍-55.0到+99.5度,顯示精度為0.5度
//關于程序中的延時請參考ds18b20的讀寫時序
#include <reg52.h>
#define uchar unsigned char
uchar tempint,tempdf; //溫度整數部分和小數部分
sbit TMDAT = P1^0; //根據實實際情況設定
sbit ld7=P1^7; //初始化成功標志led
sbit ld6=P1^6; //負溫度標志led
sbit point=P0^7; //小數點顯示
uchar f; //負溫度標志
code unsigned char ledmap[]={
0xC0, 0xF9, 0xA4, 0xB0, 0x99, 0x92, 0x82, 0xF8, 0x80, 0x90, 0xBF};
//7段數碼管0~9數字的共陽顯示代碼和負號位代碼(最后一位)
void set_ds18b20(); //初始化DS18B20子程序
void get_temperature(); //獲得溫度子程序
void read_ds18b20(); //讀DS18B20子程序
void write_ds18b20(uchar command);//向DS18B20寫1字節子程序
void delayms(uchar count); //延時count毫秒子程序
void disp_temp(); //顯示溫度子程序
void main()
{
SP=0x60; //設置堆棧指針
while(1)
{
get_temperature(); //獲得溫度
if(tempdf>=8)
{ //0.5度精度顯示
tempdf=5;
}
else
{
tempdf=0;
}
disp_temp(); //顯示溫度
}
}
void set_ds18b20()
{
while(1)
{
uchar delay,flag;
flag=0;
TMDAT=1;
delay=1;
while(--delay);
TMDAT=0; //數據線置低電平
delay=250;
while(--delay); //低電平保持500us
TMDAT=1; //數據線置高電平
delay=30;
while(--delay); //高電平保持60us
while(TMDAT==0) //判斷DS18B20是否發出低電平信號
{
delay=210; //DS18B20響應,延時420us
while(--delay);
if(TMDAT) //DS18B20發出高電平初始化成功,返回
{
flag=1; //DS18B20初始化成功標志
ld7=0; //初始化成功LED標志
break;
}
}
if(flag) //初始化成功,再延時480us,時序要求
{
delay=240;
while(--delay);
break;
}
}
}
void get_temperature() //溫度轉換、獲得溫度子程序
{
set_ds18b20(); //初始化DS18B20
write_ds18b20(0xcc); //發跳過ROM匹配命令
write_ds18b20(0x44); //發溫度轉換命令
disp_temp(); //顯示溫度,等待AD轉換
set_ds18b20();
write_ds18b20(0xcc); //發跳過ROM匹配命令
write_ds18b20(0xbe); //發出讀溫度命令
read_ds18b20(); //將讀出的溫度數據保存到tempint和tempdf處
}
void read_ds18b20()
{
uchar delay,i,j,k,temp,temph,templ;
j=2; //讀2位字節數據
do
{
for(i=8;i>0;i--) //一個字節分8位讀取
{
temp>>=1; //讀取1位右移1位
TMDAT=0; //數據線置低電平
delay=1;
while(--delay);
TMDAT=1; //數據線置高電平
delay=4;
while(--delay); //延時8us
if(TMDAT) //讀取1位數據
temp|=0x80;
delay=25; //讀取1位數據后延時50us
while(--delay);
}
if(j==2) //讀取的第一字節存templ
templ=temp;
else
temph=temp; //讀取的第二字節存temph
}while(--j);
f=0;
if((temph & 0xf8)!=0x00) //若溫度為負的處理,對二進制補碼的處理
{
f=1; //為負溫度f置1
ld6=0;
temph=~temph;
templ=~templ;
k=templ+1;
templ=k;
if(k>255)
{
temph++;
}
}
tempdf=templ & 0x0f; //將讀取的數據轉換成溫度值,整數部分存tempint,小數部分存tempdf
templ>>=4;
temph<<=4;
tempint=temph|templ;
}
void write_ds18b20(uchar command)
{
uchar delay,i;
for(i=8;i>0;i--) //將一字節數據一位一位寫入
{
TMDAT=0; //數據線置低電平
delay=6; //延時12us
while(--delay);
TMDAT=command&0x01; //將數據放置在數據線上
delay=25; //延時50us
while(--delay);
command=command>>1; //準備發送下一位數據
TMDAT=1; //發送完一位數據,數據線置高電平
}
}
void disp_temp()
{
uchar tempinth,tempintl,cnt;
tempinth=tempint/10; //整數高半字節
tempintl=tempint%10; //整數低半字節
cnt=200; //循環顯示200次
while(--cnt)
{
while(f==1)
{
P0=ledmap[10];
if(tempinth==0)
{
P2=0xef;
delayms(1);
goto loop;
}
else
{P2=0xdf;}
}
delayms(1);
P0=ledmap[tempinth];
P2=0xef; //開十位
delayms(1);
loop:P0=ledmap[tempintl];
P2=0xf7; //開個位
point=0; //小數點顯示
delayms(1);
P0=ledmap[tempdf];
P2=0xfb; //開十分位
delayms(1);
}
}
void delayms(uchar count) //延時count ms子程序
{
uchar i,j;
do
{
for(i=5;i>0;i--)
for(j=98;j>0;j--);
}while(--count);
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -