2019年11月23日土曜日

3つの単位ベクトルから回転行列を作る

MotionBuilderでゲームのコントローラーを使ってドローンのような飛行シミュレーターを作成している時に勉強した備忘録で、ドローンの各軸3つの単位ベクトルから姿勢を算出

ドローンの格軸を以下の図のように、

+Z軸が正面、+Y軸が上方向、+X軸が横方向としたときに各軸の単位ベクトルを以下のように定義します。



各軸の単位ベクトルが出来たら以下のように行列を作成する


上記の行列が回転行列になるようです。

この回転行列からオイラー角を算出してあげて姿勢を求めることが出来ます。
回転行列からオイラー角を算出する方法はこちらのサイトなどを参考に。



【行列計算のメモ】
(加算後のGblRot姿勢行列)=(加算したいGblRotの姿勢行列)*(現在のGblRotの姿勢行列)
(子供のGblRot姿勢行列)=(親のGblRotの姿勢行列)*(子供のLclRotの姿勢行列)

(減算後のGblRot姿勢行列)=(減算したいGblRotの姿勢行列の逆行列)*(現在のGblRotの姿勢行列)


2019年6月10日月曜日

動画の補助線ツール

お久しぶりです。前回の更新からだいぶ日が経ってしまいました。生きてます。

映画などの映像をよく観察するとフレームの中で見せたい物や人物が綺麗にレイアウトされています。ハリウッド映画とかは大きいサイズで撮影して編集時にトリミングしてレイアウトが綺麗になるように調整しているようです。

綺麗になるように調整するというのは、いわゆる3分割線の交点や対角線に垂線を下した交点に見せたい物や人物を配置したりしている傾向があります。

どのように配置するかは、前後関係のお話の流れだったり、登場人物同士のパワーバランス、キャラクター性などなど色々な要素が絡んでくるので、パッとこの時はこれが良いと言えるには、映画などを沢山見て自分の引き出しを多くしておいたほうがいいです。

そこで映画(映像)を見てレイアウトを勉強するとき補助線を表示するツールがあったらいいなと思ったので、いつもの通り無いなら自分で作ろうの精神で作りました。



exeを実行すると、半透明なウィンドウが表示されます。
あとは右下をドラッグしてサイズを変更したり、ウィンドウ上で右クリックしてメニューを表示して操作するだけのシンプルなアプリです。

実行ファイルはこちらのリンクよりDL出来ます。

【2021/05/20追記】
・Acpect比を固定する機能追加

【2019/07/28追記】
以下の機能追加と調整を行いました。
・Windowsの機能、AeroSnapした時に移動が出来なくなる問題を修正
・2.4:1のアスペクト比(Panavision)を追加
・ウィンドウが画面の外枠に行かないよう調整
・黄金比率に分割した線を表示機能追加

2019年1月20日日曜日

スクリーン座標からワールド座標に変換

Unityのcinemachineの機能で、Aimの位置をスクリーン座標でオフセット出来る機能があり、これをMotionBuilderで実現出来ないか開発中です。その開発途中で知りえた、ワールド座標をスクリーン座標に変換する方法と、その逆でスクリーン座標をワールド座標に変換する方法を備忘録的に記しておきます。

基本的なことはYMMTWORKさんのサイトを参考にさせていただき勉強途中で躓いた箇所も含めて記載します。
ワールド座標をスクリーン座標に変換するには以下の流れです。
参考にさせていただいてるサイトではワールド座標変換もありますが、バーテックス情報を利用したい時はワールド座標変換も必要ですが、MotionBuilderで実装する時にはオブジェクトのワールド座標(グローバル座標)が取得出来るので今回は省いていきます。
で、ワールド座標にあるオブジェクトをまずはビュー(カメラ)座標変換します。これはイメージとしてカメラの子供にした時のローカルのTrans座標を算出することです。
ここで必要になってくるのは、カメラ本体Trans座標、注視点Trans座標、カメラのUpベクターTrans座標です。これら3つを使ってカメラのローカル軸を算出していきます。


ビュー座標変換

