UV & materials

Screen-Space Distortion / Refraction

画面歪み・屈折

背景の参照位置をずらし、熱気や屈折を画面上で近似する。

8 / 10

Interactive demo

Preparing the demo…

Screen-Space Distortion / Refraction

Drag to orbit, Ctrl/⌘ + scroll to zoom. Use two fingers on touch screens.

This explanation is currently available in Japanese.

ひとことで

いったん描き終えた画面を画像として保持し、その画像を少しずらした位置から読み直して描くことで、熱気の揺らぎ(陽炎)、ガラスや水の屈折、衝撃波の歪みを表現する手法です。本当に光の屈折を計算するわけではありませんが、画面を 1 回読むだけの安いコストで、見た目にはかなり説得力のある「空気の揺らぎ」が得られます。

ゲームでの使いどころ

  • 陽炎・熱気:焚き火、ジェットエンジンの排気、砂漠の地平線、溶岩の上の空気。
  • 衝撃波:爆発やスキルの発動で、空間が輪状に押し広げられる歪み。
  • 屈折:水面越しの景色、ガラスの球や瓶、透明なバリア、透明化したキャラクターの輪郭。
  • 画面演出:ダメージを受けたときの揺らぎ、ワープ、夢や回想の場面転換。

しくみ

  1. シーン(歪ませたいものを除く)をレンダーテクスチャに描く。
  2. 画面全体(または歪みを起こす板やメッシュ)を描くとき、各画素で「どれだけずらして読むか」のオフセット Δ\Delta を計算する。
  3. c=Tscene(uv+Δ)c = T_{\text{scene}}(\mathbf{uv} + \Delta) として描く。

オフセットの作り方で表現が変わります。

表現オフセットの作り方
陽炎上へ流れるノイズ × 範囲のマスク(炎の上の縦長の領域)
衝撃波中心からの距離が輪の半径に近い画素を、放射方向へ押す
ガラス・水の屈折表面の法線(や法線マップ)の画面上の成分 × 強さ

実際のゲームでは、オフセットを描いた専用のバッファ(歪みバッファ)を用意し、パーティクルやメッシュが「ここをこれだけ歪ませたい」という値を書き込んで、最後に 1 回の全画面パスでまとめて適用する構成がよく使われます。

実装のポイント

  • 手前の物体を歪ませない:歪みを起こす物体より手前にある物体まで歪むと不自然です。深度を比較して、歪み源より手前の画素は元の位置から読むようにします。
  • 画面外参照:画面の端でオフセットすると、画面外(何も描かれていない領域)を読んでしまいます。端に近いほどオフセットを弱めます。
  • HDR のまま扱う:トーンマッピング前の明るさでずらし、最後にトーンマッピングすると、明るい光源が歪んでもにじみが自然です。

つまずきやすい点

  • 画面に無いものは写らない:屈折の向こう側に見えるべき物体が画面外や遮蔽されていると、映り込みません。これは画面空間反射と同じ、画面空間の手法共通の限界です。
  • 透明物との順序:歪みのパスより後に描いた半透明物は歪まず、前に描いたものは歪みます。どの段階で歪ませるかを決めておく必要があります。
  • 強すぎる歪み:オフセットが大きすぎると、画像がちぎれたように見えます。数ピクセル程度が自然な上限です。

デモで試すこと

  1. 焚き火の上の壁の目地が揺らいで見えるのが陽炎です。「陽炎」をオフにすると揺らぎが消えます。
  2. 「衝撃波」を押すと、床の一点から輪が広がり、背景の壁が押し広げられるように歪みます。
  3. 「ずらし量を色で表示」をオンにすると、画面のどこをどれだけずらしているかが色で見えます。

References

Unreal Engine Material Coordinates ↗

A general reference for this subcategory.