Gamasutra: The Art & Business of Making Gamesspacer
View All     RSS
October 23, 2014
arrowPress Releases
October 23, 2014
PR Newswire
View All
View All     Submit Event





If you enjoy reading this site, you might also want to check out these UBM Tech sites:


 
LibGDX in Depth series – Entry 02
by Vijay Kartick Prem Kumar on 04/07/14 02:07:00 am

The following blog post, unless otherwise noted, was written by a member of Gamasutra’s community.
The thoughts and opinions expressed are those of the writer and not Gamasutra or its parent company.

 

Blog Source http://www.jaykalabs.com/blog/

In our Previous post LibGDX in Depth series – Entry 01, we created our first triangle in LibGDX. Now we’ll see what happens behind the scene when we run that code . Source code for previous entry is here.  Explaining meshes requires more than one entry. So in this entry i’ll discuss how meshes are normally sent with Opengl and in the next entry i’ll  continue on how LibGDX hides these details from developer.

Messing with Meshes

In OpenGL in order to draw anything we create meshes and shade them with shaders. Simple right. Mesh can be as simple as a quad or as complex as an entire city environment. Mesh class is written in com.badlogic.gdx.graphics.Mesh.java

Mesh is made of vertices and each vertex has attributes such as position (non-optional), color, texcoord ,normal,etc. These vertex attributes can be stored as vertex array (in RAM) or as Vertex Buffer Objects (in GPU RAM) .For passing each of these attributes to vertex shader as vertex array in pure OpenGL we have to

1) Get the attribute reference location for the shader program using opengl funtion glGetAttribLocation

 
 
String attribute_name="a_position";
attribute_position = glGetAttribLocation (program, attribute_name);

a_position is attribute name you give in your vertex shader. LibGDX uses “a_” attributes for attribute,
“u_” for uniforms,”v_” for varying. We’ll see what each of these are in shaders section

2) Then enable vertex attribute array and point the array to the location we got previously

 
 
 
 
 
 
 
glEnableVertexAttribArray(attribute_position );
/* Describe our vertices array to OpenGL (it can't guess its format automatically) */
 glVertexAttribPointer( attribute_position, // attribute
 2, // number of elements per vertex, here (x,y)
GL_FLOAT, // the type of each element
GL_FALSE, // take our values as-is
0, // no extra data between each position
triangle_vertices_position // pointer to the float array );

For vertex Buffer Objects

1) Get attribute location as before

 
 
String attribute_name="a_position";
attribute_position = glGetAttribLocation (program, attribute_name);

2) We create the VBO buffer first

 
 
 
glGenBuffers(1, &vertexBuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(triangle_vertices_position), triangle_vertices_position, GL_STATIC_DRAW);

The above code uses GL_STATIC _DRAW as buffer usage hint

  • GL_STATIC_DRAW is for vertex buffers that are rendered many times, and whose contents are specified once and never change.
  • GL_DYNAMIC_DRAW is for vertex buffers that are rendered many times, and whose contents change during the rendering loop.
  • GL_STREAM_DRAW is for vertex buffers that are rendered a small number of times and then discarded.

3)Point the buffer to the location we got in step 1

 
 
 
glEnableVertexAttribArray(attribute_position);
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glVertexAttribPointer(attribute_position, 2, GL_FLOAT, GL_FALSE,
0,triangle_vertices_position));

The above code is only for position of vertices. We have to send optional attributes such as color, normals ,etc. LibGDX makes sending all these data very simple.  We used 0nly 3 lines of code for doing all the above.

 
 
 
 
mesh = new Mesh(true, 3, 3, VertexAttribute.Position(), VertexAttribute.ColorUnpacked());
mesh.setVertices(new float[] {-0.5f, -0.5f, 0, 1, 0.4f, 1, 1, 0.5f, -0.5f, 0, 1, 0.2f, 0f, 1, 0.5f, 0.5f, 0,
 1, 1, 1,1}); // Interleaved vertex attributes data
mesh.setIndices(new short[] {0, 1, 2});

The Constructor for a new mesh object in LibGDX is

 
public Mesh (boolean isStatic, int maxVertices, int maxIndices, VertexAttribute... attributes)

Setting isStaic to true creates a VertexBufferObject/VertexBufferObjectSubData and IndexBufferObject instead of Vertex and index array.
VertexAttribute class takes care of details of which type of attribute we are specifying.

There is also the managed mesh concept to deal with. I’ll dive into the Mesh class in next entry.


Related Jobs

Avalanche Studios
Avalanche Studios — New York, New York, United States
[10.22.14]

UI Programmer
Avalanche Studios
Avalanche Studios — New York, New York, United States
[10.22.14]

UI Artist/Designer
Wargaming.net
Wargaming.net — Hunt Valley, Maryland, United States
[10.22.14]

Lead UI Engineer
Wargaming.net
Wargaming.net — Chicago, Illinois, United States
[10.22.14]

Lead UI Engineer






Comments



none
 
Comment: