Reputation: 961
I have a deferred rendering particle system and Im trying to improve the generation of the billboard's normals for the normal map pass. Currently I render the billboard normals as a forward facing Z. When the light render passes draw the scene, they interact with the billboards moreso when the BB is facing the light (as expected).
Here is what the normal pass looks like:
This works as expected... however I would like to better simulate a kind of volume effect on the particles. I want to treat each billboard as if though its more sphere like. My thinking is that the lighting interactions with the particles would be better as a sphere has a wider range of normal directions. I.e. Id like to mimic something like this (The white border would be a single billboard):
Is this a good idea? I don't really know how to go about doing it.
EDIT
I am using points for the rendering, and my current thinking is something like this:
normal.x = gl_PointCoord.x;
normal.y = gl_PointCoord.y;
normal.z = 1.0;
But the gl_PointCoord doesnt seem to be producing the effect i thought it does. Screenshot below:
EDIT 2
Hi guys, I still seem to be having problems. The GLSL I am using now is as follows:
vec3 normal = vec3( gl_PointCoord.x * 2.0 - 1.0, 1.0 - gl_PointCoord.y * 2.0 , length(gl_PointCoord.xy) );
normal = normalize( normal );
But it still doesnt seem 100%. For most cases it seems to work well. However you can see a problem when I use a directional light which faces the billboards.
Its as if though the lower left blue normals are not right. If you look at the regular sphere normals the lower left blue fades into black (indicating the lack of z power). I think this is still what's missing. Any ideas?
EDIT 3
Figured out what was wrong. During my normal pass I forgot to properly encode the normal and then decode it later.
// Encoding pass
vec3 normal = vec3( gl_PointCoord.x * 4.0 - 2.0, 2.0 - gl_PointCoord.y * 4.0, 1.0 );
normal = normalize( normal );
normal = normal * 0.5 + 0.5;
// Decoding pass
vec3 normal = texture2D( normalMap, vUv ).xyz;
normal = normal.xyz * 2.0 - 1.0;
Upvotes: 0
Views: 1429
Reputation: 43842
The reason your gl_PointCoord
usage doesn't turn out like you wanted is that the range of gl_PointCoord
is 0.0 to 1.0, not -1.0 to 1.0.
Just subtract 0.5 to make it balanced about 0.0. If you also multiply it by 2 it will have the range -1.0 to 1.0.
You may also want to normalize
the resulting vector (not doing so can cause unwanted brightness variations as the length of the vector changes due to the z-component being fixed to 1.0).
Upvotes: 1