Dodatek ZWarstwa · CGPoziom · głębiejEXT OF · R.12, R.17
Dodatek Z / Głębiej

Dlaczego chmury w renderze są tak drogie

Czym różni się powierzchnia od objętości, co robi ray marching i dlaczego jedna chmura potrafi kosztować więcej niż całe miasto w tle.

Ten dodatek też jest lekki i bez wzorów. Odpowiada na jedno pytanie, które zadaje sobie każdy, kto pierwszy raz włączy render z chmurą: dlaczego cała scena liczyła się dwie minuty, a po dodaniu jednej chmury liczy się dwie godziny.
Powierzchnia kontra objętość

Skąd bierze się cała różnica

Prawie wszystko w renderze jest powierzchnią. Stół, samochód, twarz, ściana. Promień światła leci, trafia w powierzchnię — i w tym momencie jest po pytaniu. Wiadomo, gdzie się zatrzymał, i wystarczy policzyć, jak odbija się w tym jednym punkcie.

Chmura nie ma powierzchni. Promień w nią wlatuje i przez kilometr albo dziesięć leci przez ośrodek, w którym w każdym miejscu może się zdarzyć rozproszenie. Nie ma jednego punktu do policzenia. Jest cała droga.

To jest cała różnica i wynika wprost z tego, czym chmura jest. Z Rozdziału 9 wiemy, że chmura to zawiesina kropelek o średnicy około 20 mikrometrów, oddalonych od siebie o mniej więcej milimetr. W jednym metrze sześciennym jest ich rzędu stu milionów. Nikt ich nie modeluje pojedynczo — zamiast tego opisuje się je jako ciągłą gęstość, ale konsekwencja pozostaje: zdarzenie może zajść wszędzie po drodze, a nie w jednym miejscu.

Promień na powierzchni i promień w objętościile punktów do policzenia
powierzchnia — jeden punkt trafienie kończy pytanie: jedno rozproszenie, jedno sprawdzenie światła objętość — dziesiątki punktów każdy punkt to osobne pytanie o gęstość, a fioletowe strzałki to osobne pytanie o światło
Po lewej jedno trafienie. Po prawej kilkadziesiąt kroków, a przy każdym kroku dodatkowy promień w stronę Słońca — czyli kilkaset zapytań zamiast jednego. Ta różnica nie jest kwestią optymalizacji, tylko kształtu problemu.
Ray marching · jak się przez to przechodzi

Chodzenie małymi krokami zamiast trafiania

Skoro nie da się „trafić” w chmurę, renderer przez nią przechodzi. Dzieli drogę promienia na kroki i w każdym pyta o dwie rzeczy: ile tu jest kropelek i ile światła tu dociera. Pierwsze jest tanie. Drugie nie.

Żeby wiedzieć, ile światła dociera do punktu w środku chmury, trzeba wysłać z niego promień w stronę Słońca — i ten promień też przechodzi przez chmurę krok po kroku. Czyli w każdym z kilkudziesięciu kroków głównego promienia wykonujemy kilka albo kilkanaście kroków dodatkowych.

Rachunek na jeden piksel
Kroków przez chmurę: 64
W każdym kroku promień do Słońca po 8 kroków
Razem zapytań o gęstość: 64 × 9 = 576
Jedno zapytanie o gęstość to szum proceduralny: ok. 5 warstw
Operacji na piksel: rzędu 10 tysięcy
Powierzchnia w tym samym miejscu kosztowałaby kilkadziesiąt operacji. Chmura kosztuje ich kilkanaście tysięcy — i to jest szacunek dolny, bo zakłada, że światło rozprasza się w chmurze tylko raz. W rzeczywistości rozprasza się dziesiątki razy, o czym niżej.

Ten sam rachunek stoi za widgetami 3D w tej książce, tylko z ostro przyciętymi liczbami: 34 kroki zamiast 64, 3 kroki do Słońca zamiast 8, szum z 3 warstw zamiast 5. Dzięki temu chmura liczy się w kilkanaście milisekund zamiast w minutach — kosztem miękkości, której na małym obrazku i tak nie widać. To dokładnie ta wymiana, którą robi każdy silnik gry.

Rozproszenia wielokrotne

Dlaczego biel chmury jest droga

