Proteus仿真单片机测量空气湿度

Proteus仿真单片机测量空气湿度,第1张

几点说明:

1.主要是分以下几个模块写的:SHT10,LCD1602,主函数,头文件。

2.每支SHTxx传感器都在25℃(77 °F)和 3.3V条件下进行过标定并且完全符合精度指标.因为考虑到实际硬件5V的电压比较好 *** 作,所以SHT10用的精度采用的为5V时的参数。其他的都采取默认值(14bit湿度, 12bit 温度)。

3.SHT10中所以部分我都编颤源余写了。有的部分在本次程序中没用到,也可以作为参考。

4.所有程序都已经加了注释,且有仿真图。

5.个人认为还可以在此基础上添加个中断。

6.程序编写keil 4 ,仿真 protues7.5

/***********************************************************************************************************************************************************/

头文件(tou.h):

#ifndef __TOU_H__

#define __TOU_H__

#include<reg52.h>

#include <intrins.h>

//#include <math.h>    //Keil library

#define uchar unsigned char

enum {TEMP,HUMI}

sbit DATA = P1^7

sbit SCK = P1^6

sbit LcdRs = P2^4

sbit LcdRw = P2^5

sbit LcdEn = P2^6

sfr DBPort = 0x80     //P0=0x80,P1=0x90,P2=0xA0,P3=0xB0.数据端口

/********     DS1602函数声明     ********/

void LCD_Initial()

void GotoXY(unsigned char x, unsigned chary)

void Print(unsigned char *str)

void LCD_Write(bit style, unsigned charinput)

/********     SHT10函数声明      ********/

void s_connectionreset(void)

char s_measure(unsigned char *p_value,unsigned char *p_checksum, unsigned char mode)

void calc_sth10(float *p_humidity ,float*p_temperature)

//float calc_dewpoint(float h,float t)

#endif

/***********************************************************************************************************************************************************/

SHT10程序(SHT10.c):

#include<tou.h>

#define noACK 0                        //继续传输数据,用于判断是否结束通讯

#define ACK   1            //结束数据传输;

//地址 命令  读/写

#define STATUS_REG_W 0x06   //000  0011    0

#define STATUS_REG_R 0x07   //000  0011    1

#define MEASURE_TEMP 0x03   //000  0001    1

#define MEASURE_HUMI 0x05   //000  0010    1

#define RESET        0x1e  //000   1111    0

//写字节程序

char s_write_byte(unsigned char value)

{

unsignedchar i,error=0

for(i=0x80i>0i>>=1)            //高位为1,循环右移

{

if(i&value) DATA=1          //和要发送的数相与,结果为发送的位

       else DATA=0

       SCK=1

       _nop_()_nop_()_nop_()        //延时3us

       SCK=0

}

DATA=1                    裂漏       //释放数据线

SCK=1          茄滚                

error=DATA                       //检查应答信号,确认通讯正常

_nop_()_nop_()_nop_()

SCK=0

DATA=1

returnerror                     //error=1 通讯错误

}

//读字节程序

char s_read_byte(unsigned char ack)

//----------------------------------------------------------------------------------

{

unsignedchar i,val=0

DATA=1                           //释放数据线

for(i=0x80i>0i>>=1)             //高位为1,循环右移

{

SCK=1

       if(DATA) val=(val|i)        //读一位数据线的值

       SCK=0

}

DATA=!ack                        //如果是校验,读取完后结束通讯;

SCK=1

_nop_()_nop_()_nop_()          //延时3us

SCK=0

_nop_()_nop_()_nop_()

DATA=1                           //释放数据线

returnval

}

//启动传输

void s_transstart(void)

// generates a transmission start

//      _____         ________

// DATA:      |_______|

//          ___     ___

// SCK : ___|   |___|  |______

{

  DATA=1SCK=0                   //准备

  _nop_()

    SCK=1

  _nop_()

  DATA=0

  _nop_()

    SCK=0

     _nop_()_nop_()_nop_()

  SCK=1

  _nop_()

    DATA=1

    _nop_()

  SCK=0

}

//连接复位

void s_connectionreset(void)

// communication reset: DATA-line=1 and atleast 9 SCK cycles followed by transstart

