1

Below of my main class I am trying to render a obj from a blender .obj file after reformatting it to (supposedly) work for my rendering it gives the error. How can I fix this?

Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: -1
at java.util.ArrayList.elementData(Unknown Source)
at java.util.ArrayList.get(Unknown Source)
at flow_control.MainLoop.render(MainLoop.java:85)
    at flow_control.MainLoop.main(MainLoop.java:45)

Main class:

package flow_control;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;

import org.lwjgl.LWJGLException;
import org.lwjgl.input.Keyboard;
import org.lwjgl.opengl.Display;
import org.lwjgl.opengl.DisplayMode;
import org.lwjgl.util.glu.GLU;
import org.lwjgl.util.vector.Vector3f;
import org.newdawn.slick.opengl.Texture;
import org.newdawn.slick.opengl.TextureLoader;
import org.newdawn.slick.util.ResourceLoader;

import static org.lwjgl.opengl.GL11.*;


public class MainLoop {
    MainLoop(){
        camera = new Camera(this);
        loadTextures();
    }
private static final int WIDTH = 1280
private static final int HEIGHT = 700;
boolean[] keys = new boolean[256];
Camera camera;
Texture TexFloor;
Texture TexWhite;
Model m = null;

public static void main(String[] args) {
    System.out.println("S");
    try {
        Display.setDisplayMode(new DisplayMode(WIDTH, HEIGHT));
        Display.create();
    } catch (LWJGLException e) {
        e.printStackTrace();
    }
    MainLoop game = new MainLoop();
    game.load();
    game.loadTextures();
    while(!Keyboard.isKeyDown(Keyboard.KEY_ESCAPE)){
        game.update();
        game.render();
        Display.update();
        Display.sync(60);
    }
    Display.destroy();
    System.exit(0);
}
private void loadTextures(){
    try{
        TexFloor = TextureLoader.getTexture("JPG", ResourceLoader.getResourceAsStream("res/floor.jpg"));
    }catch(FileNotFoundException e) {
        System.err.println("Could not find textures");
        e.printStackTrace();
    }catch(IOException e){
        System.err.println("IO problem");
        e.printStackTrace();
    }

}
public void render() {
    clearScreen();

    camera.translatePostion();
    glBegin(GL_QUADS);
        glTexCoord2f(0, 0);
        glVertex3f(0, 0, 0);

        glTexCoord2f(128/8, 0);
        glVertex3f(500, 0, 0);

        glTexCoord2f(128/8, 128/8);
        glVertex3f(500, 0, 500);

        glTexCoord2f(0, 128/8);
        glVertex3f(0, 0, 500);

    glEnd();

    glBegin(GL_TRIANGLES);
        for (Faces face : m.faces) {
//error occurs on the line below
            Vector3f n1 = m.normals.get((int) face.normals.x - 1);
            glNormal3f(n1.x, n1.y, n1.z);
            Vector3f v1 = m.vertices.get((int) face.Vertex.x - 1);
            glNormal3f(v1.x, v1.y, v1.z);
            Vector3f n2 = m.normals.get((int) face.normals.y - 1);
            glNormal3f(n2.x, n2.y, n2.z);
            Vector3f v2 = m.vertices.get((int) face.Vertex.y - 1);
            glNormal3f(v2.x, v2.y, v2.z);
            Vector3f n3 = m.normals.get((int) face.normals.z - 1);
            glNormal3f(n3.x, n3.y, n3.z);
            Vector3f v3 = m.vertices.get((int) face.Vertex.z - 1);
            glNormal3f(v3.x, v3.y, v3.z);
        }

    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT ); 
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );
    TexFloor.bind();

}
public void load() {
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();

    GLU.gluPerspective((float) 100, WIDTH/HEIGHT, 0.001f, 1000);
    glMatrixMode(GL_MODELVIEW);

    glEnable(GL_TEXTURE_2D);
    glShadeModel(GL_SMOOTH);
    glClearColor(0.0f, 0.0f, 0.0f, 0.5f);
    glClearDepth(1.0f);
    glEnable(GL_DEPTH_TEST);
    glDepthFunc(GL_LEQUAL);
    glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
    try{
        m = OBJLoader.loadModel(new File("res/tree.obj"));
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }

}
public void clearScreen() {
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glLoadIdentity();
}
public void update() {
    mapKeys();
    camera.update();
}
private void mapKeys(){
    for(int i=0;i<keys.length; i++) {
        keys[i] = Keyboard.isKeyDown(i);
         }
    }
}

