20200721のUnityに関する記事は8件です。

ThreeDPoseTracker v0.2.0アップデート

はじめに

Top020.png

この記事はUSBカメラモーションキャプチャーThreeDPoseTrackerのバージョン0.2.0のアップデートについての記事です。ThreeDPoseTrackerってナニ?という方は先に

「USBカメラモーションキャプチャーThreeDPoseTrackerの説明」
https://qiita.com/yukihiko_a/items/43d09db5628334789fab

をご覧ください。

v0.2.0について

ダウンロード先

下記URLからダウンロードしてください。
https://digital-standard.com/threedpose/ThreeDPoseTracker_Win_x64_v0_2_0.zip

更新内容

今回の主な更新内容です。今回はBVHのHumanoid Boneのみの保存が主たる目的のリリースです。

  • BVH保存時に、Humanoid Boneのみの保存やその他のオプションの設定を可能にしました。詳細は後述の設定画面の章を参照ください。
  • 上記の機能追加により設定画面を変更しました
  • モーションの動きを補正するフィルターを追加しました
  • High Quality Modelの精度向上(1%程度なので見た目ではわかりません)
  • デフォルトのアバターをUnity-chanから蘭鈴りゅん (Lune)に変更しました。Unity-chanはもういません。 蘭鈴りゅん(らぬべる りゅん)のVRMファイルは下記URLからDLできます。

https://hub.vroid.com/characters/2743935442348366186/models/3045425008508757993

設定画面

設定項目が多くなったので機能ごとにタブで分けました。以下それぞれの機能の設定項目を説明します。

Images

入力画像や背景画像の設定です。設定内容はv0.1.0から変わっていません。
config_images.png

  • Show Source Image
    画面全体に表示されているSource Deviceとして読み込んだ動画やUSBカメラの画像表示・非表示を設定します。

  • Show Input Image
    AIへの入力画像(左上の小窓)の表示・非表示を設定します。

  • Skip on Drop
    動画再生時、オンの際は処理落ちするフレームは飛ばして再生します。オフにして再生すると全フレームを再生するため処理が遅い場合はスローモーションのような再生になります。

  • Movie File Repeat Playback Mode
    動画再生時、オンの場合動画をリピート再生にします。

  • Mirror when Using Camaera
    USBカメラ使用時、オンの場合カメラからの入力がミラー状態になります。

  • Source Cut Scale
    Source Imageの画像の縦を1とした比率で入力画像を切り出します。例えば動画に映っている人が小さすぎる場合は1以上の値を指定すると拡大されます。また、爪先が画面の淵に近い場合やギリギリという場合はこの値を0.9や0.8にすると少し安定します。
    cutScale.png

  • Source Cut Center position
    Source Imageの中心を原点とし画像の縦を1とした比率で指定した位置から入力画像を切り出します。動画の右側に踊っている方がいる場合などにその位置が中心になるように調整します。下図はxの移動量に0.3を指定した場合で、上図の拡大率での見え方の差になります。画像を映しているカメラが縦比で0.3だけ右に移動したと考えてください。マイナス値にすれば左に移動し、y軸についても同様です。
    cutPos.png

  • Background Image File
    背景画像を切り替えます。画像が存在しないか、この項目が空になっているとデフォルトの画像を表示します。
    背景020.png

  • Background Scale
    背景画像の大きさを調整します。画像位置は変更できないため、位置調整は元の画像を変更して調整してください。

  • Background Color
    Source Image、Input Image、Background Imageを全て非表示にすると単色の背景になります。背景色はRGB(0~255)で指定できます。グリーンバックや背景に何も出したくない時に使用してください。
    greenback020.png

Predict

主にモーションに関する設定です。
config_predict.png

  • Low Pass Filter
    飛びやブルブルを抑える為のフィルターです。Height Qualityモデルであれば0~0.2程度が妥当です。大きくするとなめらかになりますが、遅延と動きが放漫になってきます。細かい動きが不要であれば0.3くらいでもなんとかなります。数値を変更しても処理速度には影響しません。

  • n-order LPF
    上記Low Pass Filterを何階かけるかを設定します。大きくすると効果は強くなりますが、数字に比例して効果が上がる訳ではありません。対して重い処理でもないので初めから最大の9でも良いくらいです。

  • Range Pass Filter
    上記のLow Pass Filterはブルブルする高周波成分をカットする為のフィルターです。これは特定の周波数を通すためのフィルターです。そうは言っても人のゆっくりした動きは全て採用したいので事実上ローパスフィルターとして使用します。なので下の周波数は0Hzにしたい所ですが0は指定できないので0.01Hzとしています。上の周波数は、人の動きは0.2秒くらいの動きが取れれば十分と言われているので5Hz程度で十分です(1÷0.2=5Hz)。が、デフォルト値はさらに安定を求めて3.5Hzとしています。キビキビした動きにしたい時は5Hzくらいにしておいてください。
     ・Buffer:
      データをサンプリングするバッファサイズです。変更する必要はないと思います。
      大きくすると処理は重くなります。
     ・Order N:
      フィルタの次数。実はまだあんまり評価できてないので、触らないでください。
      大きくすると処理は重くなります。
     ・Hz (from to):
      低周波の0.01は変更する必要はないです。高周波は2~5Hzくらいで調整してください。
      数値を変更しても処理速度には影響しません。

  • Forward threshold
    AIからの出力は0~1のスコアで出力されます。1が自信ありで0が自信なしです。人が画像に映っている場合は通常0.5以上のスコアになります。人が映っていないときは0~0.2程度です。この設定は人が映っていないと判断する閾値で、スコアがこの閾値以下になるとモーションが止まります。Forwardはアバターが正面を向いている時(体の向きが正面に対して±45度の範囲)の閾値です。

  • Backward threshold
    Backwardは上記のForwardの範囲外の閾値です。顔が見えていないと全体のスコアが低下するため分けて管理しています。こちらの値は低めに設定してください。

  • LockFoot
    この機能はカメラにぎりぎりつま先が入らない場合や入っても安定しない場合などにつま先の動きを固定します。カメラや動画で足が範囲ギリギリの場合はロックした方がいいです(はみ出ると正確な判定は出来ません)。つま先は動かなくてもそれほど不自然にはなりません。デフォルトでオンでも良いくらいです。
    チェックを入れた時点で足首をロックします。動かしながらロックするとおかしな位置でロックされます。通常は初期位置でロックしたいと思うので、チェック後アプリケーションを再起動してください。

  • LockLegs
    膝から下の動きをロックします。LockFootのついでに作ってみましたが使い道はあまりないと思います。

  • ElbowAxisTop
    肘の回転軸を切り替えます。例えばジャージのような肘の外側にラインがあるようなテクスチャや、内側が陰になっているようなテクスチャの場合、何も考えずに腕を曲げるとテクスチャの見え方がおかしくなります。このようなテクスチャの場合肘の回転軸を切り替える事で内側外側をそれっぽい動きになるようにしています。ですが、腕を真上に上げると肘がねじれたように動いてしまいます。これをオンにする事で通常の肘の動きに切り替わり肘が自然な感じに動きます。ですが、テクスチャの見え方はおかしな感じになります。下図を見てください。上段は肘の内側に影があるテクスチャです。オフ時には内側に影がありますが、オンの時は外側に見えます。ですが、下段のようにオフの場合は肘がねじれたように見えます。腕が肌色か単色の場合はオンにしてください。もっといい方法がありそうですが、現状はこんな感じです。
    ElbowAxisTop.png

  • Trained Model
    姿勢推定のモデルを選択します。スペックが足りている場合はHigh Qualityを選択してください。この項目を変更する場合はアプリケーションんを再起動してください。スペックが足りない場合は後述のLow Qualityモデルを使用してください。

