OpenGL4.0 shader night vision效果

先将场景渲染到FBO中,然后在Fragshader中
float dist1 = length(gl_FragCoord.xy – vec2(Width/4.0, Height/2.0));
float dist2 = length(gl_FragCoord.xy – vec2(3.0 * Width/4.0, Height/2.0));
if( dist1 > Radius && dist2 > Radius ) green = 0.0;
该像素点的屏幕坐标与左四分之一与右四分之三相比,大于预设的半径值就为黑。


To create a shader program that generates a night-vision effect, use the following steps:
1. Set up your vertex shader to pass along the position, normal, and texture coordinates
via the variables Position, Normal, and TexCoord respectively.
2. Use the following code for the fragment shader:
#version 400
in vec3 Position;
in vec3 Normal;
in vec2 TexCoord;
uniform int Width;
uniform int Height;
uniform float Radius;
uniform sampler2D RenderTex;
uniform sampler2D NoiseTex;
subroutine vec4 RenderPassType();
subroutine uniform RenderPassType RenderPass;
// Define any uniforms needed for the shading model.
layout( location = 0 ) out vec4 FragColor;
vec3 phongModel( vec3 pos, vec3 norm )
{
// Compute the Phong shading model
}
// Returns the relative luminance of the color value
float luminance( vec3 color ) {
return dot( color.rgb, vec3(0.2126, 0.7152, 0.0722) );
}
subroutine (RenderPassType)
vec4 pass1()
{
return vec4(phongModel( Position, Normal ),1.0);
}
subroutine( RenderPassType )
vec4 pass2()
{
vec4 noise = texture(NoiseTex, TexCoord);
Using Noise in Shaders
286
vec4 color = texture(RenderTex, TexCoord);
float green = luminance( color.rgb );
float dist1 = length(gl_FragCoord.xy –
vec2(Width/4.0, Height/2.0));
float dist2 = length(gl_FragCoord.xy –
vec2(3.0 * Width/4.0, Height/2.0));
if( dist1 > Radius && dist2 > Radius ) green = 0.0;
return vec4(0.0, green * clamp(noise.a + 0.25, 0.0, 1.0),
0.0 ,1.0);
}
void main()
{
// This will call either pass1() or pass2()
FragColor = RenderPass();
}
3. In the render function of your OpenGL program, use the following steps:
i. Bind to the FBO that you set up for rendering the scene to a texture.
ii. Select the pass1 subroutine function in the fragment shader via RenderPass.
iii. Render the scene.
iv. Bind to the default FBO.
v. Select the pass2 subroutine function in the fragment shader via RenderPass.
vi. Draw a single quad that fills the viewport using texture coordinates that range

from 0 to 1 in each direction.


It would make this shader even more effective if the noise varied in each frame during
animation to simulate interference that is constantly changing. We can accomplish this
roughly by modifying the texture coordinates used to access the noise texture in a timedependent
way. See the blog post mentioned in See also for an example.
See also

This recipe was inspired by a blog post by Wojciech Toman: (wtomandev.
blogspot.com/2009/09/night-vision-effect.html)

你可能感兴趣的:(OpenGL4.0 shader night vision效果)