MediaPipeを使いプログラミングをしてみた。ハンド トラッキングは、コンピューターがコンピューター ビジョンを使用して入力画像から手を検出し、手の動きと方向に焦点を合わせ続けるプロセスです。手の追跡により、手の動きと向きを入力として使用できます。これを応用して楽しくドローンを操縦したいと思います。
openpose などは 顔・手・ポーズのリアルタイム検出をしようと思ったら高性能なGPUを積んだPCが必要でしたが、MediapipeはCPUだけでも行えるようです。 MediaPipieは、Googleが提供しているライブメディアやストリーミングメディア向けのMLソリューションです。
Pythonプラットフォームの、顔検出、手検出、ポーズ検出、ホリスティック検出(顔・手・ポーズの統合検出)についてご紹介します。MediaPipieについては、youtubeで見つけた”ワンストップコンピュータービジョン”のサイトを参考にしています。すごく勉強になります。
以下のようにPyCharmのPythonインタープリターでパッケージMediapipeを追加します。OpenCvは追加されている前提でしています。
過程を説明していきます。
ハンド トラッキングの動画は次のようになります。
・・と 言うように、とても 楽しいです。(^^♪
している途中でcv2.imshow()が認識されなくなり 画像が表示できなくなってしまいましたので、なぜ表示されなくなったのか、今勉強中で次に進めませんが、
Mediapipeでドローンを手の動きで方向を指示(認識)し組み合わせることができた。
進める順序は
1:パソコンの内蔵カメラから認識させる。
2:tello(ドローン)のカメラから認識させる。
3:ハンドジェスチャーからのtello(ドローン)へのコマンド送信。
以上の順序で進めることにしました。
1:パソコンの内蔵カメラから認識させる。
Pychamでは cv2.imshow()が使えなくなりましたが 原因はわからずです。インターネットのコラムによるとpython等のバージョンが原因とのコメントがあり、anacondaでの仮想環境にて バージョンを指定して実行してみました。IDEもVisualStudioに乗り換えてみたところうまくいきました。
各バージョンは次の通りです。
mediapipe == 0.8.9.1
opencv-contrib-python==4.5.4.60
Python == 3.8
例えば、pip install mediapipe ==0.8.9.1 とバージョンを指定してインストールしていきました。
とりあえずpc webカメラからは、mediapipeが起動できました。
PCパソコンweb用 (4297 ダウンロード )次は 本題 tello(ドローン)からのカメラの認識です。
私は、telloのカメラで顔認識した、コードを使用して、プログラムをmediapipe用に改良して作成してみました。
まだ 映像に遅延があり、検討中です。
2:tello(ドローン)のカメラから認識させる。
エラーコードがでて インターネットで調べらりして苦労したのは次の通りです。
エラーメッセージ:
oserror: [winerror 10048] 通常、各ソケット アドレスに対してプロトコル、ネットワーク アドレス、またはポートのどれか 1 つのみを使用できます。
locaddr = (host, port) で port = 9000を使用していましたが、tello SDKに表記されている通りport = 8889にして実行しました。ちなみに、host = ‘0.0.0.0’ です。
エラーメッセージ:
cpp:182: error: (-215:assertion failed) !_src.empty() in function ‘cv::cvtcolor’
対策:tello から送られてくる画像情報のサイズが大きくcv2.cvtColor(resize_frame, cv2.COLOR_BGR2RGB)が認識できないという意味だったみたいで、frameをresizeし、サイズを小さくすることで回避できました。
エラーメッセージ: Circular buffer overrun 対策:回避するには、fifo_size URL オプションを増やします。このような場合に生き残るには、overrun_nonfatal オプションを使用します*UDP URL を次のように変更する必要があります。"udp://%s:%s?overrun_nonfatal=1&fifo_size=50000000" % ('192.168.10.1', '11111'))overrun_nonfatal=1 は、ffmpeg が終了するのを防ぎま tello(ドローン)からの映像は次の通りです。
ブログの続きの 3:ハンドジェスチャーからのtello(ドローン)へのコマンド送信。telloからの映像等は作成中です。
3:ハンドジェスチャーからのtello(ドローン)へのコマンド送信。
Mediapipe /Hand Land Model は 手の領域の”21個”のラウンドマークを検出するモデルです。
(^_-)-☆これから行うのは、ドローンのカメラの画像から手を検出し、このラウンドマークの位置(座標)情報から手のジェスチャーを認識し、そのジェスチャーのかたちに方向を関連づけし、、それぞれ方向のcommandを、tello(ドローン)に送り、指示通り移動させることをやっていきます。
まずは、Telloを飛行させずに カメラからの映像で指を認識し、指示を出せるかを確認しました。
人差し指 ⇒ ”right”, 中指 ⇒ ”left” 、 小指 ⇒ ”land”
映像では次の通りになりました。
中指を立たせる場合
if len(lmList) ! = 0
if lmList[8][2] < lmList[6][2]
(ラウンドマーク 8番の座標が < 第2関節 6番の座標より小さい場合開いてるということなので..*opencvの向きを使用すると、画像は上から始まるため、最大の高さの最大値は”0”らしい)
print(“left”)
これをTello(ドローン)の飛行にあわせての指示に書き換えると。次の通りな動画になります。
mediapipeの認識が 人差し指 と 中指 と 小指 が 一番 正確な認識となったのでこれに指示を与えました。
人差し指:print(“right”) ⇒ テイクオフ sock.senddto(b’takeoff’, tello_address)
中指:print(“left”) ⇒ 前進 sock.senddto(b’forward 20′, tello_address) と書き換えてみた
小指:print(“land”) ⇒ 後進 sock.senddto(b’back 20′, tello_address)
動画撮影(ドローンへの指示)での苦労したポイント:
5本の指で、それぞれ認識をしてみたが #親指 関節の長さが認識短いため認識が難しかったです。#薬指 関節が硬いので指を伸ばすのが困難であった。 したがって #人差し指、中指、小指 の3本がスムーズに伸ばせたて認識できたのでこれに指示を与えました。
次に映像認識については、裸足でした場合、足の指も認識されてしまいため靴下をはいた。又 両手がカメラの範囲に映る場合 両方が認識され、指示が混乱するため、片手は後ろに隠している。
プログラミングは趣味なので 素人で粗削りですがご参考になればと・・・・・CODEを添付しときます。←クリック
Mediapipeを使ってみて 非常に楽しかったです。 それにしてもTello(ドローン)は プログラミングもいろいろできて 素晴らしいお手軽なドローンだと あらためて感心しました。(^^♪