Record

config_record.png
BVHの保存は、UnityのAsset StoreにあるBVH Toolsをそのまま使っています。Unityでデータを読み込みたい場合はこのAssetを使用するのが良いと思います。Githubはこちらのようです。オプションの説明もGithubをご覧ください。
https://github.com/emilianavt/BVHTools

  • Blender coordinate system
    Blenderへの読込、VRM Live ViewerやVMDへの変換の際にはオフで大丈夫の様です。このオプションはBlenderの座標系と一致するように変更し、Blenderで読み込んで修正した後に、またUnityで読み込むというような場合にはオンにした方が良いそうです

  • Enforce Humanoid Bones
    オンの時にはHumanoidのボーンしか保存しません。VRM Live ViewerやVMDへの変換の際にはHumanoidのボーンのみなのでオンのままにしてください。髪の毛や服などのボーンも出力に含めたい時はオフにしてください。

  • Capturing
    オンにすると指定したFPS固定でデータが保存されます。本当に指定した通りに保存されるのかは確認していません。

  • CatchUp
    これをオンに設定すると、「フレームレートが低下した場合にキャプチャフラグを使ってキャプチャを高速化し、キャプチャしたアニメーションの持続時間を正確に保つことができます。このフラグを無効にすると、キャプチャされたフレームの後に、与えられたframeRateに従って、1つのフレームが必要とするように、少なくとも多くのミリ秒が経過することを保証します。」だそうです。

Others

config_others.png

  • Use Unity Video Capture
    Unity Video Captureを有効にします。これは今表示している画面(メニューや設定画面は除く)をUSBカメラの出力とし、Zoom等の他のアプリケーションからカメラの入力として扱えるようにします(仮想カメラ)。詳細はUnity CaptureでZoomに出力を参照ください。

  • Use VMC Protocol
    VMC Protocolを使用してアバターのボーン情報と仮想トラッカーを送信します。ここはサンプルコードのままです。ブレンドシェイプは送信しません。VMC Protocolの受信もできません。まだテスト実装ですが、EVMC4Uでデータが受信できるところまでは確認しています(実はそれ以上のことはまだ理解していません)。
    vmpc_logo_128x128.png

  • IP
    VMC Protocolのサーバーが稼働しているPCのIPアドレスを指定します。通常は127.0.0.1のままで良いはずです。

  • Port
    VMC Protocolのサーバーのポート番号を指定します。通常が何番なのかはわかりませんが、たぶん39539な感じです。

  • Rot
    ThreeDPoseTrackerは180度回転した背中を向けた状態になっています。チェックを入れることで180度補正をかけます。

  • Restore Settings
    設定を初期状態に戻します。アバターの設定も初期化されます。そのままアプリケーションを終了してください。

BVHファイルについて

このアプリでは座標系が180度回転している状態になっています。正面から見て背中を向けている状態です。都合上、この方が作りやすかったのですが、少しの利点があるだけなので、ちょっと失敗したかなという気もします。とりあえずは出力後に180度回してください。

VMDへの変換

出力したBVHファイルのVMDへの変換についてですが、B-MoMi ver.0.2で変換できるところまでは確認しました。B-MoMiのダウンロードおよび詳細な使い方については下記を参照ください。
http://atupdate.web.fc2.com/

ボーンマップは下記のように設定してください。キモは左腕右腕の40と-40です。通常はプラスマイナスが逆なんですが、上にも書いた通りこのアプリの出力は背中向きになっているます。そのため、TポーズからAポーズへの補正の値を逆にしなければならないようです(たぶん)。scaleはマニュアルを参考に適時設定してください。
BVHのボーン情報はBVHファイルをテキストエディタで開くと最初のHIERARCHYの項目に載っています。必要があればそれを参考にボーンマップファイルを修正してください(B-MoMiの-makeMapオプションでもボーンの情報は取れますが完璧ではなかったです)。

boneMap_TDPT_1.txt
#
# ボーンマップ
#
# @scaleはセンターボーンの移動量を拡大縮小します
# 1.0で元データのまま。
# @scale=0.3

センター=Hips
左足=LeftUpperLeg
左ひざ=LeftLowerLeg
左足首=LeftFoot
右足=RightUpperLeg
右ひざ=RightLowerLeg
右足首=RightFoot
上半身=Chest
左肩=LeftShoulder
左腕=LeftUpperArm,0,0,40
左ひじ=LeftLowerArm
左手捩=LeftHand
右肩=RightShoulder
右腕=RightUpperArm,0,0,-40
右ひじ=RightLowerArm
右手捩=LeftHand
首=Neck
頭=Head

BVHファイルは、Blender coordinate systemをオフ、Enforce Humanoid Bonesはオンにして作成してください。保存したBVHファイルがmotion.bvh、ボーンマップファイルがboneMap_TDPT_1.txtとすると、コマンドプロンプトで下記のように実行すれば指定したBVHファイルと同名のVMDファイルが作成されます(パスは適当に直してください)。

C:\b-momi_02\b-momi>b-momi.bat -bvh motion.bvh -map boneMap_TDPT_1.txt
B-MoMi 0.2
BVH motion converter for MikuMikuDance

出力先:motion0723.vmd
BVHモデル身長=1.284616
ミク身長=15.5686
========
変換開始
========
@scale=12.11926365544256
========
変換完了 (motion.vmd)
========

あとはMikuMikuDance側で足のIKをオフにしてモーションを読み込んでください。環境によって処理速度が遅い場合は、モーションを読み込むと早回しの様になります。モーションの倍率などで調整してください(MMDあまり使った事ないので使い方が良くわかりません)。
試してみたのはここまでです。
MMD.png

最後に

アプリのリリースについての記事をQiitaに書くのもなんか違うのかなと思いつつ、Qiitaに書くのが楽なのでもうしばらくはQiitaを使わせてもらいたいと思います。
次は奥行きの移動と足付き(床の判定)を考えたいと思います。ちょっと仕組み的に難しいのでできるかどうかはわかりません。
以下は前回のコピーです。
ちなみにこのアプリのソースは下記のリポジトリにあります(準備中)。コードのライセンスはGithubに書いてあるライセンスに従ってください。姿勢推定でのお仕事もしているので全て無料とはいかないのです。機能追加して商用で使いたいという方はライセンスを購入いただくかお仕事の依頼を下さい。どうしても無料で機能追加して商用利用したいという方は、このアプリ版は無料で通すつもりなので、マージの依頼なりプルリクなりを頂ければ、そのうちアプリに追加してリリースするかも知れません(保証はしません)。

https://github.com/digital-standard/ThreeDPoseTracker

Licence

このThreeDPoseTrackerの実行ファイルについては営利・非営利問わずご自由にお使いください。この実行ファイルを使用した配信、モーションデータも同様にご自由に利用可能です。
GithubにあるソースコードについてはGithubにあるライセンスに従ってください。

免責事項

本ソフトウエアの使用に起因する、ソフトウエア、ハードウエア上の事故その他の損害、または使用できなかったことから生じる一切の損害に関して、製作者はいかなる責任も負わず、修正する義務を負いません。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

ThreeDPoseTracker Ver.0.2.0アップデート

はじめに

Top020.png

この記事はUSBカメラモーションキャプチャーThreeDPoseTrackerのバージョン0.2.0のアップデートについての記事です。ThreeDPoseTrackerってナニ?という方は先に

「USBカメラモーションキャプチャーThreeDPoseTrackerの説明」
https://qiita.com/yukihiko_a/items/43d09db5628334789fab

をご覧ください。

v0.2.0について

ダウンロード先

下記URLからダウンロードしてください。
https://digital-standard.com/threedpose/ThreeDPoseTracker_Win_x64_v0_2_0.zip

更新内容

今回の主な更新内容です。今回はBVHのHumanoid Boneのみの保存が主たる目的のリリースです。

  • BVH保存時に、Humanoid Boneのみの保存やその他のオプションの設定を可能にしました。詳細は後述の設定画面の章を参照ください。
  • 上記の機能追加により設定画面を変更しました
  • モーションの動きを補正するフィルターを追加しました
  • High Quality Modelの精度向上(1%程度なので見た目ではわかりません)
  • デフォルトのアバターをUnity-chanから蘭鈴りゅん (Lune)に変更しました。Unity-chanはもういません。 蘭鈴りゅん(らぬべる りゅん)のVRMファイルは下記URLからDLできます。

https://hub.vroid.com/characters/2743935442348366186/models/3045425008508757993

設定画面

設定項目が多くなったので機能ごとにタブで分けました。以下それぞれの機能の設定項目を説明します。

Images

入力画像や背景画像の設定です。設定内容はv0.1.0から変わっていません。
config_images.png

  • Show Source Image
    画面全体に表示されているSource Deviceとして読み込んだ動画やUSBカメラの画像表示・非表示を設定します。

  • Show Input Image
    AIへの入力画像(左上の小窓)の表示・非表示を設定します。

  • Skip on Drop
    動画再生時、オンの際は処理落ちするフレームは飛ばして再生します。オフにして再生すると全フレームを再生するため処理が遅い場合はスローモーションのような再生になります。

  • Movie File Repeat Playback Mode
    動画再生時、オンの場合動画をリピート再生にします。

  • Mirror when Using Camaera
    USBカメラ使用時、オンの場合カメラからの入力がミラー状態になります。

  • Source Cut Scale
    Source Imageの画像の縦を1とした比率で入力画像を切り出します。例えば動画に映っている人が小さすぎる場合は1以上の値を指定すると拡大されます。また、爪先が画面の淵に近い場合やギリギリという場合はこの値を0.9や0.8にすると少し安定します。
    cutScale.png

  • Source Cut Center position
    Source Imageの中心を原点とし画像の縦を1とした比率で指定した位置から入力画像を切り出します。動画の右側に踊っている方がいる場合などにその位置が中心になるように調整します。下図はxの移動量に0.3を指定した場合で、上図の拡大率での見え方の差になります。画像を映しているカメラが縦比で0.3だけ右に移動したと考えてください。マイナス値にすれば左に移動し、y軸についても同様です。
    cutPos.png

  • Background Image File
    背景画像を切り替えます。画像が存在しないか、この項目が空になっているとデフォルトの画像を表示します。
    背景020.png

  • Background Scale
    背景画像の大きさを調整します。画像位置は変更できないため、位置調整は元の画像を変更して調整してください。

  • Background Color
    Source Image、Input Image、Background Imageを全て非表示にすると単色の背景になります。背景色はRGB(0~255)で指定できます。グリーンバックや背景に何も出したくない時に使用してください。
    greenback020.png

