#include <REGX52.H>
#define uchar unsigned char
sbit DQ=P2^0; //数据传输线接单片机的相应的引脚
unsigned char tempL=0; //临时变量低位(无符号字符变量)
unsigned char tempH=0; //临时变量高位
unsigned int tempa; //温度值(整型变量)
uchar display_data[4]={0};
void DS18_delay(int useconds)//延时函数
{
int s;
for (s=0; s<useconds;s++);
}
unsigned char Init_DS18B20(void)
{
unsigned char x=0;
DQ=0; //发送复位脉冲
DS18_delay(29); //延时(>480ms)
DQ=1; //拉高数据线
DS18_delay(3); //等待(15~60ms) 等待存在脉冲
x=DQ; //获得存在信号(用于判断是否有器件)
DS18_delay(25); // 等待时间隙结束
return(x); //返回存在信号,0 = 器件存在, 1 = 无器件
}
ReadOneChar(void)//读一个字节
{
unsigned char i=0;
unsigned char dat=0;
for (i=8;i>0;i--)
{
DQ=1;
DS18_delay(1);
DQ=0;
dat>>=1;//复合赋值运算,等效dat=dat>>1(dat=dat右移一位后的值)
DQ=1;
if(DQ)
dat|=0x80;
DS18_delay(4);
}
return(dat);
}
WriteOneChar(unsigned char dat)//有参函数,功能是"写",而写的内容就是括号内的参数
{
unsigned char i=0;
for(i=8;i>0;i--)
{
DQ=0;
DQ=dat&0x01;
DS18_delay(5);
DQ=1;
dat>>=1;//复合赋值运算,等效dat=dat>>1(dat=dat右移一位后的值)
}
DS18_delay(4);
}
unsigned int ReadTemperature(void)//返回读取的温度.
{
Init_DS18B20(); //初始化,调用初始化函数
WriteOneChar(0xcc); //跳过读序列号的操作,调用写函数,写0xcc指令码(跳过读序列号)
WriteOneChar(0x44); //启动温度转换,调用写函数,写0x44指令码(启动温度转换)
DS18_delay(125); //转换需要一点时间,延时
Init_DS18B20(); //初始化,调用初始化函数
WriteOneChar(0xcc); //跳过读序列号的操作,调用写函数,写0xcc指令码(跳过读序列号?
WriteOneChar(0xbe); //调用写函数,写0xbe指令码,读温度寄存器(头两个值分别为温度的低位和高位)
tempL=ReadOneChar(); //读出温度的低位LSB
tempH=ReadOneChar(); //读出温度的高位MSB
tempa=((tempH*256)+tempL)*6.25; //温度转换,扩大100返回
//DS18_delay(10);
//tempa=tempL+tempH;
return(tempa);//运算结果返回到函数
}
void display()//显示函数
{
unsigned char i,j,k=0x80;
unsigned char code dis[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x39};
for(i=0;i<4;i++)
{
P2=0x0f;
if(i==1)
P0=dis[display_data[i]]+0x80;
else
P0=dis[display_data[i]];
P2=k;
k=k>>1;
for(j=250;j>0;j--);
}
P2=0x0f;
}
void main()
{
unsigned int temp;
uchar i;
while(1)
{
temp=ReadTemperature();
display_data[0]=temp/1000;
display_data[1]=(temp/100)%10;
display_data[2]=(temp/10)%10;
display_data[3]=temp%10;
for(i=0;i<250;i++) display();
}
}