title: Block filters using fragment shaders
body: <p>I was following <a href="http://www.ozone3d.net/tutorials/image_filtering_p2.php" rel="nofollow noreferrer">this tutorial</a> using Apple's OpenGL Shader Builder (tool similar to Nvidia's fx composer, but simpler).</p>
  
  <p>I could easily apply the filters, but I don't understand if they worked correct (and if so how can I improve the output). For example the blur filter: OpenGL itself does some image processing on the textures, so if they are displayed in a higher resolution than the original image, they are blurred already by OpenGL. Second the blurred part is brighter then the part not processed, I think this does not make sense, since it just takes pixels from the direct neighborhood. This is defined by</p>
  
  <pre><code>float step_w = (1.0/width);
  </code></pre>
  
  <p>Which I don't quite understand: The pixels are indexed using floating point values??</p>
  
  <p><a href="http://img218.imageshack.us/img218/6468/blurzt.png" rel="nofollow noreferrer">Blurred Image http://img218.imageshack.us/img218/6468/blurzt.png</a></p>
  
  <p>Edit: I forgot to attach the exact code I used:</p>
  
  <p><strong>Fragment Shader</strong></p>
  
  <pre><code>// Originally taken from: http://www.ozone3d.net/tutorials/image_filtering_p2.php#part_2
  
  #define KERNEL_SIZE 9
  
  float kernel[KERNEL_SIZE];
  
  uniform sampler2D colorMap;
  uniform float width;
  uniform float height;
  
  float step_w = (1.0/width);
  float step_h = (1.0/height);
  
  // float step_w = 20.0;
  // float step_h = 20.0;
  
  vec2 offset[KERNEL_SIZE];
  
  void main(void)
  {
     int i = 0;
     vec4 sum = vec4(0.0);
  
     offset[0] = vec2(-step_w, -step_h);  // south west
     offset[1] = vec2(0.0, -step_h);      // south
     offset[2] = vec2(step_w, -step_h);       // south east
  
     offset[3] = vec2(-step_w, 0.0);      // west
     offset[4] = vec2(0.0, 0.0);          // center
     offset[5] = vec2(step_w, 0.0);       // east
  
     offset[6] = vec2(-step_w, step_h);       // north west
     offset[7] = vec2(0.0, step_h);       // north
     offset[8] = vec2(step_w, step_h);        // north east
  
  
  // Gaussian kernel
  // 1 2 1
  // 2 4 2
  // 1 2 1
  
  
     kernel[0] = 1.0;     kernel[1] = 2.0;    kernel[2] = 1.0;
     kernel[3] = 2.0; kernel[4] = 4.0;    kernel[5] = 2.0;
     kernel[6] = 1.0;     kernel[7] = 2.0;    kernel[8] = 1.0;
  
  
  // TODO make grayscale first
  // Laplacian Filter
  // 0   1   0
  // 1  -4   1
  // 0   1   0
  
  /*
  kernel[0] = 0.0;    kernel[1] = 1.0;    kernel[2] = 0.0;
  kernel[3] = 1.0;    kernel[4] = -4.0;   kernel[5] = 1.0;
  kernel[6] = 0.0;   kernel[7] = 2.0; kernel[8] = 0.0;
  */
  
  // Mean Filter
  // 1  1  1
  // 1  1  1
  // 1  1  1
  
  /*
  kernel[0] = 1.0;    kernel[1] = 1.0;    kernel[2] = 1.0;
  kernel[3] = 1.0;    kernel[4] = 1.0;    kernel[5] = 1.0;
  kernel[6] = 1.0;   kernel[7] = 1.0; kernel[8] = 1.0;
  */
  
     if(gl_TexCoord[0].s&lt;0.5)
     {
         // For every pixel sample the neighbor pixels and sum up
         for( i=0; i&lt;KERNEL_SIZE; i++ )
         {
              // select the pixel with the concerning offset
              vec4 tmp = texture2D(colorMap, gl_TexCoord[0].st + offset[i]);
              sum += tmp * kernel[i];
         }
  
          sum /= 16.0;
     }
     else if( gl_TexCoord[0].s&gt;0.51 )
     {
          sum = texture2D(colorMap, gl_TexCoord[0].xy);
     }
     else // Draw a red line
     {
          sum = vec4(1.0, 0.0, 0.0, 1.0);
     }
  
     gl_FragColor = sum;
  }
  </code></pre>
  
  <p><strong>Vertex Shader</strong></p>
  
  <pre><code>void main(void)
  {
      gl_TexCoord[0] = gl_MultiTexCoord0;
      gl_Position = ftransform();
  }
  </code></pre>