Predict

主にモーションに関する設定です。
config_predict.png

  • Low Pass Filter
    飛びやブルブルを抑える為のフィルターです。Height Qualityモデルであれば0~0.2程度が妥当です。大きくするとなめらかになりますが、遅延と動きが放漫になってきます。細かい動きが不要であれば0.3くらいでもなんとかなります。数値を変更しても処理速度には影響しません。

  • n-order LPF
    上記Low Pass Filterを何階かけるかを設定します。大きくすると効果は強くなりますが、数字に比例して効果が上がる訳ではありません。対して重い処理でもないので初めから最大の9でも良いくらいです。

  • Range Pass Filter
    上記のLow Pass Filterはブルブルする高周波成分をカットする為のフィルターです。これは特定の周波数を通すためのフィルターです。そうは言っても人のゆっくりした動きは全て採用したいので事実上ローパスフィルターとして使用します。なので下の周波数は0Hzにしたい所ですが0は指定できないので0.01Hzとしています。上の周波数は、人の動きは0.2秒くらいの動きが取れれば十分と言われているので5Hz程度で十分です(1÷0.2=5Hz)。が、デフォルト値はさらに安定を求めて3.5Hzとしています。キビキビした動きにしたい時は5Hzくらいにしておいてください。
     ・Buffer:
      データをサンプリングするバッファサイズです。変更する必要はないと思います。
      大きくすると処理は重くなります。
     ・Order N:
      フィルタの次数。実はまだあんまり評価できてないので、触らないでください。
      大きくすると処理は重くなります。
     ・Hz (from to):
      低周波の0.01は変更する必要はないです。高周波は2~5Hzくらいで調整してください。
      数値を変更しても処理速度には影響しません。

  • Forward threshold
    AIからの出力は0~1のスコアで出力されます。1が自信ありで0が自信なしです。人が画像に映っている場合は通常0.5以上のスコアになります。人が映っていないときは0~0.2程度です。この設定は人が映っていないと判断する閾値で、スコアがこの閾値以下になるとモーションが止まります。Forwardはアバターが正面を向いている時(体の向きが正面に対して±45度の範囲)の閾値です。

  • Backward threshold
    Backwardは上記のForwardの範囲外の閾値です。顔が見えていないと全体のスコアが低下するため分けて管理しています。こちらの値は低めに設定してください。

  • LockFoot
    この機能はカメラにぎりぎりつま先が入らない場合や入っても安定しない場合などにつま先の動きを固定します。カメラや動画で足が範囲ギリギリの場合はロックした方がいいです(はみ出ると正確な判定は出来ません)。つま先は動かなくてもそれほど不自然にはなりません。デフォルトでオンでも良いくらいです。
    チェックを入れた時点で足首をロックします。動かしながらロックするとおかしな位置でロックされます。通常は初期位置でロックしたいと思うので、チェック後アプリケーションを再起動してください。

  • LockLegs
    膝から下の動きをロックします。LockFootのついでに作ってみましたが使い道はあまりないと思います。

  • ElbowAxisTop
    肘の回転軸を切り替えます。例えばジャージのような肘の外側にラインがあるようなテクスチャや、内側が陰になっているようなテクスチャの場合、何も考えずに腕を曲げるとテクスチャの見え方がおかしくなります。このようなテクスチャの場合肘の回転軸を切り替える事で内側外側をそれっぽい動きになるようにしています。ですが、腕を真上に上げると肘がねじれたように動いてしまいます。これをオンにする事で通常の肘の動きに切り替わり肘が自然な感じに動きます。ですが、テクスチャの見え方はおかしな感じになります。下図を見てください。上段は肘の内側に影があるテクスチャです。オフ時には内側に影がありますが、オンの時は外側に見えます。ですが、下段のようにオフの場合は肘がねじれたように見えます。腕が肌色か単色の場合はオンにしてください。もっといい方法がありそうですが、現状はこんな感じです。
    ElbowAxisTop.png

  • Trained Model
    姿勢推定のモデルを選択します。スペックが足りている場合はHigh Qualityを選択してください。この項目を変更する場合はアプリケーションんを再起動してください。スペックが足りない場合は後述のLow Qualityモデルを使用してください。

Record

config_record.png
BVHの保存は、UnityのAsset StoreにあるBVH Toolsをそのまま使っています。Unityでデータを読み込みたい場合はこのAssetを使用するのが良いと思います。Githubはこちらのようです。オプションの説明もGithubをご覧ください。
https://github.com/emilianavt/BVHTools

  • Blender coordinate system
    Blenderへの読込、VRM Live ViewerやVMDへの変換の際にはオフで大丈夫の様です。このオプションはBlenderの座標系と一致するように変更し、Blenderで読み込んで修正した後に、またUnityで読み込むというような場合にはオンにした方が良いそうです

  • Enforce Humanoid Bones
    オンの時にはHumanoidのボーンしか保存しません。VRM Live ViewerやVMDへの変換の際にはHumanoidのボーンのみなのでオンのままにしてください。髪の毛や服などのボーンも出力に含めたい時はオフにしてください。

  • Capturing
    オンにすると指定したFPS固定でデータが保存されます。本当に指定した通りに保存されるのかは確認していません。

  • CatchUp
    これをオンに設定すると、「フレームレートが低下した場合にキャプチャフラグを使ってキャプチャを高速化し、キャプチャしたアニメーションの持続時間を正確に保つことができます。このフラグを無効にすると、キャプチャされたフレームの後に、与えられたframeRateに従って、1つのフレームが必要とするように、少なくとも多くのミリ秒が経過することを保証します。」だそうです。

