Link to home
Start Free TrialLog in
Avatar of KVoet
KVoet

asked on

Why does my OpenGL framerate drop with CameraMovement when a texture comes into view

I'm working on a simple OpenGL program to draw a simple house.
I'm using GLUT since it's a requirement.

I have a camera class which changes the viewport en location of the camera using the keyboard and mouse.

The problem is that when I enable a single texture the program becomes very slow when these textures are in the viewport. When there are no textures in the viewport the performance is normal.

The textures are all small BMP's at 64x64 or maximum 128x128 large.
I also tried implementing a frame rate dependent movement but this hasn't helped the problem.
I'm using display lists to speed up the program but I haven't found any noticeable effect.
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#ifdef __APPLE__
#include <OpenGL/OpenGL.h>
#include <GLUT/glut.h>
#else
#include <GL/glut.h>
#endif
#include "helperfunctions.h"
#include "camera.h"
#include "kamer.h"
#include "muur.h"
#include "imageloader.h"
#define SCREEN_WIDTH 800
#define SCREEN_HEIGHT 600
#define GL_PI 3.1436f
#define cSpeed 15.0f
#define ROOF_LIST 1
#define HOUSE_LIST 2
#define LOGO_LIST 3
#define CLOUD_LIST 4
 
using namespace helperfunctions;
 
Camera cam;
GLuint _tex1;
GLuint _tex2;
GLuint _texArtesis;
GLuint _TexClouds;
GLuint _TexRoof;
GLuint _TexCeiling;
float FrameIntervalf;
GLuint loadTexture(Image* image) 
{
	GLuint textureId;
	glGenTextures(1, &textureId); //Make room for our texture
	glBindTexture(GL_TEXTURE_2D, textureID); //Tell OpenGL which texture to edit
	///////////////////////////////////////////////////////////////
	//Eigen settings voor begin texture, texture settings aanpassen?
	//Doen in main, na laden image met glBindTexture(GL_TEXTURE_2D, _TexVerwijzing)
	glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST);
	glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
	glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT );
	glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );
	///////////////////////////////////////////////////////////////////////////////
	//Map the image to the texture
	/*glTexImage2D(GL_TEXTURE_2D,                //Always GL_TEXTURE_2D
				 0,                            //0 for now
				 GL_RGB,                       //Format OpenGL uses for image
				 image->width, image->height,  //Width and height
				 0,                            //The border of the image
				 GL_RGB,						//GL_RGB, because pixels are stored in RGB format
				 GL_UNSIGNED_BYTE,				//GL_UNSIGNED_BYTE, because pixels are stored
												//as unsigned numbers
				 image->pixels);               //The actual pixel data*/
 
	//Omgevormd naar gluBuildMipmaps() voor hopelijk betere performance
	gluBuild2DMipmaps(GL_TEXTURE_2D, 3, image->width, image->height, GL_RGB, GL_UNSIGNED_BYTE, image->pixels);
	return textureId; //Returns the id of the texture
}
void Draw3DSGrid()
{
	// Turn the lines GREEN
	glColor3ub(0, 255, 0);
 
	// Draw a 1x1 grid along the X and Z axis'
	for(float i = -50; i <= 50; i += 1)
	{
		// Start drawing some lines
		glBegin(GL_LINES);
 
			// Do the horizontal lines (along the X)
			glVertex3f(-50, 0, i);
			glVertex3f(50, 0, i);
 
			// Do the vertical lines (along the Z)
			glVertex3f(i, 0, -50);
			glVertex3f(i, 0, 50);
 
		// Stop drawing lines
		glEnd();
	}
}
 
void reshape(int x, int y)
{
	if (y == 0 || x == 0) return;
	
	glMatrixMode(GL_PROJECTION);  
	glLoadIdentity();
	//gluPerspective bepaalt ons 3D Canvas, gluPersptive is beter als glOrtho
	//--> Verder weg van objecten = objecten worden kleiner
	//Bepaalt ook vanwaar tot waar openGL tekent
	gluPerspective(40.0,(GLdouble)x/(GLdouble)y,0.5,50.0);
	glMatrixMode(GL_MODELVIEW);
	glViewport(0,0,x,y);
}
 
