I'm writing a Minecraft-like game using Ogre engine and I have a problem. I must optimize my game, because when I try draw 10000 blocks, I have 2 FPS... So, I got the idea that blocks display of the plane and to hide the invisible blocks. But I have a problem - how do I know which blocks at a time are visible to the player?

And - if you know of other optimization methods for such a game, write what and how to use them in Ogre.

5 Answers
5

Well, Ogre already implements frustum culling (which basically does not draw anything that couldn't be seen from the camera) but I think your problem is a different one.

You should not really be displaying 10000 blocks, what is commonly done (or at least, in the few Ogre3d based minecraft like clones I've seen (of which I am making one too), and in the original ) is creating a mesh (of some NxNxN region of chunks) which has the outer faces of the cubes shown.
That is, when you put 2 cubes side by side, the 2 faces touching can't be seen and therefore don't need to be drawn.

You can use backface culling to cull vertices and their associated pixels that don't face the player. Depth buffering should take care of the rest. 10k blocks really isn't a lot, my 5770 can render 100k verts at 1500fps. I think that you're doing something else pretty badly wrong.

There are a couple of aspects to this problem. Firstly, how are you drawing your 10000 blocks? Are you actually drawing them as 10000 seperate object? If so this is almost certainly your bottle neck, not the lack of occlusion culling. You should group these blocks into a smaller number of meshes (perhaps a few thousand per mesh) in order to reduce draw calls.

As for your actual question, there are three types of occlusion culling which spring to mind.

1) Blocks outside the view frustum. This means blocks which are behind you or two the side. Ogre already removes these via view frustum culling.

2) Blocks which are 'underground' or completely surrounded by other blocks so they can never be seen from any angle. You can identify these by looking at the siz neighbouring blocks. If they are all solid your block is hidden. The GPU should never even hear about these blocks - they should be skipped when you are building the mesh which represent your surface.

3) Blocks which are on the surface and can be seen from some positions in the level, but which are currently hidden by a hill (or something). This is the trickiest case which I haven't addressed myself, but there's a good chance that hardware occlusion queries can be used for this case.

It's a shameless plug, but I have a fairly mature library which several people are using to develop Minecraft clones, including some using Ogre. You define the contents of the volume and it generates the surface mesh which you can then render. Here is the home page: