  '
  'SHADERS
  '
  'http://en.wikipedia.org/wiki/OpenGL_Shading_Language
  'https://www.opengl.org/sdk/docs/tutorials/ClockworkCoders/lighting.php
  '
  '
  '1  'MINIMAL
  '2  'PER PIXEL
  '3  'PHONG
  '4  'MULTIPLE LIGHTS 
  '5  'MULTIPLE LIGHTS AND TEXTURING
  '6  'SWAP COLORS
  '7  'COMBINED MULTIPLE LIGHTS AND TEXTURING AND REFLECTION
  '8  'SKY BOX
  '9  'CUBIC REFLECTION 1
  '10 'CUBIC REFLECTION 2
  '11 'CUBIC REFLECTION 3
  '12 '3.3 LIGHT MATERIAL AND CUBIC REFLECTION ALPHA SHADER
  '13 'SKY BOX using own Projection & ModelView
  '14 'FLAT COLOR
  '
  '
  ShaderProg ps[32]
  '
  sub shaders()
  =============
  '
  static float mat=
  {
  '.0,.0,.0,1, 'emissive
   .1,.1,.1,1, 'ambient
   .6,.6,.6,1, 'diffuse
   .4,.4,.4,1, 'specular
  16.0         'Shininess
  }
  '
  'material mat
  '


/*


passing MULTIPLE TEXTURES:
https://www.opengl.org/discussion_boards/showthread.php/163092-Passing-Multiple-Textures-from-OpenGL-to-GLSL-shader


  texLoc = glGetUniformLocation(ShaderID, "BaseMap");
  glUniform1i(texLoc, 0);

  texLoc = glGetUniformLocation(ShaderID, "ReflectMap");
  glUniform1i(texLoc, 1);

  texLoc = glGetUniformLocation(ShaderID, "RefractMap");
  glUniform1i(texLoc, 2);


  glActiveTexture(GL_TEXTURE0);
  glBindTexture(GL_TEXTURE_2D, Base);

  glActiveTexture(GL_TEXTURE1);
  glBindTexture(GL_TEXTURE_2D, Reflection);

  glActiveTexture(GL_TEXTURE2);
  glBindTexture(GL_TEXTURE_2D, Refraction); 
*/

  '
  'MINIMAL SHADER
  '==============
  '
  ps[1].vsrc=
  "
  #version 330 compatibility
  out vec3 normal;
  out vec2 texcoord;
  void main()
  {
    normal = normalize(gl_NormalMatrix * gl_Normal);
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
    //gl_TexCoord[0] = gl_MultiTexCoord0;
    texcoord = gl_MultiTexCoord0.st;
  }
  "
  /*
  glUniform1i(glGetUniformLocation(ShaderID, "texunit"), 0);
  glActiveTexture(GL_TEXTURE0);
  glBindTexture(GL_TEXTURE_2D, imgn);
  */
  /*
  'Pass multiple texture coordinates to my shader 
  'https://www.opengl.org/discussion_boards/showthread.php/176738-Pass-multiple-texture-coordinates-to-my-shader
  glMultiTexCoord2f( GL_TEXTURE0, s1, t1);
  glMultiTexCoord2f( GL_TEXTURE1, s2, t2);
  */
  '
  ps[1].fsrc=
  "
  #version 330 compatibility

  uniform sampler2D texunit;
  in      vec3  normal;
  in      vec2  texcoord;
  out     vec4 color;

  void main ()
  
