diff options
Diffstat (limited to 'linden/indra/newview/llspatialpartition.cpp')
-rw-r--r-- | linden/indra/newview/llspatialpartition.cpp | 390 |
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 | ||
52 | const F32 SG_OCCLUSION_FUDGE = 0.25f; | 53 | const 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 | ||
282 | LLSpatialGroup::~LLSpatialGroup() | 283 | LLSpatialGroup::~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 | |||
309 | BOOL 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 | |||
322 | void 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 | |||
341 | void 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 | |||
360 | void 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 | |||
376 | LLTextureAtlas* 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 | |||
402 | void LLSpatialGroup::setCurUpdatingSlot(LLTextureAtlasSlot* slotp) | ||
403 | { | ||
404 | mCurUpdatingSlotp = slotp; | ||
405 | |||
406 | //if(!hasAtlas(mCurUpdatingSlotp->getAtlas())) | ||
407 | //{ | ||
408 | // addAtlas(mCurUpdatingSlotp->getAtlas()) ; | ||
409 | //} | ||
410 | } | ||
411 | |||
412 | LLTextureAtlasSlot* 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 | ||
307 | void LLSpatialGroup::clearDrawMap() | 431 | void 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 | ||
573 | void LLSpatialPartition::rebuildGeom(LLSpatialGroup* group) | 698 | void 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 | |||
628 | void LLSpatialPartition::rebuildMesh(LLSpatialGroup* group) | 755 | void 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 | ||
1196 | F32 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 | |||
1053 | BOOL LLSpatialGroup::needsUpdate() | 1208 | BOOL 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 | |||
1157 | void LLSpatialGroup::destroyGL() | 1312 | void 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 | ||
1342 | LLSpatialPartition::LLSpatialPartition(U32 data_mask, U32 buffer_usage) | 1499 | LLSpatialPartition::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 | ||
2655 | void 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 | |||
2434 | void renderLights(LLDrawable* drawablep) | 2688 | void 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 | ||
2708 | void LLSpatialPartition::renderDebug() | 2995 | void 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 | ||
3042 | void 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 | ||
2756 | BOOL LLSpatialPartition::isVisible(const LLVector3& v) | 3049 | BOOL LLSpatialPartition::isVisible(const LLVector3& v) |
2757 | { | 3050 | { |
@@ -2896,11 +3189,12 @@ LLDrawable* LLSpatialPartition::lineSegmentIntersect(const LLVector3& start, con | |||
2896 | } | 3189 | } |
2897 | 3190 | ||
2898 | LLDrawInfo::LLDrawInfo(U16 start, U16 end, U32 count, U32 offset, | 3191 | LLDrawInfo::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 | ||
2933 | LLDrawInfo::~LLDrawInfo() | 3227 | LLDrawInfo::~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 | } |