Problems with impostors (camera alignment, fading)

AndiNo

06-09-2011 00:24:23

Hi!
As you can see in the other thread I "hacked" PG so impostors now get generated for me.
Now I have the problem that while the impostors are shown, they get displayed in only one direction. While walking around a tree the impostor should change (I think it has 8 directions). However I can only see the impostor trees from one direction, viewing from all others the tree simply disappears. (This might be unclear. The trees get displayed as one-sided plane which does not move and doesn't get aligned to the camera either.)
The graphics are there in the generated impostor image, so that's not the problem.

The other problem is that I use the infinite mode of PG and I use BatchPage and ImpostorPage for my trees. I also use a custom page loader. When I start my game near the position (0,0,0) everything works fine (except for the non-rotating impostors). When I approach an impostor tree it changes to a full 3D tree. However if I move away from the world origin a bit all trees still get loaded correctly but they only display as impostors, even if I approach them.

Here's my PG creation code:
PGTreeManager = new Forests::PagedGeometry();
PGTreeManager->setTempDir("game/mine/impostors/");

PGTreeManager->setCamera(cam); //Set the camera so PagedGeometry knows how to calculate LODs
PGTreeManager->setPageSize(3200); //Set the size of each page of geometry
PGTreeManager->setInfinite(); //Use infinite paging mode

PGTreeManager->addDetailLevel<Forests::BatchPage>(1000, 300);
PGTreeManager->addDetailLevel<Forests::ImpostorPage>(100000, 500);

PGPageLoader = new WoC_Pageloader();
PGTreeManager->setPageLoader(PGPageLoader);

scenemgr->createEntity("Tree1", "fir05_30.mesh");
scenemgr->createEntity("Tree2", "fir14_25.mesh");


I also call PGTreeManager->update(); in every frame.

It seems as if the camera direction is not calculated correctly (non-rotating impostors) and the distance is not calculated from camera to Batch/ImpostorPage but to the world origin.

I'm using Ogre 1.7.1 with OpenGL.

I'm thankful for any help.

tod

06-09-2011 08:48:30

You should post your changes to the loader. Al works with the default loader, I'm not sure why you changed it.

AndiNo

06-09-2011 10:55:21

Thanks for your interest!
I use my own page loader because I needed additional functionality for handling my game world which uses (more or less) a grid system similar to the one of PG but which also uses the Y axis. As I said I did not change PG itself in that respect, I just changed the way my page loader loads trees into PG.
Here's the loadPage function from my page loader (I didn't change anything else):

void WoC_Pageloader::loadPage(Forests::PageInfo &page) {
long int arrayX = page.xIndex;
long int arrayY = 0;
long int arrayZ = page.zIndex;
if ( toCellArrayCoordinates(arrayX, arrayY, arrayZ) == false ) {
// PageLoader tries to load a page that is far away and has no Cell counterpart in the vCells array
return;
}

int numCells = (int)vCells.size();

CCell *cell;
unsigned int numTrees;
CCell::TreeInfo *tree;
Ogre::Entity *tree1 = scenemgr->getEntity("Tree1");

for (arrayY=0; arrayY<numCells; arrayY++) {
// go through the list of trees for each cell and add them to the new PG page
cell = vCells[arrayX][arrayY][arrayZ];
if ( cell->vTrees == NULL ) {
continue;
}
numTrees = cell->vTrees->size();
for (unsigned int i=0; i<numTrees; i++) {
tree = &cell->vTrees->at(i);
Ogre::Vector3 position = cell->node->getPosition();

position.x += tree->voxelX * VOXEL_SIZE;
position.y += tree->voxelY * VOXEL_SIZE - (VOXEL_SIZE/2);
position.z += tree->voxelZ * VOXEL_SIZE;

Ogre::Quaternion rotation( Ogre::Radian(tree->rotation), Ogre::Vector3::UNIT_Y );
Ogre::Vector3 scale = Ogre::Vector3::UNIT_SCALE * tree->scale;
addEntity(tree1, position, rotation, scale);
}
}
}


However as I stated in the first post it seems that all trees get loaded correctly. But maybe you can see something that I missed :)

tod

06-09-2011 20:14:41

Ok! So I don't really understand what your loader does. :oops:
Other things that look strange to me though:
1) You have very big distances. From 1000 to 100000. I would guess the floating point errors are getting really bad. Also, the impostors look really bad from up close, the position and rotation also. You have real geometry only on 1% of your viewing distance, which I think is wrong. You should instead create multiple paged geometries if you really need that much of a range.
2) You have a page size bigger than you batch page. What would this even mean? Pages should be chunks of geometry AFAIK. Meaning with a batch page of 1000, I would set page size to 256 to have 4 batches for the visible meshes. With a page size of 3200 a page should contain geometry and impostors at the same time, and I wouldn't expect that to work.

AndiNo

06-09-2011 20:42:11

Ok! So I don't really understand what your loader does. :oops: It's always hard to tell this from the outside :) Basically it just loads trees into PG from the "cells" which form my world (like a 3D grid). The loadPage function gives me the X and Z coordinate of the cell to be loaded and then the function iterates through all cells at that position on the Y axis (because PG has no native support for pages above pages).

1) You have very big distances. From 1000 to 100000. I would guess the floating point errors are getting really bad. Also, the impostors look really bad from up close, the position and rotation also. You have real geometry only on 1% of your viewing distance, which I think is wrong. You should instead create multiple paged geometries if you really need that much of a range.These are really just testing values to see if everything works. I wouldn't use these values in the final game.

2) You have a page size bigger than you batch page. What would this even mean? Pages should be chunks of geometry AFAIK. Meaning with a batch page of 1000, I would set page size to 256 to have 4 batches for the visible meshes. With a page size of 3200 a page should contain geometry and impostors at the same time, and I wouldn't expect that to work.AFAIK the page size decides how many "world units" one page is in size. I think you're right they are chunks of geometry. However I think the page size should not give any problems with the detail levels. I also think that batches and impostors transition into each other no matter how large the pages are (you see that when approaching impostor trees).

Do you have any other ideas? Thanks anyway for your help!

tod

06-09-2011 21:33:23

These are really just testing values to see if everything works. I wouldn't use these values in the final game.
I don't know if you quite understand how this works. Lets say you have an unit of 10 units is 1 meter. In this case you will have geometry for the first 100 meters in front of the camera, and impostors for another 10 km. Can you see a tree at 10km? Because I sure as hell can't. Maybe you have another convention, let's say 100 units one meter. Then you will have geometry for the first 10 meters, and then impostors for 1km. At 10+ meters until let's say 100, or so, meters it would be clearly visible that your tree is a 64x64 texture (can you say VERY BIG SQUARE PIXELS?). Your values are just wrong and you can expect them to work.

Besides a float is 16 bits, but I'm not good with floats so I'll convert them to integers for easier understanding. Integer on 16 bits it's from 0 to 65532. You can't fit 100.000 in there. So you will have 100000/65535. Your precision will be around 1.5 meters. Are you OK with a tree that is here or 1.5 meters to the left?

AFAIK the page size decides how many "world units" one page is in size. I think you're right they are chunks of geometry. However I think the page size should not give any problems with the detail levels. I also think that batches and impostors transition into each other no matter how large the pages are (you see that when approaching impostor trees).
Details levels mean: 1000 units from the camera you have real geometry, from 1000 to 100000 you have quads with very low quality textures on them (I ignored transition on purpose). And you have a page size of 3200. This means closer batches will contain both geometry and impostors.
Why would you want that? The purpose of this is to have high quality meshes up front and crappy quads in the distance, where they are only a few pixels and the difference is not evident (not to mention that impostors don't have stuff like shadows or light on them)
Now, what you would really want would be to have a page of 1000, the same as your geometry. One big batch that gets fed to the video card in one big fast call. But then you get into other problems. Like all the batch will be visible or none of it will. And then you get a big batch that you see only 1% of but all the calculations use all of it. That's why you want to set the page to something lower so that some parts of the geometry can get hidden (not rendered, not processed, ignored) by the hardware.

AndiNo

07-09-2011 22:16:40

In my world 100 Ogre units are 1 meter. About the values I use: If I understood that right they only control at which distance objects get drawn (geometry or impostors). These values should not conflict with how the program works. Currently I just want to find out what causes my problem, not find the nicest looking settings. That's why I said that they're only for testing :)
And I think the usual int is a "long int" which is 32 bits = 4 bytes. The same as a float. Doubles have 8 bytes if I remember correctly. So there shouldn't be any problem with precision.

I'm not sure who of us is right now ;) but I think PG manages the world in pages which are laid out as a 2D grid where each field in the grid is one page. From what I understood the page size and the detail level rendering distance have nothing to do with each other. The page size only defines how big on page is in the world, the rendering distance only defines how far away things can be before you can't see them anymore. However it's completely possible that I missed something.
Anyhow, I think this has nothing to do with the initial problem :)
Thanks anyway for your efforts!

tod

07-09-2011 22:33:11

Well, suit yourself. The point was you have the wrong set-up and it's hard to find the cause of the problem.
Floats are 16 bit. That's what the video card uses, AFAIK. And that's what Ogre uses by default. Using floats with such big values will cause problems when you get far from the origin, just like your problem.
The page defines a portion of geometry that is rendered at once.

AndiNo

08-09-2011 09:57:58

According to this site floats are 4 bytes: http://www.cplusplus.com/doc/tutorial/variables/
That's what I'm used to. Of course it may be that video cards have different standards.
What you are proposing makes sense, the problem is that I'm not that far away from the origin. I should have been more clear on that. The rendering problem occurs already when I'm going past the rendering distance of batches. And how does my current setup make impostors not face my camera?

tod

08-09-2011 11:04:15

Some screenshots may help.

tod

08-09-2011 11:16:59

You seem to be right about floats being 4 bytes. Mea culpa.

AndiNo

08-09-2011 14:58:58

You seem to be right about floats being 4 bytes. Mea culpa.No problem. I wasn't even sure myself :)

Here's a screenshot of how the impostors look like:

As you can see they don't face the camera. If I look at them from "behind" they are invisible (because the impostor "looks" in a different direction).

About the other problem: It seems as if PG only calculates the distance from the camera to the world origin, not the distance to each page or tree as it should. I'm not even sure if anybody has ever used PG with an infinite landscape, maybe there is a problem.
Currently I'm thinking about implementing the batching etc myself without PG. It wouldn't be as nice as how PG does it, but it would work :)

tod

08-09-2011 20:20:14

I'm lost. I looked over your code, and my code, and I don't see anything wrong. My only guess is that you are not using the correct camera or that you don't call update each frame.

AndiNo

08-09-2011 21:41:54

Good points. But seeing that (near the origin) the tree beatches get displayed correctly and that impostors fade to geometry correctly makes me somewhat sure that I give the right camera to PG and also update it every frame.
Let's just assume that I have something else set up wrong in my Ogre or that there is some other incompatibility in my software. I will post it here if I should ever find the problem.
Thanks for your help, it's really appreciated! :)