10.4.2. Вершинный шейдер

В листинге 10.5 показан вершинный шейдер, который используется для наложения карты среды.

Шейдеры с сохранением данных в текстурах

Листинг 10.5. Вершинный шейдер для наложения карты среды

varying vec3 Normal: varying vec3 EyeDir: varying float Lightlntensity:
uniform vec3 LightPos:
void main(void) {
gl_Position - ftransformO:
Normal = nonnalize(g1_NormalMatrix * gl_Normal):
vec4 pos = g'ljModelViewMatrix * glj/ertex:
EyeDir = pos.xyz:
Lightlntensity = max(dot(normalize(LightPos - EyeDir). Normal). 0.0):
)

Цель данного вершинного шейдера - получить три значения, которые будут интерполироваться для каждого примитива: значения рассеянного освещения, нормали поверхности и направление обзора. Два последних значения позволяют вычислить точное направление отражения для каждого фрагмента, а отсюда можно вычислить требуемые углы возвышенности и азимута.

Преобразованные координаты вершины вычисляются в первой строке программы обычным способом: преобразуется и нормализуется нормаль, затем с помощью текущей матрицы модели-вида и входных значений для вершины вычисляется направление обзора. Эти два значения потом будут использоваться во фрагментном шейдере, чтобы определить вектор отражения. И наконец, вычисляется значение рассеянного освещения таким же способом, как и в предыдущих примерах.

В листинге 10.6 показан фрагментный шейдер, который используется для наложения карты среды.

Листинг 10.6. Фрагментный шейдер для наложения карты среды

const vec3 Xunitvec = vec3 (1.0. 0.0. O.D): const vec3 Yunitvec = vec3 (0.0. 1.0, 0.0):
uniform vec3 BaseColor; uniform float MixRatio:
uniform sampler2D EnvMap: // = 4
varying vec3 Normal; varying vec3 EyeDir: varying float Lightlntensity:
void main (void)

10.4.3. Фрагментный шейдер

// Вычислить вектор отражения

vec3 reflectDir = ref1ect(EyeDiг. Normal):

// Вычислить углы возвышенности и азимута

10.4. Пример наложения карты среды

vec2 index:

index.у = dot(normalize(reflectDiг). Yunitvec); reflectDir.y =0.0:


⇐ Предыдущая| |Следующая ⇒