はじめに
普段アニメーションで使っている機能・スクリプトを公開できる範囲で公開していこうと思います。
※スクリプト関係を使用して生じたトラブルや損害に関しましては作者は一切責任は負えませんので、悪しからず。
※公開しているコード関係について、独学で学んでいますので、書き方に統一感がなかったり、変数名・英語関係がめちゃくちゃだったりしますが、よろしくお願いいたします。
今回の機能・スクリプト
Mayaの Select Isolate 機能を使用した、キャラクターの表示の切り替えが素早くできるツールです。
説明
映画やカットシーンでのアニメーション作業だと画面内に背景や、複数キャラクターが登場することによって、コントローラの選択が大変になったり、アニメーションの再生が重たくなることがよくあります。
その時の方法としていろいろとあると思うのですが、思いつくものを挙げていきたいと思います。
・ディスプレイレイヤーを使用する。
・リグに用意されているモデルのON/OFF用意されているのを使用する。
・アウトライナから必要ないものを非表示にしていく。
・モデルパネルの機能 Isolate を使用する。
個人的な意見・知識になりますが、上記のメリット・デメリットを挙げていきます。
・ディスプレイレイヤーを使用する。
ディスプレイレイヤーを使用してのキャラクターの非表示では、キャラクターが増えた際に操作しないといけない回数が増えるので一時的な切り替えとしてはあまりおすすめはできないです。
また、ディスプレイレイヤーで非表示をしても内部的にはアニメーションが評価されているので、再生が軽くなることはありません。(評価方法によっては軽くなるかもしれないです。)
・リグに用意されているモデルのON/OFF用意されているのを使用する。
キャラクターの中には、コントローラにモデルの表示の切り替えを用意してくれているリグもあります。
こちらも切り替えの手間が多いのと、最適化していれば問題ないのですがシーンの再生が軽くならない場合もあるので、注意が必要です。
・アウトライナから必要ないものを非表示にしていく。
アウトライナから非表示にするとアニメーションの評価がされなくなるので(リグやコンストレインによっては評価されることもあります。)シーンの再生が軽くなります。
ですが、複雑なシーンでアウトライナを直接操作するのは意図しない操作を誘発したり、特定のキャラクター以外の非表示が手間で時間がかかったりするので、おすすめはできないです。
・モデルパネルの機能 isolate select (選択項目の分離) を使用する。
選択しているオブジェクトのみを画面に表示する機能です。
こちらは表示したいキャラクターのコントローラやメッシュを選択さえしていれば、ボタンを押すだけで使用することができます。
アニメーションの評価も画面に表示されているもののみが行われるので(リグやコンストレインによっては評価されることもあります。)、あげた例の中だと一番おすすめです。
※アニメーションの評価について、DGやParallel評価によって違ったり、Parallelの中でも細かな設定次第で変わってくるのですべてが上記の通りではないです。
コードの紹介・経緯
モデルパネルのIsolate Selectを使用するのが一番のおすすめなのですが、毎回アウトライナや画面からメッシュを選択するのはかなり手間ですよね。
アニメーションの作業の中で手間がかからずにisolateの機能を使用していきたいので、選択しているコントローラからキャラクターのみを表示できるようなスクリプトを用意しました。
from maya import cmds
from maya import mel
def isolate_mesh_selectionCurves(viewType):
hirSeparator = "|"
selectedTopNode = []
selectedObjs = cmds.ls(sl=True)
selectedShapes = cmds.ls(sl=True,s=True)
selectedTrToChild = cmds.listRelatives(cmds.ls(sl=True,tr=True))
if selectedTrToChild is not None:
selectedShapes.extend(selectedTrToChild)
targetMesh = None
hasMesh = False
for obj in selectedShapes:
chkNodeType = cmds.nodeType(obj)
if chkNodeType == "mesh":
targetMesh = selectedObjs
hasMesh = True
break
if not hasMesh:
for obj in selectedShapes:
selectedTopNode.append(cmds.ls(obj, long = True)[0].split(hirSeparator)[1])
selectedTopNode = list(set(selectedTopNode))
targetMesh = cmds.listRelatives(selectedTopNode, allDescendents = True, type="mesh", path = True)
viewObj = None
if viewType:
viewObj = targetMesh
else:
viewObj = selectedTopNode
curPanel = cmds.getPanel(wf=True)
isolateSetName = cmds.isolateSelect(curPanel,q=True,vo=True)
if selectedObjs:
if isolateSetName != "":
isolateObj = cmds.listConnections(isolateSetName,s=True,d=False,sh=True)
if set(isolateObj) == set(viewObj):
mel.eval("enableIsolateSelect %s false"%curPanel)
else:
cmds.select(viewObj,r=True)
mel.eval("enableIsolateSelect %s true"%curPanel)
else:
cmds.select(viewObj)
mel.eval("enableIsolateSelect %s true"%curPanel)
else:
mel.eval("enableIsolateSelect %s false"%curPanel)
cmds.select(selectedObjs)
今回は引数を用意することで、キャラクター全て(選択オブジェのトップノード) or メッシュのみ の2つを切り替えれるようにしました。
GIF画像ではシェルフのダブルクリックコマンドに別のパターンを用意して使用しています。
メッシュのみ
import selection_isolate
selection_isolate.isolate_mesh_selectionCurves(True)
キャラクター全て
import selection_isolate
selection_isolate.isolate_mesh_selectionCurves(False)
を実行していただければ簡単に切り替えることができると思います。
違いとしましては、一番最後の()内が True か False の違いになります。
あとは実行コマンドをホットキー(ショートカットキー)やシェルフに登録することで手軽に切り替えることができます。
※作業している環境によっては正常に動作しないかもしれないです。