なるように、なる

徒然なつぶやき、備忘録です。

ヨガポーズの認識と表現

ヨガポーズの認識をさせてみた

KinectV2で取得したスケルトンを、CNNで学習させたモデルでポーズ推定して、ヨガポーズと一致していたらパーティクルを出すというものをvvvvで作ってみました。

 

f:id:Shampagne:20171001221633p:plain

KinectでBodyを認識して、背景をセグメンテーションし、ヨガスタジオの背景画像に重ねました。実際は、とっ散らかった自宅で撮影してます。

f:id:Shampagne:20171001221926p:plain

ウッティタ・トリコーナーサナというポーズです。
事前に学習したポーズと一致した場合、パーティクルが出てくるようにしました。

f:id:Shampagne:20171001222200p:plain

上級者用の裏面を用意しました。
ポーズの一致度が90%以上かつ5秒以上キープできた場合に、このステージに遷移します。

f:id:Shampagne:20171001222348p:plain

ヨガのポーズはたくさんあります。8400万とも言われてます。
僕が今回学習させたのはたかだか10種類。とても上級者のヨギーには満足してもらえません。なので、このモードでは、同じ姿勢をキープ出来ていると判定したら、丹田のあたりからパーティクルを出すようにしました。

表現について考える

基本的な機能を実装できたあと、「オシャレにしていこう!」と思っていろいろ付け加いったんですが、正直、力不足でした。
こんな感じにしてみたいと思っても、vvvvでうまく表現できない。他の作品みたいに細かいパーティクルをシュワシュワしたいのに、、、とか。これは練習をするしかないな、と。
それ以上に悩んだのは「何を表現するべきか」ということ。
別に新しいことをしているつもりは無いけど、では逆になぜ自分は今この作品?を作っているんだろう、と。どのようにパーティクルを出すか、どこから出すかっていうだけでも、最初は「適当にオシャレになればいいや」と思っていたけど、ある本を読んでいるときに、ストーリーが大切、という一言を読んで、目が覚めました。

僕はなんでヨガのポーズを認識させたいんだろうか、ヴィジュアライズして何を表現したのだろう。

そういう観点から考え直した後、ヨガをして深く集中したときの世界を表現し、それをいろんな人に知ってもらえたらなぁ、と思って裏面を作りました。

もっと力をつけたら、もう一度ヨガポーズの作品に取り組みたいと思います。

次はタブラにチャレンジします。

ヨガポーズの認識(仮まとめ)

いったん一区切りして、ここまでに作ったものをアップします。

作ったもの

・OpenPoseで画像からスケルトン座標の推定

・Kerasでスケルトン座標によるヨガポーズの推定

・KinectV2のvvvvプラグインカスタマイズ

・vvvvで上記の結合

提出物1

vvvvでKinectからのデータを取り込み、TCPでKerasのバックエンドとデータ通信し、結果をもとに画像にエフェクトかけてます。パーツ作りは大変だったけど、vvvvで繋げるのはすごい簡単。

f:id:Shampagne:20170820212348j:plain

 

提出物2

 Kerasに学習させた3つのポーズとマッチすると、手の位置からパーティクルが出るようにしてみました。パーティクルが出てくる位置がちょっとずれてますが。。。

youtu.be

ここまではパーツ作りを一気にやってきたので、次は完成度を高める作業をやっていこうと思います。

ヨガポーズのクラス分類

ヨガのポーズを機械学習させて、自動で識別させるようにしました。

入力データの準備

ヨガのポーズは実にたくさんあるのですが、まずは識別し易い以下の3ポーズをチョイス。

f:id:Shampagne:20170815145230j:plain

f:id:Shampagne:20170815145244j:plain

f:id:Shampagne:20170815145310j:plain

これらのポーズの画像を10枚ずつ収集して、OpenPoseでスケルトンの座標を取得しました。

ちなみに、OpenPoseとKinectV2で取得できるスケルトンは、以下のようになってます。(OpenPoseはこちらが元ネタです。)

>OpenPose

f:id:Shampagne:20170816095804p:plain

>KinectV2

f:id:Shampagne:20170816095832p:plain

 