Others

config_others.png

  • Use Unity Video Capture
    Unity Video Captureを有効にします。これは今表示している画面(メニューや設定画面は除く)をUSBカメラの出力とし、Zoom等の他のアプリケーションからカメラの入力として扱えるようにします(仮想カメラ)。詳細はUnity CaptureでZoomに出力を参照ください。

  • Use VMC Protocol
    VMC Protocolを使用してアバターのボーン情報と仮想トラッカーを送信します。ここはサンプルコードのままです。ブレンドシェイプは送信しません。VMC Protocolの受信もできません。まだテスト実装ですが、EVMC4Uでデータが受信できるところまでは確認しています(実はそれ以上のことはまだ理解していません)。
    vmpc_logo_128x128.png

  • IP
    VMC Protocolのサーバーが稼働しているPCのIPアドレスを指定します。通常は127.0.0.1のままで良いはずです。

  • Port
    VMC Protocolのサーバーのポート番号を指定します。通常が何番なのかはわかりませんが、たぶん39539な感じです。

  • Rot
    ThreeDPoseTrackerは180度回転した背中を向けた状態になっています。チェックを入れることで180度補正をかけます。

  • Restore Settings
    設定を初期状態に戻します。アバターの設定も初期化されます。そのままアプリケーションを終了してください。

BVHファイルについて

このアプリでは座標系が180度回転している状態になっています。正面から見て背中を向けている状態です。都合上、この方が作りやすかったのですが、少しの利点があるだけなので、ちょっと失敗したかなという気もします。とりあえずは出力後に180度回してください。

VMDへの変換

出力したBVHファイルのVMDへの変換についてですが、B-MoMi ver.0.2で変換できるところまでは確認しました。B-MoMiのダウンロードおよび詳細な使い方については下記を参照ください。
http://atupdate.web.fc2.com/

ボーンマップは下記のように設定してください。キモは左腕右腕の40と-40です。通常はプラスマイナスが逆なんですが、上にも書いた通りこのアプリの出力は背中向きになっているます。そのため、TポーズからAポーズへの補正の値を逆にしなければならないようです(たぶん)。scaleはマニュアルを参考に適時設定してください。
BVHのボーン情報はBVHファイルをテキストエディタで開くと最初のHIERARCHYの項目に載っています。必要があればそれを参考にボーンマップファイルを修正してください(B-MoMiの-makeMapオプションでもボーンの情報は取れますが完璧ではなかったです)。

boneMap_TDPT_1.txt
#
# ボーンマップ
#
# @scaleはセンターボーンの移動量を拡大縮小します
# 1.0で元データのまま。
# @scale=0.3

センター=Hips
左足=LeftUpperLeg
左ひざ=LeftLowerLeg
左足首=LeftFoot
右足=RightUpperLeg
右ひざ=RightLowerLeg
右足首=RightFoot
上半身=Chest
左肩=LeftShoulder
左腕=LeftUpperArm,0,0,40
左ひじ=LeftLowerArm
左手捩=LeftHand
右肩=RightShoulder
右腕=RightUpperArm,0,0,-40
右ひじ=RightLowerArm
右手捩=LeftHand
首=Neck
頭=Head

BVHファイルは、Blender coordinate systemをオフ、Enforce Humanoid Bonesはオンにして作成してください。保存したBVHファイルがmotion.bvh、ボーンマップファイルがboneMap_TDPT_1.txtとすると、コマンドプロンプトで下記のように実行すれば指定したBVHファイルと同名のVMDファイルが作成されます(パスは適当に直してください)。

C:\b-momi_02\b-momi>b-momi.bat -bvh motion.bvh -map boneMap_TDPT_1.txt
B-MoMi 0.2
BVH motion converter for MikuMikuDance

出力先:motion0723.vmd
BVHモデル身長=1.284616
ミク身長=15.5686
========
変換開始
========
@scale=12.11926365544256
========
変換完了 (motion.vmd)
========

あとはMikuMikuDance側で足のIKをオフにしてモーションを読み込んでください。環境によって処理速度が遅い場合は、モーションを読み込むと早回しの様になります。モーションの倍率などで調整してください(MMDあまり使った事ないので使い方が良くわかりません)。
試してみたのはここまでです。
MMD.png

最後に

アプリのリリースについての記事をQiitaに書くのもなんか違うのかなと思いつつ、Qiitaに書くのが楽なのでもうしばらくはQiitaを使わせてもらいたいと思います。
次は奥行きの移動と足付き(床の判定)を考えたいと思います。ちょっと仕組み的に難しいのでできるかどうかはわかりません。
以下は前回のコピーです。
ちなみにこのアプリのソースは下記のリポジトリにあります(準備中)。コードのライセンスはGithubに書いてあるライセンスに従ってください。姿勢推定でのお仕事もしているので全て無料とはいかないのです。機能追加して商用で使いたいという方はライセンスを購入いただくかお仕事の依頼を下さい。どうしても無料で機能追加して商用利用したいという方は、このアプリ版は無料で通すつもりなので、マージの依頼なりプルリクなりを頂ければ、そのうちアプリに追加してリリースするかも知れません(保証はしません)。

https://github.com/digital-standard/ThreeDPoseTracker

Licence

このThreeDPoseTrackerの実行ファイルについては営利・非営利問わずご自由にお使いください。この実行ファイルを使用した配信、モーションデータも同様にご自由に利用可能です。
GithubにあるソースコードについてはGithubにあるライセンスに従ってください。

免責事項

本ソフトウエアの使用に起因する、ソフトウエア、ハードウエア上の事故その他の損害、または使用できなかったことから生じる一切の損害に関して、製作者はいかなる責任も負わず、修正する義務を負いません。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Unity】任意のタイミングでanimationを発動させるやり方【animation/animator】

