llspatialpartition.cpp
上传用户:king477883
上传日期:2021-03-01
资源大小:9553k
文件大小:84k
源码类别:

游戏引擎

开发平台:

C++ Builder

  1. /** 
  2.  * @file llspatialpartition.cpp
  3.  * @brief LLSpatialGroup class implementation and supporting functions
  4.  *
  5.  * $LicenseInfo:firstyear=2003&license=viewergpl$
  6.  * 
  7.  * Copyright (c) 2003-2010, Linden Research, Inc.
  8.  * 
  9.  * Second Life Viewer Source Code
  10.  * The source code in this file ("Source Code") is provided by Linden Lab
  11.  * to you under the terms of the GNU General Public License, version 2.0
  12.  * ("GPL"), unless you have obtained a separate licensing agreement
  13.  * ("Other License"), formally executed by you and Linden Lab.  Terms of
  14.  * the GPL can be found in doc/GPL-license.txt in this distribution, or
  15.  * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
  16.  * 
  17.  * There are special exceptions to the terms and conditions of the GPL as
  18.  * it is applied to this Source Code. View the full text of the exception
  19.  * in the file doc/FLOSS-exception.txt in this software distribution, or
  20.  * online at
  21.  * http://secondlifegrid.net/programs/open_source/licensing/flossexception
  22.  * 
  23.  * By copying, modifying or distributing this software, you acknowledge
  24.  * that you have read and understood your obligations described above,
  25.  * and agree to abide by those obligations.
  26.  * 
  27.  * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
  28.  * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
  29.  * COMPLETENESS OR PERFORMANCE.
  30.  * $/LicenseInfo$
  31.  */
  32. #include "llviewerprecompiledheaders.h"
  33. #include "llspatialpartition.h"
  34. #include "llviewerwindow.h"
  35. #include "llviewerobjectlist.h"
  36. #include "llvovolume.h"
  37. #include "llvolume.h"
  38. #include "llviewercamera.h"
  39. #include "llface.h"
  40. #include "llviewercontrol.h"
  41. #include "llviewerregion.h"
  42. #include "llcamera.h"
  43. #include "pipeline.h"
  44. #include "llrender.h"
  45. #include "lloctree.h"
  46. #include "llvoavatar.h"
  47. #include "lltextureatlas.h"
  48. static LLFastTimer::DeclareTimer FTM_FRUSTUM_CULL("Frustum Culling");
  49. static LLFastTimer::DeclareTimer FTM_CULL_REBOUND("Cull Rebound");
  50. const F32 SG_OCCLUSION_FUDGE = 0.25f;
  51. #define SG_DISCARD_TOLERANCE 0.01f
  52. #if LL_OCTREE_PARANOIA_CHECK
  53. #define assert_octree_valid(x) x->validate()
  54. #define assert_states_valid(x) ((LLSpatialGroup*) x->mSpatialPartition->mOctree->getListener(0))->checkStates()
  55. #else
  56. #define assert_octree_valid(x)
  57. #define assert_states_valid(x)
  58. #endif
  59. static U32 sZombieGroups = 0;
  60. U32 LLSpatialGroup::sNodeCount = 0;
  61. BOOL LLSpatialGroup::sNoDelete = FALSE;
  62. static F32 sLastMaxTexPriority = 1.f;
  63. static F32 sCurMaxTexPriority = 1.f;
  64. class LLOcclusionQueryPool : public LLGLNamePool
  65. {
  66. protected:
  67. virtual GLuint allocateName()
  68. {
  69. GLuint name;
  70. glGenQueriesARB(1, &name);
  71. return name;
  72. }
  73. virtual void releaseName(GLuint name)
  74. {
  75. glDeleteQueriesARB(1, &name);
  76. }
  77. };
  78. static LLOcclusionQueryPool sQueryPool;
  79. //static counter for frame to switch LOD on
  80. void sg_assert(BOOL expr)
  81. {
  82. #if LL_OCTREE_PARANOIA_CHECK
  83. if (!expr)
  84. {
  85. llerrs << "Octree invalid!" << llendl;
  86. }
  87. #endif
  88. }
  89. #if LL_DEBUG
  90. void validate_drawable(LLDrawable* drawablep)
  91. {
  92. F64 rad = drawablep->getBinRadius();
  93. const LLVector3* ext = drawablep->getSpatialExtents();
  94. if (rad < 0 || rad > 4096 ||
  95. (ext[1]-ext[0]).magVec() > 4096)
  96. {
  97. llwarns << "Invalid drawable found in octree." << llendl;
  98. }
  99. }
  100. #else
  101. #define validate_drawable(x)
  102. #endif
  103. S32 AABBSphereIntersect(const LLVector3& min, const LLVector3& max, const LLVector3 &origin, const F32 &rad)
  104. {
  105. return AABBSphereIntersectR2(min, max, origin, rad*rad);
  106. }
  107. S32 AABBSphereIntersectR2(const LLVector3& min, const LLVector3& max, const LLVector3 &origin, const F32 &r)
  108. {
  109. F32 d = 0.f;
  110. F32 t;
  111. if ((min-origin).magVecSquared() < r &&
  112. (max-origin).magVecSquared() < r)
  113. {
  114. return 2;
  115. }
  116. for (U32 i = 0; i < 3; i++)
  117. {
  118. if (origin.mV[i] < min.mV[i])
  119. {
  120. t = min.mV[i] - origin.mV[i];
  121. d += t*t;
  122. }
  123. else if (origin.mV[i] > max.mV[i])
  124. {
  125. t = origin.mV[i] - max.mV[i];
  126. d += t*t;
  127. }
  128. if (d > r)
  129. {
  130. return 0;
  131. }
  132. }
  133. return 1;
  134. }
  135. typedef enum
  136. {
  137. b000 = 0x00,
  138. b001 = 0x01,
  139. b010 = 0x02,
  140. b011 = 0x03,
  141. b100 = 0x04,
  142. b101 = 0x05,
  143. b110 = 0x06,
  144. b111 = 0x07,
  145. } eLoveTheBits;
  146. //contact Runitai Linden for a copy of the SL object used to write this table
  147. //basically, you give the table a bitmask of the look-at vector to a node and it
  148. //gives you a triangle fan index array
  149. static U8 sOcclusionIndices[] =
  150. {
  151.  // 000
  152. b111, b110, b010, b011, b001, b101, b100, b110,
  153. //001 
  154. b110, b000, b010, b011, b111, b101, b100, b000,
  155.  //010
  156. b101, b100, b110, b111, b011, b001, b000, b100,
  157.  //011 
  158. b100, b010, b110, b111, b101, b001, b000, b010,
  159. //100 
  160. b011, b010, b000, b001, b101, b111, b110, b010,
  161.  //101 
  162. b010, b100, b000, b001, b011, b111, b110, b100,
  163.  //110
  164. b001, b000, b100, b101, b111, b011, b010, b000,
  165.  //111
  166. b000, b110, b100, b101, b001, b011, b010, b110,
  167. };
  168. U8* get_box_fan_indices(LLCamera* camera, const LLVector3& center)
  169. {
  170. LLVector3 d = center - camera->getOrigin();
  171. U8 cypher = 0;
  172. if (d.mV[0] > 0)
  173. {
  174. cypher |= b100;
  175. }
  176. if (d.mV[1] > 0)
  177. {
  178. cypher |= b010;
  179. }
  180. if (d.mV[2] > 0)
  181. {
  182. cypher |= b001;
  183. }
  184. return sOcclusionIndices+cypher*8;
  185. }
  186. void LLSpatialGroup::buildOcclusion()
  187. {
  188. if (!mOcclusionVerts)
  189. {
  190. mOcclusionVerts = new F32[8*3];
  191. }
  192. LLVector3 r = mBounds[1] + LLVector3(SG_OCCLUSION_FUDGE, SG_OCCLUSION_FUDGE, SG_OCCLUSION_FUDGE);
  193. for (U32 k = 0; k < 3; k++)
  194. {
  195. r.mV[k] = llmin(mBounds[1].mV[k]+0.25f, r.mV[k]);
  196. }
  197. F32* v = mOcclusionVerts;
  198. F32* c = mBounds[0].mV;
  199. F32* s = r.mV;
  200. //vertex positions are encoded so the 3 bits of their vertex index 
  201. //correspond to their axis facing, with bit position 3,2,1 matching
  202. //axis facing x,y,z, bit set meaning positive facing, bit clear 
  203. //meaning negative facing
  204. v[0] = c[0]-s[0]; v[1]  = c[1]-s[1]; v[2]  = c[2]-s[2];  // 0 - 0000 
  205. v[3] = c[0]-s[0]; v[4]  = c[1]-s[1]; v[5]  = c[2]+s[2];  // 1 - 0001
  206. v[6] = c[0]-s[0]; v[7]  = c[1]+s[1]; v[8]  = c[2]-s[2];  // 2 - 0010
  207. v[9] = c[0]-s[0]; v[10] = c[1]+s[1]; v[11] = c[2]+s[2];  // 3 - 0011
  208.    
  209. v[12] = c[0]+s[0]; v[13] = c[1]-s[1]; v[14] = c[2]-s[2]; // 4 - 0100
  210. v[15] = c[0]+s[0]; v[16] = c[1]-s[1]; v[17] = c[2]+s[2]; // 5 - 0101
  211. v[18] = c[0]+s[0]; v[19] = c[1]+s[1]; v[20] = c[2]-s[2]; // 6 - 0110
  212. v[21] = c[0]+s[0]; v[22] = c[1]+s[1]; v[23] = c[2]+s[2]; // 7 - 0111
  213. clearState(LLSpatialGroup::OCCLUSION_DIRTY);
  214. }
  215. BOOL earlyFail(LLCamera* camera, LLSpatialGroup* group);
  216. //returns:
  217. // 0 if sphere and AABB are not intersecting 
  218. // 1 if they are
  219. // 2 if AABB is entirely inside sphere
  220. S32 LLSphereAABB(const LLVector3& center, const LLVector3& size, const LLVector3& pos, const F32 &rad)
  221. {
  222. S32 ret = 2;
  223. LLVector3 min = center - size;
  224. LLVector3 max = center + size;
  225. for (U32 i = 0; i < 3; i++)
  226. {
  227. if (min.mV[i] > pos.mV[i] + rad ||
  228. max.mV[i] < pos.mV[i] - rad)
  229. { //totally outside
  230. return 0;
  231. }
  232. if (min.mV[i] < pos.mV[i] - rad ||
  233. max.mV[i] > pos.mV[i] + rad)
  234. { //intersecting
  235. ret = 1;
  236. }
  237. }
  238. return ret;
  239. }
  240. LLSpatialGroup::~LLSpatialGroup()
  241. {
  242. /*if (sNoDelete)
  243. {
  244. llerrs << "Illegal deletion of LLSpatialGroup!" << llendl;
  245. }*/
  246. if (isState(DEAD))
  247. {
  248. sZombieGroups--;
  249. }
  250. sNodeCount--;
  251. if (gGLManager.mHasOcclusionQuery && mOcclusionQuery[LLViewerCamera::sCurCameraID])
  252. {
  253. sQueryPool.release(mOcclusionQuery[LLViewerCamera::sCurCameraID]);
  254. }
  255. delete [] mOcclusionVerts;
  256. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  257. clearDrawMap();
  258. clearAtlasList() ;
  259. }
  260. BOOL LLSpatialGroup::hasAtlas(LLTextureAtlas* atlasp)
  261. {
  262. S8 type = atlasp->getComponents() - 1 ;
  263. for(std::list<LLTextureAtlas*>::iterator iter = mAtlasList[type].begin(); iter != mAtlasList[type].end() ; ++iter)
  264. {
  265. if(atlasp == *iter)
  266. {
  267. return TRUE ;
  268. }
  269. }
  270. return FALSE ;
  271. }
  272. void LLSpatialGroup::addAtlas(LLTextureAtlas* atlasp, S8 recursive_level) 
  273. {
  274. if(!hasAtlas(atlasp))
  275. {
  276. mAtlasList[atlasp->getComponents() - 1].push_back(atlasp) ;
  277. atlasp->addSpatialGroup(this) ;
  278. }
  279. --recursive_level;
  280. if(recursive_level)//levels propagating up.
  281. {
  282. LLSpatialGroup* parent = getParent() ;
  283. if(parent)
  284. {
  285. parent->addAtlas(atlasp, recursive_level) ;
  286. }
  287. }
  288. }
  289. void LLSpatialGroup::removeAtlas(LLTextureAtlas* atlasp, BOOL remove_group, S8 recursive_level) 
  290. {
  291. mAtlasList[atlasp->getComponents() - 1].remove(atlasp) ;
  292. if(remove_group)
  293. {
  294. atlasp->removeSpatialGroup(this) ;
  295. }
  296. --recursive_level;
  297. if(recursive_level)//levels propagating up.
  298. {
  299. LLSpatialGroup* parent = getParent() ;
  300. if(parent)
  301. {
  302. parent->removeAtlas(atlasp, recursive_level) ;
  303. }
  304. }
  305. }
  306. void LLSpatialGroup::clearAtlasList() 
  307. {
  308. std::list<LLTextureAtlas*>::iterator iter ;
  309. for(S8 i = 0 ; i < 4 ; i++)
  310. {
  311. if(mAtlasList[i].size() > 0)
  312. {
  313. for(iter = mAtlasList[i].begin(); iter != mAtlasList[i].end() ; ++iter)
  314. {
  315. ((LLTextureAtlas*)*iter)->removeSpatialGroup(this) ;
  316. }
  317. mAtlasList[i].clear() ;
  318. }
  319. }
  320. }
  321. LLTextureAtlas* LLSpatialGroup::getAtlas(S8 ncomponents, S8 to_be_reserved, S8 recursive_level)
  322. {
  323. S8 type = ncomponents - 1 ;
  324. if(mAtlasList[type].size() > 0)
  325. {
  326. for(std::list<LLTextureAtlas*>::iterator iter = mAtlasList[type].begin(); iter != mAtlasList[type].end() ; ++iter)
  327. {
  328. if(!((LLTextureAtlas*)*iter)->isFull(to_be_reserved))
  329. {
  330. return *iter ;
  331. }
  332. }
  333. }
  334. --recursive_level;
  335. if(recursive_level)
  336. {
  337. LLSpatialGroup* parent = getParent() ;
  338. if(parent)
  339. {
  340. return parent->getAtlas(ncomponents, to_be_reserved, recursive_level) ;
  341. }
  342. }
  343. return NULL ;
  344. }
  345. void LLSpatialGroup::setCurUpdatingSlot(LLTextureAtlasSlot* slotp) 
  346. mCurUpdatingSlotp = slotp;
  347. //if(!hasAtlas(mCurUpdatingSlotp->getAtlas()))
  348. //{
  349. // addAtlas(mCurUpdatingSlotp->getAtlas()) ;
  350. //}
  351. }
  352. LLTextureAtlasSlot* LLSpatialGroup::getCurUpdatingSlot(LLViewerTexture* imagep, S8 recursive_level) 
  353. if(gFrameCount && mCurUpdatingTime == gFrameCount && mCurUpdatingTexture == imagep)
  354. {
  355. return mCurUpdatingSlotp ;
  356. }
  357. //--recursive_level ;
  358. //if(recursive_level)
  359. //{
  360. // LLSpatialGroup* parent = getParent() ;
  361. // if(parent)
  362. // {
  363. // return parent->getCurUpdatingSlot(imagep, recursive_level) ;
  364. // }
  365. //}
  366. return NULL ;
  367. }
  368. void LLSpatialGroup::clearDrawMap()
  369. {
  370. mDrawMap.clear();
  371. }
  372. BOOL LLSpatialGroup::isRecentlyVisible() const
  373. {
  374. return (LLDrawable::getCurrentFrame() - mVisible[LLViewerCamera::sCurCameraID]) < LLDrawable::getMinVisFrameRange() ;
  375. }
  376. BOOL LLSpatialGroup::isVisible() const
  377. {
  378. return mVisible[LLViewerCamera::sCurCameraID] == LLDrawable::getCurrentFrame() ? TRUE : FALSE;
  379. }
  380. void LLSpatialGroup::setVisible()
  381. {
  382. mVisible[LLViewerCamera::sCurCameraID] = LLDrawable::getCurrentFrame();
  383. }
  384. void LLSpatialGroup::validate()
  385. {
  386. #if LL_OCTREE_PARANOIA_CHECK
  387. sg_assert(!isState(DIRTY));
  388. sg_assert(!isDead());
  389. LLVector3 myMin = mBounds[0] - mBounds[1];
  390. LLVector3 myMax = mBounds[0] + mBounds[1];
  391. validateDrawMap();
  392. for (element_iter i = getData().begin(); i != getData().end(); ++i)
  393. {
  394. LLDrawable* drawable = *i;
  395. sg_assert(drawable->getSpatialGroup() == this);
  396. if (drawable->getSpatialBridge())
  397. {
  398. sg_assert(drawable->getSpatialBridge() == mSpatialPartition->asBridge());
  399. }
  400. /*if (drawable->isSpatialBridge())
  401. {
  402. LLSpatialPartition* part = drawable->asPartition();
  403. if (!part)
  404. {
  405. llerrs << "Drawable reports it is a spatial bridge but not a partition." << llendl;
  406. }
  407. LLSpatialGroup* group = (LLSpatialGroup*) part->mOctree->getListener(0);
  408. group->validate();
  409. }*/
  410. }
  411. for (U32 i = 0; i < mOctreeNode->getChildCount(); ++i)
  412. {
  413. LLSpatialGroup* group = (LLSpatialGroup*) mOctreeNode->getChild(i)->getListener(0);
  414. group->validate();
  415. //ensure all children are enclosed in this node
  416. LLVector3 center = group->mBounds[0];
  417. LLVector3 size = group->mBounds[1];
  418. LLVector3 min = center - size;
  419. LLVector3 max = center + size;
  420. for (U32 j = 0; j < 3; j++)
  421. {
  422. sg_assert(min.mV[j] >= myMin.mV[j]-0.02f);
  423. sg_assert(max.mV[j] <= myMax.mV[j]+0.02f);
  424. }
  425. }
  426. #endif
  427. }
  428. void LLSpatialGroup::checkStates()
  429. {
  430. #if LL_OCTREE_PARANOIA_CHECK
  431. LLOctreeStateCheck checker;
  432. checker.traverse(mOctreeNode);
  433. #endif
  434. }
  435. void validate_draw_info(LLDrawInfo& params)
  436. {
  437. #if LL_OCTREE_PARANOIA_CHECK
  438. if (params.mVertexBuffer.isNull())
  439. {
  440. llerrs << "Draw batch has no vertex buffer." << llendl;
  441. }
  442. //bad range
  443. if (params.mStart >= params.mEnd)
  444. {
  445. llerrs << "Draw batch has invalid range." << llendl;
  446. }
  447. if (params.mEnd >= (U32) params.mVertexBuffer->getNumVerts())
  448. {
  449. llerrs << "Draw batch has buffer overrun error." << llendl;
  450. }
  451. if (params.mOffset + params.mCount > (U32) params.mVertexBuffer->getNumIndices())
  452. {
  453. llerrs << "Draw batch has index buffer ovverrun error." << llendl;
  454. }
  455. //bad indices
  456. U16* indicesp = (U16*) params.mVertexBuffer->getIndicesPointer();
  457. if (indicesp)
  458. {
  459. for (U32 i = params.mOffset; i < params.mOffset+params.mCount; i++)
  460. {
  461. if (indicesp[i] < (U16)params.mStart)
  462. {
  463. llerrs << "Draw batch has vertex buffer index out of range error (index too low)." << llendl;
  464. }
  465. if (indicesp[i] > (U16)params.mEnd)
  466. {
  467. llerrs << "Draw batch has vertex buffer index out of range error (index too high)." << llendl;
  468. }
  469. }
  470. }
  471. #endif
  472. }
  473. void LLSpatialGroup::validateDrawMap()
  474. {
  475. #if LL_OCTREE_PARANOIA_CHECK
  476. for (draw_map_t::iterator i = mDrawMap.begin(); i != mDrawMap.end(); ++i)
  477. {
  478. LLSpatialGroup::drawmap_elem_t& draw_vec = i->second;
  479. for (drawmap_elem_t::iterator j = draw_vec.begin(); j != draw_vec.end(); ++j)
  480. {
  481. LLDrawInfo& params = **j;
  482. validate_draw_info(params);
  483. }
  484. }
  485. #endif
  486. }
  487. BOOL LLSpatialGroup::updateInGroup(LLDrawable *drawablep, BOOL immediate)
  488. {
  489. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  490. drawablep->updateSpatialExtents();
  491. validate_drawable(drawablep);
  492. OctreeNode* parent = mOctreeNode->getOctParent();
  493. if (mOctreeNode->isInside(drawablep->getPositionGroup()) && 
  494. (mOctreeNode->contains(drawablep) ||
  495.  (drawablep->getBinRadius() > mOctreeNode->getSize().mdV[0] &&
  496. parent && parent->getElementCount() >= LL_OCTREE_MAX_CAPACITY)))
  497. {
  498. unbound();
  499. setState(OBJECT_DIRTY);
  500. //setState(GEOM_DIRTY);
  501. validate_drawable(drawablep);
  502. return TRUE;
  503. }
  504. return FALSE;
  505. }
  506. BOOL LLSpatialGroup::addObject(LLDrawable *drawablep, BOOL add_all, BOOL from_octree)
  507. {
  508. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  509. if (!from_octree)
  510. {
  511. mOctreeNode->insert(drawablep);
  512. }
  513. else
  514. {
  515. drawablep->setSpatialGroup(this);
  516. validate_drawable(drawablep);
  517. setState(OBJECT_DIRTY | GEOM_DIRTY);
  518. setOcclusionState(LLSpatialGroup::DISCARD_QUERY, LLSpatialGroup::STATE_MODE_ALL_CAMERAS);
  519. gPipeline.markRebuild(this, TRUE);
  520. if (drawablep->isSpatialBridge())
  521. {
  522. mBridgeList.push_back((LLSpatialBridge*) drawablep);
  523. }
  524. if (drawablep->getRadius() > 1.f)
  525. {
  526. setState(IMAGE_DIRTY);
  527. }
  528. }
  529. return TRUE;
  530. }
  531. void LLSpatialGroup::rebuildGeom()
  532. {
  533. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  534. if (!isDead())
  535. {
  536. mSpatialPartition->rebuildGeom(this);
  537. }
  538. }
  539. void LLSpatialGroup::rebuildMesh()
  540. {
  541. if (!isDead())
  542. {
  543. mSpatialPartition->rebuildMesh(this);
  544. }
  545. }
  546. static LLFastTimer::DeclareTimer FTM_REBUILD_VBO("VBO Rebuilt");
  547. void LLSpatialPartition::rebuildGeom(LLSpatialGroup* group)
  548. {
  549. /*if (!gPipeline.hasRenderType(mDrawableType))
  550. {
  551. return;
  552. }*/
  553. if (group->isDead() || !group->isState(LLSpatialGroup::GEOM_DIRTY))
  554. {
  555. /*if (!group->isState(LLSpatialGroup::GEOM_DIRTY) && mRenderByGroup)
  556. {
  557. llerrs << "WTF?" << llendl;
  558. }*/
  559. return;
  560. }
  561. if (group->changeLOD())
  562. {
  563. group->mLastUpdateDistance = group->mDistance;
  564. group->mLastUpdateViewAngle = group->mViewAngle;
  565. }
  566. LLFastTimer ftm(FTM_REBUILD_VBO);
  567. group->clearDrawMap();
  568. //get geometry count
  569. U32 index_count = 0;
  570. U32 vertex_count = 0;
  571. addGeometryCount(group, vertex_count, index_count);
  572. if (vertex_count > 0 && index_count > 0)
  573. { //create vertex buffer containing volume geometry for this node
  574. group->mBuilt = 1.f;
  575. if (group->mVertexBuffer.isNull() || (group->mBufferUsage != group->mVertexBuffer->getUsage() && LLVertexBuffer::sEnableVBOs))
  576. {
  577. group->mVertexBuffer = createVertexBuffer(mVertexDataMask, group->mBufferUsage);
  578. group->mVertexBuffer->allocateBuffer(vertex_count, index_count, true);
  579. stop_glerror();
  580. }
  581. else
  582. {
  583. group->mVertexBuffer->resizeBuffer(vertex_count, index_count);
  584. stop_glerror();
  585. }
  586. getGeometry(group);
  587. }
  588. else
  589. {
  590. group->mVertexBuffer = NULL;
  591. group->mBufferMap.clear();
  592. }
  593. group->mLastUpdateTime = gFrameTimeSeconds;
  594. group->clearState(LLSpatialGroup::GEOM_DIRTY);
  595. }
  596. void LLSpatialPartition::rebuildMesh(LLSpatialGroup* group)
  597. {
  598. }
  599. BOOL LLSpatialGroup::boundObjects(BOOL empty, LLVector3& minOut, LLVector3& maxOut)
  600. {
  601. const OctreeNode* node = mOctreeNode;
  602. if (node->getData().empty())
  603. { //don't do anything if there are no objects
  604. if (empty && mOctreeNode->getParent())
  605. { //only root is allowed to be empty
  606. OCT_ERRS << "Empty leaf found in octree." << llendl;
  607. }
  608. return FALSE;
  609. }
  610. LLVector3& newMin = mObjectExtents[0];
  611. LLVector3& newMax = mObjectExtents[1];
  612. if (isState(OBJECT_DIRTY))
  613. { //calculate new bounding box
  614. clearState(OBJECT_DIRTY);
  615. //initialize bounding box to first element
  616. OctreeNode::const_element_iter i = node->getData().begin();
  617. LLDrawable* drawablep = *i;
  618. const LLVector3* minMax = drawablep->getSpatialExtents();
  619. newMin.setVec(minMax[0]);
  620. newMax.setVec(minMax[1]);
  621. for (++i; i != node->getData().end(); ++i)
  622. {
  623. drawablep = *i;
  624. minMax = drawablep->getSpatialExtents();
  625. update_min_max(newMin, newMax, minMax[0]);
  626. update_min_max(newMin, newMax, minMax[1]);
  627. //bin up the object
  628. /*for (U32 i = 0; i < 3; i++)
  629. {
  630. if (minMax[0].mV[i] < newMin.mV[i])
  631. {
  632. newMin.mV[i] = minMax[0].mV[i];
  633. }
  634. if (minMax[1].mV[i] > newMax.mV[i])
  635. {
  636. newMax.mV[i] = minMax[1].mV[i];
  637. }
  638. }*/
  639. }
  640. mObjectBounds[0] = (newMin + newMax) * 0.5f;
  641. mObjectBounds[1] = (newMax - newMin) * 0.5f;
  642. }
  643. if (empty)
  644. {
  645. minOut = newMin;
  646. maxOut = newMax;
  647. }
  648. else
  649. {
  650. for (U32 i = 0; i < 3; i++)
  651. {
  652. if (newMin.mV[i] < minOut.mV[i])
  653. {
  654. minOut.mV[i] = newMin.mV[i];
  655. }
  656. if (newMax.mV[i] > maxOut.mV[i])
  657. {
  658. maxOut.mV[i] = newMax.mV[i];
  659. }
  660. }
  661. }
  662. return TRUE;
  663. }
  664. void LLSpatialGroup::unbound()
  665. {
  666. if (isState(DIRTY))
  667. {
  668. return;
  669. }
  670. setState(DIRTY);
  671. //all the parent nodes need to rebound this child
  672. if (mOctreeNode)
  673. {
  674. OctreeNode* parent = (OctreeNode*) mOctreeNode->getParent();
  675. while (parent != NULL)
  676. {
  677. LLSpatialGroup* group = (LLSpatialGroup*) parent->getListener(0);
  678. if (group->isState(DIRTY))
  679. {
  680. return;
  681. }
  682. group->setState(DIRTY);
  683. parent = (OctreeNode*) parent->getParent();
  684. }
  685. }
  686. }
  687. LLSpatialGroup* LLSpatialGroup::getParent()
  688. {
  689. if (isDead())
  690. {
  691. return NULL;
  692. }
  693. if(!mOctreeNode)
  694. {
  695. return NULL;
  696. }
  697. OctreeNode* parent = mOctreeNode->getOctParent();
  698. if (parent)
  699. {
  700. return (LLSpatialGroup*) parent->getListener(0);
  701. }
  702. return NULL;
  703. }
  704. BOOL LLSpatialGroup::removeObject(LLDrawable *drawablep, BOOL from_octree)
  705. {
  706. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  707. unbound();
  708. if (mOctreeNode && !from_octree)
  709. {
  710. if (!mOctreeNode->remove(drawablep))
  711. {
  712. OCT_ERRS << "Could not remove drawable from spatial group" << llendl;
  713. }
  714. }
  715. else
  716. {
  717. drawablep->setSpatialGroup(NULL);
  718. setState(GEOM_DIRTY);
  719. gPipeline.markRebuild(this, TRUE);
  720. if (drawablep->isSpatialBridge())
  721. {
  722. for (bridge_list_t::iterator i = mBridgeList.begin(); i != mBridgeList.end(); ++i)
  723. {
  724. if (*i == drawablep)
  725. {
  726. mBridgeList.erase(i);
  727. break;
  728. }
  729. }
  730. }
  731. if (getElementCount() == 0)
  732. { //delete draw map on last element removal since a rebuild might never happen
  733. clearDrawMap();
  734. }
  735. }
  736. return TRUE;
  737. }
  738. void LLSpatialGroup::shift(const LLVector3 &offset)
  739. {
  740. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  741. LLVector3d offsetd(offset);
  742. mOctreeNode->setCenter(mOctreeNode->getCenter()+offsetd);
  743. mOctreeNode->updateMinMax();
  744. mBounds[0] += offset;
  745. mExtents[0] += offset;
  746. mExtents[1] += offset;
  747. mObjectBounds[0] += offset;
  748. mObjectExtents[0] += offset;
  749. mObjectExtents[1] += offset;
  750. //if (!mSpatialPartition->mRenderByGroup)
  751. {
  752. setState(GEOM_DIRTY);
  753. gPipeline.markRebuild(this, TRUE);
  754. }
  755. if (mOcclusionVerts)
  756. {
  757. for (U32 i = 0; i < 8; i++)
  758. {
  759. F32* v = mOcclusionVerts+i*3;
  760. v[0] += offset.mV[0];
  761. v[1] += offset.mV[1];
  762. v[2] += offset.mV[2];
  763. }
  764. }
  765. }
  766. class LLSpatialSetState : public LLSpatialGroup::OctreeTraveler
  767. {
  768. public:
  769. U32 mState;
  770. LLSpatialSetState(U32 state) : mState(state) { }
  771. virtual void visit(const LLSpatialGroup::OctreeNode* branch) { ((LLSpatialGroup*) branch->getListener(0))->setState(mState); }
  772. };
  773. class LLSpatialSetStateDiff : public LLSpatialSetState
  774. {
  775. public:
  776. LLSpatialSetStateDiff(U32 state) : LLSpatialSetState(state) { }
  777. virtual void traverse(const LLSpatialGroup::OctreeNode* n)
  778. {
  779. LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
  780. if (!group->isState(mState))
  781. {
  782. LLSpatialGroup::OctreeTraveler::traverse(n);
  783. }
  784. }
  785. };
  786. void LLSpatialGroup::setState(U32 state) 
  787. mState |= state; 
  788. if (state > LLSpatialGroup::STATE_MASK)
  789. {
  790. llerrs << "WTF?" << llendl;
  791. }
  792. }
  793. void LLSpatialGroup::setState(U32 state, S32 mode) 
  794. {
  795. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  796. if (state > LLSpatialGroup::STATE_MASK)
  797. {
  798. llerrs << "WTF?" << llendl;
  799. }
  800. if (mode > STATE_MODE_SINGLE)
  801. {
  802. if (mode == STATE_MODE_DIFF)
  803. {
  804. LLSpatialSetStateDiff setter(state);
  805. setter.traverse(mOctreeNode);
  806. }
  807. else
  808. {
  809. LLSpatialSetState setter(state);
  810. setter.traverse(mOctreeNode);
  811. }
  812. }
  813. else
  814. {
  815. mState |= state;
  816. }
  817. }
  818. class LLSpatialClearState : public LLSpatialGroup::OctreeTraveler
  819. {
  820. public:
  821. U32 mState;
  822. LLSpatialClearState(U32 state) : mState(state) { }
  823. virtual void visit(const LLSpatialGroup::OctreeNode* branch) { ((LLSpatialGroup*) branch->getListener(0))->clearState(mState); }
  824. };
  825. class LLSpatialClearStateDiff : public LLSpatialClearState
  826. {
  827. public:
  828. LLSpatialClearStateDiff(U32 state) : LLSpatialClearState(state) { }
  829. virtual void traverse(const LLSpatialGroup::OctreeNode* n)
  830. {
  831. LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
  832. if (group->isState(mState))
  833. {
  834. LLSpatialGroup::OctreeTraveler::traverse(n);
  835. }
  836. }
  837. };
  838. void LLSpatialGroup::clearState(U32 state)
  839. {
  840. if (state > LLSpatialGroup::STATE_MASK)
  841. {
  842. llerrs << "WTF?" << llendl;
  843. }
  844. mState &= ~state; 
  845. }
  846. void LLSpatialGroup::clearState(U32 state, S32 mode)
  847. {
  848. if (state > LLSpatialGroup::STATE_MASK)
  849. {
  850. llerrs << "WTF?" << llendl;
  851. }
  852. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  853. if (mode > STATE_MODE_SINGLE)
  854. {
  855. if (mode == STATE_MODE_DIFF)
  856. {
  857. LLSpatialClearStateDiff clearer(state);
  858. clearer.traverse(mOctreeNode);
  859. }
  860. else
  861. {
  862. LLSpatialClearState clearer(state);
  863. clearer.traverse(mOctreeNode);
  864. }
  865. }
  866. else
  867. {
  868. mState &= ~state;
  869. }
  870. }
  871. BOOL LLSpatialGroup::isState(U32 state) const
  872. if (state > LLSpatialGroup::STATE_MASK)
  873. {
  874. llerrs << "WTF?" << llendl;
  875. }
  876. return mState & state ? TRUE : FALSE; 
  877. }
  878. //=====================================
  879. // Occlusion State Set/Clear
  880. //=====================================
  881. class LLSpatialSetOcclusionState : public LLSpatialGroup::OctreeTraveler
  882. {
  883. public:
  884. U32 mState;
  885. LLSpatialSetOcclusionState(U32 state) : mState(state) { }
  886. virtual void visit(const LLSpatialGroup::OctreeNode* branch) { ((LLSpatialGroup*) branch->getListener(0))->setOcclusionState(mState); }
  887. };
  888. class LLSpatialSetOcclusionStateDiff : public LLSpatialSetOcclusionState
  889. {
  890. public:
  891. LLSpatialSetOcclusionStateDiff(U32 state) : LLSpatialSetOcclusionState(state) { }
  892. virtual void traverse(const LLSpatialGroup::OctreeNode* n)
  893. {
  894. LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
  895. if (!group->isOcclusionState(mState))
  896. {
  897. LLSpatialGroup::OctreeTraveler::traverse(n);
  898. }
  899. }
  900. };
  901. void LLSpatialGroup::setOcclusionState(U32 state, S32 mode) 
  902. {
  903. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  904. if (mode > STATE_MODE_SINGLE)
  905. {
  906. if (mode == STATE_MODE_DIFF)
  907. {
  908. LLSpatialSetOcclusionStateDiff setter(state);
  909. setter.traverse(mOctreeNode);
  910. }
  911. else if (mode == STATE_MODE_BRANCH)
  912. {
  913. LLSpatialSetOcclusionState setter(state);
  914. setter.traverse(mOctreeNode);
  915. }
  916. else
  917. {
  918. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  919. {
  920. mOcclusionState[i] |= state;
  921. }
  922. }
  923. }
  924. else
  925. {
  926. mOcclusionState[LLViewerCamera::sCurCameraID] |= state;
  927. }
  928. }
  929. class LLSpatialClearOcclusionState : public LLSpatialGroup::OctreeTraveler
  930. {
  931. public:
  932. U32 mState;
  933. LLSpatialClearOcclusionState(U32 state) : mState(state) { }
  934. virtual void visit(const LLSpatialGroup::OctreeNode* branch) { ((LLSpatialGroup*) branch->getListener(0))->clearOcclusionState(mState); }
  935. };
  936. class LLSpatialClearOcclusionStateDiff : public LLSpatialClearOcclusionState
  937. {
  938. public:
  939. LLSpatialClearOcclusionStateDiff(U32 state) : LLSpatialClearOcclusionState(state) { }
  940. virtual void traverse(const LLSpatialGroup::OctreeNode* n)
  941. {
  942. LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
  943. if (group->isOcclusionState(mState))
  944. {
  945. LLSpatialGroup::OctreeTraveler::traverse(n);
  946. }
  947. }
  948. };
  949. void LLSpatialGroup::clearOcclusionState(U32 state, S32 mode)
  950. {
  951. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  952. if (mode > STATE_MODE_SINGLE)
  953. {
  954. if (mode == STATE_MODE_DIFF)
  955. {
  956. LLSpatialClearOcclusionStateDiff clearer(state);
  957. clearer.traverse(mOctreeNode);
  958. }
  959. else if (mode == STATE_MODE_BRANCH)
  960. {
  961. LLSpatialClearOcclusionState clearer(state);
  962. clearer.traverse(mOctreeNode);
  963. }
  964. else
  965. {
  966. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  967. {
  968. mOcclusionState[i] &= ~state;
  969. }
  970. }
  971. }
  972. else
  973. {
  974. mOcclusionState[LLViewerCamera::sCurCameraID] &= ~state;
  975. }
  976. }
  977. //======================================
  978. // Octree Listener Implementation
  979. //======================================
  980. LLSpatialGroup::LLSpatialGroup(OctreeNode* node, LLSpatialPartition* part) :
  981. mState(0),
  982. mBuilt(0.f),
  983. mOctreeNode(node),
  984. mSpatialPartition(part),
  985. mVertexBuffer(NULL), 
  986. mBufferUsage(GL_STATIC_DRAW_ARB),
  987. mDistance(0.f),
  988. mDepth(0.f),
  989. mLastUpdateDistance(-1.f), 
  990. mLastUpdateTime(gFrameTimeSeconds),
  991. mViewAngle(0.f),
  992. mLastUpdateViewAngle(-1.f),
  993. mAtlasList(4),
  994. mCurUpdatingTime(0),
  995. mCurUpdatingSlotp(NULL),
  996. mCurUpdatingTexture (NULL)
  997. {
  998. sNodeCount++;
  999. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1000. sg_assert(mOctreeNode->getListenerCount() == 0);
  1001. mOctreeNode->addListener(this);
  1002. setState(SG_INITIAL_STATE_MASK);
  1003. gPipeline.markRebuild(this, TRUE);
  1004. mBounds[0] = LLVector3(node->getCenter());
  1005. mBounds[1] = LLVector3(node->getSize());
  1006. part->mLODSeed = (part->mLODSeed+1)%part->mLODPeriod;
  1007. mLODHash = part->mLODSeed;
  1008. OctreeNode* oct_parent = node->getOctParent();
  1009. LLSpatialGroup* parent = oct_parent ? (LLSpatialGroup*) oct_parent->getListener(0) : NULL;
  1010. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  1011. {
  1012. mOcclusionQuery[i] = 0;
  1013. mOcclusionState[i] = parent ? SG_STATE_INHERIT_MASK & parent->mOcclusionState[i] : 0;
  1014. mVisible[i] = 0;
  1015. }
  1016. mOcclusionVerts = NULL;
  1017. mRadius = 1;
  1018. mPixelArea = 1024.f;
  1019. }
  1020. void LLSpatialGroup::updateDistance(LLCamera &camera)
  1021. {
  1022. if (LLViewerCamera::sCurCameraID != LLViewerCamera::CAMERA_WORLD)
  1023. {
  1024. llerrs << "WTF?" << llendl;
  1025. }
  1026. #if !LL_RELEASE_FOR_DOWNLOAD
  1027. if (isState(LLSpatialGroup::OBJECT_DIRTY))
  1028. {
  1029. llerrs << "Spatial group dirty on distance update." << llendl;
  1030. }
  1031. #endif
  1032. if (!getData().empty())
  1033. {
  1034. mRadius = mSpatialPartition->mRenderByGroup ? mObjectBounds[1].magVec() :
  1035. (F32) mOctreeNode->getSize().magVec();
  1036. mDistance = mSpatialPartition->calcDistance(this, camera);
  1037. mPixelArea = mSpatialPartition->calcPixelArea(this, camera);
  1038. }
  1039. }
  1040. F32 LLSpatialPartition::calcDistance(LLSpatialGroup* group, LLCamera& camera)
  1041. {
  1042. LLVector3 eye = group->mObjectBounds[0] - camera.getOrigin();
  1043. F32 dist = 0.f;
  1044. if (group->mDrawMap.find(LLRenderPass::PASS_ALPHA) != group->mDrawMap.end())
  1045. {
  1046. LLVector3 v = eye;
  1047. dist = eye.normVec();
  1048. if (!group->isState(LLSpatialGroup::ALPHA_DIRTY))
  1049. {
  1050. if (!group->mSpatialPartition->isBridge())
  1051. {
  1052. LLVector3 view_angle = LLVector3(eye * LLVector3(1,0,0),
  1053.  eye * LLVector3(0,1,0),
  1054.  eye * LLVector3(0,0,1));
  1055. if ((view_angle-group->mLastUpdateViewAngle).magVec() > 0.64f)
  1056. {
  1057. group->mViewAngle = view_angle;
  1058. group->mLastUpdateViewAngle = view_angle;
  1059. //for occasional alpha sorting within the group
  1060. //NOTE: If there is a trivial way to detect that alpha sorting here would not change the render order,
  1061. //not setting this node to dirty would be a very good thing
  1062. group->setState(LLSpatialGroup::ALPHA_DIRTY);
  1063. gPipeline.markRebuild(group, FALSE);
  1064. }
  1065. }
  1066. }
  1067. //calculate depth of node for alpha sorting
  1068. LLVector3 at = camera.getAtAxis();
  1069. //front of bounding box
  1070. for (U32 i = 0; i < 3; i++)
  1071. {
  1072. v.mV[i] -= group->mObjectBounds[1].mV[i]*0.25f * at.mV[i];
  1073. }
  1074. group->mDepth = v * at;
  1075. }
  1076. else
  1077. {
  1078. dist = eye.magVec();
  1079. }
  1080. if (dist < 16.f)
  1081. {
  1082. dist /= 16.f;
  1083. dist *= dist;
  1084. dist *= 16.f;
  1085. }
  1086. return dist;
  1087. }
  1088. F32 LLSpatialPartition::calcPixelArea(LLSpatialGroup* group, LLCamera& camera)
  1089. {
  1090. return LLPipeline::calcPixelArea(group->mObjectBounds[0], group->mObjectBounds[1], camera);
  1091. }
  1092. F32 LLSpatialGroup::getUpdateUrgency() const
  1093. {
  1094. if (!isVisible())
  1095. {
  1096. return 0.f;
  1097. }
  1098. else
  1099. {
  1100. return (gFrameTimeSeconds - mLastUpdateTime+4.f)/mDistance;
  1101. }
  1102. }
  1103. BOOL LLSpatialGroup::needsUpdate()
  1104. {
  1105. return (LLDrawable::getCurrentFrame()%mSpatialPartition->mLODPeriod == mLODHash) ? TRUE : FALSE;
  1106. }
  1107. BOOL LLSpatialGroup::changeLOD()
  1108. {
  1109. if (isState(ALPHA_DIRTY))
  1110. { ///an alpha sort is going to happen, update distance and LOD
  1111. return TRUE;
  1112. }
  1113. if (mSpatialPartition->mSlopRatio > 0.f)
  1114. {
  1115. F32 ratio = (mDistance - mLastUpdateDistance)/(llmax(mLastUpdateDistance, mRadius));
  1116. if (fabsf(ratio) >= mSpatialPartition->mSlopRatio)
  1117. {
  1118. return TRUE;
  1119. }
  1120. if (mDistance > mRadius)
  1121. {
  1122. return FALSE;
  1123. }
  1124. }
  1125. if (needsUpdate())
  1126. {
  1127. return TRUE;
  1128. }
  1129. return FALSE;
  1130. }
  1131. void LLSpatialGroup::handleInsertion(const TreeNode* node, LLDrawable* drawablep)
  1132. {
  1133. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1134. addObject(drawablep, FALSE, TRUE);
  1135. unbound();
  1136. setState(OBJECT_DIRTY);
  1137. }
  1138. void LLSpatialGroup::handleRemoval(const TreeNode* node, LLDrawable* drawable)
  1139. {
  1140. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1141. removeObject(drawable, TRUE);
  1142. setState(OBJECT_DIRTY);
  1143. }
  1144. void LLSpatialGroup::handleDestruction(const TreeNode* node)
  1145. {
  1146. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1147. setState(DEAD);
  1148. for (element_iter i = getData().begin(); i != getData().end(); ++i)
  1149. {
  1150. LLDrawable* drawable = *i;
  1151. if (drawable->getSpatialGroup() == this)
  1152. {
  1153. drawable->setSpatialGroup(NULL);
  1154. }
  1155. }
  1156. clearDrawMap();
  1157. mVertexBuffer = NULL;
  1158. mBufferMap.clear();
  1159. sZombieGroups++;
  1160. mOctreeNode = NULL;
  1161. }
  1162. void LLSpatialGroup::handleStateChange(const TreeNode* node)
  1163. {
  1164. //drop bounding box upon state change
  1165. if (mOctreeNode != node)
  1166. {
  1167. mOctreeNode = (OctreeNode*) node;
  1168. }
  1169. unbound();
  1170. }
  1171. void LLSpatialGroup::handleChildAddition(const OctreeNode* parent, OctreeNode* child) 
  1172. {
  1173. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1174. if (child->getListenerCount() == 0)
  1175. {
  1176. new LLSpatialGroup(child, mSpatialPartition);
  1177. }
  1178. else
  1179. {
  1180. OCT_ERRS << "LLSpatialGroup redundancy detected." << llendl;
  1181. }
  1182. unbound();
  1183. assert_states_valid(this);
  1184. }
  1185. void LLSpatialGroup::handleChildRemoval(const OctreeNode* parent, const OctreeNode* child)
  1186. {
  1187. unbound();
  1188. }
  1189. void LLSpatialGroup::destroyGL() 
  1190. {
  1191. setState(LLSpatialGroup::GEOM_DIRTY | LLSpatialGroup::IMAGE_DIRTY);
  1192. gPipeline.markRebuild(this, TRUE);
  1193. mLastUpdateTime = gFrameTimeSeconds;
  1194. mVertexBuffer = NULL;
  1195. mBufferMap.clear();
  1196. clearDrawMap();
  1197. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  1198. {
  1199. if (mOcclusionQuery[i])
  1200. {
  1201. sQueryPool.release(mOcclusionQuery[i]);
  1202. mOcclusionQuery[i] = 0;
  1203. }
  1204. }
  1205. delete [] mOcclusionVerts;
  1206. mOcclusionVerts = NULL;
  1207. for (LLSpatialGroup::element_iter i = getData().begin(); i != getData().end(); ++i)
  1208. {
  1209. LLDrawable* drawable = *i;
  1210. for (S32 j = 0; j < drawable->getNumFaces(); j++)
  1211. {
  1212. LLFace* facep = drawable->getFace(j);
  1213. facep->mVertexBuffer = NULL;
  1214. facep->mLastVertexBuffer = NULL;
  1215. }
  1216. }
  1217. }
  1218. BOOL LLSpatialGroup::rebound()
  1219. {
  1220. if (!isState(DIRTY))
  1221. { //return TRUE if we're not empty
  1222. return TRUE;
  1223. }
  1224. if (mOctreeNode->getChildCount() == 1 && mOctreeNode->getElementCount() == 0)
  1225. {
  1226. LLSpatialGroup* group = (LLSpatialGroup*) mOctreeNode->getChild(0)->getListener(0);
  1227. group->rebound();
  1228. //copy single child's bounding box
  1229. mBounds[0] = group->mBounds[0];
  1230. mBounds[1] = group->mBounds[1];
  1231. mExtents[0] = group->mExtents[0];
  1232. mExtents[1] = group->mExtents[1];
  1233. group->setState(SKIP_FRUSTUM_CHECK);
  1234. }
  1235. else if (mOctreeNode->isLeaf())
  1236. { //copy object bounding box if this is a leaf
  1237. boundObjects(TRUE, mExtents[0], mExtents[1]);
  1238. mBounds[0] = mObjectBounds[0];
  1239. mBounds[1] = mObjectBounds[1];
  1240. }
  1241. else
  1242. {
  1243. LLVector3& newMin = mExtents[0];
  1244. LLVector3& newMax = mExtents[1];
  1245. LLSpatialGroup* group = (LLSpatialGroup*) mOctreeNode->getChild(0)->getListener(0);
  1246. group->clearState(SKIP_FRUSTUM_CHECK);
  1247. group->rebound();
  1248. //initialize to first child
  1249. newMin = group->mExtents[0];
  1250. newMax = group->mExtents[1];
  1251. //first, rebound children
  1252. for (U32 i = 1; i < mOctreeNode->getChildCount(); i++)
  1253. {
  1254. group = (LLSpatialGroup*) mOctreeNode->getChild(i)->getListener(0);
  1255. group->clearState(SKIP_FRUSTUM_CHECK);
  1256. group->rebound();
  1257. const LLVector3& max = group->mExtents[1];
  1258. const LLVector3& min = group->mExtents[0];
  1259. for (U32 j = 0; j < 3; j++)
  1260. {
  1261. if (max.mV[j] > newMax.mV[j])
  1262. {
  1263. newMax.mV[j] = max.mV[j];
  1264. }
  1265. if (min.mV[j] < newMin.mV[j])
  1266. {
  1267. newMin.mV[j] = min.mV[j];
  1268. }
  1269. }
  1270. }
  1271. boundObjects(FALSE, newMin, newMax);
  1272. mBounds[0] = (newMin + newMax)*0.5f;
  1273. mBounds[1] = (newMax - newMin)*0.5f;
  1274. }
  1275. setState(OCCLUSION_DIRTY);
  1276. clearState(DIRTY);
  1277. return TRUE;
  1278. }
  1279. static LLFastTimer::DeclareTimer FTM_OCCLUSION_READBACK("Readback Occlusion");
  1280. void LLSpatialGroup::checkOcclusion()
  1281. {
  1282. if (LLPipeline::sUseOcclusion > 1)
  1283. {
  1284. LLSpatialGroup* parent = getParent();
  1285. if (parent && parent->isOcclusionState(LLSpatialGroup::OCCLUDED))
  1286. { //if the parent has been marked as occluded, the child is implicitly occluded
  1287. clearOcclusionState(QUERY_PENDING | DISCARD_QUERY);
  1288. }
  1289. else if (isOcclusionState(QUERY_PENDING))
  1290. { //otherwise, if a query is pending, read it back
  1291. LLFastTimer t(FTM_OCCLUSION_READBACK);
  1292. GLuint res = 1;
  1293. if (!isOcclusionState(DISCARD_QUERY) && mOcclusionQuery[LLViewerCamera::sCurCameraID])
  1294. {
  1295. glGetQueryObjectuivARB(mOcclusionQuery[LLViewerCamera::sCurCameraID], GL_QUERY_RESULT_ARB, &res);
  1296. }
  1297. if (isOcclusionState(DISCARD_QUERY))
  1298. {
  1299. res = 2;
  1300. }
  1301. if (res > 0)
  1302. {
  1303. assert_states_valid(this);
  1304. clearOcclusionState(LLSpatialGroup::OCCLUDED, LLSpatialGroup::STATE_MODE_DIFF);
  1305. assert_states_valid(this);
  1306. }
  1307. else
  1308. {
  1309. assert_states_valid(this);
  1310. setOcclusionState(LLSpatialGroup::OCCLUDED, LLSpatialGroup::STATE_MODE_DIFF);
  1311. assert_states_valid(this);
  1312. }
  1313. clearOcclusionState(QUERY_PENDING | DISCARD_QUERY);
  1314. }
  1315. else if (mSpatialPartition->isOcclusionEnabled() && isOcclusionState(LLSpatialGroup::OCCLUDED))
  1316. { //check occlusion has been issued for occluded node that has not had a query issued
  1317. assert_states_valid(this);
  1318. clearOcclusionState(LLSpatialGroup::OCCLUDED, LLSpatialGroup::STATE_MODE_DIFF);
  1319. assert_states_valid(this);
  1320. }
  1321. }
  1322. }
  1323. void LLSpatialGroup::doOcclusion(LLCamera* camera)
  1324. {
  1325. if (mSpatialPartition->isOcclusionEnabled() && LLPipeline::sUseOcclusion > 1)
  1326. {
  1327. if (earlyFail(camera, this))
  1328. {
  1329. setOcclusionState(LLSpatialGroup::DISCARD_QUERY);
  1330. assert_states_valid(this);
  1331. clearOcclusionState(LLSpatialGroup::OCCLUDED, LLSpatialGroup::STATE_MODE_DIFF);
  1332. assert_states_valid(this);
  1333. }
  1334. else
  1335. {
  1336. {
  1337. LLFastTimer t(FTM_RENDER_OCCLUSION);
  1338. if (!mOcclusionQuery[LLViewerCamera::sCurCameraID])
  1339. {
  1340. mOcclusionQuery[LLViewerCamera::sCurCameraID] = sQueryPool.allocate();
  1341. }
  1342. if (!mOcclusionVerts || isState(LLSpatialGroup::OCCLUSION_DIRTY))
  1343. {
  1344. buildOcclusion();
  1345. }
  1346. glBeginQueryARB(GL_SAMPLES_PASSED_ARB, mOcclusionQuery[LLViewerCamera::sCurCameraID]);
  1347. glVertexPointer(3, GL_FLOAT, 0, mOcclusionVerts);
  1348. if (camera->getOrigin().isExactlyZero())
  1349. { //origin is invalid, draw entire box
  1350. glDrawRangeElements(GL_TRIANGLE_FAN, 0, 7, 8,
  1351. GL_UNSIGNED_BYTE, sOcclusionIndices);
  1352. glDrawRangeElements(GL_TRIANGLE_FAN, 0, 7, 8,
  1353. GL_UNSIGNED_BYTE, sOcclusionIndices+b111*8);
  1354. }
  1355. else
  1356. {
  1357. glDrawRangeElements(GL_TRIANGLE_FAN, 0, 7, 8,
  1358. GL_UNSIGNED_BYTE, get_box_fan_indices(camera, mBounds[0]));
  1359. }
  1360. glEndQueryARB(GL_SAMPLES_PASSED_ARB);
  1361. }
  1362. setOcclusionState(LLSpatialGroup::QUERY_PENDING);
  1363. clearOcclusionState(LLSpatialGroup::DISCARD_QUERY);
  1364. }
  1365. }
  1366. }
  1367. //==============================================
  1368. LLSpatialPartition::LLSpatialPartition(U32 data_mask, BOOL render_by_group, U32 buffer_usage)
  1369. : mRenderByGroup(render_by_group)
  1370. {
  1371. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1372. mOcclusionEnabled = TRUE;
  1373. mDrawableType = 0;
  1374. mPartitionType = LLViewerRegion::PARTITION_NONE;
  1375. mLODSeed = 0;
  1376. mLODPeriod = 1;
  1377. mVertexDataMask = data_mask;
  1378. mBufferUsage = buffer_usage;
  1379. mDepthMask = FALSE;
  1380. mSlopRatio = 0.25f;
  1381. mInfiniteFarClip = FALSE;
  1382. LLGLNamePool::registerPool(&sQueryPool);
  1383. mOctree = new LLSpatialGroup::OctreeRoot(LLVector3d(0,0,0), 
  1384. LLVector3d(1,1,1), 
  1385. NULL);
  1386. new LLSpatialGroup(mOctree, this);
  1387. }
  1388. LLSpatialPartition::~LLSpatialPartition()
  1389. {
  1390. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1391. delete mOctree;
  1392. mOctree = NULL;
  1393. }
  1394. LLSpatialGroup *LLSpatialPartition::put(LLDrawable *drawablep, BOOL was_visible)
  1395. {
  1396. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1397. drawablep->updateSpatialExtents();
  1398. validate_drawable(drawablep);
  1399. //keep drawable from being garbage collected
  1400. LLPointer<LLDrawable> ptr = drawablep;
  1401. assert_octree_valid(mOctree);
  1402. mOctree->insert(drawablep);
  1403. assert_octree_valid(mOctree);
  1404. LLSpatialGroup* group = drawablep->getSpatialGroup();
  1405. if (group && was_visible && group->isOcclusionState(LLSpatialGroup::QUERY_PENDING))
  1406. {
  1407. group->setOcclusionState(LLSpatialGroup::DISCARD_QUERY, LLSpatialGroup::STATE_MODE_ALL_CAMERAS);
  1408. }
  1409. return group;
  1410. }
  1411. BOOL LLSpatialPartition::remove(LLDrawable *drawablep, LLSpatialGroup *curp)
  1412. {
  1413. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1414. drawablep->setSpatialGroup(NULL);
  1415. if (!curp->removeObject(drawablep))
  1416. {
  1417. OCT_ERRS << "Failed to remove drawable from octree!" << llendl;
  1418. }
  1419. assert_octree_valid(mOctree);
  1420. return TRUE;
  1421. }
  1422. void LLSpatialPartition::move(LLDrawable *drawablep, LLSpatialGroup *curp, BOOL immediate)
  1423. {
  1424. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1425. // sanity check submitted by open source user bushing Spatula
  1426. // who was seeing crashing here. (See VWR-424 reported by Bunny Mayne)
  1427. if (!drawablep)
  1428. {
  1429. OCT_ERRS << "LLSpatialPartition::move was passed a bad drawable." << llendl;
  1430. return;
  1431. }
  1432. BOOL was_visible = curp ? curp->isVisible() : FALSE;
  1433. if (curp && curp->mSpatialPartition != this)
  1434. {
  1435. //keep drawable from being garbage collected
  1436. LLPointer<LLDrawable> ptr = drawablep;
  1437. if (curp->mSpatialPartition->remove(drawablep, curp))
  1438. {
  1439. put(drawablep, was_visible);
  1440. return;
  1441. }
  1442. else
  1443. {
  1444. OCT_ERRS << "Drawable lost between spatial partitions on outbound transition." << llendl;
  1445. }
  1446. }
  1447. if (curp && curp->updateInGroup(drawablep, immediate))
  1448. {
  1449. // Already updated, don't need to do anything
  1450. assert_octree_valid(mOctree);
  1451. return;
  1452. }
  1453. //keep drawable from being garbage collected
  1454. LLPointer<LLDrawable> ptr = drawablep;
  1455. if (curp && !remove(drawablep, curp))
  1456. {
  1457. OCT_ERRS << "Move couldn't find existing spatial group!" << llendl;
  1458. }
  1459. put(drawablep, was_visible);
  1460. }
  1461. class LLSpatialShift : public LLSpatialGroup::OctreeTraveler
  1462. {
  1463. public:
  1464. LLSpatialShift(LLVector3 offset) : mOffset(offset) { }
  1465. virtual void visit(const LLSpatialGroup::OctreeNode* branch) 
  1466. ((LLSpatialGroup*) branch->getListener(0))->shift(mOffset); 
  1467. }
  1468. LLVector3 mOffset;
  1469. };
  1470. void LLSpatialPartition::shift(const LLVector3 &offset)
  1471. { //shift octree node bounding boxes by offset
  1472. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1473. LLSpatialShift shifter(offset);
  1474. shifter.traverse(mOctree);
  1475. }
  1476. class LLOctreeCull : public LLSpatialGroup::OctreeTraveler
  1477. {
  1478. public:
  1479. LLOctreeCull(LLCamera* camera)
  1480. : mCamera(camera), mRes(0) { }
  1481. virtual bool earlyFail(LLSpatialGroup* group)
  1482. {
  1483. group->checkOcclusion();
  1484. if (group->mOctreeNode->getParent() && //never occlusion cull the root node
  1485.    LLPipeline::sUseOcclusion && //ignore occlusion if disabled
  1486. group->isOcclusionState(LLSpatialGroup::OCCLUDED))
  1487. {
  1488. gPipeline.markOccluder(group);
  1489. return true;
  1490. }
  1491. return false;
  1492. }
  1493. virtual void traverse(const LLSpatialGroup::OctreeNode* n)
  1494. {
  1495. LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
  1496. if (earlyFail(group))
  1497. {
  1498. return;
  1499. }
  1500. if (mRes == 2 || 
  1501. (mRes && group->isState(LLSpatialGroup::SKIP_FRUSTUM_CHECK)))
  1502. { //fully in, just add everything
  1503. LLSpatialGroup::OctreeTraveler::traverse(n);
  1504. }
  1505. else
  1506. {
  1507. mRes = frustumCheck(group);
  1508. if (mRes)
  1509. { //at least partially in, run on down
  1510. LLSpatialGroup::OctreeTraveler::traverse(n);
  1511. }
  1512. mRes = 0;
  1513. }
  1514. }
  1515. virtual S32 frustumCheck(const LLSpatialGroup* group)
  1516. {
  1517. S32 res = mCamera->AABBInFrustumNoFarClip(group->mBounds[0], group->mBounds[1]);
  1518. if (res != 0)
  1519. {
  1520. res = llmin(res, AABBSphereIntersect(group->mExtents[0], group->mExtents[1], mCamera->getOrigin(), mCamera->mFrustumCornerDist));
  1521. }
  1522. return res;
  1523. }
  1524. virtual S32 frustumCheckObjects(const LLSpatialGroup* group)
  1525. {
  1526. S32 res = mCamera->AABBInFrustumNoFarClip(group->mObjectBounds[0], group->mObjectBounds[1]);
  1527. if (res != 0)
  1528. {
  1529. res = llmin(res, AABBSphereIntersect(group->mObjectExtents[0], group->mObjectExtents[1], mCamera->getOrigin(), mCamera->mFrustumCornerDist));
  1530. }
  1531. return res;
  1532. }
  1533. virtual bool checkObjects(const LLSpatialGroup::OctreeNode* branch, const LLSpatialGroup* group)
  1534. {
  1535. if (branch->getElementCount() == 0) //no elements
  1536. {
  1537. return false;
  1538. }
  1539. else if (branch->getChildCount() == 0) //leaf state, already checked tightest bounding box
  1540. {
  1541. return true;
  1542. }
  1543. else if (mRes == 1 && !frustumCheckObjects(group)) //no objects in frustum
  1544. {
  1545. return false;
  1546. }
  1547. return true;
  1548. }
  1549. virtual void preprocess(LLSpatialGroup* group)
  1550. {
  1551. }
  1552. virtual void processGroup(LLSpatialGroup* group)
  1553. {
  1554. if (group->needsUpdate() ||
  1555. group->mVisible[LLViewerCamera::sCurCameraID] < LLDrawable::getCurrentFrame() - 1)
  1556. {
  1557. group->doOcclusion(mCamera);
  1558. }
  1559. gPipeline.markNotCulled(group, *mCamera);
  1560. }
  1561. virtual void visit(const LLSpatialGroup::OctreeNode* branch) 
  1562. {
  1563. LLSpatialGroup* group = (LLSpatialGroup*) branch->getListener(0);
  1564. preprocess(group);
  1565. if (checkObjects(branch, group))
  1566. {
  1567. processGroup(group);
  1568. }
  1569. }
  1570. LLCamera *mCamera;
  1571. S32 mRes;
  1572. };
  1573. class LLOctreeCullNoFarClip : public LLOctreeCull
  1574. {
  1575. public: 
  1576. LLOctreeCullNoFarClip(LLCamera* camera) 
  1577. : LLOctreeCull(camera) { }
  1578. virtual S32 frustumCheck(const LLSpatialGroup* group)
  1579. {
  1580. return mCamera->AABBInFrustumNoFarClip(group->mBounds[0], group->mBounds[1]);
  1581. }
  1582. virtual S32 frustumCheckObjects(const LLSpatialGroup* group)
  1583. {
  1584. S32 res = mCamera->AABBInFrustumNoFarClip(group->mObjectBounds[0], group->mObjectBounds[1]);
  1585. return res;
  1586. }
  1587. };
  1588. class LLOctreeCullShadow : public LLOctreeCull
  1589. {
  1590. public:
  1591. LLOctreeCullShadow(LLCamera* camera)
  1592. : LLOctreeCull(camera) { }
  1593. virtual S32 frustumCheck(const LLSpatialGroup* group)
  1594. {
  1595. return mCamera->AABBInFrustum(group->mBounds[0], group->mBounds[1]);
  1596. }
  1597. virtual S32 frustumCheckObjects(const LLSpatialGroup* group)
  1598. {
  1599. return mCamera->AABBInFrustum(group->mObjectBounds[0], group->mObjectBounds[1]);
  1600. }
  1601. };
  1602. class LLOctreeCullVisExtents: public LLOctreeCullShadow
  1603. {
  1604. public:
  1605. LLOctreeCullVisExtents(LLCamera* camera, LLVector3& min, LLVector3& max)
  1606. : LLOctreeCullShadow(camera), mMin(min), mMax(max), mEmpty(TRUE) { }
  1607. virtual bool earlyFail(LLSpatialGroup* group)
  1608. {
  1609. if (group->mOctreeNode->getParent() && //never occlusion cull the root node
  1610. LLPipeline::sUseOcclusion && //ignore occlusion if disabled
  1611. group->isOcclusionState(LLSpatialGroup::OCCLUDED))
  1612. {
  1613. return true;
  1614. }
  1615. return false;
  1616. }
  1617. virtual void traverse(const LLSpatialGroup::OctreeNode* n)
  1618. {
  1619. LLSpatialGroup* group = (LLSpatialGroup*) n->getListener(0);
  1620. if (earlyFail(group))
  1621. {
  1622. return;
  1623. }
  1624. if (mRes == 2)
  1625. {
  1626. //fully in, don't traverse further (won't effect extents
  1627. }
  1628. else if (mRes && group->isState(LLSpatialGroup::SKIP_FRUSTUM_CHECK))
  1629. { //don't need to do frustum check
  1630. LLSpatialGroup::OctreeTraveler::traverse(n);
  1631. }
  1632. else
  1633. {  
  1634. mRes = frustumCheck(group);
  1635. if (mRes)
  1636. { //at least partially in, run on down
  1637. LLSpatialGroup::OctreeTraveler::traverse(n);
  1638. }
  1639. mRes = 0;
  1640. }
  1641. }
  1642. virtual void processGroup(LLSpatialGroup* group)
  1643. {
  1644. if (group->isState(LLSpatialGroup::DIRTY) || group->getData().empty())
  1645. {
  1646. llerrs << "WTF?" << llendl;
  1647. }
  1648. if (mRes < 2)
  1649. {
  1650. if (mCamera->AABBInFrustum(group->mObjectBounds[0], group->mObjectBounds[1]) > 0)
  1651. {
  1652. mEmpty = FALSE;
  1653. update_min_max(mMin, mMax, group->mObjectExtents[0]);
  1654. update_min_max(mMin, mMax, group->mObjectExtents[1]);
  1655. }
  1656. }
  1657. else
  1658. {
  1659. mEmpty = FALSE;
  1660. update_min_max(mMin, mMax, group->mExtents[0]);
  1661. update_min_max(mMin, mMax, group->mExtents[1]);
  1662. }
  1663. }
  1664. BOOL mEmpty;
  1665. LLVector3& mMin;
  1666. LLVector3& mMax;
  1667. };
  1668. class LLOctreeCullDetectVisible: public LLOctreeCullShadow
  1669. {
  1670. public:
  1671. LLOctreeCullDetectVisible(LLCamera* camera)
  1672. : LLOctreeCullShadow(camera), mResult(FALSE) { }
  1673. virtual bool earlyFail(LLSpatialGroup* group)
  1674. {
  1675. if (mResult || //already found a node, don't check any more
  1676. (group->mOctreeNode->getParent() && //never occlusion cull the root node
  1677.  LLPipeline::sUseOcclusion && //ignore occlusion if disabled
  1678.  group->isOcclusionState(LLSpatialGroup::OCCLUDED)))
  1679. {
  1680. return true;
  1681. }
  1682. return false;
  1683. }
  1684. virtual void processGroup(LLSpatialGroup* group)
  1685. {
  1686. if (group->isVisible())
  1687. {
  1688. mResult = TRUE;
  1689. }
  1690. }
  1691. BOOL mResult;
  1692. };
  1693. class LLOctreeSelect : public LLOctreeCull
  1694. {
  1695. public:
  1696. LLOctreeSelect(LLCamera* camera, std::vector<LLDrawable*>* results)
  1697. : LLOctreeCull(camera), mResults(results) { }
  1698. virtual bool earlyFail(LLSpatialGroup* group) { return false; }
  1699. virtual void preprocess(LLSpatialGroup* group) { }
  1700. virtual void processGroup(LLSpatialGroup* group)
  1701. {
  1702. LLSpatialGroup::OctreeNode* branch = group->mOctreeNode;
  1703. for (LLSpatialGroup::OctreeNode::const_element_iter i = branch->getData().begin(); i != branch->getData().end(); ++i)
  1704. {
  1705. LLDrawable* drawable = *i;
  1706. if (!drawable->isDead())
  1707. {
  1708. if (drawable->isSpatialBridge())
  1709. {
  1710. drawable->setVisible(*mCamera, mResults, TRUE);
  1711. }
  1712. else
  1713. {
  1714. mResults->push_back(drawable);
  1715. }
  1716. }
  1717. }
  1718. }
  1719. std::vector<LLDrawable*>* mResults;
  1720. };
  1721. void drawBox(const LLVector3& c, const LLVector3& r)
  1722. {
  1723. gGL.begin(LLRender::TRIANGLE_STRIP);
  1724. //left front
  1725. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,1,-1))).mV);
  1726. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,1,1))).mV);
  1727. //right front
  1728. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,1,-1))).mV);
  1729. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,1,1))).mV);
  1730. //right back
  1731.   gGL.vertex3fv((c+r.scaledVec(LLVector3(1,-1,-1))).mV);
  1732. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,-1,1))).mV);
  1733. //left back
  1734. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,-1,-1))).mV);
  1735. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,-1,1))).mV);
  1736. //left front
  1737. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,1,-1))).mV);
  1738. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,1,1))).mV);
  1739. gGL.end();
  1740. //bottom
  1741. gGL.begin(LLRender::TRIANGLE_STRIP);
  1742. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,1,-1))).mV);
  1743. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,-1,-1))).mV);
  1744. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,1,-1))).mV);
  1745. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,-1,-1))).mV);
  1746. gGL.end();
  1747. //top
  1748. gGL.begin(LLRender::TRIANGLE_STRIP);
  1749. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,1,1))).mV);
  1750. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,1,1))).mV);
  1751. gGL.vertex3fv((c+r.scaledVec(LLVector3(1,-1,1))).mV);
  1752. gGL.vertex3fv((c+r.scaledVec(LLVector3(-1,-1,1))).mV);
  1753. gGL.end();
  1754. }
  1755. void drawBoxOutline(const LLVector3& pos, const LLVector3& size)
  1756. {
  1757. LLVector3 v1 = size.scaledVec(LLVector3( 1, 1,1));
  1758. LLVector3 v2 = size.scaledVec(LLVector3(-1, 1,1));
  1759. LLVector3 v3 = size.scaledVec(LLVector3(-1,-1,1));
  1760. LLVector3 v4 = size.scaledVec(LLVector3( 1,-1,1));
  1761. gGL.begin(LLRender::LINES); 
  1762. //top
  1763. gGL.vertex3fv((pos+v1).mV);
  1764. gGL.vertex3fv((pos+v2).mV);
  1765. gGL.vertex3fv((pos+v2).mV);
  1766. gGL.vertex3fv((pos+v3).mV);
  1767. gGL.vertex3fv((pos+v3).mV);
  1768. gGL.vertex3fv((pos+v4).mV);
  1769. gGL.vertex3fv((pos+v4).mV);
  1770. gGL.vertex3fv((pos+v1).mV);
  1771. //bottom
  1772. gGL.vertex3fv((pos-v1).mV);
  1773. gGL.vertex3fv((pos-v2).mV);
  1774. gGL.vertex3fv((pos-v2).mV);
  1775. gGL.vertex3fv((pos-v3).mV);
  1776. gGL.vertex3fv((pos-v3).mV);
  1777. gGL.vertex3fv((pos-v4).mV);
  1778. gGL.vertex3fv((pos-v4).mV);
  1779. gGL.vertex3fv((pos-v1).mV);
  1780. //right
  1781. gGL.vertex3fv((pos+v1).mV);
  1782. gGL.vertex3fv((pos-v3).mV);
  1783. gGL.vertex3fv((pos+v4).mV);
  1784. gGL.vertex3fv((pos-v2).mV);
  1785. //left
  1786. gGL.vertex3fv((pos+v2).mV);
  1787. gGL.vertex3fv((pos-v4).mV);
  1788. gGL.vertex3fv((pos+v3).mV);
  1789. gGL.vertex3fv((pos-v1).mV);
  1790. gGL.end();
  1791. }
  1792. class LLOctreeDirty : public LLOctreeTraveler<LLDrawable>
  1793. {
  1794. public:
  1795. virtual void visit(const LLOctreeNode<LLDrawable>* state)
  1796. {
  1797. LLSpatialGroup* group = (LLSpatialGroup*) state->getListener(0);
  1798. group->destroyGL();
  1799. for (LLSpatialGroup::element_iter i = group->getData().begin(); i != group->getData().end(); ++i)
  1800. {
  1801. LLDrawable* drawable = *i;
  1802. if (drawable->getVObj().notNull() && !group->mSpatialPartition->mRenderByGroup)
  1803. {
  1804. gPipeline.markRebuild(drawable, LLDrawable::REBUILD_ALL, TRUE);
  1805. }
  1806. }
  1807. for (LLSpatialGroup::bridge_list_t::iterator i = group->mBridgeList.begin(); i != group->mBridgeList.end(); ++i)
  1808. {
  1809. LLSpatialBridge* bridge = *i;
  1810. traverse(bridge->mOctree);
  1811. }
  1812. }
  1813. };
  1814. void LLSpatialPartition::restoreGL()
  1815. {
  1816. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1817. }
  1818. void LLSpatialPartition::resetVertexBuffers()
  1819. {
  1820. LLOctreeDirty dirty;
  1821. dirty.traverse(mOctree);
  1822. }
  1823. BOOL LLSpatialPartition::isOcclusionEnabled()
  1824. {
  1825. return mOcclusionEnabled || LLPipeline::sUseOcclusion > 2;
  1826. }
  1827. BOOL LLSpatialPartition::getVisibleExtents(LLCamera& camera, LLVector3& visMin, LLVector3& visMax)
  1828. {
  1829. {
  1830. LLFastTimer ftm(FTM_CULL_REBOUND);
  1831. LLSpatialGroup* group = (LLSpatialGroup*) mOctree->getListener(0);
  1832. group->rebound();
  1833. }
  1834. LLOctreeCullVisExtents vis(&camera, visMin, visMax);
  1835. vis.traverse(mOctree);
  1836. return vis.mEmpty;
  1837. }
  1838. BOOL LLSpatialPartition::visibleObjectsInFrustum(LLCamera& camera)
  1839. {
  1840. LLOctreeCullDetectVisible vis(&camera);
  1841. vis.traverse(mOctree);
  1842. return vis.mResult;
  1843. }
  1844. S32 LLSpatialPartition::cull(LLCamera &camera, std::vector<LLDrawable *>* results, BOOL for_select)
  1845. {
  1846. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  1847. #if LL_OCTREE_PARANOIA_CHECK
  1848. ((LLSpatialGroup*)mOctree->getListener(0))->checkStates();
  1849. #endif
  1850. {
  1851. LLFastTimer ftm(FTM_CULL_REBOUND);
  1852. LLSpatialGroup* group = (LLSpatialGroup*) mOctree->getListener(0);
  1853. group->rebound();
  1854. }
  1855. #if LL_OCTREE_PARANOIA_CHECK
  1856. ((LLSpatialGroup*)mOctree->getListener(0))->validate();
  1857. #endif
  1858. if (for_select)
  1859. {
  1860. LLOctreeSelect selecter(&camera, results);
  1861. selecter.traverse(mOctree);
  1862. }
  1863. else if (LLPipeline::sShadowRender)
  1864. {
  1865. LLFastTimer ftm(FTM_FRUSTUM_CULL);
  1866. LLOctreeCullShadow culler(&camera);
  1867. culler.traverse(mOctree);
  1868. }
  1869. else if (mInfiniteFarClip || !LLPipeline::sUseFarClip)
  1870. {
  1871. LLFastTimer ftm(FTM_FRUSTUM_CULL);
  1872. LLOctreeCullNoFarClip culler(&camera);
  1873. culler.traverse(mOctree);
  1874. }
  1875. else
  1876. {
  1877. LLFastTimer ftm(FTM_FRUSTUM_CULL);
  1878. LLOctreeCull culler(&camera);
  1879. culler.traverse(mOctree);
  1880. }
  1881. return 0;
  1882. }
  1883. BOOL earlyFail(LLCamera* camera, LLSpatialGroup* group)
  1884. {
  1885. if (camera->getOrigin().isExactlyZero())
  1886. {
  1887. return FALSE;
  1888. }
  1889. const F32 vel = SG_OCCLUSION_FUDGE*2.f;
  1890. LLVector3 c = group->mBounds[0];
  1891. LLVector3 r = group->mBounds[1] + LLVector3(vel,vel,vel);
  1892.     
  1893. /*if (r.magVecSquared() > 1024.0*1024.0)
  1894. {
  1895. return TRUE;
  1896. }*/
  1897. LLVector3 e = camera->getOrigin();
  1898. LLVector3 min = c - r;
  1899. LLVector3 max = c + r;
  1900. for (U32 j = 0; j < 3; j++)
  1901. {
  1902. if (e.mV[j] < min.mV[j] || e.mV[j] > max.mV[j])
  1903. {
  1904. return FALSE;
  1905. }
  1906. }
  1907. return TRUE;
  1908. }
  1909. void pushVerts(LLDrawInfo* params, U32 mask)
  1910. {
  1911. LLRenderPass::applyModelMatrix(*params);
  1912. params->mVertexBuffer->setBuffer(mask);
  1913. params->mVertexBuffer->drawRange(params->mParticle ? LLRender::POINTS : LLRender::TRIANGLES,
  1914. params->mStart, params->mEnd, params->mCount, params->mOffset);
  1915. }
  1916. void pushVerts(LLSpatialGroup* group, U32 mask)
  1917. {
  1918. LLDrawInfo* params = NULL;
  1919. for (LLSpatialGroup::draw_map_t::iterator i = group->mDrawMap.begin(); i != group->mDrawMap.end(); ++i)
  1920. {
  1921. for (LLSpatialGroup::drawmap_elem_t::iterator j = i->second.begin(); j != i->second.end(); ++j) 
  1922. {
  1923. params = *j;
  1924. pushVerts(params, mask);
  1925. }
  1926. }
  1927. }
  1928. void pushVerts(LLFace* face, U32 mask)
  1929. {
  1930. LLVertexBuffer* buffer = face->mVertexBuffer;
  1931. if (buffer)
  1932. {
  1933. buffer->setBuffer(mask);
  1934. U16 start = face->getGeomStart();
  1935. U16 end = start + face->getGeomCount()-1;
  1936. U32 count = face->getIndicesCount();
  1937. U16 offset = face->getIndicesStart();
  1938. buffer->drawRange(LLRender::TRIANGLES, start, end, count, offset);
  1939. }
  1940. }
  1941. void pushBufferVerts(LLVertexBuffer* buffer, U32 mask)
  1942. {
  1943. if (buffer)
  1944. {
  1945. buffer->setBuffer(mask);
  1946. buffer->drawRange(LLRender::TRIANGLES, 0, buffer->getRequestedVerts()-1, buffer->getRequestedIndices(), 0);
  1947. }
  1948. }
  1949. void pushBufferVerts(LLSpatialGroup* group, U32 mask)
  1950. {
  1951. if (group->mSpatialPartition->mRenderByGroup)
  1952. {
  1953. if (!group->mDrawMap.empty())
  1954. {
  1955. LLDrawInfo* params = *(group->mDrawMap.begin()->second.begin());
  1956. LLRenderPass::applyModelMatrix(*params);
  1957. pushBufferVerts(group->mVertexBuffer, mask);
  1958. for (LLSpatialGroup::buffer_map_t::iterator i = group->mBufferMap.begin(); i != group->mBufferMap.end(); ++i)
  1959. {
  1960. for (LLSpatialGroup::buffer_texture_map_t::iterator j = i->second.begin(); j != i->second.end(); ++j)
  1961. {
  1962. for (LLSpatialGroup::buffer_list_t::iterator k = j->second.begin(); k != j->second.end(); ++k)
  1963. {
  1964. pushBufferVerts(*k, mask);
  1965. }
  1966. }
  1967. }
  1968. }
  1969. }
  1970. else
  1971. {
  1972. drawBox(group->mBounds[0], group->mBounds[1]);
  1973. }
  1974. }
  1975. void pushVertsColorCoded(LLSpatialGroup* group, U32 mask)
  1976. {
  1977. LLDrawInfo* params = NULL;
  1978. LLColor4 colors[] = {
  1979. LLColor4::green,
  1980. LLColor4::green1,
  1981. LLColor4::green2,
  1982. LLColor4::green3,
  1983. LLColor4::green4,
  1984. LLColor4::green5,
  1985. LLColor4::green6
  1986. };
  1987. static const U32 col_count = LL_ARRAY_SIZE(colors);
  1988. U32 col = 0;
  1989. for (LLSpatialGroup::draw_map_t::iterator i = group->mDrawMap.begin(); i != group->mDrawMap.end(); ++i)
  1990. {
  1991. for (LLSpatialGroup::drawmap_elem_t::iterator j = i->second.begin(); j != i->second.end(); ++j) 
  1992. {
  1993. params = *j;
  1994. LLRenderPass::applyModelMatrix(*params);
  1995. glColor4f(colors[col].mV[0], colors[col].mV[1], colors[col].mV[2], 0.5f);
  1996. params->mVertexBuffer->setBuffer(mask);
  1997. params->mVertexBuffer->drawRange(params->mParticle ? LLRender::POINTS : LLRender::TRIANGLES,
  1998. params->mStart, params->mEnd, params->mCount, params->mOffset);
  1999. col = (col+1)%col_count;
  2000. }
  2001. }
  2002. }
  2003. void renderOctree(LLSpatialGroup* group)
  2004. {
  2005. //render solid object bounding box, color
  2006. //coded by buffer usage and activity
  2007. LLGLDepthTest depth(GL_TRUE, GL_FALSE);
  2008. gGL.setSceneBlendType(LLRender::BT_ADD_WITH_ALPHA);
  2009. LLVector4 col;
  2010. if (group->mBuilt > 0.f)
  2011. {
  2012. group->mBuilt -= 2.f * gFrameIntervalSeconds;
  2013. if (group->mBufferUsage == GL_STATIC_DRAW_ARB)
  2014. {
  2015. col.setVec(1.0f, 0, 0, group->mBuilt*0.5f);
  2016. }
  2017. else 
  2018. {
  2019. col.setVec(0.1f,0.1f,1,0.1f);
  2020. //col.setVec(1.0f, 1.0f, 0, sinf(group->mBuilt*3.14159f)*0.5f);
  2021. }
  2022. if (group->mBufferUsage != GL_STATIC_DRAW_ARB)
  2023. {
  2024. LLGLDepthTest gl_depth(FALSE, FALSE);
  2025. glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
  2026. gGL.color4f(1,0,0,group->mBuilt);
  2027. gGL.flush();
  2028. glLineWidth(5.f);
  2029. drawBoxOutline(group->mObjectBounds[0], group->mObjectBounds[1]);
  2030. gGL.flush();
  2031. glLineWidth(1.f);
  2032. gGL.flush();
  2033. for (LLSpatialGroup::element_iter i = group->getData().begin(); i != group->getData().end(); ++i)
  2034. {
  2035. LLDrawable* drawable = *i;
  2036. if (!group->mSpatialPartition->isBridge())
  2037. {
  2038. glPushMatrix();
  2039. LLVector3 trans = drawable->getRegion()->getOriginAgent();
  2040. glTranslatef(trans.mV[0], trans.mV[1], trans.mV[2]);
  2041. }
  2042. for (S32 j = 0; j < drawable->getNumFaces(); j++)
  2043. {
  2044. LLFace* face = drawable->getFace(j);
  2045. if (face->mVertexBuffer.notNull())
  2046. {
  2047. if (gFrameTimeSeconds - face->mLastUpdateTime < 0.5f)
  2048. {
  2049. glColor4f(0, 1, 0, group->mBuilt);
  2050. }
  2051. else if (gFrameTimeSeconds - face->mLastMoveTime < 0.5f)
  2052. {
  2053. glColor4f(1, 0, 0, group->mBuilt);
  2054. }
  2055. else
  2056. {
  2057. continue;
  2058. }
  2059. face->mVertexBuffer->setBuffer(LLVertexBuffer::MAP_VERTEX);
  2060. //drawBox((face->mExtents[0] + face->mExtents[1])*0.5f,
  2061. // (face->mExtents[1]-face->mExtents[0])*0.5f);
  2062. face->mVertexBuffer->draw(LLRender::TRIANGLES, face->getIndicesCount(), face->getIndicesStart());
  2063. }
  2064. }
  2065. if (!group->mSpatialPartition->isBridge())
  2066. {
  2067. glPopMatrix();
  2068. }
  2069. }
  2070. glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
  2071. gGL.color4f(1,1,1,1);
  2072. }
  2073. }
  2074. else
  2075. {
  2076. if (group->mBufferUsage == GL_STATIC_DRAW_ARB && !group->getData().empty() 
  2077. && group->mSpatialPartition->mRenderByGroup)
  2078. {
  2079. col.setVec(0.8f, 0.4f, 0.1f, 0.1f);
  2080. }
  2081. else
  2082. {
  2083. col.setVec(0.1f, 0.1f, 1.f, 0.1f);
  2084. }
  2085. }
  2086. gGL.color4fv(col.mV);
  2087. drawBox(group->mObjectBounds[0], group->mObjectBounds[1]*1.01f+LLVector3(0.001f, 0.001f, 0.001f));
  2088. gGL.setSceneBlendType(LLRender::BT_ALPHA);
  2089. if (group->mBuilt <= 0.f)
  2090. {
  2091. //draw opaque outline
  2092. gGL.color4f(col.mV[0], col.mV[1], col.mV[2], 1.f);
  2093. drawBoxOutline(group->mObjectBounds[0], group->mObjectBounds[1]);
  2094. if (group->mOctreeNode->isLeaf())
  2095. {
  2096. gGL.color4f(1,1,1,1);
  2097. }
  2098. else
  2099. {
  2100. gGL.color4f(0,1,1,1);
  2101. }
  2102. drawBoxOutline(group->mBounds[0],group->mBounds[1]);
  2103. //draw bounding box for draw info
  2104. if (group->mSpatialPartition->mRenderByGroup)
  2105. {
  2106. gGL.color4f(1.0f, 0.75f, 0.25f, 0.6f);
  2107. for (LLSpatialGroup::draw_map_t::iterator i = group->mDrawMap.begin(); i != group->mDrawMap.end(); ++i)
  2108. {
  2109. for (LLSpatialGroup::drawmap_elem_t::iterator j = i->second.begin(); j != i->second.end(); ++j)
  2110. {
  2111. LLDrawInfo* draw_info = *j;
  2112. LLVector3 center = (draw_info->mExtents[1] + draw_info->mExtents[0])*0.5f;
  2113. LLVector3 size = (draw_info->mExtents[1] - draw_info->mExtents[0])*0.5f;
  2114. drawBoxOutline(center, size);
  2115. }
  2116. }
  2117. }
  2118. }
  2119. // LLSpatialGroup::OctreeNode* node = group->mOctreeNode;
  2120. // gGL.color4f(0,1,0,1);
  2121. // drawBoxOutline(LLVector3(node->getCenter()), LLVector3(node->getSize()));
  2122. }
  2123. void renderVisibility(LLSpatialGroup* group, LLCamera* camera)
  2124. {
  2125. LLGLEnable blend(GL_BLEND);
  2126. gGL.setSceneBlendType(LLRender::BT_ALPHA);
  2127. LLGLEnable cull(GL_CULL_FACE);
  2128. glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
  2129. BOOL render_objects = (!LLPipeline::sUseOcclusion || !group->isOcclusionState(LLSpatialGroup::OCCLUDED)) && group->isVisible() &&
  2130. !group->getData().empty();
  2131. if (render_objects)
  2132. {
  2133. LLGLDepthTest depth_under(GL_TRUE, GL_FALSE, GL_GREATER);
  2134. glColor4f(0, 0.5f, 0, 0.5f);
  2135. gGL.color4f(0, 0.5f, 0, 0.5f);
  2136. pushBufferVerts(group, LLVertexBuffer::MAP_VERTEX);
  2137. }
  2138. {
  2139. LLGLDepthTest depth_over(GL_TRUE, GL_FALSE, GL_LEQUAL);
  2140. if (render_objects)
  2141. {
  2142. glColor4f(0.f, 0.5f, 0.f,1.f);
  2143. gGL.color4f(0.f, 0.5f, 0.f, 1.f);
  2144. pushBufferVerts(group, LLVertexBuffer::MAP_VERTEX);
  2145. }
  2146. glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
  2147. if (render_objects)
  2148. {
  2149. glColor4f(0.f, 0.75f, 0.f,0.5f);
  2150. gGL.color4f(0.f, 0.75f, 0.f, 0.5f);
  2151. pushBufferVerts(group, LLVertexBuffer::MAP_VERTEX);
  2152. }
  2153. else if (camera && group->mOcclusionVerts)
  2154. {
  2155. LLVertexBuffer::unbind();
  2156. glVertexPointer(3, GL_FLOAT, 0, group->mOcclusionVerts);
  2157. glColor4f(1.0f, 0.f, 0.f, 0.5f);
  2158. glDrawRangeElements(GL_TRIANGLE_FAN, 0, 7, 8, GL_UNSIGNED_BYTE, get_box_fan_indices(camera, group->mBounds[0]));
  2159. glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
  2160. glColor4f(1.0f, 1.f, 1.f, 1.0f);
  2161. glDrawRangeElements(GL_TRIANGLE_FAN, 0, 7, 8, GL_UNSIGNED_BYTE, get_box_fan_indices(camera, group->mBounds[0]));
  2162. glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
  2163. }
  2164. }
  2165. }
  2166. void renderCrossHairs(LLVector3 position, F32 size, LLColor4 color)
  2167. {
  2168. gGL.color4fv(color.mV);
  2169. gGL.begin(LLRender::LINES);
  2170. {
  2171. gGL.vertex3fv((position - LLVector3(size, 0.f, 0.f)).mV);
  2172. gGL.vertex3fv((position + LLVector3(size, 0.f, 0.f)).mV);
  2173. gGL.vertex3fv((position - LLVector3(0.f, size, 0.f)).mV);
  2174. gGL.vertex3fv((position + LLVector3(0.f, size, 0.f)).mV);
  2175. gGL.vertex3fv((position - LLVector3(0.f, 0.f, size)).mV);
  2176. gGL.vertex3fv((position + LLVector3(0.f, 0.f, size)).mV);
  2177. }
  2178. gGL.end();
  2179. }
  2180. void renderBoundingBox(LLDrawable* drawable, BOOL set_color = TRUE)
  2181. {
  2182. if (set_color)
  2183. {
  2184. if (drawable->isSpatialBridge())
  2185. {
  2186. gGL.color4f(1,0.5f,0,1);
  2187. }
  2188. else if (drawable->getVOVolume())
  2189. {
  2190. if (drawable->isRoot())
  2191. {
  2192. gGL.color4f(1,1,0,1);
  2193. }
  2194. else
  2195. {
  2196. gGL.color4f(0,1,0,1);
  2197. }
  2198. }
  2199. else if (drawable->getVObj())
  2200. {
  2201. switch (drawable->getVObj()->getPCode())
  2202. {
  2203. case LLViewerObject::LL_VO_SURFACE_PATCH:
  2204. gGL.color4f(0,1,1,1);
  2205. break;
  2206. case LLViewerObject::LL_VO_CLOUDS:
  2207. gGL.color4f(0.5f,0.5f,0.5f,1.0f);
  2208. break;
  2209. case LLViewerObject::LL_VO_PART_GROUP:
  2210. case LLViewerObject::LL_VO_HUD_PART_GROUP:
  2211. gGL.color4f(0,0,1,1);
  2212. break;
  2213. case LLViewerObject::LL_VO_WATER:
  2214. gGL.color4f(0,0.5f,1,1);
  2215. break;
  2216. case LL_PCODE_LEGACY_TREE:
  2217. gGL.color4f(0,0.5f,0,1);
  2218. break;
  2219. default:
  2220. gGL.color4f(1,0,1,1);
  2221. break;
  2222. }
  2223. }
  2224. else 
  2225. {
  2226. gGL.color4f(1,0,0,1);
  2227. }
  2228. }
  2229. const LLVector3* ext;
  2230. LLVector3 pos, size;
  2231. //render face bounding boxes
  2232. for (S32 i = 0; i < drawable->getNumFaces(); i++)
  2233. {
  2234. LLFace* facep = drawable->getFace(i);
  2235. ext = facep->mExtents;
  2236. if (ext[0].isExactlyZero() && ext[1].isExactlyZero())
  2237. {
  2238. continue;
  2239. }
  2240. pos = (ext[0] + ext[1]) * 0.5f;
  2241. size = (ext[1] - ext[0]) * 0.5f;
  2242. drawBoxOutline(pos,size);
  2243. }
  2244. //render drawable bounding box
  2245. ext = drawable->getSpatialExtents();
  2246. pos = (ext[0] + ext[1]) * 0.5f;
  2247. size = (ext[1] - ext[0]) * 0.5f;
  2248. LLViewerObject* vobj = drawable->getVObj();
  2249. if (vobj && vobj->onActiveList())
  2250. {
  2251. gGL.flush();
  2252. glLineWidth(llmax(4.f*sinf(gFrameTimeSeconds*2.f)+1.f, 1.f));
  2253. //glLineWidth(4.f*(sinf(gFrameTimeSeconds*2.f)*0.25f+0.75f));
  2254. stop_glerror();
  2255. drawBoxOutline(pos,size);
  2256. gGL.flush();
  2257. glLineWidth(1.f);
  2258. }
  2259. else
  2260. {
  2261. drawBoxOutline(pos,size);
  2262. }
  2263. }
  2264. void renderTexturePriority(LLDrawable* drawable)
  2265. {
  2266. for (int face=0; face<drawable->getNumFaces(); ++face)
  2267. {
  2268. LLFace *facep = drawable->getFace(face);
  2269. LLVector4 cold(0,0,0.25f);
  2270. LLVector4 hot(1,0.25f,0.25f);
  2271. LLVector4 boost_cold(0,0,0,0);
  2272. LLVector4 boost_hot(0,1,0,1);
  2273. LLGLDisable blend(GL_BLEND);
  2274. //LLViewerTexture* imagep = facep->getTexture();
  2275. //if (imagep)
  2276. {
  2277. //F32 vsize = imagep->mMaxVirtualSize;
  2278. F32 vsize = facep->getPixelArea();
  2279. if (vsize > sCurMaxTexPriority)
  2280. {
  2281. sCurMaxTexPriority = vsize;
  2282. }
  2283. F32 t = vsize/sLastMaxTexPriority;
  2284. LLVector4 col = lerp(cold, hot, t);
  2285. gGL.color4fv(col.mV);
  2286. }
  2287. //else
  2288. //{
  2289. // gGL.color4f(1,0,1,1);
  2290. //}
  2291. LLVector3 center = (facep->mExtents[1]+facep->mExtents[0])*0.5f;
  2292. LLVector3 size = (facep->mExtents[1]-facep->mExtents[0])*0.5f + LLVector3(0.01f, 0.01f, 0.01f);
  2293. drawBox(center, size);
  2294. /*S32 boost = imagep->getBoostLevel();
  2295. if (boost>LLViewerTexture::BOOST_NONE)
  2296. {
  2297. F32 t = (F32) boost / (F32) (LLViewerTexture::BOOST_MAX_LEVEL-1);
  2298. LLVector4 col = lerp(boost_cold, boost_hot, t);
  2299. LLGLEnable blend_on(GL_BLEND);
  2300. gGL.blendFunc(GL_SRC_ALPHA, GL_ONE);
  2301. gGL.color4fv(col.mV);
  2302. drawBox(center, size);
  2303. gGL.blendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
  2304. }*/
  2305. }
  2306. }
  2307. void renderPoints(LLDrawable* drawablep)
  2308. {
  2309. LLGLDepthTest depth(GL_FALSE, GL_FALSE);
  2310. if (drawablep->getNumFaces())
  2311. {
  2312. gGL.begin(LLRender::POINTS);
  2313. gGL.color3f(1,1,1);
  2314. LLVector3 center(drawablep->getPositionGroup());
  2315. for (S32 i = 0; i < drawablep->getNumFaces(); i++)
  2316. {
  2317. gGL.vertex3fv(drawablep->getFace(i)->mCenterLocal.mV);
  2318. }
  2319. gGL.end();
  2320. }
  2321. }
  2322. void renderTextureAnim(LLDrawInfo* params)
  2323. {
  2324. if (!params->mTextureMatrix)
  2325. {
  2326. return;
  2327. }
  2328. LLGLEnable blend(GL_BLEND);
  2329. glColor4f(1,1,0,0.5f);
  2330. pushVerts(params, LLVertexBuffer::MAP_VERTEX);
  2331. }
  2332. void renderBatchSize(LLDrawInfo* params)
  2333. {
  2334. glColor3ubv((GLubyte*) &(params->mDebugColor));
  2335. pushVerts(params, LLVertexBuffer::MAP_VERTEX);
  2336. }
  2337. void renderShadowFrusta(LLDrawInfo* params)
  2338. {
  2339. LLGLEnable blend(GL_BLEND);
  2340. gGL.setSceneBlendType(LLRender::BT_ADD);
  2341. LLVector3 center = (params->mExtents[1]+params->mExtents[0])*0.5f;
  2342. LLVector3 size = (params->mExtents[1]-params->mExtents[0])*0.5f;
  2343. if (gPipeline.mShadowCamera[4].AABBInFrustum(center, size))
  2344. {
  2345. glColor3f(1,0,0);
  2346. pushVerts(params, LLVertexBuffer::MAP_VERTEX);
  2347. }
  2348. if (gPipeline.mShadowCamera[5].AABBInFrustum(center, size))
  2349. {
  2350. glColor3f(0,1,0);
  2351. pushVerts(params, LLVertexBuffer::MAP_VERTEX);
  2352. }
  2353. if (gPipeline.mShadowCamera[6].AABBInFrustum(center, size))
  2354. {
  2355. glColor3f(0,0,1);
  2356. pushVerts(params, LLVertexBuffer::MAP_VERTEX);
  2357. }
  2358. if (gPipeline.mShadowCamera[7].AABBInFrustum(center, size))
  2359. {
  2360. glColor3f(1,0,1);
  2361. pushVerts(params, LLVertexBuffer::MAP_VERTEX);
  2362. }
  2363. gGL.setSceneBlendType(LLRender::BT_ALPHA);
  2364. }
  2365. void renderLights(LLDrawable* drawablep)
  2366. {
  2367. if (!drawablep->isLight())
  2368. {
  2369. return;
  2370. }
  2371. if (drawablep->getNumFaces())
  2372. {
  2373. LLGLEnable blend(GL_BLEND);
  2374. glColor4f(0,1,1,0.5f);
  2375. for (S32 i = 0; i < drawablep->getNumFaces(); i++)
  2376. {
  2377. pushVerts(drawablep->getFace(i), LLVertexBuffer::MAP_VERTEX);
  2378. }
  2379. const LLVector3* ext = drawablep->getSpatialExtents();
  2380. LLVector3 pos = (ext[0] + ext[1]) * 0.5f;
  2381. LLVector3 size = (ext[1] - ext[0]) * 0.5f;
  2382. {
  2383. LLGLDepthTest depth(GL_FALSE, GL_TRUE);
  2384. gGL.color4f(1,1,1,1);
  2385. drawBoxOutline(pos, size);
  2386. }
  2387. gGL.color4f(1,1,0,1);
  2388. F32 rad = drawablep->getVOVolume()->getLightRadius();
  2389. drawBoxOutline(pos, LLVector3(rad,rad,rad));
  2390. }
  2391. }
  2392. void renderRaycast(LLDrawable* drawablep)
  2393. {
  2394. if (drawablep->getVObj() != gDebugRaycastObject)
  2395. {
  2396. return;
  2397. }
  2398. if (drawablep->getNumFaces())
  2399. {
  2400. LLGLEnable blend(GL_BLEND);
  2401. gGL.color4f(0,1,1,0.5f);
  2402. if (drawablep->getVOVolume() && gDebugRaycastFaceHit != -1)
  2403. {
  2404. glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
  2405. pushVerts(drawablep->getFace(gDebugRaycastFaceHit), LLVertexBuffer::MAP_VERTEX);
  2406. glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
  2407. }
  2408. else if (drawablep->isAvatar())
  2409. {
  2410. LLGLDepthTest depth(GL_FALSE);
  2411. LLVOAvatar* av = (LLVOAvatar*) drawablep->getVObj().get();
  2412. av->renderCollisionVolumes();
  2413. }
  2414. // draw intersection point
  2415. glPushMatrix();
  2416. glLoadMatrixd(gGLModelView);
  2417. LLVector3 translate = gDebugRaycastIntersection;
  2418. glTranslatef(translate.mV[0], translate.mV[1], translate.mV[2]);
  2419. LLCoordFrame orient;
  2420. orient.lookDir(gDebugRaycastNormal, gDebugRaycastBinormal);
  2421. LLMatrix4 rotation;
  2422. orient.getRotMatrixToParent(rotation);
  2423. glMultMatrixf((float*)rotation.mMatrix);
  2424. gGL.color4f(1,0,0,0.5f);
  2425. drawBox(LLVector3(0, 0, 0), LLVector3(0.1f, 0.022f, 0.022f));
  2426. gGL.color4f(0,1,0,0.5f);
  2427. drawBox(LLVector3(0, 0, 0), LLVector3(0.021f, 0.1f, 0.021f));
  2428. gGL.color4f(0,0,1,0.5f);
  2429. drawBox(LLVector3(0, 0, 0), LLVector3(0.02f, 0.02f, 0.1f));
  2430. glPopMatrix();
  2431. // draw bounding box of prim
  2432. const LLVector3* ext = drawablep->getSpatialExtents();
  2433. LLVector3 pos = (ext[0] + ext[1]) * 0.5f;
  2434. LLVector3 size = (ext[1] - ext[0]) * 0.5f;
  2435. LLGLDepthTest depth(GL_FALSE, GL_TRUE);
  2436. gGL.color4f(0,0.5f,0.5f,1);
  2437. drawBoxOutline(pos, size);
  2438. }
  2439. }
  2440. void renderAvatarCollisionVolumes(LLVOAvatar* avatar)
  2441. {
  2442. avatar->renderCollisionVolumes();
  2443. }
  2444. void renderAgentTarget(LLVOAvatar* avatar)
  2445. {
  2446. // render these for self only (why, i don't know)
  2447. if (avatar->isSelf())
  2448. {
  2449. renderCrossHairs(avatar->getPositionAgent(), 0.2f, LLColor4(1, 0, 0, 0.8f));
  2450. renderCrossHairs(avatar->mDrawable->getPositionAgent(), 0.2f, LLColor4(1, 0, 0, 0.8f));
  2451. renderCrossHairs(avatar->mRoot.getWorldPosition(), 0.2f, LLColor4(1, 1, 1, 0.8f));
  2452. renderCrossHairs(avatar->mPelvisp->getWorldPosition(), 0.2f, LLColor4(0, 0, 1, 0.8f));
  2453. }
  2454. }
  2455. class LLOctreeRenderNonOccluded : public LLOctreeTraveler<LLDrawable>
  2456. {
  2457. public:
  2458. LLCamera* mCamera;
  2459. LLOctreeRenderNonOccluded(LLCamera* camera): mCamera(camera) {}
  2460. virtual void traverse(const LLSpatialGroup::OctreeNode* node)
  2461. {
  2462. LLSpatialGroup* group = (LLSpatialGroup*) node->getListener(0);
  2463. if (!mCamera || mCamera->AABBInFrustumNoFarClip(group->mBounds[0], group->mBounds[1]))
  2464. {
  2465. node->accept(this);
  2466. stop_glerror();
  2467. for (U32 i = 0; i < node->getChildCount(); i++)
  2468. {
  2469. traverse(node->getChild(i));
  2470. stop_glerror();
  2471. }
  2472. //draw tight fit bounding boxes for spatial group
  2473. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCTREE))
  2474. {
  2475. group->rebuildGeom();
  2476. group->rebuildMesh();
  2477. renderOctree(group);
  2478. stop_glerror();
  2479. }
  2480. //render visibility wireframe
  2481. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCCLUSION))
  2482. {
  2483. group->rebuildGeom();
  2484. group->rebuildMesh();
  2485. gGL.flush();
  2486. glPushMatrix();
  2487. gGLLastMatrix = NULL;
  2488. glLoadMatrixd(gGLModelView);
  2489. renderVisibility(group, mCamera);
  2490. stop_glerror();
  2491. gGLLastMatrix = NULL;
  2492. glPopMatrix();
  2493. gGL.color4f(1,1,1,1);
  2494. }
  2495. }
  2496. }
  2497. virtual void visit(const LLSpatialGroup::OctreeNode* branch)
  2498. {
  2499. LLSpatialGroup* group = (LLSpatialGroup*) branch->getListener(0);
  2500. if (group->isState(LLSpatialGroup::GEOM_DIRTY) || (mCamera && !mCamera->AABBInFrustumNoFarClip(group->mBounds[0], group->mBounds[1])))
  2501. {
  2502. return;
  2503. }
  2504. LLVector3 nodeCenter = group->mBounds[0];
  2505. LLVector3 octCenter = LLVector3(group->mOctreeNode->getCenter());
  2506. group->rebuildGeom();
  2507. group->rebuildMesh();
  2508. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_BBOXES))
  2509. {
  2510. if (!group->getData().empty())
  2511. {
  2512. gGL.color3f(0,0,1);
  2513. drawBoxOutline(group->mObjectBounds[0],
  2514. group->mObjectBounds[1]);
  2515. }
  2516. }
  2517. for (LLSpatialGroup::OctreeNode::const_element_iter i = branch->getData().begin(); i != branch->getData().end(); ++i)
  2518. {
  2519. LLDrawable* drawable = *i;
  2520. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_BBOXES))
  2521. {
  2522. renderBoundingBox(drawable);
  2523. }
  2524. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_BUILD_QUEUE))
  2525. {
  2526. if (drawable->isState(LLDrawable::IN_REBUILD_Q2))
  2527. {
  2528. gGL.color4f(0.6f, 0.6f, 0.1f, 1.f);
  2529. const LLVector3* ext = drawable->getSpatialExtents();
  2530. drawBoxOutline((ext[0]+ext[1])*0.5f, (ext[1]-ext[0])*0.5f);
  2531. }
  2532. }
  2533. if (drawable->getVOVolume() && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY))
  2534. {
  2535. renderTexturePriority(drawable);
  2536. }
  2537. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_POINTS))
  2538. {
  2539. renderPoints(drawable);
  2540. }
  2541. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_LIGHTS))
  2542. {
  2543. renderLights(drawable);
  2544. }
  2545. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_RAYCAST))
  2546. {
  2547. renderRaycast(drawable);
  2548. }
  2549. LLVOAvatar* avatar = dynamic_cast<LLVOAvatar*>(drawable->getVObj().get());
  2550. if (avatar && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_AVATAR_VOLUME))
  2551. {
  2552. renderAvatarCollisionVolumes(avatar);
  2553. }
  2554. if (avatar && gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_AGENT_TARGET))
  2555. {
  2556. renderAgentTarget(avatar);
  2557. }
  2558. }
  2559. for (LLSpatialGroup::draw_map_t::iterator i = group->mDrawMap.begin(); i != group->mDrawMap.end(); ++i)
  2560. {
  2561. LLSpatialGroup::drawmap_elem_t& draw_vec = i->second;
  2562. for (LLSpatialGroup::drawmap_elem_t::iterator j = draw_vec.begin(); j != draw_vec.end(); ++j)
  2563. {
  2564. LLDrawInfo* draw_info = *j;
  2565. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_TEXTURE_ANIM))
  2566. {
  2567. renderTextureAnim(draw_info);
  2568. }
  2569. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_BATCH_SIZE))
  2570. {
  2571. renderBatchSize(draw_info);
  2572. }
  2573. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_SHADOW_FRUSTA))
  2574. {
  2575. renderShadowFrusta(draw_info);
  2576. }
  2577. }
  2578. }
  2579. }
  2580. };
  2581. class LLOctreePushBBoxVerts : public LLOctreeTraveler<LLDrawable>
  2582. {
  2583. public:
  2584. LLCamera* mCamera;
  2585. LLOctreePushBBoxVerts(LLCamera* camera): mCamera(camera) {}
  2586. virtual void traverse(const LLSpatialGroup::OctreeNode* node)
  2587. {
  2588. LLSpatialGroup* group = (LLSpatialGroup*) node->getListener(0);
  2589. if (!mCamera || mCamera->AABBInFrustum(group->mBounds[0], group->mBounds[1]))
  2590. {
  2591. node->accept(this);
  2592. for (U32 i = 0; i < node->getChildCount(); i++)
  2593. {
  2594. traverse(node->getChild(i));
  2595. }
  2596. }
  2597. }
  2598. virtual void visit(const LLSpatialGroup::OctreeNode* branch)
  2599. {
  2600. LLSpatialGroup* group = (LLSpatialGroup*) branch->getListener(0);
  2601. if (group->isState(LLSpatialGroup::GEOM_DIRTY) || (mCamera && !mCamera->AABBInFrustumNoFarClip(group->mBounds[0], group->mBounds[1])))
  2602. {
  2603. return;
  2604. }
  2605. for (LLSpatialGroup::OctreeNode::const_element_iter i = branch->getData().begin(); i != branch->getData().end(); ++i)
  2606. {
  2607. LLDrawable* drawable = *i;
  2608. renderBoundingBox(drawable, FALSE);
  2609. }
  2610. }
  2611. };
  2612. void LLSpatialPartition::renderIntersectingBBoxes(LLCamera* camera)
  2613. {
  2614. LLOctreePushBBoxVerts pusher(camera);
  2615. pusher.traverse(mOctree);
  2616. }
  2617. class LLOctreeStateCheck : public LLOctreeTraveler<LLDrawable>
  2618. {
  2619. public:
  2620. U32 mInheritedMask[LLViewerCamera::NUM_CAMERAS];
  2621. LLOctreeStateCheck()
  2622. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  2623. {
  2624. mInheritedMask[i] = 0;
  2625. }
  2626. }
  2627. virtual void traverse(const LLSpatialGroup::OctreeNode* node)
  2628. {
  2629. LLSpatialGroup* group = (LLSpatialGroup*) node->getListener(0);
  2630. node->accept(this);
  2631. U32 temp[LLViewerCamera::NUM_CAMERAS];
  2632. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  2633. {
  2634. temp[i] = mInheritedMask[i];
  2635. mInheritedMask[i] |= group->mOcclusionState[i] & LLSpatialGroup::OCCLUDED; 
  2636. }
  2637. for (U32 i = 0; i < node->getChildCount(); i++)
  2638. {
  2639. traverse(node->getChild(i));
  2640. }
  2641. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  2642. {
  2643. mInheritedMask[i] = temp[i];
  2644. }
  2645. }
  2646. virtual void visit(const LLOctreeNode<LLDrawable>* state)
  2647. {
  2648. LLSpatialGroup* group = (LLSpatialGroup*) state->getListener(0);
  2649. for (U32 i = 0; i < LLViewerCamera::NUM_CAMERAS; i++)
  2650. {
  2651. if (mInheritedMask[i] && !(group->mOcclusionState[i] & mInheritedMask[i]))
  2652. {
  2653. llerrs << "Spatial group failed inherited mask test." << llendl;
  2654. }
  2655. }
  2656. if (group->isState(LLSpatialGroup::DIRTY))
  2657. {
  2658. assert_parent_state(group, LLSpatialGroup::DIRTY);
  2659. }
  2660. }
  2661. void assert_parent_state(LLSpatialGroup* group, U32 state)
  2662. {
  2663. LLSpatialGroup* parent = group->getParent();
  2664. while (parent)
  2665. {
  2666. if (!parent->isState(state))
  2667. {
  2668. llerrs << "Spatial group failed parent state check." << llendl;
  2669. }
  2670. parent = parent->getParent();
  2671. }
  2672. }
  2673. };
  2674. void LLSpatialPartition::renderDebug()
  2675. {
  2676. if (!gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_OCTREE |
  2677.   LLPipeline::RENDER_DEBUG_OCCLUSION |
  2678.   LLPipeline::RENDER_DEBUG_LIGHTS |
  2679.   LLPipeline::RENDER_DEBUG_BATCH_SIZE |
  2680.   LLPipeline::RENDER_DEBUG_BBOXES |
  2681.   LLPipeline::RENDER_DEBUG_POINTS |
  2682.   LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY |
  2683.   LLPipeline::RENDER_DEBUG_TEXTURE_ANIM |
  2684.   LLPipeline::RENDER_DEBUG_RAYCAST |
  2685.   LLPipeline::RENDER_DEBUG_AVATAR_VOLUME |
  2686.   LLPipeline::RENDER_DEBUG_AGENT_TARGET |
  2687.   LLPipeline::RENDER_DEBUG_BUILD_QUEUE |
  2688.   LLPipeline::RENDER_DEBUG_SHADOW_FRUSTA)) 
  2689. {
  2690. return;
  2691. }
  2692. if (gPipeline.hasRenderDebugMask(LLPipeline::RENDER_DEBUG_TEXTURE_PRIORITY))
  2693. {
  2694. //sLastMaxTexPriority = lerp(sLastMaxTexPriority, sCurMaxTexPriority, gFrameIntervalSeconds);
  2695. sLastMaxTexPriority = (F32) LLViewerCamera::getInstance()->getScreenPixelArea();
  2696. sCurMaxTexPriority = 0.f;
  2697. }
  2698. LLMemType mt(LLMemType::MTYPE_SPACE_PARTITION);
  2699. LLGLDisable cullface(GL_CULL_FACE);
  2700. LLGLEnable blend(GL_BLEND);
  2701. gGL.setSceneBlendType(LLRender::BT_ALPHA);
  2702. gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE);
  2703. gPipeline.disableLights();
  2704. LLSpatialBridge* bridge = asBridge();
  2705. LLCamera* camera = LLViewerCamera::getInstance();
  2706. if (bridge)
  2707. {
  2708. camera = NULL;
  2709. }
  2710. LLOctreeStateCheck checker;
  2711. checker.traverse(mOctree);
  2712. LLOctreeRenderNonOccluded render_debug(camera);
  2713. render_debug.traverse(mOctree);
  2714. }
  2715. void LLSpatialGroup::drawObjectBox(LLColor4 col)
  2716. {
  2717. gGL.color4fv(col.mV);
  2718. drawBox(mObjectBounds[0], mObjectBounds[1]*1.01f+LLVector3(0.001f, 0.001f, 0.001f));
  2719. }
  2720. BOOL LLSpatialPartition::isVisible(const LLVector3& v)
  2721. {
  2722. if (!LLViewerCamera::getInstance()->sphereInFrustum(v, 4.0f))
  2723. {
  2724. return FALSE;
  2725. }
  2726. return TRUE;
  2727. }
  2728. class LLOctreeIntersect : public LLSpatialGroup::OctreeTraveler
  2729. {
  2730. public:
  2731. LLVector3 mStart;
  2732. LLVector3 mEnd;
  2733. S32       *mFaceHit;
  2734. LLVector3 *mIntersection;
  2735. LLVector2 *mTexCoord;
  2736. LLVector3 *mNormal;
  2737. LLVector3 *mBinormal;
  2738. LLDrawable* mHit;
  2739. BOOL mPickTransparent;
  2740. LLOctreeIntersect(LLVector3 start, LLVector3 end, BOOL pick_transparent,
  2741.   S32* face_hit, LLVector3* intersection, LLVector2* tex_coord, LLVector3* normal, LLVector3* binormal)
  2742. : mStart(start),
  2743.   mEnd(end),
  2744.   mFaceHit(face_hit),
  2745.   mIntersection(intersection),
  2746.   mTexCoord(tex_coord),
  2747.   mNormal(normal),
  2748.   mBinormal(binormal),
  2749.   mHit(NULL),
  2750.   mPickTransparent(pick_transparent)
  2751. {
  2752. }
  2753. virtual void visit(const LLSpatialGroup::OctreeNode* branch) 
  2754. {
  2755. for (LLSpatialGroup::OctreeNode::const_element_iter i = branch->getData().begin(); i != branch->getData().end(); ++i)
  2756. {
  2757. check(*i);
  2758. }
  2759. }
  2760. virtual LLDrawable* check(const LLSpatialGroup::OctreeNode* node)
  2761. {
  2762. node->accept(this);
  2763. for (U32 i = 0; i < node->getChildCount(); i++)
  2764. {
  2765. const LLSpatialGroup::OctreeNode* child = node->getChild(i);
  2766. LLVector3 res;
  2767. LLSpatialGroup* group = (LLSpatialGroup*) child->getListener(0);
  2768. LLVector3 size;
  2769. LLVector3 center;
  2770. size = group->mBounds[1];
  2771. center = group->mBounds[0];
  2772. LLVector3 local_start = mStart;
  2773. LLVector3 local_end   = mEnd;
  2774. if (group->mSpatialPartition->isBridge())
  2775. {
  2776. LLMatrix4 local_matrix = group->mSpatialPartition->asBridge()->mDrawable->getRenderMatrix();
  2777. local_matrix.invert();
  2778. local_start = mStart * local_matrix;
  2779. local_end   = mEnd   * local_matrix;
  2780. }
  2781. if (LLLineSegmentBoxIntersect(local_start, local_end, center, size))
  2782. {
  2783. check(child);
  2784. }
  2785. }
  2786. return mHit;
  2787. }
  2788. virtual bool check(LLDrawable* drawable)
  2789. {
  2790. LLVector3 local_start = mStart;
  2791. LLVector3 local_end = mEnd;
  2792. if (!gPipeline.hasRenderType(drawable->getRenderType()) || !drawable->isVisible())
  2793. {
  2794. return false;
  2795. }
  2796. if (drawable->isSpatialBridge())
  2797. {
  2798. LLSpatialPartition *part = drawable->asPartition();
  2799. LLSpatialBridge* bridge = part->asBridge();
  2800. if (bridge && gPipeline.hasRenderType(bridge->mDrawableType))
  2801. {
  2802. check(part->mOctree);
  2803. }
  2804. }
  2805. else
  2806. {
  2807. LLViewerObject* vobj = drawable->getVObj();
  2808. if (vobj)
  2809. {
  2810. LLVector3 intersection;
  2811. if (vobj->lineSegmentIntersect(mStart, mEnd, -1, mPickTransparent, mFaceHit, &intersection, mTexCoord, mNormal, mBinormal))
  2812. {
  2813. mEnd = intersection;  // shorten ray so we only find CLOSER hits
  2814. if (mIntersection)
  2815. {
  2816. *mIntersection = intersection;
  2817. }
  2818. mHit = vobj->mDrawable;
  2819. }
  2820. }
  2821. }
  2822. return false;
  2823. }
  2824. };
  2825. LLDrawable* LLSpatialPartition::lineSegmentIntersect(const LLVector3& start, const LLVector3& end,
  2826.  BOOL pick_transparent,
  2827.  S32* face_hit,                   // return the face hit
  2828.  LLVector3* intersection,         // return the intersection point
  2829.  LLVector2* tex_coord,            // return the texture coordinates of the intersection point
  2830.  LLVector3* normal,               // return the surface normal at the intersection point
  2831.  LLVector3* bi_normal             // return the surface bi-normal at the intersection point
  2832. )
  2833. {
  2834. LLOctreeIntersect intersect(start, end, pick_transparent, face_hit, intersection, tex_coord, normal, bi_normal);
  2835. LLDrawable* drawable = intersect.check(mOctree);
  2836. return drawable;
  2837. }
  2838. LLDrawInfo::LLDrawInfo(U16 start, U16 end, U32 count, U32 offset, 
  2839.    LLViewerTexture* texture, LLVertexBuffer* buffer,
  2840.    BOOL fullbright, U8 bump, BOOL particle, F32 part_size)
  2841. :
  2842. mVertexBuffer(buffer),
  2843. mTexture(texture),
  2844. mTextureMatrix(NULL),
  2845. mModelMatrix(NULL),
  2846. mStart(start),
  2847. mEnd(end),
  2848. mCount(count),
  2849. mOffset(offset), 
  2850. mFullbright(fullbright),
  2851. mBump(bump),
  2852. mParticle(particle),
  2853. mPartSize(part_size),
  2854. mVSize(0.f),
  2855. mGroup(NULL),
  2856. mFace(NULL),
  2857. mDistance(0.f)
  2858. {
  2859. mDebugColor = (rand() << 16) + rand();
  2860. if (mStart >= mVertexBuffer->getRequestedVerts() ||
  2861. mEnd >= mVertexBuffer->getRequestedVerts())
  2862. {
  2863. llerrs << "Invalid draw info vertex range." << llendl;
  2864. }
  2865. if (mOffset >= (U32) mVertexBuffer->getRequestedIndices() ||
  2866. mOffset + mCount > (U32) mVertexBuffer->getRequestedIndices())
  2867. {
  2868. llerrs << "Invalid draw info index range." << llendl;
  2869. }
  2870. }
  2871. LLDrawInfo::~LLDrawInfo()
  2872. {
  2873. /*if (LLSpatialGroup::sNoDelete)
  2874. {
  2875. llerrs << "LLDrawInfo deleted illegally!" << llendl;
  2876. }*/
  2877. if (mFace)
  2878. {
  2879. mFace->setDrawInfo(NULL);
  2880. }
  2881. }
  2882. LLVertexBuffer* LLGeometryManager::createVertexBuffer(U32 type_mask, U32 usage)
  2883. {
  2884. return new LLVertexBuffer(type_mask, usage);
  2885. }
  2886. LLCullResult::LLCullResult() 
  2887. {
  2888. clear();
  2889. }
  2890. void LLCullResult::clear()
  2891. {
  2892. mVisibleGroupsSize = 0;
  2893. mAlphaGroupsSize = 0;
  2894. mOcclusionGroupsSize = 0;
  2895. mDrawableGroupsSize = 0;
  2896. mVisibleListSize = 0;
  2897. mVisibleBridgeSize = 0;
  2898. for (U32 i = 0; i < LLRenderPass::NUM_RENDER_TYPES; i++)
  2899. {
  2900. for (U32 j = 0; j < mRenderMapSize[i]; j++)
  2901. {
  2902. mRenderMap[i][j] = 0;
  2903. }
  2904. mRenderMapSize[i] = 0;
  2905. }
  2906. }
  2907. LLCullResult::sg_list_t::iterator LLCullResult::beginVisibleGroups()
  2908. {
  2909. return mVisibleGroups.begin();
  2910. }
  2911. LLCullResult::sg_list_t::iterator LLCullResult::endVisibleGroups()
  2912. {
  2913. return mVisibleGroups.begin() + mVisibleGroupsSize;
  2914. }
  2915. LLCullResult::sg_list_t::iterator LLCullResult::beginAlphaGroups()
  2916. {
  2917. return mAlphaGroups.begin();
  2918. }
  2919. LLCullResult::sg_list_t::iterator LLCullResult::endAlphaGroups()
  2920. {
  2921. return mAlphaGroups.begin() + mAlphaGroupsSize;
  2922. }
  2923. LLCullResult::sg_list_t::iterator LLCullResult::beginOcclusionGroups()
  2924. {
  2925. return mOcclusionGroups.begin();
  2926. }
  2927. LLCullResult::sg_list_t::iterator LLCullResult::endOcclusionGroups()
  2928. {
  2929. return mOcclusionGroups.begin() + mOcclusionGroupsSize;
  2930. }
  2931. LLCullResult::sg_list_t::iterator LLCullResult::beginDrawableGroups()
  2932. {
  2933. return mDrawableGroups.begin();
  2934. }
  2935. LLCullResult::sg_list_t::iterator LLCullResult::endDrawableGroups()
  2936. {
  2937. return mDrawableGroups.begin() + mDrawableGroupsSize;
  2938. }
  2939. LLCullResult::drawable_list_t::iterator LLCullResult::beginVisibleList()
  2940. {
  2941. return mVisibleList.begin();
  2942. }
  2943. LLCullResult::drawable_list_t::iterator LLCullResult::endVisibleList()
  2944. {
  2945. return mVisibleList.begin() + mVisibleListSize;
  2946. }
  2947. LLCullResult::bridge_list_t::iterator LLCullResult::beginVisibleBridge()
  2948. {
  2949. return mVisibleBridge.begin();
  2950. }
  2951. LLCullResult::bridge_list_t::iterator LLCullResult::endVisibleBridge()
  2952. {
  2953. return mVisibleBridge.begin() + mVisibleBridgeSize;
  2954. }
  2955. LLCullResult::drawinfo_list_t::iterator LLCullResult::beginRenderMap(U32 type)
  2956. {
  2957. return mRenderMap[type].begin();
  2958. }
  2959. LLCullResult::drawinfo_list_t::iterator LLCullResult::endRenderMap(U32 type)
  2960. {
  2961. return mRenderMap[type].begin() + mRenderMapSize[type];
  2962. }
  2963. void LLCullResult::pushVisibleGroup(LLSpatialGroup* group)
  2964. {
  2965. if (mVisibleGroupsSize < mVisibleGroups.size())
  2966. {
  2967. mVisibleGroups[mVisibleGroupsSize] = group;
  2968. }
  2969. else
  2970. {
  2971. mVisibleGroups.push_back(group);
  2972. }
  2973. ++mVisibleGroupsSize;
  2974. }
  2975. void LLCullResult::pushAlphaGroup(LLSpatialGroup* group)
  2976. {
  2977. if (mAlphaGroupsSize < mAlphaGroups.size())
  2978. {
  2979. mAlphaGroups[mAlphaGroupsSize] = group;
  2980. }
  2981. else
  2982. {
  2983. mAlphaGroups.push_back(group);
  2984. }
  2985. ++mAlphaGroupsSize;
  2986. }
  2987. void LLCullResult::pushOcclusionGroup(LLSpatialGroup* group)
  2988. {
  2989. if (mOcclusionGroupsSize < mOcclusionGroups.size())
  2990. {
  2991. mOcclusionGroups[mOcclusionGroupsSize] = group;
  2992. }
  2993. else
  2994. {
  2995. mOcclusionGroups.push_back(group);
  2996. }
  2997. ++mOcclusionGroupsSize;
  2998. }
  2999. void LLCullResult::pushDrawableGroup(LLSpatialGroup* group)
  3000. {
  3001. if (mDrawableGroupsSize < mDrawableGroups.size())
  3002. {
  3003. mDrawableGroups[mDrawableGroupsSize] = group;
  3004. }
  3005. else
  3006. {
  3007. mDrawableGroups.push_back(group);
  3008. }
  3009. ++mDrawableGroupsSize;
  3010. }
  3011. void LLCullResult::pushDrawable(LLDrawable* drawable)
  3012. {
  3013. if (mVisibleListSize < mVisibleList.size())
  3014. {
  3015. mVisibleList[mVisibleListSize] = drawable;
  3016. }
  3017. else
  3018. {
  3019. mVisibleList.push_back(drawable);
  3020. }
  3021. ++mVisibleListSize;
  3022. }
  3023. void LLCullResult::pushBridge(LLSpatialBridge* bridge)
  3024. {
  3025. if (mVisibleBridgeSize < mVisibleBridge.size())
  3026. {
  3027. mVisibleBridge[mVisibleBridgeSize] = bridge;
  3028. }
  3029. else
  3030. {
  3031. mVisibleBridge.push_back(bridge);
  3032. }
  3033. ++mVisibleBridgeSize;
  3034. }
  3035. void LLCullResult::pushDrawInfo(U32 type, LLDrawInfo* draw_info)
  3036. {
  3037. if (mRenderMapSize[type] < mRenderMap[type].size())
  3038. {
  3039. mRenderMap[type][mRenderMapSize[type]] = draw_info;
  3040. }
  3041. else
  3042. {
  3043. mRenderMap[type].push_back(draw_info);
  3044. }
  3045. ++mRenderMapSize[type];
  3046. }
  3047. void LLCullResult::assertDrawMapsEmpty()
  3048. {
  3049. for (U32 i = 0; i < LLRenderPass::NUM_RENDER_TYPES; i++)
  3050. {
  3051. if (mRenderMapSize[i] != 0)
  3052. {
  3053. llerrs << "Stale LLDrawInfo's in LLCullResult!" << llendl;
  3054. }
  3055. }
  3056. }