Part of the Khronos Group
OpenGL.org

The Industry's Foundation for High Performance Graphics

from games to virtual reality, mobile phones to supercomputers

Results 1 to 5 of 5

Thread: Problem converting to Vertex/Fragment shaders

  1. #1
    Junior Member Regular Contributor
    Join Date
    Feb 2004
    Location
    Los Angeles, CA
    Posts
    151

    Problem converting to Vertex/Fragment shaders

    I have written this little vertex/fragment program code a little while ago to simulate per-pixel reflection using normal maps.
    Everything worked just fine and seeing how everyone seems to jump on the OGLSL bandwagon, I thought I'd give it a try and see if I can convert my mentioned shaders into OGLSL.

    Spent few hours reading the pdf posted on the forums webhost, and then proceeded to convert my code.
    After many attempts, I got it to work, well not with a serious visual bug though.
    The problem is, I'm not getting the correct result and the cube map texture seems to rotate as I move my object around instead of staying fix.

    Here's the code, can someone help me out figure what errors I might have skipped during the conversion?

    Code :
    !!ARBvp1.0
     
    #********************************************************************#
    # Coder  : Abdul Bezrati                                             #
    # Contact: [email]abezrati@hotmail.com[/email]                                      #
    # Info   : Texture  Coordinates = vertex.texcoord[0]                 #
    #          Tangent  Vector      = vertex.texcoord[1]                 #
    #          Binoraml Vector      = vertex.texcoord[2]                 #
    #********************************************************************#
     
    OPTION ARB_position_invariant;
     
    PARAM modelViewInvTrans[4] = { state.matrix.modelview.invtrans};
    PARAM modelView[4]         = { state.matrix.modelview};
     
    TEMP  eyeVector;
     
    DP4 eyeVector.x, modelView[0], vertex.position;
    DP4 eyeVector.y, modelView[1], vertex.position;
    DP4 eyeVector.z, modelView[2], vertex.position;
     
    MOV eyeVector, -eyeVector;
     
    MOV result.texcoord[0], vertex.texcoord[0];
     
    DP3 result.texcoord[1].x, modelViewInvTrans[0], vertex.texcoord[1];
    DP3 result.texcoord[1].y, modelViewInvTrans[0], vertex.texcoord[2];
    DP3 result.texcoord[1].z, modelViewInvTrans[0], vertex.normal;
     
    DP3 result.texcoord[2].x, modelViewInvTrans[1], vertex.texcoord[1];
    DP3 result.texcoord[2].y, modelViewInvTrans[1], vertex.texcoord[2];
    DP3 result.texcoord[2].z, modelViewInvTrans[1], vertex.normal;
     
    DP3 result.texcoord[3].x, modelViewInvTrans[2], vertex.texcoord[1];
    DP3 result.texcoord[3].y, modelViewInvTrans[2], vertex.texcoord[2];
    DP3 result.texcoord[3].z, modelViewInvTrans[2], vertex.normal;
     
    MOV result.texcoord[1].w, eyeVector.x; 
    MOV result.texcoord[2].w, eyeVector.y;   
    MOV result.texcoord[3].w, eyeVector.z;  
    END
    #
    !!ARBfp1.0
     
    #*********************************************************************#
    #Author:Abdul Bezrati    "Java Cool Dude"                             #
    #*********************************************************************#
     
    TEMP normalVector, reflectionVector, viewVector;
    TEMP usefulTemp, cubeMapFragment;
     
    TEX  usefulTemp, fragment.texcoord[0], texture[0], 2D;
     
    MAD  usefulTemp, usefulTemp, 2.0, -1.0;
     
    DP3 normalVector.x, usefulTemp, fragment.texcoord[1];
    DP3 normalVector.y, usefulTemp, fragment.texcoord[2];
    DP3 normalVector.z, usefulTemp, fragment.texcoord[3];
     
    DP3 normalVector.w, normalVector, normalVector;
    RSQ normalVector.w, normalVector.w;
    MUL normalVector, normalVector, normalVector.w;
     
    MOV viewVector.x  , fragment.texcoord[1].w;
    MOV viewVector.y  , fragment.texcoord[2].w;
    MOV viewVector.z  , fragment.texcoord[3].w;
     
    DP3 usefulTemp , normalVector, viewVector;
    ADD usefulTemp , usefulTemp  , usefulTemp;
     
    MAD reflectionVector, usefulTemp, normalVector, -viewVector;
     
    TEX usefulTemp     , fragment.texcoord[0], texture[1], 2D;
    TEX cubeMapFragment, reflectionVector    , texture[2], CUBE;
     
    MUL usefulTemp, usefulTemp, 1.6;
    MUL result.color, usefulTemp, cubeMapFragment;
    END
    Code :
    varying vec3 binormalVector,
                 tangentVector,
                 normalVector,
                 eyeVector;
     
    void main(void)
    {
      gl_TexCoord[0]   = gl_MultiTexCoord0;
     
      eyeVector        =  -(gl_Vertex * gl_ModelViewMatrix).xyz;
     
      binormalVector.x = dot(gl_MultiTexCoord1.xyz, gl_NormalMatrix[1]);
      binormalVector.y = dot(gl_MultiTexCoord2.xyz, gl_NormalMatrix[1]);
      binormalVector.z = dot(gl_Normal.xyz        , gl_NormalMatrix[1]);
     
      tangentVector.x  = dot(gl_MultiTexCoord1.xyz, gl_NormalMatrix[0]);
      tangentVector.y  = dot(gl_MultiTexCoord2.xyz, gl_NormalMatrix[0]);
      tangentVector.z  = dot(gl_Normal.xyz        , gl_NormalMatrix[0]);
     
      normalVector.x   = dot(gl_MultiTexCoord1.xyz, gl_NormalMatrix[2]);
      normalVector.y   = dot(gl_MultiTexCoord2.xyz, gl_NormalMatrix[2]);
      normalVector.z   = dot(gl_Normal.xyz        , gl_NormalMatrix[2]);
     
      gl_Position =   gl_ModelViewProjectionMatrix * gl_Vertex; 
    }
     
    varying vec3 binormalVector,
                 tangentVector,
                 normalVector,
                 eyeVector;
     
    uniform sampler2D   Bump,
                        Base;
    uniform samplerCube Cube;
     
      void main (void)
      {
        vec3 bump       = texture2D(Bump, vec2(gl_TexCoord[0])).xyz * 2.0 - 1.0,
             TBNnormal  = normalize(vec3(dot(tangentVector , bump),
                                         dot(binormalVector, bump),
                                         dot(normalVector  , bump)));
     
        vec3 reflection = (2.0*dot(eyeVector, TBNnormal)*TBNnormal - eyeVector); 
        vec4 base       = texture2D(Base, vec2(gl_TexCoord[0])),
             cube       = textureCube(Cube, reflection);
     
        gl_FragColor =  cube*base *1.6; 
      }
    Thanks in advance

  2. #2
    Junior Member Newbie
    Join Date
    Feb 2004
    Location
    Bristol, England
    Posts
    13

    Re: Problem converting to Vertex/Fragment shaders

    Why... the... hell are you using all those dot product calls? Just use the '*' operator, because GLSL does proper linear algebra with vectors and matrices.
    If at first you don't succeed, destroy all evidence that you ever tried.

  3. #3
    Member Regular Contributor
    Join Date
    Apr 2002
    Location
    Austria
    Posts
    328

    Re: Problem converting to Vertex/Fragment shaders

    Why don't you compute the light and view vector in tagent space and pass it to the fragment shader instead of calculating a tangent-space matrix, passing it to the fragment shader and then compute the normal in world space? That would be a lot easier!
    There is a theory which states that if ever anybody discovers exactly what the Universe is for and why it is here, it will instantly disappear and be replaced by something even more bizarre and inexplicable.

    There is another theory which states that this has already happened...

  4. #4
    Member Regular Contributor
    Join Date
    Apr 2002
    Location
    Austria
    Posts
    328

    Re: Problem converting to Vertex/Fragment shaders

    Here's my bump mapping shader:

    Vertex Shader:
    Code :
    attribute vec3 a2v_Normal;
    attribute vec3 a2v_Tangent;
    attribute vec3 a2v_Binormal;
    attribute vec2 a2v_TexCoord;
     
    varying vec3 v2f_LightVec;
    varying vec3 v2f_ViewVec;
    varying vec2 v2f_TexCoord;
     
    void main()
    {
    	// Vertex transformation
    	gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
     
    	mat3 TBN_Matrix;
    	TBN_Matrix[0] =  gl_NormalMatrix * a2v_Tangent;
    	TBN_Matrix[1] =  gl_NormalMatrix * a2v_Binormal;
    	TBN_Matrix[2] =  gl_NormalMatrix * a2v_Normal;
     
    	// Calculation Light vector in ModelView Space
    	vec4 Vertex_ModelView = gl_ModelViewMatrix * gl_Vertex;
    	v2f_LightVec = TBN_Matrix * vec3(gl_LightSource[0].position - Vertex_ModelView);
    	v2f_ViewVec = TBN_Matrix * vec3(-Vertex_ModelView);
     
    	v2f_TexCoord = a2v_TexCoord;
    }
    Fragment Shader:
    Code :
    uniform sampler2D BaseMap;
    uniform sampler2D BumpMap;
     
    varying vec3 v2f_LightVec;
    varying vec3 v2f_ViewVec;
    varying vec2 v2f_TexCoord;
     
    void main()
    {
    	vec4 LightColor = vec4(1.0, 0.0, 0.0, 1.0);
     
    	vec4 Color = texture2D(BaseMap, v2f_TexCoord);
    	vec3 Normal = normalize(vec3(texture2D(BumpMap, v2f_TexCoord)) - 0.5);
     
    	// Normalize the interpolated Light and View Vector
    	vec3 LightVec = normalize(v2f_LightVec);
    	vec3 ViewVec = normalize(v2f_ViewVec);
     
    	// Calculating Diffuse Term
    	float DiffuseTerm = clamp(dot(Normal, LightVec), 0.0, 1.0);
     
    	//float Shadow = clamp(DiffuseTerm * 4.0, 0.0, 1.0);
     
    	// Calculating Specular Term 
    	vec3 Reflect = normalize(2.0 * DiffuseTerm * Normal - LightVec);
    	vec4 Specular = vec4(min(pow(clamp(dot(Reflect, ViewVec), 0.0, 1.0), 16.0), Color.w));
     
    	// Calculating the final Color
    	gl_FragColor = Color*0.2 + (Color*DiffuseTerm + Specular);
    }
    There is a theory which states that if ever anybody discovers exactly what the Universe is for and why it is here, it will instantly disappear and be replaced by something even more bizarre and inexplicable.

    There is another theory which states that this has already happened...

  5. #5
    Junior Member Regular Contributor
    Join Date
    Feb 2004
    Location
    Los Angeles, CA
    Posts
    151

    Re: Problem converting to Vertex/Fragment shaders

    Thanks for the help people, I do really appreciate it
    Having said that, keep in mind that I'm trying to put together my very first OGLSL shader, therefore don't expect me to write cutting-edge code on the first try(hint plenty of dot products here and there).
    I took sometime and analyzed the sample code posted above which helped me out learning a lot more about the syntax and the cool optimizations that could be done.

    Now here's my shaders for anyone who wanna try em

    Code :
    varying vec3 eyeVector;
    varying mat3 normalMatrix;
     
    void main(void)
    {
     
      eyeVector      = -(gl_ModelViewMatrix * gl_Vertex).xyz;
      normalMatrix   = gl_NormalMatrix*mat3(gl_MultiTexCoord1.x, gl_MultiTexCoord1.y, gl_MultiTexCoord1.z,
                                            gl_MultiTexCoord2.x, gl_MultiTexCoord2.y, gl_MultiTexCoord2.z,
                                            gl_Normal.x        , gl_Normal.y        , gl_Normal.z);
     
      gl_Position    = gl_ModelViewProjectionMatrix * gl_Vertex; 
      gl_TexCoord[0] = gl_MultiTexCoord0;
    }
     
     
    uniform samplerCube Cube;
    uniform sampler2D   Bump,
                        Base;
    varying mat3        normalMatrix;
    varying vec3        eyeVector;
     
    void main()
    {
      vec3 bump       = vec3(texture2D(Bump, vec2(gl_TexCoord[0]))* 2.0 - 1.0),
           normal     = normalize(normalMatrix*bump);
     
      vec3 reflection = normalize((2.0*dot(eyeVector, normal)*normal - eyeVector)); 
      vec4 base       = texture2D(Base, vec2(gl_TexCoord[0])),
           cube       = textureCube(Cube, reflection);
     
      gl_FragColor    =  cube*base; 
    }
    The performance is a bit slower compared to the Fragment/Vertex programs combo though :insert confused smiley here:

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •