超簡単な炎シェーダーを実装してみた。
今更ですが、「Shade」というiOSのシェーダー作成アプリケーションを使用して超簡単な炎を作ってみました。「Shade」というアプリケーションにはHLSLまたはGLSLのdiscardとか、lerp(mix)という関数の機能を提供してくれるノードがないため、ちょっと余計に複雑になりました。ですけどノイズマップとグラデーションを使用して類似乱数みたいな表現が出来たという基本的なテクニックは様々なところに使えそうだから良いですね。
Shadeを使用した実装
ノイズマップを使用した炎は以下の順番で実装が出来ます。
- ノイズマップと、グラデーションマップを準備。炎が上に燃え立つよう、ノイズモップのUVの
V部分は上へ移動するように。 - ノイズマップを基準として(
y)、step関数を行う。値が0か1へと分かれる。 - 色を付けることで一番簡単な炎が出来上がる。
- ノイズマップの値を上げることで、
step以後の炎の分布はどんどん下へとさがる。これを利用して段階的に色をつけて、lerp(線形補間)かsmoothstepで炎にグラデーションをつけることも可能。 - 炎ではない部分は
discardで着色を取り消す。(Shadeアプリではdiscardがない為、単に黒い色に。)
具体的な実装手順

スクリーンスペースのScaledされた座標をUVとして扱います。しかしノイズマップを上へ移動させるため、Timeノードから(秒単位で値を返す)少数部分を取り出し、Vへ足すことでノイズマップを縦移動させます。

Stepを使用してノイズの一部分を取り、そして引き算をさせることで赤、オレンジ、そして黄色になる部分を取り出します。Subtract One Minus Subtract順に赤色、黄色、オレンジ色の配置となります。

線形補間を使用して色を付けます。まずは、赤色と黄色を付けてから、そして混合したものをまたオレンジ色と線形補間をして最終的に混合させます。

Shadeアプリケーションではdiscardノードがないため、炎ではない部分をただの黒に塗り替えてから色を表示させます。

これで3段階で色がある炎が実装できました。もっと複雑な模様で炎を出すためには、マスクマップを使用してマクスされていない部分を取り除けば良くなりそうと思います。