void RenderRoof()
{		
	glNewList(ROOF_LIST, GL_COMPILE);
		glColor3f(1.0f, 1.0f, 1.0f);
		glEnable(GL_TEXTURE_2D);
		glEnable(GL_DEPTH_TEST);
		glColor3f((160.0f/255.0f),(82.0f/255.0f),(45.0f/255.0f));
		glBindTexture(GL_TEXTURE_2D, _tex2);
		
		
		glBegin(GL_TRIANGLES);
			/*Voorkant*/
			glTexCoord2f(5.0f, 5.0f); glVertex3f(0.0f, 7.0f, -5.0f); //Top
			glTexCoord2f(5.0f, 0.0f); glVertex3f(-11.0F, 4.0f, -5.0f); //Links
			glTexCoord2f(0.0f, 5.0f); glVertex3f(9.0f, 4.0f, -5.0f); //Rechts
 
			//Achterzijde
			glVertex3f(0.0f, 7.0f, -25.0f); //Top
			glVertex3f(-11.0F, 4.0f, -25.0f); //Links
			glVertex3f(9.5f, 4.0f, -25.0f); //Rechts
		glEnd();
		glBindTexture(GL_TEXTURE_2D, _TexRoof);
		glColor3f(1.0f, 1.0f, 1.0f);
		glBegin(GL_QUADS);
			glTexCoord2f(3.0, 0.0f); glVertex3f(0.0f, 7.0f, -25.0f);
			glTexCoord2f(3.0, 3.0f); glVertex3f(0.0f, 7.0f, -5.0f);
			glTexCoord2f(0.0, 3.0f); glVertex3f(9.3f,4.0f, -5.0f);
			glTexCoord2f(0.0, 0.0f); glVertex3f(9.3f, 4.0f, -25.0f);
 
			glTexCoord2f(3.0, 0.0f); glVertex3f(0.0f, 7.0f, -25.0f);
			glTexCoord2f(3.0, 3.0f); glVertex3f(0.0f, 7.0f, -5.0f);
			glTexCoord2f(0.0, 3.0f); glVertex3f(-10.0f,4.2f, -5.0f);
			glTexCoord2f(0.0, 0.0f); glVertex3f(-10.0f, 4.2f, -25.0f);
		glEnd();//Nodig voor volgende texture
			glBindTexture(GL_TEXTURE_2D, _TexCeiling);
		glBegin(GL_QUADS);
			glTexCoord2f(0.0, 5.0f); glVertex3f(-11.0f, 4.0f, -25.0f);
			glTexCoord2f(5.0, 5.0f); glVertex3f(-11.0f, 4.0f, -5.0f);
			glTexCoord2f(5.0, 0.0f); glVertex3f(9.5f,4.0f, -5.0f);
			glTexCoord2f(0.0, 0.0f); glVertex3f(9.5f, 4.0f, -25.0f);
		glEnd();
		glDisable(GL_TEXTURE_2D);
	glEndList();
}
void RenderArtesisLogo()
{
	glNewList(LOGO_LIST, GL_COMPILE);
		glEnable(GL_TEXTURE_2D);
		glBindTexture(GL_TEXTURE_2D, _texArtesis);
		glColor3f(1.0f, 1.0f, 1.0f);
		glBegin(GL_QUADS);
			glTexCoord2f(0.0f, 1.0f); glVertex3f(2.0, 3.0f, -4.9f);
			glTexCoord2f(1.0f, 1.0f); glVertex3f(6.0f, 3.0f, -4.9f);
			glTexCoord2f(1.0f, 0.0f); glVertex3f(6.0f, 1.0f, -4.9f);
			glTexCoord2f(0.0f, 0.0f); glVertex3f(2.0f, 1.0f, -4.9f);
		glEnd();
		glDisable(GL_TEXTURE_2D);
	glEndList();
}
 
void RenderHouse()
{
	glNewList(HOUSE_LIST, GL_COMPILE);
		kamer myRooms[5];
		glColor4f(1.0,1.0,1.0,1.0);
		myRooms[0] = kamer(-1.0,-15.0, 20.0, 20.0, 0, 3, _tex1);
		myRooms[1] = kamer(-8.0, -22.5, 4, 6,0,3, _tex2);
		myRooms[2] = kamer(4.0, -21.0, 8, 10, 3, 3, 0);
 
		for (int i=0;i<4;i++)
		{
			myRooms[i].display();
		}
	glEndList();
}
void RenderClouds()
{
	glNewList(CLOUD_LIST, GL_COMPILE);
		glEnable(GL_TEXTURE_2D);
		glBindTexture(GL_TEXTURE_2D, _TexClouds);
		glBegin(GL_QUADS);
			glTexCoord2f(3.0f, 0.0f); glVertex3f(-50.f, 8.0f, -50.0f);
			glTexCoord2f(3.0f, 3.0f); glVertex3f(50.0f, 8.0f, -50.0f);
			glTexCoord2f(0.0f, 3.0f); glVertex3f(50.0f,8.0f, 50.0f);
			glTexCoord2f(0.0f, 0.0f); glVertex3f(-50.0f, 8.0f, 50.0f);
		glEnd();
		glDisable(GL_TEXTURE_2D);
	glEndList();
}
 
