title: Xcode iOS GPUImage - drawing triangles over live video
body: <p>I am making use of Brad Larson's wonderful GPUImage library for image manipulation. Thank you Brad, great work.</p>
  
  <p>I am trying to add a new filter that will allow for objects to be drawn over a live video source.  </p>
  
  <p>This is early stages. At this point, I am just trying to draw 3 triangles over the video source.  Code follows.</p>
  
  <p>It seems to be working but I get an intermittent change in aspect ratio while this effect is applied.  and then it settles down.   The filterView is stretched vertically. looks like a strobe.</p>
  
  <p>HEADER:</p>
  
  <pre><code>//  GPUImageParticles.h
  #import &lt;GLKit/GLKit.h&gt;
  #import "GPUImageFilter.h"
  
  @interface GPUImageParticles : GPUImageFilter{
  
      GLint triVertexBufferIDUniform;
  
      GLuint triVertexBufferID;    
  }
  
  - (void)update:(CMTime)frameTime;
  - (void)setDrawColorRed:(GLfloat)redComponent green:(GLfloat)greenComponent blue:(GLfloat)blueComponent;
  
  
  
  @end
  </code></pre>
  
  <p>IMPLEMENTATION:</p>
  
  <pre><code>//  GPUImageParticles.m
  #import "GPUImageParticles.h"
  
  // SHADERS
  NSString *const kParticleGenVSString = SHADER_STRING
  (
   attribute vec4 position;
  
   void main()
   {
       gl_Position = position;
   }
   );
  
  NSString *const kParticleGenFSString = SHADER_STRING
  (
   uniform lowp vec3 drawColor;
  
   void main()
   {
       gl_FragColor = vec4(drawColor, 1.0);
   }
   );
  
  // END SHADERS
  
  @implementation GPUImageParticles
  
  
  /////////////////////////////////////////////////////////////////
  // This data type is used to store information for each vertex
  typedef struct {
      GPUVector3 positionCoords;
  }
  SceneVertex;
  
  
  /////////////////////////////////////////////////////////////////
  // Define vertex data for a triangle to use in example
  static const SceneVertex triVertices[] =
  {
      {{0.0f, 0.0f, 0.0f}},
      {{0.0f, 0.1f, 0.0f}},
      {{0.1f, 0.1f, 0.0f}},
  
  
      {{-0.3f, -0.7f, 0.0}}, // lower left corner
  
      {{ 0.3f, -0.7f, 0.0}}, // lower right corner
  
      {{ 0.01f, 0.5f, 0.0}}, // upper left corner
  
  
      {{-0.5f, -0.5f, 0.0}}, // lower left corner
  
      {{-0.25f, -0.25f, 0.0}}, // lower right corner
  
      {{-0.5f, -0.25f, 0.0}} // upper left corner
  
  };
  
  
  - (id)init;
  {
  
      if (!(self = [super initWithVertexShaderFromString:kParticleGenVSString fragmentShaderFromString:kParticleGenFSString]))
      {
          return nil;
      }
  
      runSynchronouslyOnVideoProcessingQueue(^{
  
          triVertexBufferIDUniform =[filterProgram uniformIndex:@"triVertexBuffer"];
  
          drawColorUniform = [filterProgram uniformIndex:@"drawColor"];
  
          [self setDrawColorRed:1.0 green:0.0 blue:1.0];
  
  
          glGenBuffers(1, // STEP 1
                       &amp;triVertexBufferID);
  
          glBindBuffer(GL_ARRAY_BUFFER, // STEP 2
                       triVertexBufferID);
  
          glBufferData( // STEP 3
                       GL_ARRAY_BUFFER, // Initialize buffer contents
                       sizeof(triVertices), // Number of bytes to copy
                       triVertices, // Address of bytes to copy
                       GL_STATIC_DRAW); // Hint: cache in GPU memory
  
  
          glBindBuffer(GL_ARRAY_BUFFER, 0);
  
  
      });
  
  
      return self;
  }
  
  - (void) dealloc;
  {
  
  }
  
  
  
  -(void)update:(CMTime)frameTime;
  {
      if (self.preventRendering)
      {
          return;
      }
  
      runSynchronouslyOnVideoProcessingQueue(^{
  
          [GPUImageContext setActiveShaderProgram:filterProgram];
  
          [self setFilterFBO];
  
          glClearColor(0.0, 0.0, 0.0, 0.0);
          glClear(GL_COLOR_BUFFER_BIT);
  
          glBlendEquation(GL_FUNC_ADD);
          glBlendFunc(GL_ONE, GL_ONE);
          glEnable(GL_BLEND);
  
          glVertexAttribPointer(filterPositionAttribute, 3, GL_FLOAT, GL_FALSE, sizeof(SceneVertex), triVertices);
  
          glDrawArrays(GL_TRIANGLES, 0, (unsigned int)9);
  
          glDisable(GL_BLEND);
  
          [self informTargetsAboutNewFrameAtTime:frameTime];
  
      });
  
  }
  
  
  
  - (void)setDrawColorRed:(GLfloat)redComponent green:(GLfloat)greenComponent blue:(GLfloat)blueComponent;
  {
      GPUVector3 drawColor = {redComponent, greenComponent, blueComponent};
  
      [self setVec3:drawColor forUniform:drawColorUniform program:filterProgram];
  }
  
  
  @end
  </code></pre>