DS18B20温度传感器在STM8S208MB中的应用
实验工具:
STM8S208MB开发一个,工作频率16MHz,12864LCD显示屏一个,DS18B20温度传感器芯片3只。 开发环境:
IAR Embedded Workbench 实验要求:
1、要求将读取的温度数据保留任意小数位数,并且可以处理负温度值。2、当拔掉传感器时,对应的位置提示“传感器检测失败!”,插上后恢复正常,拔掉所有的传感器时屏幕显示“无任何器件!”,插上恢复正常。3、用清屏的方式解决屏幕字符残留问题。4、软件编写温度报警阈值驱动蜂鸣器。5、用匹配ROM的方式三点测温。
12864显示屏只能处理字符,并不能直接处理数字,通常我们是将数字转换为字符逐一送到12864中显示,并且还要处理显示顺序、小数点、负数的问题程序非常繁琐。这里我们是通过将标准输入输出库中(stdio.h)的printf重定向到12864去显示,将读取的温度值直接调用printf函数打印到12864屏幕上,借助printf强大的功能我们基本不需要考虑任何问题,并且可以很方便控制显示格式,例如处理温度值小数位数与负数问题。
printf函数重定向,实际上是重新定义了pubchar函数输出。
int putchar( int ch) //printf重定向到12864显示 {
LCDwrite((unsigned char)ch,1); //12864显示屏字符显示函数 return ch; } 原理图:
按照上面的原理接线,用什么牌子的开发板都是一样,有些开发板带有12864LCD显示屏接口,可以根据开发板的实际情况修改12864.c驱动程序IO定义也可以。
常见封闭外观:
接线图:
初始化时序图:
初始化程序流程:
1、切换引脚为输出
2、输出高电平(可以省略)
3、延时480-900微秒,稳定高电平状态(可以省略) 4、切换输出为低电平
5、延时480-900微秒,稳定低电平 6、输出高电平
7、切换引脚到输入状态 8、延时约30微秒 9、获取引脚电平状态 10、延时500微秒结束。
unsigned char DS18B20init() //DS18B20初始化函数 {
unsigned char x;
DS18B20IO(1); //引脚切换到输出状态
//DS18B20out=1; //引脚为高电平输出,此句可以省略 //delay1(1700); //延时大约600us,此句可以省略 DS18B20out=0; //引脚切换到低电平输出 delay1(1700); //延时大约600us
DS18B20out=1; //引脚切换到高电平输出
DS18B20IO(0); //引脚状态切换为输入状态侦听数据 delay1(65); //延时约30us
x=PI_IDR_IDR4; //保存引脚的电平状态 Delay1(1150); //约500us
while(!PI_IDR_IDR4); //等待低电平结束 return x; //返回数据,0或1 }
正常情况,引脚置低电平后延时600微秒,然后置高,引脚置高电平后立即切换到输入状态检测传感器的反映,约30微秒后,此时温度传感器会拉低引脚电平,变量“x”得到引脚的低电平“0”返回给函数,调用此函数时只需判断函数返回值0或1便可知道温度传感
器是否连接正常。
写时序图
写数据流程:
1、引脚切换到输出状态 2、引脚置低电平
3、延时>1微秒<15微秒 4、将数据0或1送到引脚上 5、延时60微秒
6、引脚置高电平结束
void DS18B20Write(unsigned char data) //写命令函数,先从低位开始写 {
unsigned char mask; DS18B20IO(1);
for(mask=0x01;mask!=0;mask<<=1) {
DS18B20out=0; delay1(10); if((mask&data)) DS18B20out=1; else
DS18B20out=0; delay1(100); DS18B20out=1; } }
写入数据是从低位开始逐位送出,此程序每送出一个位mask左移一位并和形参相与,如果为1,引脚电平置高;如果为0,引脚电平置低,这样很简单地将送入给形参的8位数据,在引脚上逐位地表现出来,并且每个位维持约60微秒让温度传感器来读。
读时序图:
读流程:
1、切换引脚为输出状态 2、引脚置低 3、延时>1us 4、引脚置高
5、切换引脚为输入状态 6、延时>1us<15us 7、获取引脚电平状态 8、延时60us左右结束
unsigned int DS18B20Read() {
unsigned int mask,data; unsigned char x=0;
for(mask=1;mask!=0;mask<<=1) {
DS18B20IO(1); DS18B20out=0; delay1(10); DS18B20out=1; DS18B20IO(0); delay1(10); x=PI_IDR_IDR4; if(x)
data|=mask; else
data&=~mask; delay1(150); }
return data; }
//读数据函数,先从低位开始读。