From 56b327ff9738984ff0cc7e2c84a553e3d0595905 Mon Sep 17 00:00:00 2001 From: Shyotl Date: Wed, 2 Mar 2011 20:23:37 -0600 Subject: [PATCH 1/3] Possibly fixed pickmask (altcam+alpha issues). Uninitialized variables. --- indra/llrender/llimagegl.cpp | 52 +++++++++++++++++++++--------------- 1 file changed, 31 insertions(+), 21 deletions(-) diff --git a/indra/llrender/llimagegl.cpp b/indra/llrender/llimagegl.cpp index a8ef4ee9d..ffa25b425 100644 --- a/indra/llrender/llimagegl.cpp +++ b/indra/llrender/llimagegl.cpp @@ -416,48 +416,58 @@ LLImageGL::~LLImageGL() void LLImageGL::init(BOOL usemipmaps) { -#ifdef DEBUG_MISS - mMissed = FALSE; -#endif + // keep these members in the same order as declared in llimagehl.h + // so that it is obvious by visual inspection if we forgot to + // init a field. - mPickMask = NULL; - mTextureState = NO_DELETE ; - mTextureMemory = 0; - mLastBindTime = 0.f; + mTextureMemory = 0; + mLastBindTime = 0.f; + + mPickMask = NULL; mPickMaskWidth = 0; mPickMaskHeight = 0; + mUseMipMaps = usemipmaps; + mHasExplicitFormat = FALSE; + mAutoGenMips = FALSE; + + mIsMask = FALSE; + mNeedsAlphaAndPickMask = TRUE ; mAlphaStride = 0 ; mAlphaOffset = 0 ; + + mGLTextureCreated = FALSE ; + mTexName = 0; + mWidth = 0; + mHeight = 0; + mCurrentDiscardLevel = -1; mTarget = GL_TEXTURE_2D; mBindTarget = LLTexUnit::TT_TEXTURE; - mUseMipMaps = usemipmaps; mHasMipMaps = false; - mAutoGenMips = FALSE; - mTexName = 0; - mIsResident = 0; + + mIsResident = 0; + + mComponents = 0; + mMaxDiscardLevel = MAX_DISCARD_LEVEL; mTexOptionsDirty = true; mAddressMode = LLTexUnit::TAM_WRAP; mFilterOption = LLTexUnit::TFO_ANISOTROPIC; - mWidth = 0; - mHeight = 0; - mComponents = 0; - - mMaxDiscardLevel = MAX_DISCARD_LEVEL; - mCurrentDiscardLevel = -1; - mDontDiscard = FALSE; mFormatInternal = -1; mFormatPrimary = (LLGLenum) 0; mFormatType = GL_UNSIGNED_BYTE; mFormatSwapBytes = FALSE; - mHasExplicitFormat = FALSE; - mGLTextureCreated = FALSE ; +#ifdef DEBUG_MISS + mMissed = FALSE; +#endif - mIsMask = FALSE; mCategory = -1 ; + + //LLTexture stuff + mDontDiscard = FALSE; + mTextureState = NO_DELETE ; } void LLImageGL::cleanup() From 3c29dd3c20a2724eda5cdeadf8efdbe51413cf33 Mon Sep 17 00:00:00 2001 From: Shyotl Date: Wed, 2 Mar 2011 20:28:59 -0600 Subject: [PATCH 2/3] Added some null checks. --- indra/newview/llhudicon.cpp | 18 +++++----- indra/newview/lltoolmgr.cpp | 4 ++- indra/newview/llviewerobject.cpp | 53 ++++++++++++++++++++++------ indra/newview/llviewerobjectlist.cpp | 5 ++- 4 files changed, 58 insertions(+), 22 deletions(-) diff --git a/indra/newview/llhudicon.cpp b/indra/newview/llhudicon.cpp index 3535fe185..1e49d9ef2 100644 --- a/indra/newview/llhudicon.cpp +++ b/indra/newview/llhudicon.cpp @@ -103,28 +103,29 @@ void LLHUDIcon::renderIcon(BOOL for_select) // put icon above object, and in front // RN: don't use drawable radius, it's fricking HUGE - LLVector3 icon_relative_pos = (LLViewerCamera::getInstance()->getUpAxis() * ~mSourceObject->getRenderRotation()); + LLViewerCamera* camera = LLViewerCamera::getInstance(); + LLVector3 icon_relative_pos = (camera->getUpAxis() * ~mSourceObject->getRenderRotation()); icon_relative_pos.abs(); F32 distance_scale = llmin(mSourceObject->getScale().mV[VX] / icon_relative_pos.mV[VX], mSourceObject->getScale().mV[VY] / icon_relative_pos.mV[VY], mSourceObject->getScale().mV[VZ] / icon_relative_pos.mV[VZ]); F32 up_distance = 0.5f * distance_scale; - LLVector3 icon_position = obj_position + (up_distance * LLViewerCamera::getInstance()->getUpAxis()) * 1.2f; + LLVector3 icon_position = obj_position + (up_distance * camera->getUpAxis()) * 1.2f; LLVector3 icon_to_cam = LLViewerCamera::getInstance()->getOrigin() - icon_position; icon_to_cam.normVec(); icon_position += icon_to_cam * mSourceObject->mDrawable->getRadius() * 1.1f; - mDistance = dist_vec(icon_position, LLViewerCamera::getInstance()->getOrigin()); + mDistance = dist_vec(icon_position, camera->getOrigin()); F32 alpha_factor = for_select ? 1.f : clamp_rescale(mDistance, DIST_START_FADE, DIST_END_FADE, 1.f, 0.f); LLVector3 x_pixel_vec; LLVector3 y_pixel_vec; - LLViewerCamera::getInstance()->getPixelVectors(icon_position, y_pixel_vec, x_pixel_vec); + camera->getPixelVectors(icon_position, y_pixel_vec, x_pixel_vec); F32 scale_factor = 1.f; if (mAnimTimer.getElapsedTimeF32() < ANIM_TIME) @@ -226,26 +227,27 @@ BOOL LLHUDIcon::lineSegmentIntersect(const LLVector3& start, const LLVector3& en // put icon above object, and in front // RN: don't use drawable radius, it's fricking HUGE - LLVector3 icon_relative_pos = (LLViewerCamera::getInstance()->getUpAxis() * ~mSourceObject->getRenderRotation()); + LLViewerCamera* camera = LLViewerCamera::getInstance(); + LLVector3 icon_relative_pos = (camera->getUpAxis() * ~mSourceObject->getRenderRotation()); icon_relative_pos.abs(); F32 distance_scale = llmin(mSourceObject->getScale().mV[VX] / icon_relative_pos.mV[VX], mSourceObject->getScale().mV[VY] / icon_relative_pos.mV[VY], mSourceObject->getScale().mV[VZ] / icon_relative_pos.mV[VZ]); F32 up_distance = 0.5f * distance_scale; - LLVector3 icon_position = obj_position + (up_distance * LLViewerCamera::getInstance()->getUpAxis()) * 1.2f; + LLVector3 icon_position = obj_position + (up_distance * camera->getUpAxis()) * 1.2f; LLVector3 icon_to_cam = LLViewerCamera::getInstance()->getOrigin() - icon_position; icon_to_cam.normVec(); icon_position += icon_to_cam * mSourceObject->mDrawable->getRadius() * 1.1f; - mDistance = dist_vec(icon_position, LLViewerCamera::getInstance()->getOrigin()); + mDistance = dist_vec(icon_position, camera->getOrigin()); LLVector3 x_pixel_vec; LLVector3 y_pixel_vec; - LLViewerCamera::getInstance()->getPixelVectors(icon_position, y_pixel_vec, x_pixel_vec); + camera->getPixelVectors(icon_position, y_pixel_vec, x_pixel_vec); F32 scale_factor = 1.f; if (mAnimTimer.getElapsedTimeF32() < ANIM_TIME) diff --git a/indra/newview/lltoolmgr.cpp b/indra/newview/lltoolmgr.cpp index 021b6364f..db47f023f 100644 --- a/indra/newview/lltoolmgr.cpp +++ b/indra/newview/lltoolmgr.cpp @@ -170,11 +170,13 @@ void LLToolMgr::setCurrentTool( LLTool* tool ) mBaseTool = tool; updateToolStatus(); + + mSavedTool = NULL; } LLTool* LLToolMgr::getCurrentTool() { - MASK override_mask = gKeyboard->currentMask(TRUE); + MASK override_mask = gKeyboard ? gKeyboard->currentMask(TRUE) : 0; LLTool* cur_tool = NULL; // always use transient tools if available diff --git a/indra/newview/llviewerobject.cpp b/indra/newview/llviewerobject.cpp index 67b3a7aeb..9964eea6f 100644 --- a/indra/newview/llviewerobject.cpp +++ b/indra/newview/llviewerobject.cpp @@ -222,7 +222,7 @@ LLViewerObject::LLViewerObject(const LLUUID &id, const LLPCode pcode, LLViewerRe mPositionRegion = LLVector3(0.f, 0.f, 0.f); - if(!is_global) + if (!is_global && mRegionp) { mPositionAgent = mRegionp->getOriginAgent(); } @@ -464,6 +464,7 @@ void LLViewerObject::cleanupVOClasses() LLVOWater::cleanupClass(); LLVOTree::cleanupClass(); LLVOAvatar::cleanupClass(); + LLVOVolume::cleanupClass(); } // Replaces all name value pairs with data from \n delimited list @@ -559,7 +560,11 @@ void LLViewerObject::removeChild(LLViewerObject *childp) } mChildList.erase(i); - childp->setParent(NULL); + + if(childp->getParent() == this) + { + childp->setParent(NULL); + } break; } } @@ -704,7 +709,24 @@ U32 LLViewerObject::processUpdateMessage(LLMessageSystem *mesgsys, // Coordinates of objects on simulators are region-local. U64 region_handle; mesgsys->getU64Fast(_PREHASH_RegionData, _PREHASH_RegionHandle, region_handle); - mRegionp = LLWorld::getInstance()->getRegionFromHandle(region_handle); + + { + LLViewerRegion* regionp = LLWorld::getInstance()->getRegionFromHandle(region_handle); + if(regionp != mRegionp && regionp && mRegionp)//region cross + { + //this is the redundant position and region update, but it is necessary in case the viewer misses the following + //position and region update messages from sim. + //this redundant update should not cause any problems. + LLVector3 delta_pos = mRegionp->getOriginAgent() - regionp->getOriginAgent(); + setPositionParent(getPosition() + delta_pos); //update to the new region position immediately. + setRegion(regionp) ; //change the region. + } + else + { + mRegionp = regionp ; + } + } + if (!mRegionp) { U32 x, y; @@ -2807,22 +2829,23 @@ void LLViewerObject::setPixelAreaAndAngle(LLAgent &agent) // I don't think there's a better way to do this without calculating distance per-poly F32 range = sqrt(dx*dx + dy*dy + dz*dz) - min_scale/2; + LLViewerCamera* camera = LLViewerCamera::getInstance(); if (range < 0.001f || isHUDAttachment()) // range == zero { mAppAngle = 180.f; - mPixelArea = (F32)LLViewerCamera::getInstance()->getScreenPixelArea(); + mPixelArea = (F32)camera->getScreenPixelArea(); } else { mAppAngle = (F32) atan2( max_scale, range) * RAD_TO_DEG; - F32 pixels_per_meter = LLViewerCamera::getInstance()->getPixelMeterRatio() / range; + F32 pixels_per_meter = camera->getPixelMeterRatio() / range; mPixelArea = (pixels_per_meter * max_scale) * (pixels_per_meter * mid_scale); - if (mPixelArea > LLViewerCamera::getInstance()->getScreenPixelArea()) + if (mPixelArea > camera->getScreenPixelArea()) { mAppAngle = 180.f; - mPixelArea = (F32)LLViewerCamera::getInstance()->getScreenPixelArea(); + mPixelArea = (F32)camera->getScreenPixelArea(); } } } @@ -4040,9 +4063,15 @@ LLBBox LLViewerObject::getBoundingBoxAgent() const { LLVector3 position_agent; LLQuaternion rot; + LLViewerObject* avatar_parent = NULL; LLViewerObject* root_edit = (LLViewerObject*)getRootEdit(); - LLViewerObject* avatar_parent = (LLViewerObject*)root_edit->getParent(); - if (avatar_parent && avatar_parent->isAvatar() && root_edit->mDrawable.notNull()) + if (root_edit) + { + avatar_parent = (LLViewerObject*)root_edit->getParent(); + } + + if (avatar_parent && avatar_parent->isAvatar() && + root_edit && root_edit->mDrawable.notNull() && root_edit->mDrawable->getXform()->getParent()) { LLXform* parent_xform = root_edit->mDrawable->getXform()->getParent(); position_agent = (getPositionEdit() * parent_xform->getWorldRotation()) + parent_xform->getWorldPosition(); @@ -4940,7 +4969,11 @@ void LLViewerObject::setIncludeInSearch(bool include_in_search) void LLViewerObject::setRegion(LLViewerRegion *regionp) { - llassert(regionp); + if (!regionp) + { + llwarns << "viewer object set region to NULL" << llendl; + } + mLatestRecvPacketID = 0; mRegionp = regionp; diff --git a/indra/newview/llviewerobjectlist.cpp b/indra/newview/llviewerobjectlist.cpp index 44fa54177..3d6471ab5 100644 --- a/indra/newview/llviewerobjectlist.cpp +++ b/indra/newview/llviewerobjectlist.cpp @@ -172,9 +172,8 @@ BOOL LLViewerObjectList::removeFromLocalIDTable(const LLViewerObject &object) if(object.getRegion()) { U32 local_id = object.mLocalID; - LLHost region_host = object.getRegion()->getHost(); - U32 ip = region_host.getAddress(); - U32 port = region_host.getPort(); + U32 ip = object.getRegion()->getHost().getAddress(); + U32 port = object.getRegion()->getHost().getPort(); U64 ipport = (((U64)ip) << 32) | (U64)port; U32 index = sIPAndPortToIndex[ipport]; From 694f95269e39a06ceb0f8688632489e933d40ccc Mon Sep 17 00:00:00 2001 From: Shyotl Date: Wed, 2 Mar 2011 20:32:10 -0600 Subject: [PATCH 3/3] Added LLFace::canRenderAsMask() Added LLVOVolume::isVisible() Avatar VBO now uses stream type under all scenarios. Todo: Perf test. Added other misc render-related tweaks that looked safe. --- indra/newview/lldrawable.cpp | 7 ++- indra/newview/lldrawable.h | 19 ++++++-- indra/newview/lldrawpoolavatar.cpp | 7 +-- indra/newview/lldrawpoolsimple.cpp | 4 ++ indra/newview/llface.cpp | 42 ++++++++++++----- indra/newview/llface.h | 1 + indra/newview/llvovolume.cpp | 72 +++++++++++++++++++----------- indra/newview/llvovolume.h | 2 + 8 files changed, 110 insertions(+), 44 deletions(-) diff --git a/indra/newview/lldrawable.cpp b/indra/newview/lldrawable.cpp index fcfa957fe..2ae30f9da 100644 --- a/indra/newview/lldrawable.cpp +++ b/indra/newview/lldrawable.cpp @@ -693,6 +693,8 @@ void LLDrawable::updateDistance(LLCamera& camera, bool force_update) pos += volume->getRegion()->getOriginAgent(); } + if (isState(LLDrawable::HAS_ALPHA)) + { for (S32 i = 0; i < getNumFaces(); i++) { LLFace* facep = getFace(i); @@ -708,6 +710,7 @@ void LLDrawable::updateDistance(LLCamera& camera, bool force_update) facep->mDistance = v * camera.getAtAxis(); } } + } } else { @@ -1239,7 +1242,9 @@ void LLSpatialBridge::setVisible(LLCamera& camera_in, std::vector* (camera_in.AABBInFrustumNoFarClip(center, size) && AABBSphereIntersect(mExtents[0], mExtents[1], camera_in.getOrigin(), camera_in.mFrustumCornerDist))) { - if (!LLPipeline::sImpostorRender && LLPipeline::calcPixelArea(center, size, camera_in) < FORCE_INVISIBLE_AREA) + if (!LLPipeline::sImpostorRender && + !LLPipeline::sShadowRender && + LLPipeline::calcPixelArea(center, size, camera_in) < FORCE_INVISIBLE_AREA) { return; } diff --git a/indra/newview/lldrawable.h b/indra/newview/lldrawable.h index 71b75dc4c..2d693b6d2 100644 --- a/indra/newview/lldrawable.h +++ b/indra/newview/lldrawable.h @@ -267,7 +267,8 @@ public: BUILT = 0x08000000, FORCE_INVISIBLE = 0x10000000, // stay invis until CLEAR_INVISIBLE is set (set of orphaned) CLEAR_INVISIBLE = 0x20000000, // clear FORCE_INVISIBLE next draw frame - REBUILD_SHADOW = 0x40000000 + REBUILD_SHADOW = 0x40000000, + HAS_ALPHA = 0x80000000, } EDrawableFlags; LLXformMatrix mXform; @@ -314,8 +315,20 @@ private: inline LLFace* LLDrawable::getFace(const S32 i) const { - llassert((U32)i < mFaces.size()); - llassert(mFaces[i]); + //switch these asserts to llerrs -- davep + //llassert((U32)i < mFaces.size()); + //llassert(mFaces[i]); + + if ((U32) i >= mFaces.size()) + { + llerrs << "Invalid face index." << llendl; + } + + if (!mFaces[i]) + { + llerrs << "Null face found." << llendl; + } + return mFaces[i]; } diff --git a/indra/newview/lldrawpoolavatar.cpp b/indra/newview/lldrawpoolavatar.cpp index f86e8a08f..38996e624 100644 --- a/indra/newview/lldrawpoolavatar.cpp +++ b/indra/newview/lldrawpoolavatar.cpp @@ -125,7 +125,8 @@ void LLDrawPoolAvatar::prerender() if (sShaderLevel > 0) { - sBufferUsage = GL_STATIC_DRAW_ARB; + sBufferUsage = GL_DYNAMIC_DRAW_ARB; + //sBufferUsage = GL_STATIC_DRAW_ARB; } else { @@ -861,8 +862,8 @@ LLColor3 LLDrawPoolAvatar::getDebugColor() const LLVertexBufferAvatar::LLVertexBufferAvatar() : LLVertexBuffer(sDataMask, - LLViewerShaderMgr::instance()->getVertexShaderLevel(LLViewerShaderMgr::SHADER_AVATAR) > 0 ? - GL_DYNAMIC_DRAW_ARB : + //LLViewerShaderMgr::instance()->getVertexShaderLevel(LLViewerShaderMgr::SHADER_AVATAR) > 0 ? + //GL_DYNAMIC_DRAW_ARB : GL_STREAM_DRAW_ARB) { diff --git a/indra/newview/lldrawpoolsimple.cpp b/indra/newview/lldrawpoolsimple.cpp index 1fdf87f6d..14931024e 100644 --- a/indra/newview/lldrawpoolsimple.cpp +++ b/indra/newview/lldrawpoolsimple.cpp @@ -53,6 +53,10 @@ void LLDrawPoolGlow::render(S32 pass) LLFastTimer t(LLFastTimer::FTM_RENDER_GLOW); LLGLEnable blend(GL_BLEND); LLGLDisable test(GL_ALPHA_TEST); + gGL.flush(); + /// Get rid of z-fighting with non-glow pass. + LLGLEnable polyOffset(GL_POLYGON_OFFSET_FILL); + glPolygonOffset(-1.0f, -1.0f); gGL.setSceneBlendType(LLRender::BT_ADD); U32 shader_level = LLViewerShaderMgr::instance()->getVertexShaderLevel(LLViewerShaderMgr::SHADER_OBJECT); diff --git a/indra/newview/llface.cpp b/indra/newview/llface.cpp index f8e79e735..5ce007d1e 100644 --- a/indra/newview/llface.cpp +++ b/indra/newview/llface.cpp @@ -896,6 +896,25 @@ void LLFace::updateRebuildFlags() } } + +bool LLFace::canRenderAsMask() +{ + const LLTextureEntry* te = getTextureEntry(); + return ( + ( + LLPipeline::sFastAlpha + /*(LLPipeline::sRenderDeferred && LLPipeline::sAutoMaskAlphaDeferred) || + (!LLPipeline::sRenderDeferred && LLPipeline::sAutoMaskAlphaNonDeferred)*/ + ) // do we want masks at all? + && + (te->getColor().mV[3] == 1.0f) && // can't treat as mask if we have face alpha + !(LLPipeline::sRenderDeferred && te->getFullbright()) && // hack: alpha masking renders fullbright faces invisible in deferred rendering mode, need to figure out why - for now, avoid + (te->getGlow() == 0.f) && // glowing masks are hard to implement - don't mask + + getTexture()->getIsAlphaMask() // texture actually qualifies for masking (lazily recalculated but expensive) + ); +} + BOOL LLFace::getGeometryVolume(const LLVolume& volume, const S32 &f, const LLMatrix4& mat_vert, const LLMatrix3& mat_normal, @@ -1049,17 +1068,20 @@ BOOL LLFace::getGeometryVolume(const LLVolume& volume, if (rebuild_color) { - GLfloat alpha[4] = + if (tep) { - 0.00f, - 0.25f, - 0.5f, - 0.75f - }; - - if (getPoolType() != LLDrawPool::POOL_ALPHA && (LLPipeline::sRenderDeferred || (LLPipeline::sRenderBump && tep->getShiny()))) - { - color.mV[3] = U8 (alpha[tep->getShiny()] * 255); + GLfloat alpha[4] = + { + 0.00f, + 0.25f, + 0.5f, + 0.75f + }; + + if (getPoolType() != LLDrawPool::POOL_ALPHA && (LLPipeline::sRenderDeferred || (LLPipeline::sRenderBump && tep->getShiny()))) + { + color.mV[3] = U8 (alpha[tep->getShiny()] * 255); + } } } diff --git a/indra/newview/llface.h b/indra/newview/llface.h index 716e608b3..90edf9de1 100644 --- a/indra/newview/llface.h +++ b/indra/newview/llface.h @@ -143,6 +143,7 @@ public: //for volumes void updateRebuildFlags(); + bool canRenderAsMask(); // logic helper BOOL getGeometryVolume(const LLVolume& volume, const S32 &f, const LLMatrix4& mat_vert, const LLMatrix3& mat_normal, diff --git a/indra/newview/llvovolume.cpp b/indra/newview/llvovolume.cpp index f1603beef..8ac628e32 100644 --- a/indra/newview/llvovolume.cpp +++ b/indra/newview/llvovolume.cpp @@ -110,6 +110,10 @@ void LLVOVolume::initClass() { } +// static +void LLVOVolume::cleanupClass() +{ +} U32 LLVOVolume::processUpdateMessage(LLMessageSystem *mesgsys, void **user_data, @@ -415,6 +419,26 @@ void LLVOVolume::updateTextures() } } +BOOL LLVOVolume::isVisible() const +{ + if(mDrawable.notNull() && mDrawable->isVisible()) + { + return TRUE ; + } + + if(isAttachment()) + { + LLViewerObject* objp = (LLViewerObject*)getParent() ; + while(objp && !objp->isAvatar()) + { + objp = (LLViewerObject*)objp->getParent() ; + } + + return objp && objp->mDrawable.notNull() && objp->mDrawable->isVisible() ; + } + + return FALSE ; +} void LLVOVolume::updateTextureVirtualSize() { // Update the pixel area of all faces @@ -938,7 +962,7 @@ BOOL LLVOVolume::setParent(LLViewerObject* parent) if (parent != getParent()) { ret = LLViewerObject::setParent(parent); - if (mDrawable) + if (ret && mDrawable) { gPipeline.markMoved(mDrawable); gPipeline.markRebuild(mDrawable, LLDrawable::REBUILD_VOLUME, TRUE); @@ -1778,14 +1802,7 @@ void LLVOVolume::updateRadius() BOOL LLVOVolume::isAttachment() const { - if (mState == 0) - { - return FALSE; - } - else - { - return TRUE; - } + return mState != 0 ; } BOOL LLVOVolume::isHUDAttachment() const @@ -1863,9 +1880,7 @@ F32 LLVOVolume::getBinRadius() { LLFace* face = mDrawable->getFace(i); if (face->getPoolType() == LLDrawPool::POOL_ALPHA && - (!LLPipeline::sFastAlpha || - face->getFaceColor().mV[3] != 1.f || - !face->getTexture()->getIsAlphaMask())) + !face->canRenderAsMask()) { alpha_wrap = TRUE; break; @@ -2057,9 +2072,9 @@ BOOL LLVOVolume::lineSegmentIntersect(const LLVector3& start, const LLVector3& e if (face_hit >= 0 && mDrawable->getNumFaces() > face_hit) { - LLFace* face = mDrawable->getFace(face_hit); + LLFace* face = mDrawable->getFace(face_hit); - if (pick_transparent || !face->getTexture() || face->getTexture()->getMask(face->surfaceToTexture(tc, p, n))) + if (pick_transparent || !face->getTexture() || !face->getTexture()->getHasGLTexture() || face->getTexture()->getMask(face->surfaceToTexture(tc, p, n))) { v_end = p; if (face_hitp != NULL) @@ -2141,7 +2156,7 @@ void LLVolumeGeometryManager::registerFace(LLSpatialGroup* group, LLFace* facep, const LLViewerObject* pObj = facep->getViewerObject(); if ( (pObj->isSelected() && gHideSelectedObjects) && ((!rlv_handler_t::isEnabled()) || (!pObj->isHUDAttachment()) || (!gRlvAttachmentLocks.isLockedAttachment(pObj->getRootEdit()))) ) -// [/RVLa:KB] +// [/RLVa:KB] { return; } @@ -2151,9 +2166,9 @@ void LLVolumeGeometryManager::registerFace(LLSpatialGroup* group, LLFace* facep, S32 idx = draw_vec.size()-1; - - BOOL fullbright = (type == LLRenderPass::PASS_FULLBRIGHT || - type == LLRenderPass::PASS_ALPHA) ? facep->isState(LLFace::FULLBRIGHT) : FALSE; + BOOL fullbright = (type == LLRenderPass::PASS_FULLBRIGHT) || + (type == LLRenderPass::PASS_INVISIBLE) || + (type == LLRenderPass::PASS_ALPHA && facep->isState(LLFace::FULLBRIGHT)); const LLMatrix4* tex_mat = NULL; if (facep->isState(LLFace::TEXTURE_ANIM) && facep->getVirtualSize() > MIN_TEX_ANIM_SIZE) @@ -2309,6 +2324,8 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group) vobj->updateTextureVirtualSize(); vobj->preRebuild(); + drawablep->clearState(LLDrawable::HAS_ALPHA); + //for each face for (S32 i = 0; i < drawablep->getNumFaces(); i++) { @@ -2316,7 +2333,7 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group) drawablep->updateFaceSize(i); LLFace* facep = drawablep->getFace(i); - if (cur_total > max_total) + if (cur_total > max_total || facep->getIndicesCount() <= 0 || facep->getGeomCount() <= 0) { facep->mVertexBuffer = NULL; facep->mLastVertexBuffer = NULL; @@ -2369,14 +2386,13 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group) if (type == LLDrawPool::POOL_ALPHA) { - if (LLPipeline::sFastAlpha && - (te->getColor().mV[VW] == 1.0f) && - facep->getTexture()->getIsAlphaMask()) + if (facep->canRenderAsMask()) { //can be treated as alpha mask simple_faces.push_back(facep); } else { + drawablep->setState(LLDrawable::HAS_ALPHA); alpha_faces.push_back(facep); } } @@ -2474,8 +2490,7 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group) void LLVolumeGeometryManager::rebuildMesh(LLSpatialGroup* group) { static int warningsCount = 20; - - if (group->isState(LLSpatialGroup::MESH_DIRTY)) + if (group && group->isState(LLSpatialGroup::MESH_DIRTY) && !group->isState(LLSpatialGroup::GEOM_DIRTY)) { S32 num_mapped_vertex_buffer = LLVertexBuffer::sMappedCount ; @@ -2703,6 +2718,11 @@ void LLVolumeGeometryManager::genDrawInfo(LLSpatialGroup* group, U32 mask, std:: BOOL force_simple = facep->mPixelArea < FORCE_SIMPLE_RENDER_AREA; BOOL fullbright = facep->isState(LLFace::FULLBRIGHT); + if ((mask & LLVertexBuffer::MAP_NORMAL) == 0) + { //paranoia check to make sure GL doesn't try to read non-existant normals + fullbright = TRUE; + } + const LLTextureEntry* te = facep->getTextureEntry(); BOOL is_alpha = facep->getPoolType() == LLDrawPool::POOL_ALPHA ? TRUE : FALSE; @@ -2710,9 +2730,7 @@ void LLVolumeGeometryManager::genDrawInfo(LLSpatialGroup* group, U32 mask, std:: if (is_alpha) { // can we safely treat this as an alpha mask? - if (LLPipeline::sFastAlpha && - (te->getColor().mV[VW] == 1.0f) && - facep->getTexture()->getIsAlphaMask()) + if (facep->canRenderAsMask()) { if (te->getFullbright()) { diff --git a/indra/newview/llvovolume.h b/indra/newview/llvovolume.h index 8cc1331f5..882616cd0 100644 --- a/indra/newview/llvovolume.h +++ b/indra/newview/llvovolume.h @@ -78,6 +78,7 @@ protected: public: static void initClass(); + static void cleanupClass(); static void preUpdateGeom(); enum @@ -99,6 +100,7 @@ public: void animateTextures(); /*virtual*/ BOOL idleUpdate(LLAgent &agent, LLWorld &world, const F64 &time); + BOOL isVisible() const ; /*virtual*/ BOOL isActive() const; /*virtual*/ BOOL isAttachment() const; /*virtual*/ BOOL isRootEdit() const; // overridden for sake of attachments treating themselves as a root object