世界を動かす技術を、日本語で。

空、夕焼け、惑星の描写

概要

  • スペースシャトル Endeavour の夕焼け写真を再現するシェーダー開発の記録
  • 大気散乱 の物理現象とそのシミュレーション手法の解説
  • Rayleigh散乱・Mie散乱・オゾン吸収 の実装方法を紹介
  • リアルな空の描画 を目指し、ゲームやWebでの応用を意識
  • 最適化として LUTベースの手法 にも挑戦

スペースシャトルEndeavourの夕焼け写真と大気散乱現象

  • インスピレーション元は Endeavour の写真、地球の大気層が美しいグラデーションを描く
  • この色彩の正体は 大気散乱 現象
  • 大気散乱 は空の色や夕焼け、朝焼けの原因となる物理現象
  • ゲームやWebで 現実的な空 を描画するための基礎知識
  • 背景に単純な青グラデーションを使っても リアルさ は再現できない

大気シェーダーの実装方針

  • 空の色を ボリュームとして扱う ことが重要
  • 観測者の高度、塵、時刻 など複数の変数を考慮
  • レイマーチング による大気サンプリング手法
    • カメラからシーンへレイを飛ばし、透明な大気を段階的に評価
    • 光の減衰(透過率:Transmittance)散乱光 の2つを計算
  • Rayleigh密度関数 で高度ごとの大気密度をモデル化
    • 高度が上がるほど大気が薄くなる

光の減衰とRayleigh散乱

  • 光の減衰(透過率T) は光が大気を通過する際の減衰度合い
    • Beer's Law で計算
  • Rayleigh散乱 は分子サイズの粒子による散乱
    • 短波長(青)が強く散乱され、昼間の空が青く見える原因
  • Rayleigh位相関数 で太陽光と視線の角度による散乱方向性を計算
  • フラグメントシェーダーでピクセルごとにこれらを実装

Mie散乱とオゾン吸収の追加

  • Mie散乱 :大きな粒子(塵・エアロゾル)による散乱
    • 太陽付近の霞や夕焼けの赤みを再現
    • 独自の密度・位相関数でモデル化
  • オゾン吸収 :オゾン層による特定波長の吸収
    • 空の色合いの変化や夕焼け時の深みを表現
    • 散乱はせず、光の一部を吸収するのみ

光源方向の減衰(ライトマーチ)

  • カメラ→サンプル点 の減衰だけでなく、 太陽→サンプル点 の減衰も考慮
  • 各サンプル点から太陽方向へもレイマーチし、追加の光減衰を計算
  • これにより、 夕焼け・朝焼けの赤み光の減衰 がリアルに表現可能

LUTベースの高速化手法

  • Sebastian Hillaire のLUT(Look-Up Table)ベース手法を参考に最適化
  • 事前計算したテーブルを使い、リアルタイム描画時の計算負荷を大幅削減
  • ゲームやWebGLでの実用的な大気表現を実現

まとめ

  • 大気散乱のシミュレーション はリアルな空の描画に不可欠
  • Rayleigh・Mie散乱、オゾン吸収 を組み合わせることで自然な色彩を再現
  • レイマーチングLUT最適化 が現実的な描画とパフォーマンス両立の鍵
  • Webやゲームでの インタラクティブな体験 にも応用可能
  • Artemis IIミッション など宇宙への興味をきっかけに、技術と科学の融合を体感

Hackerたちの意見

すごい!これはかなりの体験だった。多分5%くらいしか理解できなかったけど、めっちゃ感動したよ。

同じく。ビジュアルだけでも読む価値があったよ。

これがペレスのオールウェザーやプリースサムの空モデルとどう関係してるのか気になるな。専門家じゃないけど、過去にそれを実装したことがあって、結構楽しいプロジェクトだったよ! https://github.com/jscanvic/SkySim

SpaceEngineもこれにかなり力を入れてることで知られてるよ。めっちゃおすすめ!: https://www.youtube.com/watch?v=_4TjdVAbXks https://spaceengine.org/

これは素晴らしいソフトウェアで、何年も前からあって、細部にまでこだわりがある。この記事もそれを思い出させてくれた!

すごく素敵な個人ウェブサイトだね、いい投稿だ!超クールなコンテンツ!

同意!このブログはめっちゃ美しいね。自分のブログもいつかリデザインしたくなる(デザインはあんまり得意じゃないけど)。

ちょっと前にこれを見たから、完全に関連してるわけじゃないかもしれないけど、セバスチャン・ラグが彼の惑星生成実験のために大気についての動画を作ってて、それもすごく面白かったよ[1]。ビジュアルを開発して、それが現実になるのを見るのは特に楽しいよね。いつかこの分野で実験できるといいな。[1] https://www.youtube.com/watch?v=DxfEbulyFcY

セバスチャン・ラグのすごいところは、YouTubeのアルゴリズムがどれだけ影響するかってことだね。彼の動画は昔は何百万回も再生されてたのに、今はやっと50万回くらい。まあ、コロナの影響もあるかもしれないし、みんな家にいてランダムなことに興味を持つようになったからかも。

これは本当に素晴らしい。前に、ウェブ上で空を重ねたグラデーションのシリーズとしてレンダリングしようと考えたことがあるんだけど、ある程度の成功は収められたかもしれないけど、あなたが作ったものには到底及ばないよ。本当にありがとう、これを共有してくれて。インスピレーションを受けたし、まとめるのにすごく時間がかかったんだろうね。あなたの成果に驚かされてるよ。

一度、自分の趣味でゲームエンジンにレイリー散乱とミー散乱を実装したことがあるんだ。それだけでかなりいい夕日や朝日サイクルが見れたのがすごかった。確か、太陽自体もなんか出てきた気がする。XNA(マイクロソフトのC#ゲーム開発プラットフォーム)を使って、ライマーの素晴らしいチュートリアルシリーズを参考にしてたんだけど、散乱については何も書いてなかったかも。数学の論文を読んだ記憶はあるな。[0] https://github.com/SimonDarksideJ/XNAGameStudio/wiki/Riemers...

これめっちゃ綺麗だね。グラフィックハック(重ねたグラデーションとか)じゃなくて、物理モデルに基づいたものが好きなんだ。

大好き!これはウェブで見た大気レンダリングの説明の中で一番良いものの一つだね。

散乱はリアルなレンダリング画像を作るのにずっと重要な要素だよね。お気に入りの論文の一つはこれだよ:http://www.graphics.stanford.edu/papers/bssrdf/bssrdf.pdf これでミルクのレンダリングが難しい問題だって初めて知った気がする。

これ、俺の興味にめっちゃ関連してる!暇な時にプラネタリウム/星図アプリ(iOS / Vision Pro)を作ってて、大気散乱はずっとやりたかったことなんだ。雰囲気的には俺が目指してるものを超えてるけど、見るのは本当にすごい!マキシム、このまとめありがとう!