#ifndef __RENDERTRAVERSER_H #define __RENDERTRAVERSER_H #include "Bvh.h" #include "OcclusionQuery.h" //#include "Timer/PerfTimer.h" #include namespace CHCDemoEngine { class Camera; class RenderQueue; struct TraversalStatistics { public: void Reset(); ////////// //-- several statistics for a rendering pass int mNumTraversedNodes; int mNumQueryCulledNodes; int mNumFrustumCulledNodes; int mNumRenderedGeometry; int mNumRenderedTriangles; int mNumRenderedNodes; int mNumIssuedQueries; int mNumStateChanges; int mNumBatches; double mWaitTime; double mQueryTime; double mRestTime; }; /** Abstract class implementing a scene traversal for rendering. */ class RenderTraverser { public: /// types of traversers enum {CULL_FRUSTUM, STOP_AND_WAIT, CHC, CHCPLUSPLUS, //CULL_COLLECTOR, NUM_TRAVERSAL_TYPES}; /** Default constructor. */ RenderTraverser(); /** Virtual constructor, has to be redefined in subclasses. */ virtual ~RenderTraverser(); /** Maim method that traverses and renders the scene. */ void RenderScene(); /** Returns the type of the traversal. The type is one of CULL_FRUSTUM: view frustum culling only STOP_AND_WAIT: hierarchical stop and wait algorithm CHC: coherent hierarchical algorithm CHCPLUSPLUS: coherent hierarchical algorithm revisited */ virtual int GetType() const = 0; /** Sets the scene hierarchy. */ void SetHierarchy(Bvh *bvh); /** Sets the camera. */ void SetCamera(Camera *cam); /** Sets the render queue. */ void SetRenderQueue(RenderQueue *rq); /** Sets the current render state. */ void SetRenderState(RenderState *state); /** The traversal statistics */ const TraversalStatistics &GetStats() const; /** The current frame id */ inline int GetCurrentFrameId() const; ////////////////// //-- methods that concern one or more of the implemented rendering algorithms /** If a render queue should be used to batch up and sort scene entities before rendering. */ void SetUseRenderQueue(bool useRenderQueue); /** If depth pass should be used. If true, the entities found visible in the current pass are stored */ void SetUseDepthPass(bool storeVisibleObjects); /** Sets visible pixels threshold for visibility classification */ void SetVisibilityThreshold(int threshold); /////////////////// //-- CHC / CHC ++ related options //-- note: could be implemented more cleanly in a CoherentOcclusionCullingTraverser parent class! /** CHC optimization to query the geometry itself instead of the bounding box. */ void SetUseOptimization(bool useOptimization); /** The number of frames a previously visible node is assumed to stay visible. */ void SetAssumedVisibleFrames(int assumedVisibleFrames); /** The maximum batch size for the i-queue */ void SetMaxBatchSize(int batchSize); /** If multiqueries should be used. */ void SetUseMultiQueries(bool useMultiQueries); /** If thight bounds should be used or the bounding boxes should be tested. */ void SetUseTightBounds(bool useTightBounds); /** If bounds should be shown */ void SetShowBounds(bool showBounds); /** Returns the entities found visible in current frame (only if StoreVisibleObjects is set) */ const SceneEntityContainer &GetVisibleObjects() const; /** Returns the current camera. */ Camera *GetCamera() const; /** Returns the maximal visible distance encountered in the scene. Useful for e.g., shadow map focussing */ float GetMaxVisibleDistance() const; /** Render objects declared as dynamic (non-static) */ void SetRenderDynamicObjects(bool dynamic); protected: /** This is the actual rendering algorithm. It must be implemented by all the subclasses. */ virtual void Traverse() = 0; /** Hierarchy traversal */ void TraverseNode(BvhNode *node); /** Issues occlusion query for a single node */ OcclusionQuery *IssueOcclusionQuery(BvhNode *node); /** Issue multiquery. */ void IssueOcclusionQuery(const OcclusionQuery &query); /** Enqueues a bvh node for distance traversal */ void EnqueueNode(BvhNode *node); /** Renders the bvh node. */ void RenderNode(BvhNode *node); /** Renders and clears the contents of the render queue. */ void ApplyRenderQueue(); /** Returns true if at least one of the objects in this node are marked as visible. maxSize describes the maximum sized node (in # of objects) that is tested. if maxSize is -1, all nodes are tested. */ bool IsNodeGeometryVisible(BvhNode *node, int maxSize); //////////// //-- members /// the current camera Camera *mCamera; /// the root of the scene hierarchy Bvh *mBvh; /// the priority queue used for front to back traversal TraversalQueue mDistanceQueue; /// the current frame id int mFrameId; /// the current render state RenderState *mRenderState; /// manages creation and destruction of the queries QueryHandler mQueryHandler; /// the statisitcs TraversalStatistics mStats; /// the render queue RenderQueue *mRenderQueue; /// the objects found visible in current frame SceneEntityContainer mVisibleObjects; /// the maximal visible distance in the scene float mMaxVisibleDistance; ///////////////// //-- algorithm parameters int mVisibilityThreshold; bool mUseOptimization; bool mUseRenderQueue; int mAssumedVisibleFrames; int mMaxBatchSize; bool mUseMultiQueries; bool mUseTightBounds; bool mShowBounds; bool mUseDepthPass; bool mRenderDynamicObjects; }; inline int RenderTraverser::GetCurrentFrameId() const { return mFrameId; } } #endif // RENDERTRAVERSER_H