この記事で書かれていること

  • 通常animationから作成してanimatorも自動生成された場合、常に実行時からanimationが動きます。
  • 下図のように、animatorと組み合わせることで、スクリプトからキー押下など任意のタイミングで、一回だけanimationを動かすといったことも可能になります。
  • この記事では、そのやり方について解説していきます。
  • ↓動画解説はコチラから↓
  • 【Unity】任意のタイミングでanimationを発動させるやり方【animation/animator】

animatorで任意のタイミングでanimationを動かす.gif

手順

  1. animationの作成
  2. animatorの編集
  3. スクリプトの作成
  4. 動作確認

それぞれ以下に書いていきます。

1. animationの作成

  • 下記記事を参考にして、[Window]メニューから[animation]を追加して、任意のanimationを作成してください。
  • 【Unity】ノンコーディングでオブジェクトを動かしたい【Animation】
  • 今回のオブジェクトは、Cubeで進めていきます。 a01のコピー.png
  • animationのファイル名は「cubeanim」と設定、animatorのファイル名は「Cube」と自動生成されます。 a01のコピー2.png
  • Cubeのanimationは下図のとおりとなります。
    スクリーンショット 2020-07-21 10.03.08.png

  • 下図のように、まずはanimationが動けばokです。
    cubeanim.gif

  • また、「アニメーションは1回だけでよい」場合、
    下図のように、cubeanimのインスペクターウィンドウで、
    「Loop Time」のチェックを外します。
    スクリーンショット 2020-07-21 11.09.17.png

2. animatorの編集

  • 自動生成されたanimatorは下図の通りとなります。

  • この状態では、実行時からanimationが動くので、今回はanimatorも編集していきます。
    a01のコピー3.png

  • さて、このあとのanimatorコントローラー内にあるオレンジのブロックである「cubeanim」の編集の仕方ですが、『泥臭いやり方』と『イケてるやり方』の二種類をご紹介しますね。


①泥臭いやり方

  • まずは、自動生成された、オレンジ色の「cubeanim」をDeleteで削除します。
    スクリーンショット 2020-07-21 10.10.14.png

  • オレンジ色の「cubeanim」を削除後、
    空いている場所で[右クリック]-[Create State]-[Empty]を選択します。
    スクリーンショット 2020-07-21 10.11.27.png

  • 下図のように、オレンジ色のブロックが作成されたらokです。
    グリーンのEntryからは、必ずオレンジのブロックへ遷移するので、
    オレンジの空のブロックを作ることで、実行時にいきなりanimationが起動することを避けています。
    スクリーンショット 2020-07-21 10.11.43.png

  • Assetsの中にある「cubeanim」を、
    下図のように、Animatorコントローラーへドラッグアンドドロップします。
    スクリーンショット 2020-07-21 10.14.55.png
    スクリーンショット 2020-07-21 10.15.13.png


②イケてるやり方

スクショの都合で、「cubeanim」ではなく、「cube2anim」になっていますが、そこはスルーしてください。

  • 下図は、animationから自動生成された直後
    スクリーンショット 2020-07-21 12.31.24.png

  • 空いている場所で[右クリック]-[Create State]-[Empty]で空のブロックを作る
    スクリーンショット 2020-07-21 12.31.43.png

  • グレーの「New State」のブロックで右クリックして、「Set as Layer Default State」を選択する。
    グリーンの「Entry」の次のブロックは、「New State」にするぜ、という設定です。
    スクリーンショット 2020-07-21 12.32.09.png

  • 下図のようになったらok。
    スクリーンショット 2020-07-21 12.32.19.png


  • つづいて、オレンジのブロックから、電気のスイッチのように、 「オンになったらアニメーションする」ように、パラメーターを作ります。
  • 下図のように、「Animatorコントローラー」の中にある[Parameters]-[+]-[Bool]を選択します。 Bool型はTrueかFalseのみ返すので、今回はBool型を使用します。 よく[Layers]で追加しようとするケースがあるので、注意しましょう。 スクリーンショット 2020-07-21 10.24.49.png
  • 下図のように、適当な名前をつけます。 今回は、 「Bool型である」 「アニメーションは回転(Rotation)である」 「Boolの略としてblとする」 「Rotationの略としてRotとする」 を含めて、「blRot」と命名しました。 決して、「aaaaaaaa」とか「fvum@afwvfujiko」とか、悪い意味での適当はやめましょう。 スクリーンショット 2020-07-21 10.30.16.png
  • 今度は、オレンジの空ブロックから、ちゃんとcubeanimへ遷移するようにします。
    下図のように、オレンジのブロックで[右クリック]-[Make Transition]を選択します。
    矢印が、マウスカーソルを追っかけるので、そのままグレーのcubeanimをクリックします。
    スクリーンショット 2020-07-21 10.33.10.png

  • 下図のように矢印がつながったらok。
    スクリーンショット 2020-07-21 10.35.07.png

  • 同じように、グレーのcubeanimで[右クリック]-[Make Transition]を選択して、
    今度はオレンジのブロックをクリックします。
    下図のようにお互いが矢印でつながったらok。
    スクリーンショット 2020-07-21 10.44.18.png

  • 最後に、オレンジのブロックから、グレーのcubeanimへ、決められた条件で遷移するように設定します。
    下図のように、矢印をクリックして、インスペターウィンドウを表示させておきます。
    スクリーンショット 2020-07-21 10.46.19.png

  • 下図のように、「Conditions」の項目が「List is Empty」となっており、「何も入ってないよ!!」という状態なので、ここにBool型のパラメーターを追加してあげます。
    スクリーンショット 2020-07-21 10.46.19のコピー.png

  • 下図のように、[+]を押すと、現在設定されているパラメーターが追加されます。
    今回はこのままで問題ありません。
    スクリーンショット 2020-07-21 10.46.19のコピー2.png

    スクリーンショット 2020-07-21 10.50.03.png

  • 同様に、グレーのcubeanimから、オレンジのブロックへ戻る矢印も、
    下図のように「Conditions」を設定します。この場合は「blRot」が「false」のときに遷移するようにします。
    スクリーンショット 2020-07-21 11.14.31.png

