Difference between revisions of "VBO - just examples"

From OpenGL Wiki
Jump to: navigation, search
(Forward compatibility is hereby banished from this wiki.)
 
Line 8: Line 8:
 
   struct MyVertex
 
   struct MyVertex
 
   {
 
   {
     float x, y, z;        //Vertex
+
     float x, y, z;        // Vertex
     float nx, ny, nz;    //Normal
+
     float nx, ny, nz;    // Normal
     float s0, t0;        //Texcoord0
+
     float s0, t0;        // Texcoord0
 
   };
 
   };
 
    
 
    
 
   MyVertex pvertex[3];
 
   MyVertex pvertex[3];
   //VERTEX 0
+
   // VERTEX 0
 
   pvertex[0].x = 0.0;
 
   pvertex[0].x = 0.0;
 
   pvertex[0].y = 0.0;
 
   pvertex[0].y = 0.0;
Line 23: Line 23:
 
   pvertex[0].s0 = 0.0;
 
   pvertex[0].s0 = 0.0;
 
   pvertex[0].t0 = 0.0;
 
   pvertex[0].t0 = 0.0;
   //VERTEX 1
+
   // VERTEX 1
 
   pvertex[1].x = 1.0;
 
   pvertex[1].x = 1.0;
 
   pvertex[1].y = 0.0;
 
   pvertex[1].y = 0.0;
Line 32: Line 32:
 
   pvertex[1].s0 = 1.0;
 
   pvertex[1].s0 = 1.0;
 
   pvertex[1].t0 = 0.0;
 
   pvertex[1].t0 = 0.0;
   //VERTEX 2
+
   // VERTEX 2
 
   pvertex[2].x = 0.0;
 
   pvertex[2].x = 0.0;
 
   pvertex[2].y = 1.0;
 
   pvertex[2].y = 1.0;
Line 55: Line 55:
 
   glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(ushort)*3, pindices, GL_STATIC_DRAW);
 
   glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(ushort)*3, pindices, GL_STATIC_DRAW);
 
    
 
    
   //Define this somewhere in your header file
+
   // Define this somewhere in your header file
 
   #define BUFFER_OFFSET(i) ((void*)(i))
 
   #define BUFFER_OFFSET(i) ((void*)(i))
 
    
 
    
 
   glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
 
   glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
 
   glEnableClientState(GL_VERTEX_ARRAY);
 
   glEnableClientState(GL_VERTEX_ARRAY);
   glVertexPointer(3, GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(0));   //The starting point of the VBO, for the vertices
+
   glVertexPointer(3, GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(0));   // The starting point of the VBO, for the vertices
 
   glEnableClientState(GL_NORMAL_ARRAY);
 
   glEnableClientState(GL_NORMAL_ARRAY);
   glNormalPointer(GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(12));   //The starting point of normals, 12 bytes away
+
   glNormalPointer(GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(12));     // The starting point of normals, 12 bytes away
 
   glClientActiveTexture(GL_TEXTURE0);
 
   glClientActiveTexture(GL_TEXTURE0);
 
   glEnableClientState(GL_TEXTURE_COORD_ARRAY);
 
   glEnableClientState(GL_TEXTURE_COORD_ARRAY);
   glTexCoordPointer(2, GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(24));   //The starting point of texcoords, 24 bytes away
+
   glTexCoordPointer(2, GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(24)); // The starting point of texcoords, 24 bytes away
 
    
 
    
 
   glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
 
   glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
   //To render, we can either use glDrawElements or glDrawRangeElements
+
   // To render, we can either use glDrawElements or glDrawRangeElements
   //The is the number of indices. 3 indices needed to make a single triangle
+
   // The is the number of indices. 3 indices needed to make a single triangle
   glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   //The starting point of the IBO
+
   glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   // The starting point of the IBO
   //0 and 3 are the first and last vertices
+
   // 0 and 3 are the first and last vertices
   //glDrawRangeElements(GL_TRIANGLES, 0, 3, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   //The starting point of the IBO
+
   // glDrawRangeElements(GL_TRIANGLES, 0, 3, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   // The starting point of the IBO
   //glDrawRangeElements may or may not give a performance advantage over glDrawElements
