source: GTP/trunk/Lib/Vis/Preprocessing/src/VspTree.h @ 1576

Revision 1576, 26.5 KB checked in by mattausch, 18 years ago (diff)

added measurement for pvs entries size decrease during subdivision

Line 
1#ifndef _VspTree_H__
2#define _VspTree_H__
3
4#include <stack>
5
6#include "Mesh.h"
7#include "Containers.h"
8#include "Statistics.h"
9#include "VssRay.h"
10#include "RayInfo.h"
11#include "gzstream.h"
12#include "SubdivisionCandidate.h"
13
14
15namespace GtpVisibilityPreprocessor {
16
17class ViewCellLeaf;
18class Plane3;
19class AxisAlignedBox3;
20class Ray;
21class ViewCellsStatistics;
22class ViewCellsManager;
23class MergeCandidate;
24class Beam;
25class ViewCellsTree;
26class Environment;
27class VspInterior;
28class VspLeaf;
29class VspNode;
30class KdNode;
31class KdInterior;
32class KdLeaf;
33class HierarchyManager;
34class KdIntersectable;
35class KdTree;
36class VspTree;
37class KdTreeStatistics;
38
39
40/** View space partition statistics.
41*/
42class VspTreeStatistics: public StatisticsBase
43{
44public:
45        // total number of nodes
46        int nodes;
47        // number of splits
48        int splits[3];
49       
50        // totals number of rays
51        int rays;
52        // maximal reached depth
53        int maxDepth;
54        // minimal depth
55        int minDepth;
56       
57        // max depth nodes
58        int maxDepthNodes;
59        // minimum depth nodes
60        int minDepthNodes;
61        // max depth nodes
62        int minPvsNodes;
63        // nodes with minimum PVS
64        int minRaysNodes;
65        // max ray contribution nodes
66        int maxRayContribNodes;
67        // minimum area nodes
68        int minProbabilityNodes;
69        /// nodes termination because of max cost ratio;
70        int maxCostNodes;
71        // max number of rays per node
72        int maxObjectRefs;
73        /// samples contributing to pvs
74        int contributingSamples;
75        /// sample contributions to pvs
76        int sampleContributions;
77        /// largest pvs
78        int maxPvs;
79        /// number of invalid leaves
80        int invalidLeaves;
81        /// accumulated number of rays refs
82        int accumRays;
83        /// overall pvs size
84        int pvs;
85        // accumulated depth (used to compute average)
86        int accumDepth;
87        // global cost ratio violations
88        int mGlobalCostMisses;
89
90        // Constructor
91        VspTreeStatistics()
92        {
93                Reset();
94        }
95
96        int Nodes() const {return nodes;}
97        int Interior() const { return nodes / 2; }
98        int Leaves() const { return (nodes / 2) + 1; }
99       
100        // TODO: computation wrong
101        double AvgDepth() const { return accumDepth / (double)Leaves();};
102        double AvgRays() const { return accumRays / (double)Leaves();};
103
104        void Reset()
105        {
106                nodes = 0;
107                for (int i = 0; i < 3; ++ i)
108                        splits[i] = 0;
109               
110                maxDepth = 0;
111                minDepth = 99999;
112                accumDepth = 0;
113        pvs = 0;
114                maxDepthNodes = 0;
115                minPvsNodes = 0;
116                minRaysNodes = 0;
117                maxRayContribNodes = 0;
118                minProbabilityNodes = 0;
119                maxCostNodes = 0;
120
121                contributingSamples = 0;
122                sampleContributions = 0;
123
124                maxPvs = 0;
125                invalidLeaves = 0;
126                accumRays = 0;
127                maxObjectRefs = 0;
128                mGlobalCostMisses = 0;
129        }
130
131        void Print(ostream &app) const;
132
133        friend ostream &operator<<(ostream &s, const VspTreeStatistics &stat)
134        {
135                stat.Print(s);
136                return s;
137        }
138};
139
140
141/**
142    VspNode abstract class serving for interior and leaf node implementation
143*/
144class VspNode
145{
146public:
147       
148        // types of vsp nodes
149        enum {Interior, Leaf};
150
151        VspNode();
152        virtual ~VspNode(){};
153        VspNode(VspInterior *parent);
154
155        /** Determines whether this node is a leaf or not
156                @return true if leaf
157        */
158        virtual bool IsLeaf() const = 0;
159
160        virtual int Type() const = 0;
161
162        /** Determines whether this node is a root
163                @return true if root
164        */
165        virtual bool IsRoot() const;
166        /** Returns parent node.
167        */
168        VspInterior *GetParent();
169        /** Sets parent node.
170        */
171        void SetParent(VspInterior *parent);
172        /** Returns true if this node is a sibling of node n.
173        */
174        bool IsSibling(VspNode *n) const;
175        /** returns depth of the node.
176        */
177        int GetDepth() const;
178        /** returns true if the whole subtree is valid
179        */
180        bool TreeValid() const;
181
182        void SetTreeValid(const bool v);
183
184        //-- mailing options
185
186        void Mail() { mMailbox = sMailId; }
187        static void NewMail() { ++ sMailId; }
188        bool Mailed() const { return mMailbox == sMailId; }
189
190
191        static int sMailId;
192        int mMailbox;
193
194        int mTimeStamp;
195
196protected:
197
198        /// if this sub tree is a completely valid view space region
199        bool mTreeValid;
200        /// parent of this node
201        VspInterior *mParent;
202};
203
204
205/** BSP interior node implementation
206*/
207class VspInterior: public VspNode
208{
209public:
210        /** Standard contructor taking split plane as argument.
211        */
212        VspInterior(const AxisAlignedPlane &plane);
213
214        ~VspInterior();
215        /** @return false since it is an interior node
216        */
217        bool IsLeaf() const;
218
219        int Type() const;
220
221        VspNode *GetBack();
222        VspNode *GetFront();
223
224        /** Returns split plane.
225        */
226        AxisAlignedPlane GetPlane() const;
227
228        /** Returns position of split plane.
229        */
230        float GetPosition() const;
231
232        /** Returns split axis.
233        */
234        int GetAxis() const;
235
236        /** Replace front or back child with new child.
237        */
238        void ReplaceChildLink(VspNode *oldChild, VspNode *newChild);
239
240        /** Replace front and back child.
241        */
242        void SetupChildLinks(VspNode *front, VspNode *back);
243
244        friend ostream &operator<<(ostream &s, const VspInterior &A)
245        {
246                return s << A.mPlane.mAxis << " " << A.mPlane.mPosition;
247        }
248
249        AxisAlignedBox3 GetBoundingBox() const;
250        void SetBoundingBox(const AxisAlignedBox3 &box);
251
252        /** Computes intersection of this plane with the ray segment.
253        */
254        int ComputeRayIntersection(const RayInfo &rayData, float &t) const
255        {
256                return rayData.ComputeRayIntersection(mPlane.mAxis, mPlane.mPosition, t);
257        }
258
259
260protected:
261        /// bounding box for this interior node: should we really store this?
262        AxisAlignedBox3 mBoundingBox;
263
264        /// Splitting plane corresponding to this node
265        AxisAlignedPlane mPlane;
266
267        /// back node
268        VspNode *mBack;
269        /// front node
270        VspNode *mFront;
271};
272
273
274/** BSP leaf node implementation.
275*/
276class VspLeaf: public VspNode
277{
278        friend VspTree;
279
280public:
281        VspLeaf();
282        VspLeaf(ViewCellLeaf *viewCell);
283        VspLeaf(VspInterior *parent);
284        VspLeaf(VspInterior *parent, ViewCellLeaf *viewCell);
285
286        ~VspLeaf();
287
288        /** @return true since it is an interior node
289        */
290        bool IsLeaf() const;
291       
292        int Type() const;
293
294        /** Returns pointer of view cell.
295        */
296        ViewCellLeaf *GetViewCell() const;
297        /** Sets pointer to view cell.
298        */
299        void SetViewCell(ViewCellLeaf *viewCell);
300
301        SubdivisionCandidate *GetSubdivisionCandidate()
302        {
303                return mSubdivisionCandidate;
304        }
305
306        void SetSubdivisionCandidate(SubdivisionCandidate *candidate)
307        {
308                mSubdivisionCandidate = candidate;
309        }
310
311
312public:
313
314        /// Rays piercing this leaf.
315        VssRayContainer mVssRays;
316        /// leaf pvs
317        ObjectPvs *mPvs;
318        /// Probability that the view point lies in this leaf
319        float mProbability;
320
321protected:
322
323        /// pointer to a split plane candidate splitting this leaf
324        SubdivisionCandidate *mSubdivisionCandidate;
325        /// if NULL this does not correspond to feasible viewcell
326        ViewCellLeaf *mViewCell;
327};
328
329
330/** View Space Partitioning tree.
331*/
332class VspTree
333{
334        friend class ViewCellsParseHandlers;
335        friend class HierarchyManager;
336
337public:
338       
339        /** Additional data which is passed down the BSP tree during traversal.
340        */
341        class VspTraversalData
342        { 
343        public:
344               
345                /** Returns average ray contribution.
346                */
347                float GetAvgRayContribution() const
348                {
349                        return (float)mPvs / ((float)mRays->size() + Limits::Small);
350                }
351
352
353                VspTraversalData():
354                mNode(NULL),
355                mDepth(0),
356                mRays(NULL),
357                mPvs(0),
358                mProbability(0.0),
359                mMaxCostMisses(0),
360                mPriority(0)
361                {}
362               
363                VspTraversalData(VspLeaf *node,
364                                                 const int depth,
365                                                 RayInfoContainer *rays,
366                                                 const int pvs,
367                                                 const float p,
368                                                 const AxisAlignedBox3 &box):
369                mNode(node),
370                mDepth(depth),
371                mRays(rays),
372                mPvs(pvs),
373                mProbability(p),
374                mBoundingBox(box),
375                mMaxCostMisses(0),
376                mPriority(0)
377                {}
378
379                VspTraversalData(const int depth,
380                                                 RayInfoContainer *rays,
381                                                 const AxisAlignedBox3 &box):
382                mNode(NULL),
383                mDepth(depth),
384                mRays(rays),
385                mPvs(0),
386                mProbability(0),
387                mMaxCostMisses(0),
388                mBoundingBox(box)
389                {}
390
391                /** Returns cost of the traversal data.
392                */
393                float GetCost() const
394                {
395                        return mPriority;
396                }
397
398                /// deletes contents and sets them to NULL
399                void Clear()
400                {
401                        DEL_PTR(mRays);
402
403                        if (mNode)
404                        {
405                                // delete old view cell
406                                delete mNode->GetViewCell();
407                                delete mNode;
408                                mNode = NULL;
409                        }
410                }
411
412                /// the current node
413                VspLeaf *mNode;
414                /// current depth
415                int mDepth;
416                /// rays piercing this node
417                RayInfoContainer *mRays;
418                /// the probability that this node contains view point
419                float mProbability;
420                /// the bounding box of the node
421                AxisAlignedBox3 mBoundingBox;
422                /// pvs size
423                int mPvs;
424                /// how often this branch has missed the max-cost ratio
425                int mMaxCostMisses;
426                // current priority
427                float mPriority;
428
429               
430                friend bool operator<(const VspTraversalData &a, const VspTraversalData &b)
431                {
432                        return a.GetCost() < b.GetCost();
433                }
434    };
435
436        /** Candidate for a view space split.
437        */
438        class VspSubdivisionCandidate: public SubdivisionCandidate
439        { 
440        public:
441
442                static VspTree* sVspTree;
443
444                /// the current split plane
445                AxisAlignedPlane mSplitPlane;
446                /// parent node traversal data
447                VspTraversalData mParentData;
448               
449                VspSubdivisionCandidate(const VspTraversalData &tData): mParentData(tData)
450                {};
451
452                ~VspSubdivisionCandidate()
453                {
454                        mParentData.Clear();
455                }
456
457                int Type() const { return VIEW_SPACE; }
458
459                void EvalPriority()
460                {
461                        sVspTree->EvalSubdivisionCandidate(*this);     
462                }
463
464                bool GlobalTerminationCriteriaMet() const
465                {
466                        return sVspTree->GlobalTerminationCriteriaMet(mParentData);
467                }
468
469                VspSubdivisionCandidate(
470                        const AxisAlignedPlane &plane,
471                        const VspTraversalData &tData):
472                mSplitPlane(plane), mParentData(tData)
473                {}
474        };
475
476        /** Struct for traversing line segment.
477        */
478        struct LineTraversalData
479        {
480                VspNode *mNode;
481                Vector3 mExitPoint;
482                float mMaxT;
483   
484                LineTraversalData () {}
485                LineTraversalData (VspNode *n, const Vector3 &p, const float maxt):
486                mNode(n), mExitPoint(p), mMaxT(maxt) {}
487        };
488
489        /** Default constructor creating an empty tree.
490        */
491        VspTree();
492        /** Default destructor.
493        */
494        ~VspTree();
495
496        /** Returns BSP Tree statistics.
497        */
498        const VspTreeStatistics &GetStatistics() const;
499 
500        /** Returns bounding box of the specified node.
501        */
502        AxisAlignedBox3 GetBoundingBox(VspNode *node) const;
503
504        /** Returns list of BSP leaves with pvs smaller than
505                a certain threshold.
506                @param onlyUnmailed if only the unmailed leaves should be considered
507                @param maxPvs the maximal pvs of a leaf to be added (-1 means unlimited)
508        */
509        void CollectLeaves(vector<VspLeaf *> &leaves,
510                                           const bool onlyUnmailed = false,
511                                           const int maxPvs = -1) const;
512
513        /** Returns box which bounds the whole tree.
514        */
515        AxisAlignedBox3 GetBoundingBox() const;
516
517        /** Returns root of the view space partitioning tree.
518        */
519        VspNode *GetRoot() const;
520
521        /** Collects the leaf view cells of the tree
522                @param viewCells returns the view cells
523        */
524        void CollectViewCells(ViewCellContainer &viewCells, bool onlyValid) const;
525
526        /** A ray is cast possible intersecting the tree.
527                @param the ray that is cast.
528                @returns the number of intersections with objects stored in the tree.
529        */
530        int CastRay(Ray &ray);
531
532
533        /** finds neighbouring leaves of this tree node.
534        */
535        int FindNeighbors(VspLeaf *n,
536                                          vector<VspLeaf *> &neighbors,
537                                          const bool onlyUnmailed) const;
538
539        /** Returns random leaf of BSP tree.
540                @param halfspace defines the halfspace from which the leaf is taken.
541        */
542        VspLeaf *GetRandomLeaf(const Plane3 &halfspace);
543
544        /** Returns random leaf of BSP tree.
545                @param onlyUnmailed if only unmailed leaves should be returned.
546        */
547        VspLeaf *GetRandomLeaf(const bool onlyUnmailed = false);
548
549        /** Returns epsilon of this tree.
550        */
551        float GetEpsilon() const;
552
553        /** Casts line segment into the tree.
554                @param origin the origin of the line segment
555                @param termination the end point of the line segment
556                @returns view cells intersecting the line segment.
557        */
558    int CastLineSegment(const Vector3 &origin,
559                                                const Vector3 &termination,
560                                                ViewCellContainer &viewcells,
561                                                const bool useMailboxing = true);
562
563               
564        /** Sets pointer to view cells manager.
565        */
566        void SetViewCellsManager(ViewCellsManager *vcm);
567
568        /** Returns view cell the current point is located in.
569                @param point the current view point
570                @param active if currently active view cells should be returned or
571                elementary view cell
572        */
573        ViewCell *GetViewCell(const Vector3 &point, const bool active = false);
574
575
576        /** Returns true if this view point is in a valid view space,
577                false otherwise.
578        */
579        bool ViewPointValid(const Vector3 &viewPoint) const;
580
581        /** Returns view cell corresponding to
582                the invalid view space.
583        */
584        VspViewCell *GetOutOfBoundsCell();
585
586        /** Writes tree to output stream
587        */
588        bool Export(OUT_STREAM &stream);
589
590        /** Casts beam, i.e. a 5D frustum of rays, into tree.
591                Tests conservative using the bounding box of the nodes.
592                @returns number of view cells it intersected
593        */
594        int CastBeam(Beam &beam);
595
596        /** Checks if tree validity-flags are right
597                with respect to view cell valitiy.
598                If not, marks subtree as invalid.
599        */
600        void ValidateTree();
601
602        /** Invalid view cells are added to the unbounded space
603        */
604        void CollapseViewCells();
605
606        /** Collects rays stored in the leaves.
607        */
608        void CollectRays(VssRayContainer &rays);
609
610        /** Intersects box with the tree and returns the number of intersected boxes.
611                @returns number of view cells found
612        */
613        int ComputeBoxIntersections(const AxisAlignedBox3 &box,
614                                                                ViewCellContainer &viewCells) const;
615
616        /** Returns view cells of this ray, either taking precomputed cells
617                or by recomputation.
618        */
619        void GetViewCells(const VssRay &ray, ViewCellContainer &viewCells);
620
621        /** Returns view cells tree.
622        */
623        ViewCellsTree *GetViewCellsTree() const { return mViewCellsTree; }
624
625        /** Sets the view cells tree.
626        */
627        void SetViewCellsTree(ViewCellsTree *vt) { mViewCellsTree = vt; }
628
629#if WORK_WITH_VIEWCELLS
630        /** Remove the references of the parent view cell from the kd nodes associated with
631                the objects.
632        */
633        void RemoveParentViewCellReferences(ViewCell *parent) const;
634
635        /** Adds references to the view cell to the kd nodes associated with the objects.
636        */
637        void AddViewCellReferences(ViewCell *vc) const;
638#endif
639
640protected:
641
642        // --------------------------------------------------------------
643        // For sorting objects
644        // --------------------------------------------------------------
645        struct SortableEntry
646        {
647                enum EType
648                {
649                        ERayMin,
650                        ERayMax
651                };
652
653                int type;
654                float value;
655                VssRay *ray;
656 
657                SortableEntry() {}
658                SortableEntry(const int t, const float v, VssRay *r):
659                type(t), value(v), ray(r)
660                {
661                }
662               
663                friend inline bool operator<(const SortableEntry &a, const SortableEntry &b)
664                {       // prefer max event
665                        //if (EpsilonEqual(a.value, b.value, 0.0001f))
666                        //      return (a.type == ERayMax);
667
668                        return (a.value < b.value);
669                }
670        };
671
672        /** faster evaluation of split plane cost for kd axis aligned cells.
673        */
674        float EvalLocalSplitCost(const VspTraversalData &data,
675                                                         const AxisAlignedBox3 &box,
676                                                         const int axis,
677                                                         const float &position,
678                                                         float &pFront,
679                                                         float &pBack) const;
680
681        void ComputeBoundingBox(const VssRayContainer &rays,
682                                                        AxisAlignedBox3 *forcedBoundingBox);
683
684        /** Evaluates candidate for splitting.
685        */
686        void EvalSubdivisionCandidate(VspSubdivisionCandidate &splitData);
687
688        /** Evaluates render cost decrease of next split.
689        */
690        float EvalRenderCostDecrease(const AxisAlignedPlane &candidatePlane,
691                                                                 const VspTraversalData &data,
692                                                                 float &normalizedOldRenderCost) const;
693
694        /** Collects view cells in the subtree under root.
695        */
696        void CollectViewCells(VspNode *root,
697                                                  bool onlyValid,
698                                                  ViewCellContainer &viewCells,
699                                                  bool onlyUnmailed = false) const;
700
701        /** Returns view cell corresponding to
702                the invalid view space. If it does not exist, it is created.
703        */
704        VspViewCell *GetOrCreateOutOfBoundsCell();
705
706        /** Collapses the tree with respect to the view cell partition,
707                i.e. leaves having the same view cell are collapsed.
708                @param node the root of the subtree to be collapsed
709                @param collapsed returns the number of collapsed nodes
710                @returns node of type leaf if the node could be collapsed,
711                this node otherwise
712        */
713        VspNode *CollapseTree(VspNode *node, int &collapsed);
714
715        /** Helper function revalidating the view cell leaf list after merge.
716        */
717        void RepairViewCellsLeafLists();
718
719        /** Evaluates tree stats in the BSP tree leafs.
720        */
721        void EvaluateLeafStats(const VspTraversalData &data);
722
723        /** Subdivides node using a best split priority queue.
724            @param tQueue the best split priority queue
725                @param splitCandidate the candidate for the next split
726                @param globalCriteriaMet if the global termination criteria were already met
727                @returns new root of the subtree
728        */
729        VspNode *Subdivide(SplitQueue &tQueue,
730                                           SubdivisionCandidate *splitCandidate,
731                                           const bool globalCriteriaMet);
732
733        /** Adds stats to subdivision log file.
734        */
735        void AddSubdivisionStats(const int viewCells,
736                                                         const float renderCostDecr,
737                                                         const float totalRenderCost,
738                                                         const float avgRenderCost);
739       
740        /** Subdivides leaf.
741                       
742                @param tData data object holding, e.g., a pointer to the leaf
743                @param frontData returns the data (e.g.,  pointer to the leaf) in front of the split plane
744                @param backData returns the data (e.g.,  pointer to the leaf) in the back of the split plane
745               
746                @param rays the polygons to be filtered
747                @param frontRays returns the polygons in front of the split plane
748       
749                @returns the root of the subdivision
750        */
751        VspInterior *SubdivideNode(const AxisAlignedPlane &splitPlane,
752                                                           VspTraversalData &tData,
753                                                           VspTraversalData &frontData,
754                               VspTraversalData &backData);
755
756        /** Selects an axis aligned for the next split.
757                @returns cost for this split
758        */
759        float SelectSplitPlane(const VspTraversalData &tData,
760                                                   AxisAlignedPlane &plane,
761                                                   float &pFront,
762                                                   float &pBack);
763
764        /** Sorts split candidates along the specified axis.
765                The split candidates are generated on possible visibility
766                events (i.e., where ray segments intersect the ray boundaries).
767                The sorted candidates are needed to compute the heuristics.
768
769                @param polys the input for choosing split candidates
770                @param axis the current split axis
771                @param splitCandidates returns sorted list of split candidates
772        */
773        void SortSubdivisionCandidates(const RayInfoContainer &rays,
774                                                         const int axis,
775                                                         float minBand,
776                                                         float maxBand);
777
778        /** Evaluate pvs size as induced by the samples.
779        */
780        int EvalPvsSize(const RayInfoContainer &rays) const;
781
782        int EvalPvsEntriesIncr(VspSubdivisionCandidate &splitCandidate) const;
783
784        /** Returns number of effective entries in the pvs.
785        */
786        int EvalPvsEntriesSize(const RayInfoContainer &rays) const;
787        int EvalPvsEntriesContribution(const VssRay &ray, const bool isTermination) const;
788        /** Computes best cost for axis aligned planes.
789        */
790        float EvalLocalCostHeuristics(const VspTraversalData &tData,
791                                                                  const AxisAlignedBox3 &box,
792                                                                  const int axis,
793                                                                  float &position);
794
795
796        //////////////////////////////////////////
797        // Helper function for computing heuristics
798
799        /** Evaluates the contribution to left and right pvs at a visibility event ve.
800                @param ve the visibility event
801                @param pvsLeft updates the left pvs
802                @param rightPvs updates the right pvs
803        */
804        void EvalHeuristics(const SortableEntry &ve, int &pvsLeft, int &pvsRight) const;
805
806        /** Evaluates contribution of min event to pvs
807        */
808        int EvalMinEventContribution(
809                const VssRay &ray, const bool isTermination) const;
810
811        /** Evaluates contribution of max event to pvs
812        */
813        int EvalMaxEventContribution(
814                const VssRay &ray, const bool isTermination) const;
815
816        /** Evaluates contribution of kd leaf when encountering a min event
817        */
818        int EvalMinEventContribution(KdLeaf *leaf) const;
819        /**  Evaluates contribution of kd leaf when encountering a max event
820        */
821        int EvalMaxEventContribution(KdLeaf *leaf) const;
822
823        /** Prepares objects for the heuristics.
824                @returns pvs size as seen by the rays.
825        */
826        int PrepareHeuristics(const RayInfoContainer &rays);
827       
828        /** Prepare a single ray for heuristics.
829        */
830        int PrepareHeuristics(const VssRay &ray, const bool isTermination);
831        /** Prepare a single kd leaf for heuristics.
832        */
833        int PrepareHeuristics(KdLeaf *leaf);
834
835        /////////////////////////////////////////////////////////////////////////////
836
837
838        /** Subdivides the rays into front and back rays according to the split plane.
839               
840                @param plane the split plane
841                @param rays contains the rays to be split. The rays are
842                           distributed into front and back rays.
843                @param frontRays returns rays on the front side of the plane
844                @param backRays returns rays on the back side of the plane
845               
846                @returns the number of splits
847        */
848        int SplitRays(const AxisAlignedPlane &plane,
849                                  RayInfoContainer &rays,
850                              RayInfoContainer &frontRays,
851                                  RayInfoContainer &backRays) const;
852
853        void UpdatePvsEntriesContribution(
854                const VssRay &ray,
855                const bool isTermination,
856                const int cf,
857                float &frontPvs,
858                float &backPvs,
859                float &totalPvs) const;
860
861        /** Classfifies the object with respect to the
862                pvs of the front and back leaf and updates pvs size
863                accordingly.
864
865                @param obj the object to be added
866                @param cf the ray classification regarding the split plane
867                @param frontPvs returns the PVS of the front partition
868                @param backPvs returns the PVS of the back partition
869       
870        */
871        void UpdateContributionsToPvs(
872                const VssRay &ray,
873                const bool isTermination,
874                const int cf,
875                float &frontPvs,
876                float &backPvs,
877                float &totalPvs) const;
878
879        /** Evaluates the contribution for objects.
880        */
881        void UpdateContributionsToPvs(
882                Intersectable *obj,
883                const int cf,
884                float &frontPvs,
885                float &backPvs,
886                float &totalPvs) const;
887
888        /** Evaluates the contribution for bounding volume leaves.
889        */
890        void UpdateContributionsToPvs(
891                BvhLeaf *leaf,
892                const int cf,
893                float &frontPvs,
894                float &backPvs,
895                float &totalPvsm,
896                const bool countEntries = false) const;
897
898        /** Evaluates the contribution for kd leaves.
899        */
900        void UpdateContributionsToPvs(
901                KdLeaf *leaf,
902                const int cf,
903                float &frontPvs,
904                float &backPvs,
905                float &totalPvs) const;
906
907        /** Returns true if tree can be terminated.
908        */
909        bool LocalTerminationCriteriaMet(const VspTraversalData &data) const;
910
911        /** Returns true if global tree can be terminated.
912        */
913        bool GlobalTerminationCriteriaMet(const VspTraversalData &data) const;
914
915        /** Adds ray sample contributions to the PVS.
916                @param sampleContributions the number contributions of the samples
917                @param contributingSampels the number of contributing rays
918               
919        */
920        void AddSamplesToPvs(VspLeaf *leaf,
921                                                 const RayInfoContainer &rays,
922                                                 float &sampleContributions,
923                                                 int &contributingSamples);
924
925        /** Propagates valid flag up the tree.
926        */
927        void PropagateUpValidity(VspNode *node);
928
929        /** Writes the node to disk
930                @note: should be implemented as visitor.
931        */
932        void ExportNode(VspNode *node, OUT_STREAM &stream);
933
934        /** Returns estimated memory usage of tree.
935        */
936        float GetMemUsage() const;
937
938        /** Updates view cell pvs of objects.
939        */
940        void ProcessViewCellObjects(ViewCell *parent,
941                ViewCell *front,
942                ViewCell *back) const;
943
944        void CreateViewCell(VspTraversalData &tData, const bool updatePvs);
945
946        /** Collect split candidates which are affected by the last split
947                and must be reevaluated.
948        */
949        void CollectDirtyCandidates(VspSubdivisionCandidate *sc, vector<SubdivisionCandidate *> &dirtyList);
950
951        void CollectDirtyCandidate(
952                const VssRay &ray,
953                const bool isTermination,
954                vector<SubdivisionCandidate *> &dirtyList) const;
955
956        /** Rays will be clipped to the bounding box.
957        */
958        void PreprocessRays(const VssRayContainer &sampleRays, RayInfoContainer &rays);
959
960        /** Evaluate subdivision statistics.
961        */
962        void EvalSubdivisionStats(const SubdivisionCandidate &tData);
963
964        SubdivisionCandidate *PrepareConstruction(
965                const VssRayContainer &sampleRays,
966                RayInfoContainer &rays);
967
968        /** Evaluates pvs contribution of this ray.
969        */
970        int EvalContributionToPvs(const VssRay &ray, const bool isTermination) const;
971
972        /** Evaluates pvs contribution of a kd node.
973        */
974        int EvalContributionToPvs(KdLeaf *leaf) const;
975
976
977protected:
978
979        /// pointer to the hierarchy of view cells
980        ViewCellsTree *mViewCellsTree;
981
982        HierarchyManager *mHierarchyManager;
983        //OspTree *mOspTree;
984        //bool mUseKdPvsForHeuristics;
985       
986        ViewCellsManager *mViewCellsManager;
987       
988        vector<SortableEntry> *mLocalSubdivisionCandidates;
989
990        /// Pointer to the root of the tree
991        VspNode *mRoot;
992               
993        VspTreeStatistics mVspStats;
994       
995        /// View cell corresponding to the space outside the valid view space
996        VspViewCell *mOutOfBoundsCell;
997
998        /// box around the whole view domain
999        AxisAlignedBox3 mBoundingBox;
1000
1001
1002        //-- local termination
1003
1004        /// minimal number of rays before subdivision termination
1005        int mTermMinRays;
1006        /// maximal possible depth
1007        int mTermMaxDepth;
1008        /// mininum probability
1009        float mTermMinProbability;
1010        /// mininum PVS
1011        int mTermMinPvs;
1012        /// maximal contribution per ray
1013        float mTermMaxRayContribution;
1014        /// maximal acceptable cost ratio
1015        float mTermMaxCostRatio;
1016        /// tolerance value indicating how often the max cost ratio can be failed
1017        int mTermMissTolerance;
1018
1019
1020        //-- global criteria
1021        float mTermMinGlobalCostRatio;
1022        int mTermGlobalCostMissTolerance;
1023       
1024
1025        /// maximal number of view cells
1026        int mMaxViewCells;
1027        /// maximal tree memory
1028        float mMaxMemory;
1029        /// the tree is out of memory
1030        bool mOutOfMemory;
1031
1032
1033        //-- split heuristics based parameters
1034       
1035        bool mUseCostHeuristics;
1036        /// balancing factor for PVS criterium
1037        float mCtDivCi;
1038        /// if only driving axis should be used for split
1039        bool mOnlyDrivingAxis;
1040        /// if random split axis should be used
1041        bool mUseRandomAxis;
1042        /// if vsp bsp tree should simulate octree
1043        bool mCirculatingAxis;
1044        /// minimal relative position where the split axis can be placed
1045        float mMinBand;
1046        /// maximal relative position where the split axis can be placed
1047        float mMaxBand;
1048
1049
1050        /// current time stamp (used for keeping split history)
1051        int mTimeStamp;
1052        // if rays should be stored in leaves
1053        bool mStoreRays;
1054
1055        /// epsilon for geometric comparisons
1056        float mEpsilon;
1057
1058
1059        /// subdivision stats output file
1060        ofstream  mSubdivisionStats;
1061        /// keeps track of cost during subdivision
1062        float mTotalCost;
1063        /// keeps track of overall pvs size during subdivision
1064        int mTotalPvsSize;
1065        /// number of currenly generated view cells
1066        int mCreatedViewCells;
1067
1068        /// weight between render cost decrease and node render cost
1069        float mRenderCostDecreaseWeight;
1070
1071        int mMaxTests;
1072};
1073
1074
1075}
1076
1077#endif
Note: See TracBrowser for help on using the repository browser.