凡是官网购买产品,均可以获得积分,(积分可以用来下载技术资料)还可以获得精致技术支持。yabovip2018.com实验室可提供全套电子方案定制服务,了解详情请咨询客服。???????????
查看: 1573|回复: 8
打印 上一主题 下一主题

yabovip2018.com开源模块篇1-温湿度模块 SHT2X SHT20 SHT21 SHT25

[复制链接]

339

主题

2008

帖子

887

活跃值

管理员

Rank: 9Rank: 9Rank: 9

活跃值
887
跳转到指定楼层
楼主
发表于 2018-5-10 19:09:51 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
1、说明
MCU:yabovip2018.com开源开发板
温湿度模块:SHT2X
开发工具:yabovip2018.com实验室开发工具
功能:测量环境的温度和湿度信息

2、硬件连接

3、核心代码(会员可见)
[C++] 纯文本查看 复制代码
/**
*        使用SHT2X 模块测试温湿度信息
*/

#include "SparkFunHTU21D.h"

#define LED1        PA8

//Create an instance of the object
HTU21D myHumidity;

void setup()
{
  Serial.begin(9600);
  Serial.println("HTU21D Example!");

        pinMode(LED1, OUTPUT);

  myHumidity.begin();
}

void loop()
{
        digitalWrite(LED1, HIGH);
        delay(500);
        digitalWrite(LED1, LOW);
        
  float humd = myHumidity.readHumidity();
  float temp = myHumidity.readTemperature();

  Serial.print("时间:");
  Serial.print(millis());
  Serial.print(" 温度:");
  Serial.print(temp, 1);
  Serial.print(" °C");
  Serial.print(" 湿度:"); 
  Serial.print(humd, 1);
  Serial.print("%");

  Serial.println();
  delay(1000);
}

/* 
HTU21D Humidity Sensor Library
By: Nathan Seidle
SparkFun Electronics
Date: September 22nd, 2013
License: This code is public domain but you buy me a beer if you use this and we meet someday (Beerware license).

Get humidity and temperature from the HTU21D sensor.

This same library should work for the other similar sensors including the Si

*/


#if defined(ARDUINO) && ARDUINO >= 100
#include "Arduino.h"
#else
#include "WProgram.h"
#endif

#include 

#define HTU21D_ADDRESS 0x40  //Unshifted 7-bit I2C address for the sensor

#define ERROR_I2C_TIMEOUT         998
#define ERROR_BAD_CRC                999

#define TRIGGER_TEMP_MEASURE_HOLD  0xE3
#define TRIGGER_HUMD_MEASURE_HOLD  0xE5
#define TRIGGER_TEMP_MEASURE_NOHOLD  0xF3
#define TRIGGER_HUMD_MEASURE_NOHOLD  0xF5
#define WRITE_USER_REG  0xE6
#define READ_USER_REG  0xE7
#define SOFT_RESET  0xFE

#define USER_REGISTER_RESOLUTION_MASK 0x81
#define USER_REGISTER_RESOLUTION_RH12_TEMP14 0x00
#define USER_REGISTER_RESOLUTION_RH8_TEMP12 0x01
#define USER_REGISTER_RESOLUTION_RH10_TEMP13 0x80
#define USER_REGISTER_RESOLUTION_RH11_TEMP11 0x81

#define USER_REGISTER_END_OF_BATTERY 0x40
#define USER_REGISTER_HEATER_ENABLED 0x04
#define USER_REGISTER_DISABLE_OTP_RELOAD 0x02

class HTU21D {

public:
  HTU21D();

  //Public Functions
  void begin(SoftWire &wirePort = Wire); //If user doesn't specificy then Wire will be used
  float readHumidity(void);
  float readTemperature(void);
  void setResolution(byte resBits);

  byte readUserRegister(void);
  void writeUserRegister(byte val);

  //Public Variables

private:
  //Private Functions
  SoftWire *_i2cPort; //The generic connection to user's chosen I2C hardware

  byte checkCRC(uint16_t message_from_sensor, uint8_t check_value_from_sensor);
  uint16_t readValue(byte cmd);

  //Private Variables

};

/*
  HTU21D Humidity Sensor Library
  By: Nathan Seidle
  SparkFun Electronics
  Date: September 22nd, 2013
  License: This code is public domain but you buy me a beer if you use this and we meet someday (Beerware license).

  This library allows an Arduino to read from the HTU21D low-cost high-precision humidity sensor.

  If you have feature suggestions or need support please use the github support page: [url=https://github.com/sparkfun/HTU21D]https://github.com/sparkfun/HTU21D[/url]

  Hardware Setup: The HTU21D lives on the I2C bus. Attach the SDA pin to A4, SCL to A5. If you are using the SparkFun
  breakout board you *do not* need 4.7k pull-up resistors on the bus (they are built-in).

  Link to the breakout board product:

  Software:
  Call HTU21D.Begin() in setup.
  HTU21D.ReadHumidity() will return a float containing the humidity. Ex: 54.7
  HTU21D.ReadTemperature() will return a float containing the temperature in Celsius. Ex: 24.1
  HTU21D.SetResolution(byte: 0b.76543210) sets the resolution of the readings.
  HTU21D.check_crc(message, check_value) verifies the 8-bit CRC generated by the sensor
  HTU21D.read_user_register() returns the user register. Used to set resolution.
*/

