source: trunk/VUT/GtpVisibilityPreprocessor/src/ViewCell.h @ 590

Revision 590, 11.7 KB checked in by mattausch, 18 years ago (diff)

implemented some code for merge history loading

Line 
1#ifndef _ViewCell_H__
2#define _ViewCell_H__
3
4#include "Mesh.h"
5#include "Containers.h"
6#include "Ray.h"
7#include "Statistics.h"
8//namespace GtpVisibilityPreprocessor {
9
10struct Triangle3;
11
12class BspInterior;
13class BspPvs;
14class BspLeaf;
15class VspKdTree;
16class VspKdLeaf;
17class KdLeaf;
18class ViewCellInterior;
19class MergeCandidate;
20class ViewCellsManager;
21
22/** Statistics for a view cell partition.
23*/
24
25class ViewCellsStatistics: public StatisticsBase
26{
27public:
28
29        /// number of view cells
30        int viewCells;
31
32        /// size of the PVS
33        int pvs;
34
35        /// largest PVS of all view cells
36        int maxPvs;
37
38        /// smallest PVS of all view cells
39        int minPvs;
40
41        /// view cells with empty PVS
42        int emptyPvs;
43
44        /// number of leaves covering the view space
45        int leaves;
46
47        /// largest number of leaves covered by one view cell
48        int maxLeaves;
49
50        int invalid;
51
52    // Constructor
53        ViewCellsStatistics()
54        {
55                Reset();
56        }
57
58        double AvgLeaves() const {return (double)leaves / (double)viewCells;};
59        double AvgPvs() const {return (double)pvs / (double)viewCells;};
60
61        void Reset()
62        {
63                viewCells = 0;
64                pvs = 0;
65                maxPvs = 0;
66
67                minPvs = 999999;
68                emptyPvs = 0;
69                leaves = 0;
70                maxLeaves = 0;
71                invalid = 0;
72        }
73
74        void Print(ostream &app) const;
75
76        friend ostream &operator<<(ostream &s, const ViewCellsStatistics &stat)
77        {
78                stat.Print(s);
79                return s;
80        }
81};
82
83
84/**
85        View cell with an optional mesh representation
86*/
87
88
89class ViewCell: public MeshInstance
90{
91public:
92        ViewCell();
93
94        /** Constructor taking a mesh representing the shape of the viewcell.
95        */
96        ViewCell(Mesh *mesh);
97
98        /** Default destructor.
99        */
100        virtual ~ViewCell() {}
101
102        /** Returns Pvs.
103        */
104        const ObjectPvs &GetPvs() const;
105        ObjectPvs &GetPvs();
106
107        int Type() const;
108
109        void SetParent(ViewCellInterior *parent);
110
111        /** Adds a passing ray to the passing ray container.
112        */
113        void AddPassingRay(const Ray &ray, const int contributions);
114
115        /** Returns volume of the view cell.
116        */
117        float GetVolume() const;
118
119        /** Returns area of the view cell.
120        */
121        float GetArea() const;
122
123        /** Sets the volume of the view cell.
124        */
125        void SetVolume(float volume);
126       
127        /** Sets the area of the view cell.
128        */
129        void SetArea(float area);
130
131        /** Updates the view cell statstics for this particular view cell.
132        */
133        virtual void UpdateViewCellsStats(ViewCellsStatistics &vcStat);
134
135        /** if this view cell is the root of a view cell hierarchy
136        */
137        bool IsRoot() const;
138
139        /** Returns parent view cell.
140        */
141        ViewCellInterior *GetParent() const;
142
143       
144        /** Sets the mesh for this view cell.
145        */
146        void SetMesh(Mesh *mesh);
147
148        void SetValid(const bool valid);
149        bool GetValid() const;
150
151
152
153
154        /// parent view cell in the view cell hierarchy
155        ViewCellInterior *mParent;
156
157        /// Rays piercing this view cell.
158        RayContainer mPiercingRays;
159
160
161        /** if this is a view cell correspending to a leaf in a hierarchy.
162        */
163        virtual bool IsLeaf() const = 0;
164
165  static bool SmallerPvs(const ViewCell *a,
166                                                 const ViewCell *b) {
167        return a->GetPvs().GetSize() < b->GetPvs().GetSize();
168  }
169
170
171        void SetTimeStamp(const int timeStamp);
172        int GetTimeStamp() const;
173        static void NewMail(const int reserve = 1) {
174                sMailId += sReservedMailboxes;
175                sReservedMailboxes = reserve;
176        }
177        void Mail() { mMailbox = sMailId; }
178        bool Mailed() const { return mMailbox == sMailId; }
179
180        void Mail(const int mailbox) { mMailbox = sMailId + mailbox; }
181        bool Mailed(const int mailbox) const { return mMailbox == sMailId + mailbox; }
182
183        int IncMail() { return ++mMailbox - sMailId; }
184
185
186                                                 
187        // last mail id -> warning not thread safe!
188        // both mailId and mailbox should be unique for each thread!!!
189        static int sMailId;
190        static int sReservedMailboxes;
191       
192        bool mIsActive;
193
194protected:
195
196
197        /// the potentially visible objects
198        ObjectPvs mPvs;
199
200        float mVolume;
201        float mArea;
202
203        int mTimeStamp;
204
205        bool mValid;
206};
207
208
209class ViewCellInterior: public ViewCell
210{
211public:
212        ViewCellInterior();
213        ~ViewCellInterior();
214
215        ViewCellInterior(Mesh *mesh);
216       
217
218        /** Sets pointer from parent to child and vice versa.
219        */
220        void SetupChildLink(ViewCell *l);
221        void RemoveChildLink(ViewCell *l);
222        bool IsLeaf() const;
223
224        ViewCellContainer mChildren;
225
226};
227
228/**
229        View cell belonging to a hierarchy.
230*/
231template<typename T>
232class ViewCellLeaf: public ViewCell
233{
234public:
235
236        ViewCellLeaf<T>(): mLeaf(NULL) {}
237        ViewCellLeaf<T>(Mesh *mesh):
238                ViewCell(mesh), mLeaf(NULL) {}
239
240        void UpdateViewCellsStats(ViewCellsStatistics &vcStat)
241        {
242                ViewCell::UpdateViewCellsStats(vcStat);
243
244                //if ((int)mLeaves.size() > vcStat.maxLeaves)
245                //      vcStat.maxLeaves = (int)mLeaves.size();
246                //vcStat.leaves += (int)mLeaves.size();
247        }
248
249        bool IsLeaf() const
250        {
251                return true;
252        }
253
254        /// Leaf of some hierarchy which is part of this view cell.
255        T mLeaf;
256};
257
258
259typedef ViewCellLeaf<BspLeaf *> BspViewCell;
260typedef ViewCellLeaf<KdLeaf *> KdViewCell;
261typedef ViewCellLeaf<VspKdLeaf *> VspKdViewCell;
262
263
264
265class ViewCellsTree
266{
267public:
268        ViewCellsTree(ViewCellsManager *vcm);
269        ~ViewCellsTree();
270
271        /** Returns number of leaves this view cell consists of.
272        */
273        int GetSize(ViewCell *vc) const;
274
275        /** Collects leaves corresponding to a view cell.
276        */
277        void CollectLeaves(ViewCell *vc, ViewCellContainer &leaves) const;
278
279        /** Merges view cells according to some cost heuristics.
280        */
281        int ConstructMergeTree(const VssRayContainer &rays, const ObjectContainer &objects);
282       
283        /** Refines view cells using shuffling, i.e., border leaves
284                of two view cells are exchanged if the resulting view cells
285                are tested to be "better" than the old ones.
286                @returns number of refined view cells
287        */
288        int RefineViewCells(const VssRayContainer &rays, const ObjectContainer &objects);
289
290       
291
292        /** Returns optimal set of view cells for a given number of view cells.
293        */
294        void CollectBestViewCellSet(ViewCellContainer &viewCells, const int numViewCells);
295
296        /** Root of view cells tree.
297        */
298        ViewCell *GetRoot() const;
299
300        /** Returns pvs of view cell.
301                @note pvs is returned per reference if tree is not compressed,
302                per copy else.
303        */
304        void GetPvs(ViewCell *vc, ObjectPvs &pvs) const;
305
306        /** Returns pvs size of view cell.
307        */
308        int GetPvsSize(ViewCell *vc) const;
309
310        /** Returns actual number of object in this pvs and the children.
311        */
312        int GetNumPvsEntries(ViewCell *vc) const;
313
314        /** Returns memory cost of this view cell.
315        */
316        float GetMemoryCost(ViewCell *vc) const;
317
318        /** Compresses the pvs of the view cells from the root.
319        */
320        void CompressViewCellsPvs();
321
322        /** If view cells in this tree have compressed pvs.
323        */
324        bool IsCompressed() const;
325
326        ViewCell *GetActiveViewCell(ViewCell *vc) const;
327
328protected:
329
330
331        //////////////////////////////////////////////////////////////
332        //                 merge options                            //
333        //////////////////////////////////////////////////////////////
334       
335
336        /** Returns cost of this leaf according to current heuristics.
337        */
338        float GetCostHeuristics(ViewCell *vc) const;
339
340        /** Returns cost of leaf.
341        */
342        float GetRenderCost(ViewCell *vc) const;
343
344        /** Evaluates the merge cost of this merge candidate pair.
345        */
346        void EvalMergeCost(MergeCandidate &mc) const;
347
348        /** Variance of leaf.
349        */
350        float GetVariance(ViewCell *vc) const;
351
352        /** Standard deviation of leaf.
353        */
354        float GetDeviation(ViewCell *vc) const;
355
356        /** Tries to set this merge candidate to valid.
357                @returns false if both view cells are the same
358        */
359        bool ValidateMergeCandidate(MergeCandidate &mc) const;
360
361        /** Merge view cells of leaves l1 and l2.
362                @returns difference in pvs size
363        */
364        ViewCellInterior *MergeViewCells(ViewCell *l, ViewCell *r, int &pvsDiff); //const;
365
366        /** Shuffles, i.e. takes border leaf from view cell 1 and adds it
367                to view cell 2.
368        */
369        void ShuffleLeaf(ViewCell *leaf, ViewCellInterior *vc1, ViewCellInterior *vc2) const;   
370               
371        /** Shuffles the leaves, i.e., tests if exchanging
372                the leaves helps in improving the view cells.
373        */
374        bool ShuffleLeaves(MergeCandidate &mc) const;
375
376        /** Calculates cost for merge of view cell 1 and 2.
377        */
378        float EvalShuffleCost(ViewCell *leaf,
379                                                  ViewCellInterior *vc1,
380                                                  ViewCellInterior *vc2) const;
381
382        /** Exports a snapshot of the merged view cells to disc.
383        */
384        void ExportMergedViewCells(ViewCellContainer &viewCells,
385                                                           const ObjectContainer &objects,
386                                                           const int numNewViewCells);
387
388        /** merge queue must be reset after some time because expected value
389                may not be valid.
390        */
391        void ResetMergeQueue();
392
393        /** Updates the current top level of view cells.
394                @returns number of newly merged view cells
395        */
396        int UpdateActiveViewCells(ViewCellContainer &viewCells);
397
398        void PropagateUpVisibility(ViewCellInterior *interior);
399
400        void CompressViewCellsPvs(ViewCell *root);
401
402        /** Returns memory usage of view cells.
403        */
404        float GetMemUsage() const;
405
406
407        /// if the view cell tree hold compressed pvs
408        bool mIsCompressed;
409
410        ViewCellsManager *mViewCellsManager;
411        ViewCell *mRoot;
412
413        /// if merge visualization should be shown
414        bool mExportMergedViewCells;
415
416       
417               
418        ViewCellContainer mMergedViewCells;
419       
420
421        bool mRefineViewCells;
422
423        /// weights between variance and render cost increase (must be between zero and one)
424        float mRenderCostWeight;
425
426        /// overall cost used to normalize cost ratio
427        float mOverallCost;
428        float mExpectedCost;
429    float mDeviation;
430        float mAvgRenderCost;
431
432        int mUseAreaForPvs;
433
434        int mNumActiveViewCells;
435
436        /// minimal number of view cells
437        int mMergeMinViewCells;
438        /// maximal cost ratio for the merge
439        float mMergeMaxCostRatio;
440
441        ofstream mStats;
442
443        typedef priority_queue<MergeCandidate> MergeQueue;
444
445        MergeQueue mMergeQueue;
446
447        float mMaxMemory;
448
449};
450
451
452/**
453        Candidate for leaf merging based on priority.
454*/
455class MergeCandidate
456
457        friend class ViewCellsTree;
458
459public:
460
461        MergeCandidate(ViewCell *l, ViewCell *r);
462
463        /** If this merge pair is still valid.
464        */
465        bool IsValid() const;
466
467       
468        friend bool operator<(const MergeCandidate &leafa, const MergeCandidate &leafb)
469        {
470                return leafb.GetMergeCost() < leafa.GetMergeCost();
471        }
472
473        void SetLeftViewCell(ViewCell *l);
474        void SetRightViewCell(ViewCell *l);
475
476        ViewCell *GetLeftViewCell() const;
477        ViewCell *GetRightViewCell() const;
478
479        ViewCell *GetInitialLeftViewCell() const;
480        ViewCell *GetInitialRightViewCell() const;
481
482        /** Returns the increase of the standard deviation of this merge candidate.
483        */
484        float GetDeviationIncr() const;
485
486        /** Merge cost of this candidate pair.
487        */
488        float GetMergeCost() const;
489
490        /** Render cost of this candidate.
491        */
492        float GetRenderCost() const;
493       
494        static float sRenderCostWeight;
495
496protected:
497
498        /// render cost increase by this merge
499        float mRenderCost;
500        /// increase / decrease of standard deviation
501        float mDeviationIncr;
502
503        ViewCell *mLeftViewCell;
504        ViewCell *mRightViewCell;
505
506        ViewCell *mInitialLeftViewCell;
507        ViewCell *mInitialRightViewCell;
508};
509
510
511class MergeStatistics: public StatisticsBase
512{
513public:
514       
515        int merged;
516        int siblings;
517        int candidates;
518        int nodes;
519
520        int accTreeDist;
521        int maxTreeDist;
522       
523        Real collectTime;
524        Real mergeTime;
525
526        Real overallCost;
527
528        Real expectedRenderCost;
529        Real deviation;
530        Real heuristics;
531
532        // Constructor
533        MergeStatistics()
534        {
535                Reset();
536        }
537       
538        double AvgTreeDist() const {return (double)accTreeDist / (double)merged;};
539
540        void Reset()
541        {
542                nodes = 0;
543                merged = 0;
544                siblings = 0;
545                candidates = 0;
546       
547                accTreeDist = 0;
548                maxTreeDist = 0;
549
550                collectTime = 0;
551                mergeTime = 0;
552                overallCost = 0;
553
554                expectedRenderCost = 0;
555                deviation = 0;
556                heuristics = 0;
557
558        }
559
560        void Print(ostream &app) const;
561
562        friend ostream &operator<<(ostream &s, const MergeStatistics &stat)
563        {
564                stat.Print(s);
565                return s;
566        }
567};
568
569#endif
Note: See TracBrowser for help on using the repository browser.