airpocketのアイコン画像

Maix Bitを使って音源定位と可視化

airpocket 2020年12月26日に作成  (2020年12月26日に更新)

Maix Bitを使って音源定位と可視化

初めに

マイクロフォンアレイという装置を使うと、音がどの方向からやってくるのか、その音源の方位を求めることができます。
産業用や研究用の設備のほか、最近広く普及しているスマートスピーカーにも使われていて、ユーザーの音声の分析に活躍しています。

今回作成したのは、Sipeed社のMaix Bitというマイコンボードとマイクロフォンアレイモジュールを組み合わせた音源可視化装置です。
Maix Bitは、音声解析や画像解析に強いK210というマイコンが搭載されており、マイクロフォンアレイの音源定位解析と同時にカメラによる画像撮影と合成まで行うことができました。

完成品の動作状況はこの通りです。

ここに動画が表示されます

使用したもの

  1. Sipeed Maix Bit
    カメラ、LCD付きのものを準備してください。
  2. Sipeed R6+1 Microphone Array
    今回のキモになるセンサーモジュールです。
    6角形の基盤の頂点と中央に7個のmemsマイクがあり、音声波形の周期のずれから音源位置を推定します。また全周に12個のRGBがあり音源方位のインジケーターとして利用できます。
    キャプションを入力できます
  3. ユニバーサル基板もしくはブレッドボード
    Maix Bitを載せれるサイズ、今回は40㎜×60㎜の基板を使いました。
  4. プラバン等のベース材
    Maix BitとMic Arrayを並べて載せられるサイズ。今回は3t×80㎜×120㎜のアクリル板を使いました。
  5. スペーサー、ねじ類
    Mic Arrayには、M3の真鍮スペーサとナット各4個が付属しています。板等に固定する場合、M3のボルトが必要です。今回はM3×6㎜のボルト×4個を使用しました。
    Mix Bitを固定する際、今回はユニバーサル基盤を介してM2スペーサとボルト、ナットで固定しています。
  6. ピンソケット、ケーブル
    Maix Bit、Mic Arrayともに、QI2550コネクタのPINがついていますので、これにあったピンソケットやケーブルで接続します。

組み立て

Maix BitとMic Arrayの各ピンを下表のとおり接続します。

Maix Bit Mic Array
PIN23 MIC_D0
PIN22 MIC_D1
PIN21 MIC_D2
PIN20 MIC_D3
PIN19 MIC_WS
PIN18 MIC_BCK
PIN17 LED_CK
PIN15 LID_DA
3V3 VIN
GND GND

また、それぞれのモジュールがばらばらだと扱いにくいので、プラバン等の上にボルトないしは両面テープ等で固定します。今回は、写真のような基板を作成してMaix Bitを固定し、Mic Arrayとならべてアクリル板の上にボルト止めしました。
表面(マイコンボード側)
裏面
キャプションを入力できます

開発環境

Maix Bitは、MaixPyという、MicroPython系統のスクリプトでコーディングしました。K210では主流の開発言語だと思います。開発環境はMaixPy専用のMaixIDEのv0,2.4、ファームにはmaixpy_v0.6_9_g88bfd0177.binを使用しました。
コードの実行方法は以下の3つの方法があります。私は、開発中は1、コード完成後は3の方法で実行しています。

  1. Maix IDEに接続し、実行したいコードを読み込んで実行ボタンを押す。
  2. ファイル名をboot.pyとしてmicro SDに保存し、Maix Bitに入れて電源を入れると自動的に実行されます。
  3. uPYLoaderを使用して、Maix Bitのflash領域へ直接書き込む

コーディング

Git HubのMic Arrayから音源位置をマップ化させるコードを参考にしました。
このコードをもとに、Maix Bitのカメラで画像を取得し、音源位置のマップ画像とリアルタイム合成して表示させています。

from Maix import MIC_ARRAY as mic
from Maix import FPIOA
from fpioa_manager import fm
import lcd
import sensor
import gc

from Maix import utils      #heap mem使用量確認及び設定用
utils.gc_heap_size(2500000) #Heap mem山盛り設定 soundmap画像を480*480に引き伸ばし処理するため増量必要。

lcd.init()
lcd.direction(lcd.YX_LRDU)   #soundmapとcameraイメージの向き合わせのため、hmirrorとvflipと組み合わて使用。
sensor.reset()
sensor.set_auto_gain(1)             #自動ゲインは入れましょう。
sensor.set_auto_whitebal(1)         #自動WBも入れましょう
sensor.set_pixformat(sensor.RGB565)
sensor.set_framesize(sensor.QVGA)
sensor.set_hmirror(3)
sensor.set_vflip(0)
sensor.run(1)

mic.init()
Fpioa = FPIOA()
LEDdir = (100,100,100)            #マイクアレイモジュールのLEDインジケーター表示。RGBの輝度を0-255で設定。まぶしいのでいらない。

#Maxi Bit用のピン設定。
Fpioa.set_function(23, fm.fpioa.I2S0_IN_D0);
Fpioa.set_function(22, fm.fpioa.I2S0_IN_D1);
Fpioa.set_function(21, fm.fpioa.I2S0_IN_D2);
Fpioa.set_function(20, fm.fpioa.I2S0_IN_D3);
Fpioa.set_function(19, fm.fpioa.I2S0_WS);
Fpioa.set_function(18, fm.fpioa.I2S0_SCLK);
Fpioa.set_function(17, fm.fpioa.GPIOHS28);
Fpioa.set_function(15, fm.fpioa.GPIOHS27);

while True:

    img = sensor.snapshot()                         #カメラ画像取得

    soundmap = mic.get_map()                        #マイクアレイから音源の推定位置を16*16pixelのgrayscaleで求める。
    sounddir = mic.get_dir(soundmap)                #soundmapから音源方向を求める?
    mic.set_led(sounddir,(LEDdir))                  #マイクアレイモジュールのLEDを光らせる。
    soundmap = soundmap.copy((4,4,8,8))             #サウンドマップの画格をカメラに合わせるため、中央8*8pixcelを切り出す
    soundmap = soundmap.resize(240,240)             #サウンドマップをカメラ画像に合わせるため240*240pixelに拡大
    maskmap = soundmap.copy()                       #soundmapとカメラ画像を合成する際のマスク様画像を作成
    maskmap = maskmap.binary([(1,255)])             #maskmapを二値化してマスクにする。
    soundmap = soundmap.to_rainbow(1)               #soudnmapをレインボーカラーに変更
    img = img.copy((30,0,240,240))                  #合成する前にカメラ画像をsoundmapとサイズ合わせる。
    img.blend(soundmap,alpha = 150,mask = maskmap)  #マスクを使い、soundmapの音検出部分のみをカメラ画像に重ね合わせる。alpha値が大きいほど音の表示が薄くなる。
    lcd.display(img)

mic.deinit()

初期設定ではheap memory不足となるため、ヒープ領域を拡大しています。
大きくしすぎるとマイコンボードが動かなくなるためご注意ください。
また、ヒープ領域設定はリセット後も維持されるため、開発終了後は400000程度まで減らしておくことをお勧めします。

表示領域について

今回使用しているMaixBitはOV2640の標準的なレンズを使用しています。FOV(視野角)は80°ぐらいだと思いますが、Mic Arrayの音源定位のFOVはより広角で160°以上ありそうです。
今回は、Mic Arrayの外側視野を切り捨てる形でそれぞれの画像のFOVを合わせていますが、カメラ側に広角レンズを装着することで、より広い視野での音源定位ができます。
次の画像は、カメラのレンズ前にスマホ用の広角レンズを装着した際の様子です。

ここに動画が表示されます

また、マイクアレイの中心とカメラレンズの中心がずれているため、視野の中心軸がずれてしまいます。装置を作成する際にはマイクアレイとカメラを可能な限り近くに配置することと、視野の軸を公差させるように配置し、狙いの距離で視野の中心が一致するようにセッティングしましょう。今回は約1m先で視野の中心が一致するように調整しています。

まとめ

今回はSipeedのエッジAI開発用マイコンMaix Bitと、K210の処理能力を生かしたMic Arrayを利用して音源定位と可視化を行いました。
ちいさなマイコンで音響と画像処理を並行して走らせ、ここまでのパフォーマンスを得られるのは驚きでした。Mic Array自体、1年ほど前の発売だったと思いますが、開発事例の報告を見かける機会もなく放置していましたが、思いもよらず面白いガジェットができました。
とてもポテンシャルの高いセンサーだと思いますのでより多くの人に、手に取っていただければと思います。

2
ログインしてコメントを投稿する