source: trunk/VUT/GtpVisibilityPreprocessor/src/VspBspTree.h @ 469

Revision 469, 14.8 KB checked in by mattausch, 19 years ago (diff)

updated view cells, view cell manager. changed rendersimulator

Line 
1#ifndef _VspBspTree_H__
2#define _VspBspTree_H__
3
4#include "Mesh.h"
5#include "Containers.h"
6#include "Polygon3.h"
7#include <stack>
8#include "Statistics.h"
9#include "VssRay.h"
10#include "RayInfo.h"
11#include "ViewCellBsp.h"
12#include "ViewCell.h"
13
14class ViewCell;
15//class BspViewCell;
16class Plane3;
17class VspBspTree; 
18class BspInterior;
19class BspNode;
20class AxisAlignedBox3;
21class Ray;
22class ViewCellsStatistics;
23
24/*class BspNodeGeometry;
25class BspTreeStatistics;
26class ViewCellsStatistics;
27class BspNode;
28class BspLeaf;
29class BspInterior;
30*/
31
32/**
33        This is a view space partitioning specialised BSPtree. 
34        There are no polygon splits, but we split the sample rays.
35        The candidates for the next split plane are evaluated only
36        by checking the sampled visibility information.
37        The polygons are employed merely as candidates for the next split planes.
38*/
39class VspBspTree
40{
41public:
42       
43        /** Additional data which is passed down the BSP tree during traversal.
44        */
45        struct VspBspTraversalData
46        { 
47                /// the current node
48                BspNode *mNode;
49                /// polygonal data for splitting
50                PolygonContainer *mPolygons;
51                /// current depth
52                int mDepth;
53               
54                /// rays piercing this node
55                RayInfoContainer *mRays;
56                /// area of current node
57                float mArea;
58                /// geometry of node as induced by planes
59                BspNodeGeometry *mGeometry;
60               
61                /// pvs size
62                int mPvs;
63               
64                /** Returns average ray contribution.
65                */
66                float GetAvgRayContribution() const
67                {
68                        return (float)mPvs / ((float)mRays->size() + Limits::Small);
69                }
70
71
72                VspBspTraversalData():
73                mNode(NULL),
74                mPolygons(NULL),
75                mDepth(0),
76                mRays(NULL),
77                mPvs(0),
78                mArea(0.0),
79                mGeometry(NULL)
80                {}
81               
82                VspBspTraversalData(BspNode *node,
83                                                 PolygonContainer *polys,
84                                                 const int depth,
85                                                 RayInfoContainer *rays,
86                                                 int pvs,
87                                                 float area,
88                                                 BspNodeGeometry *geom):
89                mNode(node),
90                mPolygons(polys),
91                mDepth(depth),
92                mRays(rays),
93                mPvs(pvs),
94                mArea(area),
95                mGeometry(geom)
96                {}
97
98                VspBspTraversalData(PolygonContainer *polys,
99                                                        const int depth,
100                                                        RayInfoContainer *rays,
101                                                        BspNodeGeometry *geom):
102                mNode(NULL),
103                mPolygons(polys),
104                mDepth(depth),
105                mRays(rays),
106                mPvs(0),
107                mArea(0),
108                mGeometry(geom)
109                {}
110    };
111       
112        typedef std::stack<VspBspTraversalData> VspBspTraversalStack;
113
114        /** Default constructor creating an empty tree.
115        */
116        VspBspTree();
117
118        /** Default destructor.
119        */
120        ~VspBspTree();
121
122        /** Returns BSP Tree statistics.
123        */
124        const BspTreeStatistics &GetStatistics() const;
125 
126
127        /** Constructs the tree from a given set of rays.
128                @param sampleRays the set of sample rays the construction is based on
129                @param viewCells if not NULL, new view cells are
130                created in the leafs and stored in the container
131        */
132        void Construct(const VssRayContainer &sampleRays);
133
134        /** Returns list of BSP leaves.
135        */
136        void CollectLeaves(vector<BspLeaf *> &leaves) const;
137
138        /** Returns box which bounds the whole tree.
139        */
140        AxisAlignedBox3 GetBoundingBox()const;
141
142        /** Returns root of BSP tree.
143        */
144        BspNode *GetRoot() const;
145
146        /** Exports VspBsp tree to file.
147        */
148        bool Export(const string filename);
149
150        /** Collects the leaf view cells of the tree
151                @param viewCells returns the view cells
152        */
153        void CollectViewCells(ViewCellContainer &viewCells) const;
154
155        /** A ray is cast possible intersecting the tree.
156                @param the ray that is cast.
157                @returns the number of intersections with objects stored in the tree.
158        */
159        int CastRay(Ray &ray);
160
161        /// bsp tree construction types
162        enum {FROM_INPUT_VIEW_CELLS, FROM_SCENE_GEOMETRY, FROM_SAMPLES};
163
164        /** Returns statistics.
165        */
166        BspTreeStatistics &GetStat();
167
168        /** finds neighbouring leaves of this tree node.
169        */
170        int FindNeighbors(BspNode *n,
171                                          vector<BspLeaf *> &neighbors,
172                                          const bool onlyUnmailed) const;
173
174        /** Constructs geometry associated with the half space intersections
175                leading to this node.
176        */
177        void ConstructGeometry(BspNode *n, PolygonContainer &cell) const;
178
179        /** Constructs geometry associated with the half space intersections
180                leading to this node.
181        */
182        void ConstructGeometry(BspViewCell *vc, PolygonContainer &cell) const;
183
184        /** Construct geometry and stores it in a geometry node container.
185        */
186        void ConstructGeometry(BspNode *n, BspNodeGeometry &cell) const;
187
188        /** Returns random leaf of BSP tree.
189                @param halfspace defines the halfspace from which the leaf is taken.
190        */
191        BspLeaf *GetRandomLeaf(const Plane3 &halfspace);
192
193        /** Returns random leaf of BSP tree.
194                @param onlyUnmailed if only unmailed leaves should be returned.
195        */
196        BspLeaf *GetRandomLeaf(const bool onlyUnmailed = false);
197
198        /** Traverses tree and counts all view cells as well as their PVS size.
199        */
200        void EvaluateViewCellsStats(ViewCellsStatistics &stat) const;
201
202
203        /** Returns view cell corresponding to unbounded space.
204        */
205        BspViewCell *GetRootCell() const;
206
207        /** Returns epsilon of this tree.
208        */
209        float GetEpsilon() const;
210
211
212    int
213        CastLineSegment(const Vector3 &origin,
214                                        const Vector3 &termination,
215                                        ViewCellContainer &viewcells
216                                        );
217
218protected:
219
220        // --------------------------------------------------------------
221        // For sorting objects
222        // --------------------------------------------------------------
223        struct SortableEntry
224        {
225                enum {POLY_MIN, POLY_MAX};
226   
227                int type;
228                float value;
229                Polygon3 *poly;
230                SortableEntry() {}
231                SortableEntry(const int t, const float v, Polygon3 *poly):
232                type(t), value(v), poly(poly) {}
233               
234                bool operator<(const SortableEntry &b) const
235                {
236                        return value < b.value;
237                } 
238        };
239
240        /** Evaluates tree stats in the BSP tree leafs.
241        */
242        void EvaluateLeafStats(const VspBspTraversalData &data);
243
244        /** Subdivides node with respect to the traversal data.
245            @param tStack current traversal stack
246                @param tData traversal data also holding node to be subdivided
247                @returns new root of the subtree
248        */
249        BspNode *Subdivide(VspBspTraversalStack &tStack,
250                                           VspBspTraversalData &tData);
251
252        /** Constructs the tree from the given traversal data.
253                @param polys stores set of polygons on which subdivision may be based
254                @param rays storesset of rays on which subdivision may be based
255        */
256        void Construct(const PolygonContainer &polys, RayInfoContainer *rays);
257
258        /** Selects the best possible splitting plane.
259                @param leaf the leaf to be split
260                @param polys the polygon list on which the split decition is based
261                @param rays ray container on which selection may be based
262                @note the polygons can be reordered in the process
263                @returns the split plane
264        */
265        Plane3 SelectPlane(BspLeaf *leaf,
266                                           VspBspTraversalData &data);
267
268       
269        /** Strategies where the effect of the split plane is tested
270            on all input rays.
271
272                @returns the cost of the candidate split plane
273        */
274        float SplitPlaneCost(const Plane3 &candidatePlane,
275                                                 const VspBspTraversalData &data);
276
277
278
279        /** Subdivide leaf.
280                @param leaf the leaf to be subdivided
281               
282                @param polys the polygons to be split
283                @param frontPolys returns the polygons in front of the split plane
284                @param backPolys returns the polygons in the back of the split plane
285               
286                @param rays the polygons to be filtered
287                @param frontRays returns the polygons in front of the split plane
288                @param backRays returns the polygons in the back of the split plane
289
290                @returns the root of the subdivision
291        */
292
293        BspInterior *SubdivideNode(VspBspTraversalData &tData,
294                                                           VspBspTraversalData &frontData,
295                                                           VspBspTraversalData &backData,
296                                                           PolygonContainer &coincident);
297
298        /** Selects the split plane in order to construct a tree with
299                certain characteristics (e.g., balanced tree, least splits,
300                2.5d aligned)
301                @param polygons container of polygons
302                @param rays bundle of rays on which the split can be based
303        */
304        Plane3 SelectPlaneHeuristics(BspLeaf *leaf,
305                                                                 VspBspTraversalData &data);
306
307        /** Extracts the meshes of the objects and adds them to polygons.
308                Adds object aabb to the aabb of the tree.
309                @param maxPolys the maximal number of objects to be stored as polygons
310                @returns the number of polygons
311        */
312        int AddToPolygonSoup(const ObjectContainer &objects,
313                                                 PolygonContainer &polys,
314                                                 int maxObjects = 0);
315
316        /** Extracts the meshes of the view cells and and adds them to polygons.
317                Adds view cell aabb to the aabb of the tree.
318                @param maxPolys the maximal number of objects to be stored as polygons
319                @returns the number of polygons
320        */
321        int AddToPolygonSoup(const ViewCellContainer &viewCells,
322                                                 PolygonContainer &polys,
323                                                 int maxObjects = 0);
324
325        /** Extract polygons of this mesh and add to polygon container.
326                @param mesh the mesh that drives the polygon construction
327                @param parent the parent intersectable this polygon is constructed from
328                @returns number of polygons
329        */
330        int AddMeshToPolygons(Mesh *mesh, PolygonContainer &polys, MeshInstance *parent);
331
332        /** returns next candidate index and reorders polygons so no candidate is chosen two times
333                @param the current candidate index
334                @param max the range of candidates
335        */
336        int GetNextCandidateIdx(int currentIdx, PolygonContainer &polys);
337       
338        /** Computes best cost ratio for the suface area heuristics for axis aligned
339                splits. This heuristics minimizes the cost for ray traversal.
340                @param polys the polygons guiding the ratio computation
341                @param box the bounding box of the leaf
342                @param axis the current split axis
343                @param position returns the split position
344                @param objectsBack the number of objects in the back of the split plane
345                @param objectsFront the number of objects in the front of the split plane
346        */
347        float BestCostRatio(const PolygonContainer &polys,
348                                                const AxisAlignedBox3 &box,
349                                                const int axis,
350                                                float &position,
351                                                int &objectsBack,
352                                                int &objectsFront) const;
353       
354        /** Sorts split candidates for surface area heuristics for axis aligned splits.
355                @param polys the input for choosing split candidates
356                @param axis the current split axis
357                @param splitCandidates returns sorted list of split candidates
358        */
359        void SortSplitCandidates(const PolygonContainer &polys,
360                                                         const int axis,
361                                                         vector<SortableEntry> &splitCandidates) const;
362
363        /** Selects an axis aligned split plane.
364                Returns true if split is valied
365        */
366        bool SelectAxisAlignedPlane(Plane3 &plane, const PolygonContainer &polys) const;
367
368        /** Subdivides the rays into front and back rays according to the split plane.
369               
370                @param plane the split plane
371                @param rays contains the rays to be split. The rays are
372                           distributed into front and back rays.
373                @param frontRays returns rays on the front side of the plane
374                @param backRays returns rays on the back side of the plane
375               
376                @returns the number of splits
377        */
378        int SplitRays(const Plane3 &plane,
379                                  RayInfoContainer &rays,
380                              RayInfoContainer &frontRays,
381                                  RayInfoContainer &backRays);
382
383
384        /** Extracts the split planes representing the space bounded by node n.
385        */
386        void ExtractHalfSpaces(BspNode *n, vector<Plane3> &halfSpaces) const;
387
388        /** Adds the object to the pvs of the front and back leaf with a given classification.
389
390                @param obj the object to be added
391                @param cf the ray classification regarding the split plane
392                @param frontPvs returns the PVS of the front partition
393                @param backPvs returns the PVS of the back partition
394       
395        */
396        void AddObjToPvs(Intersectable *obj, const int cf, int &frontPvs, int &backPvs) const;
397       
398        /** Computes PVS size induced by the rays.
399        */
400        int ComputePvsSize(const RayInfoContainer &rays) const;
401
402        /** Returns true if tree can be terminated.
403        */
404        inline bool TerminationCriteriaMet(const VspBspTraversalData &data) const;
405
406        /** Computes accumulated ray lenght of this rays.
407        */
408        float AccumulatedRayLength(const RayInfoContainer &rays) const;
409
410        /** Splits polygons with respect to the split plane.
411
412                @param plane the split plane
413                @param polys the polygons to be split. the polygons are consumed and
414                           distributed to the containers frontPolys, backPolys, coincident.
415                @param frontPolys returns the polygons in the front of the split plane
416                @param backPolys returns the polygons in the back of the split plane
417                @param coincident returns the polygons coincident to the split plane
418
419                @returns the number of splits   
420        */
421        int SplitPolygons(const Plane3 &plane,
422                                          PolygonContainer &polys,
423                                          PolygonContainer &frontPolys,
424                                          PolygonContainer &backPolys,
425                                          PolygonContainer &coincident) const;
426
427        /** Adds ray sample contributions to the PVS.
428                @param sampleContributions the number contributions of the samples
429                @param contributingSampels the number of contributing rays
430               
431        */
432        void AddToPvs(BspLeaf *leaf,
433                                  const RayInfoContainer &rays,
434                                  int &sampleContributions,
435                                  int &contributingSamples);
436
437
438
439 
440        /// Pointer to the root of the tree
441        BspNode *mRoot;
442               
443        BspTreeStatistics mStat;
444
445        /// Strategies for choosing next split plane.
446        enum {NO_STRATEGY = 0,
447                  RANDOM_POLYGON = 1,
448                  AXIS_ALIGNED = 2,
449                  LEAST_RAY_SPLITS = 256,
450                  BALANCED_RAYS = 512,
451                  PVS = 1024
452                };
453
454        /// box around the whole view domain
455        AxisAlignedBox3 mBox;
456
457        /// view cell corresponding to unbounded space
458        BspViewCell *mRootCell;
459
460        /// minimal number of rays before subdivision termination
461        int mTermMinRays;
462        /// maximal possible depth
463        int mTermMaxDepth;
464        /// mininum area
465        float mTermMinArea;
466        /// mininum PVS
467        int mTermMinPvs;
468
469        /// minimal number of rays for axis aligned split
470        int mTermMinRaysForAxisAligned;
471        /// minimal number of objects for axis aligned split
472        int mTermMinObjectsForAxisAligned;
473        /// maximal contribution per ray
474        float mTermMaxRayContribution;
475        /// minimal accumulated ray length
476        float mTermMinAccRayLength;
477
478
479        /// strategy to get the best split plane
480        int mSplitPlaneStrategy;
481        /// number of candidates evaluated for the next split plane
482        int mMaxPolyCandidates;
483        /// number of candidates for split planes evaluated using the rays
484        int mMaxRayCandidates;
485        /// balancing factor for PVS criterium
486        float mCtDivCi;
487
488        //-- axis aligned split criteria
489        float mAaCtDivCi;
490        float mSplitBorder;
491        float mMaxCostRatio;
492
493        //-- factors guiding the split plane heuristics
494        float mLeastRaySplitsFactor;
495        float mBalancedRaysFactor;
496        float mPvsFactor;
497
498        /// if area or accumulated ray lenght should be used for PVS heuristics
499        bool mPvsUseArea;
500
501        float mEpsilon;
502
503        int mMaxTests;
504
505private:
506       
507        static const float sLeastRaySplitsTable[5];
508        /** Evaluates split plane classification with respect to the plane's
509                contribution for balanced rays.
510        */
511        static const float sBalancedRaysTable[5];
512
513        /// Generates unique ids for PVS criterium
514        static void GenerateUniqueIdsForPvs();
515
516        //-- unique ids for PVS criterium
517        static int sFrontId;
518        static int sBackId;
519        static int sFrontAndBackId;
520};
521
522#endif
Note: See TracBrowser for help on using the repository browser.