Mixing the Ortho and Perspective views: issues

Started by
4 comments, last by Specchum 18 years, 3 months ago
Yep, me again with yet another OGLES issue. :) Following on from the help I had from here with the view matrix last time, I have a camera that I can move around and rotate etc. Now I'm trying to render some sprites on the screen to display fonts and other 2d effects. I have a sprite class for this purpose that sets up a quad with u, v co-ords and has a render method to render the sprite, like this:

CSprite::CSprite(igInt32 id, CVector3 pos, CVector3 size)
{
 imageId = id;
 position = pos;
 scale = size;
	
 //build a quad centered on position
 vertex[0] = CVector3(-scale.x + position.x, position.y + scale.y,  position.z);
 vertex[1] = CVector3(-scale.x + position.x, position.y - scale.y, position.z);
 vertex[2] = CVector3(scale.x + position.x, position.y + scale.y, position.z);
 vertex[3] = CVector3(scale.x + position.x, position.y - scale.y, position.z);
};

//more stuff to set up tex-coords skipped here

//not the most efficient render method but I thought I'll start simple ;)
void CSprite::Render()
{
 igInt16 indices[6] = {0,1,2,2,1,3};
 glVertexPointer (3, GL_FIXED, 0,  vertex);
 glTexCoordPointer(3, GL_FIXED, 0, texCoord);
 glDrawElements(GL_TRIANGLES, 6 , GL_UNSIGNED_SHORT, indices);
};

My camera view matrix is being set up like this:

void CCamera::SetView()
{
 glMatrixMode(GL_MODELVIEW);
 glLoadIdentity();
 igFixed viewmatrix[16]=
 {
  right.x, up.x, -forward.x, 0,
  right.y, up.y, -forward.y, 0,
  right.z, up.z, -forward.z, 0,
  -(FixMul(right.x,position.x) + FixMul(right.y,position.y) +  FixMul(right.z,position.z)),
  -(FixMul(up.x, position.x) + FixMul(up.y , position.y) + FixMul(up.z , position.z)), 
  (FixMul(forward.x, position.x) + FixMul(forward.y, position.y) + FixMul(forward.z, position.z)), 
  ITOX(1)
};

 glMultMatrixx(viewmatrix);
 glTranslatex(-position.x, -position.y, -position.z);
};
FixMul is a function that multiplies two fixed point values together. I'm using OpenGL ES with BREW and so I'm using fix point mathematics. Which is why some GL functions have the 'x' suffix. Anyway, no problems with the view matrix. Everything looks and works fine. Now then when it's time to render something I do tell my render class to render a model viz (bear with me!):

void CRenderer::Render(CModel* model)
{
 glEnableClientState(GL_VERTEX_ARRAY);
 glEnableClientState(GL_NORMAL_ARRAY);
 glEnableClientState(GL_COLOR_ARRAY);
 glEnableClientState(GL_TEXTURE_COORD_ARRAY);   
 glEnable(GL_TEXTURE_2D);

 //cache the vertex size
 const igInt32 CVERTEX_SIZE = sizeof(CVertex);

 for(igInt32 i = 0; i < model->nMaterials; ++i)
 {
  igFixed mat_col[] = {model->materialBuffer.diffuse.r,
			model->materialBuffer.diffuse.g,
			model->materialBuffer.diffuse.b,
			model->materialBuffer.diffuse.a};
		
  glMaterialxv(GL_FRONT_AND_BACK, GL_DIFFUSE, mat_col);
  glBindTexture(GL_TEXTURE_2D, model->materialBuffer.texture->id);
  for (igInt32 j = 0; j < model->nMeshes; ++j)
  {
	if (model->mesh[j].materialId == model->materialBuffer.id)
	{
  		glVertexPointer (3, GL_FIXED,	CVERTEX_SIZE, (void *)  &model->mesh[j].renderBuffer->position);
 		glNormalPointer  (GL_FIXED,		CVERTEX_SIZE, (void *) &model->mesh[j].renderBuffer->normal);
		glColorPointer   (4, GL_FIXED,	CVERTEX_SIZE, (void *) &model->mesh[j].renderBuffer->diffuse);
		glTexCoordPointer(2, GL_FIXED,  CVERTEX_SIZE, (void *) &model->mesh[j].renderBuffer->u);
			
		glDrawElements(GL_TRIANGLES, model->mesh[j].nIndices * 3, GL_UNSIGNED_SHORT, model->mesh[j].indexBuffer);
	}
  } //mesh loop
 }	//material loop
	
 glFlush();
	
 glDisableClientState(GL_VERTEX_ARRAY);
 glDisableClientState(GL_NORMAL_ARRAY);
 glDisableClientState(GL_COLOR_ARRAY);
 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
Works well enough. Need to optimise it later on. When it's time to render the world and the sprite I do this (the last bit of code, really):

void CGame::ShowDisplay(void)
{
	renderer->BeginFrame();
	camera->SetView();

	renderer->Render(world);
	
        //setup ortho mode for sprite rendering	
	glMatrixMode(GL_PROJECTION);
	renderer->LoadIdentity();
	glOrthox(0,0,240,320,0,1);
	renderer->RenderSprites();
	
	//switch back to perspective mode
        glMatrixMode(GL_MODELVIEW);
        glLoadIdentity();
	renderer->EndFrame();
}
The above bit doesn't work though. If I comment the SetView call, then my sprites render correctly, but uncommenting it shows nothing on the screen. To render only the world I need to comment the entire ortho mode setting up process and not call the RenderSprites function. Can anyone tell me what I'm doing wrong here? Why am I not able to switch between the modes cleanly?
"There is no dark side of the moon." - Pink Floyd
Advertisement
To render the sprites, your need to switch back to the MODELVIEW matrix mode after setting ortho mode (before rendering the sprites). Then, when done with the sprites, you need to go back to projection mode with a glMatrixMode(GL_PROJECTION) and glFrustum() call. Once back in projection mode, don't forget to set the matrix mode back to MODELVIEW again.

As far as I know, setting ortho mode overrides the old projection mode, and therefor it needs to be reinstated again. Also, you should always be in MODELVIEW matrix mode when actually rendering. The other modes are for setting up perspective.
-Tom BlindGame Design and Developmenthttp://tomblind.squad-seven.comtomblind@squad-seven.com
void Begin2D ( void ){  glDisable ( GL_DEPTH_TEST );  glMatrixMode(GL_PROJECTION);  glPushMatrix();  glLoadIdentity();  gluOrtho2D(0, Width, 0, Height);  glMatrixMode(GL_MODELVIEW);  glPushMatrix();  glLoadIdentity();}void End2D ( void ){  glPopMatrix();  glMatrixMode(GL_PROJECTION);  glPopMatrix();  glMatrixMode(GL_MODELVIEW);  glEnable ( GL_DEPTH_TEST );}
-----"Master! Apprentice! Heartborne, 7th Seeker Warrior! Disciple! In me the Wishmaster..." Wishmaster - Nightwish
Wow. That's like, my code exactly. Function names and all.
-Tom BlindGame Design and Developmenthttp://tomblind.squad-seven.comtomblind@squad-seven.com
i have it from tips page of gamedev.ru
-----"Master! Apprentice! Heartborne, 7th Seeker Warrior! Disciple! In me the Wishmaster..." Wishmaster - Nightwish
Thanks a lot chaps! The code sure did the trick!
"There is no dark side of the moon." - Pink Floyd

This topic is closed to new replies.

Advertisement