2012-04-05 6 views
9

내 접선 공간 노멀 매핑 쉐이더에서 꽤 괴상한 결과를 얻고 있습니다 :). 여기서 보여지는 장면에서 찻 주전자와 바둑판 모양의 벽은 보통의 Phong-Blinn 쉐이더로 음영 처리됩니다 (분명히 찻 주전자 뒷면 커브는 가볍게 일시적인 외양과 느낌을줍니다 :-)). 나는 환각 결과, 구에 노멀 매핑에 추가하려고했습니다접선 공간 일반 매핑 - 쉐도우 온 전성 체크

Incorrect Normal Mapping on Sphere

빛이 (가) 오른쪽에서오고있다 (단지 검은 덩어리로 볼 수에 대해). 내가 구에 사용하고 정상적인지도는 다음과 같습니다 : I 입력 모델을 처리 할 AssImp을 사용하고, 그래서 나를 위해 자동으로 각 정점 탄젠트 및 양방향 법선을 계산하는 것

Normal Map

.

픽셀 및 버텍스 쉐이더는 아래와 같습니다. 나는 틀린 것이 무엇인지 잘 모르겠지만, 접선의 기본 행렬이 어떻게 든 잘못 되었다면 나에게 놀라지 않을 것이다. 저는 눈 공간으로 사물을 계산 한 다음 눈과 빛 벡터를 접선 공간으로 변형시켜야하고 이것은 올바른 방향으로 나아가 야한다고 가정합니다. 라이트 위치는 이미 뷰 공간에있는 쉐이더에 들어갑니다.

// Pixel Shader 
#version 420 

// Samplers 
uniform sampler2D Map_Normal; 

// Global Uniforms 

// Material. 
layout (std140) uniform Material 
{ 
    vec4 Material_Ambient_Colour; 
    vec4 Material_Diffuse_Colour; 
    vec4 Material_Specular_Colour; 
    vec4 Material_Emissive_Colour; 

    float Material_Shininess; 
    float Material_Strength; 
}; 

// Spotlight. 
layout (std140) uniform OmniLight 
{ 
    float Light_Intensity; 

    vec3 Light_Position;  
    vec4 Light_Ambient_Colour; 
    vec4 Light_Diffuse_Colour; 
    vec4 Light_Specular_Colour; 
}; 

// Input streams (per vertex) 
in vec3 attrib_Fragment_Normal; 
in vec3 attrib_Fragment_Position; 
in vec3 attrib_Fragment_Light; 
in vec3 attrib_Fragment_Eye; 

// Shared. 
in vec2 varying_TextureCoord; 

// Result 
out vec4 Out_Colour; 

// Main 
void main(void) 
{ 
    // Compute normals. 
    vec3 N = normalize(texture(Map_Normal, varying_TextureCoord).xyz * 2.0 - 1.0); 
    vec3 L = normalize(attrib_Fragment_Light); 
    vec3 V = normalize(attrib_Fragment_Eye); 
    vec3 R = normalize(-reflect(L, N)); 

    // Compute products. 
    float NdotL = max(0.0, dot(N, L)); 
    float RdotV = max(0.0, dot(R, V)); 

    // Compute final colours. 
    vec4 ambient = Light_Ambient_Colour * Material_Ambient_Colour; 
    vec4 diffuse = Light_Diffuse_Colour * Material_Diffuse_Colour * NdotL; 
    vec4 specular = Light_Specular_Colour * Material_Specular_Colour * (pow(RdotV, Material_Shininess) * Material_Strength); 

    // Final colour. 
    Out_Colour = ambient + diffuse + specular;  
} 

편집 : 3D 스튜디오 장면의 렌더링 (자외선의이 영역에 OK입니다 보여주기 위해) :

enter image description here

// Vertex Shader 
#version 420 

// Uniform Buffer Structures 

// Camera. 
layout (std140) uniform Camera 
{ 
    mat4 Camera_Projection; 
    mat4 Camera_View; 
}; 

// Matrices per model. 
layout (std140) uniform Model 
{ 
    mat4 Model_ViewModelSpace; 
    mat4 Model_ViewModelSpaceInverseTranspose; 
}; 

// Spotlight. 
layout (std140) uniform OmniLight 
{ 
    float Light_Intensity; 

    vec3 Light_Position;   // Already in view space. 
    vec4 Light_Ambient_Colour; 
    vec4 Light_Diffuse_Colour; 
    vec4 Light_Specular_Colour; 
}; 

// Streams (per vertex) 
layout(location = 0) in vec3 attrib_Position; 
layout(location = 1) in vec3 attrib_Normal; 
layout(location = 2) in vec3 attrib_Tangent; 
layout(location = 3) in vec3 attrib_BiNormal; 
layout(location = 4) in vec2 attrib_Texture; 

// Output streams (per vertex) 
out vec3 attrib_Fragment_Normal; 
out vec4 attrib_Fragment_Position; 
out vec3 attrib_Fragment_Light; 
out vec3 attrib_Fragment_Eye; 

// Shared. 
out vec2 varying_TextureCoord; 

// Main 
void main() 
{ 
    // Compute normal. 
    attrib_Fragment_Normal = (Model_ViewModelSpaceInverseTranspose * vec4(attrib_Normal, 0.0)).xyz; 

    // Compute position. 
    vec4 position = Model_ViewModelSpace * vec4(attrib_Position, 1.0); 

    // Generate matrix for tangent basis. 
    mat3 tangentBasis = mat3( attrib_Tangent, 
           attrib_BiNormal, 
           attrib_Normal); 

    // Light vector. 
    attrib_Fragment_Light = tangentBasis * normalize(Light_Position - position.xyz); 

    // Eye vector. 
    attrib_Fragment_Eye = tangentBasis * normalize(-position.xyz); 

    // Return position. 
    gl_Position = Camera_Projection * position; 
} 

... 그리고 픽셀 쉐이더는 다음과 같습니다

답변

3

쉐이더는 괜찮지 만 구체의 텍스처 좌표는 완전히 꺼져 있다고 생각합니다. 그것은 마치 경도를 따라 막대기쪽으로 왜곡 된 것처럼 보입니다.

+0

감사합니다. 구의 UV가 모두 정상임을 보여주기 위해 장면의 3D Studio 렌더링을 추가했습니다. 범프에도 같은 맵을 사용하고 있습니다. – Robinson

+1

평상시와 마찬가지로, 당신은 저에게 datenwolf에 대한 좋은 단서를 제공합니다. 구형을 color = (u, v, 0, 1)로 렌더링하면이 메쉬의 임포트시 UV를 올바르게 처리하지 못하거나 셰이더가 올바르게 바인딩되지 않습니다. – Robinson

+1

그것이 그랬습니다. 버텍스 쉐이더 필요 : \t varying_TextureCoord = attrib_Texture ;. 그런 멍청한 실수와 질문을 준비하는 시간 .--). – Robinson

관련 문제