ビュー変換はカメラを原点に戻してZプラス方向に向け姿勢を戻します。その時に戻したTransやRotationも対象オブジェクトに反映します。
ようは対象オブジェクトをカメラの子供にしたときのローカル座標を算出しています。

プロジェクション座標変換

ビュー座標変換された座標を使って、プロジェクション座標変換をします。
プロジェクション座標変換は、カメラからの見た範囲を正規化した座標位置を算出するイメージです。


プロジェクション座標変換された空間のことをクリップ空間というらしいです。この空間は、-1<=X<=1、-1<=Y<=1、0<=Z<=1の範囲収まるようになります。ちなみに、Z=0のときはnear値、Z=1の時はfarの値になります。



スクリーン座標変換

プロジェクション座標変換された座標を使ってスクリーン座標変換します。

この計算結果で得られるXとYがスクリーン上の座標となります。
計算のイメージ図

参考にさせていただいてるサイトと少し違うのは、スクリーン座標の原点が画面中央にあることです。なんでかよくわからないですが(笑)、MotionBuilder上ではそれでも問題なさそうでした。


補足として、スクリーン座標からワールド座標に変換したいときは、スクリーン座標に対して、スクリーン座標変換の逆行列を掛けて、プロジェクション座標変換の逆行列を掛けて、ビュー座標変換の逆行列を掛けるという順番で計算すればワールド座標が求まります。

あと、私が行列の基本が出来ていなかったため躓いた点として、同次座標です。
座標を1つ上の次元で表現する方法で、ωの値が1になるようにx、y、zをωで割らないといけないことです。

2018年4月13日金曜日

備忘録

CGのカメラでフォーカス(ピント)をアニメーションする時、若干ズームを使うといい。

【フォーカス】
手前 → 奥  ズームアウト

奥 → 手前 ズームイン



2017年7月31日月曜日

MB Plugin STORES閉店のお知らせ

MB Plugin STORESでのMotionBuilderのプラグインの販売について諸事情により一旦終了とさせていただきます。

これまでご利用いただいてユーザー様にはご迷惑をおかけしますが何卒ご理解を賜りますようお願いいたします。

また再開できるようになりましたらご連絡をいたします。

このBlogにつきましては今後とも不定期ではありますが、記事を投稿してまいりますので引き続きよろしくお願いいたします。

2017年5月6日土曜日

【Tips】Scaleを使ったStretch&Squashの小技

Scaleを使用してStretch IKなどはネットで調べると色々なサイトで紹介されています。

Stretch&Squashを使用したカートゥーンの表現では体積を一定に保つ事が重要で、体積を一定に保たないでScaleをかけてしまうと単純に長くなったり、短くなった状態で見えてしまいます。そこでStretchやSquashさせた軸以外は縮小や拡大させて体積を保つような処理が必要です。今回はそんな体積を一定に保つ方法をご紹介です。

実はとても簡単な方法ですが、理解しやすいように1辺が1の長さの立方体を考えます。実際のセンチメートルやメートル等のような値ではなく比率で考えます。

体積を導く式は以下のように式です。


このときにStretch&Squashをかける軸を仮に高さ方向にした時、奥行の軸と横の軸の値が何になるのかを計算で導きます。仮に辺の長さを以下のようにおきます。


上記の式に各軸を当てはめると以下のような数式になります。
この時に横軸のXと奥行き軸のZは同じなので、XにZを代入します。



今回知りたいのはZの値なのでこれをZについて整理します。


さらに整理すると

ZとXは同じ値なのでXも同じです。
つまりScaleYの値がわかればX軸とZ軸には上記の式の計算結果をいれてあげればいいわけです。これをMayaで実現するにはノードエディターで以下のようにコネクションを繋げるだけです。



MotionBuilderではRelationコンストレインで以下のようなコネクションをつなげてあげれば同じ動作をします。


これをskeletonにも同じような設定をしても同じ結果が得られます。



2016年12月27日火曜日

【Review】MoitonBuilder2017 Security Fix バージョン

MotionBuilder2017がリリースされて少しだけ触ってみたところ良い点と悪い点が見えてきました。

