在《LCD1602屏幕显示——库的使用》一文中,采用自定义的库函数来实现显示屏输出的控制
lcd.print("Hello World!");
该方法不需要知道硬件的具体实现过程,使得硬件的管理和控制更加简单。下面通过一个温湿度传感器DHT11(其精度湿度+-5%RH,温度+-2℃,量程湿度20-90%RH,温度0~50℃),来具体说明一下类库的使用,以及类库的自定义方法。
实物图
接线图
DHT11库文件链接地址:
https://pan.baidu.com/s/1I27vHvkU_FgiMnZOAyWGsA 密码:r8qj。
如果读者按照地址无法下载,可以按照如下的源代码自行编写, DHT库常常包含如下三个文件(也可以带keywords.txt文件,为了方便期间在此省略)
将DHT文件夹解压缩后发到Arduino安装文件夹的libraries文件夹下:
C:\Program Files (x86)\Arduino\libraries。
既可以使用examples中的案例程序来使用该库。示例文件源代码如下:
示例文件源代码
double Fahrenheit(double celsius)
{
return 1.8 * celsius + 32;
} //摄氏温度度转化为华氏温度
double Kelvin(double celsius)
{
return celsius + 273.15;
} //摄氏温度转化为开氏温度
#include
dht11 DHT11;
#define DHT11PIN 2
void setup()
{
Serial.begin(9600);
Serial.println("DHT11 TEST PROGRAM ");
Serial.print("LIBRARY VERSION: ");
Serial.println(DHT11LIB_VERSION);
Serial.println();
}
void loop()
{
Serial.println("\n");
int chk = DHT11.read(DHT11PIN);
Serial.print("Read sensor: ");
switch (chk)
{
case DHTLIB_OK:
Serial.println("OK");
break;
case DHTLIB_ERROR_CHECKSUM:
Serial.println("Checksum error");
break;
case DHTLIB_ERROR_TIMEOUT:
Serial.println("Time out error");
break;
default:
Serial.println("Unknown error");
break;
}
Serial.print("Humidity (%): ");
Serial.println((float)DHT11.humidity, 2);
Serial.print("Temperature (oC): ");
Serial.println((float)DHT11.temperature, 2);
Serial.print("Temperature (oF): ");
Serial.println(Fahrenheit(DHT11.temperature), 2);
Serial.print("Temperature (K): ");
Serial.println(Kelvin(DHT11.temperature), 2);
delay(2000);
}
该示例文件非常简单,其中包含两个子函数,其一是将读取到的温度值(摄氏度)转换为华氏度,其二是将读取到的温度值转换为开氏温度。输出结果如下(输出结果包含Dew Point及Dew PointFast,为了简便起见将这两个子函数在此略去):
输出结果
通过上述的示例函数可以看出,库DTH11通过方法
DHT11.read(DHT11PIN)
该方法能够获得传感器测量的温湿度数值,即
DHT11.temperature
DHT11.humidity。
深究该方法的实现原理,需要阅读以dth11.h和dth11.cpp这两个文件的源代码,其中dth11.h的源代码如下:
以"#"开头的语句称为预处理命令,包含文件使用的#include及在常量定义时使用的#define均为预处理命令。预处理命令并不是C/C++语言的组成部分,编译器不会直接对其进行编译,而是在编译之前预先处理这些命令。
在示例源代码中使用了#include
在dth11.h这个文件中申明了一个方法 read()和两个变量 humidity,temperature。该方法的具体实现方式在dht11.cpp文件中给出,在此不再详细解释,读者可以想象查阅DHT11传感器的工作原理在去理解源代码。
dht11.cpp源代码
#include "dht11.h"
int dht11::read(int pin)
{
// BUFFER TO RECEIVE
uint8_t bits[5];
uint8_t cnt = 7;
uint8_t idx = 0;
// EMPTY BUFFER
for (int i=0; i< 5; i++) bits[i] = 0;
// REQUEST SAMPLE
pinMode(pin, OUTPUT);
digitalWrite(pin, LOW);
delay(18);
digitalWrite(pin, HIGH);
delayMicroseconds(40);
pinMode(pin, INPUT);
// ACKNOWLEDGE or TIMEOUT
unsigned int loopCnt = 10000;
while(digitalRead(pin) == LOW)
if (loopCnt-- == 0) return DHTLIB_ERROR_TIMEOUT;
loopCnt = 10000;
while(digitalRead(pin) == HIGH)
if (loopCnt-- == 0) return DHTLIB_ERROR_TIMEOUT;
// READ OUTPUT - 40 BITS => 5 BYTES or TIMEOUT
for (int i=0; i<40; i++)
{
loopCnt = 10000;
while(digitalRead(pin) == LOW)
if (loopCnt-- == 0) return DHTLIB_ERROR_TIMEOUT;
unsigned long t = micros();
loopCnt = 10000;
while(digitalRead(pin) == HIGH)
if (loopCnt-- == 0) return DHTLIB_ERROR_TIMEOUT;
if ((micros() - t) > 40) bits[idx] |= (1 << cnt);
if (cnt == 0) // next byte?
{
cnt = 7; // restart at MSB
idx++; // next byte!
}
else cnt--;
}
// WRITE TO RIGHT VARS
// as bits[1] and bits[3] are allways zero they are omitted in formulas.
humidity = bits[0];
temperature = bits[2];
uint8_t sum = bits[0] + bits[2];
if (bits[4] != sum) return DHTLIB_ERROR_CHECKSUM;
return DHTLIB_OK;
}
//
// END OF FILE
//
完
2018/6/26