Game Development Reference
In-Depth Information
Note that the vertex positions, texture coordinates, and normals do not have to be defined in
such a nice order. They could be intertwined if the software that saved the file chose to do so.
The indices given in an f statement are one based, rather than zero based (as in the case of a
Java array). Some software even outputs negative indices at times. This is permitted by the OBJ
format specification but is a major pain. We have to keep track of how many vertex positions,
texture coordinates, or vertex normals we have loaded so far and then add that negative index
to the respective number of positions, vertex coordinates, or normals, depending on what vertex
attribute that index is indicating.
Implementing an OBJ Loader
Our plan of attack will be to load the file completely into memory and to create a string per line.
We will also create temporary float arrays for all of the vertex positions, texture coordinates,
and normals that we are going to load. Their size will be equal to the number of lines in the OBJ
file times the number of components per attribute; that is, two for texture coordinates or three
for normals. By doing this, we overshoot the necessary amount of memory needed to store the
data, but that's still better than allocating new arrays every time we have filled them up.
We also do the same for the indices that define each triangle. While the OBJ format is indeed
an indexed format, we can't use those indices directly with our Vertices3 class. The reason
for this is that a vertex attribute might be reused by multiple vertices, so there's a one-to-many
relationship that is not allowed in OpenGL ES. Therefore, we'll use a nonindexed Vertices3
instance and simply duplicate the vertices. For our needs, that's OK.
Let's see how we can implement all of this. Listing 11-12 shows the code.
Listing 11-12. ObjLoader.java, a Simple Class for Loading a Subset of the OBJ Format
package com.badlogic.androidgames.framework.gl;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.List;
import com.badlogic.androidgames.framework.impl.GLGame;
public class ObjLoader {
public static Vertices3 load(GLGame game, String file) {
InputStream in = null ;
try {
in = game.getFileIO().readAsset(file);
List<String>lines = readLines (in);
float [] vertices = new float [lines.size()* 3];
float [] normals = new float [lines.size()* 3];
float [] uv = new float [lines.size()* 2];
 
Search WWH ::




Custom Search