【良い点】
・SplineIKが使用出来るようになった
・スケマティックビューで縦方向にも整列出来るようになった
・軌跡でモーションを修正できるようになった

【悪い点】
・SplineIKのRoll方向のアニメーションがPlotに対応していない
・コンストレイントをフォルダにいれるとおかしな動作をする

上記のような事がわかりました。
悪い点が作業中に重要な事なので早く直って欲しいと思っていたところ
12月5日にサービスパックではなくてセキュリティ修正バージョンとしてMotionBuilder2017 Security Fixがリリースされました。

https://knowledge.autodesk.com/ja/support/motionbuilder/downloads/caas/downloads/downloads/JPN/content/autodesk-motionbuilder-2017-security-fix.html


細かい修正内容が記載しているReadmeを読むと、

Dragging a constraint into the Navigator constraint folder duplicates the constraint
上記の悪い点のコンストレイントをフォルダにいれるとおかしな動作をするが修正されているようです。地味な事ですけど実作業しているとコンストレイントを整理する事が多々あるので嬉しいですね。

しかし、今回のMB2017の目玉機能であるSplineIKについて何も修正が入ってる様子はないので、悪い点のRoll方向のアニメーションがPlotに対応していないのは未だ修正されてないかったです。

これは結構クリティカルな問題でアニメーション作業中の物とPlot結果が違う事になります。結局はMotionBuilderのSplineIKはまだまだ実作業に耐えうるレベルにはなっていないということですね。

一応の解決策として、SplineIKで拘束されている骨を選択した状態で
1フレーム移動してキーフレームを打つ、1フレーム移動してキーフレームを打つ、という作業を繰り返せば、作業中の物と結果が一緒になります。

以下の動画はSplineIKのセットアップと一応の対応策の1フレーム移動してキーフレームを打つを繰り返す方法を示した物です。




2016年11月19日土曜日

【Tips】MotionBuilderでRotationを分解してRollの補助骨のRigging

Rollの補助骨のセットアップとして、例えば手首を回して前腕(手首と肘の間)にある補助骨を半分だけ回すということが多々あります。
その時、手首のXYZの回転値がRoll方向や縦横方向を表しているわけではないので、単純に手首のX軸値の50%だけ補助骨を追従させるという事は厳密には正確では無く、姿勢によっては予期しない結果なることがあります。

オイラー角の回転値をRoll方向、縦方向、横方向に分解するというのは既にMayaでプラグインを作成して公開している素晴らしい方がいます。
https://github.com/ryusas/maya_rotationDriver

ソースも公開されているので同じような計算をMBで作成すればいいのですが、クォータニオンを使用して高度な計算をしているので難易度がかなり高いです。

そこでMotionBuilderの標準機能だけを使用してオイラーの回転値を分解して前腕の補助骨を駆動させる方法を紹介します。

骨階層は以下の図のような階層でキャラクタライズ時の時のTスタンスの姿勢を前提としています。


まずはNULLを4つ作成して、下図のような名前と階層構造を作成します。

CHAINは下の階層のNullのTransやRotを0にするためのNull、
PANならY軸(横方向)、TILTならZ軸(縦方向)、ROLLならX軸(捻り方向)に曲がるNULLです。


そして、各PAN、TILT、ROLLのRotationOrderとMinとMaxを以下の画像のように設定していきます。



PANならY軸(横方向)、TILTならZ軸(縦方向)、ROLLならX軸(捻り方向)となっていますので各有効軸が最後にくるようにRotationOrderを変更します。
PAN(RotaionOrder XZY)
TILT(RotaionOrder XYZ)
ROLL(RotaionOrder YZX)

また、有効軸以外が動かないようにMinとMaxを設定します。

次に、4つのNull群を肘の骨(ForeArm)の子供に親子付けし、位置のみを手首(Hand)の骨に合わせます。回転は合わせません。

次に、手首の骨と各PAN、TILT、ROLLをRotationコンストレイントを作成していきます。手首の骨をSource、NullをConstrained Objectとして設定します。
設定したらSnapでコンストレイントをアクティブにします。


この状態で、手首の骨を回すとRotationの値が各成分に分解されたのが各PAN、TILT、ROLLに入る状態になります。