+
   // glDrawRangeElements may or may not give a performance advantage over glDrawElements
 
</source>
 
</source>
 
#Don't forget to glDisableClientState.
 
#Don't forget to glDisableClientState.
Line 92: Line 92:
 
   struct MyVertex
 
   struct MyVertex
 
   {
 
   {
     float x, y, z;        //Vertex
+
     float x, y, z;        // Vertex
     float nx, ny, nz;    //Normal
+
     float nx, ny, nz;    // Normal
     float s0, t0;        //Texcoord0
+
     float s0, t0;        // Texcoord0
 
   };
 
   };
 
    
 
    
 
   MyVertex pvertex[3];
 
   MyVertex pvertex[3];
   //VERTEX 0
+
   // VERTEX 0
 
   pvertex[0].x = 0.0;
 
   pvertex[0].x = 0.0;
 
   pvertex[0].y = 0.0;
 
   pvertex[0].y = 0.0;
Line 107: Line 107:
 
   pvertex[0].s0 = 0.0;
 
   pvertex[0].s0 = 0.0;
 
   pvertex[0].t0 = 0.0;
 
   pvertex[0].t0 = 0.0;
   //VERTEX 1
+
   // VERTEX 1
 
   pvertex[1].x = 1.0;
 
   pvertex[1].x = 1.0;
 
   pvertex[1].y = 0.0;
 
   pvertex[1].y = 0.0;
Line 116: Line 116:
 
   pvertex[1].s0 = 1.0;
 
   pvertex[1].s0 = 1.0;
 
   pvertex[1].t0 = 0.0;
 
   pvertex[1].t0 = 0.0;
   //VERTEX 2
+
   // VERTEX 2
 
   pvertex[2].x = 0.0;
 
   pvertex[2].x = 0.0;
 
   pvertex[2].y = 1.0;
 
   pvertex[2].y = 1.0;
Line 139: Line 139:
 
   glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(ushort)*3, pindices, GL_STATIC_DRAW);
 
   glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(ushort)*3, pindices, GL_STATIC_DRAW);
 
    
 
    
   //Define this somewhere in your header file
+
   // Define this somewhere in your header file
 
   define BUFFER_OFFSET(i) ((char *)NULL + (i))
 
   define BUFFER_OFFSET(i) ((char *)NULL + (i))
 
    
 
    
 
   glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
 
   glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
   glEnableVertexAttribArray(0);    //We like submitting vertices on stream 0 for no special reason
+
   glEnableVertexAttribArray(0);    // We like submitting vertices on stream 0 for no special reason
   glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(0));   //The starting point of the VBO, for the vertices
+
   glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(0));     // The starting point of the VBO, for the vertices
   glEnableVertexAttribArray(1);    //We like submitting normals on stream 1 for no special reason
+
   glEnableVertexAttribArray(1);    // We like submitting normals on stream 1 for no special reason
   glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(12));    //The starting point of normals, 12 bytes away
+
   glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(12));    // The starting point of normals, 12 bytes away
   glEnableVertexAttribArray(2);    //We like submitting texcoords on stream 2 for no special reason
+
   glEnableVertexAttribArray(2);    // We like submitting texcoords on stream 2 for no special reason
   glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(24));   //The starting point of texcoords, 24 bytes away
+
   glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(24));     // The starting point of texcoords, 24 bytes away
 
    
 
    
 
   glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
 
   glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
   //To render, we can either use glDrawElements or glDrawRangeElements
+
   // To render, we can either use glDrawElements or glDrawRangeElements
   //The is the number of indices. 3 indices needed to make a single triangle
+
   // The is the number of indices. 3 indices needed to make a single triangle
   glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   //The starting point of the IBO
+
   glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   // The starting point of the IBO
   //0 and 3 are the first and last vertices
+
   // 0 and 3 are the first and last vertices
   //glDrawRangeElements(GL_TRIANGLES, 0, 3, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   //The starting point of the IBO
+
   // glDrawRangeElements(GL_TRIANGLES, 0, 3, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));   //The starting point of the IBO
   //glDrawRangeElements may or may not give a performance advantage over glDrawElements