#include "SparkFunHTU21D.h"

HTU21D::HTU21D()
{
  //Set initial values for private vars
}

//Begin
/*******************************************************************************************/
//Start I2C communication
void HTU21D::begin(SoftWire &wirePort)
{
  _i2cPort = &wirePort; //Grab which port the user wants us to use
  
  _i2cPort->begin();
}

#define MAX_WAIT 100
#define DELAY_INTERVAL 10
#define MAX_COUNTER (MAX_WAIT/DELAY_INTERVAL)

//Given a command, reads a given 2-byte value with CRC from the HTU21D
uint16_t HTU21D::readValue(byte cmd)
{
  //Request a humidity reading
  _i2cPort->beginTransmission(HTU21D_ADDRESS);
  _i2cPort->write(cmd); //Measure value (prefer no hold!)
  _i2cPort->endTransmission();
  
  //Hang out while measurement is taken. datasheet says 50ms, practice may call for more
  byte toRead;
  byte counter;
  for (counter = 0, toRead = 0 ; counter < MAX_COUNTER && toRead != 3 ; counter++)
  {
    delay(DELAY_INTERVAL);

    //Comes back in three bytes, data(MSB) / data(LSB) / Checksum
    toRead = _i2cPort->requestFrom(HTU21D_ADDRESS, 3);
  }

  if (counter == MAX_COUNTER) return (ERROR_I2C_TIMEOUT); //Error out

  byte msb, lsb, checksum;
  msb = _i2cPort->read();
  lsb = _i2cPort->read();
  checksum = _i2cPort->read();

  uint16_t rawValue = ((uint16_t) msb << 8) | (uint16_t) lsb;

  if (checkCRC(rawValue, checksum) != 0) return (ERROR_BAD_CRC); //Error out

  return rawValue & 0xFFFC; // Zero out the status bits
}

//Read the humidity
/*******************************************************************************************/
//Calc humidity and return it to the user
//Returns 998 if I2C timed out
//Returns 999 if CRC is wrong
float HTU21D::readHumidity(void)
{
  uint16_t rawHumidity = readValue(TRIGGER_HUMD_MEASURE_NOHOLD);
  
  if(rawHumidity == ERROR_I2C_TIMEOUT || rawHumidity == ERROR_BAD_CRC) return(rawHumidity);

  //Given the raw humidity data, calculate the actual relative humidity
  float tempRH = rawHumidity * (125.0 / 65536.0); //2^16 = 65536
  float rh = tempRH - 6.0; //From page 14

  return (rh);
}

//Read the temperature
/*******************************************************************************************/
//Calc temperature and return it to the user
//Returns 998 if I2C timed out
//Returns 999 if CRC is wrong
float HTU21D::readTemperature(void)
{
  uint16_t rawTemperature = readValue(TRIGGER_TEMP_MEASURE_NOHOLD);

  if(rawTemperature == ERROR_I2C_TIMEOUT || rawTemperature == ERROR_BAD_CRC) return(rawTemperature);

  //Given the raw temperature data, calculate the actual temperature
  float tempTemperature = rawTemperature * (175.72 / 65536.0); //2^16 = 65536
  float realTemperature = tempTemperature - 46.85; //From page 14

  return (realTemperature);
}

//Set sensor resolution
/*******************************************************************************************/
//Sets the sensor resolution to one of four levels
//Page 12:
// 0/0 = 12bit RH, 14bit Temp
// 0/1 = 8bit RH, 12bit Temp
// 1/0 = 10bit RH, 13bit Temp
// 1/1 = 11bit RH, 11bit Temp
//Power on default is 0/0

void HTU21D::setResolution(byte resolution)
{
  byte userRegister = readUserRegister(); //Go get the current register state
  userRegister &= B01111110; //Turn off the resolution bits
  resolution &= B10000001; //Turn off all other bits but resolution bits
  userRegister |= resolution; //Mask in the requested resolution bits

  //Request a write to user register
  writeUserRegister(userRegister);
}

//Read the user register
byte HTU21D::readUserRegister(void)
{
  byte userRegister;

  //Request the user register
  _i2cPort->beginTransmission(HTU21D_ADDRESS);
  _i2cPort->write(READ_USER_REG); //Read the user register
  _i2cPort->endTransmission();

  //Read result
  _i2cPort->requestFrom(HTU21D_ADDRESS, 1);

  userRegister = _i2cPort->read();

  return (userRegister);
}

void HTU21D::writeUserRegister(byte val)
{
  _i2cPort->beginTransmission(HTU21D_ADDRESS);
  _i2cPort->write(WRITE_USER_REG); //Write to the user register
  _i2cPort->write(val); //Write the new resolution bits
  _i2cPort->endTransmission();
}

//Give this function the 2 byte message (measurement) and the check_value byte from the HTU21D
//If it returns 0, then the transmission was good
//If it returns something other than 0, then the communication was corrupted
//From: [url=http://www.nongnu.org/avr-libc/user-manual/group__util__crc.html]http://www.nongnu.org/avr-libc/user-manual/group__util__crc.html[/url]
//POLYNOMIAL = 0x0131 = x^8 + x^5 + x^4 + 1 : [url=http://en.wikipedia.org/wiki/Computation_of_cyclic_redundancy_checks]http://en.wikipedia.org/wiki/Com ... c_redundancy_checks[/url]
#define SHIFTED_DIVISOR 0x988000 //This is the 0x0131 polynomial shifted to farthest left of three bytes

byte HTU21D::checkCRC(uint16_t message_from_sensor, uint8_t check_value_from_sensor)
{
  //Test cases from datasheet:
  //message = 0xDC, checkvalue is 0x79
  //message = 0x683A, checkvalue is 0x7C
  //message = 0x4E85, checkvalue is 0x6B

  uint32_t remainder = (uint32_t)message_from_sensor << 8; //Pad with 8 bits because we have to add in the check value
  remainder |= check_value_from_sensor; //Add on the check value

  uint32_t divsor = (uint32_t)SHIFTED_DIVISOR;

  for (int i = 0 ; i < 16 ; i++) //Operate on only 16 positions of max 24. The remaining 8 are our remainder and should be zero when we're done.
  {
    //Serial.print("remainder: ");
    //Serial.println(remainder, BIN);
    //Serial.print("divsor:    ");
    //Serial.println(divsor, BIN);
    //Serial.println();

    if ( remainder & (uint32_t)1 << (23 - i) ) //Check if there is a one in the left position
      remainder ^= divsor;

    divsor >>= 1; //Rotate the divsor max 16 times so that we have 8 bits left of a remainder
  }

  return (byte)remainder;
}

注:使用的库文件参照Arduino平台改写[/hide]
4、测试结果

5、完整工程
将该文件解压后放到IDE安装目录的stm32duino文件夹下面,在开发工具中就可以从示例中看到该工程示例。

sht2x-lingzhilab.rar

4.15 KB, 下载次数: 17, 下载积分: 积分 -5

yabovip2018.com开源-让电子制作变得更简单! --- yabovip2018.com实验室

1

主题

7

帖子

33

活跃值

新手上路

Rank: 1

活跃值
33
沙发
发表于 2018-6-22 22:42:36 | 只看该作者
我是来学习的

0

主题

7

帖子

18

活跃值

新手上路

Rank: 1

活跃值
18
板凳
发表于 2019-1-1 16:40:56 | 只看该作者
学习学习

2

主题

13

帖子

98

活跃值

注册会员

Rank: 2

活跃值
98
地板
发表于 2019-2-27 18:06:17 | 只看该作者
学习一下

1

主题

5

帖子

25

活跃值

新手上路

Rank: 1

活跃值
25
5#
发表于 2019-3-3 16:21:11 | 只看该作者
你好,可以用于Arduino nano 型号吗

339

主题

2008

帖子

887

活跃值

管理员

Rank: 9Rank: 9Rank: 9

活跃值
887
6#
?楼主| 发表于 2019-3-3 17:02:48 | 只看该作者
wcl128 发表于 2019-3-3 16:21
你好,可以用于Arduino nano 型号吗

可以的,用的I2C接口,库也可以使用的
yabovip2018.com开源-让电子制作变得更简单! --- yabovip2018.com实验室

0

主题

5

帖子

72

活跃值

注册会员

Rank: 2

活跃值
72
7#
发表于 2019-4-3 19:18:01 | 只看该作者
非常好的例程!

0

主题

5

帖子

22

活跃值

新手上路

Rank: 1

活跃值
22
8#
发表于 2019-4-15 18:19:20 | 只看该作者
学习? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?

0

主题

1

帖子

0

活跃值

新手上路

Rank: 1

活跃值
0
9#
发表于 2019-6-21 17:04:21 | 只看该作者

学习??
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver| 手机版| 小黑屋| yabovip2018.com实验室 ( 粤ICP备17040594号-3 )

GMT+8, 2019-9-23 12:11 , Processed in 0.096116 second(s), 22 queries .

快速回复 返回顶部 返回列表