2012-04-15 97 views
2

總之,我的全屏着色器不輸出任何東西,爲什麼OpenGL + GLSL着色器不輸出任何內容?

我正在GLSL寫一個延期着色器,我已經到了我在屏幕空間應用燈光的階段。我有一個環境通道,我基本上把GBuffer的diffuse強度寫入默認的FBO,這很好。然後,我應用另一個全屏幕四邊形來計算場景中的方向燈,再次從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)會實現這個嗎?我有一個固定的函數替代管道來測試我是否得到相同的結果,但它們略有不同。 – 2012-04-16 10:01:46

+0

@RDay:是的,那blendfunc應該做你想做的。不要忘記glEnable(GL_BLEND) – Tim 2012-04-16 17:23:04

+0

太棒了,再次感謝你! – 2012-04-16 19:15:37