//      _____________________________________________________         ________

// DATA:                                                     |_______|

//         _    _    _   _    _    _   _    _    _       ___     ___

// SCK : __| |__| |__| |__| |__| |__| |__||__| |__| |______|   |___|   |______

{

unsignedchar i

DATA=1SCK=0                    //准备

for(i=0i<9i++)                  //DATA保持高,SCK时钟触发9次,发送启动传输,通迅即复位

{

SCK=1

       SCK=0

}

s_transstart()                   //启动传输

}

//软复位程序

char s_softreset(void)

// resets the sensor by a softreset

{

unsignedchar error=0

s_connectionreset()              //启动连接复位

error+=s_write_byte(RESET)       //发送复位命令

returnerror                     //error=1 通讯错误

}

/*读状态寄存器

char s_read_statusreg(unsigned char*p_value, unsigned char *p_checksum)

//----------------------------------------------------------------------------------

// reads the status register with checksum(8-bit)

{

unsignedchar error=0

s_transstart()                   //transmission start

error=s_write_byte(STATUS_REG_R)//send command to sensor

*p_value=s_read_byte(ACK)        //read status register (8-bit)

*p_checksum=s_read_byte(noACK)   //read checksum (8-bit)

returnerror                     //error=1 incase of no response form the sensor

}

这是一个温湿度检测的程序,可以参考一下:

#include <reg52.h>

#include <intrins.h>

#include <stdio.h>

#include <string.h>

#include <absacc.h>

#include <math.h>

#define uchar unsigned char

#define uint unsigned int

sbit LcdRs=P2^0 //1602液晶端口定义

sbit LcdRw=P2^1

sbit LcdEn=P2^2

sbit led1=P3^0

sbit led2=P3^4 //报警灯端口定义

sbit ACC0=ACC^0

sbit ACC7=ACC^7

sbit k_ud=P2^4//定义上下限选择

sbit k_ws=P2^5//定义温度/湿度 选择

sbit k_add=P2^6//定义按键 +

sbit k_sub=P2^7//定义按键 -

bit flag_ud,flag_ws

bit start

uchar str[7]

//向LCD写命令

#define LCD_COMMAND 0//Command

#define LCD_DATA 1 //Data

#define LCD_CLEAR_SCREEN 0x01 //清屏

#define LCD_HOMING0X02 //光标返回原点

//设置显示模式

#define LCD_SHOW 0x04 //显示开

#define LCD_HIDE 0x00 //显示关举念

#define LCD_CURSOR0x02 //显示光标

#define LCD_NO_CURSOR 0x00 //无光标

#define LCD_FLASH 0x01 //光标闪动

#define LCD_NO_FLASH 0x00 //光标不闪动

//输入设置

#define LCD_AC_UP 0x02

#define LCD_AC_DOWN 0x00 //default

#define LCD_MOVE 0x01 //画面可平移

#define LCD_NO_MOVE 0x00 //default

unsigned char TEMP_UP=20 //温度上限

unsigned char TEMP_DOWN=0 //温度下限

unsigned char HUMUP=30//湿度上限

unsigned char HUMDOWN=10//湿度下限

unsigned char dis[4]

unsigned char LCD_Wait(void)

//SHT10设置

sbit SCK =P1^2 //定义通讯时钟端口

sbit DATA=P1^3 //定义通讯数据端口

typedef union

{ uint i//定义了两个共用体

float f

}value

enum {TEMP,HUMI}//TEMP=0,HUMI=1

#define noACK 0 //用于判断是否结束通讯

#define ACK 1 //结束数据传输

//adr command r/w

#define STATUS_REG_W 0x06 //000 0011 0

#define STATUS_REG_R 0x07 //000 0011 1

#define MEASURE_TEMP 0x03 //000 0001 1

#define MEASURE_HUMI 0x05 //000 0010 1

#define RESET0xle //运雹000 1111 0

//定义函数

void s_transstart(void) //启动传输函数

void s_connectionreset(void) //连接复位函数

char s_write_byte(unsigned char value)//SHT10写函数正悄困

char s_read_byte(unsigned char ack)//SHT10读函数

char s_measure(unsigned char*p_value,unsigned char*p_checksum,unsigned char mode)//测量温湿度函数

void calc_dht90(float*p_humidity,float*p_temperature)//温湿度补偿

void LCD_Write(bit style, unsigned char input)

//液晶显示子程序

void delay(uint z) //延时函数

{

int x

for(x=zx>0x--)

{

int y

for(y=110y>0y--)

}

}

void dat_char(uchar ff,uchar a)

{

dis[0]=ff

dis[1]='_'

dis[2]=0x30+a/10

dis[3]=0x30+a%10

}

void LCD_Write(bit style,unsigned char input)

{

LcdRs=style

P0=input

delay(5)

LcdEn=1

delay(5)

LcdEn=0

}

void LCD_SetDisplay(unsigned char DisplayMode) //设置输出

{

LCD_Write(LCD_COMMAND,0x08|DisplayMode)

}

void LCD_SetInput(unsigned char InputMode) //设置输入

{

LCD_Write(LCD_COMMAND,0x04|InputMode)

}

void LCD_Initial()//初始化LCD函数

{

LcdEn=0

LCD_Write(LCD_COMMAND,0x38) //8位数据端口,2行显示,5*7点阵

LCD_Write(LCD_COMMAND,0x38)

LCD_SetDisplay(LCD_SHOW|LCD_NO_CURSOR)//开启显示,无光标

LCD_Write(LCD_COMMAND,LCD_CLEAR_SCREEN) //清屏

LCD_SetInput(LCD_AC_UP|LCD_NO_MOVE) //AC递增,画面不动

}

void GotoXY(uchar x, uchar y) //液晶字符输入的位置

{

if(y==0)

LCD_Write(LCD_COMMAND,0x80|x)

if(y==1)

LCD_Write(LCD_COMMAND,0x80|(x-0x40))

}

void Rrint(uchar *str) //将字符输出到液晶显示

{

while(*str!='\0')

{

LCD_Write(LCD_DATA,*str)

str++

}

}

void zhuanhuan(float a) //浮点数转换成字符串函数

{

memset(str,0,sizeof(str))

sprintf(str,"%f",a)

}

void welcome() //初始界面函数

{

LCD_Initial()

GotoXY(0,0)

Rrint(" Welcome! ")

GotoXY(0,1)

Rrint(" Code of sht10 ")

delay(200)

}

/*

void delay_n10us(uint n) //延时n个10us@12M晶振

{

uint i

for(i=ni>0i--)

{

_nop_()_nop_()_nop_()

_nop_()_nop_()_nop_()

}

} */

