感谢大哥们的帮助,问题已经解决![]() |
![]() |
3201444707 发表于 2020-12-9 15:11 给你改好了,原来的程序在开发板上也不一定正常吧。 ![]() |
建议你按照如下步骤调试程序: 1、忽略文段模块的通讯,调通数码显示这块。逐位显示0-9的所有数字,包括带小数点的情况 2、第一步都跳调通了,再去调试ds18b20。由于ds18b20的口位简单,重点在于时序。 第一步很重要。另外如果担心显示出问题。可以把取得的温度数据直接发送到串口去显示,看看对不对。 以下是我做过的和18B20有关的代码,用的12M晶振,STC89C52,实测过的 // 温度传感器接口 sbit DQ=P3^7; //数据传输线接单片机的相应的引脚 /* ******************************************************************************** ** 函数名称 : Init_DS18B20(void) ** 函数功能 : 初始化 ******************************************************************************** */ void Init_DS18B20(void) { unsigned char x=0; DQ=1; //DQ先置高 Delay10us(60);//最小480,最大960 DQ=0; //发送复位脉冲 Delay10us(60);//最小480,最大960 DQ=1; //拉高数据线 Delay10us(6);//15-60us // x=DQ; //用X的值来判断初始化有没有成功,18B20存在的话X=0,否则X=1 //delay(20); while(DQ==0); DQ=1;//让传感器释放总线,避免影响下一步 } /* ******************************************************************************** ** 函数名称 : ReadOneChar() ** 函数功能 : 读一个字节 ******************************************************************************** */ unsigned char ReadOneChar() //主机数据线先从高拉至低电平1us以上,再使数据线升为高电平,从而产生读信号 { unsigned char dat=0; unsigned char mask,fmask; for(mask=0x01;mask!=0;mask<<=1)//一个周期需要至少60us,但采样要在15us内完成 { DQ=0; _nop_(); DQ=1; _nop_(); _nop_(); _nop_(); _nop_(); _nop_(); _nop_(); if(DQ==0)//读0 { fmask=~mask; dat=dat&fmask; } else { dat|=mask; } Delay10us(5); DQ=1; } return dat; } /* ******************************************************************************** ** 函数名称 : WriteOneChar(unsigned char dat) ** 函数功能 : 写一个字节 //一个写周期为60-120us,主机在15--45us内对信号采样 ******************************************************************************** */ void WriteOneChar(unsigned char dat) { unsigned char i=0; //数据线从高电平拉至低电平,产生写起始信号。15us之内将所需写的位送到数据线上, for(i=8;i>0;i--) //在15~60us之间对数据线进行采样,如果是高电平就写1,低写0发生。 { DQ=0; //在开始另一个写周期前必须有1us以上的高电平恢复期。 DQ=dat&0x01; Delay10us(6);//15-60us采样 DQ=1; dat>>=1; } delay(4); } /* ******************************************************************************** ** 函数名称 : ReadTemperature(void) ** 函数功能 : 读温度值(低位放tempL;高位放tempH;) ******************************************************************************** */ void ReadTemperature(void) { Init_DS18B20(); //初始化 WriteOneChar(0xcc); //跳过读序列号的操作 WriteOneChar(0x44); //启动温度转换 delayms(125); //转换需要一点时间,延时 Init_DS18B20(); //初始化 WriteOneChar(0xcc); //跳过读序列号的操作 WriteOneChar(0xbe); //读温度寄存器(头两个值分别为温度的低位和高位) tempL=ReadOneChar(); //读出温度的低位LSB tempH=ReadOneChar(); //读出温度的高位MSB if(tempH>0x7f) //最高位为1时温度是负 { tempL=~tempL; //补码转换,取反加一 tempH=~tempH+1; fg=0; //读取温度为负时fg=0 } sdate = tempL/16+tempH*16; //整数部分 xiaoshu1 = (tempL&0x0f)*10/16; //小数第一位 xiaoshu2 = (tempL&0x0f)*100/16%10;//小数第二位 xiaoshu=xiaoshu1*10+xiaoshu2; //小数两位 } |
你从下面的链接下载 51单片机应用开发25例,其中有多点温度采集系统,有程序有仿真,下图是仿真截图 http://www.51hei.com/bbs/dpj-54940-1.html ![]() |
主要是在开发板上能够正常运行,变成仿真图就嗝屁了 |
本坛里有现成的直接下载一个就好 ![]() |