3. スクリプトの作成

  • オブジェクトcube内にスクリプトを作ります。
    作り方(スクリプトのアタッチの仕方)は割愛します。
    スクリプト名は適当につけてください。今回の例では「cubemove」としています。

  • 下記スクリプト例のように、必要なのはたったの3行です。
    (あとはどのタイミングでanimationを動かすかなので、if文の分だけステップ数が増えます)

public class cubemove : MonoBehaviour
{
    //===== 定義領域 =====
    private Animator anim;  //Animatorをanimという変数で定義する

    //===== 初期処理 =====
    void Start()
    {
        //変数animに、Animatorコンポーネントを設定する
        anim = gameObject.GetComponent<Animator>();
    }

    //===== 主処理 =====
    void Update()
    {
        //もし、スペースキーが押されたらなら
        if (Input.GetKey(KeyCode.Space))
        {
            //Bool型のパラメーターであるblRotをTrueにする
            anim.SetBool("blRot", true);
        }
    }

4.動作確認

  • 実行すると、Spaceキー押下時に、 下図アニメーションgifのように、cubeが「一回だけ回転」します。 (gifアニメだからループしているので注意)

cubeanim動作確認.gif

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

CinemachineでBlendを待つ

概要

CinemachineでPriority切り替え時のBlendAnimationを待つ

バージョン

Unity2019.3.7f1
Cinemachine v2.6.0

Blend開始の検知

CinemachineExtensionOnTransitionFromCameraメソッドがTransition元のVirtualCameraも取得できるので
Extensionを拡張するアプローチを行った。

public class CinemachineTransitionNotify : CinemachineExtension {

    public override bool OnTransitionFromCamera(ICinemachineCamera fromCam, Vector3 worldUp, float deltaTime) {
        // ここでTransitionの開始を検知できる
        // fromCamがTransition元のVirtualCamera
    }

}

Blend終了の検知

OnTransitionFromCameraの中で自身を管理するBrainを取得し、ActiveBlendを見ることで判定できる。

// 自身を管理しているBrainを取得
CinemachineBrain brain = CinemachineCore.Instance.FindPotentialTargetBrain(VirtualCamera);
// 現在動いているActiveBlendを取得
var blend = brain.ActiveBlend;
// blend.BlendWeightが1.0になれば終了なので、AsyncやCoroutineで待機してあげる。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

CinemachineでBlendの開始終了を検知する

概要

CinemachineでPriority切り替え時のBlendAnimationの開始終了を検知する方法を探ってて
完成したので備忘録として投稿。
もっと簡単な方法があれば教えてください!

バージョン

Unity2019.3.7f1
Cinemachine v2.6.0

Blend開始の検知

CinemachineExtensionOnTransitionFromCameraメソッドがTransition元のVirtualCameraも取得できるので
Extensionを拡張するアプローチを行った。

public class CinemachineTransitionNotify : CinemachineExtension {

    public override bool OnTransitionFromCamera(ICinemachineCamera fromCam, Vector3 worldUp, float deltaTime) {
        // ここでTransitionの開始を検知できる
        // fromCamがTransition元のVirtualCamera
    }

}

Blend終了の検知

OnTransitionFromCameraの中で自身を管理するBrainを取得し、ActiveBlendを見ることで判定できる。

// 自身を管理しているBrainを取得
CinemachineBrain brain = CinemachineCore.Instance.FindPotentialTargetBrain(VirtualCamera);
// 現在動いているActiveBlendを取得
var blend = brain.ActiveBlend;
// blend.BlendWeightが1.0になれば終了なので、AsyncやCoroutineで待機してあげる。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Unity 3D入門 #6 [宝探しゲームに向けて]

今回は宝探しゲームを作ってみようと思います。

空間上に配置された5つのCubeを全て触るまでの時間を競うゲームを作ります。

ゲームとしての体裁を整えるため、することを箇条書します。
・Cubeを集める処理
・Cubeを集めた時間の測定
・再スタートボタンの追加
・キャラクターの動きの修正(現在は上下左右に動かした時、まっすぐ走ってくれない)

[Cubeを集める処理]

他のスクリプトの変数を使用する参考URL:
他のオブジェクトの関数を使用する参考URL:https://htsuda.net/archives/1702
関数の実行のタイミングを決める参考URL:https://nopitech.com/2018/07/02/post-700/

GameObject player;  // プレイヤーのゲームオブジェクト
private int get_item_num = 0;  // 現在取得したCubeの数
GameObject NoticePanel;  // Cube取得の通知パネル
public GameObject Dis;  // 残りCubeの数の表示パネル
display dis;

void Start(){
    Dis = GameObject.Find("display");
    dis = Dis.GetComponent<display>();
    player = GameObject.FindWithTag ("Player");
    NoticePanel = GameObject.Find("NoticePanel");
}

void Update(){
    Vector3 pos = player.transform.position;
    pos.y += 0.5f;  // Rayの発射場所をプレイヤーの腰あたりに調整
    Ray ray = new Ray(pos, player.transform.forward);
    RaycastHit hit;
    if (Physics.Raycast(ray, out hit, 2.0f)){
            // Itemオブジェクトに触れた時
            if (Input.GetKeyDown(KeyCode.Return) && hit.collider.gameObject.tag == "Item"){
                // まだ触っていないオブジェクトの時
                if(hit.collider.gameObject.GetComponent<Renderer>().material.color != Color.red){
                    hit.collider.gameObject.GetComponent<Renderer>().material.color = Color.red;
                    get_item_num++;  // 触ったCubeの数を上げる
                    NoticePanel.SetActive(true);  // Cube取得の通知を表示
                    Invoke("disactive", 0.5f);  // Cube取得の通知を0.5秒後に非表示
                    dis.message = "Touch Cube and press enter\nFind Cubes["+get_item_num+"/5]";  // 残りのCubeの数を修正
                }
            }
        }
    }

