Raspberry Pi PicoでCO2を計測・表示してみる


Raspberry Pi Picoでの開発の練習として、以前ESP32で作成したのと同じように、CO2を計測・表示してみました。

ほかの方も同じようなことをしているようですが、おそらく一番シンプルな方法で実現してます。

準備

  • ハードウェア
    • Raspberry Pi Pico
    • MH-Z19C(CO2センサー)
    • SSD1306(OLEDディスプレイ)
    • その他(ケーブルやらブレッドボードなど)
  • ソフトウェア
    • MicroPython(Thonnyで開発)

SSD1306用ライブラリの取得

自分で全部書くのはめんどくさかったので、先人の知恵をお借りすることにしました。
githubのこちらからファイルをダウンロードし、Raspberry Pi Picoに入れました。

具体的には、githubのページでraw表示し、Thonnyの新規ファイルにコピペして、ファイル名「ssd1306.py」をつけてRaspberry Pi Picoに保存しました。

配線

CO2センサー、OLEDディスプレイの配線は以下のようになっています。

〇CO2センサー(UARTで通信)

pico側 CO2側
電源(5V) VBUS(40番ピン) Vin power in(3番ピン)
アース GND(23番ピン) GND(3番ピン)
UART1 TX(GP4、6番ピン) UART(RXD)(5番ピン)
UART1 RX(GP5、7番ピン) UART(TXD)(6番ピン)

〇OLEDディスプレイ(I2Cで通信)

pico側 OLED側
電源(3.3V) 3V3(OUT)(36番ピン) VCC
アース GND(23番ピン) GND
SDA I2C0 SDA(GP0、1番ピン) SDA
SCL I2C0 SCL(GP1、2番ピン) SCL


プログラミング

CO2センサーからのデータの取得

まず、CO2センサーからデータを取得します。

main.py
from machine import Pin, UART
import utime

mhz19c = UART(1, baudrate=9600, tx=Pin(4), rx=Pin(5))

while True:
    data = bytearray([0xff, 0x01, 0x86, 0x00, 0x00, 0x00, 0x00, 0x00, 0x79])
    mhz19c.write(data)
    mhz19c.readinto(data,len(data))
    co2 = data[2] * 256 + data[3]
    temp = data[4] - 48
    print('CO2 (ppm):'+str(co2))
    print('Temperature (C):'+str(temp))

    utime.sleep(1)

なお、CO2の値だけでなく、温度も取得できるので、一緒に表示しています。

また、ファイル名は「main.py」にしておきます。
(起動時に自動で実行させたいので)

実行すると、Thonnyのコンソールに1秒間隔で取得したデータが表示されます。

OLEDディスプレイへの表示

次に、取得したデータをOLEDディスプレイに表示するようにします。

main.py
from machine import Pin, UART, I2C
import ssd1306
import utime

mhz19c = UART(1, baudrate=9600, tx=Pin(4), rx=Pin(5))
i2c = I2C(0, sda=Pin(0), scl=Pin(1))
display = ssd1306.SSD1306_I2C(128, 32, i2c)

while True:
    data = bytearray([0xff, 0x01, 0x86, 0x00, 0x00, 0x00, 0x00, 0x00, 0x79])
    mhz19c.write(data)
    mhz19c.readinto(data,len(data))
    co2 = data[2] * 256 + data[3]
    temp = data[4] - 48
    print('CO2 (ppm):'+str(co2))
    print('Temperature (C):'+str(temp))

    display.fill(0)
    display.text(str(co2)+' ppm', 0, 0, 1)
    display.text(str(temp)+' degree', 0, 10, 1)
    display.show()

    utime.sleep(1)

コンソールにも表示されますが、OLEDディスプレイにも取得したデータが表示されます。
(省略形で表示しています)

余談

USBケーブルが違うと、取得される値が異なるのが気になる...
供給電圧が低いのかな?
→キャリブレーションされたら(しばらくほっといたら)正しくなりました

Raspberry Pi Picoの中身

ちなみに、Raspberry Pi Picoには以下の2つのファイルが置かれます。

できれば、モジュールのインストール(「pip intall 〇〇」)ができればいいんだけど、その辺りはまだよくわかりませんでした。
Raspberry Pi Picoに入れるMicroPythonを作り直せばいいのかな?

まとめ

非常に簡単にCO2を計測・表示できました。