source: GTP/trunk/Lib/Vis/OnlineCullingCHC/OGRE/src/OgreBoundingBoxConverter.cpp @ 1296

Revision 1296, 3.9 KB checked in by szydlowski, 18 years ago (diff)

Implemented PVS support in kdtree scene manager - not complete, defunct
modified BoundingBoxConverter? to work with KdTreeSceneManager?

Line 
1#include "OgreBoundingBoxConverter.h"
2#include "OgreTypeConverter.h"
3#include "OgreMeshInstance.h"
4#include "OgreOctreeSceneManager.h"
5#include "OgreKdTreeSceneManager.h"
6#include <OgreLogManager.h>
7
8
9namespace Ogre
10{
11//-------------------------------------------------------------------------
12OgreBoundingBoxConverter::OgreBoundingBoxConverter(OctreeSceneManager *sm):
13mOctSceneMgr(sm), mKdSceneMgr(0)
14{
15}
16//-------------------------------------------------------------------------
17OgreBoundingBoxConverter::OgreBoundingBoxConverter(KdTreeSceneManager *sm):
18mOctSceneMgr(0), mKdSceneMgr(sm)
19{
20}
21//-------------------------------------------------------------------------
22bool OgreBoundingBoxConverter::IdentifyObjects(const GtpVisibilityPreprocessor::IndexedBoundingBoxContainer &iboxes,
23                                                                                           GtpVisibilityPreprocessor::ObjectContainer &objects) const
24{
25        GtpVisibilityPreprocessor::IndexedBoundingBoxContainer::
26                const_iterator iit, iit_end = iboxes.end();
27 
28        for (iit = iboxes.begin(); iit != iit_end; ++ iit)
29        {
30                const GtpVisibilityPreprocessor::AxisAlignedBox3 box = (*iit).second;
31                const AxisAlignedBox currentBox = OgreTypeConverter::ConvertToOgre(box);
32   
33                Entity *ent = FindCorrespondingObject(currentBox);
34
35                // create new mesh instance
36                OgreMeshInstance *omi = new OgreMeshInstance(ent);
37                omi->SetId((*iit).first);
38                objects.push_back(omi);
39        }
40
41        return true;
42}
43//-------------------------------------------------------------------------
44inline static AxisAlignedBox EnlargeBox(const AxisAlignedBox &box)
45{
46        const float eps = 1e-3f;
47        const Vector3 veps(eps, eps, eps);
48
49        Vector3 max = box.getMaximum();
50        Vector3 min = box.getMinimum();
51
52        return AxisAlignedBox(min - veps, max + veps);
53}
54//-----------------------------------------------------------------------
55Entity *OgreBoundingBoxConverter::FindCorrespondingObject(const AxisAlignedBox &box) const
56{
57        list<SceneNode *> sceneNodeList;
58        AxisAlignedBox mybox = EnlargeBox(box);
59        //AxisAlignedBox dummy(Vector3(-50000, -50000, -50000), Vector3(50000, 50000, 50000));
60       
61        // get intersecting scene nodes
62        if (mOctSceneMgr)
63                mOctSceneMgr->findNodesIn(mybox, sceneNodeList, NULL);
64        else if (mKdSceneMgr)
65                mKdSceneMgr->findNodesIn(mybox, sceneNodeList, NULL);
66        else
67                OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR, "Bounding Box Converter cannot "
68                "find appropriate scene manager.", "OgreBoundingBoxConverter::FindCorrespondingObject");
69       
70
71        list<SceneNode *>::const_iterator sit, sit_end = sceneNodeList.end();
72
73        // minimal overlap
74        float overlap = 0;//1e-6;
75
76        Entity *bestFittingObj = NULL;
77        float bestFit = overlap;
78
79        // perfect fit threshold
80        const float thresh = 1.0 - GtpVisibilityPreprocessor::Limits::Small;
81
82
83        // find the bbox which is closest to the current bbox
84        for (sit = sceneNodeList.begin(); sit != sceneNodeList.end(); ++ sit)
85        {
86                SceneNode *sn = *sit;
87                SceneNode::ObjectIterator oit = sn->getAttachedObjectIterator();
88
89        while (oit.hasMoreElements())
90                {
91                        MovableObject *mo = oit.getNext();
92
93                        // we are only interested in scene entities
94                        if (mo->getMovableType() != "Entity")
95                        {
96                                continue;
97                        }
98                         
99                        const AxisAlignedBox bbox = EnlargeBox(mo->getWorldBoundingBox());
100                                       
101
102                        // compute measure how much aabbs overlap
103                        overlap = RatioOfOverlap(OgreTypeConverter::ConvertFromOgre(mybox),
104                                                                         OgreTypeConverter::ConvertFromOgre(bbox));
105       
106                         if (overlap > bestFit)
107                         {
108                                 bestFit = overlap;
109                       
110                                 bestFittingObj = static_cast<Entity *>(mo);
111
112                                 // perfect fit => object found, early exit
113                                 if (overlap >= thresh)
114                                         return bestFittingObj;                         
115                         }
116                }
117        }
118
119        if (0)
120        {
121                std::stringstream d;
122                if (bestFittingObj)
123                        d << "best fit: " << bestFit;     
124                else
125                        d << "warning, objects do not fit\n" << box;
126       
127                Ogre::LogManager::getSingleton().logMessage(d.str());
128        }
129
130        return bestFittingObj;
131}
132
133}
Note: See TracBrowser for help on using the repository browser.