请教一下大神,我用STC15W408AS+DS18B20, 想实现串口输出文本类型的温度数值,类似28.50这样的温度数值,用下面这个代码需要怎么样改,感谢。
#ifndef _DS18B20_H
#define _DS18B20_H
#include "reg51.h"
#include "intrins.h"
#define uchar unsigned char
#define uint unsigned int
sbit DQ = P3^2; //DS1820数据线IO口
bit nflag; //温度正负标志
/*****************************************************
延时函数:延时1us
******************************************************/
void delayus(uint i)
{
while(i--);
}
/*****************************************************
功能: 延时,最小单位为ms(晶振为11.0592
计算方法:一个for循环 = 8个指令周期 = 8*12个机器周期
= 8*12*1/11.0592 = 0.0086ms
xms = 0.0086 * 110 = 0.946 ms
******************************************************/
void delayms(uint xms)
{
uint i,j;
for(i=xms;i>0;i--)
for(j=110;j>0;j--);
}
/*****************************************************
DS18B20复位函数:
1 数据线拉低,延时480us
2 数据线拉高,延时480us
******************************************************/
void ds1820rst()
{
DQ = 1; //初始状态
delayus(4);
DQ = 0; //拉低
delayus(480); //延时480us
DQ = 1; //拉高
delayus(480);
}
/****************************************************
18b20读数据:由低位到高位,重复八次,读一个字节
1 数据线拉低,延时4us
2 数据线拉高,延时10us
3 读数据线状态一位,处理数据,延时45us
4 重复步骤1-3
*****************************************************/
uchar ds1820rd()
{
uchar i = 0;
uchar dat = 0;
for(i=8;i>0;i--)
{
DQ = 0; //拉低数据线
delayus(4);
dat>>=1; //空出第一位
DQ = 1; //拉高数据线
delayus(10);
if(DQ) //若为高电平,则最高位置一
dat|=0x80;
delayus(45);//延时45us
}
return(dat);
}
/**************************************************
18b20写数据:由低位到高位,重复八次,写一个字节
1 数据线拉低,延时15us
2 送一位数据到数据线,延时60us
3 数据线拉高
4 重复步骤1-3
**************************************************/
void ds1820wr(uchar wdata)
{
uchar i = 0;
for (i=8; i>0; i--)
{
DQ = 0; //数据线拉低
delayus(15);
DQ = wdata&0x01; //将数据最低位送入数据线
delayus(60); //延时10us
DQ = 1; //数据线拉高
wdata>>=1; //字节右移一位
}
}
/*****************************************************
读温度并转换,根据RAM命令表写命令
0xcc: 不读取序列地址
0x44: 启动温度转换
0xbe: 读取温度
******************************************************/
uint read_temp()
{
uchar TL,TH; //TL:低八位 TH:高八位
uchar wd; //最终温度的绝对值
ds1820rst(); //先复位
ds1820wr(0xcc); //不读取64位地址,因为总线上只有一个DB1820,单片工作
ds1820wr(0x44); //启动温度转换
delayus(125);
ds1820rst();
ds1820wr(0xcc); //跳过读序列号
ds1820wr(0xbe); //读取温度
TL = ds1820rd(); //读低八位
TH = ds1820rd(); //读高八位
wd = TL/16+TH*16;
// tvalue = TH; //tvalue为16位
// tvalue = (tvalue<<8)+TL;
// if((tvalue&0xf800) == 0xf800) //判断负温度
// {
// tvalue=~tvalue+1; //补码=反码+1
// nflag = 0; //置标志位为0
// }
// else
// nflag = 1;
//
// wd = tvalue*0.625; //计算温度值
return(wd); //返回温度值
}
/*****************************************************
串口初始化函数:
******************************************************/
void init()
{
P1M0 = 0;P1M1 = 0;
SCON = 0x40;
T2L = 0xe0;
T2H = 0xfe;
AUXR = 0x14;
AUXR |= 0x01;
TI = 1;
}
/*****************************************************
串口通讯函数:发送两个字节,首字节为正负标志位,
第二个字节为温度值
******************************************************/
void comm(uchar temper)
{
// while(!TI == 1);
// {
// TI = 0;
// SBUF = nflag;
// }
while(!TI == 1);
{
TI = 0;
SBUF = temper;
}
}
#endif
void main()
{
uchar temp; //临时变量存储温度
init(); //串口的初始化
while(1)
{
temp=read_temp(); //读取温度
delayms(500); //延时0.5s
comm(temp); //发送至上位机
}
} |