应用于本项目开发SHT1X该系列有温湿度传感器SHT10、SHT11和SHT15,属于Sersirion温湿度传感器家族的贴片包装系列。包括电容聚合物湿度测量敏感元件和由能量间隙材料制成的温度测量元件。传感器内部有一个精度高达14的位置A/D转换器。详情请参考说明书。
本次使用现在SHT简要介绍15作。引脚定义如下:
|
|
|
|
1 |
GND |
地 |
|
2 |
DATA |
串行数据, 双向 |
|
3 |
SCK |
串行时钟, 输入口 |
|
4 |
VDD |
电源 |
|
NC |
NC |
必须为空 |
SHT1X温湿度传感器使用的2线通讯,类是于I2C总线,但不一样,用普通的GPIO通信可以实现。这次使用。STM32F103VET6来操作SHT具体连接方式如下:
SCK 用于微处理器和SHT1x 通信同步。由于界面包含完全静态逻辑,因此没有最小值SCK 频率。
DATA 引脚是读取传感器数据的三态结构 . 当向传感器发送命令时, DATA 在 SCK 上升边有效且在 SCK 平时高电必须保持稳定。 DATA 在 SCK 下降边后变化。微处理器应驱动以避免信号冲突DATA 在低电平。需要外部上拉电阻(例如: 10kΩ)将信号提升到高电平。微处理器通常包含上拉电阻I/O 电路中。
2、通讯实现
现在说明一下传感器通讯的实现。首先,看看它的操作命令。传感器的命令包括三个地址(目前只支持000,只能挂在空闲中IIC总线原因)和五个命令位。SHT1x 以下方式表示正确接收指令:在第八个SCK 时钟下降后,DATA 下拉为低电平(ACK 位)。在第9个SCK 时钟下降后,释放DATA(恢复高电平)。命令集如下:
|
|
预留 |
0000x |
温度测量 |
|
湿度测量 |
|
阅读状态寄存器 |
00111/p> |
写状态寄存器 |
00110 |
预留 |
0101x-1110x |
软复位 |
|
接下来具体说说各种该命令操作的实现:
2.1、启动时序
用一组“启动传输”时序来完成数据传输的初始化。它包括:当SCK时钟高电平时DATA翻转为低电平,紧接着SCK变成低电平,随后是在SCK时钟高电平,随后是在SCK时钟高电平DATA翻转位高电平。时序如下:
具体的编码实现如下:
/*SHT1X启动时序操作*/
void StartSHT1XOperation(BusPinOperation *SetBusPin)
{
/*将data线设置为输出模式*/
SetDataPineDirection(Out);
SetBusPin[DataPin](Set);
SetBusPin[SckPin](Reset);
Delayus(10);
SetBusPin[SckPin](Set);
Delayus(5);
SetBusPin[DataPin](Reset);
Delayus(5);
SetBusPin[SckPin](Reset);
Delayus(10);
SetBusPin[SckPin](Set);
Delayus(5);
SetBusPin[DataPin](Set);
Delayus(10);
SetBusPin[SckPin](Reset);
}
2.2、通讯复位
如果与SHT1x 通讯中断,可通过下列信号时序复位:当DATA 保持高电平时,触发SCK 时钟9 次或更多。时序图如下:
具体的编码实现如下:
/*SHT1X通讯复位*/
void ResetSHT1XCommunication(BusPinOperation *SetBusPin)
{
/*将data线设置为输出模式*/
SetDataPineDirection(Out);
Delayms(1);
SetBusPin[DataPin](Set);
SetBusPin[SckPin](Reset);
for(int i=0;i<9;i++)
{
SetBusPin[SckPin](Set);
Delayus(10);
SetBusPin[SckPin](Reset);
Delayus(10);
}
StartSHT1XOperation(SetBusPin);
}
同时也可以实现软件复位,状态寄存器复位为默认状态。在要发送下一个命令前,至少等待 11ms。具体实现如下:
/*对SHT1X实现软件复位*/
uint8_t Sht1xSoftwareReset(BusPinOperation *SetBusPin)
{
uint8_t err = 0;
ResetSHT1XCommunication(SetBusPin);
err=err+WriteByteT0Sht1x(SOFTWARE_RESET,SetBusPin);
return err;
}
2.3、操作状态寄存器
SHT1x 的某些高级功能可以通过给状态寄存器发送指令来实现,如选择测量分辨率,电量不足提醒,使用 OTP 加载或启动加热功能等。
/*读状态寄存器*/
uint8_t ReadStatusRegister(uint8_t *pValue,uint8_t *pCheckSum,BusPinOperation *SetBusPin)
{
uint8_t err=0;
StartSHT1XOperation(SetBusPin);
err=WriteByteT0Sht1x(READ_STATUS_REGISTER,SetBusPin);
*pValue=ReadByteFromSht1x( Ack,SetBusPin);
*pCheckSum=ReadByteFromSht1x( noAck,SetBusPin);
return err;
}
/*写状态寄存器*/
uint8_t WriteStatusRegister(uint8_t *pValue,BusPinOperation *SetBusPin)
{
uint8_t err=0;
StartSHT1XOperation(SetBusPin);
err +=WriteByteT0Sht1x(WRITE_STATUS_REGISTER,SetBusPin);
err +=WriteByteT0Sht1x(*pValue,SetBusPin);
return err;
}
2.4、温湿度的读取和计算
发布一组测量命令(‘00000101’表示相对湿度RH,‘00000011’表示温度T)后,控制器要等待测量结束。这个过程需要大约20/80/320ms,分别对应8/12/14bit 测量。根据本人测试8位时,15ms可以;12位时,70ms可以;14位时240ms可以。 SHT1x 通过下拉DATA 至低电平并进入空闲模式,表示测量的结束。控制器在再次触发SCK 时钟前,必须等待这个“数据备妥”信号来读出数据。检测数据可以先被存储,这样控制器可以继续执行其它任务在需要时再读出数据。
/*获取SHT1X的温度值*/
float GetSht1xTemperatureValue(float vdd,BusPinOperation *SetBusPin)
{
float tempValue=0.0;
uint16_t sot=0;
uint8_t err=0;
uint8_t highByte=0;
uint8_t lowByte=0;
uint8_t checkSum=0;
StartSHT1XOperation(SetBusPin);
WriteByteT0Sht1x(TEMP_MEAS_COMMAND,SetBusPin);
SetDataPineDirection(In);
Delayms(240);
if(ReadDataPinBit() == 1)
{
err += 1;
}
highByte=ReadByteFromSht1x(Ack,SetBusPin);
lowByte=ReadByteFromSht1x(Ack,SetBusPin);
checkSum=ReadByteFromSht1x(noAck,SetBusPin);
sot=(uint16_t)highByte;
sot=(sot*256)+(uint16_t)lowByte;
if(err != 0)
{
ResetSHT1XCommunication(SetBusPin);
}
else
{
tempValue=ConvertTemperatureData(sot,vdd);
}
return tempValue;
}
/*获取SHT1X的湿度值*/
float GetSht1xHumidityValue(float temp,BusPinOperation *SetBusPin)
{
float humiValue=0.0;
uint16_t sorh=0;
uint8_t err=0;
uint8_t highByte=0;
uint8_t lowByte=0;
uint8_t checkSum=0;
StartSHT1XOperation(SetBusPin);
WriteByteT0Sht1x(HUMI_MEAS_COMMAND,SetBusPin);
SetDataPineDirection(In);
Delayms(70);
if(ReadDataPinBit() == 1)
{
err += 1;
}
highByte=ReadByteFromSht1x(Ack,SetBusPin);
lowByte=ReadByteFromSht1x(Ack,SetBusPin);
checkSum=ReadByteFromSht1x(noAck,SetBusPin);
sorh=(highByte<<8)|lowByte;
if(err != 0)
{
ResetSHT1XCommunication(SetBusPin);
}
else
{
humiValue=ConvertHumidityData(sorh,temp);
}
return humiValue;
}
对于其他的计算部分直接按公式便写即可。