Реализация рассеяния света в атмосфере

Я пытаюсь реализовать атмосферное рассеяние в openGL. Я использую эту «бумагу» в качестве учебника:
http://developer.amd.com/wordpress/media/2012/10/GDC_02_HoffmanPreetham.pdf

Однако у меня есть некоторые трудности, чтобы понять определенные моменты и выяснить некоторые константы.

В основном я должен реализовать эти формулы:
введите описание изображения здесь

Во-первых, я не знаю, является ли s расстоянием от глаза до купола или расстоянием от глаза до источника света (здесь солнце).
То же самое касается угла тета, я не могу понять, является ли это углом от земли к солнцу или к положению купола, на которое смотрит глаз.

Во-вторых, на этом слайде:
введите описание изображения здесь
Он говорит мне, что появится синий цвет неба. Я знаю, что это причина рассеяния рэлея, но есть кое-что, чего я не могу понять. Все вычисления в приведенных выше формулах дают мне скаляр: так, как белый свет солнца, который по сути является vec3 (1,1,1), станет синим, когда я умножу его на скаляры, он получится только в оттенках серого потому что я буду иметь для результата, например, vec3 (0.8,0.8,0.8). Я имею в виду, если появляется какой-то другой цвет неба, я должен умножить солнечный свет на vec3, чтобы по-другому изменить значение RGB.

Теперь я столкнулся с некоторыми трудностями при реализации моего шейдера.
Вот код для небесного шейдера:

#version 330

in vec3 vpoint;

in vec2 vtexcoord;out vec2 uv;out vec3 atmos;uniform mat4 M;

uniform mat4 V;

uniform mat4 P;mat4 MVP = P*V*M;//uniform vec3 lpos;

vec3 lpos = vec3(100,0,0);

uniform vec3 cpos;vec3 br = vec3(5.5e-6, 13.0e-6, 22.4e-6);

vec3 bm = vec3(21e-6);
float g = -0.75f;vec3 Esun = vec3(2000,2000,2000);vec3 Br(float theta){
return 3/(16*3.14) * br * (1+cos(theta)*cos(theta));

}vec3 Bm(float theta){
return 1/(4*3.14) * bm * ((1 - g)*(1 - g))/(pow(1+g*g-
2*g*cos(theta),3/2));

}vec3 atmospheric(float theta, float s){
return (Br(theta)*Bm(theta))/(br+bm) * Esun * (1- exp( -(br+bm)*s ));

}void main() {

gl_Position = MVP * vec4(vpoint, 1.0);
uv = vtexcoord;

vec3 domePos = vec3(M*vec4(vpoint,1.0));

vec3 ldir = lpos - domePos;

float s = length(domePos-cpos);
float theta = acos(dot(normalize(ldir-domePos),normalize(domePos-
cpos)*vec3(1,1,0)));

atmos = atmospheric(theta,s)*1000000*5;

}

Я не понимаю, чего ожидаю, вот что я получаю:

введите описание изображения здесь

У меня только синий, и нет красноватого заката, но солнце низкое, и, согласно разным урокам, которые я видел, я должен видеть, что красноватый цвет появляется, когда солнце садится низко.

1

Решение

Предупреждение Я не эксперт в этой области, возьми это с недоверием.

с и тэта значения
Это в значительной степени говорит обо всем.

s это расстояние между вершиной / пикселем и камерой.
θ это угол между солнцем и прямой видимости.

Чтобы вычислить θ, вам нужно знать «желтую линию» и «линию обзора».
Последний — обычная шейдерная математика; первый — просто способ выразить, как высоко на небе солнце. Вы можете смоделировать его как луч от солнца до точки на земле.


Вся формула выше дает вам векторы.
L0 это вектор.
Есолнце тоже вектор.

Слайды в основном говорят, что физические понятия, такие как светимость а также интенсивность излучения (Eсолнце) непрерывны по спектру, и следует использовать Спектральное распределение мощности описать огни и цвета.
Однако более быстрый подход состоит в том, чтобы выполнять математику только в трех точках спектра, одной для длин волн R, G и B.
На практике это говорит о том, что Есолнце является вектором, описывающим излучение солнца для трех длин волн RGB.

Голубое небо исходит из параметра βр который зависит от θ которая зависит от «линии обзора», которая зависит от высоты окрашенного фрагмента неба.

1

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]