{
     //color = vec4(0.75, 0.5, 0.0, 1.0);
     color = texture2D(texunit, texcoord);
  
}


  "
  'PER PIXEL DIFFUSE SHADER
  '========================
  '
  ps[2].vsrc=
  "
  #version 330 compatibility
  out vec3 vN;
  out vec3 vP;
  void main(void)
  {
     vP = vec3(gl_ModelViewMatrix * gl_Vertex);       
     vN = normalize(gl_NormalMatrix * gl_Normal);
     gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
  }
  "
  ps[2].fsrc=
  "
  #version 330 compatibility
  in vec3  vN;
  in vec3  vP;
  out vec4 vC;

  void main(void)
  {
    vec3 vL = normalize(gl_LightSource[0].position.xyz - vP);   
    vec4 Idiff = gl_FrontLightProduct[0].diffuse * max(dot(vN,vL), 0.0);  
    Idiff = clamp(Idiff, 0.0, 1.0); 
    vC = Idiff;
  }
  "
  '
  'PHONG SHADER
  '============
  '
  ps[3].vsrc=
  "
  varying vec3 vN;
  varying vec3 vP;
  void main(void)  
  {     
    vP = vec3(gl_ModelViewMatrix * gl_Vertex);       
    vN = normalize(gl_NormalMatrix * gl_Normal);
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;  
  }
  "
  ps[3].fsrc=
  "
  varying vec3 vN;
  varying vec3 vP;    
  void main (void)  
  {  
    vec3 vL = normalize(gl_LightSource[0].position.xyz - vP);   
    vec3 vE = normalize(-vP); // we are in Eye Coordinates, so EyePos is (0,0,0)  
    vec3 vR = normalize(-reflect(vL,vN));  
 
    //calculate Ambient Term:  
    vec4 Iamb = gl_FrontLightProduct[0].ambient;    

    //calculate Diffuse Term:  
    vec4 Idiff = gl_FrontLightProduct[0].diffuse * max(dot(vN,vL), 0.0);
    Idiff = clamp(Idiff, 0.0, 1.0);     
   
    // calculate Specular Term:
    vec4 Ispec = gl_FrontLightProduct[0].specular 
                * pow(max(dot(vR,vE),0.0),0.3*gl_FrontMaterial.shininess);
    Ispec = clamp(Ispec, 0.0, 1.0); 
    // write Total Color:  
    gl_FragColor = gl_FrontLightModelProduct.sceneColor + Iamb + Idiff + Ispec;     
  }
  "
  '
  'MULTIPLE LIGHT SHADER
  '=====================
  '
  ps[4].vsrc=
  "
  varying vec3 vN;
  varying vec3 vP;
  void main(void)  
  {     
    vP = vec3(gl_ModelViewMatrix * gl_Vertex);       
    vN = normalize(gl_NormalMatrix * gl_Normal);
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;  
  }
  "
  ps[4].fsrc=
  "
  uniform vec4 Tint;
  varying vec3 vN;
  varying vec3 vP; 
  #define MAX_LIGHTS 3 
  void main (void) 
  { 
    vec4 finalColor = Tint;
   
    for (int i=0;i<MAX_LIGHTS;i++)
    {
      vec3 vL = normalize(gl_LightSource[i].position.xyz - vP); 
      vec3 vE = normalize(-vP); // we are in Eye Coordinates, so EyePos is (0,0,0) 
      vec3 vR = normalize(-reflect(vL,vN)); 
   
      //calculate Ambient Term: 
      vec4 Iamb = gl_FrontLightProduct[i].ambient; 
      //calculate Diffuse Term: 
      vec4 Idiff = gl_FrontLightProduct[i].diffuse * max(dot(vN,vL), 0.0);
      Idiff = clamp(Idiff, 0.0, 1.0); 
   
      // calculate Specular Term:
      vec4 Ispec = gl_FrontLightProduct[i].specular 
             * pow(max(dot(vR,vE),0.0),0.3*gl_FrontMaterial.shininess);
      Ispec = clamp(Ispec, 0.0, 1.0); 
   
      finalColor += 
        Iamb 
      + Idiff
      + Ispec;
    }
    // write Total Color: 
    gl_FragColor = gl_FrontLightModelProduct.sceneColor + finalColor;
  }
  "
  'LIGHT AND TEXTURE SHADER
  '========================
  '
  ps[5].vsrc=
  "
  #version 330 compatibility

  out  vec3 vN;
  out  vec3 vP;
  out  vec2 vT;
  
  void main(void)  
  {     
    vT = vec2(gl_MultiTexCoord0);
    vP = vec3(gl_ModelViewMatrix * gl_Vertex);       
    vN = normalize(gl_NormalMatrix * gl_Normal);
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;  
  }
  "
  ps[5].fsrc=
  "
  #version 330 compatibility
  uniform vec4 Tint;
  uniform sampler2D TextureUnit;
  in      vec3 vN;
  in      vec3 vP; 
  in      vec2 vT;
  out     vec4 FragColor;
  #define MAX_LIGHTS 3 

  void main (void) 
  { 
    vec4 finalColor = Tint;
   
    for (int i=0;i<MAX_LIGHTS;i++)
    {
      vec3 vL = normalize(gl_LightSource[i].position.xyz - vP); 
      vec3 vE = normalize(-vP); // we are in Eye Coordinates, so EyePos is (0,0,0) 
      vec3 vR = normalize(-reflect(vL,vN)); 
   
      //calculate Ambient Term: 
      vec4 Iamb = gl_FrontLightProduct[i].ambient; 
      //calculate Diffuse Term: 
      vec4 Idiff = gl_FrontLightProduct[i].diffuse * max(dot(vN,vL), 0.0);
      Idiff = clamp(Idiff, 0.0, 1.0); 
   
      // calculate Specular Term:
      vec4 Ispec = gl_FrontLightProduct[i].specular 
      * pow(max(dot(vR,vE),0.0),0.3*gl_FrontMaterial.shininess);
      Ispec = clamp(Ispec, 0.0, 1.0); 
   
      finalColor += 
      Iamb 
      +Idiff
      +Ispec;
      finalColor*= texture2D(TextureUnit, vT);
    }
    // write Total Color: 
    FragColor = gl_FrontLightModelProduct.sceneColor + finalColor;
  }
  "
  '
  'https://www.opengl.org/sdk/docs/tutorials/ClockworkCoders/texturing.php
  '
  '
  'SWAP COLORS
  '===========
  '
  ps[6].vsrc=
  "
  varying vec2 vT;
  void main(void)
  {
    vT = gl_MultiTexCoord0;
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
  }
  "
  ps[6].fsrc=
  "
  uniform sampler2D myTexture;
  varying vec2 vT;
  void main(void)
  {
    gl_FragColor = texture2D(myTexture, vT).bgra;
  }
  "
  '
  'LIGHT MATERIAL AND CUBIC REFLECTION ALPHA SHADER
  '================================================
  '
  ps[7].vsrc=
  "
  #version 330 compatibility
  // #version 330
  // http://stackoverflow.com/questions/21980947/replacement-for-gl-position-gl-modelviewprojectionmatrix-gl-vertex
  // Noise
  // http://stackoverflow.com/questions/4200224/random-noise-functions-for-glsl

  float turbulence( vec3 p ) {
    float t = -.5;
    return t;
  }

  uint hash( uint x ) {
    x += ( x << 10u );
    x ^= ( x >>  6u );
    x += ( x <<  3u );
    x ^= ( x >> 11u );
    x += ( x << 15u );
    return x;
  }


  uint hash( uvec2 v ) { return hash( v.x ^ hash(v.y)                         ); }
  uint hash( uvec3 v ) { return hash( v.x ^ hash(v.y) ^ hash(v.z)             ); }
  uint hash( uvec4 v ) { return hash( v.x ^ hash(v.y) ^ hash(v.z) ^ hash(v.w) ); }


  float floatConstruct( uint m ) {
    const uint ieeeMantissa = 0x007FFFFFu; // binary32 mantissa bitmask
    const uint ieeeOne      = 0x3F800000u; // 1.0 in IEEE binary32

    m &= ieeeMantissa;                     // Keep only mantissa bits (fractional part)
    m |= ieeeOne;                          // Add fractional part to 1.0

    float  f = uintBitsToFloat( m );       // Range [1:2]
//vec2 g = vec2(floatToUintBits( f ), 1.0));
    return f - 1.0;                        // Range [0:1]
  }

  // User-specified uniforms
  uniform vec3 CameraPosition;
 
  vec3 vN;
  vec3 vP;
  vec2 vT;
  vec3 dN; //NormalDirection;
  vec3 dV; //ViewDirection;
  ///vec4 vM;
  void main(void)  
  {
    ///vM = noise4(gl_Vertex);
    vT = vec2(gl_MultiTexCoord0);
    vP = vec3(gl_ModelViewMatrix * gl_Vertex);       
    vN = normalize(gl_NormalMatrix * gl_Normal);
    dV = vec3(gl_ModelViewMatrix * gl_Vertex - vec4(CameraPosition, 1.0));
    dN = normalize(vec3(vec4(gl_Normal, 0.0) * gl_ModelViewMatrixInverse));
    vec4 vC=gl_Vertex; //+vec4(gl_Normal,0.0)*noise4(1.0);
    gl_Position = gl_ModelViewProjectionMatrix * vC;
  }
  "
  ps[7].fsrc=
  "
  #version 330 compatibility
  uniform vec4 Tint;
  uniform sampler2D TextureUnit;
  uniform samplerCube CubeMap;   
  
  vec3 vN;
  vec3 vP; 
  vec2 vT;
  
  //for cubic reflection
  vec3 dN;
  vec3 dV;
  #define MAX_LIGHTS 3 
  void main (void) 
  { 
    vec4  finalColor = Tint;
    float Alpha = Tint.a;
    vec3  dR = reflect(dV, dN);
   
    for (int i=0;i<MAX_LIGHTS;i++)
    {
      vec3 vL = normalize(gl_LightSource[i].position.xyz - vP); 
      vec3 vE = normalize(-vP); // we are in Eye Coordinates, so EyePos is (0,0,0) 
      vec3 vR = normalize(-reflect(vL,vN)); 
      //calculate Ambient Term: 
      vec4 Iamb = gl_FrontLightProduct[i].ambient; 
      //calculate Diffuse Term: 
      vec4 Idiff = gl_FrontLightProduct[i].diffuse * max(dot(vN,vL), 0.0);
      Idiff = clamp(Idiff, 0.0, 1.0); 
   
      // calculate Specular Term:
      vec4 Ispec = gl_FrontLightProduct[i].specular 
      * pow(max(dot(vR,vE),0.0),0.3*gl_FrontMaterial.shininess);
      Ispec = clamp(Ispec, 0.0, 1.0); 
   
      finalColor += 
      Iamb 
      +Idiff
      +Ispec;
    }
    finalColor *=
    ///texture2D(TextureUnit, vT);
    textureCube(CubeMap, dR);
    gl_FragColor = vec4(vec3(finalColor),Alpha);
  }
  "
  '
  'SKYBOX SHADER
  '=============
  '
  ps[8].vsrc=
  "
  #version 400
  out vec4 Position;
  void main()
  {
    gl_TexCoord[0].stp = gl_Vertex.xyz;
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
  }
  "
  ps[8].fsrc=
  "
  #version 400
  uniform samplerCube CubeMap;
  out vec4 Color;
  void main()
  {
    Color = textureCube(CubeMap, gl_TexCoord[0].stp);
  }
  "
  '
  'CUBIC REFLECTION SHADERS 1
  '==========================
  '
  ps[9].vsrc=
  "
  //#version 400
  uniform vec3   CameraPosition;
  uniform mat3x3 NormalMatrix;
  uniform mat4x4 ModelMatrix;
  void main()
  {
    vec3 vN = NormalMatrix * gl_Normal;
    vec4 vP = ModelMatrix  * gl_Vertex;
    vec3 vR = reflect(vP.xyz - CameraPosition, normalize(vN));
    gl_TexCoord[0].stp = vec3(vR.x, -vR.yz);
    //gl_TexCoord[0].stp = gl_Vertex.xyz;
    gl_Position = gl_ModelViewProjectionMatrix * vP;
  }
  "
  ps[9].fsrc=
  "
  #version 400
  uniform samplerCube CubeMap;
  out vec4 Color;
  void main()
  {
    Color = textureCube(CubeMap, gl_TexCoord[0].stp);
  }
  "
  '
  '
  'CUBIC REFLECTION SHADERS 2
  '==========================
  '
  ps[10].vsrc=
  "
  // User-specified uniforms
  uniform vec3 CameraPosition; 
  uniform mat4 ModelMatrix; // _Object2World
  uniform mat4 ModelMatrixInverse; // _World2Object
  //
  varying vec3 NormalDirection;
  varying vec3 ViewDirection;
 
  void main()
  {            
    NormalDirection = normalize(vec3(vec4(gl_Normal, 0.0) * ModelMatrixInverse));

    ViewDirection = vec3(ModelMatrix * gl_Vertex
    - vec4(CameraPosition, 1.0));
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
  }
  "
  ps[10].fsrc=
  "
  uniform samplerCube CubeMap;   
  varying vec3 NormalDirection;
  varying vec3 ViewDirection;
  void main()
  {
    vec3 reflectedDirection = 
    reflect(ViewDirection, NormalDirection);
    gl_FragColor = textureCube(CubeMap, reflectedDirection);
  }
  "
  '
  'CUBIC REFLECTION SHADERS 3
  '==========================
  '
  ps[11].vsrc=
  "
  #version 330 compatibility

  uniform vec3 CameraPosition; 
  out     vec3 NormalDirection;
  out     vec3 ViewDirection;
 
  void main()
  {            
    NormalDirection = normalize(vec3(vec4(gl_Normal, 0.0) * gl_ModelViewMatrixInverse));

    ViewDirection = vec3(gl_ModelViewMatrix * gl_Vertex
    - vec4(CameraPosition, 1.0));
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
  }
  "
  ps[11].fsrc=
  "
  #version 330 compatibility

  uniform samplerCube CubeMap;   
  in      vec3 NormalDirection;
  in      vec3 ViewDirection;
  out     vec4 FragColor;
  void main()
  {
    vec3 reflectedDirection = 
    reflect(ViewDirection, NormalDirection);
    FragColor = textureCube(CubeMap, reflectedDirection) * vec4(0.5,0.5,0.5,1.0);
  }
  "
  '
  '3.30 SHADER
  '===========
  '
  'https://www.opengl.org/registry/doc/GLSLangSpec.3.30.6.clean.pdf  vs[12]=
  '
  'LIGHT MATERIAL AND CUBIC REFLECTION ALPHA SHADER
  '================================================
  '
  ps[12].vsrc=
  "

  #version 330 compatibility

  // http://stackoverflow.com/questions/21980947/replacement-for-gl-position-gl-modelviewprojectionmatrix-gl-vertex
  // Noise
  // http://stackoverflow.com/questions/4200224/random-noise-functions-for-glsl

  float turbulence( vec3 p ) {
    float t = -.5;
    return t;
  }

  uint hash( uint x ) {
    x += ( x << 10u );
    x ^= ( x >>  6u );
    x += ( x <<  3u );
    x ^= ( x >> 11u );
    x += ( x << 15u );
    return x;
  }


  uint hash( uvec2 v ) { return hash( v.x ^ hash(v.y)                         ); }
  uint hash( uvec3 v ) { return hash( v.x ^ hash(v.y) ^ hash(v.z)             ); }
  uint hash( uvec4 v ) { return hash( v.x ^ hash(v.y) ^ hash(v.z) ^ hash(v.w) ); }


  float floatConstruct( uint m ) {
    const uint ieeeMantissa = 0x007FFFFFu; // binary32 mantissa bitmask
    const uint ieeeOne      = 0x3F800000u; // 1.0 in IEEE binary32

    m &= ieeeMantissa;                     // Keep only mantissa bits (fractional part)
    m |= ieeeOne;                          // Add fractional part to 1.0

    float  f = uintBitsToFloat( m );       // Range [1:2]
//vec2 g = vec2(floatToUintBits( f ), 1.0));
    return f - 1.0;                        // Range [0:1]
  }

  // User-specified uniforms
  uniform vec3 CameraPosition;
 
  out vec3 vN;
  out vec3 vP;
  out vec2 vT;

  out vec3 dN; //NormalDirection;
  out vec3 dV; //ViewDirection;
  ///vec4 vM;
  void main(void)  
  {
    ///vM = noise4(gl_Vertex);
    vT = vec2(gl_MultiTexCoord0);
    vN = normalize(gl_NormalMatrix * gl_Normal);
    dV = vec3(gl_ModelViewMatrix * gl_Vertex - vec4(CameraPosition, 1.0));
    dN = normalize(vec3(vec4(vN, 0.0) * gl_ModelViewMatrixInverse));
    //vec4 vC = gl_Vertex + vec4(gl_Normal,0.0) *noise4(1.0);
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
    vP = vec3(gl_Position);
  }
  "
  '
  ps[12].fsrc=
  "
  #version 330  compatibility
  uniform vec4 Tint;
  uniform sampler2D TextureUnit;
  uniform samplerCube CubeMap;   
  
  in vec3 vN;
  in vec3 vP; 
  in vec2 vT;
  //for cubic reflection
  in vec3 dN;
  in vec3 dV;

  #define MAX_LIGHTS 3 
  void main (void) 
  { 
    vec4  finalColor = Tint;
    float Alpha = Tint.a;
    vec3  dR = reflect(dV, dN);
   
    for (int i=0;i<MAX_LIGHTS;i++)
    {
      vec3 vL = normalize(gl_LightSource[i].position.xyz - vP); 
      vec3 vE = normalize(-vP); // we are in Eye Coordinates, so EyePos is (0,0,0) 
      vec3 vR = normalize(-reflect(vL,vN)); 
      //calculate Ambient Term: 
      vec4 Iamb = gl_FrontLightProduct[i].ambient; 
      //calculate Diffuse Term: 
      vec4 Idiff = gl_FrontLightProduct[i].diffuse * max(dot(vN,vL), 0.0);
      Idiff = clamp(Idiff, 0.0, 1.0); 
   
      // calculate Specular Term:
      vec4 Ispec = gl_FrontLightProduct[i].specular 
      * pow(max(dot(vR,vE),0.0),0.3*gl_FrontMaterial.shininess);
      Ispec = clamp(Ispec, 0.0, 1.0); 
   
      finalColor += Iamb + Idiff + Ispec;
    }
    finalColor *=
    ///texture2D(TextureUnit, vT);
    textureCube(CubeMap, dR);
    gl_FragColor = vec4(vec3(finalColor),Alpha);
  }
  "


  'SKYBOX SHADER
  '=============
  '
  ps[13].vsrc=
  "
  #version 400
  uniform mat4 Projection;
  uniform mat4 ModelView;
  void main()
  {
    //gl_TexCoord[0].stp = gl_Vertex.xyz;
    //gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
    gl_TexCoord[0] = gl_Vertex;
    gl_Position = Projection * ModelView * gl_Vertex;
  }
  "
  ps[13].fsrc=
  "
  #version 400
  uniform samplerCube CubeMap;
  out vec4 Color;
  void main()
  {
    Color = textureCube(CubeMap, gl_TexCoord[0].stp);
  }
  "
  '
  'MINIMAL SHADER
  '==============
  '
  ps[14].vsrc=
  "
  #version 400
  void main()
  {
    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
  }
  "
  '
  ps[14].fsrc=
  "
  #version 400
  uniform vec4  Tint;
  out     vec4 color;

  void main ()
  
  {
     color=Tint;
  }
  "



  end sub

