[c++] Effective Rendering

Started by
9 comments, last by Yann L 15 years, 1 month ago
Hey, guys. I could use a little help with making a program render more effectively, if you don't mind lending me a few minutes of your time. I have been working on this small project for a little while now and I thought it was about time to try and improve my method of rendering. My goal of the project is to have a simple 3d fps-style game (not really caring about game aspects like AI or lighting at the moment, just trying to get the 3d environment and stuff up and running smoothly), as my final project in my high school C++ class. Basically I have multiple functions (cube, wall, .ect) for rendering, and the program has to call these functions every time the loop goes through. Then I use these functions to draw the world and everything in it. I believe that this method is very ineffective but I don't know of any other way. Would this be a good time to look into display lists, or would that help at all? Any other tips on making a better rendering engine? Thanks for your time and help! ->basic program model Main() { Window_Setup() Import_Textures() Init() Game_Loop() { Rendering() Input() Physics() } Destroy() } ->function for rendering cubes
void BuildCube(float x1, float y1, float z1, float x2, float y2, float z2, int tex_l, int tex_x, int tex_y)
{
    glBindTexture(GL_TEXTURE_2D, tex_l);
    glBegin(GL_QUADS);
    //bottom
    glTexCoord2f(0.0, 0.0); glVertex3f(x1, y1, z1); glTexCoord2f(tex_x, 0.0); glVertex3f(x2, y1, z1); glTexCoord2f(tex_x, tex_y); glVertex3f(x2, y2, z1); glTexCoord2f(0.0, tex_y); glVertex3f(x1, y2, z1);
    //top
    glTexCoord2f(0.0, 0.0); glVertex3f(x1, y1, z2); glTexCoord2f(tex_x, 0.0); glVertex3f(x2, y1, z2); glTexCoord2f(tex_x, tex_y); glVertex3f(x2, y2, z2); glTexCoord2f(0.0, tex_y); glVertex3f(x1, y2, z2);
    //sides
    glTexCoord2f(0.0, 0.0); glVertex3f(x1, y1, z1); glTexCoord2f(0.0, tex_y); glVertex3f(x1, y1, z2); glTexCoord2f(tex_x, tex_y); glVertex3f(x2, y1, z2); glTexCoord2f(tex_x, 0.0); glVertex3f(x2, y1, z1);
    glTexCoord2f(0.0, 0.0); glVertex3f(x2, y1, z1); glTexCoord2f(tex_x, 0.0); glVertex3f(x2, y2, z1); glTexCoord2f(tex_x, tex_y); glVertex3f(x2, y2, z2); glTexCoord2f(0.0, tex_y); glVertex3f(x2, y1, z2);
    glTexCoord2f(0.0, 0.0); glVertex3f(x2, y2, z1); glTexCoord2f(tex_x, 0.0); glVertex3f(x1, y2, z1); glTexCoord2f(tex_x, tex_y); glVertex3f(x1, y2, z2); glTexCoord2f(0.0, tex_y); glVertex3f(x2, y2, z2);
    glTexCoord2f(0.0, 0.0); glVertex3f(x1, y2, z1); glTexCoord2f(0.0, tex_y); glVertex3f(x1, y2, z2); glTexCoord2f(tex_x, tex_y); glVertex3f(x1, y1, z2); glTexCoord2f(tex_x, 0.0); glVertex3f(x1, y1, z1);
    glEnd();
}
Advertisement
First, an implementation note: ditch immediate mode (glBegin, glEnd, etc.) and learn to use Vertex Buffer Objects (VBO), or at least Vertex Arrays. Immediate mode is an archaic holdover, and you will benefit from moving on.

Next, don't hardcode your level design like this. Design your level in a 3D modelling application (Blender is free, if you don't have one already), and load it into your game from a model file. Again, you will thank yourself later, whether or not you see the point right now.

Tristam MacDonald. Ex-BigTech Software Engineer. Future farmer. [https://trist.am]

I think I am going to give vertex arrays a try. So far I have been able to setup a vertex array that renders all my code as before. But I am having trouble understanding how I can have the type of texture support that I did before. I already know how to setup the texture coordinates, but I don't see how I can have different textures assigned to different shapes without having a new array for each shape of one texture.

Is there a way to give multitexture support for these arrays?
You could indeed have multiple arrays, e.g. one per texture.

Another approach would be texture atlasses where all texture images are packed into a huge texture and texture coordinates are adjusted. However, if you're using fixed function (I assume you do), tiling will be very hard to achieve, if not impossible. Using shader's it's quite easy, but I assume they're out of scope right now.
If I was helpful, feel free to rate me up ;)If I wasn't and you feel to rate me down, please let me know why!
Well I already have bitmaps assigned to an array. It would help the most if I could put all the vertexs in one array regardless of the texture its using. It would grow a little confusing having a different vertex array for each texture to be used. If its an option to do this, what might I want to look into?

