Sign in to follow this  

These VBO indices are still confusing me...

This topic is 4689 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Sorry for all the posts, but I feel like I've done everything I could possibly do, and a little more, to fix this situation. I want to load my terrain into the graphics card as a VBO, and then to use indices to draw it. Maybe I don't understand how indices work, but can anyone look at this code for me? First, I load the vertices:
	for(int x=0; x < m_mapWidth; ++x)
	{
		for(int z=0; z < m_mapLength; ++z)
		{
			int j=x+z*m_mapWidth;

			textureData[2*j]=x/((float)m_mapWidth);
			textureData[2*j+1]=1.0-(z/((float)m_mapLength));

			mapData[3*j]=x;
                        mapData[3*j+1]=GetHeight(x, z);
			mapData[3*j+2]=z;
		}
	}

So that should mean that if I go to mapData[3*(x+z*m_mapWidth)] then I have the point (x, Height(x, z), z), right? So then if I want to draw these points as a triangle strip, I need to draw them like:
5---4
|-/-|
3/--2
|-/-|
1/--0

Right? If so, then I don't understand why the following index doesn't work:
	int index=0;
	for(int z=0; z < m_mapWidth; ++z)
	{
		for(int x=0; x < m_mapLength; ++x)
		{
			m_indices[index++]=x+(z+1)*m_mapLength;
			m_indices[index++]=x+z*m_mapLength;
		}
	}

I then draw (or try to draw) the terrain using glDrawElements(GL_TRIANGLE_STRIP, m_mapLength*m_mapWidth*2, GL_UNSIGNED_SHORT, (GLvoid*)m_indices) Where am I going wrong? The end result is a strip of correct terrain down the x-axis, but then there's a big trianglular prism of terrain that surrounds it, and a bunch of junk everywhere. Thanks for the help, this is really frustrating me!

Share this post


Link to post
Share on other sites
int j=x+z*m_mapWidth;

I am sure this is not the only problem with your code, but that statement should be

int j = x * m_mapWidth + z;

//and this
mapData[3*(x+z*m_mapWidth)];
//should be
mapData[3*(x * m_mapWidth + z];




And I am not sure if you are using CCW or CW rotations you might want to check that.

and your index buffer is setup wrong
I would use this pattern instead easier to read...


1---3---5
|-\-|-\-|
0--\2--\4


int index = 0;
int current_index = 0;
for(int z = 0; z < m_mapWidth; z++)
{
for(int x = 0; x < m_mapLength; x++)
{
current_index = z * m_mapWidth+ x;
m_indices[index++] = current_index;
m_indices[index++] = current_index + m_mapWidth;
}
}


Share this post


Link to post
Share on other sites
Still doesn't work... it's now a bunch of scattered strips that run down the z-axis...

Just to make sure that I didn't mistype anything, here is the full code that I have right now:

void HeightMap::LoadMap(std::string mapfile)
{
//....(Height loading, etc. done up to this point).....

float *mapData=new float[m_mapLength*m_mapWidth*3];

float *textureData=new float[m_mapLength*m_mapWidth*2];
m_indices=new unsigned short[m_mapLength*m_mapWidth*2];

m_tallestPoint=-HEIGHT_CONSTANT;
float tempHeight;
for(int x=0; x < m_mapWidth; ++x)
{
for(int z=0; z < m_mapLength; ++z)
{
int j=x*m_mapWidth+z;

textureData[2*j]=x/((float)m_mapWidth);
textureData[2*j+1]=1.0-(z/((float)m_mapLength));

mapData[3*j]=x;
if((tempHeight=mapData[3*j+1]=GetHeight(x, z)) > m_tallestPoint)
m_tallestPoint=tempHeight;
mapData[3*j+2]=z;
}
}

int index=0;
for(int z=0; z < m_mapWidth; ++z)
{
for(int x=0; x < m_mapLength; ++x)
{
unsigned short j = x * m_mapWidth+ z;
m_indices[index++]=j;
m_indices[index++]=j+m_mapWidth;
}
}

// send to a VBO
glGenBuffersARB(1, &m_vboNum);
glBindBufferARB(GL_ARRAY_BUFFER_ARB, m_vboNum);
//store data into buffer object, which is accelerated gc memory
//when available
glBufferDataARB(GL_ARRAY_BUFFER_ARB, sizeof(mapData[0])*m_mapLength*m_mapWidth*3,
mapData, GL_STATIC_DRAW_ARB);

// Generate And Bind The Texture Coordinate Buffer
glGenBuffersARB( 1, &m_texVBO );
glBindBufferARB( GL_ARRAY_BUFFER_ARB, m_texVBO );
// Load The Data
glBufferDataARB( GL_ARRAY_BUFFER_ARB, m_mapLength*m_mapWidth*2*sizeof(float),
textureData, GL_STATIC_DRAW_ARB );

delete [] textureData;
delete [] mapData;
}

void HeightMap::draw()
{
glColor3f(1, 1, 1);

if(!m_heightData)
return;

glEnableClientState( GL_VERTEX_ARRAY ); // Enable Vertex Arrays
glEnableClientState( GL_TEXTURE_COORD_ARRAY ); // Enable Texture Coord Arrays

glBindBufferARB( GL_ARRAY_BUFFER_ARB, m_vboNum );
glVertexPointer( 3, GL_FLOAT, 0, (char *) NULL ); // Set The Vertex Pointer To The Vertex Buffer
glBindBufferARB( GL_ARRAY_BUFFER_ARB, m_texVBO );
glTexCoordPointer( 2, GL_FLOAT, 0, (char *) NULL ); // Set The TexCoord Pointer To The TexCoord Buffer

glDisable(GL_CULL_FACE);
m_texture->Bind();
glDrawElements(GL_TRIANGLE_STRIP, m_mapLength*m_mapWidth*2, GL_UNSIGNED_SHORT,
(GLvoid*)m_indices);
m_texture->Unbind();
glEnable(GL_CULL_FACE);

// Disable Pointers
glDisableClientState( GL_VERTEX_ARRAY ); // Disable Vertex Arrays
glDisableClientState( GL_TEXTURE_COORD_ARRAY ); // Disable Texture Coord Arrays
}



This is just such a confusing and frustrating problem for me... I've been stuck just trying to figure out how to brute force this terrain using indices for about 4 days now. Before I was just storing the vertices in order (with repeated verts, etc.) and it was working perfectly. Obviously that method is wasteful of graphics memory, so I'd like to switch, but I honestly can't figure out what's wrong.

Thanks!

Share this post


Link to post
Share on other sites
EDIT: Solved it, finally.

It turns out that the unsigned short couldn't hold the vertex numbers... I up'd it to an unsigned int and it works.

Geez, what a trip.

Thanks to everyone for the help!

[Edited by - sirSolarius on February 8, 2005 9:40:01 PM]

Share this post


Link to post
Share on other sites

This topic is 4689 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this