ESP32 でシャープの埃センサーを制御して,PM2.5 の濃度を測定する方法を紹介します.
はじめに
ESP32 でのセンシング事例としては I2C 通信や A/D 変換器を使ったものが多い気がしますが,ここでは PWM と A/D 変換器を組み合わせて,PM2.5 のノイズを計測する方法を紹介します.
作るものは左のような感じ.
ペリフェラルてんこ盛りの ESP32 の活用の場を広げる一例として参考にしてもらえば幸いです.
回路,ソフト,ケースの順で説明していきます.
必要な部品
必要な部品はこんな感じ.代表的なもののみ記載しています.
AliExpress で入手するもの
- DN7C3CA006
-
シャープの PM2.5 センサーです.より新しいバージョンである DN7C3CA007 でも OK です.送料含めると $28 程度です.
秋月電子 で入手するもの
- BS170
-
PM2.5 センサーの LED 制御用の Nch MOSFET です.
- B6B-XH-A
-
PM2.5 センサー接続用のコネクタです.
- 220uF 電解コンデンサー
-
PM2.5 センサーの LED 用電源に接続するコンデンサです.データシートでこの容量が指定されています.150Ω の抵抗も必要になります.
回路
PM2.5 センサーのデータシート [キャッシュ] は正直わかりやすいとは言えないので,その内部で使われている GP2Y1010AU のアプリケーションノート [キャッシュ] を参照するのがオススメです.掲載されている下記の回路図の通りに回路を組めば OK です.
ここに載っていないものとして,PM2.5 センサ特有のファンがありますが,こちらは電源制御用の MOSFET を介して 5V に接続すれば OK です.
センシング方法
センサーの制御内容としては,データシートに記載されている下図の通りに LED を制御し,Vo の電圧を A/D 変換する形になります.
注意点が一つだけあります.
データシートに記載されている 10ms 周期ののパルス波形は LED 端子に電流が流れるときに H になる形で書かれています.そのため,Nch MOSFET を使う場合は,H のタイミングでゲートを H にしてやる形になります.(図は LED 端子の電圧波形ではありません)
ソフト
ソフト全体は,github に上げてありますので,ここではポイントとなる部分のみ抜粋していきます.
まず,パルス出力から.dust_sense_start
を呼ぶと 100s 周期で 0.32ms のパルスを出力し,パルス出力から 0.28ms 後に割り込みが発生するようにします.cmpr_b は周期に対する割合(%)で設定するので注意.dust_sense_stop
ではパルス出力を停止し,端子を L に設定します.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
static void dust_sense_start() { mcpwm_config_t pwm_config; pwm_config.frequency = 100; // period is 10ms pwm_config.cmpr_a = 0; pwm_config.cmpr_b = 2.8; // sampling timing is 0.28ms (= 10ms * 2.8%) later pwm_config.counter_mode = MCPWM_UP_COUNTER; pwm_config.duty_mode = MCPWM_DUTY_MODE_0; ESP_ERROR_CHECK(mcpwm_init(MCPWM_UNIT_0, MCPWM_TIMER_0, &pwm_config)); ESP_ERROR_CHECK(mcpwm_set_duty_in_us(MCPWM_UNIT_0, MCPWM_TIMER_0, MCPWM_OPR_A, 320)); // pulse width is 320us ESP_ERROR_CHECK(mcpwm_start(MCPWM_UNIT_0, MCPWM_TIMER_0)); } static void dust_sense_stop() { ESP_ERROR_CHECK(mcpwm_stop(MCPWM_UNIT_0, MCPWM_TIMER_0)); ESP_ERROR_CHECK(mcpwm_set_signal_low(MCPWM_UNIT_0, MCPWM_TIMER_0, MCPWM_OPR_A)); } |
続いて,A/D 変換.割り込みハンドラ isr_handler
の中で A/D 変換を行います.割り込みハンドラは,初期化中に呼ぶ init_gpio
の中で登録します.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
static void IRAM_ATTR isr_handler() { signed portBASE_TYPE task_woken; // clear interrupt MCPWM[MCPWM_UNIT_0]->int_clr.val = MCPWM[MCPWM_UNIT_0]->int_st.val; uint32_t dust_ad = adc1_to_voltage(DUST_ADC_CH, &adc_char); } static void init_gpio() { ESP_ERROR_CHECK(mcpwm_gpio_init(MCPWM_UNIT_0, MCPWM0A, DUST_LED_GPIO)); MCPWM[MCPWM_UNIT_0]->int_ena.val = 1 << 18; ESP_ERROR_CHECK(mcpwm_isr_register(MCPWM_UNIT_0, isr_handler, NULL, ESP_INTR_FLAG_IRAM, NULL)); } |
測定される値はばらつきが大きいので,実際に計測する場合は何回か A/D 変換を行い,その平均値を使うと良いと思います.github に上げたコードではそのあたりも組み込んでいます.
ケース
使うものとしては,タカチの TWN13-5-13W がお勧めです.PM2.5 センサーの高さがそれなりにあるので,これでもギリギリです.
センサー用に下記のような穴をあけて,回路を突っ込んでやれば完成です.
設置
PM2.5 の計測なので理想的には屋外に置きたいですが,雨対策とか考えると屋内設置が便利です.
ここでは,下記のものを使って,跡を残さず設置する方法を紹介します.
まず,塩ビ板を適当なサイズにカットして,Jフックミニについているピンを使って次のように壁に固定します.
あとは,その塩ビ板とセンサーケースを面ファスナーで固定すれば完成.
上で紹介した面ファスナーは,正確にはデュアルロックとよばれるもので,ファスナーのように着脱が可能ですが,付けたときにはとても強力に固定できる優れものです.
設置例は下図の通り.エアコンの右側に来ているのがセンサーです.
うちの場合,センサーの右に外気の吸気口があるので,屋内設置とはいえそれなりに正確な PM2.5 の量が測れるのではないかとおもっています.
今の季節だと下のような感じで,まだ全然飛んでいないようですが.
参考文献
ナチュラル研究所
http://www.ishikawa-lab.com/RasPi_PM2_5.html
センサーの原理から制御方法まで詳しくまとまっていてオススメです.
コメント