BloodyMess Ogre::Terrain heightfield fps drop to zero

caifie

03-05-2010 02:40:01

hi, every one!

i'm using ogre1.7+BloodyMess.
when i want to create a heightfield with the method from below url
http://www.ogre3d.org/wiki/index.php/BloodyMess_Ogre::Terrain_Heightfield
the ogre render fps will drop to 0, and triangle will up to even 400 thousand.

i create the ogre terrain lwith below code,
mTerrainGlobals = OGRE_NEW Ogre::TerrainGlobalOptions();
mTerrain = OGRE_NEW Ogre::Terrain(mSceneMgr);

Ogre::Image img;
img.load("terrain.png", Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
mTerrainGlobals->setMaxPixelError(8);
mTerrainGlobals->setCompositeMapDistance(3000);
TerrainMaterialGeneratorA::SM2Profile* matProfile =
static_cast<TerrainMaterialGeneratorA::SM2Profile*>(mTerrainGlobals->getDefaultMaterialGenerator()->getActiveProfile());
mTerrainGlobals->setLightMapDirection(l->getDerivedDirection());
mTerrainGlobals->setCompositeMapAmbient(mSceneMgr->getAmbientLight());
mTerrainGlobals->setCompositeMapDiffuse(l->getDiffuseColour());

Ogre::Terrain::ImportData defaultimp;
defaultimp.terrainSize = TERRAIN_SIZE;
defaultimp.worldSize = TERRAIN_WORLD_SIZE;
defaultimp.inputScale = 600;
defaultimp.minBatchSize = 33;
defaultimp.maxBatchSize = 65;
defaultimp.inputImage = &img;

// textures
defaultimp.layerList.resize(3);
defaultimp.layerList[0].worldSize = 100;
defaultimp.layerList[0].textureNames.push_back("dirt_grayrocky_diffusespecular.dds");
defaultimp.layerList[0].textureNames.push_back("dirt_grayrocky_normalheight.dds");
defaultimp.layerList[1].worldSize = 30;
defaultimp.layerList[1].textureNames.push_back("grass_green-01_diffusespecular.dds");
defaultimp.layerList[1].textureNames.push_back("grass_green-01_normalheight.dds");
defaultimp.layerList[2].worldSize = 200;
defaultimp.layerList[2].textureNames.push_back("growth_weirdfungus-03_diffusespecular.dds");
defaultimp.layerList[2].textureNames.push_back("growth_weirdfungus-03_normalheight.dds");

mTerrain->prepare(defaultimp);
mTerrain->load();

Ogre::TerrainLayerBlendMap* blendMap0 = mTerrain->getLayerBlendMap(1);
Ogre::TerrainLayerBlendMap* blendMap1 = mTerrain->getLayerBlendMap(2);
Ogre::Real minHeight0 = 70;
Ogre::Real fadeDist0 = 40;
Ogre::Real minHeight1 = 70;
Ogre::Real fadeDist1 = 15;
float* pBlend0 = blendMap0->getBlendPointer();
float* pBlend1 = blendMap1->getBlendPointer();
for (Ogre::uint16 y = 0; y < mTerrain->getLayerBlendMapSize(); ++y)
{
for (Ogre::uint16 x = 0; x < mTerrain->getLayerBlendMapSize(); ++x)
{
Ogre::Real tx, ty;

blendMap0->convertImageToTerrainSpace(x, y, &tx, &ty);
Ogre::Real height = mTerrain->getHeightAtTerrainPosition(tx, ty);
Ogre::Real val = (height - minHeight0) / fadeDist0;
val = Ogre::Math::Clamp(val, (Ogre::Real)0, (Ogre::Real)1);

val = (height - minHeight1) / fadeDist1;
val = Ogre::Math::Clamp(val, (Ogre::Real)0, (Ogre::Real)1);
*pBlend1++ = val * 255;
}
}
blendMap0->dirty();
blendMap1->dirty();
blendMap0->update();
blendMap1->update();

loadTerrainGeometry(mTerrain->getMaterialName(), mTerrain->getHeightData(), mTerrain->getSize(),
mTerrain->getWorldSize(), mTerrain->getMinHeight(), mTerrain->getMaxHeight(), mTerrain->getPosition());

mTerrain->freeTemporaryResources();



and the loadTerrainGeometry method code is below,
void loadTerrainGeometry(const Ogre::String& name, float* data, Ogre::uint16 size, Ogre::Real worldSize, Ogre::Real minHeight, Ogre::Real maxHeight, const Ogre::Vector3& position)
{
// Create the manual heightfield
NxOgre::ManualHeightField *mhf = OGRE_NEW_T(NxOgre::ManualHeightField, Ogre::MEMCATEGORY_GENERAL)();
mhf->begin(size, size);
Ogre::Real normMin = -32767.0f;
Ogre::Real normMax = 32767.0f;
// Sample the data to the manual heightfield
for(int x = 0; x < size; ++x)
{
NxOgre::Enums::HeightFieldTesselation tess = NxOgre::Enums::HeightFieldTesselation_NW_SE;
for(int z = size-1; z >= 0; --z)
{
Ogre::Real height = data[(size * z) + x];
short sample = (short)(((height - minHeight) / (maxHeight - minHeight)) * (normMax - normMin) + normMin);
mhf->sample(sample, 0, 0, tess);
if(tess == NxOgre::Enums::HeightFieldTesselation_NE_SW)
tess = NxOgre::Enums::HeightFieldTesselation_NW_SE;
else
tess = NxOgre::Enums::HeightFieldTesselation_NE_SW;
}
}

// Create the actual heightfield
NxOgre::HeightField *hf = mhf->end(name.c_str());
Ogre::Real hf_size = worldSize + (worldSize / size);
Ogre::Real hf_height = (maxHeight - minHeight) / 2.0f;
Ogre::Real hf_pose_x = position.x - (worldSize / 2.0f);
Ogre::Real hf_pose_y = position.y + ((maxHeight + minHeight) / 2.0f);
Ogre::Real hf_pose_z = position.z - (worldSize / 2.0f);
#if NxOgreVersionMajor <= 1 && NxOgreVersionMinor <= 5
NxOgre::HeightFieldGeometry* hfg = new NxOgre::HeightFieldGeometry(hf, NxOgre::Vec3(hf_size, hf_height, hf_size));
hfg->setLocalPose(NxOgre::Matrix44(NxOgre::Vec3(hf_pose_x, hf_pose_y, hf_pose_z)));
mScene->createSceneGeometry(hfg);
#else
NxOgre::HeightFieldGeometryDescription desc(hf, NxOgre::Vec3(hf_size, hf_height, hf_size));
mScene->createSceneGeometry(desc, NxOgre::Matrix44(NxOgre::Vec3(hf_pose_x, hf_pose_y, hf_pose_z)));
#endif
// Free memory
OGRE_DELETE_T(mhf, ManualHeightField, Ogre::MEMCATEGORY_GENERAL);
}


does anyone kown about this?
help me to solve this, thans very much!

betajaen

03-05-2010 10:35:04

Make sure the visualisation flags in the HeightfieldGeometryDescription is off. That is usually the culprit.

caifie

03-05-2010 11:09:23

Make sure the visualisation flags in the HeightfieldGeometryDescription is off. That is usually the culprit.

thanks for your reply!

i'm using nxogre1.5.5, i cannot find the HeightfieldGeometryDescription.

i only find this,
class NxHeightFieldDesc; //< \internal Prototyped class. DO NOT USE.
so the class NxHeightFieldDesc looks like can not use in app.

can you tell me how to do it? i am a newer to this, :D .

betajaen

03-05-2010 12:43:15

Oh your using BloodyMess, then I mean "HeightFieldGeometryBlueprint"

Make sure the flags in it are set to zero, when passing it to your HeightFieldGeometry.

caifie

03-05-2010 13:00:57

Oh your using BloodyMess, then I mean "HeightFieldGeometryBlueprint"

Make sure the flags in it are set to zero, when passing it to your HeightFieldGeometry.


thanks again, :D

do you mean below?
NxOgre::HeightFieldGeometryBlueprint* blue = new HeightFieldGeometryBlueprint();
blue->mFlags=0;
blue->mHeightField=0;

NxOgre::HeightFieldGeometry* hfg = new NxOgre::HeightFieldGeometry(hf, NxOgre::Vec3(hf_size, hf_height, hf_size),blue);
hfg->setLocalPose(NxOgre::Matrix44(NxOgre::Vec3(hf_pose_x, hf_pose_y, hf_pose_z)));
mScene->createSceneGeometry(hfg);


there are many flags in blue,all are set to zero, or just some special?