Houdiniのforループを理解する

■ループの種類と用途

  1. forループ
    入力したジオメトリデータ全体を対象に、複数回の処理を繰り返し行う

    (例)
    Copy SOPで複製されたジオメトリ全体を対象に、Mountain SOPの処理を累積的に10回行う。

  2. for-eachループ
    入力したジオメトリ内の個別のピースに対し、同一の処理を行う

    (例)
    複数のグループを複数含むジオメトリデータから、特定のルールにマッチするグループを1つずつ個別に取得し、個別にバウンディングボックスに置き換える。

  3. Fetch FeedbackとFetch Pieceの組み合わせ
    ループに入力されたジオメトリに対し、別の入力されたジオメトリのピースを使って反復的かつ累積的に処理を行う事ができる。

    (例)
    穴あきチーズ
    複数の気泡オブジェクトを入力し、気泡オブジェクトのピースごとに、チーズの本体に累積的に繰り返し削り取る。


■forループ

Tab -> For loop

オレンジ色に囲まれた部分がforループのブロック

MountainSOPを挿入しHeightを0.1に変更
Block EndのIterationパラメータを変化させると、各ボックスが累積的に変形することが確認できる。

※同じ設定のMountainSOPで同一の処理を累積的に10回繰り返すことと同じなので、CopySOPの下流にMountainSOPを10個作って直列で繋げても同じ結果が得られます。


■for-eachループ

Tab -> For-Each loop

ピース単位の処理。
ピースは、ピースを表現するアトリビュート(通例では@name)の値の同一性により表現される。

For-Each loopを作成した直後は、上流に@pieceや@nameがないためにエラーが出る場合がある。このような場合は、自分でアトリビュートを作成する。

Voronoi Fracture SOPなど、自動的に@nameを作るSOPもある。
Voronoi Fracture SOPのデフォルト設定では、破片ごとにPrimitiveクラスの@nameを作成し、piece+番号の命名規則で各Primitiveが所属するピースを表現する。

@name以外のアトリビュートを使用してピースを表現したい場合は、Block End SOPのPiece Attributeを変更し、任意のアトリビュート名を指定する。

CopySOPで複製したBoxをVoronoi Fracture SOPで分割

For-Each loopにより、各破片のピースをバウンディングボックスに置き換え


■Block Begin SOP

・Methodパラメータ

  1. Fetch Feedback
    累積的に処理を行う場合に選択。
    ループが行われる度、前回のループで出力された結果を現在の処理対象としてフィードバックし、再Fetchする。
  2. Fetch Piece
    入力されたジオメトリ内のピースごとに処理を行う場合に選択。
    ループ毎に、認識されているピースの中から新たなピースがFetchされる。
  3. Fetch Metadata
    現在のループに関する情報をDetailsアトリビュートに持つジオメトリを作成する。
    detail関数を使ってこれらの値へアクセスし、ループ内で使用することができる。

・Block Pathパラメータ

このループの終点を示すBlock End SOPへのパス

・Create Meta Import Node

Metaデータを持つBlock Begin SOPを作成する。
この実態は、ModeがFetch Metadataに設定され、Block Pathが現在のループの終点にセットされているBlock Begin SOP。


■Block End SOP

・Gather Method

  1. Fetch Each Iteration
    ループが終わるたびに結果を再Fetchする
    ループのBlock Begin SOPでMethodがFetch Feedbackの場合に使用する。
  2. Merge Each Iteration
    ループ毎にジオメトリを記録し、最後に結合する。
    ループのBlock Begin SOPでMethodがFetch Pieceの場合に使用する。
    ピースは個別に処理され最後に結合され、結果として出力される。

・Iterations/StartValue/Increment

ループ回数の指定
一般的なforループで使用する変数

・Python風に書くならこんな感じ
for i in range(startValue , iterations , increment):


■Block Begin SOP – Fetch Feedback と Fetch Pieceの組み合わせ

あるジオメトリに対し、別のジオメトリを使って複数回の処理を累積的に行う事ができる。
Block BeginのヘルプにあるSwiss Cheeseサンプルでは、チーズ本体のVDBオブジェクトを一つと、気泡のVDBオブジェクトを複数入力し、チーズ本体オブジェクトを気泡オブジェクトごとに削り取る処理を行う。

  1. チーズ本体のジオメトリを作成
  2. 気泡ジオメトリを作成
    SphereSOPをPolygonなどではなくPrimitiveモードで作成。
  3. Scatter SOP + Copy SOPでチーズ表面に気泡をばらまく
  4. For loopを作成
  5. チーズ本体を受け取るBlock Begin SOPの設定を確認
    Methodパラメータ:Fetch Feedback
    Block Pathパラメータ : Block Endへのパス
  6. 気泡を受け取るBlock Begin SOPを追加
    Block Begin SOPを作成後、以下のパラメータをセット。
    Methodパラメータ : Fetch Piece
    Block Pathパラメータ : 1で作ったBlock Endへのパスをセット
  7. Block End SOPを確認
    Iteration Method:By Pieces(またはAuto Detect from Inputs)
    Gather Method:Feedback Each Iteration
    Piece Elements:Primitive
    Piece Name:オフ
    Default Block Path/Piece Block Path:Block Begin

 


■Block Begin SOP – Fetch Metadataの使い方

  1. Block Begin SOPを作成
    Method:Fetch Metadata
    Block Path:末端のBlock End SOPへのパス

・Detailsアトリビュート

  • numiterations
    最大のループ回数
  • iteration
    現在のループ回数
  • value
    Pieceループ時、現在ループ中のピースを識別するためのアトリビュート値。
  • ivalue
    valueの整数版。
    valueがfloatの精度範囲を超える場合などに使う。
    特別な理由がなければ普段はこっちを使うのがよさそう

・Metadataを取得する

ループ内でdetailエクスプレッション関数を使う。

  1. detailエクスプレッション関数を使う
    detail(“../foreach_begin1_metadata”, “iteration”, 0)
  2. detail VEX関数を使う
  3. Import detail attribute VOPを使う
  4. Pythonで取得する
    node(“../foreach_begin1_metadata”).geometry().attribValue(“iteration”)

■ループの停止条件

Block End SOP の Stop Condition を1にセットすると強制的にループを終了できる。


■デバッグとテストループ

・Feedbackループの場合

Block End SOP の Max Iterationsパラメータで最大ループ数を設定できる。
数回のループだけである程度結果が判断できる場合は、このパラメータを有効化することでループ処理を制限し、素早く調整が行えるので便利。

・Pieceループの場合

Block End SOP の Single Passパラメータでピース番号を指定して、ピースごとの処理結果を確認できる。


■グループからピースを作成する

グループパラメータを使ってピースを作成したい場合は、Name SOPを使用して@nameを作成し、グループ名をセットしておく。


何か間違いがあれば突っ込んでいただけると嬉しいです

コメントを残す