春夏之交,气温多变,值此季节,制作了一个数字温度计,感知冷暖,尊重自然。
制作出来的实物图如下:
一、设计思路:
1. 采用AT89S52+DS18B20+三位共阳数码管构架。本案例最终生成的HEX文件只有3.2K,单片机用AT89S52有些浪费了,但芯片是以前学习时留下来的,而且P0口有断脚,发挥余热吧。有强迫症的朋友可以选用STC15W204S+74HC595。
2. 数码管上下倒置,目的是为了能显示温度单位,数码管代码需另外取码(推荐),或是在焊接时重新分布脚位也可。
二、电路构成:
1. 单片机最小系统:AT89S52、40P双列插座、晶振(12MHz)、30pF贴片电容(2个)、10K电阻、10uF电解电容。
2. 温度采集电路:DS18B20(数字温度传感器)、4.7K贴片电阻。
3. 数码管显示电路:F4301BH(三位共阳)、100欧电阻8个(段限流电阻,实际焊接为91欧)、SS8550三极管3个+10K电阻3个(位驱动)。
4. 供电电路:DC5V电源座、100uF滤波电容。
三、编程与仿真:
此过程略……
四、电路焊接:
电路较简单,万能板就可以。一些小元件焊接在40P座里面或是在底层。底层的导线有些杂乱,最后用上了硅胶枪,感觉还行。
仿真原理图如下(proteus仿真工程文件可到本帖附件中下载)
附程序(不全):
#include <reg52.h>
#define uchar unsigned char
#define uint unsigned int
sbit w1=P2^5;
sbit w2=P2^6;
sbit w3=P2^7;
sbit DQ=P3^4;
bit TempFlag;
uint Temp;
uchar code tab[]={0xc0,0xcf,0xa4,0x86,0x8b,0x92,0x90,0xc7,0x80,0x82}; //代码表,已重新取码
void Delayms(uint xms);
void Delayus(uint xus);
void GetTemp(void);
void InitT0(void);
void Init_DS18B20(void);
uchar Read_DS18B20(void);
void Write_DS18B20(uchar Dat);
void display()
{
P1=0x33;
w3=0;
Delayms(2);
w3=1;
P1=tab[Temp%10];
w2=0;
Delayms(2);
w2=1;
P1=tab[Temp/10];
w1=0;
Delayms(2);
w1=1;
}
void main() //主函数
{
InitT0();
while(1)
{
GetTemp(); //读取温度
display();
}
}
void Init_DS18B20(void) //初始化DS18B20函数
{
DQ=1;
Delayus(4);
DQ=0;
Delayus(100);
DQ=1;
Delayus(40);
}
uchar Read_DS18B20(void) //读DS18B20函数
{
uchar i=0,Dat=0;
for(i=0;i<8;i++)
{
DQ=1;
DQ=0;
Dat>>=1;
DQ=1;
if(DQ)
Dat|=0x80;
DQ=1;
Delayus(25);
}
return(Dat);
}
void Write_DS18B20(uchar Dat) //写DS18B20函数
{
uchar i=0;
for(i=0;i<8;i++)
{
DQ=1;
Dat>>=1;
DQ=0;
DQ=CY;
Delayus(25);
DQ=1;
}
}
void GetTemp(void) //取温度函数
{
uchar a=0,b=0;
Init_DS18B20();
Write_DS18B20(0xcc);
Write_DS18B20(0x44);
Init_DS18B20();
Write_DS18B20(0xcc);
Write_DS18B20(0xbe);
a=Read_DS18B20();
b=Read_DS18B20();
Temp=b;
Temp<<=8;
Temp=Temp|a;
if(b>=8)
{
Temp=~Temp+1;
TempFlag=1;
}
else
TempFlag=0;
Temp=Temp*0.0625;
}
全部程序51hei下载地址:
18B20.rar
(868 Bytes, 下载次数: 138)
|