source: trunk/VUT/Ogre/src/OgreVisibilityOctreeSceneManager.cpp @ 139

Revision 139, 12.6 KB checked in by mattausch, 19 years ago (diff)

fixed bug with tight octree boxes
added more flexible renderqueue (can delete per flag)
reordered functions in visibility terrain scene manager

Line 
1#include "OgreVisibilityOctreeSceneManager.h"
2#include "OgreVisibilityOptionsManager.h"
3#include <OgreMath.h>
4#include <OgreIteratorWrappers.h>
5#include <OgreRenderSystem.h>
6#include <OgreCamera.h>
7#include <OgreLogManager.h>
8#include <OgreStringConverter.h>
9
10
11namespace Ogre {
12
13//-----------------------------------------------------------------------
14VisibilityOctreeSceneManager::VisibilityOctreeSceneManager(
15        GtpVisibility::VisibilityManager *visManager)
16:
17mVisibilityManager(visManager),
18mRenderDepthPass(false),
19mShowVisualization(false),
20mRenderNodesForViz(false),
21mRenderNodesContentForViz(false),
22mVisualizeCulledNodes(false),
23mDelayRenderTransparents(true),
24mUseDepthPass(true),
25mSkipTransparents(false)
26{
27        mHierarchyInterface = new OctreeHierarchyInterface(this, mDestRenderSystem);
28               
29        //mDisplayNodes = true;
30        //mShowBoundingBoxes = true;
31        //mShowBoxes = true;
32
33        // TODO: find reasonable value for max depth
34        mMaxDepth = 50;
35}
36//-----------------------------------------------------------------------
37void VisibilityOctreeSceneManager::InitDepthPass()
38{
39        MaterialPtr depthMat = MaterialManager::getSingleton().getByName("Visibility/DepthPass");
40
41        if (depthMat.isNull())
42    {
43                // Init
44                depthMat = MaterialManager::getSingleton().create(
45                "Visibility/DepthPass",
46                ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
47
48                mDepthPass = depthMat->getTechnique(0)->getPass(0);
49                mDepthPass->setColourWriteEnabled(false);
50                mDepthPass->setDepthWriteEnabled(true);
51                mDepthPass->setLightingEnabled(false);
52        }
53        else
54        {
55                mDepthPass = depthMat->getTechnique(0)->getPass(0);
56        }
57}
58//-----------------------------------------------------------------------
59VisibilityOctreeSceneManager::~VisibilityOctreeSceneManager()
60{
61        if (mHierarchyInterface)
62        {
63                delete mHierarchyInterface;
64                mHierarchyInterface = NULL;
65        }
66}
67//-----------------------------------------------------------------------
68Pass *VisibilityOctreeSceneManager::setPass(Pass* pass)
69{
70        // setting vertex program is not efficient
71        Pass *usedPass = ((mRenderDepthPass && pass->getDepthWriteEnabled() &&
72                !pass->hasVertexProgram()) ? mDepthPass : pass);               
73
74        /*
75        // set depth fill pass only if depth write enabled
76        Pass *usedPass = (mRenderDepthPass && pass->getDepthWriteEnabled() ? mDepthPass : pass);
77
78    if (mRenderDepthPass && pass->hasVertexProgram())
79    {
80                // set vertex program of current pass to depth pass
81                mDepthPass->setVertexProgram(pass->getVertexProgramName());
82
83                if (mDepthPass->hasVertexProgram())
84                {
85                        const GpuProgramPtr& prg = mDepthPass->getVertexProgram();
86                        // Load this program if not done already
87                        if (!prg->isLoaded())
88                                prg->load();
89                        // Copy params
90                        mDepthPass->setVertexProgramParameters(pass->getVertexProgramParameters());
91                }
92                else if (mDepthPass->hasVertexProgram())
93                {
94                        mDepthPass->setVertexProgram("");
95                }
96        }*/
97
98        SceneManager::setPass(usedPass);
99
100        return usedPass;
101}
102//-----------------------------------------------------------------------
103void VisibilityOctreeSceneManager::PrepareVisualization(Camera *cam)
104{
105        // add player camera for visualization purpose
106        try
107        {
108                Camera *c;
109                if ((c = getCamera("PlayerCam")) != NULL)
110                {
111                        getRenderQueue()->addRenderable(c);
112                }   
113    }
114    catch(...)
115    {
116        // ignore
117    }
118        for (BoxList::iterator it = mBoxes.begin(); it != mBoxes.end(); ++it)
119{
120                getRenderQueue()->addRenderable(*it);
121        }
122        if (mRenderNodesForViz || mRenderNodesContentForViz)
123        {
124                // change node material so it is better suited for visualization
125                MaterialPtr nodeMat = MaterialManager::getSingleton().getByName("Core/NodeMaterial");
126                nodeMat->setAmbient(1, 1, 0);
127                nodeMat->setLightingEnabled(true);
128                nodeMat->getTechnique(0)->getPass(0)->removeAllTextureUnitStates();
129
130                for (NodeList::iterator it = mVisible.begin(); it != mVisible.end(); ++it)
131                {
132                        if (mRenderNodesForViz)
133                        {
134                                getRenderQueue()->addRenderable(*it);
135                                // addbounding boxes instead of node itself
136                                //(*it)->_addBoundingBoxToQueue(getRenderQueue());
137                        }
138                        if (mRenderNodesContentForViz)
139                        {
140                                (*it)->_addToRenderQueue(cam, getRenderQueue(), false);
141                        }
142                }
143        }
144       
145}
146//-----------------------------------------------------------------------
147void VisibilityOctreeSceneManager::_findVisibleObjects(Camera* cam, bool onlyShadowCasters)
148{
149        //-- show visible scene nodes and octree bounding boxes from last frame
150        if (mShowVisualization)
151    {
152                PrepareVisualization(cam);
153        }
154        else
155        {       
156                mVisible.clear();
157            mBoxes.clear();
158       
159                // if there is no depth pass =>
160                // we interleave identification and rendering of objects
161                // in _renderVisibibleObjects
162
163                // only shadow casters will be rendered in shadow texture pass
164                mHierarchyInterface->SetOnlyShadowCasters(onlyShadowCasters);
165        }
166}
167//-----------------------------------------------------------------------
168void VisibilityOctreeSceneManager::_renderVisibleObjects()
169{
170        // create material for depth pass
171        InitDepthPass();
172       
173        // visualization: apply standard rendering
174        if (mShowVisualization)
175        {       
176                OctreeSceneManager::_renderVisibleObjects();
177                return;
178        }       
179
180        //-- hierarchical culling
181        // the objects of different layers (e.g., background, scene,
182        // overlay) must be identified and rendered one after another
183
184        bool leaveTransparentsInQueue = mDelayRenderTransparents && !mUseDepthPass;
185
186        // possible two cameras (one for culling, one for rendering)
187        mHierarchyInterface->InitFrame(mOctree, mCameraInProgress,
188                                                        mCullCamera ? getCamera("CullCamera") : NULL,
189                                                        leaveTransparentsInQueue);
190
191        // reset culling manager stats
192        mVisibilityManager->GetCullingManager()->InitFrame(mVisualizeCulledNodes);
193       
194        mSkipTransparents = false;
195
196        //-- render background, in case there is one
197        clearSpecialCaseRenderQueues();
198        addSpecialCaseRenderQueue(RENDER_QUEUE_BACKGROUND);
199        addSpecialCaseRenderQueue(RENDER_QUEUE_SKIES_EARLY);
200        setSpecialCaseRenderQueueMode(SceneManager::SCRQM_INCLUDE);
201
202        SceneManager::_renderVisibleObjects();
203
204
205#ifdef GTP_VISIBILITY_MODIFIED_OGRE
206        _deleteRenderedQueueGroups();
207#endif
208
209        //-- render visible objects (i.e., all but overlay)
210        clearSpecialCaseRenderQueues();
211        addSpecialCaseRenderQueue(RENDER_QUEUE_SKIES_LATE);
212        addSpecialCaseRenderQueue(RENDER_QUEUE_OVERLAY);
213        setSpecialCaseRenderQueueMode(SceneManager::SCRQM_EXCLUDE);
214       
215        // transparents are skipped from hierarchical rendering
216        // => they need sorting, thus we render them afterwards
217        mSkipTransparents = mDelayRenderTransparents;
218
219        // set state for depth pass
220    mRenderDepthPass = mUseDepthPass;
221       
222        /**
223        * the hierarchical culling algorithm
224          * for depth pass: will just find objects and update depth buffer
225          * for delayed rendering: will render all but transparents
226        **/
227       
228        mVisibilityManager->ApplyVisibilityCulling();
229       
230        //-- now we can savely render all remaining objects, e.g., transparents, overlay
231        mSkipTransparents = false;
232
233        clearSpecialCaseRenderQueues();
234        SceneManager::_renderVisibleObjects();
235
236        // for depth pass: add visible nodes found with the visibility culling
237        if (mUseDepthPass)
238        {
239                for (NodeList::iterator it = mVisible.begin(); it != mVisible.end(); ++it)
240                {
241                        (*it)->_addToRenderQueue(mCameraInProgress, getRenderQueue(), false);
242                }
243                mRenderDepthPass = false;
244    }
245        mSkipTransparents = false;
246               
247        //-- now we can render all remaining queue objects
248        // for depth pass: all
249        // for delayed rendering: transparents, overlay
250        clearSpecialCaseRenderQueues();
251        OctreeSceneManager::_renderVisibleObjects();
252       
253        WriteLog(); // write out stats
254}
255//-----------------------------------------------------------------------
256void VisibilityOctreeSceneManager::_updateSceneGraph(Camera* cam)
257{
258        mVisibilityManager->GetCullingManager()->SetHierarchyInterface(mHierarchyInterface);
259        mHierarchyInterface->SetRenderSystem(mDestRenderSystem);
260
261#ifdef GTP_VISIBILITY_MODIFIED_OGRE
262    mHierarchyInterface->SetNumOctreeNodes(mNumOctreeNodes);
263#endif
264        OctreeSceneManager::_updateSceneGraph(cam);
265}
266//-----------------------------------------------------------------------
267bool VisibilityOctreeSceneManager::setOption(const String & key, const void * val)
268{
269        if (key == "UseDepthPass")
270        {
271                mUseDepthPass = (*static_cast<const bool *>(val));
272                return true;
273        }
274        if (key == "PrepareVisualization")
275        {
276                mShowVisualization = (*static_cast<const bool *>(val));
277                return true;
278        }
279        if (key == "RenderNodesForViz")
280        {
281                mRenderNodesForViz = (*static_cast<const bool *>(val));
282                return true;
283        }
284        if (key == "RenderNodesContentForViz")
285        {
286                mRenderNodesContentForViz = (*static_cast<const bool *>(val));
287                return true;
288        }
289        if (key == "SkyBoxEnabled")
290        {
291                mSkyBoxEnabled = (*static_cast<const bool *>(val));
292                return true;
293        }
294        if (key == "SkyPlaneEnabled")
295        {
296                mSkyPlaneEnabled = (*static_cast<const bool *>(val));
297                return true;
298        }
299        if (key == "SkyDomeEnabled")
300        {
301                mSkyDomeEnabled = (*static_cast<const bool *>(val));
302                return true;
303        }
304        if (key == "VisualizeCulledNodes")
305        {
306                mVisualizeCulledNodes = (*static_cast<const bool *>(val));
307                return true;
308        }
309        if (key == "DelayRenderTransparents")
310        {
311                mDelayRenderTransparents = (*static_cast<const bool *>(val));
312                return true;
313        }
314        return VisibilityOptionsManager(mVisibilityManager, mHierarchyInterface).
315                setOption(key, val) || OctreeSceneManager::setOption(key, val);
316}
317//-----------------------------------------------------------------------
318bool VisibilityOctreeSceneManager::getOption(const String & key, void *val)
319{
320        if (key == "NumHierarchyNodes")
321        {
322                * static_cast<unsigned int *>(val) = (unsigned int)mNumOctreeNodes;
323                return true;
324        }
325
326        return VisibilityOptionsManager(mVisibilityManager, mHierarchyInterface).
327                getOption(key, val) && OctreeSceneManager::getOption(key, val);
328}
329//-----------------------------------------------------------------------
330bool VisibilityOctreeSceneManager::getOptionValues(const String & key, StringVector  &refValueList)
331{
332        return OctreeSceneManager::getOptionValues( key, refValueList );
333}
334//-----------------------------------------------------------------------
335bool VisibilityOctreeSceneManager::getOptionKeys(StringVector & refKeys)
336{
337        return  VisibilityOptionsManager(mVisibilityManager, mHierarchyInterface).
338                getOptionKeys (refKeys) || OctreeSceneManager::getOptionKeys(refKeys);
339}
340//-----------------------------------------------------------------------
341void VisibilityOctreeSceneManager::setVisibilityManager(GtpVisibility::VisibilityManager *visManager)
342{
343    mVisibilityManager = visManager;
344}
345//-----------------------------------------------------------------------
346GtpVisibility::VisibilityManager *VisibilityOctreeSceneManager::getVisibilityManager()
347{
348        return mVisibilityManager;
349}
350//-----------------------------------------------------------------------
351void VisibilityOctreeSceneManager::WriteLog()
352{
353        std::stringstream d;
354
355        d << "Depth pass: " << StringConverter::toString(mUseDepthPass) << ", "
356          << "Delay transparents: " << StringConverter::toString(mDelayRenderTransparents) << ", "
357          << "Use optimization: " << StringConverter::toString(mHierarchyInterface->GetUseOptimization()) << ", "
358          << "Algorithm type: " << mVisibilityManager->GetCullingManagerType() << "\n"
359          << "Hierarchy nodes: " << mNumOctreeNodes << ", "
360          << "Traversed nodes: " << mHierarchyInterface->GetNumTraversedNodes() << ", "
361          << "Rendered nodes: " << mHierarchyInterface->GetNumRenderedNodes() << ", "
362          << "Query culled nodes: " << mVisibilityManager->GetCullingManager()->GetNumQueryCulledNodes() << ", "
363          << "Frustum culled nodes: " << mVisibilityManager->GetCullingManager()->GetNumFrustumCulledNodes() << ", "
364      << "Queries issued: " << mVisibilityManager->GetCullingManager()->GetNumQueriesIssued() << "\n";
365          /*<< "avg. FPS: " << mCurrentViewport->getTarget()->getAverageFPS() << ", "
366          << "best FPS: " << mCurrentViewport->getTarget()->getBestFPS() << ", "
367          << "worst FPS: " << mCurrentViewport->getTarget()->getWorstFPS() << ", "
368          << "best frame time: " <<     mCurrentViewport->getTarget()->getBestFrameTime() << ", "
369          << "worst frame time: " << mCurrentViewport->getTarget()->getWorstFrameTime() << "\n";*/
370
371        LogManager::getSingleton().logMessage(d.str());
372}
373//-----------------------------------------------------------------------
374void VisibilityOctreeSceneManager::renderObjects(const RenderPriorityGroup::TransparentRenderablePassList& objs,
375            bool doLightIteration, const LightList* manualLightList)
376{
377        if (!mSkipTransparents)
378        {
379                OctreeSceneManager::renderObjects(objs, doLightIteration, manualLightList);
380        }
381}
382
383}   // namespace Ogre
Note: See TracBrowser for help on using the repository browser.