    void disactive(){
        NoticePanel.SetActive(false);
    }

[Cubeを集めた時間の測定]

if(get_item_num >= 5){
    dis.message = "Finish! Time:"+dis.countTime+"\npress [r] to restart";
}

Cubeを集める処理のコードのdis.messageの後に上のコードを挿入することで実装。

[再スタートボタンの追加]

シーンの再スタートの参考URL:http://negi-lab.blog.jp/archives/12908675.html

using UnityEngine.SceneManagement; 
if(get_item_num >= 5 && Input.GetKeyDown(KeyCode.R)){
    SceneManager.LoadScene (0);
}

URLを参考にして、上のコードをそれぞれ適切な場所に配置することで実装した。

[キャラクターの動きの修正]

unity-chanのUnityChanControlScriptWithRgidBody.csを修正する。

anim.SetFloat ("Speed", Mathf.Max(Mathf.Abs(h),Mathf.Abs(v)));
//anim.SetFloat ("Direction", h); 

上のようにコードを変更することで、上下左右に走ることができるようになった。
詳しくはわからないため、ここでは割愛する。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Unity 3D入門 #6 [宝探しゲーム作成]

今回は宝探しゲームを作ってみようと思います。

空間上に配置された5つのCubeを全て触るまでの時間を競うゲームを作ります。

ゲームとしての体裁を整えるため、することを箇条書します。
・Cubeを集める処理
・Cubeを集めた時間の測定
・再スタートボタンの追加
・キャラクターの動きの修正(現在は上下左右に動かした時、まっすぐ走ってくれない)

[Cubeを集める処理]

他のスクリプトの変数を使用する参考URL:https://qiita.com/tsukasa_wear_parker/items/09d4bcc5af3556b9bb3a
他のオブジェクトの関数を使用する参考URL:https://htsuda.net/archives/1702
関数の実行のタイミングを決める参考URL:https://nopitech.com/2018/07/02/post-700/

GameObject player;  // プレイヤーのゲームオブジェクト
private int get_item_num = 0;  // 現在取得したCubeの数
GameObject NoticePanel;  // Cube取得の通知パネル
public GameObject Dis;  // 残りCubeの数の表示パネル
display dis;

void Start(){
    Dis = GameObject.Find("display");
    dis = Dis.GetComponent<display>();
    player = GameObject.FindWithTag ("Player");
    NoticePanel = GameObject.Find("NoticePanel");
}

void Update(){
    Vector3 pos = player.transform.position;
    pos.y += 0.5f;  // Rayの発射場所をプレイヤーの腰あたりに調整
    Ray ray = new Ray(pos, player.transform.forward);
    RaycastHit hit;
    if (Physics.Raycast(ray, out hit, 2.0f)){
            // Itemオブジェクトに触れた時
            if (Input.GetKeyDown(KeyCode.Return) && hit.collider.gameObject.tag == "Item"){
                // まだ触っていないオブジェクトの時
                if(hit.collider.gameObject.GetComponent<Renderer>().material.color != Color.red){
                    hit.collider.gameObject.GetComponent<Renderer>().material.color = Color.red;
                    get_item_num++;  // 触ったCubeの数を上げる
                    NoticePanel.SetActive(true);  // Cube取得の通知を表示
                    Invoke("disactive", 0.5f);  // Cube取得の通知を0.5秒後に非表示
                    dis.message = "Touch Cube and press enter\nFind Cubes["+get_item_num+"/5]";  // 残りのCubeの数を修正
                }
            }
        }
    }

    void disactive(){
        NoticePanel.SetActive(false);
    }

[Cubeを集めた時間の測定]

if(get_item_num >= 5){
    dis.message = "Finish! Time:"+dis.countTime+"\npress [r] to restart";
}

Cubeを集める処理のコードのdis.messageの後に上のコードを挿入することで実装。

[再スタートボタンの追加]

シーンの再スタートの参考URL:http://negi-lab.blog.jp/archives/12908675.html

using UnityEngine.SceneManagement; 
if(get_item_num >= 5 && Input.GetKeyDown(KeyCode.R)){
    SceneManager.LoadScene (0);
}

URLを参考にして、上のコードをそれぞれ適切な場所に配置することで実装した。

[キャラクターの動きの修正]

unity-chanのUnityChanControlScriptWithRgidBody.csを修正する。

anim.SetFloat ("Speed", Mathf.Max(Mathf.Abs(h),Mathf.Abs(v)));
//anim.SetFloat ("Direction", h); 

上のようにコードを変更することで、上下左右に走ることができるようになった。
詳しくはわからないため、ここでは割愛する。

これで、ゲームらしきものが完成した。以下、今回の進捗GIF

ezgif-7-2d1ab99b47d5.gif

長すぎたので4倍速をかけてGIFのFPSも落としました。

追記:せっかくなのでunityroomにゲームをアップロードしました。
unityroomアップロード参考URL:https://qiita.com/Junichi0227/items/3498421c65b4162bed0f
ゲームURL:https://unityroom.com/games/findtreasure0720

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Unity:自分から見たターゲットの少し左(もしくは右)を狙いたい場合

3Dアクションゲームを作成していてタイトルの問題にぶち当たった。
解決策が見つかったのでここに記載。※某質問サイトで質問したら超スピードで回答を頂いた。

【実現したかったこと】
キャラクターA(自分)から見たターゲットBの座標があり、その少し左方向に狙いをつけたい、という事態に遭遇。
(作成した攻撃モーションが少し右にずれてたので狙いをつける位置自体を逆方向にずらして当たるようにしちゃえ、というぶッ飛んだ発想)
つまり以下のような状態
キャプチャ.PNG

【解決策】
ターゲットのポジション - 自分のtransform.Right * 少し(float)  でターゲットの少し左の座標を導き出せる。

var newPos = target.transform.position - (self.transform.right * 0.5f)//ずらしたい距離
 左右逆にずらしたい場合はずらしたい距離の正負を逆にしてやれば良い。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む