+
   // glDrawRangeElements may or may not give a performance advantage over glDrawElements
 
</source>
 
</source>
 
#Don't forget to glDisableVertexAttribArray.
 
#Don't forget to glDisableVertexAttribArray.

Latest revision as of 10:32, 3 January 2018

Render A Triangle

This example assumes C++ or a similar language.

Warning : this is not a "tutorial" page. There isn't much code commenting or explanation of the functions. This page is referenced by other pages on this Wiki. We are using VBOs and glVertexPointer, glNormalPointer, glTexCoordPointer and glEnableClientState in the code below. The vertex format is VNT which means vertex and normals and texcoords. Since glVertexPointer and those other functions are deprecated in GL 3.0 and removed in core 3.1 and above contexts, you should in fact use glVertexAttribPointer in modern code. Look further down for the example with glVertexAttribPointer.

  struct MyVertex
  {
    float x, y, z;        // Vertex
    float nx, ny, nz;     // Normal
    float s0, t0;         // Texcoord0
  };
  
  MyVertex pvertex[3];
  // VERTEX 0
  pvertex[0].x = 0.0;
  pvertex[0].y = 0.0;
  pvertex[0].z = 0.0;
  pvertex[0].nx = 0.0;
  pvertex[0].ny = 0.0;
  pvertex[0].nz = 1.0;
  pvertex[0].s0 = 0.0;
  pvertex[0].t0 = 0.0;
  // VERTEX 1
  pvertex[1].x = 1.0;
  pvertex[1].y = 0.0;
  pvertex[1].z = 0.0;
  pvertex[1].nx = 0.0;
  pvertex[1].ny = 0.0;
  pvertex[1].nz = 1.0;
  pvertex[1].s0 = 1.0;
  pvertex[1].t0 = 0.0;
  // VERTEX 2
  pvertex[2].x = 0.0;
  pvertex[2].y = 1.0;
  pvertex[2].z = 0.0;
  pvertex[2].nx = 0.0;
  pvertex[2].ny = 0.0;
  pvertex[2].nz = 1.0;
  pvertex[2].s0 = 0.0;
  pvertex[2].t0 = 1.0;
  
  glGenBuffers(1, VertexVBOID);
  glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
  glBufferData(GL_ARRAY_BUFFER, sizeof(MyVertex)*3, &pvertex[0].x, GL_STATIC_DRAW);
  
  ushort pindices[3];
  pindices[0] = 0;
  pindices[1] = 1;
  pindices[2] = 2;
  
  glGenBuffers(1, &IndexVBOID);
  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
  glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(ushort)*3, pindices, GL_STATIC_DRAW);
  
  // Define this somewhere in your header file
  #define BUFFER_OFFSET(i) ((void*)(i))
  
  glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
  glEnableClientState(GL_VERTEX_ARRAY);
  glVertexPointer(3, GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(0));    // The starting point of the VBO, for the vertices
  glEnableClientState(GL_NORMAL_ARRAY);
  glNormalPointer(GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(12));      // The starting point of normals, 12 bytes away
  glClientActiveTexture(GL_TEXTURE0);
  glEnableClientState(GL_TEXTURE_COORD_ARRAY);
  glTexCoordPointer(2, GL_FLOAT, sizeof(MyVertex), BUFFER_OFFSET(24)); // The starting point of texcoords, 24 bytes away
  
  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
  // To render, we can either use glDrawElements or glDrawRangeElements
  // The is the number of indices. 3 indices needed to make a single triangle
  glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));    // The starting point of the IBO
  // 0 and 3 are the first and last vertices
  // glDrawRangeElements(GL_TRIANGLES, 0, 3, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));    // The starting point of the IBO
  // glDrawRangeElements may or may not give a performance advantage over glDrawElements
  1. Don't forget to glDisableClientState.
  2. Remember that as long as a VBO and IBO are bound, functions like glVertexPointer refer to the start address of a VBO.
  • You must bind glBindBuffer(GL_ARRAY_BUFFER, 0); and glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0); if you want to source a standard memory