What method is used in most modern or older games? In a game like Quake what method of rendering would you expect they used?
A few more things you need to consider are using a scene graph, using some pre-calculated visibility data, and using frustum culling.

Scene graphs:
BSP Trees (Binary Space Partition Trees) are very good for
enclosed spaces such as large buldings. They can be used for outside
environments too but are not as well suited as other techniques.
These come in two flavours...
Solid Node and Leafy. I'm not going to go into detail about the differences
but Leafy BSP trees are more common and are the type that i use in my engine.

Oct Trees / Quads Trees are another option.
These are good if alot of your environment is outside.
I dont know much about Oct Trees and Quad trees tho.

Pre-calculated visibility data:
This is something that is more commonly known as a PVS (Potentially Visible Sets) It's a set of data that describes what areas of your 3D world are visible
to other areas. For instance if one room in a building is visble to another
through a door way or whole in a wall.

Frustum culling:
This is a farily simple technique to avoid trying to render objects that are
outside of the camera's FOV (Field Of View). Again, im not going to go into
too much detail but there is so much info out there on the net that I'm sure
you'll find what you need.

These technique combined will dramatically bump up your frame rate, even with very large maps. They are standard techniques used in the game industry.

Both the BSP Tree and PVS need to pre-compiled. You cannot build a BSP tree
and calulate visibility data at render time as this process is VERY cpu intensive and takes a loooong time to assemble the data.
Frustrum culling however needs to be done at run time but is not particually
heavy on the CPU if done in an intellegent way.

So anyway, have a look around for some tutorials on BSP trees, PVS and Frustum culling. And good luck! keep coding.
Oh and to answer your question about what techniques games like quake use
look no further than the previous message i posted. ;)
After spending some time looking into these methods I feel a bit overwhelmed. What can I do to prepare myself for this more advanced style of 3d programming? I have basically worked my way through Beginning Opengl Game Programming by Dave Astle, Kevin Hawkins. But when I try to take the next step into more advanced methods it just seems too much. Know of any good books that make a good transformation from beginner to intermediate. Also where can I go to learn about the structure of a real time 3d program?

Thanks for all the great incite so far, you all have been a great help!
I dont blame you for feeling overwelmed by these techniques.
I know i certainly felt the same way when i first looked at them.
Especially the BSP trees, those really confused me at first but stick at it
because they do make sense in the end.
These can be tricky techniques to learn but are very rewarding when you grasp
how they work.

Unfortunetly i dont really know of any good books on these subjects as i learnt almost everything i know from online resources.
however, this was a number of years ago so i cannot for the life of me remember
what these websites are. Or even if they still exist for that matter!

What i will say tho is, as this is a high school project you are working on then
perhaps it might be more prudent for you to build a VERY simple first person
shooter. IE have it consist of only a few basic rooms without too much detail
in the map, that way you can for now at least just about get away without using
BSP trees, PVS and frustum culling. Although it would still require a resonable
spec PC to run because of the extra strain you'll be putting on both the CPU
and GPU.

But please, dont let the complexity of these techniques put you off the subject.
Game development is full of many joys (as well as many headaches haha) and is
very satisfying when you get things running just the way you want.
I certainly felt very pleased with myself when i got my last engine to run at
an exsessively high frame rate.

A final note on BSP trees tho... (im a big fan of these as you maight have guessed)
BSP trees not only lend them selves very well to helping you with rendering
your map very quickly, they are also very good for helping with very efficient collision detection, lighting and shadow casting.

Anyway, good luck with your project. And please keep researching these subjects,
they will benefit you more than i can say!

By the way, sorry if this post is slightly chaotic, I just got in from the pub ;)
See I love programming also, that's why I plan going to college for computer engineering. This project that I am currently working is also meant to be the beginning to a long term game project. I just was hoping the get the game to be as impressive as possible (haha, only one using something besides iostream), but I do believe that these concepts are a bit difficult for me right now. When I feel more comfortable I will take time to try these later (probably over summer break).

Thanks a lot zombiebasher and everyone else for you guidance and time.

This topic is closed to new replies.

Advertisement