2012-04-15 3 views
2

요약하면, 전체 화면 쉐이더가 아무 것도 출력하지 않습니다.왜 OpenGL + GLSL 셰이더가 아무 것도 출력하지 않습니까?

GLSL에 지연 쉐이더를 쓰고 있습니다. 화면 공간에 조명을 적용 할 무대에 도달했습니다. 나는 기본적으로 GBuffer에서 기본 FBO로 diffuse intensity를 작성하는 ambient pass를 가지고있다. 그런 다음 장면의 방향 표시등을 계산하기 위해 다른 전체 화면 쿼드를 적용합니다. 다시 GBUffer의 샘플이며 기본 FBO와 혼합되어야합니다.

내가 겪고있는 문제는 지향성 라이트 쉐이더가 아무 것도 출력하지 않는다는 것입니다. 앰비언스 패스와 동일한 매트릭스와 변환을 사용하지만 아무것도 변경되지 않습니다.

나는 다음을 시도했다;

  1. 주변 출력의 모든 조각에서 동일한 색상을 출력하여 전혀 출력하지 않도록합니다. (작동)
  2. 지향성 광선 통과의 모든 조각에서 같은 색을 출력합니다. (여전히 아무것도 얻지 못함)
  3. 정규화 된 좌표와 반대로 XY 정점 좌표에는 화면 해상도를 사용하십시오.
    • 예상대로 결과가 변경되는 것을 볼 수 있기 때문에 이것은 주위 통과에 사용할 수 있습니다.
    • 방향성 광선 통과에 아무런 변화가 없으며 동일한 출력을 얻습니다. 텍스처를 보장하기 위해 주변 셰이더 정상 또는 버퍼 위치에서 샘플링 할
  4. 변화 (작동) 여기서

어플리케이션 코드이다에서 샘플링 될 수있다;

glBindFramebuffer(GL_READ_FRAMEBUFFER, m_GeometryBuffer->m_Name); 
glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0); 
glDrawBuffers(1,draw_buffers); 
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 

m_AmbientShader->Begin(); 
    m_AmbientShader->SetUniformInt1("Diffuse",m_DiffuseTexture->m_TextureUnit); 
    // Draw full screen quad 
    glBegin(GL_QUADS); 
     glMultiTexCoord2i(GL_TEXTURE0,0,0); 
     glVertex2i(-1,-1); 
     glMultiTexCoord2i(GL_TEXTURE0,1,0); 
     glVertex2i(1,-1); 
     glMultiTexCoord2i(GL_TEXTURE0,1,1); 
     glVertex2i(1,1); 
     glMultiTexCoord2i(GL_TEXTURE0,0,1); 
     glVertex2i(-1,1); 
    glEnd(); 
m_AmbientShader->End(); 

const DirectionalLight& dl = scene.GetDirectionalLight(); 

glDrawBuffers(1, draw_buffers); 
m_DirectionalLightShader->Begin(); 
m_DirectionalLightShader->SetUniformInt1("Diffuse",m_DiffuseTexture->m_TextureUnit); 
m_DirectionalLightShader->SetUniformInt1("Position",m_PositionTexture->m_TextureUnit); 
m_DirectionalLightShader->SetUniformInt1("Normal",m_NormalTexture->m_TextureUnit); 
m_DirectionalLightShader->SetUniformFloat3("LightDir",dl.GetDirection()); 
m_DirectionalLightShader->SetUniformFloat3("LightAmb",dl.GetAmb()); 
m_DirectionalLightShader->SetUniformFloat3("LightDiff",dl.GetDiff()); 
m_DirectionalLightShader->SetUniformFloat3("LightSpec",dl.GetSpec()); 
m_DirectionalLightShader->SetUniformFloat3("LightAtt",dl.GetAtt()); 
m_DirectionalLightShader->SetUniformFloat1("LightIntensity",dl.GetIntensity()); 
    // Draw full screen quad 
    glBegin(GL_QUADS); 
     glMultiTexCoord2i(GL_TEXTURE0,0,0); 
     glVertex2i(-1,-1); 
     glMultiTexCoord2i(GL_TEXTURE0,1,0); 
     glVertex2i(1,-1); 
     glMultiTexCoord2i(GL_TEXTURE0,1,1); 
     glVertex2i(1,1); 
     glMultiTexCoord2i(GL_TEXTURE0,0,1); 
     glVertex2i(-1,1); 
    glEnd(); 
