|
温度读取函数
7 [. ?0 L, y6 ]5 h1 M$ R5 F/ I# M" A 初始化 DS18B20 后,我们就可以按照前面介绍的 DS18B20 的典型温度读取过程来编写温度读取函数,代码如下: - /****************************************************************
! \, n( x9 f' i2 J. G/ H! D* Z( _$ N - * 函 数 名 : DS18B20_GetTemperture
( q& e7 Y+ s! _$ _, r7 z - * 函数功能 : 从ds18b20 得到温度值
' G" `; {6 {% t2 d - * 输 入 : 无) z4 \$ S, O' E4 F; l. e! \
- * 输 出 : 温度数据
0 S. Y! B( E! T1 ~ - *****************************************************************/
- t9 a5 ?- ~% k5 @7 l1 d6 ` - float DS18B20_GetTemperture(void). o. [* X4 j3 o
- {
7 ?3 v3 |3 c$ V7 ]4 d - u16 temp;
/ V7 p; C8 }4 `- `5 j6 D - u8 a,b;" f7 V( N& z7 p% ?+ [5 w
- float value;
5 Q! g5 [8 t7 A" I0 M w5 y3 E$ N - DS18B20_Start(); // ds1820 start convert& h1 t! ]1 h* e4 Y b. J. R* P
- DS18B20_Reset();
$ N3 i+ q* L: M" i2 b) { - DS18B20_Check();" y( E% n) o4 U4 S5 N2 y
- DS18B20_Write_Byte(0xcc);// skip rom
# ~- t" \/ c; H; A5 s* P - DS18B20_Write_Byte(0xbe);// convert% v( ~% x$ i m7 ]: }5 p! C
- a=DS18B20_Read_Byte(); // LSB' a* |$ E8 K4 r$ f. _6 a0 T: t& s
- b=DS18B20_Read_Byte(); // MSB! n4 d; v! |- ^) a' R! f& y9 G! \
- temp=b;
& B# V3 X7 U! l9 U - temp=(temp<<8)+a;
/ |' @7 y |* [4 T0 t - if((temp&0xf800)==0xf800)6 U7 @* J# t; H' X
- {
5 p/ d( M C2 S9 l: ?; S, k- ? - temp=(~temp)+1;
9 A$ y: ?, E; }" j& D+ T/ s - value=temp*(-0.0625);/ \" L0 U. u3 f0 A
- }
: S: h( W$ |7 K$ c! B4 R9 l1 Y - else
, b* Y8 k1 M' | - {
9 Z8 K: b2 }! H0 _- N" B# S - value=temp*0.0625; N- e7 G" S, B* ^7 h; \
- }
! @) `" s7 g8 A* T. k+ w2 h% q% E - return value;
* O8 j( A; _5 p% |# |* c& F+ c - }
1 x1 J6 e+ c8 t1 ]: ]4 `" v
复制代码
4 c+ ?# W) \- L9 q# @
该函数首先调用了 DS18B20_Start 函数用来开始 DS18B20 的温度转换, 其代码如下: - /****************************************************************$ u1 M4 u# m7 s# y$ ~& m6 i
- * 函 数 名 : DS18B20_Start9 D1 F) j9 e5 x6 ?9 D
- * 函数功能 : 开始温度转换
! g* [: C. ~% J - * 输 入 : 无
& U" i8 S1 _( h7 Y2 i - * 输 出 : 无
* O, O' E1 a6 ^5 Y1 H# j# o0 ] - *****************************************************************/, k5 O% i! U; l$ s
- void DS18B20_Start(void)// ds1820 start convert" N8 `2 _3 K ~. t
- {! ^( W$ w2 E+ n6 }1 K
- DS18B20_Reset();
7 D3 D9 J! e) r9 ^ - DS18B20_Check();
$ N/ D, Y; P) u2 R8 k- ~" ^ - DS18B20_Write_Byte(0xcc);// skip rom
+ c+ G, Y2 F$ X8 T; { - DS18B20_Write_Byte(0x44);// convert
# B0 @& |& J _3 f7 i - }
复制代码; o7 j* y3 h) N# F5 |, Y. l
最终将 2 个字节的温度数据读取出来,判断最高字节的高 5 位是否为 0,如果为 0 表明读取的温度值为正温度,直接乘以 0.0625 即可,否则为负温度,需取反后加 1 再乘以 0.0625。
: @1 G4 J4 U. B- R
主函数 编写好 DS18B20 初始化和温度读取函数后,接下来就可以编写主函数了,代码如下: - /****************************************************************
) \" E' G) Y# l3 t - * 函 数 名 : main
4 m# i' X+ ]' b8 p - * 函数功能 : 主函数" i' ?$ w. F) e" w# e& ~+ O( e: N
- * 输 入 : 无
. \- V1 m0 y+ V/ e - * 输 出 : 无( n. t; l @1 M/ a
- *****************************************************************/; W7 U H* o* l V0 k7 k
- int main()' b* Z5 C$ k/ C6 r, m' f7 S' U
- {4 I/ y6 E% p4 J+ Y1 w3 g& q8 I
- u8 i=0;# S& Z+ u& v0 x, V/ C9 P( i
- float temper;
1 B& u" m7 T V; q- z! B8 m' f; M - SysTick_Init(72);, c: n5 {" [* `) M h
- NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); //中断优先级
# B& S3 c6 N" L0 R - 分组 分2 组
9 @# g7 P0 ?7 S+ \ - LED_Init();
" F: K Q( C9 B6 e - USART1_Init(9600);
( ^$ C. M; @$ X6 ^1 W; C: e3 C8 }' I - while(DS18B20_Init())
* s* T2 c5 |) T4 c# A$ \9 _ - {
+ B1 ]! S1 H% R! Q' s1 i$ e4 X1 D - printf("DS18B20检测失败,请插好!\r\n");7 L( h, G8 K' v8 a9 Y
- delay_ms(500);$ L, l3 A% w4 ^) o. g7 [1 C# B
- }
( `9 K# f7 o5 Z& v$ W- f' O - printf("DS18B20检测成功!\r\n");$ e9 h: m, o! _" _" j/ C
- while(1)
$ k) i4 |9 @# n* Y G: G - { ]( K7 |) K8 T& L3 P
- i++;0 i& m+ C8 {) L/ I
- if(i%20==0)
; A1 V: F/ _5 z3 R) X2 K w - {4 {4 j; ?1 |6 P c/ k) U+ {+ ~
- led1=!led1;
- `* x( r" N6 p2 t - }
2 ` ^% K. O p) F - if(i%50==0)& O2 F2 H; f7 g# b: x
- {% m8 J- F7 \( L1 z
- temper=DS18B20_GetTemperture();, S& G/ k! G3 e& N" u4 U# ~
- if(temper<0)0 m) Q# ?+ q" f" ]/ X: r9 h
- {
1 R v* ?0 `' u/ e' {' z% V - printf("检测的温度为:-");, \# E: g6 N4 k4 T
- }/ w4 P! j S& o4 ^. ^7 e" I
- else2 s1 O+ E& S5 k% P
- {
+ J: X @0 Z# _ - printf("检测的温度为:");6 V F! r' l# A9 D4 G
- }
h: q+ L6 t. _* Q - printf("%.2f°C\r\n",temper);
* M, C2 {3 D5 R7 Q' t O5 y' ]3 c - }
. U& ]$ F! j u! n5 K - delay_ms(10);
" n7 w1 j" `+ E, L7 X, y - }
! j% G7 u& `% b4 P - }
复制代码* M% m8 v. S- E( U
主函数实现的功能很简单,首先调用之前编写好的硬件初始化函数,包括SysTick 系统时钟,中断分组,LED 初始化等。然后调用我们前面编写的DS18B20_Init 函数用来检测 DS18B20 温度传感器是否成功,若初始化成功,打印输出“DS18B20 检测成功!”提示信息,否则一直循环打印输出“DS18B20检测失败,请插好!”,初始化成功后进入 while 循环,间隔 500ms 读取一次温度,并将温度打印输出,并且D1指示灯间隔 200ms 闪烁,提示系统正常运行。
. K2 W: Z+ W/ h, h
实验现象 将工程程序编译后下载到开发板内, 如果未将 DS18B20 插入开发板上温度传感器接口,串口将一直打印输出“DS18B20 检测失败,请插好!”提示信息,如果插好DS18B20 后,将打印输出“DS18B20 检测成功!”信息,并且每间隔 500ms打印输出一次读取的温度数据,同时可以看到 D1 指示灯不断闪烁,表示程序正常运行。如果想在串口调试助手上看到输出信息, 可以打开 串口调试助手,首先勾选下标号1 DTR 框,然后再取消勾选。 这是因为此串口助手启动时会把系统复位住,通过 DTR 状态切换下即可。然后设置好波特率等参数后,串口助手上即会收到串口发送过来的信息。(串口助手上先勾选下标号 1 DTR 框,然后再取消勾选)如下图所示: 8 t1 ]7 u" b8 x5 [1 \
; x' C5 B- a: ?
|