void s_transstart(void) //启动函数

{

DATA=1SCK=0

_nop_()

SCK=1

_nop_()

DATA=0

_nop_()

SCK=0

_nop_()_nop_()_nop_()

SCK=1

_nop_()

DATA=1

_nop_()

SCK=0

}

void s_connectionreset(void) //连接复位函数

{

uchar i

DATA=1SCK=0 //Initial state

for(i=0i<9i++) //9 SCK cycles

{

SCK=1

SCK=0

}

s_transstart()

}

char s_write_byte(unsigned char value)//SHT10写字节函数

{

uchar i,error=0

for (i=0x80i>0i/=2) //shift bie for masking

{

if(i&value)DATA=1 //masking value with i,write to SENSI-BUS

else DATA=0

SCK=1

_nop_()_nop_()_nop_() //pulswith approx. 3 us

SCK=0

}

DATA=1 //release DATA-line

SCK=1 //clk#9for ack

error=DATA //check ack(DATA will be pulled down by DHT90),DATA在第9个上升沿将被DHT90自动下拉为低电平。

_nop_()_nop_()_nop_()

SCK=0

DATA=1//release DATA-line

return error //error=1 in case of no acknowledge//返回:0成功 1失败

}

//SHT10读取函数

char s_read_byte(uchar ack)

{

uchar i,val=0

DATA=1 //release DATA-line

for(i=0x80i>0i/=2)//shift bit for masking

{SCK=1

if(DATA)val=(val|i)//read bit

_nop_()_nop_()_nop_()//pulswith approx.3 us

SCK=0

}

if(ack==1)DATA=0//in case of"ack==1"pull down DATA-Line

else DATA=1//如果是校验(ack=0),读取完后结束通讯

_nop_()_nop_()_nop_() //pulswith approx. 3 us

SCK=1//clk#9 for ack

_nop_()_nop_()_nop_() //pulswith approx. 3 us

SCK=0

_nop_()_nop_()_nop_() //pulswith approx. 3 us

DATA=1 //release DATA-line

return val

}

