基于51单片机的数字温度计设计一.课题选择随着时代的发展,控制智能化,仪器小型化,功耗微量化得到广泛关注。单片机控制系统无疑在这方面起到了举足轻重的作用。单片机的应用系统设计业已成为新的技术热点,其中数字温度计就是一个典型的例子,它可广泛应用与生产生活的各个方面,具有巨大的市场前景。二.设计目的1.理解掌握51单片机的功能和实际应用。2.掌握仿真开发软件的使用。3.掌握数字式温度计电路的设计、组装与调试方法。三.实验要求1.以51系列单片机为核心器件,组成一个数字式温度计。2.采用数字式温度传感器为检测器件,进行单点温度检测。3.温度显示采用4位LED数码管显示,三位整数,一位小数。四.设计思路1.根据设计要求,选择STC89C51RC单片机为核心器件。2.温度检测采用DS18B20数字式温度传感器。与单片机的接口为P3.6引脚。3.采用usb数据线连接充电宝供电,接电后由按钮开关控制电路供电。硬件电路设计总体框图为图1:五.系统的硬件构成及功能1.主控制器单片机STC89C51RC具有低电压供电和体积小等特点,有40个引脚,其仿真图像如下图所示:2.显示电路显示电路采用4位共阳LED数码管,从P3口RXD,TXD串口输出段码。LED数码管在仿真软件中如下图所示:3.温度传感器DS18B20是美国DALLAS半导体公司最新推出的一种改进型智能温度传感器,与传统的热敏电阻等测温元件相比,它能直接读出被测温度,并且可根据实际要求通过简单的编程实现9~12位的数字值读数方式。DS18B20的性能特点如下:1.独特的单线接口仅需一个端口引脚进行通讯。2.简单的多点分布应用。3.无需外部器件。4.可通过数据线供电。5.零待机功耗。6.测温范围-55~+125摄氏度。其电路图如下图所示:在仿真软件中如下图所示:DS18B20的测温原理图如下图所示:在正常测温情况下,DS18B20的测温分辨力为0.5摄氏度,可采用下述方法获得高分辨率的温度测量结果。:首先用DS18B20提供的读暂存器指令(BEH)读出以0.5摄氏度为分辨率的温度测量结果,然后切去测量结果中的最低有效位(LSB),得到所测实际温度的整数部分Tz,然后再利用BEH指令取计数器1的计数剩余值Cs和每度计数值CD。考虑到DS18B20测量温度的整数部分以0.25、0.75摄氏度为进位界限的关系,实际温度Ts可以用下式计算:Ts=(Tz-0.25)+(CD-Cs)/CD六.系统整体硬件电路根据设计要求与设计思路,硬件电路设计框图如下图所示,在仿真软件Proteus上完成,其中LED数码管以动态扫描法实现温度显示,由四个PNP型晶体管Q2,Q3,Q4,Q5和8个电阻组成。基极与单片机的P1.0,P1.1,P1.2连接,DS18B20的数据I/O端与单片机P3.6引脚连接。外部晶振为12MHZ。七.系统程序设计数字式温度计的应用程序主要包括主程序,温度检测程序,温度转换程序,LED显示程序等。其思路如下图所示:八.测量及其结果分析1.Proteus仿真结果软件方面,在Proteus编译下进行,源程序编译及仿真调试。在软件中选定传感器后可对其进行环境温度设置,如下图,将环境温度设为34.9.2.硬件测试结果在硬件测试方面,检查电路板及焊接的质量情况,在焊接无误后通电检查LED显示器。其中成品图如图所示:通电后,室温下LED的示数如图所示九.设计心得体会本次实验对我们组来说是一次难得的经历,首先是第一次接触了仿真软件Proteus,在使用时经历了很多次失败,因为这款软件与以前使用过的软件有很大不同,使用时不停出错,接线时由于原件放置不合理而接的杂乱无章,输入源程序时还算顺利,显示结果比较满意。其次是程序设计,我们在参考别人成功先例的基础上根据自己设计的需要进行编程,其中经历了不少曲折,最后我的收获是编程一定要细心,针对每一个细节,稍有疏忽程序就不能正常运行。在这次的实践与学习中,尽管期间困难重重,但我们还是从中学习了不少新的知识和技能,也体会到了经历失败最终成功的喜悦。总之,通过这次电工电子综合设计,我收获了很多,我希望自己在今后的各项研究工作中也坚持这种精神。十.附录源程序#includereg52.h#includeintrins.h#defineucharunsignedchar#defineuintunsignedintsbitDATA=P1^1;//DS18B20接入口ucharcodetable[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};//共阴极字型码inttemp;//温度值intss;//中间的一个变量intdd;intj;uchardatab;//定时器中断次数uchardatabuf[4];//字型显示中间变量intalarmH=320;//默认报警值intalarmL=100;//定义开关的接入口sbitk1=P2^5;//+sbitk2=P2^6;//-sbitk3=P2^7;//确认sbitk4=P2^4;//切换sbitbell=P1^0;//蜂鸣器sbitHLight=P1^2;//正温指示灯sbitLLight=P1^3;//负温度指示灯sbitwarn=P1^4;//报警指示灯sbitRed=P1^6;//温度上限设置指示灯sbitGreen=P1^7;//温度下限设置指示灯bitset=0;//初始化bitFlag=0;//设置标志intn;//函数的声明区voidkey_to1();voidkey_to2();voiddelay(uint);voidkey();voidShow();//函数的定义区/*延时子函数*/voiddelay(uintnum){while(num--);}//DS18b20温度传感器所需函数,分为初始化,读写字节,读取温度4个函数Init_DS18B20(void)//传感器初始化{ucharx=0;DATA=1;//DQ复位delay(10);//稍做延时DATA=0;//单片机将DQ拉低delay(80);//精确延时大于480us//450DATA=1;//拉高总线delay(20);x=DATA;//稍做延时后如果x=0则初始化成功x=1则初始化失败delay(30);}ReadOneChar(void)//读一个字节{uchari=0;uchardat=0;for(i=8;i0;i--){DATA=0;//给脉冲信号dat=1;DATA=1;//给脉冲信号if(DATA)dat|=0x80;delay(8);}return(dat);}WriteOneChar(unsignedchardat)//写一个字节{uchari=0;for(i=8;i0;i--){DATA=0;DATA=dat&0x01;delay(10);DATA=1;dat=1;}delay(8);}intReadTemperature(void)//读取温度{uchara=0;ucharb=0;intt=0;floattt=0;Init_DS18B20();WriteOneChar(0xCC);//跳过读序号列号的操作WriteOneChar(0x44);//启动温度转换Init_DS18B20();WriteOneChar(0xCC);//跳过读序号列号的操作WriteOneChar(0xBE);//读取温度寄存器等(共可读9个寄存器)前两个就是温度a=ReadOneChar();//低位b=ReadOneChar();//高位t=b;t=8;t=t|a;tt=t*0.0625;t=tt*10+0.5;return(t);}voiddisplay00()//*********显示负值子函数{dd=-(temp-1);buf[1]=dd/100;buf[2]=dd/100;buf[3]=dd%100/10;buf[0]=dd%10;//动态显示for(j=0;j5;j++){P2=0xff;//初始灯为灭的P0=0x00;P2=0xfd;//显示小数点P0=0x80;//显示小数点delay(100);P2=0xff;//初始灯为灭的P0=0x00;P2=0xf7;//片选LCD1P0=0x40;delay(100);P2=0xff;P0=0x00;P2=0xfb;//片选LCD2P0=table[buf[2]];delay(100);P2=0xff;P0=0x00;P2=0Xfd;//片选LCD3P0=table[buf[3]];delay(100);P2=0xff;P0=0x00;P2=0Xfe;P0=table[buf[0]];//片选LCD4delay(100);P2=0xff;}}//显示正值子函数voiddisplay(){buf[1]=temp/1000;//显示百位buf[2]=temp/100%10;//显示十位buf[3]=temp%100/10;//显示个位buf[0]=temp%10;//小数位for(j=0;j3;j++){P2=0xff;//初始灯为灭的P0=0x00;P2=0xfd;//显示小数点P0=0x80;//显示小数点delay(300);P2=0xff;//初始灯为灭的P0=0x00;P2=0xf7;//片选LCD1P0=table[buf[1]];delay(300);P2=0xff;P0=0x00;P2=0xfb;//片选LCD2P0=table[buf[2]];delay(300);P2=0xff;P0=0x00;P2=0Xfd;//片选LCD3P0=table[buf[3]];delay(300);P2=0xff;P0=0x00;P2=0Xfe;P0=table[buf[0]];//片选LCD4delay(300);P2=0xff;}}voidkey()//按键扫描子程序{if(k1!=1){delay(20);if(k1!=1){while(k1!=1){key_to1();for(n=0;n8;n++)Show();}}}if(k2!=1){delay(20);if(k2!=1){while(k2!=1){key_to2();for(n=0;n8;n++)Show();}}}if(k3!=1){TR0=1;//复位,开定时temp=ReadTemperature();}if(k4!=1){delay(20);if(k4!=1){while(k4!=1);set=!set;if(set==0){Red=0;Green=1;}else{Green=0;Red=1;}}}}voidkey_to1(){TR0=0;//关定时器temp+=10;if(temp=1100){temp=-550;}if(set==0){alarmH=temp;}else{alarmL=temp;}}voidkey_to2(){TR0=0;//关定时器temp-=10;if(temp=-550){temp=1100;}if(set==0){alarmH=temp;}else{alarmL=temp;}}voidalarm(void){if(tempalarmH||tempalarmL){//bell=1;//delay(50);//bell=0;Flag=1;}else{Flag=0;}}logo()//开机的Logo{P0=0x40;P2=0xf7;delay(50);P2=0xfb;delay(50);P2=0Xfd;delay(50);P2=0Xfe;delay(50);P1=0xff;//关闭显示}voidShow()//显示函数,分别表示温度正负值{if(temp=0){HLight=1;LLight=0;display();}if(temp0){HLight=0;LLight=1;display00();}}voidmain(){T