チュートリアル / 読んで触ってよくわかる!Mayaを使いこなす為のAtoZ
第22回:ゲームでのスケルトン作成
- Maya
- キャラクター・リグ
- ゲーム
- コラム
- チュートリアル
- 中級者
- 学生・初心者
- 教育
- 映画・TV
いまさらですが、思い返してみるとゲーム開発者ならではの話が少ない…ということに気付いたので、今回はゲームでの話をしてみたいと思います。これからもちょくちょくゲームでのデータ作成方法を紹介して行きます。
前回はジョイントが変形に与える影響を見ました。基本的にジョイントを増やせばクオリティも上がります。が、ゲームはリアルタイム性が命です。「自然にキャラが動いているけど、処理落ちして動きがカクカクでゲームにならない!」では困ります。
(モデルに対してもっとも変形の自由度が高いようにジョイントを配置するということは、各頂点にジョイントを置くことです。つまりブレンドシェープです。これについても話ができれば面白いのですが、そのうち。)
多いジョイントは高負荷につながり「処理落ち」を誘発します。なので、なるべく少ないジョイント数できれいに見せる必要があります。
昔は無茶苦茶ジョイントを減らして、とにかく処理を速くするという感じでした。減らしすぎてデータが見にくくなることもしばしば。最近はコンピューターの性能が高いですから、あまりにジョイントを減らしすぎてデータが扱いにくくなるよりは、ほどほどな感じでジョイントを減らした方が良いです。
減らしすぎると、普通の状態に戻すのがとても大変なんですよね…。
他のアプローチ方法としては、オリジナルのデータは映画同様のジョイント数にしておいて、ゲーム用のデータとしてコンバートしたり、ゲーム実行時にゲーム用データとして最適化する、という方法もありです。なかなかそこまでの環境を用意しているところは無いと思いますが、今後は増えていくことでしょう。
あとゲームではデータをクリーンに保つことも重要です。コントローラーで上を押せば+Zに歩き出すプログラムを作ったとします。キャラクターモデルの正面がうっかり-Zを向いていれば後ろに向かって歩いてしまいます。同じようなデータは同じ仕様にそろえます。そうすればプログラマーは残業することなく帰ることができるでしょう。
というわけで、プログラマーの健康をどのように保てばいいのか、デザインで出来ることはあるのか!?見ていきたいと思います。
Maya では別にエラーが出るわけでもなく、普通にバインドできるので特に問題ないのですが、ゲームに持っていくと様々な問題を引き起こします。スケールの計算処理は思っている以上にややっこしいのです。なので1以外のスケールになっているのが発覚すると、大体プログラマーの雷が落ちます!
Softimage や 3ds Max など他の3DCGアプリケーションとデータをやり取りする場合でもそれぞれのアプリケーションでスケールの処理が異なるのでスケールは常にXYZ=1,1,1にしておくのが無難です。Maya のツールでもスケールが1以外だと正常に動かないことが多々あります。本当に厄介な部分なので注意しましょう。
スケールを入れてしまった場合、Modify > Freeze Transformationsでフリーズすればスケールがリセットされ、ジョイントの位置情報に変換されます。これで大丈夫ですが、そもそもスケールを使わないようにしておけば「うっかりフリーズし忘れた」なんてことも起きないので安心です。
また、キーフレームを打てばアニメーションは0の値を基準として始まるので、グラフエディターで複数アニメーションを表示したときに見やすくなります。下図のキーフレームを見てどう思いますか?
図のAはデフォルトでのジョイントのRotate値がバラバラな場合です。アニメーションによってどのジョイントがどれだけ回転しているのか把握しにくいですね。
BはデフォルトのRotate値が0になっているので、それぞれのジョイントがどのぐらい回転しているか一目瞭然です。これならアニメーションがつけやすいです。
さて、Rotate値0のジョイントの作り方です。ジョイントは通常のオブジェクトと異なり、内部的な、ローカルな回転情報を持っています。アトリビュートエディターを開くとJoint Orientというものがあります。
ここに数値を入れるとジョイントがRotate同様に回転しますがRotate値は0のままです。これを利用してスケルトンを構築します。
もっと手っ取り早い方法もあります。普通にRotateを使ってジョイントを回転して配置した後に、Modify > Freeze Transformationでフリーズすれば、Rotateの値がJoint Orientの値に変換されます。
Joint Orientにはマニピュレーターがありません。だからジョイントを操作するのが難しいです。普通に回転させて後でフリーズというほうがいいかもしれませんね。
ルールがあって、二つ以上兄弟がいるジョイントはTranslateXYZに値を入れてもいい、ということにします。それ以外は必ずXだけに値を入れます。人型でいえば足の付け根、肩や首あたりのジョイントはTranslateXYZに値を入れても良いです。
Xの移動だけでスケルトンが作れるの?と思われるかもしれませんが、意外とできます。以下やり方です。
Skeleton > Joint Toolでジョイントを作る時、ツールオプションのPrimary AxisをXにします。これでジョイントを作れば自然と+Xがジョイントの進行方向を向くようになり、TranslateXだけ値が入るようになります。
では位置を後から変更する時はどうするのでしょうか?
A) Joint Orientでジョイントの方向を変更し、X軸だけ動かして位置調整。
上から順に解説すると、まず横一直線にジョイントを作ります。次にJoint OrientYに-30を入れてジョイントを回転します。二本目のジョイントはTranslateXだけを操作して位置を変えます。次にまたJoint OrientYに-30入れて位置を調整します。最後もTranslateXだけ動かして位置を変えます。まあこんな風に今まではやってました。が、ところが、最近は違います!
B) Move Toolのオプションで、Automatically Orient Jointsをオンにしてジョイントを動かします。自動的にJoint Orientを調整してくれるので、結果としてTranslateXだけに値が入ります!
うっとり…すごく便利です。
こうしてジョイントの位置情報と回転情報がきれいになっていれば、アニメーションを左右反転して利用することも簡単になります。そうすれば一つのアニメーションデータで二つのアニメーションを作り出せるのです。ゲームではメモリの節約になります。
きれいなデータならジョイントやアニメーションを加工するツールも作りやすくなります。
例えば下図の様につま先の先にジョイントがあったり、頭のてっぺんにジョイントがあったりすることがありますが、これらはスキンウェイトを付ける必要がありません。なので削除してしまいます。
ゲームに出すモデルのスケルトンは「スキンウェイトが使われているジョイント」だけです。つまり「バインドしたジョイント」だけです。「アニメーションに使うジョイント」はリグに含めます。この話は追々したいと思います。
データを簡潔にすることはゲーム製作だけでなく映像製作でも役立つことです。Mayaでの処理スピードが上がれば、それだけアニメーションの作業を行いやすくなりますし、レンダリング時間も速くなります。何よりデータの管理がしやすければ、それだけ創造的な作業に注力できますから、普段からこの辺は気を付けてデータを作りたいものです。
さて次回は、うわさによると思ったより簡単だとか言っている人がいるらしい、スキンウェイトについてみていきたいと思います。
前回はジョイントが変形に与える影響を見ました。基本的にジョイントを増やせばクオリティも上がります。が、ゲームはリアルタイム性が命です。「自然にキャラが動いているけど、処理落ちして動きがカクカクでゲームにならない!」では困ります。
(モデルに対してもっとも変形の自由度が高いようにジョイントを配置するということは、各頂点にジョイントを置くことです。つまりブレンドシェープです。これについても話ができれば面白いのですが、そのうち。)
多いジョイントは高負荷につながり「処理落ち」を誘発します。なので、なるべく少ないジョイント数できれいに見せる必要があります。
昔は無茶苦茶ジョイントを減らして、とにかく処理を速くするという感じでした。減らしすぎてデータが見にくくなることもしばしば。最近はコンピューターの性能が高いですから、あまりにジョイントを減らしすぎてデータが扱いにくくなるよりは、ほどほどな感じでジョイントを減らした方が良いです。
減らしすぎると、普通の状態に戻すのがとても大変なんですよね…。
他のアプローチ方法としては、オリジナルのデータは映画同様のジョイント数にしておいて、ゲーム用のデータとしてコンバートしたり、ゲーム実行時にゲーム用データとして最適化する、という方法もありです。なかなかそこまでの環境を用意しているところは無いと思いますが、今後は増えていくことでしょう。
あとゲームではデータをクリーンに保つことも重要です。コントローラーで上を押せば+Zに歩き出すプログラムを作ったとします。キャラクターモデルの正面がうっかり-Zを向いていれば後ろに向かって歩いてしまいます。同じようなデータは同じ仕様にそろえます。そうすればプログラマーは残業することなく帰ることができるでしょう。
というわけで、プログラマーの健康をどのように保てばいいのか、デザインで出来ることはあるのか!?見ていきたいと思います。
スケールは使わない
下の図は同じスケルトンに見えますが、片方はジョイントのスケールで位置を調整し、もう一方は移動で調整しています。Maya では別にエラーが出るわけでもなく、普通にバインドできるので特に問題ないのですが、ゲームに持っていくと様々な問題を引き起こします。スケールの計算処理は思っている以上にややっこしいのです。なので1以外のスケールになっているのが発覚すると、大体プログラマーの雷が落ちます!
Softimage や 3ds Max など他の3DCGアプリケーションとデータをやり取りする場合でもそれぞれのアプリケーションでスケールの処理が異なるのでスケールは常にXYZ=1,1,1にしておくのが無難です。Maya のツールでもスケールが1以外だと正常に動かないことが多々あります。本当に厄介な部分なので注意しましょう。
スケールを入れてしまった場合、Modify > Freeze Transformationsでフリーズすればスケールがリセットされ、ジョイントの位置情報に変換されます。これで大丈夫ですが、そもそもスケールを使わないようにしておけば「うっかりフリーズし忘れた」なんてことも起きないので安心です。
Rotateの値は常に0にする
Rotate値が0になるようにジョイントを作ります。そうすればRotate値を0にすることで簡単にいつでもデフォルトのポーズに戻すことができます。また、キーフレームを打てばアニメーションは0の値を基準として始まるので、グラフエディターで複数アニメーションを表示したときに見やすくなります。下図のキーフレームを見てどう思いますか?
図のAはデフォルトでのジョイントのRotate値がバラバラな場合です。アニメーションによってどのジョイントがどれだけ回転しているのか把握しにくいですね。
BはデフォルトのRotate値が0になっているので、それぞれのジョイントがどのぐらい回転しているか一目瞭然です。これならアニメーションがつけやすいです。
さて、Rotate値0のジョイントの作り方です。ジョイントは通常のオブジェクトと異なり、内部的な、ローカルな回転情報を持っています。アトリビュートエディターを開くとJoint Orientというものがあります。
ここに数値を入れるとジョイントがRotate同様に回転しますがRotate値は0のままです。これを利用してスケルトンを構築します。
もっと手っ取り早い方法もあります。普通にRotateを使ってジョイントを回転して配置した後に、Modify > Freeze Transformationでフリーズすれば、Rotateの値がJoint Orientの値に変換されます。
Joint Orientにはマニピュレーターがありません。だからジョイントを操作するのが難しいです。普通に回転させて後でフリーズというほうがいいかもしれませんね。
余分な位置情報入れない
+X方向にのみジョイントを動かすようにします。可能な限りTranslateのYとZは0にしておきます。ルールがあって、二つ以上兄弟がいるジョイントはTranslateXYZに値を入れてもいい、ということにします。それ以外は必ずXだけに値を入れます。人型でいえば足の付け根、肩や首あたりのジョイントはTranslateXYZに値を入れても良いです。
Xの移動だけでスケルトンが作れるの?と思われるかもしれませんが、意外とできます。以下やり方です。
Skeleton > Joint Toolでジョイントを作る時、ツールオプションのPrimary AxisをXにします。これでジョイントを作れば自然と+Xがジョイントの進行方向を向くようになり、TranslateXだけ値が入るようになります。
では位置を後から変更する時はどうするのでしょうか?
A) Joint Orientでジョイントの方向を変更し、X軸だけ動かして位置調整。
上から順に解説すると、まず横一直線にジョイントを作ります。次にJoint OrientYに-30を入れてジョイントを回転します。二本目のジョイントはTranslateXだけを操作して位置を変えます。次にまたJoint OrientYに-30入れて位置を調整します。最後もTranslateXだけ動かして位置を変えます。まあこんな風に今まではやってました。が、ところが、最近は違います!
B) Move Toolのオプションで、Automatically Orient Jointsをオンにしてジョイントを動かします。自動的にJoint Orientを調整してくれるので、結果としてTranslateXだけに値が入ります!
うっとり…すごく便利です。
こうしてジョイントの位置情報と回転情報がきれいになっていれば、アニメーションを左右反転して利用することも簡単になります。そうすれば一つのアニメーションデータで二つのアニメーションを作り出せるのです。ゲームではメモリの節約になります。
きれいなデータならジョイントやアニメーションを加工するツールも作りやすくなります。
スキンウェイトを付けないジョイントは捨てる
スキニングしていないジョイント、つまりスキンウェイトを持たなくて良いジョイントは捨てて、可能な限りシンプルなスケルトンにしましょう。例えば下図の様につま先の先にジョイントがあったり、頭のてっぺんにジョイントがあったりすることがありますが、これらはスキンウェイトを付ける必要がありません。なので削除してしまいます。
ゲームに出すモデルのスケルトンは「スキンウェイトが使われているジョイント」だけです。つまり「バインドしたジョイント」だけです。「アニメーションに使うジョイント」はリグに含めます。この話は追々したいと思います。
まとめ
というわけで、若干複雑でしたがクリーンなスケルトンを作る上でのデータの仕上げ方を紹介しました。これを知っておけばゲーム業界で働く時、スケルトンの作り方で困ることは無いでしょう。データを簡潔にすることはゲーム製作だけでなく映像製作でも役立つことです。Mayaでの処理スピードが上がれば、それだけアニメーションの作業を行いやすくなりますし、レンダリング時間も速くなります。何よりデータの管理がしやすければ、それだけ創造的な作業に注力できますから、普段からこの辺は気を付けてデータを作りたいものです。
さて次回は、うわさによると思ったより簡単だとか言っている人がいるらしい、スキンウェイトについてみていきたいと思います。