//测量温湿度函数

char s_measure(uchar *p_value,uchar *p_checksum,uchar mode)

{

unsigned error=0

uint i

s_transstart() //transstart atart

switch(mode) //send command to sensor

{

case TEMP :error+=s_write_byte(MEASURE_TEMP)break

case HUMI :error+=s_write_byte(MEASURE_HUMI)break

default :break

}

for(i=0i<65535i++)if(DATA==0)break //wait until sensor has finishede the measurement

if(DATA)error+=1 //or timeout(~2 sec.)is reached

*(p_value) =s_read_byte(ACK) //read the first byte(MSB)

*(p_value+1)=s_read_byte(ACK) //read the second byte(LSB)

*p_checksum=s_read_byte(noACK) //read checksum

return error

}

void calc_sht90(float*p_humidity,float*p_temperature) //温湿度补偿函数

{

const float C1=-4.0//for 12 Bit

const float C2=+0.0405 //for 12 Bit

const float C3=-0.0000028 //for 12 Bit

const float T1=+0.01 //for 14 Bit@5V

const float T2=+0.00008 //for 14 Bit@5V

float rh=*p_humidity //rh: Humidity[Ticks]12 Bit

float t=*p_temperature//t: Temperature[Ticks]14 Bit

float rh_lin //rh_lin: Humidity linear

float rh_true //rh_true:Temperature compensated humidity

float t_C //t_C : Temperature[C]

t_C=t*0.01-40 //calc.temperature from ticks to [C]

rh_lin=C3*rh*rh+C2*rh+C1 //calc.humidity from ticks to[%RH]

rh_true=(t_C-25)*(T1+T2*rh)+rh_lin //calc.temperature compensated humidity[%RH]

if(rh_true>100)rh_true=100 //cut if the value is outside of

if(rh_true<0.1)rh_true=0.1 //the physical possible range

*p_temperature=t_C //return temperature[C]

*p_humidity=rh_true //return humidity[%RH]

}

void keyscan()

{

if(k_ud==0)

{

delay(10)//去抖动 100ms

if(k_ud==0)

{

while(!k_ud)

flag_ud = ~flag_ud

}

}

if(k_ws==0)

{

delay(10)//去抖动 100ms

if(k_ws==0)

{

while(!k_ws)

flag_ws = ~flag_ws

}

}

if(k_add==0)

{

delay(10)//去抖动 100ms

if(k_add==0)

{

while(!k_add)

GotoXY(12,0)

if(!flag_ws)

{

if(flag_ud){TEMP_UP++dat_char('T',TEMP_UP)}

else {TEMP_DOWN++dat_char('T',TEMP_DOWN)}

Rrint(&dis)

}

else

{

if(flag_ud){HUMUP++dat_char('H',HUMUP)}

else {HUMDOWN++dat_char('H',HUMDOWN)}

Rrint(&dis)

}

}

}

if(k_sub==0)

{

delay(10)//去抖动 100ms

if(k_sub==0)

{

while(!k_sub)

GotoXY(12,1)

if(!flag_ws)

{

if(flag_ud){TEMP_UP--dat_char('T',TEMP_UP)}

else {TEMP_DOWN--dat_char('T',TEMP_DOWN)}

Rrint(&dis)

}

else

{

if(flag_ud){HUMUP--dat_char('H',HUMUP)}

else {HUMDOWN--dat_char('H',HUMDOWN)}

Rrint(&dis)}

}

}

}

//主函数

void main()

