#include "LBBCLeafDistributionGenerator.h" #include namespace LBBC { LeafDistributionGenerator::LeafDistributionGenerator() { mEntity = BBC::EntityPtr(new BBC::Entity()); } LeafDistributionGenerator::~LeafDistributionGenerator() { } void LeafDistributionGenerator::generate() { BBC::Timer leafDistributionTimer; leafDistributionTimer.start(); leafDistributionTimer.printStartTime(); mEntity->loadMesh(true); unsigned int posNorm = 0; unsigned int negNorm = 0; std::vector::iterator iFaces01; std::vector::iterator iFaces02; std::vector::iterator iVertexs; std::vector vD,vNx,vNy,vNz; unsigned int iV101,iV201,iV301; unsigned int iV102,iV202,iV302; Ogre::Vector3 v101,v201,v301; Ogre::Vector3 v102,v202,v302; for (unsigned int iF01 = 0; iF01 < mEntity->getSubEntity(0)->getNumFaces(); iF01++) { Ogre::Vector3 vFace01 = mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01); iV101 = vFace01[0]; iV201 = vFace01[1]; iV301 = vFace01[2]; v101 = mEntity->getSubEntity(0)->getUniqueVertex(iV101).position; v201 = mEntity->getSubEntity(0)->getUniqueVertex(iV201).position; v301 = mEntity->getSubEntity(0)->getUniqueVertex(iV301).position; for (unsigned int iF02 = 0; iF02 < mEntity->getSubEntity(0)->getNumFaces(); iF02++) { Ogre::Vector3 vFace02 = mEntity->getSubEntity(0)->getFaceVerticesIDs(iF02); iV102 = vFace02[0]; iV202 = vFace02[1]; iV302 = vFace02[2]; v102 = mEntity->getSubEntity(0)->getUniqueVertex(iV102).position; v202 = mEntity->getSubEntity(0)->getUniqueVertex(iV202).position; v302 = mEntity->getSubEntity(0)->getUniqueVertex(iV302).position; //Ogre::LogManager::getSingleton().logMessage("face A: " + Ogre::StringConverter::toString(iF01)); //Ogre::LogManager::getSingleton().logMessage("indices A:" + Ogre::StringConverter::toString(vFace01)); //Ogre::LogManager::getSingleton().logMessage("face B: " + Ogre::StringConverter::toString(iF02)); //Ogre::LogManager::getSingleton().logMessage("indices B:" + Ogre::StringConverter::toString(vFace02)); if ((iF01 != iF02) && ( ((v101 == v102) && (v201 == v202)) || ((v101 == v202) && (v201 == v102)) || ((v101 == v102) && (v201 == v302)) || ((v101 == v302) && (v201 == v102)) || ((v101 == v202) && (v201 == v302)) || ((v101 == v302) && (v201 == v202)) || //----------------------------------- ((v201 == v102) && (v301 == v202)) || ((v201 == v202) && (v301 == v102)) || ((v201 == v102) && (v301 == v302)) || ((v201 == v302) && (v301 == v102)) || ((v201 == v202) && (v301 == v302)) || ((v201 == v302) && (v301 == v202)) || //----------------------------------- ((v101 == v102) && (v301 == v202)) || ((v101 == v202) && (v301 == v102)) || ((v101 == v102) && (v301 == v302)) || ((v101 == v302) && (v301 == v102)) || ((v101 == v202) && (v301 == v302)) || ((v101 == v302) && (v301 == v202)) ) ) { if (mEntityDistribution->getNumEntities() == 0) { // Instance new leaf Leaf *leaf = new Leaf(); leaf->setEntityHandle(mEntityDistribution->getNumEntities()); leaf->getSubEntity(0)->addTextureCoordSet(2); leaf->addFace(iF01); leaf->addFaceInfo( mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).x), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).y), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).z)); mEntityDistribution->addEntity(leaf); //Ogre::LogManager::getSingleton().logMessage("leaf:" + Ogre::StringConverter::toString(leaf->getEntityHandle())); //Ogre::LogManager::getSingleton().logMessage("indices:" + Ogre::StringConverter::toString(vFace01)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(iF01)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(leaf->getFace(0))); } else { unsigned int j = 0; bool leaveFound = false; // Check if the face is in one of the Leaf sets... while ((j < mEntityDistribution->getNumEntities()) && (!leaveFound)) { Leaf *leaf = (Leaf *)mEntityDistribution->getEntity(j).get(); if (leaf->hasFace(iF01)) { leaveFound = true; leaf->addFace(iF02); leaf->addFaceInfo( mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF02).x), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF02).y), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF02).z)); //Ogre::LogManager::getSingleton().logMessage("leaf:" + Ogre::StringConverter::toString(leaf->getEntityHandle())); //Ogre::LogManager::getSingleton().logMessage("indices:" + Ogre::StringConverter::toString(vFace02)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(iF02)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(leaf->getFace(0))); } else { if (leaf->hasFace(iF02)) { leaveFound = true; leaf->addFace(iF01); leaf->addFaceInfo( mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).x), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).y), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).z)); //Ogre::LogManager::getSingleton().logMessage("leaf:" + Ogre::StringConverter::toString(leaf->getEntityHandle())); //Ogre::LogManager::getSingleton().logMessage("indices:" + Ogre::StringConverter::toString(vFace01)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(iF01)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(leaf->getFace(0))); } } j++; } if (!leaveFound) { // Instance new leaf Leaf *leaf = new Leaf(); leaf->setEntityHandle(mEntityDistribution->getNumEntities()); leaf->getSubEntity(0)->addTextureCoordSet(2); leaf->addFace(iF01); leaf->addFaceInfo( mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).x), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).y), mEntity->getSubEntity(0)->getUniqueVertex(mEntity->getSubEntity(0)->getFaceVerticesIDs(iF01).z)); mEntityDistribution->addEntity(leaf); //Ogre::LogManager::getSingleton().logMessage("leaf:" + Ogre::StringConverter::toString(leaf->getEntityHandle())); //Ogre::LogManager::getSingleton().logMessage("indices:" + Ogre::StringConverter::toString(vFace01)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(iF01)); //Ogre::LogManager::getSingleton().logMessage("face stored: " + Ogre::StringConverter::toString(leaf->getFace(0))); //cin.get(); } } } } } // Generate the average normal, leaf position, and d leaf plane parameter for each leaf... for (unsigned int ileaf = 0; ileaf < mEntityDistribution->getNumEntities(); ileaf++) { Leaf *leaf = (Leaf*) mEntityDistribution->getEntity(ileaf).get(); generateAverageLeafPosition(leaf); generateAverageLeafNormal(leaf); leaf->setLeafD(-leaf->getLeafNormal().dotProduct(leaf->getPosition())); } // Compute the max and min d leaf plane parameter, and the max and min normal value... float minD; float maxD; Ogre::Vector3 minNormal; Ogre::Vector3 maxNormal; generateNormalDThreshold(minD, maxD, minNormal, maxNormal); ((LeafDistribution*)mEntityDistribution)->setMaxD(maxD); ((LeafDistribution*)mEntityDistribution)->setMinD(minD); ((LeafDistribution*)mEntityDistribution)->setMaxNormal(maxNormal); ((LeafDistribution*)mEntityDistribution)->setMinNormal(minNormal); leafDistributionTimer.stop(); leafDistributionTimer.printStopTime(); } void LeafDistributionGenerator::generateNormalDThreshold(float &minD, float &maxD, Ogre::Vector3 &minNormal, Ogre::Vector3 &maxNormal) { float dMin = FLT_MAX; float dMax = -FLT_MAX; float nXMax = -1; float nYMax = -1; float nZMax = -1; float nYMin = 1; float nXMin = 1; float nZMin = 1; for (unsigned int iD = 0; iD < mEntityDistribution->getNumEntities(); iD++) { Leaf *leaf = (Leaf *)mEntityDistribution->getEntity(iD).get(); if (leaf->getLeafD() < dMin) { dMin = leaf->getLeafD(); } if (leaf->getLeafD() > dMax) { dMax = leaf->getLeafD(); } //-------------------- if (leaf->getLeafNormal().x < nXMin) { nXMin = leaf->getLeafNormal().x; } if (leaf->getLeafNormal().x > nXMax) { nXMax = leaf->getLeafNormal().x; } //-------------------- if (leaf->getLeafNormal().y < nYMin) { nYMin = leaf->getLeafNormal().y; } if (leaf->getLeafNormal().y > nYMax) { nYMax = leaf->getLeafNormal().y; } //-------------------- if (leaf->getLeafNormal().z < nZMin) { nZMin = leaf->getLeafNormal().z; } if (leaf->getLeafNormal().z > nZMax) { nZMax = leaf->getLeafNormal().z; } } minNormal = Ogre::Vector3(nXMin, nYMin, nZMin); maxNormal = Ogre::Vector3(nXMax, nYMax, nZMax); minD = dMin; maxD = dMax; } void LeafDistributionGenerator::generateAverageLeafNormal(Leaf *leaf) { Ogre::Vector3 aVnormal(0,0,0); for (unsigned int iN = 0; iN < leaf->getNumLeafNormals(); iN++) { aVnormal = aVnormal + leaf->getFaceNormal(iN); } aVnormal = aVnormal / leaf->getNumLeafNormals(); aVnormal.normalise(); leaf->setLeafNormal(aVnormal); } void LeafDistributionGenerator::generateAverageLeafPosition(Leaf *leaf) { Ogre::Vector3 aVPosition(0,0,0); for (unsigned int iN = 0; iN < leaf->getSubEntity(0)->getNumVertices(); iN++) { aVPosition = aVPosition + leaf->getSubEntity(0)->getPosition(iN); } aVPosition = aVPosition / leaf->getSubEntity(0)->getNumVertices(); leaf->setPosition(aVPosition); } }