W Rozdziale 12 ustaliliśmy, dlaczego chmura jest biała: kropelki są duże w porównaniu z długością fali, więc rozpraszają wszystkie barwy jednakowo. Ale ustaliliśmy też coś, co dla renderu jest kosztowniejsze — że światło w chmurze odbija się między kropelkami wiele razy, zanim wyjdzie na zewnątrz. Kilkadziesiąt, czasem kilkaset razy. Tyle odbić jest w ogóle możliwych tylko dlatego, że kropelka wody niczego ze światła widzialnego nie pochłania (Rozdział 3): każde rozproszenie oddaje całe światło dalej. Gdyby przy każdym ginął choćby jeden procent, po kilkuset odbiciach z chmury nie wyszłoby prawie nic — tak wygląda dym z sadzą, który zamiast bieleć, szarzeje.

To właśnie te wielokrotne odbicia dają chmurze jej wygląd: miękkie przejście od jasnej góry do szarego spodu, świecące brzegi pod światło, wrażenie, że chmura jest gęsta, a nie że jest mgiełką. Renderer liczący tylko jedno rozproszenie daje chmurę, która wygląda jak brudny dym.

A koszt rośnie zabójczo. Jedno rozproszenie to jeden promień do Słońca. Dwa — to promień do Słońca z każdego punktu, w którym mogło zajść pierwsze. Trzy — to samo do potęgi. Dlatego każdy praktyczny renderer w pewnym momencie przestaje liczyć i zaczyna zgadywać: po kilku rozproszeniach resztę zastępuje przybliżeniem, które nie jest poprawne fizycznie, ale wygląda podobnie i kosztuje stałą kwotę.

Trzy poziomy uczciwości, w kolejności ceny
Jedno rozproszenie. Szybkie, używane w grach i w widgetach tej książki. Chmura wychodzi zbyt ciemna i zbyt płaska.
Kilka rozproszeń plus przybliżenie reszty. Standard w filmie. Wygląda dobrze, kosztuje minuty na klatkę.
Pełna symulacja aż do wyjścia fotonu. Poprawne, używane w nauce o klimacie. Godziny na obraz.
Warto zauważyć, że rosnąca cena kupuje tu coraz mniej wyglądu. Przejście z pierwszego poziomu na drugi zmienia obraz radykalnie; przejście z drugiego na trzeci widać głównie na wykresach. Dlatego film zatrzymał się na drugim i nie zamierza iść dalej.
Konsekwencje · co z tego wynika w praktyce

Dlaczego chmury w grach są płaskie, a w filmach powolne

W grze budżet na klatkę to kilkanaście milisekund na wszystko. Chmura wolumetryczna liczona uczciwie nie ma szans, więc gry stosują kolejne uniki: chmura renderowana w czwartej części rozdzielczości i rozmyta, wynik rozłożony na kilkanaście klatek, dalekie chmury wypalone raz i traktowane jak tło. Stąd charakterystyczne artefakty — chmury, które doganiają obrót kamery z opóźnieniem.

W filmie budżetem są godziny. Dlatego chmury filmowe wyglądają, ale sceny z nimi są w produkcji pilnowane osobno. Typowa reguła kciuka jest taka, że ujęcie z chmurą wolumetryczną kosztuje kilka razy więcej niż to samo ujęcie bez niej — i że opłaca się to sprawdzić, zanim ktoś zatwierdzi sto takich ujęć.

Jest w tym coś, co warto zabrać poza grafikę. Chmura jest droga do policzenia z tego samego powodu, dla którego jest ładna. Jej wygląd bierze się z rozproszeń, które zachodzą w całej objętości, nie na brzegu — i nie ma sposobu, żeby dostać ten wygląd, nie płacąc za tę objętość. Programy potrafią tę cenę obejść przybliżeniami, ale nie potrafią jej znieść.

I ostatnia rzecz, którą widać dopiero z tej perspektywy. Ilekroć patrzymy na zwykły Cumulus w słoneczne popołudnie, oglądamy wynik obliczenia, którego nikt nie potrafi wykonać dokładnie w rozsądnym czasie — a które atmosfera wykonuje w czasie rzeczywistym, w każdej chwili, nad całą planetą naraz.