夜風のMixedReality

xRと出会って変わった人生と出会った技術を書き残すためのGeekなHoloRangerの居場所

ガチラボでShaderGraphを使用したShader芸勉強会を開催しました。 面のアニメーション

本日はイベント登壇枠です。

10月27日20:30から熊本のxRコミュニティ[KumaMCN]のオンライン勉強会を開催しました。

今回はShaderGraphを使用してShaderAnimationを作成しています。

〇ガチラボとは?

[ガチラボ]とは熊本のxRコミュニティ[KumaMCN]で行われるガチ勢育成勉強会です。

熊本で活躍されているがち本さんが主に開催しておりましたが今回はがち本さんの弟子である筆者が主にShaderに関しての知見を共有しながら実際にオンラインワークショップを開催しました。

今回はShaderGraphを使用してより実践的な内容としてShader芸を披露、共有しました。

〇シールドシェーダー

今回は次のようなシールドシェーダーを作成しました。

f:id:Holomoto-Sumire:20211030212118g:plain

f:id:Holomoto-Sumire:20211030212259p:plain

Shaderのベースは[Unlit]のShaderGraphを使用しています。

また、[Surface]を[Transparent]に設定し、透明度(アルファ値)を扱えるようにしています。

f:id:Holomoto-Sumire:20211030213046p:plain

これはShaderGraph作成後に[Fragment]スタックを選択し、[GraphInspector]ウィンドウで設定します。

〇頂点のアニメーション

今回のシェーダーではアニメーションの機能を有しています。

f:id:Holomoto-Sumire:20211030212819g:plain

このアニメーションは[Vertex]スタックの頂点シェーダーで処理をしています。

[NormalVector]の値を[Position]ノードの結果に足し算(Add)しています。

f:id:Holomoto-Sumire:20211030213537p:plain

[Position]ノードはポジションという名前の通り座標を扱うノードです。

[Space]を[Object]にすることでゲームオブジェクトの持つ座標に合わせた座標になります。この設定ではほかにUnityのワールド座標などを取得することもできます。

f:id:Holomoto-Sumire:20211030213921p:plain

[NormalVector]ノードは法線の向きを取得するノードです。

こちらも[Space]を[Object]に設定することで3Dオブジェクトのメッシュが持つ法線の向きを取得します。 

f:id:Holomoto-Sumire:20211030214302p:plain

[NormalVector]の値を[Position]ノードの結果に足し算(Add)することでShaderがオブジェクトを描画する際に頂点が法線方向に展開されて描画されます。

f:id:Holomoto-Sumire:20211030214514p:plain

今回のShaderでは[Add]ノードで足し算する前に変数[VertexExtention(頂点押し出し)]を作成し[Multiply]ノードでつないでいることで頂点の展開する量を調整できるようにしています。

たとえば[VertexExtention]の値が0の場合[Position]ノードの出力がそのまま行われそのままの形で描画が行われますが、[VertexExtention]の値を上げることでその値に応じて面がずれて描画されます。

今回使用している3Dオブジェクトは面ごとにそれぞれメッシュを分離しているため、面ごとに押し出されます。

redhologerbera.hatenablog.com

〇面ごとに不規則にアニメーションを起こす

 頂点の押し出し機能で面が展開されるようになりましたが、ここではすべての面が一律に展開されるのではなく、面ごとにそれぞれランダムに展開されるようにします。

 これは次の処理で実現しています。

 f:id:Holomoto-Sumire:20211030215525p:plain

一つ一つ見ていきます。

まず[UV]ノードを[Posterize]ノードに私処理しています。 

f:id:Holomoto-Sumire:20211030215632p:plain

[UV]はテクスチャ画像を指し、[Posterize]ノードは[step]に指定された数で値を分割しモザイク処理を行います。

これによってUVが11分割された値を持つものとして扱われます。通常UVは0~1に滑らかに変異した値を持っていますが、ここでは11分割された領域内で同じ値を持っています。

実は今回使用している3Dモデルの持っているUVが面ごとに11分割しています。

f:id:Holomoto-Sumire:20211030220341p:plain

Shaderでは[Posterize]ノードの処理を行うことで面ごとにそれぞれの値を持てるように処理しています。

この結果を[Gradient Noise]のUVとして使用しています。

f:id:Holomoto-Sumire:20211030220527p:plain

[Scale]にはTimeノードを挟みアニメーションが行われるようにしています。

このノイズによって11分割されたUVでそれぞれランダムな0~1までの値を持つことができます。 これは面ごとに0~1のランダムな値を持っているという意味に相当します。

この結果を[VertexExtention]の出力に[Multiply]で掛け合わせ[Add]で[Position]ノードの結果と足し合わせることで面ごとにランダムに押し出されるようになります。

以上で面ごとにランダムに動くアニメーションができました。

f:id:Holomoto-Sumire:20211030220944g:plain

次回は面ごとの見た目を作成します。