KinectV2で取得できない目、耳、背中の位置は使用せず、14点のx,y座標を入力データとしました。また、学習のための前処理として、以下の2つを行いました。

 ・頭の位置を原点とする

 ・頭から喉(0番と1番)の距離をもとにリサイズする

こうして得られた入力データを、ちょっと加工して各ポーズ400個に水増ししました。合計1200個なので、まぁまだ少ないですが、いったん進みます。

 

機械学習

利用したのはKerasで、バックエンドはTensorFlowです。

環境構築は、このサイトにお世話になりました(ありがとうございます)。

Keras、マニュアルも分かりやすかったので、無知でしたが割合すぐに使うことができました。

ただし、無知なのでネットワークをどう組めばいいかは、よく分かりません。

なので、MNISTのサンプルをそのまま使うことにしました。

MNISTは32x32の画像を入力としています。なので、行列サイズを16x16に変更して、各行に14カ所のx,y座標をマッピングしてみました。

半信半疑の感はありましたが、学習させたモデルを使って自分のヨガポーズを分類させてみると、見事に識別できてました。

すーごーいー。
(けもふれ再放送中)

開発合宿@家

今日から盆休みに入りました。

つまり時間はいくらでもある、はずです。

なんとか、これからの1週間でひととおりの実装をしたいと思ってます。

現状のおさらい。

Kinect + VVVV

 こちらのサイトを参考に、KinectのデータをVVVVで取り込めるようになりました。

f:id:Shampagne:20170812153904j:plain

・OpenPose

 サンプルコードを元に、スケルトン座標をファイル出力できるようになりました。

f:id:Shampagne:20170812153632j:plain

 

この1週間で、OpenPoseで取得したスケルトンからヨガのポーズを学習させて、姿勢認識ができるようにしたいと思います。

 

(*´ω`*)ガンバル

 

えっと、、、

Kinectに手を出しました(*´ω`*)

f:id:Shampagne:20170720054811j:plain

雑な感想・・・

  • 大きい。RealSenseが驚異的に小さく感じる。
  • 機能は豊富。
  • ライブラリの使い方がとても似ている。
    (RealSense使っていたら、なんなく使えた)

Kinectに手を出したのは、RealSenseを使っていて、背景のセグメンテーションするのが大変だったのと、vvvvのプラグインがすでに用意されてたから。つまり、今後の開発に必要なものが用意されてたから。

やっぱり世の中的にはまだKinectのほうが色々と充実している感はある。

ただ、RealSenseの小ささと、近距離(0.2m~)測位は、アプリケーションの広がりを期待ができるように思う。そう考えていると、スマホに3Dセンサが載るまでにいろいろと準備しているといいかも。あまり時間なさそうですが。

Tangoが載ったスマホLenovoが出したし、iPhone8にも載りそうと噂されているし、この時流に乗っていけるように、がんばろ。

 

OpenPose動いた!

またしても環境構築にハマりまくったけど、無事にOpenPose動きました。

f:id:Shampagne:20170703000952p:plain

サンプルを動かしただけですが、いちおうソースコードからビルドまでやりました。
こちらのサイトが大変参考になりました。

動いてよかった。。

セグメンテーション

R200はセグメンテーション機能が使えないので、depthを使って自分で実装することにしました。

自力でセグメンテーション

  1. カラー画像とDepth画像を取得する
  2. Depth画像をカラー座標系に座標変換する
  3. パーソントラッキング機能で、カラー画像から人物の中心位置を取得する
  4. 人物の中心位置のdepthをもとに、前後50cm以外の箇所をカラー画像から取り除く

f:id:Shampagne:20170622060833p:plain

ざっくりですが、こんな感じになりました。
エッジ部分があらい、ブロブの内部も除去されてる、遅い。このあたりを改善したいです。

座標変換

カラー画像とDepth画像はカメラの位置がずれてるので、併せて使う場合は座標変換をする必要があります。今回はDepth画像の座標系をカラー画像に変換しました。
座標変換用のクラス「PXCProjection」を使います。
使い方は、こちらのサイトが参考になりました。
あと、RSDKのサンプルにある「Projection」も参考になります。