llroam.cpp

Go to the documentation of this file.
00001 
00032 #include "llviewerprecompiledheaders.h"
00033 
00034 #include "llroam.h"
00035 
00036 LLRoam* LLRoamTriNode::sQueues;// = new LLRoam();
00037 
00038 void LLRoamTriNode::updateLink(LLRoamTriNode* old_link, LLRoamTriNode* new_link)
00039 {
00040         if (old_link == mLeft)
00041                 mLeft = new_link;
00042         else if (old_link == mRight)
00043                 mRight = new_link;
00044         else if (old_link == mBase)
00045                 mBase = new_link;
00046 }
00047 
00048 BOOL LLRoamTriNode::split(BOOL forceful)
00049 {
00050         //U32 c1 = patch()->checkCount();
00051         if (forceful)
00052         {
00053                 initForcefulRefine();
00054         } /*else {
00055                 if (!refine())
00056                         return FALSE;
00057         }*/
00058 
00059         if (!leaf())
00060                 return TRUE;
00061 
00062         if (mLchild == NULL)
00063         {
00064                 mLchild = newLChild();
00065                 mRchild = newRChild();
00066 
00067                 //mLchild->setPatch(patch());
00068                 //mRchild->setPatch(patch());
00069 
00070                 mLchild->setLeft(mRchild);
00071                 mRchild->setRight(mLchild);
00072         }
00073 
00074         mLchild->setBase(mLeft);
00075         mRchild->setBase(mRight);
00076 
00077         if (mLeft)
00078                 mLeft->updateLink(this, mLchild);
00079         if (mRight)
00080                 mRight->updateLink(this, mRchild);
00081 
00082         mLeaf = FALSE;
00083 
00084         patch()->numTrisInc();
00085 
00086         //U32 c2 = patch()->checkCount();
00087         sQueues->numOfProcessedTrisInc();
00088         if (mBase == NULL)
00089                 return TRUE;
00090 
00091         if (mBase->base() != this)      // not Diamond shape
00092                 mBase->split(TRUE);
00093 
00094         if (mBase->leaf())
00095                 mBase->split(TRUE);
00096 
00097         mLchild->setRight(mBase->Rchild());
00098         mRchild->setLeft(mBase->Lchild());
00099         //U32 c3 = patch()->checkCount();
00100         return TRUE;
00101 }
00102 
00103 BOOL LLRoamTriNode::merge()
00104 {
00105         //U32 c1 = patch()->checkCount();
00106         if (leaf())
00107                 return TRUE;
00108 
00109         if (mBase && mBase->refine())
00110                 return FALSE;
00111 
00112         if (!mLchild->merge() || !mRchild->merge())
00113                 return FALSE;
00114 
00115         //U32 c2 = patch()->checkCount();
00116         mLeft = mLchild->base();
00117         mRight = mRchild->base();
00118 
00119         if (mLeft)
00120                 mLeft->updateLink(mLchild, this);
00121         if (mRight)
00122                 mRight->updateLink(mRchild, this);
00123 
00124         //U32 c4 = patch()->checkCount();
00125         mLeaf = TRUE;
00126 
00127         patch()->numTrisDec();
00128 
00129         //U32 c5 = patch()->checkCount();
00130         if (mBase != NULL)
00131         {
00132                 if (!mBase->merge())
00133                 {
00134                         mLeaf = FALSE;
00135                         patch()->numTrisInc();
00136                         return FALSE;
00137                 }
00138         }
00139 
00140         //U32 c6 = patch()->checkCount();
00141         return TRUE;
00142 }
00143 
00144 void LLRoamTriNode::mergeSimple()
00145 {
00146         mLeft = mLchild->base();
00147         mRight = mRchild->base();
00148         
00149         if (mLeft)
00150                 mLeft->updateLink(mLchild, this);
00151         if (mRight)
00152                 mRight->updateLink(mRchild, this);
00153         
00154         mLeaf = TRUE;
00155         patch()->numTrisDec();
00156         sQueues->numOfProcessedTrisInc();
00157 }
00158 
00159 void LLRoamTriNode::update()
00160 {
00161         if (refine())
00162                 sQueues->queueForSplit(this);
00163         else if (!leaf())
00164                 sQueues->queueForMerge(this);
00165 }
00166 
00167 /*
00168 void LLRoamTriNode::update()
00169 {
00170         //U32 c1 = patch()->checkCount();
00171         if (split())
00172         {
00173                 mLchild->update();
00174                 mRchild->update();
00175         //U32 c2 = patch()->checkCount();
00176         }
00177         else if (!leaf())
00178         {
00179                 merge();
00180         }
00181 }
00182 */
00183 
00184 LLRoamTriNode::~LLRoamTriNode()
00185 {
00186         delete mLchild;
00187         mLchild = 0;
00188         delete mRchild;
00189         mRchild = 0;
00190         //delete sQueues;
00191         //sQueues = 0;
00192 }
00193 
00194 
00195 
00196 const LLRoamTriNode* LLRoamTriNode::getFirstLeaf() const
00197 {
00198         const LLRoamTriNode* node = this;
00199         while (!node->leaf())
00200                 node = node->Lchild();
00201         return node;
00202 }
00203 const LLRoamTriNode* LLRoamTriNode::getNextLeaf() const
00204 {
00205         const LLRoamTriNode* child = this;
00206         const LLRoamTriNode* prev = parent();
00207         while (prev) {
00208                 if (prev->Lchild() == child)
00209                         return prev->Rchild()->getFirstLeaf();
00210                 child = prev;
00211                 prev = prev->parent();
00212         };
00213         return NULL;
00214 }
00215 
00216 void LLRoam::queueForSplit(LLRoamTriNode* t, BOOL process_base)
00217 {
00218         //if (splitQueueTooLong())
00219         //      processSplit();
00220         //if (t->base() && process_base)
00221         //      queueForSplit(t->base(), FALSE)
00222         pushSplit(t);
00223 }
00224 
00225 void LLRoam::queueForMerge(LLRoamTriNode* t, BOOL process_base)
00226 {
00227         //if (mergeQueueTooLong())
00228         //      processMerge();
00229         if (t->leaf())
00230                 return;
00231         queueForMerge(t->Lchild());
00232         queueForMerge(t->Rchild());
00233         if (t->base() && process_base)
00234                 queueForMerge(t->base(), FALSE);
00235         pushMerge(t);
00236 }
00237 
00238 
00239 void LLRoam::processSplit()
00240 {
00241         while(!mSplitQ.isEmpty())
00242         {
00243                 LLRoamTriNode* tri = popSplit();
00244                 if (tri->split())
00245                 {
00246                         tri->Lchild()->update();
00247                         tri->Rchild()->update();
00248                 }
00249                 //checkTiming();
00250         }
00251 }
00252 
00253 void LLRoam::processMerge()
00254 {
00255         while(!mMergeQ.isEmpty())
00256         {
00257                 LLRoamTriNode* tri = popMerge();
00258                 if (tri->refine())
00259                         continue;
00260                 if (tri->leaf())
00261                         continue;
00262                 if (!tri->Lchild()->leaf() || !tri->Rchild()->leaf())
00263                         continue;
00264                 if (LLRoamTriNode* b = tri->base())
00265                 {
00266                         if (b->leaf() || (b->Lchild()->leaf() && b->Rchild()->leaf()))
00267                         {
00268                                 tri->mergeSimple();
00269                         }
00270                 }
00271                 //checkTiming();
00272         }
00273 }
00274 
00275 void LLRoam::process()
00276 {
00277         while(!mSplitQ.isEmpty() || !mMergeQ.isEmpty())
00278         {
00279                 processMerge();
00280                 processSplit();
00281         }
00282 }
00283 
00284 
00285 void LLRoam::flushSplit()
00286 {
00287         while(!mSplitQ.isEmpty())
00288         {
00289                 LLRoamTriNode* tri = popSplit();
00290                 tri->flushFromQueue();
00291         }
00292 }
00293 
00294 void LLRoam::flushMerge()
00295 {
00296         while(!mMergeQ.isEmpty())
00297         {
00298                 LLRoamTriNode* tri = popMerge();
00299                 if (tri->leaf())
00300                         continue;
00301                 if (tri->base()->leaf())
00302                 {
00303                         tri->mergeSimple();
00304                 }
00305                 tri->flushFromQueue();
00306         }
00307 }

Generated on Thu Jul 1 06:09:05 2010 for Second Life Viewer by  doxygen 1.4.7