後は捻り方向の成分が入るROLLのNULLの値の50%だけ補助骨が追従するように下図のようにRelationコンストレイントを作成します。


これでRollの骨のRiggingは以上です。

デメリットとして階層が増えたり、手間が少しかかる事ですが、
メリットとしてはMotionBuilderの標準機能だけでRotationを捻り方向、縦方向、横方向と分解出来るという点です。

また応用次第ではMocapなどでアニメーションされた物を今回の方法でRotatioを分解してあげることで、Rotationのアニメーション編集がしやすくなる事があります。

2016年9月15日木曜日

【Tips】Motionbuilderでsoft/stretchIKのRigging

Motiobuilderでリグを組むときに基本的にはキャラクタライズしてFullBodyIK(HumanIK)を使いますが、時たま他のDCCツールと同じ様なオリジナルのリグを組む時があります。
オリジナルのリグではHumanIKで実現できない、soft/stretchIKの機能が度々使用されます。
ネットで色々調べるとSoftimage Blogでsoft/stretchIKを実現する魔法の式がありました。
今回はこの魔法の式を使用してMotionbuilderでsoft/stretchIKを実現する方法を紹介します。

まずは魔法の式からみていきます。


ネイピア数のところをプログラム的におとしこむと以下のような式になります。


dsoftを1、dchainを3にした場合をグラフにすると以下の画像のようになります。

つまり、
xが2未満のときまではy=xの式で、
xが2以上の時はy=1-exp(-(x-2))+2の式で指数関数的に減衰するようになっています。


これをMotionBuilderで実現していきます。
まずは、ChainIKを組みます。この時に、IK_HandleとIK_Ctrlを2つ用意し、ChainIKコンストレイントにはIK_Handleを登録します。



次に魔法の式の下準備として、da、dsoft、dchainを分かりやすくするために以下のようなvariableという名前でRelationコンストレイントを作成しておきます。



次にSoft_StretchIK_Solverという名前でRelationコンストレイントを作成し、魔法の式を以下のようなコネクションで作成します。variableのRelationコンストレイントはMy MacrosからD&Dで出す事が出来ます。



一番右はじのAddボックスからの出力は魔法の式で言うとこのyの値になりますがこれは根元の骨からIK_Hanleまでの距離でIK_HandleのTransになっていないので、さらに以下のようなコネクションを作成してあげて、IK_HandleのTrans値にしてあげます。




次に、魔法の式の条件で0≦x<daの時、y=xの式になるようにコネクションも作成します。





ここまでコネクションが作成出来ているとsoftIKが実現出来ています。
コネクションの全体像は以下のようになります。



次はStretch部分のRiggingです。
MotionBuilderのChainIKでは、ChainIKがONの時にコンストレインされている骨のTransやScaleを変更すると回転の計算が壊れてしまうので、Stretchさせる用のダミー骨階層を作成し、ChainIKで算出された骨からダミー骨階層へRotationコンストレイントしてあげます。


このダミー骨階層に対してStretchを仕込んでいきます。
Stretchを実現する式は以下のようになります。

上記の式のコネクションを作成します。


これでダミー骨階層でSoft/StretchIKが実現出来るようになりました。


2016年9月3日土曜日

プラグイン ユーザー様

私が作成したプラグインが細々とですがユーザー様が増えてまいりました。
プラグイン販売は個人でやっている事なので、購入を検討している方とかは不安があるかと思います。 そこでその不安を少しでも取り除けるように、これまで購入して頂いたユーザー様を紹介させて頂きます。 (ユーザー様は随時更新してい参ります。)


東映 ツークン研究所 様
日本を代表する映画制作、配給、興行会社の事業部の1つ。
パフォーマンスキャプチャーなど最先端のデジタル技術を提供。



house of moves 様
ハリウッドを代表するモーションキャプチャー会社。




ECHOES 様
少数精鋭部隊で高品質なアニメーションを制作。オリジナル作品も多数制作。



D3D様
老舗のCGプロダクション。AAA級タイトルにも多数実績としてある会社。


他、多数。

他にもご紹介できる時がきましたら随時更新してまいります。