void CalculateFrameRate()
{
	int frame=0,time,timebase=0;
 
	frame++;
	time=glutGet(GLUT_ELAPSED_TIME);
	if (time - timebase > 1000) {
		FrameIntervalf = frame*1000.0/(time-timebase);
	 	timebase = time;		
		frame = 0;
	}
 
}
void RenderScene(void)
{
	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
	glLoadIdentity();
	CalculateFrameRate();
	cam.Render();
	Draw3DSGrid();
	
	//DisplayLists aanroepen
	glCallList(HOUSE_LIST);
	glCallList(ROOF_LIST);
	glCallList(LOGO_LIST);
	glCallList(CLOUD_LIST);
	////////////////////////
	glFlush();  
	glutSwapBuffers();
}
void checkKeyboard(unsigned char key, int x, int y)
{
	float speed = cSpeed * FrameIntervalf;
	switch (key)
	{
	case 27: 
		exit(0);
	case 'e':
		cam.RotateY(-speed);
		RenderScene();
		break;
	case 'a':
		cam.RotateY(speed);
		RenderScene();
		break;
	case 'z':
		cam.MoveForwards(-speed);
		RenderScene();
		break;
	case 's':
		cam.MoveForwards(speed);
		RenderScene();
		break;
	case 'q':
		cam.StrafeRight(-speed);
		RenderScene();
		break;
	case 'd':
		cam.StrafeRight(speed);
		RenderScene();
		break;
	}
}
void checkMouse(int x, int y)
{
	float angleY, angleZ, angleX = 0.0f;
	int MiddenX = SCREEN_WIDTH >> 1;
	int MiddenY = SCREEN_HEIGHT >> 1;
	
	if (x == MiddenX && y == MiddenY) return;
	angleY = (float)( (MiddenX - x) ) / 10.0f;
	angleZ = (float)( (MiddenY - y) ) / 10.0f;
	angleX = angleX + angleZ;
	if(angleX > 1.0f)
		angleX = 1.0f;
	else if(angleX < -1.0f)
		angleX = -1.0f;
	else
		cam.RotateXYZ(Vect3d(angleX,angleY, 0.0f));
	glutWarpPointer(MiddenX,MiddenY);
}
 
int main (int argc, char **argv) {
	/*//////////////////Algemene Settings///////////////////////
	///Deze sectie bevat de algemene settings zoals resolutie///
	///Curormode, beelschermmode////////////////////////////////
	*///////////////////////////////////////////////////////////
	const char * FSMode = "800x600:16@75";
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB);
	glutGameModeString(FSMode);
	glutEnterGameMode();
	glutSetCursor(GLUT_CURSOR_NONE);
	glEnable(GL_DEPTH_TEST);
	
	/*//////////////////Camera Settings/////////////////////////
	///Deze sectie bevat de Camera Settings/////////////////////
	*///////////////////////////////////////////////////////////
	//cam.PlaatsCamera(0, 1.5f, 4,   0, 1.5f, 0,   0, 0.2, 0);
	cam.Move(Vect3d(0.0f, 1.5f, 4.0f));
	cam.MoveForwards(1.0f);
	/*//////////////////Texture Settings////////////////////////
	///Deze sectie bevat de algemene textures //////////////////
	*///////////////////////////////////////////////////////////
	//glEnable(GL_TEXTURE_2D);
	Image* img = loadBMP("brick.bmp");
	_tex1 = loadTexture(img);
	delete img;
	
	img = loadBMP("houtenBinnen.bmp");
	_tex2 = loadTexture(img);
	delete img;
 
	img = loadBMP("ArtesisPic.bmp");
	_texArtesis = loadTexture(img);
	delete img;
 
	img = loadBMP("Clouds.bmp");
	_TexClouds = loadTexture(img);
	delete img;
 
	img = loadBMP("Roof_Tex.bmp");
	_TexRoof = loadTexture(img);
	delete img;
 
	img = loadBMP("Ceiling_Tex.bmp");
	_TexCeiling = loadTexture(img);
	delete img;
 
	/*//////////////////glDisplayLists/////////////////////////////
	///Deze sectie bouwt onze Display Lists op/////////////////////
	*//////////////////////////////////////////////////////////////
	RenderRoof();
	RenderHouse();
	RenderArtesisLogo();
	RenderClouds();
 
	/*//////////////////glFuncties/////////////////////////////////
	///Deze sectie bevat de verwijzingen naar de OpenGL functies///
	*//////////////////////////////////////////////////////////////
	glutDisplayFunc(RenderScene);
	glutIdleFunc(RenderScene);
	glutReshapeFunc(reshape);
	glutKeyboardFunc(checkKeyboard);
	glutPassiveMotionFunc(checkMouse);
	glutMainLoop();
	return 0;  
}

Open in new window

Avatar of ikework
ikework
Flag of Germany image

you're calling gluBuild2DMipmaps for every texture you load.. when you remove it, do you have the same performance issues?
and put glTexImage2D back of course .. ;)
Avatar of KVoet
KVoet

ASKER

I was using glTexImage2D as you can see since it's commented out and I tried switching to mipmaps to actually increase performance. But there is no discernable change between the two.
ASKER CERTIFIED SOLUTION
Avatar of KVoet
KVoet

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
great .. :) for me its ok, if you ask for a delete-request ..