{

value humi_val,temp_val

unsigned char error,checksum

bit status_th=0,status_ch=0

unsigned char cnt=0

LCD_Initial()

LcdRw=0

led1=0

led2=0

start=0

s_connectionreset()

welcome()//显示欢迎画面

delay(20000)

while(1)

{

cnt++

if(!(cnt%10))

{

cnt=0

error=0

error+=s_measure((unsigned char*)&humi_val.i,&checksum,HUMI)

error+=s_measure((unsigned char*)&temp_val.i,&checksum,TEMP)

if(error!=0)

{

s_connectionreset() //in case of an erroe:connection reset

}else

{

humi_val.f=(float)humi_val.i //converts integer to float

temp_val.f=(float)temp_val.i //converts integer to float

calc_sht90(&humi_val.f,&temp_val.f)//计算温度与湿?

LCD_Initial()

GotoXY(0,0)

Rrint("Tep:")

GotoXY(0,1)

Rrint("Hum:")

zhuanhuan(temp_val.f) //转换温度为uchar方便液晶显示

GotoXY(4,0)

str[5]=0xDF //℃的符号

str[6]=0x43

str[7]='\0'

Rrint(str)

if(temp_val.f>TEMP_UP-1||temp_val.f<TEMP_DOWN)

led1=1

else

led1=0

zhuanhuan(humi_val.f) //转换湿度为uchar方便液晶显示

GotoXY(4,1)

str[5]='%' //%的符号

str[6]='\0' //字符串结束标志

Rrint(str)

if((humi_val.f>HUMUP-1)||(humi_val.f<HUMDOWN))

led2=1

else

led2=0

}

}

if(!flag_ws) {GotoXY(12,0)dat_char('T',TEMP_UP)Rrint(&dis)GotoXY(12,1)dat_char('T',TEMP_DOWN)Rrint(&dis)}

else {GotoXY(12,0)dat_char('H',HUMUP)Rrint(&dis)dat_char('H',HUMDOWN)GotoXY(12,1)Rrint(&dis)}

keyscan()

}

}

主要是精度不同前哗搜

SHT10

湿度测量范围:0~100%RH;

湿度测量范围:-40~+123.8℃;

湿度测量精度:±4.5%RH

温度测量精度:±0.5℃

SHT11

湿度测量范围:0~100%RH;

温度测量范围:-40~+123.8℃;

温度测量精度: ±0.4℃

湿度测量精度:±3.0%RH

可以通用

SHT11温湿度传感器的主要特性如下:●将温湿度传感器、信号放大调理、A/D转换、I2C总线接口全部集成于一芯片(CMOSensTM技术);●可给出全校准相对湿度及温度值输出;●带有工业标准的I2C总线数字输出接口;●具有露点值计算输出功能;●具有卓越的长期稳定性;●湿度值输出分辨率为14位,温度值输出分辨率为12位,并可编程为12位和8位;●小体积(7.65×5.08×23.5mm),可表面贴装;●具有可靠的CRC数据传输校验功能;●片内装载的校准系数可保证100%互换性●电源电压范围为2.4~5.5V●电流消耗,测量时为550μA,平均为28μA,休眠时为3μA。

SHT11温湿度传感器采用SMD(LCC)表面贴片封装形式,管脚排列如图1所示,其引脚说明如下:(1)GND:接地端;(2)DATA:双向串行数据线;(3)SCK:串行时钟输入;(4)VDD电源端:0.4~5.5V电源端;(5~8)NC:空管脚。

3 工作原理SHT11的湿度检测运用电容式结构,并采用具有不同保护的“微型结构”检测电极系统与聚合物覆盖层来组成传感器芯片的电容,除保持电容式湿敏器件的原有特性外,还可抵御来自外界的影响。由于它将温度传感器与湿度传感器结合在一起而构成了一个单一的个体,因而测量精度较高且可精确得出露点,同时不会产生由于温度与湿度传感器之间随温度梯度变化引起的误差。CMOSensTM技术不仅将温湿度传感器结合在一起,而且还将信号放大器、模/数转换器、校准数据存储器、标准I2C总线等电路全部集成在一个芯片内。SHT11传感器的内部结构框图如图2所示。SHT11的每一个传感器都是在极为精确的湿度室中校准的。SHT11传感器的校准系数预先存在OTP内存中。经校准的相对湿度和温度传感器与一个14位的A/D转换器相连,可将转换后的数字温湿度值送给二线I2C总线器件,从而将数字信号转换为符合I2C总线协议的串行数字信号。

