Функция, которая будет формировать коорди наты GL_SPHERE_MAP в соответствии со спецификацией OpenGL, приведена в листинге 9.20.
Листинг 9.20. Вычисление GL_SPHERE_MAP
vee2 SphereMapCin vec3 ecPosition3. in vec3 normal) {
float m: vec3 r. u:
u - normalize(ecPosition3): r - reflect(u. normal):
m = 2.0 * sqrt(r.x * r.x + r.y * r.y + (r.z + 1.0) * Cr.z + 1.0)): return vec2 (r.x / m + 0.5. r.y / m + 0.5):
}
Функция для GL_REFLECTI0N_MAP выглядит почти так же, как предыдущая, за исключением того, что возвращает вектор отражения (листинг 9.21).
Листинг 9.21. Вычисление GL_REFLECTION_MAP
vec3 ReflectionMaptin vec3 ecPosition3, in vec3 normal) {
float NdotU, m: vec3 u:
9.7. Формирование текстурных координат
u = normalize(ecPosition3); return (reflect(u. normal)):
\
i
Выбор нужного метода формирования текстурных координат и вычисление окончательных значений показаны в листинге 9.22.
Листинг 9.22. Вычисление текстурных координат
// Вычислить координаты сферического отображения при необходимости if (TexGenSphere)
sphereMap - SphereMap(ecposition3. normal):
// Вычислить координаты отражения при необходимости If (TexGenReflection)
reflection = ReflectionMap(ecpo5ition3. normal):
/./ Вычислить текстурные координаты для каждого активного текстурного модуля for (i - 0; i < NumEnabledTextureUnits: i++)
{
If (TexGenGbject) I
gl_TexCoord[i].s = dot(gl_Vertex, gl_ObjectPlaneS[i]); gl_TexCoord[i].t - dot(gl Vertex. gl_ObjectPlaneT[i]): gl_TexCoord[i].p = dot(gl_Vertex. gl_ObjectPlaneR[i]); glTexCoordCi].q = dot(gl_Vertex. gl_ObjectPlaneQ[i]):
}
if (TexGenEye) {
gl_TexCoord[i].s = dottecPosition. gl_EyePlaneS[i]): gl_TexCoord[i].t = dottecPosition, gl_EyePlaneT[i]): gl_TexCoord[i].p = dottecPosition. gl_EyePlaneR[i]); gl_TexCoord[i].q = dotCecPosition. gl_EyePlaneQ[i]);
}
if (TexGenSphere)
gl_TexCoord[i] = vec4(sphereMap. 0.0. 1.0):
if (TexGenReflection)
gl_TexCoord[i] = vec4(reflection. 1.0):
if (TexGenNormal)
gl_Tex.Coord[i] = vec4(normal. 1.0);
)
Предполагается, что каждый текстурный модуль этого кода имеет номер меньший, чем NumEnabl edTextureUnits. Если это значение равно 0, цикл по модулям будет пропущен, В противном случае все необходимые текстурные координаты будут вычислены внутри цикла.