Class OBJLoader:

package flow_control;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;

import org.lwjgl.util.vector.Vector3f;

public class OBJLoader {
    public static Model loadModel(File f) throws FileNotFoundException,     IOException {
    BufferedReader reader = new BufferedReader(new FileReader(f));
    Model m = new Model();
    String line;
    while((line = reader.readLine()) != null){
        //parse object
        if (line.startsWith("v ")){
            float x = Float.valueOf(line.split(" ")[1]);
            float y = Float.valueOf(line.split(" ")[2]);
            float z = Float.valueOf(line.split(" ")[3]);
            m.vertices.add(new Vector3f(x,y,z));
        } else if (line.startsWith("vn ")) {
            float x = Float.valueOf(line.split(" ")[1]);
            float y = Float.valueOf(line.split(" ")[2]);
            float z = Float.valueOf(line.split(" ")[3]);
            m.normals.add(new Vector3f(x,y,z));
        } else if (line.startsWith("f ")) {
            Vector3f vertexIndices = new Vector3f(Float.valueOf(line.split(" ")[1].split("/")[0]),Float.valueOf(line.split(" ")[2].split("/")[0]),Float.valueOf(line.split(" ")[3].split("/")[0]));
            Vector3f normalIndices = new Vector3f(Float.valueOf(line.split(" ")[1].split("/")[2]),Float.valueOf(line.split(" ")[2].split("/")[2]),Float.valueOf(line.split(" ")[3].split("/")[2]));
            m.faces.add(new Faces(vertexIndices, normalIndices));


        }
    }
    reader.close();
    return m;
    }
}

Class Model:

package flow_control;

import java.util.ArrayList;
import java.util.List;

import org.lwjgl.util.vector.Vector3f;

public class Model {
    public List<Vector3f> vertices = new ArrayList<Vector3f>();
    public List<Vector3f> normals = new ArrayList<Vector3f>();
    public List<Faces> faces = new ArrayList<Faces>();
    public Model(){

    }
}

Class Faces:

package flow_control;


import org.lwjgl.util.vector.Vector3f;

 public class Faces {
    public Vector3f Vertex = new Vector3f();
    public Vector3f normals = new Vector3f();

    public Faces(Vector3f vertex, Vector3f normal) {
        this.Vertex = vertex;
        this.normals = normals;
    }
}

Sorry if some of this is excessive I know the errors coming from line 85 but I can't seem to figure out how to fix it.

OBJ file example (slimmed down):

# Blender v2.74 (sub 0) OBJ File: ''

# www.blender.org

mtllib tree.mtl

o Mesh_default
v -0.163260 2.023340 -0.247879

v 0.163260 2.023340 -0.247878

v 0.163260 2.023340 0.247879

f 35//34 39//40 36//35

f 36//35 40//39 37//36

f 38//37 34//41 41//38

vn -0.259900 0.445500 -0.856700

vn 0.087800 0.445500 -0.891000

vn -0.422000 0.445500 -0.789600
6
  • Do you know what the error message means? Commented Jun 4, 2015 at 2:51
  • im going out of the boundry of my array i understand the concept of the error message but i cant figure out how to fix that Commented Jun 4, 2015 at 2:53
  • Please mark the line where the error occured with a comment. Commented Jun 4, 2015 at 6:20
  • in the top class i added the comment Commented Jun 4, 2015 at 6:30
  • What LWJGL version are you using? Commented Jun 4, 2015 at 6:57

1 Answer 1

2

You made a couple of typo's in your program.

First off, in your OBJLoader class

else if (line.startsWith("vm ")) 

Its looking for lines in the OBJ file that start with "vm " but your obj files uses "vn ". Simply change this and the array won't be empty anymore.

vn -0.259900 0.445500 -0.856700
vn 0.087800 0.445500 -0.891000
vn -0.422000 0.445500 -0.789600

Secondly, in the Faces class

public Faces(Vector3f vertex, Vector3f normal) 
{
    this.Vertex = vertex;
    this.normals = normals;
}

You are setting the "normals" variable equal to itself rather then the Vector3f in the constructor, change it to this.

    this.normals = normal;
Sign up to request clarification or add additional context in comments.

3 Comments

I actually caught that after continuously going over my code and that isnt causing the error but thanks for pointing it out
@Ryan I found something else, can you confirm if it works now?
@Ryan No need to thank me, accepting the answer is enough :)!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.