I know this is not OpenGL but I don’t know any other 3D programming forum with so many experts ready to help. And I am desperate cause I see no further possibility to debug my application and shader.
I am trying to implement animation using vertex shader. And it ALMOST works. I mean I want my object to move smoothly with time. And I basically does this but there is some small artifact that I cannot track down. Here are the details:
Every position is described by a 3x4 matrix - every vertex of an object must be multiplied by this matrix for this object to be in this position.
I have 3 such matrices - one at each point of time.
matrixA = {1,0,0,0, 0,1,0,0, 0,0,1,0};
at point in time 0 ms
matrixB = {1,0,0,0, 0,1,0,1, 0,0,1,0};
at point in time 1000 ms
matrixC = {1,0,0,0, 0,1,0,2, 0,0,1,0};
at point in time 2000 ms
My app keeps track of current time and updates shader parameters accordingly. These 3 (uniform in Cg) parameters are: 2 matrices and a weight factor. The weight factor is used to linearly interpolate between two matrices, so it changes it’s value from 0.0 to 1.0 during the flow of animation from 0 ms to 1000 ms, and again from 0.0 to 1.0 during animation from 1000 ms to 2000 ms. The 2 matrices send to a vertex shader are updated when 1000 ms have passed - so it is now blending between matrixB and matrixC.
Such interpolation between matrices in a vertex shader guarantees that the motion is smooth. And it is smooth. Except for one small problem: at the point in time when matrices are updated (1000 ms) the animated object for a fraction of second takes the position of the next matrix - that is, at time 1000 ms the object is for a fraction of second at position implied by matrixC, then instantly comes back to a position close to matrixB (which is the right position at this point in time) and continues to move smoothly towards position implied by matrixC.
Here is my shader code:
struct vertex_input
{
float4 position : POSITION;
};
struct vertex_output
{
float4 position : POSITION;
};
vertex_output vertex_program(vertex_input IN, uniform float4x4 model_view_proj, uniform float3x4 previous_matrix, uniform float3x4 next_matrix, uniform float weight)
{
vertex_output OUT;
float3 previous_position = mul( previous_matrix, IN.position );
float3 next_position = mul( next_matrix, IN.position );
float3 position = lerp(previous_position, next_position, weight);//here is the interpolation
OUT.position = mul(model_view_proj, float4(position, 1.0f));
return OUT;
}
I thought I pass in parameters with wrong values so I printed them out just before sending them to the shader. Here is a fragment of the output at this problematic moment around 1000 ms.
previous_matrix : 1000 0100 0010
next_matrix : 1000 0101 0010
weight : 0.982
previous_matrix : 1000 0100 0010
next_matrix : 1000 0101 0010
weight : 0.999
previous_matrix : 1000 0101 0010
next_matrix : 1000 0102 0010
weight : 0.016
previous_matrix : 1000 0101 0010
next_matrix : 1000 0102 0010
weight : 0.034
You see it’s correct!!
Please I want to hear that I did some very stupid mistake!