location (RAM)

  • Don't forget to deallocate when your program will shut down.:
  glDeleteBuffers(1, &VertexVBOID);
  glDeleteBuffers(1, &IndexVBOID);

Render A Triangle #2

This example assumes C++ or a similar language.

Warning : this is not a "tutorial" page. There isn't much code commenting or explanation of the functions. This page is referenced by other pages on this Wiki. We are using VBOs and glVertexAttribPointer and glEnableVertexAttribArray in the code below. The vertex format is VNT which means vertex and normals and texcoords. The example below doesn't use VAO for the sake of simplicity. Please search this Wiki for pages that explain the concept of VAO. Also, we aren't using shaders but you must setup a shader and setup the binding for your vertex attributes to your shader for things to work.

  struct MyVertex
  {
    float x, y, z;        // Vertex
    float nx, ny, nz;     // Normal
    float s0, t0;         // Texcoord0
  };
  
  MyVertex pvertex[3];
  // VERTEX 0
  pvertex[0].x = 0.0;
  pvertex[0].y = 0.0;
  pvertex[0].z = 0.0;
  pvertex[0].nx = 0.0;
  pvertex[0].ny = 0.0;
  pvertex[0].nz = 1.0;
  pvertex[0].s0 = 0.0;
  pvertex[0].t0 = 0.0;
  // VERTEX 1
  pvertex[1].x = 1.0;
  pvertex[1].y = 0.0;
  pvertex[1].z = 0.0;
  pvertex[1].nx = 0.0;
  pvertex[1].ny = 0.0;
  pvertex[1].nz = 1.0;
  pvertex[1].s0 = 1.0;
  pvertex[1].t0 = 0.0;
  // VERTEX 2
  pvertex[2].x = 0.0;
  pvertex[2].y = 1.0;
  pvertex[2].z = 0.0;
  pvertex[2].nx = 0.0;
  pvertex[2].ny = 0.0;
  pvertex[2].nz = 1.0;
  pvertex[2].s0 = 0.0;
  pvertex[2].t0 = 1.0;
  
  glGenBuffers(1, VertexVBOID);
  glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
  glBufferData(GL_ARRAY_BUFFER, sizeof(MyVertex)*3, &pvertex[0].x, GL_STATIC_DRAW);
  
  ushort pindices[3];
  pindices[0] = 0;
  pindices[1] = 1;
  pindices[2] = 2;
  
  glGenBuffers(1, &IndexVBOID);
  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
  glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(ushort)*3, pindices, GL_STATIC_DRAW);
  
  // Define this somewhere in your header file
  define BUFFER_OFFSET(i) ((char *)NULL + (i))
  
  glBindBuffer(GL_ARRAY_BUFFER, VertexVBOID);
  glEnableVertexAttribArray(0);    // We like submitting vertices on stream 0 for no special reason
  glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(0));      // The starting point of the VBO, for the vertices
  glEnableVertexAttribArray(1);    // We like submitting normals on stream 1 for no special reason
  glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(12));     // The starting point of normals, 12 bytes away
  glEnableVertexAttribArray(2);    // We like submitting texcoords on stream 2 for no special reason
  glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(MyVertex), BUFFER_OFFSET(24));     // The starting point of texcoords, 24 bytes away
  
  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IndexVBOID);
  // To render, we can either use glDrawElements or glDrawRangeElements
  // The is the number of indices. 3 indices needed to make a single triangle
  glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));    // The starting point of the IBO
  // 0 and 3 are the first and last vertices
  // glDrawRangeElements(GL_TRIANGLES, 0, 3, 3, GL_UNSIGNED_SHORT, BUFFER_OFFSET(0));    //The starting point of the IBO
  // glDrawRangeElements may or may not give a performance advantage over glDrawElements
  1. Don't forget to glDisableVertexAttribArray.
  2. Remember that as long as a VBO and IBO are bound, glVertexAttribPointer refers to the start address of a VBO.
  • You must bind glBindBuffer(GL_ARRAY_BUFFER, 0); and glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0); if you want to source a standard memory

location (RAM)

  • Don't forget to deallocate when your program will shut down.
  glDeleteBuffers(1, &VertexVBOID);
  glDeleteBuffers(1, &IndexVBOID);