ホーム < ゲームつくろー! < Shader編

その6 波:波の合成で複雑なハイトマップを作る

 その4でsin波による環状波と直進波、そしてその5でそれらの波の波頭を尖らせて性質をより波に近付けました。ここではそういう波を重ね合わせてより複雑な波を作成してみます。と言っても話は凄く単純です(^-^)



@ 波の合成は足し算

 波は足し算する事で合成されます。通常2つ以上の事象が重なり合う時には足す成分(加算成分)と合わせてお互いが重なり合った事による作用(相互作用成分)という2つの要素が必要になるのですが、波は嬉しい事に相互作用項がゼロです。つまり足すだけで合成完了になります。試しに2つの形の異なるsin波を足し算してみるとこんなグラフになります:

上がそれぞれの波で、下がそれを単純に足し合わせたものです。合成した波は柔らかい曲線を描きつつも起伏にとんでいますよね。このように複数の波を合成する事でより複雑な波を表現する事が出来ます。このように合成自体のお話は至極簡単です。寧ろ問題は「どういう波を足し合わせると水面の波のようになるのか?」という所にあります。



A 波長と波高の比率は7:1

 その4で説明したのですが、自然の波には「波長に対して波高は1/7程度の高さにしかならない」という性質があります。これは地球の重力の大きさがそうさせています。もちろん凪(なぎ)の時などはこれよりもずっと小さい波高にしかなりませんが、少なくともこれよりも大きい比率の波高を持った波を使うと違和感が大きくなってしまいます。



B 細かな波は無数の尖った環状波の集まり

 海を眺めた時に「あ〜波が迫ってるなぁ」と感じる波は「有義波」に含まれています。有義波というのは観測できる波の内大きい方から1/3位の頻度に含まれる波で、人が目で見てどう動いているか認識できる波なのだそうです。という事は、残り2/3の波は動きを認識するのが難しい程小さくランダムに見える波だと言えます。実際の海を観察してみると、


https://www.beiz.jp/download_P/sea-ocean/00047.html(一部改変

有義波と考えられる大きめの波の表面に非常に細かい波が分布しているのが見て取れます。多分これらの波は凸凹のテクスチャとしての意味合いが強く、個々の方向性についてはあまり認識できないと考えられます。

 大きな波は別に考えるとして、この小さな小さな小波は風などが吹き付けた事によってあらゆる所から発生した環状波と考える事が出来そうです。そしてよ〜く観察すると、その波高は結構尖ってます。逆光気味の写真のせいというのもありますが、波頂が良く見えますものね。とは言え、あまりに波長の小さい波はもう波としても認識出来ませんので無視して構わないです。感覚として全体のスケールに対して50分の1位の波長が意識できる最小なのかなという感じです。

 で、1/50スケールの波だけでこの小さなディテイルを再現できるかというと、それだけでは足りません。上の写真を良く見ると、最小ではないにせよ、もうちょっとだけ大きい波も無数に含まれています。これらは最小の波よりも波長が長いはずです。そして、頻度は大分下がると。ざっくりですが、波長が2倍になると、頻度は半分くらいになるのかなという感じがします。まぁこの辺りは厳密性を求めなくとも見た目重視でも良さそうな気もします。

 例として、10m四方の水面を想定し、波長が20cm〜40cm位の環状波を250個、40〜80cmの環状波を50個ランダムな位置で発生させて作った1024×1024のハイトマップ、及びそれをUnity上のプレートに適用した絵がこちらです:


 ちょっと尖った感じが出ているかなぁと思います(^-^;。表面に細かい凸凹が出来てもいます。全体的に緩やかな風が吹き続けて水面を叩いているような波になりました。ちなみにStandardスペキュラシェーダの法線マップのみ使用(FirstとSecondary両方に適用、一方のスケールを1/2に縮小)で、視差マッピングはしていません。



C 有義波は平均波長を最頻に

 波としっかり感じられる有義波は、色々なフィールド研究でその発生頻度が示されています。例えば、こちらのサイトに波の周期の頻度分布の一例がありました:

銚子沖公海観測データ
https://www.nedo.go.jp/fuusha/public/c_2_02.html

これを見ると7〜8秒の周期、つまり波長が75m〜100m位の波の頻度が高く、後は釣鐘状な頻度分布になっています。有義波の場合、小さくなる程頻度が高くなるという訳でも無いようです。ですから、明確な平均波長を定め、そこを最大頻度として、後は前後に分散させてあげると良さそうです。

 とは言え有義波程の大きさの波となると、テクスチャディテイルで表現するのには限界があります。全体スケールの1/20以上の大きさの波はジオメトリを直接起伏させる波で表現した方が無理がありません。ジオメトリレベルの波については後の章で見ていく事にします。

 有義波の合成する数は1/50スケールで設定した数よりも少なくはなりますが、余り少ないと人工的になってしまうため、最低でも8から10個、できれば20個くらいは重ねたい所です。また、有義波レベルの波は直進波を使います。これは大きなうねりのある波は非常に遠くで発生した大規模な環状波が伝わってきた物であるため、殆ど直進しているように見えるからです。


 という事で、本章では波の合成について考えてきました。ハイトマップ(法線マップ)を用いた波についてはこのく位で上のUnityの出力のようなものは出来ます。ここにさらにフレネル反射等を追加するとさらにリアルになります。が、その話は追々として、次は「ジオメトリレベルの波」について考えていきたいと思います。