最近都在学习和写单片机的程序, 今天有空又模仿DS18B20温度测量显示实验写了一个与DS18B20基于单总线通信的程序.
DS18B20 数字温度传感器(参考:智能温度传感器DS18B20的原理与应用)是DALLAS 公司生产的1-Wire,即单总线器件,具有线路简单,体积小的特点。因此用它来组成一个测温系统,具有线路简单,在一根通信线,可以挂很多这样的数字温度计。DS18B20 产品的特点:
(1)、只要求一个I/O 口即可实现通信。
(2)、在DS18B20 中的每个器件上都有独一无二的序列号。
(3)、实际应用中不需要外部任何元器件即可实现测温。
(4)、测量温度范围在-55 到+125℃之间; 在-10 ~ +85℃范围内误差为±5℃; (5)、数字温度计的分辨率用户可以从9 位到12 位选择。将12位的温度值转换为数字量所需时间不超过750ms;
(6)、内部有温度上、下限告警设置。
DS18B20引脚分布图
DS18B20 详细引脚功能描述:
1、GND 地信号;
2、DQ数据输入出引脚。开漏单总线接口引脚。当被用在寄生电源下,此引脚可以向器件提供电源;漏极开路, 常太下高电平. 通常要求外接一个约5kΩ的上拉电阻.
3、VDD可选择的VDD 引脚。电压范围:3~5.5V; 当工作于寄生电源时,此引脚必须接地。
DS18B20存储器结构图
暂存储器的头两个字节为测得温度信息的低位和高位字节;
第3, 4字节是TH和TL的易失性拷贝, 在每次电复位时都会被刷新;
第5字节是配置寄存器的易失性拷贝, 同样在电复位时被刷新;
第9字节是前面8个字节的CRC检验值.
配置寄存器的命令内容如下:
MSB LSB
R0和R1是温度值分辨率位, 按下表进行配置.默认出厂设置是R1R0 = 11, 即12位.
温度值分辨率配置表
4种分辨率对应的温度分辨率为0.5℃, 0.25℃, 0.125℃, 0.0625℃(即最低一位代表的温度值)
12位分辨率时的两个温度字节的具体格式如下:
其中高字节前5位都是符号位S, 若分辨率低于12位时, 相应地使最低为0, 如: 当分辨
, 高字节不变....
一些温度与转换后输出的数字参照如下:
由上表可看出, 当输出是负温度时, 使用补码表示, 方便计算机运算(若是用C语言, 直接将结果赋值给一个int变量即可).
DS18B20 的使用方法:
由于DS18B20 采用的是1-Wire 总线协议方式,即在一根数据线实现数据的双向传输,而对单片机来说,我们必须采用软件的方法来模拟单总线的协议时序来完成对DS18B20芯片的访问。
由于DS18B20是在一根I/O线上读写数据,因此,对读写的数据位有着严格的时序要求。DS18B20有严格的通信协议来保证各位数据传输的正确性和完整性。
该协议定义了几种信号的时序:初始化时序(dsInit()实现)、读时序(readByte())、写时序(writeByte())。
所有时序都是将主机作为主设备,单总线器件作为从设备。而每一次命令和数据的传输都是从主机主动启动写时序开始,如果要求单总线器件回送数据,在进行写命令后,主机需启动读时序完成数据接收。数据和命令的传输都是低位在先。
DS18B20与单片机连接电路图:
利用软件模拟DS18B20的单线协议和命令:主机操作DS18B20必须遵循下面的顺序1. 初始化
单线总线上的所有操作都是从初始化开始的. 过程如下:
1)请求: 主机通过拉低单线480us以上, 产生复位脉冲, 然后释放该线, 进入Rx接收模式. 主机释放总线时, 会产生一个上升沿脉冲.
DQ : 1 -> 0(480us+) -> 1
2)响应: DS18B20检测到该上升沿后, 延时15~60us, 通过拉低总线60~240us来产生应答脉冲.
DQ: 1(15~60us) -> 0(60~240us)
3)接收响应: 主机接收到从机的应答脉冲后, 说明有单线器件在线. 至此, 初始化完成. DQ: 0
2. ROM操作命令
当主机检测到应答脉冲, 便可发起ROM操作命令. 共有5类ROM操作命令, 如下表
3. 内存操作命令
在成功执行ROM操作命令后, 才可使用内存操作命令. 共有6种内存操作命令:
4. 数据处理
DS18B20要求有严格的时序来保证数据的完整性. 在单线DQ上, 有复位脉冲, 应答脉冲,
写0, 写1, 读0, 读1这6种信号类型. 除了应答脉冲外, 其它都由主机产生. 数据位的读和写是通过读、写时隙实现的.
1) 写时隙: 当主机将数据线从高电平拉至低电平时, 产生写时隙.所有写时隙都必须在
60us以上, 各写时隙间必须保证1us的恢复时间.
写"1" : 主机将数据线DQ先拉低, 然后释放15us后, 将数据线DQ拉高;
写"0" : 主机将DQ拉低并至少保持60us以上.
2)读时隙: 当主机将数据线DQ从高电平拉至低电平时, 产生读时隙. 所有读时隙最短必须持续60us, 各读时隙间必须保证1us的恢复时间.
读: 主机将DQ拉低至少1us,. 此时主机马上将DQ拉高, 然后就可以延时15us后, 读取DQ即可.
源代码: (测量范围: 0 ~ 99度)
DS18B20
1#include
2//通过DS18B20测试当前环境温度, 并通过数码管显示当前温度值
3sbit wela = P2^7; //数码管位选
4sbit dula = P2^6; //数码管段选
5sbit ds = P2^2;
6//0-F数码管的编码(共阴极)
7unsigned char code table[]={0x3f,0x06,0x5b,0x4f,0x66,
8 0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};
9//0-9数码管的编码(共阴极), 带小数点
10
unsigned char code tableWidthDot[]={0xbf, 0x86, 0xdb, 0xcf, 0xe6, 0xed, 0xfd, 11 0x87, 0xff, 0xef};
12
13//延时函数, 例i=10,则大概延时10ms.
14void delay(unsigned char i)
15{
16 unsigned char j, k;
17for(j = i; j > 0; j--)
18 {
19for(k = 125; k > 0; k--);
20 }
21}
22
23//初始化DS18B20
24//让DS18B20一段相对长时间低电平, 然后一段相对非常短时间高电平, 即可启动
25void dsInit()
26{
27//一定要使用unsigned int型, 一个i++指令的时间, 作为与DS18B20通信的小时间间隔
28 //以下都是一样使用unsigned int型
30 ds = 0;
31 i = 103;
32while(i>0) i--;
33 ds = 1;
34 i = 4;
35while(i>0) i--;
36}
37
38//向DS18B20读取一位数据
39//读一位, 让DS18B20一小周期低电平, 然后两小周期高电平,
40//之后DS18B20则会输出持续一段时间的一位数据
41bit readBit()
42{
43 unsigned int i;
44 bit b;
45 ds = 0;
46 i++;
47 ds = 1;
48 i++; i++;
49 b = ds;
50 i = 8;
51while(i>0) i--;
52return b;
53}
54
55//读取一字节数据, 通过调用readBit()来实现
56unsigned char readByte()
57{
58 unsigned int i;
59 unsigned char j, dat;
60 dat = 0;
61for(i=0; i<8; i++)
62 {
63 j = readBit();
64//最先读出的是最低位数据
65 dat = (j << 7) | (dat >> 1);
66 }
67return dat;
68}
69
70//向DS18B20写入一字节数据
71void writeByte(unsigned char dat)
72{
74 unsigned char j;
75 bit b;
76for(j = 0; j < 8; j++)
77 {
78 b = dat & 0x01;
79 dat >>= 1;
80//写"1", 让低电平持续2个小延时, 高电平持续8个小延时
81if(b)
82 {
83 ds = 0;
84 i++; i++;
85 ds = 1;
86 i = 8; while(i>0) i--;
87 }
88else//写"0", 让低电平持续8个小延时, 高电平持续2个小延时
89 {
90 ds = 0;
91 i = 8; while(i>0) i--;
92 ds = 1;
93 i++; i++;
94 }
95 }
96}
97
98//向DS18B20发送温度转换命令
99void sendChangeCmd()
100{
101 dsInit(); //初始化DS18B20
102 delay(1); //延时1ms
103 writeByte(0xcc); //写入跳过序列号命令字
104 writeByte(0x44); //写入温度转换命令字
105}
106
107//向DS18B20发送读取数据命令
108void sendReadCmd()
109{
110 dsInit();
111 delay(1);
112 writeByte(0xcc); //写入跳过序列号命令字
113 writeByte(0xbe); //写入读取数据令字
114}
115
116//获取当前温度值
117unsigned int getTmpValue()
118{
119 unsigned int value; //存放温度数值
120float t;
121 unsigned char low, high;
122 sendReadCmd();
123//连续读取两个字节数据
124 low = readByte();
125 high = readByte();
126//将高低两个字节合成一个整形变量
127 value = high;
128 value <<= 8;
129 value |= low;
130//DS18B20的精确度为0.0625度, 即读回数据的最低位代表0.0625度
131 t = value * 0.0625;
132//将它放大10倍, 使显示时可显示小数点后一位, 并对小数点后第二2进行4舍5入
133 //如t=11.0625, 进行计数后, 得到value = 111, 即11.1 度
134 value = t * 10 + 0.5;
135return value;
136}
137
138//显示当前温度值, 精确到小数点后一位
139void display(unsigned int v)
140{
141 unsigned char count;
142 unsigned char datas[] = {0, 0, 0};
143 datas[0] = v / 100;
144 datas[1] = v % 100 / 10;
145 datas[2] = v % 10;
146for(count = 0; count < 3; count++)
147 {
148//片选
149 wela = 0;
150 P0 = ((0xfe << count) | (0xfe >> (8 - count))); //选择第(count + 1) 个数码管
151 wela = 1; //打开锁存, 给它一个下降沿量
152 wela = 0;
153//段选
154 dula = 0;
155if(count != 1)
156 {
157 P0 = table[datas[count]]; //显示数字
158 }
159else
160 {
161 P0 = tableWidthDot[datas[count]]; //显示带小数点数字
162 }
163 dula = 1; //打开锁存, 给它一个下降沿量
164 dula = 0;
165 delay(5); //延时5ms, 即亮5ms
166
167 //清除段先, 让数码管灭, 去除对下一位的影响, 去掉高位对低位重影
168 //若想知道影响效果如何, 可自行去掉此段代码
169 //因为数码管是共阴极的, 所有灭的代码为: 00H
170 dula = 0;
171 P0 = 0x00; //显示数字
172 dula = 1; //打开锁存, 给它一个下降沿量
173 dula = 0;
174 }
175}
176
177void main()
178{
179 unsigned char i;
180 unsigned int value;
181while(1)
182 {
183//启动温度转换
184 sendChangeCmd();
185 value = getTmpValue();
186//显示3次
187for(i = 0; i < 3; i++)
188 {
189 display(value);
190 }
191 }
192}
显示效果:
流程图:
改进代码: 扩大测量范围, 使可测量范围为: -55度~ +125度, 严格按照上面的流程进行软件设计
改进代码
1#include
2#include
3#include
4//
5sbit wela = P2^7; //数码管位选
6sbit dula = P2^6; //数码管段选
7sbit ds = P2^2;
8int tempValue;
9
10//0-F数码管的编码(共阴极)
11unsigned char code table[]={0x3f,0x06,0x5b,0x4f,0x66,
12 0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};
13//0-9数码管的编码(共阴极), 带小数点
14
unsigned char code tableWidthDot[]={0xbf, 0x86, 0xdb, 0xcf, 0xe6, 0xed, 0xfd, 15 0x87, 0xff, 0xef};
16
17//延时函数, 对于11.0592MHz时钟, 例i=10,则大概延时10ms.
18void delay(unsigned int i)
19{
20 unsigned int j;
21while(i--)
22 {
23for(j = 0; j < 125; j++);
24 }
25}
26
27//初始化DS18B20
28//让DS18B20一段相对长时间低电平, 然后一段相对非常短时间高电平, 即可启动
29void dsInit()
30{
31//对于11.0592MHz时钟, unsigned int型的i, 作一个i++操作的时间大于为8us
32 unsigned int i;
33 ds = 0;
34 i = 100; //拉低约800us, 符合协议要求的480us以上
35while(i>0) i--;
36 ds = 1; //产生一个上升沿, 进入等待应答状态
37 i = 4;
38while(i>0) i--;
39}
40
41void dsWait()
42{
43 unsigned int i;
44while(ds);
45while(~ds); //检测到应答脉冲
46 i = 4;
47while(i > 0) i--;
48}
49
50//向DS18B20读取一位数据
51//读一位, 让DS18B20一小周期低电平, 然后两小周期高电平,
52//之后DS18B20则会输出持续一段时间的一位数据
53bit readBit()
54{
55 unsigned int i;
56 bit b;
57 ds = 0;
58 i++; //延时约8us, 符合协议要求至少保持1us
59 ds = 1;
60 i++; i++; //延时约16us, 符合协议要求的至少延时15us以上
61 b = ds;
62 i = 8;
63while(i>0) i--; //延时约64us, 符合读时隙不低于60us要求
64return b;
65}
66
67//读取一字节数据, 通过调用readBit()来实现
68unsigned char readByte()
69{
70 unsigned int i;
71 unsigned char j, dat;
72 dat = 0;
73for(i=0; i<8; i++)
74 {
75 j = readBit();
76//最先读出的是最低位数据
77 dat = (j << 7) | (dat >> 1);
78 }
79return dat;
80}
81
82//向DS18B20写入一字节数据
83void writeByte(unsigned char dat)
84{
85 unsigned int i;
86 unsigned char j;
87 bit b;
88for(j = 0; j < 8; j++)
89 {
90 b = dat & 0x01;
91 dat >>= 1;
92//写"1", 将DQ拉低15us后, 在15us~60us内将DQ拉高, 即完成写1
93if(b)
94 {
95 ds = 0;
96 i++; i++; //拉低约16us, 符号要求15~60us内
97 ds = 1;
98 i = 8; while(i>0) i--; //延时约64us, 符合写时隙不低于60us要求
99 }
100else//写"0", 将DQ拉低60us~120us
101 {
102 ds = 0;
103 i = 8; while(i>0) i--; //拉低约64us, 符号要求
104 ds = 1;
105 i++; i++; //整个写0时隙过程已经超过60us, 这里就不用像写1那样, 再延时64us了
106 }
107 }
108}
109
110//向DS18B20发送温度转换命令
111void sendChangeCmd()
112{
113 dsInit(); //初始化DS18B20, 无论什么命令, 首先都要发起初始化
114 dsWait(); //等待DS18B20应答
115 delay(1); //延时1ms, 因为DS18B20会拉低DQ 60~240us作为应答信号
116 writeByte(0xcc); //写入跳过序列号命令字 Skip Rom
117 writeByte(0x44); //写入温度转换命令字 Convert T
118}
119
120//向DS18B20发送读取数据命令
121void sendReadCmd()
122{
123 dsInit();
124 dsWait();
125 delay(1);
126 writeByte(0xcc); //写入跳过序列号命令字 Skip Rom
127 writeByte(0xbe); //写入读取数据令字 Read Scratchpad
128}
129
130//获取当前温度值
131int getTmpValue()
132{
133 unsigned int tmpvalue;
134int value; //存放温度数值
135float t;
136 unsigned char low, high;
137 sendReadCmd();
138//连续读取两个字节数据
139 low = readByte();
140 high = readByte();
141//将高低两个字节合成一个整形变量
142 //计算机中对于负数是利用补码来表示的
143 //若是负值, 读取出来的数值是用补码表示的, 可直接赋值给int型的value
144 tmpvalue = high;
145 tmpvalue <<= 8;
146 tmpvalue |= low;
147 value = tmpvalue;
148
149//使用DS18B20的默认分辨率12位, 精确度为0.0625度, 即读回数据的最低位代表0.0625度
150 t = value * 0.0625;
151//将它放大100倍, 使显示时可显示小数点后两位, 并对小数点后第三进行4舍5入
152 //如t=11.0625, 进行计数后, 得到value = 1106, 即11.06 度
153 //如t=-11.0625, 进行计数后, 得到value = -1106, 即-11.06 度
154 value = t * 100 + (value > 0 ? 0.5 : -0.5); //大于0加0.5, 小于0减0.5
155return value;
156}
157
158unsigned char const timeCount = 3; //动态扫描的时间间隔
159//显示当前温度值, 精确到小数点后一位
160//若先位选再段选, 由于IO口默认输出高电平, 所以当先位选会使数码管出现乱码
161void display(int v)
162{
163 unsigned char count;
164 unsigned char datas[] = {0, 0, 0, 0, 0};
165 unsigned int tmp = abs(v);
166 datas[0] = tmp / 10000;
167 datas[1] = tmp % 10000 / 1000;
168 datas[2] = tmp % 1000 / 100;
169 datas[3] = tmp % 100 / 10;
170 datas[4] = tmp % 10;
171if(v < 0)
172 {
173//关位选, 去除对上一位的影响
174 P0 = 0xff;
175 wela = 1; //打开锁存, 给它一个下降沿量
176 wela = 0;
177//段选
178 P0 = 0x40; //显示"-"号
179 dula = 1; //打开锁存, 给它一个下降沿量
180 dula = 0;
181
182//位选
183 P0 = 0xfe;
184 wela = 1; //打开锁存, 给它一个下降沿量
185 wela = 0;
186 delay(timeCount);
187 }
188for(count = 0; count != 5; count++)
189 {
190//关位选, 去除对上一位的影响
191 P0 = 0xff;
192 wela = 1; //打开锁存, 给它一个下降沿量
193 wela = 0;
194//段选
195if(count != 2)
196 {
197/* if((count == 0 && datas[count] == 0)
198 || ((count == 1 && datas[count] == 0) && (count == 0 && data s[count - 1] == 0)))
199 {
200 P0 = 0x00; //当最高位为0时, 不作显示
201 }
202 else*/
203 P0 = table[datas[count]]; //显示数字
204 }
205else
206 {
207 P0 = tableWidthDot[datas[count]]; //显示带小数点数字
208 }
209 dula = 1; //打开锁存, 给它一个下降沿量
210 dula = 0;
211
212//位选
213 P0 = _crol_(0xfd, count); //选择第(count + 1) 个数码管
214 wela = 1; //打开锁存, 给它一个下降沿量
215 wela = 0;
216 delay(timeCount);
217 }
218}
219
220void main()
221{
222 unsigned char i;
223
224while(1)
225 {
226//启动温度转换
227 sendChangeCmd();
228//显示5次
229for(i = 0; i < 40; i++)
230 {
231 display(tempValue);
232 }
233 tempValue = getTmpValue();
234 }
235}
改进后的效果图:
只有一位小数
两位小数, 并消除下一位对上一位的影响
(1)先将数据线置高电平“1”。 (2)延时(该时间要求的不是很严格,但是尽可能的短一点) (3)数据线拉到低电平“0”。 (4)延时750微秒(该时间的时间范围可以从480到960微秒)。 (5)数据线拉到高电平“1”。 (6)延时等待(如果初始化成功则在15到60毫秒时间之内产生一个由DS18B20所返回的低电平“0”。据该状态可以来确定它的存在,但是应注意不能无限的进行等待,不然会使程序进入死循环,所以要进行超时控制)。 (7)若CPU读到了数据线上的低电平“0”后,还要做延时,其延时的时间从发出的高电平算起(第(5)步的时间算起)最少要480微秒。 (8)将数据线再次拉高到高电平“1”后结束。
(1)数据线先置低电平“0”。 (2)延时确定的时间为15微秒。 (3)按从低位到高位的顺序发送字节(一次只发送一位)。 (4)延时时间为45微秒。 (5)将数据线拉到高电平。 (6)重复上(1)到(6)的操作直到所有的字节全部发送完为止。(7)最后将数据线拉高。 DS18B20的写操作时序图如图
DS18B20的读操作 (1)将数据线拉高“1”。 (2)延时2微秒。 (3)将数据线拉低“0”。 (4)延时15微秒。 (5)将数据线拉高“1”。 (6)延时15微秒。 (7)读数据线的状态得到1个状态位,并进行数据处理。 (8)延时30微秒。DS18B20的读操作时序图如图所示。
DS18B20的Protues仿真图 源程序代码: #include "reg51.h" #include "intrins.h" // 此头文件中有空操作语句NOP 几个微秒的延时可以用NOP 语句,但本人没用NOP,直接用了I++来延时 #define uchar unsigned char #define uint unsigned int uchar code table[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37, 0x38,0x39}; sbit ds18b20_io=P2^0; //单片机与DS18B20的连接口 sbit lcdrs=P2^6; //1602与单片机的接口 sbit lcden=P2^7;
最近都在学习和写单片机的程序, 今天有空又模仿DS18B20温度测量显示实验写了一个与DS18B20基于单总线通信的程序. DS18B20 数字温度传感器(参考:智能温度传感器DS18B20的原理与应用)是DALLAS 公司生产的1-Wire,即单总线器件,具有线路简单,体积小的特点。因此用它来组成一个测温系统,具有线路简单,在一根通信线,可以挂很多这样的数字温度计。DS18B20 产品的特点: (1)、只要求一个I/O 口即可实现通信。 (2)、在DS18B20 中的每个器件上都有独一无二的序列号。 (3)、实际应用中不需要外部任何元器件即可实现测温。 (4)、测量温度范围在-55 到+125℃之间; 在-10 ~ +85℃范围内误差为±5℃; (5)、数字温度计的分辨率用户可以从9 位到12 位选择。将12位的温度值转换为数字量所需时间不超过750ms; (6)、内部有温度上、下限告警设置。 DS18B20引脚分布图 DS18B20 详细引脚功能描述: 1、GND 地信号; 2、DQ数据输入出引脚。开漏单总线接口引脚。当被用在寄生电源下,此引脚可以向器件提供电源;漏极开路, 常太下高电平. 通常要求外接一个约5kΩ的上拉电阻. 3、VDD可选择的VDD 引脚。电压范围:3~5.5V; 当工作于寄生电源时,此引脚必须接地。 DS18B20存储器结构图 暂存储器的头两个字节为测得温度信息的低位和高位字节;
第3, 4字节是TH和TL的易失性拷贝, 在每次电复位时都会被刷新; 第5字节是配置寄存器的易失性拷贝, 同样在电复位时被刷新; 第9字节是前面8个字节的CRC检验值. 配置寄存器的命令内容如下: MSB LSB R0和R1是温度值分辨率位, 按下表进行配置.默认出厂设置是R1R0 = 11, 即12位. 温度值分辨率配置表 4种分辨率对应的温度分辨率为0.5℃, 0.25℃, 0.125℃, 0.0625℃(即最低一位代表的温度值) 12位分辨率时的两个温度字节的具体格式如下: 其中高字节前5位都是符号位S, 若分辨率低于12位时, 相应地使最低为0, 如: 当分辨 , 高字节不变.... 一些温度与转换后输出的数字参照如下:
最近天气热了,想要是做个能显示温度的小设备就好了, 于是想到DIY 个电子温度计, 网上找了很多资料,结合自己的材料,设计了这个用单片机控制的实时电子温度计。 作为单 片机小虾的我做这个用了 2天时间,当然是下班后,做工不行见谅了。 主要元件用到了单片机 STC89C54RD+ , DB18B20温度传感器,4为共阳数码管, PNPS8550三极管等。 先上原理图: 洞洞板布局图: 然后就是实物图了: 函8D P3 iW 、 E E FJ T I RF D51*BZ0渥度澈码管显示 F7 Dl'AI>D li'A£> I 2、心 PDRM, 杖心P0WAD7 Pl I^TO 洋心EI^AJ D FLSAH
附上源程序:程序是别人写的,我只是自己 修改了下,先谢谢原程序者的无私奉献。 #include"reg52.h” #define uchar unsigned char #define uint unsigned int sbit DQ=P3A 4; 〃温度数据口 sbit wx1=P2A0; sbit wx2=P2A1; sbit wx3=P2A2; sbit wx4=P2A3; unsigned int temp, temp1,temp2, xs; //位选1 //位选2 //位选3 //位选4
uchar code table[]={0xc0,0xf9,0xa4,0xb0,0x99, 0x92,0x82,0xf8,0x80,0x90,0x88,0x83,0xc6}; /****** 延时程序 *******/ void delay1(unsigned int m) { unsigned int i,j; for(i=m;i>0;i--) for(j=110;j>0;j--); } void delay(unsigned int m) { while(m--); } /***********ds18b20 uchar ReadOneChar() { unsigned char i=0; unsigned char dat = 0; for (i=8;i>0;i--) { 读一个字节 **************/ void Init_DS18B20() { unsigned char x=0; DQ = 1; //DQ 复位 delay(8); 〃稍做延时 DQ = 0; 〃单片机将 ds18b20通信端口 DQ 拉低 delay(80); //精确延时大于480us DQ = 1; delay(4); x=DQ; delay(20); } 〃拉高总线 //稍做延时后如果x=0则初始化成功 x=1 则初始化失败 〃共阳数码管 〃温度延时程序
DS18B20的工作原理: DS18B20单线数字温度传感器是DALLAS半导体公司开发的适配微处理器的智能温度传感器。它具有3脚TO-92小体积封装形式。温度测量范围为-55℃--+125℃,可进行9-12位的编程,分辨率可达0.0625。被测温度用符号扩展的16位数字量方式串行输出。工作电压支持3V-5.5V,CPU只需一根端口线就能与诸多DS18B20通信,占用微处理器的端口较少。DS18B20采用3脚TO-92封装,引脚排列如图: DQ:数字信号端;GND:电源地;VDD:电源输入端 DS18B20的内部框图如图: 主要由寄生电源、64位激光ROM与单线接口、温度传感器、高速暂存器、触发寄存器、存储与控制逻辑、8位循环冗余校验码发生器组成。 测温电路原理: 低温度系数振荡器用于产生稳定的频率f,振荡频率受温度的影响很小,高温度系数振荡器将被测温度转化成频率信号,随温度变化其振荡频率明显改变。图中还隐含着计数门,当计数门打开时,DS18B20就对低温度振荡器产生的时钟脉冲进行计数,进而完成温度测量。计数门的开启时间由高温度系数振荡器来决定。每次测量前,首先将-55℃所对应的基数分别
置入减法计数器、温度寄存器中。在计数门关闭之前若计数器已减至零,温度寄存器中的数值就增加0.5℃。然后,计数器依斜率累加器的状态置入新的数值,再对时钟计数,然后减至零,温度寄存器值又增加0.5℃。只要计数门仍未关闭,就重复上诉过程,直至温度寄存器值达到被测温度值。 温度传感器的应用背景: 当今社会已经完全进入了电子信息化,温度控制器在各行各业中已经得到了充分的利用。具有对温度进行实时监控的功能,保证机器,测量仪器等等的正常运坐,他最大的特点是能实时监控周围温度的高低,并能同时控制电机运作来改变温度。现阶段运用于国内大部分家庭,系统效率越来越高,成本也越来越低。并可以根据其性质进行相应的改进运用于不同场合进行温度监测控制,比如仓库里、汽车里、电脑等等,带来大量的经济效益。可广泛应用于城市、农村、各种工业生产,在一定情况下也可以用于太阳能、锅炉及对温度敏感的产业的自动控制和温度报警,是实现无人值守的理想产品,市场极为广阔,需求量大。并且使用寿命长,适用范围广,安装及其容易。 智能风扇的应用: 传统的风扇大部分只有手动调速,再加一个定时器,功能单一。往往也存在一些隐患,如人们常常离开后忘记关闭风扇,浪费电且容易引发火灾,长时间工作还容易损坏电器。在如前半夜温度高,电风扇调的风速较高,但到了后半夜,温度下降,风速不会随气温变化,容易着凉,智能风扇的出现就能对环境进行检测,能随温度的变化而改变风速。 温度传感器的选择方案: 方案1:热敏电阻。 采用热敏电阻,可满足40摄氏度至90摄氏度的测量范围,但热敏电阻精度、重复性、可靠性比较差,对于检测1摄氏度的信号是不适用的。而且在温度测量系统中,是采用单片温度传感器,比如AD590,LM35等,但这些芯片输出的都是模拟信号,必须经过A/D转化后才能送给计算机,这样就使得测温装置的结构较复杂,另外,这种测温装置的一根线上只能挂一个传感器,不能进行多点测量,即使能实现,也要用到复杂的算法,一定程度上增加了软件实现的难度 方案2:DS18B20 DS18B20温度传感器是以9位数字量的形式反映器件的温度值,DS18B20通过一个单线接口发送或接受信息,因此在中央微处理器和DS18B20之间仅需一条连线(加上地线),用于读写和温度转化的电源可以从数据线本身获得,无需外部电源。它可以直接将模拟信号转化为数字信号,降低了电路的复杂程度,提高电路的运行质量。 综上,选择了方案2进行温度测量。 DS18B20的一般操作过程: 1:初始化 2:跳过ROM(命令CCH) 3:温度变换(命令44H)
温度值精确到0.1度,lcd1602显示 仿真电路图如下: c程序如下: #include
uchar data disdata[5]; uint tvalue;//温度值 uchar tflag;//温度正负标志 /*************************lcd1602程序**************************/ void delay1ms(unsigned int ms)//延时1毫秒(不够精确的){unsigned int i,j; for(i=0;i 1.DS18B20复位程序分析 单片机发送复位脉冲低电平保持至少480us 释放总线进入接收状态,等待15us-60us DS18B20发出存在脉冲脉冲持续60-240us void reset() { uint i;//i 定义为uchar型 ds=0; i=103; while(i>0)i--; ds=1; while(i>0)i--;//在这里不做存在检测 } 2.DS18B20写程序 时序分析: 单片机由高电平拉低至低电平产生写时间隙 15us之后就需要将所需要写的位送到总线上面 DS18B20在开始之后的15-60us内对总线进行采样(注意采样时间)uint dswrite(uchar dat) { uchar i; uint j; sbit tempbyte; for(i=0;i<8;i++) { tempbyte=dat&0x01; dat>>=1;//从最低位开始每一位送到tempbyte临时位 //总线拉低为低电平 if(tempbyte)//写1 { ds=0; j++; j++;//延时个13us ds=1; j=8; while(j>0)j--//延时个71us } else { ds=0; j=8; while(j>0)j--; ds=1; j++;j++;//保证大于1us- } } } 3.DS18B20读时序 时序分析 单片机从高电平拉低至低电平 低电平保持4us后将总线拉高产生读时间隙 读时间在4us后到15us之前(注意一定在15us之前)读时间才有效从拉低总线60us-120us之间释放总线(注意是在这个时间间隙之间,严格按照时序操作) 51单片机操作DS18B20汇编源程序 推荐 ; FLAG1:标志位,为"1"时表示检测到DS18B20 ; DQ:DS18B20的数据总线接脚 ; TEMPER_NUM:保存读出的温度数据 ; 本程序仅适合单个DS18B20和51单片机的连接,晶振为12MHZ左右TEMPER_LEQU36H TEMPER_HEQU35H DQBITP1.7 ; DS18B20初始化程序 ;//*****************************************// INIT_1820: SETBDQ NOP CLRDQ MOVR0,#06BH TSR1: DJNZR0,TSR1; 延时 SETBDQ MOVR0,#25H TSR2: JNBDQ,TSR3 DJNZR0,TSR2 LJMPTSR4; 延时 TSR3: SETBFLAG1; 置标志位,表示DS1820存在 LJMPTSR5 TSR4: CLRFLAG1; 清标志位,表示DS1820不存在 LJMPTSR7 TSR5: MOVR0,#06BH TSR6: DJNZR0,TSR6; 延时 TSR7: SETBDQ RET ;//*****************************************// ; 重新写DS18B20暂存存储器设定值 ;//*****************************************// RE_CONFIG: JBFLAG1,RE_CONFIG1; 若DS18B20存在,转RE_CONFIG1 RET RE_CONFIG1: MOVA,#0CCH; 发SKIP ROM命令 LCALLWRITE_1820 MOVA,#4EH; 发写暂存存储器命令 LCALLWRITE_1820 MOVA,#00H; TH(报警上限)中写入00H LCALLWRITE_1820 MOVA,#00H; TL(报警下限)中写入00H LCALLWRITE_1820 MOVA,#1FH; 选择9位温度分辨率 LCALLWRITE_1820 RET ;//*****************************************// ; 读出转换后的温度值 ;//*****************************************// GET_TEMPER: SETBDQ; 定时入口 LCALLINIT_1820 JBFLAG1,TSS2 RET; 若DS18B20不存在则返回 TSS2: MOVA,#0CCH; 跳过ROM匹配 LCALLWRITE_1820 MOVA,#44H; 发出温度转换命令 LCALLWRITE_1820 LCALLINIT_1820 MOVA,#0CCH; 跳过ROM匹配 LCALLWRITE_1820 MOVA,#0BEH; 发出读温度命令 LCALLWRITE_1820 LCALLREAD_1820 MOVTEMPER_NUM,A; 将读出的温度数据保存 RET ;//*****************************************// ; 读DS18B20的程序,从DS18B20中读出一个字节的数据 温度传感器DS18B20资料 2008-08-28 16:06 美国Dallas半导体公司的数字化温度传感器DS1820是世界上第一片支持 "一线总线"接口的温度传感器,在其内部使用了在板(ON-B0ARD)专利技术。全部传感元件及转换电路集成在形如一只三极管的集成电路内。一线总线独特而且经济的特点,使用户可轻松地组建传感器网络,为测量系统的构建引入全新概念。现在,新一代的DS18B20体积更小、更经济、更灵活。使你可以充分发挥“一线总线”的优点。目前DS18B20批量采购价格仅10元左右。 在传统的模拟信号远距离温度测量系统中,需要很好的解决引线误差补偿问题、多点测量切换误差问题和放大电路零点漂移误差问题等技术问题,才能够达到较高的测量精度。另外一般监控现场的电磁环境都非常恶劣,各种干扰信号较强,模拟温度信号容易受到干扰而产生测量误差,影响测量精度。因此,在温度测量系统中,采用抗干扰能力强的新型数字温度传感器是解决这些问题的最有效方案,新型数字温度传感器DS18B20具有体积更小、精度更高、适用电压更宽、采用一线总线、可组网等优点,在实际应用中取得了良好的测温效果。 新的"一线器件"DS18B20体积更小、适用电压更宽、更经济。 DS18B20、DS1822的特性 DS18B20可以程序设定9~12位的分辨率,精度为±0.5°C。可选更小的封装方式,更宽的电压适用范围。分辨率设定,及用户设定的报警温度存储在EEPROM中,掉电后依然保存。DS18B20的性能是新一代产品中最好的!性能价格比也非常出色!DS1822与DS18B20软件兼容,是DS18B20的简化版本。省略了存储用户定义报警温度、分辨率参数的EEPROM,精度降低为±2°C,适用于对性能要求不高,成本控制严格的应用,是经济型产品。 继"一线总线"的早期产品后,DS1820开辟了温度传感器技术的新概念。DS18B20和DS1822使电压、特性及封装有更多的选择,让我们可以构建适合自己的经济的测温系统。 DS18B20、DS1822 "一线总线"数字化温度传感器 同DS1820一样,DS18B20也支持"一线总线"接口,测量温度范围为-55°C~+125°C,在-10~+85°C 范围内,精度为±0.5°C。DS1822的精度较差为±2°C。现场温度直接以"一线总线"的数字方式传输,大大提高了系统的抗干扰性。适合于恶劣环境的现场温度测量,如:环境控制、设备或过程控制、测温类消费电子产品等。与前一代产品不同,新的产品支持3V~5.5V的电压范围,使系统设计更灵活、方便。而且新一代产品更便宜,体积更小。 一、DS18B20的主要特性 (1)适应电压范围更宽,电压范围:3.0~5.5V,在寄生电源方式下可由数据线供电 (2)独特的单线接口方式,DS18B20在与微处理器连接时仅需要一条口线即可实现微处理器与DS18B20的双向通讯 (3)DS18B20支持多点组网功能,多个DS18B20可以并联在唯一的三线上,实现组网多点测温 (4)DS18B20在使用中不需要任何外围元件,全部传感元件及转换电路集成在形如一只三极管的集成电路内 (5)温范围-55℃~+125℃,在-10~+85℃时精度为±0.5℃ (6)可编程的分辨率为9~12位,对应的可分辨温度分别为0.5℃、0.25℃、0.125℃和0.0625℃, 最近天气热了,想要是做个能显示温度的小设备就好了,于是想到DIY个电子温度计,网上找了很多资料,结合自己的材料,设计了这个用单片机控制的实时电子温度计。作为单片机小虾的我做这个用了2天时间,当然是下班后,做工不行见谅了。 主要元件用到了单片机STC89C54RD+,DB18B20温度传感器,4为共阳数码管,PNPS8550三极管等。 先上原理图: 洞洞板布局图: 然后就是实物图了: 附上源程序:程序是别人写的,我只是自己修改了下,先谢谢原程序者的无私奉献。#include"reg52.h" #define uchar unsigned char #define uint unsigned int sbit DQ=P3^4; //温度数据口 sbit wx1=P2^0; //位选1 sbit wx2=P2^1; //位选2 sbit wx3=P2^2; //位选3 sbit wx4=P2^3; //位选4 unsigned int temp, temp1,temp2, xs; uchar code table[]={0xc0,0xf9,0xa4,0xb0,0x99, //共阳数码管0x92,0x82,0xf8,0x80,0x90,0x88,0x83,0xc6}; /******延时程序*******/ void delay1(unsigned int m) { unsigned int i,j; for(i=m;i>0;i--) for(j=110;j>0;j--); } void delay(unsigned int m) //温度延时程序 { while(m--); } void Init_DS18B20() { unsigned char x=0; DQ = 1; //DQ复位ds18b20通信端口 delay(8); //稍做延时 DQ = 0; //单片机将DQ拉低 delay(80); //精确延时大于480us DQ = 1; //拉高总线 delay(4); x=DQ; //稍做延时后如果x=0则初始化成功x=1则初始化失败delay(20); } /***********ds18b20读一个字节**************/ uchar ReadOneChar() { unsigned char i=0; unsigned char dat = 0; for (i=8;i>0;i--) { 18B20温度传感器应用解析 温度传感器的种类众多,在应用与高精度、高可靠性的场合时DALLAS(达拉斯)公司生产的DS18B20温度传感器当仁不让。超小的体积,超低的硬件开消,抗干扰能力强,精度高,附加功能强,使得DS18B 20更受欢迎。对于我们普通的电子爱好者来说,DS18B20的优势更是我们学习单片机技术和开发温度相关的小产品的不二选择。了解其工作原理和应用可以拓宽您对单片机开发的思路。 DS18B20的主要特征: ?? 全数字温度转换及输出。 ?? 先进的单总线数据通信。 ?? 最高12位分辨率,精度可达土0.5摄氏度。 ?? 12位分辨率时的最大工作周期为750毫秒。 ?? 可选择寄生工作方式。 ?? 检测温度范围为–55°C ~+125°C (–67°F ~+257°F) ?? 内置EEPROM,限温报警功能。 ?? 64位光刻ROM,内置产品序列号,方便多机挂接。 ?? 多样封装形式,适应不同硬件系统。 DS18B20芯片封装结构: DS18B20引脚功能: ·GND 电压地·DQ 单数据总线·VDD 电源电压·NC 空引脚 DS18B20工作原理及应用: DS18B20的温度检测与数字数据输出全集成于一个芯片之上,从而抗干扰力更强。其一个工作周期可分为两个部分,即温度检测和数据处理。在讲解其工作流程之前我们有必要了解18B20的内部存储器资源。18B20共有三种形态的存储器资源,它们分别是: ROM 只读存储器,用于存放DS18B20ID编码,其前8位是单线系列编码(DS18B20的编码是19H),后面48位是芯片唯一的序列号,最后8位是以上56的位的CRC码(冗余校验)。数据在出产时设置不由用户更改。DS18B20共64位ROM。 RAM 数据暂存器,用于内部计算和数据存取,数据在掉电后丢失,DS18B20共9个字节RAM,每个字节为8位。第1、2个字节是温度转换后的数据值信息,第3、4个字节是用户EEPROM(常用于温度报警值储存)的镜像。在上电复位时其值将被刷新。第5个字节则是用户第3个EEPROM的镜像。第6、7、8个字节为计数寄存器,是为了让用户得到更高的温度分辨率而设计的,同样也是内部温度转换、计算的暂存单元。第9个字节为前8个字节的CRC码。EEPROM 非易失性记忆体,用于存放长期需要保存的数据,上下限温度报警值和校验数据,DS18B20共3位EEPROM,并在RAM都存在镜像,以方便用户操作。RAM及EEPROM结构图: 图2 我们在每一次读温度之前都必须进行复杂的且精准时序的处理,因为DS18B20的硬件简单结果就会导致软件的巨大开消,也是尽力减少有形资产转化为无形资产的投入,是一种较好的节约之道。 控制器对18B20操作流程: 1,复位:首先我们必须对DS18B20芯片进行复位,复位就是由控制器(单片机)给DS18B20单总线至少480uS的低电平信号。当18B20接到此复位信号后则会在15~60uS后回发一个芯片的存在脉冲。 2,存在脉冲:在复位电平结束之后,控制器应该将数据单总线拉高,以便于在15~60uS后接收存在脉冲,存在脉冲为一个60~240uS的低电平信号。至此,通信双方已经达成了基本的协议,接下来将会是控制器与18B20间的数据通信。如果复位低电平的时间不足或是单总线的电路断路都不会接到存在脉冲,在设计时要注意意外情况的处理。 3,控制器发送ROM指令:双方打完了招呼之后最要将进行交流了,ROM指令共有5条,每一个工作周期只能发一条,ROM指令分别是读ROM数据、指定匹配芯片、跳跃ROM、芯片搜索、报警芯片搜索。ROM指令为8位长度,功能是对片内的64位光刻ROM进行操作。其主要目的是为了分辨一条总线上挂接的多个器件并作处理。诚然,单总线上可以同时挂接多个器件,并通过每个器件上所独有的ID号来区别,一般只挂接单个18B20芯片时可以跳过ROM指令(注意:此处指的跳过ROM指令并非不发送ROM指令,而是用特有的一条“跳过指令”)。ROM指令在下文有详细的介绍。 4,控制器发送存储器操作指令:在ROM指令发送给18B20之后,紧接着(不间断)就是发送存储器操作指令了。操作指令同样为8位,共6条,存储器操作指令分别是写RAM数据、读RAM数据、将R AM数据复制到EEPROM、温度转换、将EEPROM中的报警值复制到RAM、工作方式切换。存储器操作指令的功能是命令18B20作什么样的工作,是芯片控制的关键。 5,执行或数据读写:一个存储器操作指令结束后则将进行指令执行或数据的读写,这个操作要视存储器操作指令而定。如执行温度转换指令则控制器(单片机)必须等待18B20执行其指令,一般转换时间为500uS。如执行数据读写指令则需要严格遵循18B20的读写时序来操作。数据的读写方法将有下文有详细介绍。 若要读出当前的温度数据我们需要执行两次工作周期,第一个周期为复位、跳过ROM指令、执行温度转换存储器操作指令、等待500uS温度转换时间。紧接着执行第二个周期为复位、跳过ROM指令、执行读 DS18B20单线数字温度传感器 DALLAS半导体公司的数字化温度传感器DS1820是世界上第一片支持“一线总线”接口的温度传感器,体积更小、适用电压更宽、更经济。一线总线独特而且经济的特点,使用户可轻松地组建温度传感器网络,为测量系统的构建引入全新概念。DS18B20、DS1822 “一线总线”数字化温度传感器同DS1820一样,支持“一线总线”接口,测量温度范围为-55°C~+125°C,在-10~+85°C范围内,精度为±0.5°C,而DS1822的精度较差为± 2°C 。现场温度直接以“一线总线”的数字方式传输,大大提高了系统的抗干扰性,适合于恶劣环境的现场温度测量,如:环境控制、设备或过程控制、测温类消费电子产品等。 DS18B20可以程序设定9~12位的分辨率,精度为±0.5°C,分辨率设定,以及用户设定的报警温度存储在EEPROM中,掉电后依然保存。DS1822与DS18B20软件兼容,是DS18B20的简化版本。省略了存储用户定义报警温度、分辨率参数的EEPROM,精度降低为±2°C,适用于对性能要求不高,成本控制严格的应用,是经济型产品。继“一线总线”的早期产品后,DS1820开辟了温度传感器技术的新概念。DS18B20和DS1822使电压、特性及封装有更多的选择,让我们可以构建适合自己的经济的测温系统。 1、 DS18B20性能特点 DS18B20的性能特点:①采用单总线专用技术,既可通过串行口线,也可通过其它I/O口线与微机接口,无须经过其它变换电路,直接输出被测温度值(9位二进制数,含符号位),②测温范围为-55℃-+125℃,测量分辨率为0.0625℃,③内含64位经过激光修正的只读存储器ROM,④适配各种单片机或系统机,⑤用户可分别设定各路温度的上、下限,⑥内含 寄生电源。 2、 DS18B20内部结构 DS18B20内部结构主要由四部分组成:64位光刻 ROM,温度传感器,非挥发的温度报警触发器TH和 TL,高速暂存器。DS18B20的管脚排列如图1所示。64 位光刻ROM是出厂前被光刻好的,它可以看作是该 DS18B20的地址序列号,不同的器件地址序列号不同。 8位产品系列号48位产品序号8位CRC编码DS18B20高速暂存器共9个存储单元,如表所示: 序号寄存器名称作用序号寄存器名称作用 0 温度低字节 以16位补码形式存放4、5 保留字节1、2 1 温度高字节 6 计数器余值 2 TH/用户字节1 存放温度上限7 计数器/℃ 3 HL/用户字节2 存放温度下限8 CRC CRC校验 图1 DS18B20引脚分布图 第一部分:DS18B20的封装和管脚定义 首先,我们来认识一下DS18B20这款芯片的外观和针脚定义,DS18B20芯片的常见封装为TO-92,也就是普通直插三极管的样子,当然也可以找到以SO(DS18B20Z)和μSOP(DS18B20U)形式封装的产品,下面为DS18B20各种封装的图示及引脚图。 了解了这些该芯片的封装形式,下面就要说到各个管脚的定义了,如下表即 为该芯片的管脚定义: 上面的表中提到了一个“奇怪”的词——“寄生电源”,那我有必要说明一下了,DS18B20芯片可以工作在“寄生电源模式”下,该模式允许DS18B20工作在无外部电源状态,当总线为高电平时,寄生电源由单总线通过VDD 引脚,此时DS18B20可以从总线“窃取”能量,并将“偷来”的能量储存到寄生电源储能电容(Cpp)中,当总线为低电平时释放能量供给器件工作使用。所以,当DS18B20工作在寄生电源模式时,VDD引脚必须接地。 第二部分:DS18B20的多种电路连接方式 如下面的两张图片所示,分别为外部供电模式下单只和多只DS18B20测温系统的典型电路连接图。 (1)外部供电模式下的单只DS18B20芯片的连接图 (2)外部供电模式下的多只DS18B20芯片的连接图 这里需要说明的是,DS18B20芯片通过达拉斯公司的单总线协议依靠一个单线端口通讯,当全部器件经由一个三态端口或者漏极开路端口与总线连接时,控制线需要连接一个弱上拉电阻。在多只DS18B20连接时,每个DS18B20都拥有一个全球唯一的64位序列号,在这个总线系统中,微处理器依靠每个器件独有的64位片序列号辨认总线上的器件和记录总线上的器件地址,从而允许多只DS18B20同时连接在一条单线总线上,因此,可以很轻松地利用一个微处理器去控制很多分布在不同区域的DS18B20,这一特性在环境控制、探测建 //////////////////////////////ds18b20模块//////////////////////////////////////////////////// DS18B20是美国DALLAS半导体公司生产的可组网的一线式数字温度传感器,由于DS18B20是在一根I/O线上读写数据,因此,对读写的数据位有着严格的时序要求。 DS18B20有严格的通信协议来保证各位数据传输的正确性和完整性。该协议定义了几种信号的时序:初始化时序、读时序、写时序。所有时序都是将主机作为主设备,单总线器件作为从设备。而每一次命令和数据的传输都是从主机主动启动写时序开始,如果要求单总线器件回送数据,在进行写命令后,主机需启动读时序完成数据接收。数据和命令的传输都是低位在先。以下是常见的DS18B20的测温程序,其正确性笔者已经通过仿真实验和实际电路验证过。 在程序设计时,只要将ds18b20.c和主程序放在同一个工程中,且在主程序中包含头文件ds18b20.h即可。 DS18B20头文件:ds18b20.h #ifndef __DS18B20_H__ #define __DS18B20_H__ void delay_18B20(unsigned int i); Init_DS18B20(void) ; ReadOneChar(void); WriteOneChar(unsigned char dat); ReadTemperature(void); #endif 测温C程序:ds18b20.c #include DS18B20时序详解 初始化时序: DS18B20的所有通信都是以由复位脉冲组成的初始化序列开始的。该初始化序列由主机发出,后跟由DS18B20发出的存在脉冲(presence pulse)。下图阐述了这一点。 DS18B20发出存在脉冲,以通知主机它在总线上并且准备好操作了。 在初始化时序中,总线上的主机通过拉低单总线至少480μs来发送复位脉冲。然后总线主机释放总线并进入接收模式。总线释放后,4.7kΩ的上拉电阻把单总线上的电平拉回高电平。当DS18B20检测到上升沿后等待15到60us,然后以拉低总线60-240us的方式发出存在脉冲。如上所述,主机将总线拉低最短480us,之后释放总线。由4.7kΩ上拉电阻将总线恢复到高电平。DS18B20检测到上升沿后等待15到60us,发出存在脉冲:拉低总线60-240us。至此,初始化和存在时序完毕。 /*延时函数:(由于DS18B20延时均以15us为单位,故编写了延时单位为15us的延时函数,注意:以下延时函数晶振为12MHz)*/ /* ************************************ 函数:Delayxus_DS18B20 功能:DS18B20延时函数 参数:t为定时时间长度 返回:无 说明:延时公式:15n+15(近似),晶振12Mhz ****************************************** */ void Delayxus_DS18B20(unsigned int t) { for(t;t>0;t--) { _nop_();_nop_();_nop_();_nop_(); } _nop_(); _nop_(); void init_ds18b20(void) { uchar x=0; DQ = 1; //DQ 复位 delay_18B20(8); //稍做延时 DQ = 0; //单片机将DQ 拉低 delay_18B20(40); //精确延时大于 480us DQ = 1; //拉高总线 delay_18B20(7); x=DQ; //稍做延时后如果x=0 则初始化成功 x=1 则初始化失败delay_18B20(10); } uchar read_18b20(void)//读取ds18b20 的一个字节 { uchar loop,dat = 0; for (loop=8;loop>0;loop--) { DQ = 0; // 给脉冲信号 dat>>=1;//移位,准备存放下一次数据 DQ = 1; // 给脉冲信号 if(DQ)//读取数据 dat|=0x80;//读取到的数据为1 delay_18B20(4); } return dat;//返来读取到的数据 } void write_18b20(uchar dat)//向ds18b20 器件写一个字节{ uchar loop; for (loop=8; loop>0; loop--) { DQ = 0; DQ = dat&0x01;//向器件写一位数 delay_18B20(5); DQ = 1; dat>>=1;//移位准备写下一个数据 } } void Read_temperature(void)//读取当前温度函数 { uchar temperature_l=0;//存放当前温度的低位 uchar temperature_h=0;//存放当前温度的高位 init_ds18b20(); //在对器件操作之前先初始化 write_18b20(0xCC); // 跳过读序列号的操作 欢迎光临我的学习交流博客:https://www.doczj.com/doc/1a10662990.html, 上面有很多我个人的嵌入式开发经验总结、程序源码及详细注释。 邮箱:zpz2005@https://www.doczj.com/doc/1a10662990.html, 电路实物图如下图所示: 电路原理图如下图所示: C语言程序如下所示: /******************************************************************** * 程序名; 基于DS18B20的测温系统 * 功能:实时测量温度,超过上下限报警,报警温度可手动调整。K1是用来 * 进入上下限调节模式的,当按一下K1进入上限调节模式,再按一下进入下限 * 调节模式。在正常模式下,按一下K2进入查看上限温度模式,显示1s左右自动* 退出;按一下K3进入查看下限温度模式,显示1s左右自动退出;在调节上下限* 温度模式下,K2是实现加1功能,K1是实现减1功能,K3是用来设定上下限温* 度正负的。 * 编程者:ZPZ * 编程时间:2009/10/2 *********************************************************************/ #include #include DS18B20操作时序详解
51单片机操作DS18B20汇编源程序
DS18B20中文全套资料
DS18B20 单片机数码管显示原理图和程序
DS18B20中文资料+C程序
DS18B20介绍、流程图和程序源代码
DS18B20中文资料
ds18b20模块C程序
DS18B20时序详解
DS18B20程序1
基于51单片机及DS18B20温度传感器的数字温度计程序及详细注释
51单片机与ds18b20程序