aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/linden/indra/newview/llspatialpartition.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'linden/indra/newview/llspatialpartition.cpp')
-rw-r--r--linden/indra/newview/llspatialpartition.cpp390
1 files changed, 342 insertions, 48 deletions
diff --git a/linden/indra/newview/llspatialpartition.cpp b/linden/indra/newview/llspatialpartition.cpp
index 31b537c..114d3b5 100644
--- a/linden/indra/newview/llspatialpartition.cpp
+++ b/linden/indra/newview/llspatialpartition.cpp
@@ -48,6 +48,7 @@
48#include "llrender.h" 48#include "llrender.h"
49#include "lloctree.h" 49#include "lloctree.h"
50#include "llvoavatar.h" 50#include "llvoavatar.h"
51#include "lltextureatlas.h"
51 52
52const F32 SG_OCCLUSION_FUDGE = 0.25f; 53const F32 SG_OCCLUSION_FUDGE = 0.25f;
53#define SG_DISCARD_TOLERANCE 0.01f 54#define SG_DISCARD_TOLERANCE 0.01f
@@ -95,7 +96,7 @@ void sg_assert(BOOL expr)
95#if LL_OCTREE_PARANOIA_CHECK 96#if LL_OCTREE_PARANOIA_CHECK
96 if (!expr) 97 if (!expr)
97 { 98 {
98 llerrs << "Octree invalid!" << llendl; 99 llwarns << "Octree invalid!" << llendl;
99 } 100 }
100#endif 101#endif
101} 102}
@@ -281,10 +282,10 @@ S32 LLSphereAABB(const LLVector3& center, const LLVector3& size, const LLVector3
281 282
282LLSpatialGroup::~LLSpatialGroup() 283LLSpatialGroup::~LLSpatialGroup()
283{ 284{
284 if (sNoDelete) 285 /*if (sNoDelete)
285 { 286 {
286 llerrs << "Illegal deletion of LLSpatialGroup!" << llendl; 287 llwarns << "Illegal deletion of LLSpatialGroup!" << llendl;
287 } 288 }*/
288 289
289 if (isState(DEAD)) 290 if (isState(DEAD))
290 { 291 {
@@ -302,6 +303,129 @@ LLSpatialGroup::~LLSpatialGroup()
302 303
303 LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION); 304 LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
304 clearDrawMap(); 305 clearDrawMap();
306 clearAtlasList() ;
307}
308
309BOOL LLSpatialGroup::hasAtlas(LLTextureAtlas* atlasp)
310{
311 S8 type = atlasp->getComponents() - 1 ;
312 for(std::list<LLTextureAtlas*>::iterator iter = mAtlasList[type].begin(); iter != mAtlasList[type].end() ; ++iter)
313 {
314 if(atlasp == *iter)
315 {
316 return TRUE ;
317 }
318 }
319 return FALSE ;
320}
321
322void LLSpatialGroup::addAtlas(LLTextureAtlas* atlasp, S8 recursive_level)
323{
324 if(!hasAtlas(atlasp))
325 {
326 mAtlasList[atlasp->getComponents() - 1].push_back(atlasp) ;
327 atlasp->addSpatialGroup(this) ;
328 }
329
330 --recursive_level;
331 if(recursive_level)//levels propagating up.
332 {
333 LLSpatialGroup* parent = getParent() ;
334 if(parent)
335 {
336 parent->addAtlas(atlasp, recursive_level) ;
337 }
338 }
339}
340
341void LLSpatialGroup::removeAtlas(LLTextureAtlas* atlasp, BOOL remove_group, S8 recursive_level)
342{
343 mAtlasList[atlasp->getComponents() - 1].remove(atlasp) ;
344 if(remove_group)
345 {
346 atlasp->removeSpatialGroup(this) ;
347 }
348
349 --recursive_level;
350 if(recursive_level)//levels propagating up.
351 {
352 LLSpatialGroup* parent = getParent() ;
353 if(parent)
354 {
355 parent->removeAtlas(atlasp, recursive_level) ;
356 }
357 }
358}
359
360void LLSpatialGroup::clearAtlasList()
361{
362 std::list<LLTextureAtlas*>::iterator iter ;
363 for(S8 i = 0 ; i < 4 ; i++)
364 {
365 if(mAtlasList[i].size() > 0)
366 {
367 for(iter = mAtlasList[i].begin(); iter != mAtlasList[i].end() ; ++iter)
368 {
369 ((LLTextureAtlas*)*iter)->removeSpatialGroup(this) ;
370 }
371 mAtlasList[i].clear() ;
372 }
373 }
374}
375
376LLTextureAtlas* LLSpatialGroup::getAtlas(S8 ncomponents, S8 to_be_reserved, S8 recursive_level)
377{
378 S8 type = ncomponents - 1 ;
379 if(mAtlasList[type].size() > 0)
380 {
381 for(std::list<LLTextureAtlas*>::iterator iter = mAtlasList[type].begin(); iter != mAtlasList[type].end() ; ++iter)
382 {
383 if(!((LLTextureAtlas*)*iter)->isFull(to_be_reserved))
384 {
385 return *iter ;
386 }
387 }
388 }
389
390 --recursive_level;
391 if(recursive_level)
392 {
393 LLSpatialGroup* parent = getParent() ;
394 if(parent)
395 {
396 return parent->getAtlas(ncomponents, to_be_reserved, recursive_level) ;
397 }
398 }
399 return NULL ;
400}
401
402void LLSpatialGroup::setCurUpdatingSlot(LLTextureAtlasSlot* slotp)
403{
404 mCurUpdatingSlotp = slotp;
405
406 //if(!hasAtlas(mCurUpdatingSlotp->getAtlas()))
407 //{
408 // addAtlas(mCurUpdatingSlotp->getAtlas()) ;
409 //}
410}
411
412LLTextureAtlasSlot* LLSpatialGroup::getCurUpdatingSlot(LLViewerImage* imagep, S8 recursive_level)
413{
414 if(gFrameCount && mCurUpdatingTime == gFrameCount && mCurUpdatingTexture == imagep)
415 {
416 return mCurUpdatingSlotp ;
417 }
418
419 //--recursive_level ;
420 //if(recursive_level)
421 //{
422 // LLSpatialGroup* parent = getParent() ;
423 // if(parent)
424 // {
425 // return parent->getCurUpdatingSlot(imagep, recursive_level) ;
426 // }
427 //}
428 return NULL ;
305} 429}
306 430
307void LLSpatialGroup::clearDrawMap() 431void LLSpatialGroup::clearDrawMap()
@@ -348,7 +472,7 @@ void LLSpatialGroup::validate()
348 LLSpatialPartition* part = drawable->asPartition(); 472 LLSpatialPartition* part = drawable->asPartition();
349 if (!part) 473 if (!part)
350 { 474 {
351 llerrs << "Drawable reports it is a spatial bridge but not a partition." << llendl; 475 llwarns << "Drawable reports it is a spatial bridge but not a partition." << llendl;
352 } 476 }
353 LLSpatialGroup* group = (LLSpatialGroup*) part->mOctree->getListener(0); 477 LLSpatialGroup* group = (LLSpatialGroup*) part->mOctree->getListener(0);
354 group->validate(); 478 group->validate();
@@ -411,7 +535,7 @@ public:
411 535
412 if (mInheritedMask && !group->isState(mInheritedMask)) 536 if (mInheritedMask && !group->isState(mInheritedMask))
413 { 537 {
414 llerrs << "Spatial group failed inherited mask test." << llendl; 538 llwarns << "Spatial group failed inherited mask test." << llendl;
415 } 539 }
416 540
417 if (group->isState(LLSpatialGroup::DIRTY)) 541 if (group->isState(LLSpatialGroup::DIRTY))
@@ -427,7 +551,7 @@ public:
427 { 551 {
428 if (!parent->isState(state)) 552 if (!parent->isState(state))
429 { 553 {
430 llerrs << "Spatial group failed parent state check." << llendl; 554 llwarns << "Spatial group failed parent state check." << llendl;
431 } 555 }
432 parent = parent->getParent(); 556 parent = parent->getParent();
433 } 557 }
@@ -448,39 +572,39 @@ void validate_draw_info(LLDrawInfo& params)
448#if LL_OCTREE_PARANOIA_CHECK 572#if LL_OCTREE_PARANOIA_CHECK
449 if (params.mVertexBuffer.isNull()) 573 if (params.mVertexBuffer.isNull())
450 { 574 {
451 llerrs << "Draw batch has no vertex buffer." << llendl; 575 llwarns << "Draw batch has no vertex buffer." << llendl;
452 } 576 }
453 577
454 //bad range 578 //bad range
455 if (params.mStart >= params.mEnd) 579 if (params.mStart >= params.mEnd)
456 { 580 {
457 llerrs << "Draw batch has invalid range." << llendl; 581 llwarns << "Draw batch has invalid range." << llendl;
458 } 582 }
459 583
460 if (params.mEnd >= (U32) params.mVertexBuffer->getNumVerts()) 584 if (params.mEnd >= (U32) params.mVertexBuffer->getNumVerts())
461 { 585 {
462 llerrs << "Draw batch has buffer overrun error." << llendl; 586 llwarns << "Draw batch has buffer overrun error." << llendl;
463 } 587 }
464 588
465 if (params.mOffset + params.mCount > (U32) params.mVertexBuffer->getNumIndices()) 589 if (params.mOffset + params.mCount > (U32) params.mVertexBuffer->getNumIndices())
466 { 590 {
467 llerrs << "Draw batch has index buffer ovverrun error." << llendl; 591 llwarns << "Draw batch has index buffer ovverrun error." << llendl;
468 } 592 }
469 593
470 //bad indices 594 //bad indices
471 U32* indicesp = (U32*) params.mVertexBuffer->getIndicesPointer(); 595 U16* indicesp = (U16*) params.mVertexBuffer->getIndicesPointer(); // KL 16 indices for SD not 32
472 if (indicesp) 596 if (indicesp)
473 { 597 {
474 for (U32 i = params.mOffset; i < params.mOffset+params.mCount; i++) 598 for (U32 i = params.mOffset; i < params.mOffset+params.mCount; i++)
475 { 599 {
476 if (indicesp[i] < params.mStart) 600 if (indicesp[i] < (U16)params.mStart) //KL
477 { 601 {
478 llerrs << "Draw batch has vertex buffer index out of range error (index too low)." << llendl; 602 llwarns << "Draw batch has vertex buffer index out of range error (index too low)." << llendl;
479 } 603 }
480 604
481 if (indicesp[i] > params.mEnd) 605 if (indicesp[i] > (U16)params.mEnd) // KL
482 { 606 {
483 llerrs << "Draw batch has vertex buffer index out of range error (index too high)." << llendl; 607 llwarns << "Draw batch has vertex buffer index out of range error (index too high)." << llendl;
484 } 608 }
485 } 609 }
486 } 610 }
@@ -540,6 +664,7 @@ BOOL LLSpatialGroup::addObject(LLDrawable *drawablep, BOOL add_all, BOOL from_oc
540 drawablep->setSpatialGroup(this); 664 drawablep->setSpatialGroup(this);
541 validate_drawable(drawablep); 665 validate_drawable(drawablep);
542 setState(OBJECT_DIRTY | GEOM_DIRTY | DISCARD_QUERY); 666 setState(OBJECT_DIRTY | GEOM_DIRTY | DISCARD_QUERY);
667 gPipeline.markRebuild(this, TRUE);
543 if (drawablep->isSpatialBridge()) 668 if (drawablep->isSpatialBridge())
544 { 669 {
545 mBridgeList.push_back((LLSpatialBridge*) drawablep); 670 mBridgeList.push_back((LLSpatialBridge*) drawablep);
@@ -572,22 +697,23 @@ void LLSpatialGroup::rebuildMesh()
572 697
573void LLSpatialPartition::rebuildGeom(LLSpatialGroup* group) 698void LLSpatialPartition::rebuildGeom(LLSpatialGroup* group)
574{ 699{
575 if (!gPipeline.hasRenderType(mDrawableType)) 700 /*if (!gPipeline.hasRenderType(mDrawableType))
576 { 701 {
577 return; 702 return;
578 } 703 }*/
579
580 if (!LLPipeline::sSkipUpdate && group->changeLOD())
581 {
582 group->mLastUpdateDistance = group->mDistance;
583 group->mLastUpdateViewAngle = group->mViewAngle;
584 }
585 704
586 if (group->isDead() || !group->isState(LLSpatialGroup::GEOM_DIRTY)) 705 if (group->isDead() || !group->isState(LLSpatialGroup::GEOM_DIRTY))
587 { 706 {
707 /*if (!group->isState(LLSpatialGroup::GEOM_DIRTY) && mRenderByGroup)
708 {
709 llwarns << "WTF?" << llendl;
710 }*/
588 return; 711 return;
589 } 712 }
590 713
714 group->mLastUpdateDistance = group->mDistance;
715 group->mLastUpdateViewAngle = group->mViewAngle;
716
591 LLFastTimer ftm(LLFastTimer::FTM_REBUILD_VBO); 717 LLFastTimer ftm(LLFastTimer::FTM_REBUILD_VBO);
592 718
593 group->clearDrawMap(); 719 group->clearDrawMap();
@@ -625,6 +751,7 @@ void LLSpatialPartition::rebuildGeom(LLSpatialGroup* group)
625 group->clearState(LLSpatialGroup::GEOM_DIRTY); 751 group->clearState(LLSpatialGroup::GEOM_DIRTY);
626} 752}
627 753
754
628void LLSpatialPartition::rebuildMesh(LLSpatialGroup* group) 755void LLSpatialPartition::rebuildMesh(LLSpatialGroup* group)
629{ 756{
630 757
@@ -663,8 +790,11 @@ BOOL LLSpatialGroup::boundObjects(BOOL empty, LLVector3& minOut, LLVector3& maxO
663 drawablep = *i; 790 drawablep = *i;
664 minMax = drawablep->getSpatialExtents(); 791 minMax = drawablep->getSpatialExtents();
665 792
793 update_min_max(newMin, newMax, minMax[0]);
794 update_min_max(newMin, newMax, minMax[1]);
795
666 //bin up the object 796 //bin up the object
667 for (U32 i = 0; i < 3; i++) 797 /*for (U32 i = 0; i < 3; i++)
668 { 798 {
669 if (minMax[0].mV[i] < newMin.mV[i]) 799 if (minMax[0].mV[i] < newMin.mV[i])
670 { 800 {
@@ -674,7 +804,7 @@ BOOL LLSpatialGroup::boundObjects(BOOL empty, LLVector3& minOut, LLVector3& maxO
674 { 804 {
675 newMax.mV[i] = minMax[1].mV[i]; 805 newMax.mV[i] = minMax[1].mV[i];
676 } 806 }
677 } 807 }*/
678 } 808 }
679 809
680 mObjectBounds[0] = (newMin + newMax) * 0.5f; 810 mObjectBounds[0] = (newMin + newMax) * 0.5f;
@@ -738,6 +868,10 @@ LLSpatialGroup* LLSpatialGroup::getParent()
738 return NULL; 868 return NULL;
739 } 869 }
740 870
871 if(!mOctreeNode)
872 {
873 return NULL;
874 }
741 OctreeNode* parent = mOctreeNode->getOctParent(); 875 OctreeNode* parent = mOctreeNode->getOctParent();
742 876
743 if (parent) 877 if (parent)
@@ -763,6 +897,8 @@ BOOL LLSpatialGroup::removeObject(LLDrawable *drawablep, BOOL from_octree)
763 { 897 {
764 drawablep->setSpatialGroup(NULL); 898 drawablep->setSpatialGroup(NULL);
765 setState(GEOM_DIRTY); 899 setState(GEOM_DIRTY);
900 gPipeline.markRebuild(this, TRUE);
901
766 if (drawablep->isSpatialBridge()) 902 if (drawablep->isSpatialBridge())
767 { 903 {
768 for (bridge_list_t::iterator i = mBridgeList.begin(); i != mBridgeList.end(); ++i) 904 for (bridge_list_t::iterator i = mBridgeList.begin(); i != mBridgeList.end(); ++i)
@@ -799,6 +935,7 @@ void LLSpatialGroup::shift(const LLVector3 &offset)
799 //if (!mSpatialPartition->mRenderByGroup) 935 //if (!mSpatialPartition->mRenderByGroup)
800 { 936 {
801 setState(GEOM_DIRTY); 937 setState(GEOM_DIRTY);
938 gPipeline.markRebuild(this, TRUE);
802 } 939 }
803 940
804 if (mOcclusionVerts) 941 if (mOcclusionVerts)
@@ -948,7 +1085,11 @@ LLSpatialGroup::LLSpatialGroup(OctreeNode* node, LLSpatialPartition* part) :
948 mLastUpdateDistance(-1.f), 1085 mLastUpdateDistance(-1.f),
949 mLastUpdateTime(gFrameTimeSeconds), 1086 mLastUpdateTime(gFrameTimeSeconds),
950 mViewAngle(0.f), 1087 mViewAngle(0.f),
951 mLastUpdateViewAngle(-1.f) 1088 mLastUpdateViewAngle(-1.f),
1089 mAtlasList(4),
1090 mCurUpdatingTime(0),
1091 mCurUpdatingSlotp(NULL),
1092 mCurUpdatingTexture (NULL)
952{ 1093{
953 sNodeCount++; 1094 sNodeCount++;
954 LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION); 1095 LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
@@ -956,6 +1097,7 @@ LLSpatialGroup::LLSpatialGroup(OctreeNode* node, LLSpatialPartition* part) :
956 sg_assert(mOctreeNode->getListenerCount() == 0); 1097 sg_assert(mOctreeNode->getListenerCount() == 0);
957 mOctreeNode->addListener(this); 1098 mOctreeNode->addListener(this);
958 setState(SG_INITIAL_STATE_MASK); 1099 setState(SG_INITIAL_STATE_MASK);
1100 gPipeline.markRebuild(this, TRUE);
959 1101
960 mBounds[0] = LLVector3(node->getCenter()); 1102 mBounds[0] = LLVector3(node->getCenter());
961 mBounds[1] = LLVector3(node->getSize()); 1103 mBounds[1] = LLVector3(node->getSize());
@@ -975,7 +1117,7 @@ void LLSpatialGroup::updateDistance(LLCamera &camera)
975#if !LL_RELEASE_FOR_DOWNLOAD 1117#if !LL_RELEASE_FOR_DOWNLOAD
976 if (isState(LLSpatialGroup::OBJECT_DIRTY)) 1118 if (isState(LLSpatialGroup::OBJECT_DIRTY))
977 { 1119 {
978 llerrs << "Spatial group dirty on distance update." << llendl; 1120 llwarns << "Spatial group dirty on distance update." << llendl;
979 } 1121 }
980#endif 1122#endif
981 if (!getData().empty() && !LLSpatialPartition::sFreezeState) 1123 if (!getData().empty() && !LLSpatialPartition::sFreezeState)
@@ -1014,6 +1156,7 @@ F32 LLSpatialPartition::calcDistance(LLSpatialGroup* group, LLCamera& camera)
1014 //NOTE: If there is a trivial way to detect that alpha sorting here would not change the render order, 1156 //NOTE: If there is a trivial way to detect that alpha sorting here would not change the render order,
1015 //not setting this node to dirty would be a very good thing 1157 //not setting this node to dirty would be a very good thing
1016 group->setState(LLSpatialGroup::ALPHA_DIRTY); 1158 group->setState(LLSpatialGroup::ALPHA_DIRTY);
1159 gPipeline.markRebuild(group, FALSE);
1017 } 1160 }
1018 } 1161 }
1019 } 1162 }
@@ -1050,6 +1193,18 @@ F32 LLSpatialPartition::calcPixelArea(LLSpatialGroup* group, LLCamera& camera)
1050 return LLPipeline::calcPixelArea(group->mObjectBounds[0], group->mObjectBounds[1], camera); 1193 return LLPipeline::calcPixelArea(group->mObjectBounds[0], group->mObjectBounds[1], camera);
1051} 1194}
1052 1195
1196F32 LLSpatialGroup::getUpdateUrgency() const
1197{
1198 if (!isVisible())
1199 {
1200 return 0.f;
1201 }
1202 else
1203 {
1204 return (gFrameTimeSeconds - mLastUpdateTime+4.f)/mDistance;
1205 }
1206}
1207
1053BOOL LLSpatialGroup::needsUpdate() 1208BOOL LLSpatialGroup::needsUpdate()
1054{ 1209{
1055 return (LLDrawable::getCurrentFrame()%mSpatialPartition->mLODPeriod == mLODHash) ? TRUE : FALSE; 1210 return (LLDrawable::getCurrentFrame()%mSpatialPartition->mLODPeriod == mLODHash) ? TRUE : FALSE;
@@ -1157,6 +1312,8 @@ void LLSpatialGroup::handleChildRemoval(const OctreeNode* parent, const OctreeNo
1157void LLSpatialGroup::destroyGL() 1312void LLSpatialGroup::destroyGL()
1158{ 1313{
1159 setState(LLSpatialGroup::GEOM_DIRTY | LLSpatialGroup::IMAGE_DIRTY); 1314 setState(LLSpatialGroup::GEOM_DIRTY | LLSpatialGroup::IMAGE_DIRTY);
1315 gPipeline.markRebuild(this, TRUE);
1316
1160 mLastUpdateTime = gFrameTimeSeconds; 1317 mLastUpdateTime = gFrameTimeSeconds;
1161 mVertexBuffer = NULL; 1318 mVertexBuffer = NULL;
1162 mBufferMap.clear(); 1319 mBufferMap.clear();
@@ -1339,7 +1496,8 @@ void LLSpatialGroup::doOcclusion(LLCamera* camera)
1339 1496
1340//============================================== 1497//==============================================
1341 1498
1342LLSpatialPartition::LLSpatialPartition(U32 data_mask, U32 buffer_usage) 1499LLSpatialPartition::LLSpatialPartition(U32 data_mask, BOOL render_by_group, U32 buffer_usage)
1500: mRenderByGroup(render_by_group)
1343{ 1501{
1344 LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION); 1502 LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
1345 mOcclusionEnabled = TRUE; 1503 mOcclusionEnabled = TRUE;
@@ -1351,7 +1509,7 @@ LLSpatialPartition::LLSpatialPartition(U32 data_mask, U32 buffer_usage)
1351 mBufferUsage = buffer_usage; 1509 mBufferUsage = buffer_usage;
1352 mDepthMask = FALSE; 1510 mDepthMask = FALSE;
1353 mSlopRatio = 0.25f; 1511 mSlopRatio = 0.25f;
1354 mRenderByGroup = TRUE; 1512 //mRenderByGroup = TRUE;
1355 mInfiniteFarClip = FALSE; 1513 mInfiniteFarClip = FALSE;
1356 1514
1357 LLGLNamePool::registerPool(&sQueryPool); 1515 LLGLNamePool::registerPool(&sQueryPool);
@@ -1647,13 +1805,76 @@ public:
1647 return false; 1805 return false;
1648 } 1806 }
1649 1807
1808 virtual void traverse(const LLSpatialGroup::TreeNode* n)
1809 {
1810 LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
1811
1812 if (earlyFail(group))
1813 {
1814 return;
1815 }
1816
1817 if (mRes == 2)
1818 {
1819 //fully in, don't traverse further (won't effect extents
1820 }
1821 else if (mRes && group->isState(LLSpatialGroup::SKIP_FRUSTUM_CHECK))
1822 { //don't need to do frustum check
1823 LLSpatialGroup::OctreeTraveler::traverse(n);
1824 }
1825 else
1826 {
1827 mRes = frustumCheck(group);
1828
1829 if (mRes)
1830 { //at least partially in, run on down
1831 LLSpatialGroup::OctreeTraveler::traverse(n);
1832 }
1833
1834 mRes = 0;
1835 }
1836 }
1837
1650 virtual void processGroup(LLSpatialGroup* group) 1838 virtual void processGroup(LLSpatialGroup* group)
1651 { 1839 {
1652 if (group->mObjectBounds[1].magVecSquared() < 256.f * 256.f) 1840 if (group->isState(LLSpatialGroup::DIRTY) || group->getData().empty())
1653 { //megaprims and water edge patches be damned! 1841 {
1842 llwarns << "WTF?" << llendl;
1843 }
1844
1845 if (mRes < 2)
1846 {
1847
1848 if (mCamera->AABBInFrustum(group->mObjectBounds[0], group->mObjectBounds[1]) == 2)
1849 {
1850 mEmpty = FALSE;
1851 update_min_max(mMin, mMax, group->mObjectExtents[0]);
1852 update_min_max(mMin, mMax, group->mObjectExtents[1]);
1853 }
1854 else
1855 {
1856 if (group->mObjectBounds[1].magVecSquared() < 256.f * 256.f)
1857 { //megaprims and water edge patches be damned!
1858 for (LLSpatialGroup::element_iter i = group->getData().begin(); i != group->getData().end(); ++i)
1859 {
1860 LLDrawable* drawable = i->get();
1861 const LLVector3* ext = drawable->getSpatialExtents();
1862
1863 if (mCamera->AABBInFrustum((ext[1]+ext[0])*0.5f, (ext[1]-ext[0])*0.5f))
1864 {
1865 mEmpty = FALSE;
1866 update_min_max(mMin, mMax, ext[0]);
1867 update_min_max(mMin, mMax, ext[1]);
1868 }
1869 }
1870 }
1871 }
1872 }
1873 else
1874 {
1654 mEmpty = FALSE; 1875 mEmpty = FALSE;
1655 update_min_max(mMin, mMax, group->mObjectExtents[0]); 1876 update_min_max(mMin, mMax, group->mExtents[0]);
1656 update_min_max(mMin, mMax, group->mObjectExtents[1]); 1877 update_min_max(mMin, mMax, group->mExtents[1]);
1657 } 1878 }
1658 } 1879 }
1659 1880
@@ -2431,6 +2652,39 @@ void renderBatchSize(LLDrawInfo* params)
2431 pushVerts(params, LLVertexBuffer::MAP_VERTEX); 2652 pushVerts(params, LLVertexBuffer::MAP_VERTEX);
2432} 2653}
2433 2654
2655void renderShadowFrusta(LLDrawInfo* params)
2656{
2657 LLGLEnable blend(GL_BLEND);
2658 gGL.setSceneBlendType(LLRender::BT_ADD);
2659
2660 LLVector3 center = (params->mExtents[1]+params->mExtents[0])*0.5f;
2661 LLVector3 size = (params->mExtents[1]-params->mExtents[0])*0.5f;
2662
2663 if (gPipeline.mShadowCamera[4].AABBInFrustum(center, size))
2664 {
2665 glColor3f(1,0,0);
2666 pushVerts(params, LLVertexBuffer::MAP_VERTEX);
2667 }
2668 if (gPipeline.mShadowCamera[5].AABBInFrustum(center, size))
2669 {
2670 glColor3f(0,1,0);
2671 pushVerts(params, LLVertexBuffer::MAP_VERTEX);
2672 }
2673 if (gPipeline.mShadowCamera[6].AABBInFrustum(center, size))
2674 {
2675 glColor3f(0,0,1);
2676 pushVerts(params, LLVertexBuffer::MAP_VERTEX);
2677 }
2678 if (gPipeline.mShadowCamera[7].AABBInFrustum(center, size))
2679 {
2680 glColor3f(1,0,1);
2681 pushVerts(params, LLVertexBuffer::MAP_VERTEX);
2682 }
2683
2684 gGL.setSceneBlendType(LLRender::BT_ALPHA);
2685}
2686
2687
2434void renderLights(LLDrawable* drawablep) 2688void renderLights(LLDrawable* drawablep)
2435{ 2689{
2436 if (!drawablep->isLight()) 2690 if (!drawablep->isLight())
@@ -2566,6 +2820,9 @@ public:
2566 //draw tight fit bounding boxes for spatial group 2820 //draw tight fit bounding boxes for spatial group
2567 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCTREE)) 2821 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCTREE))
2568 { 2822 {
2823 group->rebuildGeom();
2824 group->rebuildMesh();
2825
2569 renderOctree(group); 2826 renderOctree(group);
2570 stop_glerror(); 2827 stop_glerror();
2571 } 2828 }
@@ -2573,6 +2830,9 @@ public:
2573 //render visibility wireframe 2830 //render visibility wireframe
2574 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCCLUSION)) 2831 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCCLUSION))
2575 { 2832 {
2833 group->rebuildGeom();
2834 group->rebuildMesh();
2835
2576 gGL.flush(); 2836 gGL.flush();
2577 glPushMatrix(); 2837 glPushMatrix();
2578 gGLLastMatrix = NULL; 2838 gGLLastMatrix = NULL;
@@ -2598,6 +2858,19 @@ public:
2598 LLVector3 nodeCenter = group->mBounds[0]; 2858 LLVector3 nodeCenter = group->mBounds[0];
2599 LLVector3 octCenter = LLVector3(group->mOctreeNode->getCenter()); 2859 LLVector3 octCenter = LLVector3(group->mOctreeNode->getCenter());
2600 2860
2861 group->rebuildGeom();
2862 group->rebuildMesh();
2863
2864 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_BBOXES))
2865 {
2866 if (!group->getData().empty())
2867 {
2868 gGL.color3f(0,0,1);
2869 drawBoxOutline(group->mObjectBounds[0],
2870 group->mObjectBounds[1]);
2871 }
2872 }
2873
2601 for (LLSpatialGroup::OctreeNode::const_element_iter i = branch->getData().begin(); i != branch->getData().end(); ++i) 2874 for (LLSpatialGroup::OctreeNode::const_element_iter i = branch->getData().begin(); i != branch->getData().end(); ++i)
2602 { 2875 {
2603 LLDrawable* drawable = *i; 2876 LLDrawable* drawable = *i;
@@ -2607,6 +2880,16 @@ public:
2607 renderBoundingBox(drawable); 2880 renderBoundingBox(drawable);
2608 } 2881 }
2609 2882
2883 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_BUILD_QUEUE))
2884 {
2885 if (drawable->isState(LLDrawable::IN_REBUILD_Q2))
2886 {
2887 gGL.color4f(0.6f, 0.6f, 0.1f, 1.f);
2888 const LLVector3* ext = drawable->getSpatialExtents();
2889 drawBoxOutline((ext[0]+ext[1])*0.5f, (ext[1]-ext[0])*0.5f);
2890 }
2891 }
2892
2610 if (drawable->getVOVolume() && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY)) 2893 if (drawable->getVOVolume() && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY))
2611 { 2894 {
2612 renderTexturePriority(drawable); 2895 renderTexturePriority(drawable);
@@ -2627,9 +2910,9 @@ public:
2627 renderRaycast(drawable); 2910 renderRaycast(drawable);
2628 } 2911 }
2629 2912
2630 LLVOAvatar* avatar = dynamic_cast<LLVOAvatar*>(drawable->getVObj().get()); 2913 // LLVOAvatar* avatar = dynamic_cast<LLVOAvatar*>(drawable->getVObj().get());
2631 2914
2632 if (avatar && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_AVATAR_VOLUME)) 2915 /* if (avatar && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_AVATAR_VOLUME))
2633 { 2916 {
2634 renderAvatarCollisionVolumes(avatar); 2917 renderAvatarCollisionVolumes(avatar);
2635 } 2918 }
@@ -2637,7 +2920,7 @@ public:
2637 if (avatar && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_AGENT_TARGET)) 2920 if (avatar && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_AGENT_TARGET))
2638 { 2921 {
2639 renderAgentTarget(avatar); 2922 renderAgentTarget(avatar);
2640 } 2923 } */
2641 2924
2642 } 2925 }
2643 2926
@@ -2655,6 +2938,10 @@ public:
2655 { 2938 {
2656 renderBatchSize(draw_info); 2939 renderBatchSize(draw_info);
2657 } 2940 }
2941 if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_SHADOW_FRUSTA))
2942 {
2943 renderShadowFrusta(draw_info);
2944 }
2658 } 2945 }
2659 } 2946 }
2660 } 2947 }
@@ -2705,7 +2992,7 @@ void LLSpatialPartition::renderIntersectingBBoxes(LLCamera* camera)
2705 pusher.traverse(mOctree); 2992 pusher.traverse(mOctree);
2706} 2993}
2707 2994
2708void LLSpatialPartition::renderDebug() 2995void LLSpatialPartition::renderDebug() // KL SD version
2709{ 2996{
2710 if (!gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCTREE | 2997 if (!gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCTREE |
2711 LLPipeline::RENDER_DEBUG_OCCLUSION | 2998 LLPipeline::RENDER_DEBUG_OCCLUSION |
@@ -2716,8 +3003,8 @@ void LLSpatialPartition::renderDebug()
2716 LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY | 3003 LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY |
2717 LLPipeline::RENDER_DEBUG_TEXTURE_ANIM | 3004 LLPipeline::RENDER_DEBUG_TEXTURE_ANIM |
2718 LLPipeline::RENDER_DEBUG_RAYCAST | 3005 LLPipeline::RENDER_DEBUG_RAYCAST |
2719 LLPipeline::RENDER_DEBUG_AVATAR_VOLUME | 3006 LLPipeline::RENDER_DEBUG_BUILD_QUEUE |
2720 LLPipeline::RENDER_DEBUG_AGENT_TARGET)) 3007 LLPipeline::RENDER_DEBUG_SHADOW_FRUSTA))
2721 { 3008 {
2722 return; 3009 return;
2723 } 3010 }
@@ -2752,6 +3039,12 @@ void LLSpatialPartition::renderDebug()
2752 render_debug.traverse(mOctree); 3039 render_debug.traverse(mOctree);
2753} 3040}
2754 3041
3042void LLSpatialGroup::drawObjectBox(LLColor4 col)
3043{
3044 gGL.color4fv(col.mV);
3045 drawBox(mObjectBounds[0], mObjectBounds[1]*1.01f+LLVector3(0.001f, 0.001f, 0.001f));
3046}
3047
2755 3048
2756BOOL LLSpatialPartition::isVisible(const LLVector3& v) 3049BOOL LLSpatialPartition::isVisible(const LLVector3& v)
2757{ 3050{
@@ -2896,11 +3189,12 @@ LLDrawable* LLSpatialPartition::lineSegmentIntersect(const LLVector3& start, con
2896} 3189}
2897 3190
2898LLDrawInfo::LLDrawInfo(U16 start, U16 end, U32 count, U32 offset, 3191LLDrawInfo::LLDrawInfo(U16 start, U16 end, U32 count, U32 offset,
2899 LLViewerImage* texture, LLVertexBuffer* buffer, 3192 LLImageGL* gl_texture, LLViewerImage* texture, LLVertexBuffer* buffer,
2900 BOOL fullbright, U8 bump, BOOL particle, F32 part_size) 3193 BOOL fullbright, U8 bump, BOOL particle, F32 part_size)
2901: 3194:
2902 mVertexBuffer(buffer), 3195 mVertexBuffer(buffer),
2903 mTexture(texture), 3196 mTexture(gl_texture),
3197 mViewerTexture(texture),
2904 mTextureMatrix(NULL), 3198 mTextureMatrix(NULL),
2905 mModelMatrix(NULL), 3199 mModelMatrix(NULL),
2906 mStart(start), 3200 mStart(start),
@@ -2920,22 +3214,22 @@ LLDrawInfo::LLDrawInfo(U16 start, U16 end, U32 count, U32 offset,
2920 if (mStart >= mVertexBuffer->getRequestedVerts() || 3214 if (mStart >= mVertexBuffer->getRequestedVerts() ||
2921 mEnd >= mVertexBuffer->getRequestedVerts()) 3215 mEnd >= mVertexBuffer->getRequestedVerts())
2922 { 3216 {
2923 llerrs << "Invalid draw info vertex range." << llendl; 3217 llwarns << "Invalid draw info vertex range." << llendl;
2924 } 3218 }
2925 3219
2926 if (mOffset >= (U32) mVertexBuffer->getRequestedIndices() || 3220 if (mOffset >= (U32) mVertexBuffer->getRequestedIndices() ||
2927 mOffset + mCount > (U32) mVertexBuffer->getRequestedIndices()) 3221 mOffset + mCount > (U32) mVertexBuffer->getRequestedIndices())
2928 { 3222 {
2929 llerrs << "Invalid draw info index range." << llendl; 3223 llwarns << "Invalid draw info index range." << llendl;
2930 } 3224 }
2931} 3225}
2932 3226
2933LLDrawInfo::~LLDrawInfo() 3227LLDrawInfo::~LLDrawInfo()
2934{ 3228{
2935 if (LLSpatialGroup::sNoDelete) 3229 /*if (LLSpatialGroup::sNoDelete)
2936 { 3230 {
2937 llerrs << "LLDrawInfo deleted illegally!" << llendl; 3231 llwarns << "LLDrawInfo deleted illegally!" << llendl;
2938 } 3232 }*/
2939 3233
2940 if (mFace) 3234 if (mFace)
2941 { 3235 {
@@ -3140,7 +3434,7 @@ void LLCullResult::assertDrawMapsEmpty()
3140 { 3434 {
3141 if (mRenderMapSize[i] != 0) 3435 if (mRenderMapSize[i] != 0)
3142 { 3436 {
3143 llerrs << "Stale LLDrawInfo's in LLCullResult!" << llendl; 3437 llwarns << "Stale LLDrawInfo's in LLCullResult!" << llendl;
3144 } 3438 }
3145 } 3439 }
3146} 3440}