M5StackにGroveでセンサつないで気圧測定する
概要
M5Stackにオムロンの気圧センサ(2SMPB-02E)を使ったモジュールをつないで、気圧を計測した。
ついでに、センサに平均機能とIIRフィルタ機能がついていたので、それを使ってセンサの値にフィルタをかけてみた。
背景
先日、M5Stackを購入した。
PICよりも周波数が高く、ライブラリが多くて扱いやすそうというイメージで購入してみたが、初期化にしろ何にしろとにかくコーディングが楽。(一方で内部で何してるのかわからなくても動いてしまうということでもあるが・・・)
さて、M5Stackの派生でM5Stack Grayがある。
これにはBasicのM5Stackに加え、9軸IMU(加速度、ジャイロ、磁気)が搭載されており、動きモノの制御に使ったりするのに最適である。
また、Basicと同じくLCD・3つのボタン・SDカードスロットがあるのでちょっとしたUIやログの記録もできる。プロトタイプ開発にはもってこいである。
今回、M5Stack Grayに内蔵されているセンサで取得できる値(加速度・角速度・磁場)以外に、高度の取得が必要になったので、M5Stack GrayにGroveで気圧センサを接続し、値を取得した。
オムロン絶対圧センサ2SMPB-02E
今回、使用した気圧センサは、以下のページで紹介されていたオムロンの気圧センサ2SMPB-02Eである。
基本的なソースコードは上記ページを参照のこと。
スイッチサイエンスからモジュールが出ているので、それを使った。
M5Stack Grayに接続するとこんな感じ。
センサのデータシートはこちら。
また、ありがたいことにArduino環境でこのセンサを使うためのライブラリがGithubで公開されている。
M5Stackでも、このライブラリを使用した開発ができる。
ライブラリインストール
Arduino環境にこの気圧センサのライブラリをインストールする。
上記Githubからライブラリをzip形式でダウンロード、Arduinoから スケッチ→ライブラリをインクルード→.zip形式のライブラリをインストール でOK。
M5Stackで読み込む
ライブラリが読み込めたら、最低限は以下の関数を使って値を読み込める。
// ライブラリインクルード #include "Omron2SMPB02E.h" #include <M5Stack.h> // センサのインスタンス Omron2SMPB02E prs; // 初期化・リード prs.begin(); M5.begin(); prs.set_mode(MODE_NORMAL); float tmp = prs.read_temp(); // 温度[deg]も読める float pressure = prs.read_pressure(); // 気圧[Pa]も読める
なお、MODE_NORMALとは測定→スタンバイ→測定を繰り返すモード。通常の使用ではこれを使えば良い。
その他に、SleepモードやForcedモードといった省電力のためのモードが存在する。(データシート参照)
センサ値にフィルタをかける
このセンサ、デフォルトではセンサ出力値になんのフィルタもかかっておらず、結構ノイズが乗る。
例えば以下のグラフは部屋の地面と天井の間をセンサを動かしたときの気圧の生データである。
まぁ動いていることはわかるが、ノイズ多いよね、という感じ。
そこで、センサ値にフィルタをかけるわけだが、このセンサには機能として「複数回の測定平均を出力」「IIRフィルタ」が内蔵されている。今回は内蔵されたこれらの機能を使うこととする。
こうした機能がない場合はCPU側でIIRフィルタなどのプログラムを組んでやる必要があるが、このセンサはその機能自体が内蔵されているのでCPU側としては楽である。
複数回のセンサ値の測定平均を出力
データシートに測定モード別の測定回数の記述がある。測定回数が増えるほど精度は上がるが、変換時間が伸びたり平均電流が大きくなる。
例えば、Standard Modeでの測定をする場合は、温度/ 圧力(気圧)それぞれの平均回数を1,8に設定する。
prs.set_average(AVG_1, AVG_8); // 第1引数が温度の平均回数、第2引数が気圧の平均回数 // 引数は以下の定義 // arg of set_average() #define AVG_SKIP 0x0 #define AVG_1 0x1 #define AVG_2 0x2 #define AVG_4 0x3 #define AVG_8 0x4 #define AVG_16 0x5 #define AVG_32 0x6 #define AVG_64 0x7
IIRフィルタ
さらに、IIRフィルタをかけてノイズを低減する。
IIRフィルタとは、無限インパルス応答を利用した信号処理によるフィルタである。詳細はWikipedia等参照。
このセンサはIIRフィルタによるローパスフィルタが内蔵されているので、それを設定する。
IIRフィルタを設定することで、さらにノイズを低減できる。データシートには以下のような表が記載されており、例えばStandard Modeではフィルタ係数を4に設定することでRMSノイズ[Pa]が2.6→0.8に低減できる。
なお、フィルタ係数を大きくするとノイズ自体は小さくなるが、原理上出力の遅れが大きくなるので、使うシステムに応じて適切な係数を設定することが必要である。
IIRフィルタ係数を設定する関数は以下の通り。
prs.set_filter(FILTER_4); // IIRフィルタ係数を設定(4) // 引数は以下の定義 // arg of set_filter() #define FILTER_OFF 0x0 #define FILTER_2 0x1 #define FILTER_4 0x2 #define FILTER_8 0x3 #define FILTER_16 0x4 #define FILTER_32 0x5
これらのset_average()やset_filter()はset_mode()の前に呼ぶと良い。
測定結果
上記の手順で温度の平均回数8(Standard mode)、IIRフィルタ係数を4と設定し、センサを部屋の地面から天井まで動かしたときの出力値は以下の通り。ノイズが低減されていることがわかる。
部屋の天井までは2.5m程度なので、見た感じ±10cmくらいの精度で相対高度が測定できそうである。
平均回数を上げたり、フィルタ係数を大きくするとさらに精度は上がるだろう。
まとめ
オムロンの気圧センサ2SMPB-02EのモジュールをGroveでM5Stackに接続して値を取得した。
さらに、センサ内蔵の平均値出力・IIRフィルタ機能を利用してノイズを低減し、±10cm程度の精度で相対高度が取れることを確認した。