m_DirectionalLightShader->End(); 

내 수학이 잘못된 경우에 저를 용서하십시오, 나는 시도하고 출력의 어떤 종류를 얻을 수 있지만, 여기 쉐이더 소스 파일이하는 쉐이더와 장난되었다;

< - directional_light.vert ->

varying out vec2 ScreenPos; 

varying out vec3 VSLightDir; 

uniform vec3 LightDir; 
uniform vec3 LightAmb; 
uniform vec3 LightDiff; 
uniform vec3 LightSpec; 
uniform float LightIntensity; 

void main() 
{ 
    gl_Position = gl_Vertex; 
    ScreenPos = gl_MultiTexCoord0.st; 
    VSLightDir = normalize((gl_ModelViewMatrix * vec4(LightDir,0.0)).xyz); 
} 

< - directional_light.frag ->

// Gbuffer textures 
uniform sampler2D Diffuse; 
uniform sampler2D Position; 
uniform sampler2D Normal; 

in vec2 ScreenPos; 
uniform vec3 LightDir; 
uniform vec3 LightAmb; 
uniform vec3 LightDiff; 
uniform vec3 LightSpec; 
uniform float LightIntensity; 

in vec3 VSLightDir; 
out vec4 OutColour; 

void main() 
{ 
    // Sample from the GBuffer 
    vec4 Diffuse = texture2D(Diffuse, ScreenPos); 
    vec4 VSPos = texture2D(Position, ScreenPos); 
    vec4 MRT2 = texture2D(Normal, ScreenPos); 
    vec3 VSNormal = normalize(MRT2.xyz); 
    float Shininess = MRT2.w; 

    float LDotN = dot(VSNormal, VSLightDir); 

    vec3 View = -normalize(VSPos.xyz); 

    // Compute ambient contribution 
    vec3 ambient = LightIntensity * LightAmb * Diffuse.xyz; 

    // Compute diffuse contribution 
    vec3 diffuse = LightIntensity * LightDiff * Diffuse.xyz * max(0.0, LDotN); 

    // Compute specular contribution 
    vec3 HalfWay = normalize(LightDir + View); 
    vec3 specular = (LDotN <= 0.0) 
       ? vec3(0.0) 
       : LightIntensity * LightSpec * Diffuse.xyz * pow(max(0.0, dot(VSNormal,HalfWay)), Shininess); 

    OutColour = vec4(ambient + diffuse + specular, Diffuse.a); 
    //OutColour = vec4(0.0,0.0,1.0,1.0); //Debug line 
} 

< - ambient.vert ->

varying out vec2 ScreenPos; 

void main() 
{ 
    gl_Position = gl_Vertex; 

    // Used for the position to sample from GBuffer 
    ScreenPos = gl_MultiTexCoord0.st; 
} 

< - ambient.frag ->

// Gbuffer textures 
uniform sampler2D Diffuse; 

in vec2 ScreenPos; 

out vec4 OutColour; 

void main() 
{ 
    OutColour = texture2D(Diffuse, ScreenPos); 
    //OutColour = vec4(0.0,0.0,1.0,1.0); 
} 

답변

3

깊이 테스트를 사용하도록 설정 했습니까? 깊이 버퍼를 지우고있는 것 같아서 어쩌면 의심 스럽지만 두 번째 텍스처를 첫 번째 텍스처와 정확히 같은 깊이로 그립니다. glDepthFunc 기본값이 GL_LESS 인 경우 두 번째 끌기가 완전히 거부 될 수 있습니다.

그렇지 않으면 어떻게 두 무승부를 결합하고 싶습니까? 몇 가지 혼합이 있어야합니까?

+0

답장을 보내 주셔서 감사합니다. 깊이 테스트를 사용 중지 했으므로 제대로 작동합니다.나는 그것들을 빛의 공헌으로 혼합하여 포화 상태에 이르기까지 추가하려고합니다. glBlendFunc (GL_ONE, GL_ONE) 달성 할 것인가? 나는 동일한 결과를 얻고 있는지 테스트하기 위해 고정 함수 대체 파이프 라인을 가지고 있지만 약간 다르다. –

+0

@RDay : 그래, 그 blendfunc 당신이 원하는대로해야합니다. glEnable (GL_BLEND)을 잊지 마세요. – Tim

+0

굉장, 다시 한번 감사드립니다! –

관련 문제