[電子工作]Arduinoで二酸化炭素濃度測定器を作ってみた(Vol.2)
先週に引き続き電子工作について書きます。
前回は、Grove Beginner Kit For ArduinoでCO2濃度測定機を作成しました。シリアルモニタに測定値を出力し、CO2が一致値を超えるとブザーとLEDをONにするところまでやりました。
いちおう最低限の機能は実装できましたが、これだとPCにつないでシリアルモニタを見ないと測定値が分かりません。そこで今回は、Grove Beginner KitについているOLEDディスプレイに結果を表示するのにチャレンジしてみました。
前回のおさらい
まずは、CO2測定のコードのおさらいです。前回載せたコードはほぼサンプルのままだったので、余計な処理やコメントを外したりして整理してみました。こうするとだいぶすっきりしますね。
#include <CCS811.h>
CCS811 sensor; // CCS811クラスインスタンス化
const int ledPin = 4; //LED端子設定
const int co2_limit = 1000; // CO2アラーム設定値
void setup(void)
{
Serial.begin(115200); // シリアルモニタ設定
sensor.begin(); // CO2センサ起動
sensor.setMeasCycle(sensor.eCycle_250ms); // CO2センササイクル設定
pinMode(ledPin, OUTPUT); // LEDピン設定
}
void loop() {
int co2, tvoc; // 結果格納用変数宣言
delay(1000); // 測定サイクル設定(1000ミリ秒→1秒)
co2 = sensor.getCO2PPM(); // CO2測定
tvoc = sensor.getTVOCPPB(); // TVOC測定
outputSerialMonitor(co2, tvoc); // シリアルモニタ出力
if(co2 > co2_limit){ //CO2濃度が設定値を上回ったらアラームを鳴らす
tone(5, 440); // Buzzer ON
digitalWrite(ledPin, HIGH); // LED ON
} else {
noTone(5); // Buzzer OFF
digitalWrite(ledPin, LOW); // LED OFF
}
}
// シリアルモニタ出力関数
void outputSerialMonitor(int co2, int tvoc) {
Serial.print("CO2: ");
Serial.print(co2);
Serial.print("ppm, TVOC: ");
Serial.print(tvoc);
Serial.println("ppb");
}
OLEDディスプレイにCO2濃度を出力する
では、いよいよOLEDに出力していきます。
OLEDの表示は、Grove Beginner Kit付属のチュートリアルと、ノンプロ研電子工作部のHirocom777先生のブログを参考にしました。
追加した記述は以下です。
まず、コードの最初のグローバル領域です。(void setup()関数の前)
#include <U8x8lib.h> // OLED用ライブラリインクルード
U8X8_SSD1306_128X64_ALT0_HW_I2C u8x8(/* reset=*/ U8X8_PIN_NONE); // OLEDクラスインスタンス化
次に、void setup()内での初期設定。
u8x8.begin();
u8x8.setFlipMode(1);
u8x8.setFont(u8x8_font_chroma48medium8_r);
最後に、void loop()内で実際に表示させます。
u8x8.setCursor(0, 1); // OLED表示位置設定
u8x8.print("CO2: "); // OLED表示
u8x8.print(co2); // OLED表示
u8x8.print("ppm"); // OLED表示
組み込んだ後の全体のコードはこんな感じです。
#include <CCS811.h> // CO2センサ用ライブラリインクルード
#include <U8x8lib.h> // OLED用ライブラリインクルード
CCS811 sensor; // CCS811クラスインスタンス化
U8X8_SSD1306_128X64_ALT0_HW_I2C u8x8(/* reset=*/ U8X8_PIN_NONE); // OLEDクラスインスタンス化
const int ledPin = 4; // LED端子設定
const int co2_limit = 1000; // CO2アラーム設定値
void setup(void)
{
Serial.begin(115200); // シリアルモニタ設定
sensor.begin(); // CO2センサ起動
sensor.setMeasCycle(sensor.eCycle_250ms); // CO2センササイクル設定
pinMode(ledPin, OUTPUT); // LEDピン設定
// OLED初期設定
u8x8.begin();
u8x8.setFlipMode(1);
u8x8.setFont(u8x8_font_chroma48medium8_r);
}
void loop() {
int co2, tvoc; // 結果格納用変数宣言
delay(1000); // 測定サイクル設定(1000ミリ秒→1秒)
co2 = sensor.getCO2PPM(); // CO2測定
tvoc = sensor.getTVOCPPB(); // TVOC測定
outputSerialMonitor(co2, tvoc); // シリアルモニタ出力関数呼び出し
u8x8.setCursor(0, 1); // OLED表示位置設定
u8x8.print("CO2: "); // OLED表示
u8x8.print(co2); // OLED表示
u8x8.print("ppm"); // OLED表示
if(co2 > co2_limit){ //CO2濃度が設定値を上回ったらアラームを鳴らす
tone(5, 440); // Buzzer ON
digitalWrite(ledPin, HIGH); // LED ON
} else {
noTone(5); // Buzzer OFF
digitalWrite(ledPin, LOW); // LED OFF
}
}
// シリアルモニタ出力関数
void outputSerialMonitor(int co2, int tvoc) {
Serial.print("CO2: ");
Serial.print(co2);
Serial.print("ppm, TVOC: ");
Serial.print(tvoc);
Serial.println("ppb");
}
これで以下のようにCO2濃度がOLEDディスプレイに表示されました!
アラーム設定も残していますので、設定値を超えるとブザーとLEDのアラームも鳴ります。
温度・湿度・気圧も表示させてみる
これで出来上がり!と言いたいところですが、なんかちょっと表示が寂しいですね。
Grove Beginner Kitには、温度・湿度センサーと、気圧センサーがありますので、ついでに表示してみます。温度・湿度センサーと、気圧センサーの使い方もHiroCom777先生のブログに載っています。
センサーの使い方はモジュールの名前やメソッド名が違うくらいで、それほど難しくはないです。それぞれ変数に格納すれば同じようにOLEDに表示できます。
OLEDは4行まで表示できるので、温度、湿度、気圧、CO2濃度の順番に表示してみました。出来上がったコードはこんな感じ。
#include "DHT.h" // 温湿度センサ用ライブラリインクルード
#include "Seeed_BMP280.h" // 気圧センサ用ライブラリインクルード
#include <CCS811.h> // CO2センサ用ライブラリインクルード
#include <U8x8lib.h> // OLED用ライブラリインクルード
CCS811 sensor; // CCS811クラスインスタンス化
U8X8_SSD1306_128X64_ALT0_HW_I2C u8x8(/* reset=*/ U8X8_PIN_NONE); // OLEDクラスインスタンス化
DHT dht(3, DHT11); // 温湿度センサクラスインスタンス化
BMP280 bmp280; // 気圧センサクラスインスタンス化
const int ledPin = 4; // LED端子設定
const int co2_limit = 1000; // CO2アラーム設定値
void setup(void)
{
Serial.begin(115200); // シリアルモニタ設定
sensor.begin(); // CO2センサ起動
sensor.setMeasCycle(sensor.eCycle_250ms); // CO2センササイクル設定
pinMode(ledPin, OUTPUT); // LEDピン設定
bmp280.init(); // 気圧センサ初期化
// OLED初期設定
u8x8.begin();
u8x8.setFlipMode(1);
u8x8.setFont(u8x8_font_chroma48medium8_r);
}
void loop() {
int co2, tvoc, temp, humid, pressure; // 結果格納用変数宣言
delay(1000); // 測定サイクル設定(1000ミリ秒→1秒)
temp = dht.readTemperature(); // 温度測定
humid = dht.readHumidity(); // 湿度測定
pressure = bmp280.getPressure() / 100; // 気圧測定
co2 = sensor.getCO2PPM(); // CO2測定
tvoc = sensor.getTVOCPPB(); // TVOC測定
outputSerialMonitor(temp, humid, pressure, co2, tvoc); // シリアルモニタ出力関数呼び出し
// OLED表示
u8x8.setCursor(0, 0); // 1行目
u8x8.print("Temp : ");
u8x8.print(temp);
u8x8.print("C");
u8x8.setCursor(0, 1); // 2行目
u8x8.print("Humid: ");
u8x8.print(humid);
u8x8.print("%");
u8x8.setCursor(0, 2); // 3行目
u8x8.print("Press: ");
u8x8.print(pressure);
u8x8.print("hPa");
u8x8.setCursor(0, 3); // 4行目
u8x8.print("CO2 : ");
u8x8.print(co2);
u8x8.print("ppm");
if(co2 > co2_limit){ //CO2濃度が設定値を上回ったらアラームを鳴らす
tone(5, 440); // Buzzer ON
digitalWrite(ledPin, HIGH); // LED ON
} else {
noTone(5); // Buzzer OFF
digitalWrite(ledPin, LOW); // LED OFF
}
}
// シリアルモニタ出力関数
void outputSerialMonitor(int temp, int humid, int pressure, int co2, int tvoc) {
Serial.print("Temperature: ");
Serial.print(temp);
Serial.print("C, Humidity: ");
Serial.print(humid);
Serial.print("% Press: ");
Serial.print(pressure);
Serial.print("hPa CO2: ");
Serial.print(co2);
Serial.print("ppm, TVOC: ");
Serial.print(tvoc);
Serial.println("ppb");
}
OLED表示とは関係ないですが、いちおうシリアルモニタへの出力も増やしています。
ではコンパイルしてArduinoに書き込んでみましょう。
上から温度、湿度、気圧、CO2濃度の順に表示されています。完璧です!
まとめ
今回は、CO2濃度測定結果に加えて温度・湿度・気圧もOLEDディスプレイに表示するところまでやってみました。Grove Beginner Kitはいろんなセンサーが最初からついているので便利です。(精度は知らん)
ちなみに、Arduinoは一回プログラムを書き込んでしまえばUSBから電源供給するだけで動き続けます。一旦USBケーブル引っこ抜いてからモバイルバッテリーに接続すれば自動的に起動するので、どこにでも持っていけます。
下の写真の右の緑の箱がモバイルバッテリーです。数年前の古いものなのでやたらデカいですが、気にしないで下さい。。
Grove Beginner Kitは各モジュールを切り離してケーブルでつなげるので、持ち運び前提であれば、必要なものだけ箱とかに入れてもよいかもしれません。
はんだ付けや難しい配線もありませんので電子工作感はあまりないですが、プログラミングで機能を追加したりできるので楽しいですね。ブザーの鳴らし方や画面表示とかも色々カスタマイズできると思います。
それほどお金かけずに楽しめるので、興味のある方はやってみて下さい。思い通り動くと楽しいですよ~
最後に改めて、使ったパーツを載せておきます。
ジャンパーワイヤーは上記以外でも「オスーメス」のタイプであれば何でもOKです。私は前にラズパイ工作用にセットで買ったものがあったのを流用しています。通販だと無駄に本数が多いのが微妙ですね。ホームセンターとか行けば少しだけとか買えるかもしれません。
また気になるパーツを見つけたら、何か作ってみたいと思います。