由于将传感器与电路部分结合在一起,因此,该传感器具有比其它类型的湿度传感器优越得多的性能。首先是传感器信号强度的增加增强了传感器的抗干扰性能,保证了传感器的长期稳定性,而A/D转换的同时完成,则降低了传感器对干扰噪声的敏感程度。其次在传感器芯片内装载的校准数据保证了每一只湿度传感器都具有相同的功能,即具有100%的互换性。最后,传感器可直接通过I2C总线与任何类型的微处理器、微控制器系统连接,从而减少了接口电路的硬件成本,简化了接口方式。3.1 输出特性(1)湿度值输出SHT11可通芦伏过I2C总线直接输出数字量湿度值,其相对湿度数字输出特性曲线如图3所示。由图3可看出,SHT11的输出特性呈一定的非线性,为了补偿湿度传感器的非线性,可按如下公式修正湿度值:RHlinear=c1+c2SORH+c3SORH2式中,SORH为传感器相对湿度测量值,系数取值如下:12位:SORH:c1=-4,c2=0.0405,c3=-2.8×10-68位:SORH:c1=-4,c2=0.648,c3=-7.2×10-4(2)温度值输出由于SHT11温度传感器的线性非常好,故可用下列公式将温度数字输出转换成实际温度值:T=d1+d2SOT当电源电压为5V,且温度传感器的分辨率为14位时,d1=-40 d2=0.01,当温度传感器的分辨率为12位时,d1=-40 d2=0.04。(3)露点计算空气的露点值可根据相对湿度和温度值来得出,具体的计算公式如下:LogEW=(0.66077+7.5T/(237.3+T)+[log10(RH)-2]Dp=[(0.66077-logEW)×237.3]/(logEW-8.16077)3.2 命令与接口时序SHT11传感器共有5条用户命令,具体命令格式见表1所列。下面介绍一下具体的慧历命令顺序及命令时序。

表1 SHT11传感器命令列表命 令 编 码 说明

测量温度 00011 温度测量

测量湿度 00101 湿度测量

读寄存器状态 00111 “读”状态寄存器

写寄存器状态 00110 “写”状态寄存器

软启动 11110 重启芯片,清除状态记录器的错误记录11毫秒后进入下一个命令

(1)传输开始初始化传输时,应首先发出“传输开始”命令,该命令可在SCK为高时使DATA由高电平变为低电平,并在下一个SCK为高时将DATA升高。接下来的命令顺序包含三个地址位(目前只支持“000”)和5个命令位,当DATA脚的ack位处于低电位时,表示SHT11正确收到命令。(2)连接复位顺序如果与SHT11传感器的通讯中断,下列信号顺序会使串口复位:即当DATA线处于高电平时,触发SCK 9次以上(含9次),此后应接着发一个“传输开始”命令。

表2 SHT11状态寄存器类型及说明位 类型 说 明 缺 省

7 保留 0

6 读 工检限(低电压检查) X

5 保留 0

4 保留 0

3 只用于试验,不可以使用 0

2 读/写 加热 0 关

1 读/写 不从OTP重下载 0 重下载

0 读/写 ‘1‘=8位相对湿度,12位温度分辨率。‘0‘=12位相对湿度,14位湿度分辨率 0 12位相对湿度,14位湿度

(3)温湿度测量时序当发出了温(湿)度测量命令后,控制器就要等到测量完成。使用8/12/14位的分辨率测量分别需要大约11/55/210ms的时间。为表明测量完成,SHT11会使数据线为低,此时控制器必须重新启动SCK,然后传送两字节的测量数据与1字节CRC校验和。控制器必须通过使DATA为低来确认每一个字节,所有的量均从右算,MSB列于第一位。通讯在确认CRC数据位后停止。如果没有用CRC-8校验和,则控制器就会在测量数据LSB后保持ack为高来停止通讯,SHT11在测量和通讯完成后会自动返回睡眠模式。需要注意的是:为使SHT11的温升低于0.1℃ 此时的工作频率不能大于标定值的15%(如:12位精确度时,每秒最多进行3次测量)。测量温度和湿度命令所对应的时序如图4所示。

图4

3.3 寄存器配置SHT11传感器中的一些高级功能是通过状态寄存器来实现的,寄存器各位的类型及说明见表2所列。下面对寄存器相关位的功能说明:(1)加热使芯片中的加热开关接通后,传感器温度大约增加5℃,从而使功耗增加至8mA@5V。加热用途如下:●通过对启动加热器前后的温、湿度进行比较,可以正确地区别传感器的功能;●在相对湿度较高的环境下,传感器可通过加热来避免冷凝。(2)低电压检测SHT11工作时可以自行检测VDD电压是否低于2.45V,准确度为±0.1V。(3)下载校准系数为了节省能量并提高速度,OTP在每次测量前都要重新下载校准系数,从而使每一次测量节省8.2ms的时间。(4)测量分辨率设定将测量分辨率从14位(温度)和12位(湿度)分别减到12位和8位可应用于高速或低功耗场合。

4 应用说明4.1 运行条件测量量程以外的温度会使湿度信号暂时地偏移+3%。然后传感器会慢慢返回到校准条件。若将芯片在湿度小于5%环境下加热24小时到90℃,芯片就会迅速恢复高相对湿度、高温度环境的影响,但是,延长强度条件会加速芯片的老化。4.2 安装注意事项由于大气的相对湿度与温度的关系比较密切,因此,测量大气温度时的要点是将传感器与大气保持同一温度,如果传感器线路板上有发热元件,SHT11应与热源保持良好的通风,为减少SHT11和PCB之间的热传导,应使铜导线最细并在其中加上窄缝,同时应避免使传感器在强光或UV下曝晒。传感器在布线时,SCK和DATA信号平行且相互接近,或信号线长于10cm时,均会产生干扰信息,此时应在两组信号之间放置VDD或GND。

5 具体应用图5是AT89C2051单片机与SHT11的接口电路。由于AT89C2051不具备I2C总线接口,故使用单片机通用I/O口线来虚拟I2C总线,并利用P1.0来虚拟数据线DATA,利用P1.1口线来虚拟时钟线,并在DATA端接入一只4.7kΩ的上拉电阻,同时,在VDD及GND端接入一只0.1μF的去耦电容。下面给出与上述硬件电路配套的C51应用程序。#define DATA P1_1#define SCK P1_0#define ACK 1#define noACK 0#define MEASURE_TEMP 0x03 //测量温度命令#define MEASURE_HUMI 0x05 //测量湿度命令//读温湿度数据char s-measure(unsigned char *p- value, un-signed char *p_checksum, unsigned char mode){unsigned char error=0unsigned int is_transstart()//传输开始switch(mode){caseTEMP:error+=s_write_byte(measure_temp)breakcaseHUMI:error+=s_write_byte(measure_humi)breakdefault:break}for(i=0i<65535i++) if(DATA==0) breakif (DATA) reeor+=1*(p_value)=s_read_byte(ACK)*(p_value+1)=s_read_byte(ACK)*p_checksum=s_read_byte(noACK)return error}//温湿度值标度变换及温度补偿void calc_sth15(float *p_humidity,float *p_tempera-ture){const float c1=-4.0const float c2=0.0405const float c3=-0.0000028const float t1=-0.01const float t2=0.00008float rh=×p_humidityfloat t=×p_temperaturefloat rh_linfloat th_turefloat t_ct_c=t×0.01-40rh_lin=c3×rh×rh+c2×rh+c1trh_ture=(t_c-25)×(t1+t2×rh)+rh_lin×p_temperature=t-c×p_humidity=rh_ture}//从相对温度和湿度计算露点char calc_dewpoint(float h,float t){float logex,dew_pointlogex=0.66077+7.5×t/(237.3+t)+[log10(h)-2]dew_point=(logex-0.66077)×237.3/(0.66077+7.5-logex)return dew_point}限于篇幅,上述程序中未给出传输开始、写字节数据、读字节数据函数。

6 结束语SHT11数字式温湿度传感器由于将温度传感器、湿度传感器、信号调理、模/数转换器、标定参数及I2C总线接口全部集成到传感器内部,因此,既提高了传感器的性能,又降低了成本、减少了体积,同时也非常便于和微控制器接口,由此可见,该传感器是嵌入式系统温湿度测试的理想选择。


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/yw/12465264.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-05-25
下一篇 2023-05-25

发表评论

登录后才能评论

评论列表(0条)

保存