setting up Vertex Array in LWJLG

i’m trying run a simple test to see how vertex arrays work (just drawing two triangles on screen), but sort of stuck/confused on how lwjgl does the buffer stuff array stuff here my code so far.


FloatBuffer vertices;
IntBuffer buf;


public void initVariables() {
		
	vertices = BufferUtils.createFloatBuffer(12);
		
	vertices.put(100).put(100).put(300).put(100).put(200).put(250).put(400).put(100).put(600).put(100).put(500).put(250);
	vertices.rewind();
		
	buf = BufferUtils.createIntBuffer(12);
	buf.put(0).put(1).put(2).put(3).put(4).put(5).put(6).put(7).put(8).put(9).put(10).put(11);
	buf.flip();
}

	
public void mainloop() {
	GL11.glClear(GL11.GL_COLOR_BUFFER_BIT | GL11.GL_DEPTH_BUFFER_BIT);
		
	GL11.glColor3f(1.0f, 1.0f, 1.0f);
		
	/*This is what it should do
	GL11.glBegin(GL11.GL_TRIANGLES);
		GL11.glVertex2f(100, 100);
		GL11.glVertex2f(300, 100);
		GL11.glVertex2f(200, 250);
			
		GL11.glVertex2f(400, 100);
		GL11.glVertex2f(600, 100);
		GL11.glVertex2f(500, 250);
	GL11.glEnd();*/
		
	GL11.glEnableClientState(GL11.GL_VERTEX_ARRAY);
	GL11.glVertexPointer(2, GL11.GL_FLOAT, buf);
	
	GL11.glDrawElements(GL11.GL_TRIANGLES, buf);
}
}

I don’t do any buffer flip()ing myself, I’m not sure what that is supposed to get you.

However the problem is most likely your use of glDrawElements(). glDrawElements() expects a buffer of indices, not a buffer of verts. You already specified your verts with glVertexPointer(). The function you want to render with is glDrawArrays().

the indices way is probably what i’m after then any idea how to do that?

IntBuffer ib = BufferUtils.createIntBuffer(12);
ib.put(0).put(1).put(2).put(3)…

GL11.glDrawElements(GL11.GL_TRIANGLES, ib);

You really have to flip your buffer in LWJGL as opposed to JOGL.

Otherwise your stuff Just Don’t Work.


GL11.glVertexPointer(2, GL11.GL_FLOAT, buf);

should be:


GL11.glVertexPointer(2, 0, buf);

as the second parameter is the stride, not the type.

DP


import java.nio.FloatBuffer;
import java.nio.IntBuffer;

import org.lwjgl.BufferUtils;
import org.lwjgl.Sys;
import org.lwjgl.input.Keyboard;
import org.lwjgl.opengl.Display;
import org.lwjgl.opengl.GL11;

/**
 * 
 */
public class Game {

	/** Game title */
	public static final String GAME_TITLE = "My Game";

	/** Desired frame time */
	private static final int FRAMERATE = 60;

	/** Exit the game */
	private static boolean finished;

	/** Angle of rotating square */
	private static float angle;
	
	/** the vertex float buffer	 */
	private static FloatBuffer vertices;
	
	/** the indices */
	private static IntBuffer indices;

	/**
	 * Application init
	 * 
	 * @param args
	 *            Commandline args
	 */
	public static void main( String[] args ) {
		boolean fullscreen = (args.length == 1 && args[0].equals("-fullscreen"));

		try {
			init(fullscreen);
			run();
		} catch (Exception e) {
			e.printStackTrace(System.err);
			Sys.alert(GAME_TITLE, "An error occured and the game will exit.");
		} finally {
			cleanup();
		}
		System.exit(0);
	}

	/**
	 * Initialise the game
	 * 
	 * @throws Exception
	 *             if init fails
	 */
	private static void init( boolean fullscreen ) throws Exception {
		// Create a fullscreen window with 1:1 orthographic 2D projection
		// (default)
		Display.setTitle(GAME_TITLE);
		Display.setFullscreen(fullscreen);

		// Enable vsync if we can (due to how OpenGL works, it cannot be
		// guarenteed to always work)
		Display.setVSyncEnabled(true);

		// Create default display of 640x480
		Display.create();
		
		vertices = BufferUtils.createFloatBuffer(4 * 2);
		vertices.put(-50).put(-50);
		vertices.put(50).put(-50);
		vertices.put(50).put(50);
		vertices.put(-50).put(50);
		vertices.flip();
		
		indices = BufferUtils.createIntBuffer(6);
		indices.put(0).put(1).put(2).put(0).put(2).put(3);
		indices.flip();
	}

	/**
	 * Runs the game (the "main loop")
	 */
	private static void run() {

		while (!finished) {
			// Always call Window.update(), all the time - it does some behind
			// the
			// scenes work, and also displays the rendered output
			Display.update();

			// Check for close requests
			if (Display.isCloseRequested()) {
				finished = true;
			}

			// The window is in the foreground, so we should play the game
			else if (Display.isActive()) {
				logic();
				render();
				Display.sync(FRAMERATE);
			}

			// The window is not in the foreground, so we can allow other stuff
			// to run and
			// infrequently update
			else {
				try {
					Thread.sleep(100);
				} catch (InterruptedException e) {
				}
				logic();

				// Only bother rendering if the window is visible or dirty
				if (Display.isVisible() || Display.isDirty()) {
					render();
				}
			}
		}
	}

	/**
	 * Do any game-specific cleanup
	 */
	private static void cleanup() {
		// Close the window
		Display.destroy();
	}

	/**
	 * Do all calculations, handle input, etc.
	 */
	private static void logic() {
		// Example input handler: we'll check for the ESC key and finish the
		// game instantly when it's pressed
		if (Keyboard.isKeyDown(Keyboard.KEY_ESCAPE)) {
			finished = true;
		}

		// Rotate the square
		angle += 2.0f % 360;
	}

	private static void render() {
		// clear the screen
		GL11.glClear(GL11.GL_COLOR_BUFFER_BIT | GL11.GL_STENCIL_BUFFER_BIT);

		// center square according to screen size
		GL11.glPushMatrix();
		GL11.glTranslatef(Display.getDisplayMode().getWidth() / 2, Display.getDisplayMode().getHeight() / 2, 0.0f);

		// rotate square according to angle
		GL11.glRotatef(angle, 0, 0, 1.0f);

		// render the square
		GL11.glEnableClientState(GL11.GL_VERTEX_ARRAY);
		GL11.glVertexPointer(2, 0, vertices);
		
		GL11.glDrawElements(GL11.GL_TRIANGLES, indices);

		GL11.glPopMatrix();
	}
}

Main parts are init and render.

DP

ok thx dp, sorted the problem with the above code too
here the correction for the record


GL11.glVertexPointer(2, GL11.GL_FLOAT, buf);

should have been


GL11.glVertexPointer(2, 0, vertices);

and


vertices.rewind();

was


vertices.flip();

although i’ve been told that .flip() and rewind() shouldn’t really affect the out come!

thx

Yeah, flip() is only useful if you want to change the limit.

So for instance

FloatBuffer fb = BufferUtils.createFloatBuffer(10);

fb.put(10).put(10);
fp.flip();

you end up with a fb with pos=0 and limit=2 (instead of the 10 from initialization)

If your buffer is already the correct size, you can just use rewind() which is what I usually do:

FloatBuffer fb = BufferUtils.createFloatBuffer(2);

fb.put(10).put(10);
fp.rewind();

So in other words, flip() is used when you have a large scratch Buffer and only want to use a portion of it.