summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--indra/newview/llspatialpartition.cpp25
-rw-r--r--indra/newview/llvoavatar.cpp79
-rw-r--r--indra/newview/llvoavatar.h8
-rw-r--r--indra/newview/llvovolume.cpp3
4 files changed, 113 insertions, 2 deletions
diff --git a/indra/newview/llspatialpartition.cpp b/indra/newview/llspatialpartition.cpp
index 7f91f9a952..d96fa087b1 100644
--- a/indra/newview/llspatialpartition.cpp
+++ b/indra/newview/llspatialpartition.cpp
@@ -35,6 +35,7 @@
#include "llvolumeoctree.h"
#include "llviewercamera.h"
#include "llface.h"
+#include "llfloatertools.h"
#include "llviewercontrol.h"
#include "llviewerregion.h"
#include "llcamera.h"
@@ -4272,7 +4273,29 @@ public:
if (vobj)
{
LLVector3 intersection;
- if (vobj->lineSegmentIntersect(mStart, mEnd, -1, mPickTransparent, mFaceHit, &intersection, mTexCoord, mNormal, mBinormal))
+ bool skip_check = false;
+ if (vobj->isAvatar())
+ {
+ LLVOAvatar* avatar = (LLVOAvatar*) vobj;
+ if (avatar->isSelf() && LLFloater::isVisible(gFloaterTools))
+ {
+ LLViewerObject* hit = avatar->lineSegmentIntersectRiggedAttachments(mStart, mEnd, -1, mPickTransparent, mFaceHit, &intersection, mTexCoord, mNormal, mBinormal);
+ if (hit)
+ {
+ mEnd = intersection;
+ if (mIntersection)
+ {
+ *mIntersection = intersection;
+ }
+
+ mHit = hit->mDrawable;
+ skip_check = true;
+ }
+
+ }
+ }
+
+ if (!skip_check && vobj->lineSegmentIntersect(mStart, mEnd, -1, mPickTransparent, mFaceHit, &intersection, mTexCoord, mNormal, mBinormal))
{
mEnd = intersection; // shorten ray so we only find CLOSER hits
if (mIntersection)
diff --git a/indra/newview/llvoavatar.cpp b/indra/newview/llvoavatar.cpp
index 77bbf994e9..1b53348b43 100644
--- a/indra/newview/llvoavatar.cpp
+++ b/indra/newview/llvoavatar.cpp
@@ -56,6 +56,7 @@
#include "lleditingmotion.h"
#include "llemote.h"
//#include "llfirstuse.h"
+#include "llfloatertools.h"
#include "llheadrotmotion.h"
#include "llhudeffecttrail.h"
#include "llhudmanager.h"
@@ -1541,7 +1542,35 @@ BOOL LLVOAvatar::lineSegmentIntersect(const LLVector3& start, const LLVector3& e
return TRUE;
}
}
+
+ if (isSelf())
+ {
+ for (attachment_map_t::iterator iter = mAttachmentPoints.begin();
+ iter != mAttachmentPoints.end();
+ ++iter)
+ {
+ LLViewerJointAttachment* attachment = iter->second;
+
+ for (LLViewerJointAttachment::attachedobjs_vec_t::iterator attachment_iter = attachment->mAttachedObjects.begin();
+ attachment_iter != attachment->mAttachedObjects.end();
+ ++attachment_iter)
+ {
+ LLViewerObject* attached_object = (*attachment_iter);
+
+ if (attached_object && !attached_object->isDead() && attachment->getValid())
+ {
+ LLDrawable* drawable = attached_object->mDrawable;
+ if (drawable->isState(LLDrawable::RIGGED))
+ { //regenerate octree for rigged attachment
+ gPipeline.markRebuild(mDrawable, LLDrawable::REBUILD_RIGGED, TRUE);
+ }
+ }
+ }
+ }
+ }
}
+
+
LLVector3 position;
if (mNameText.notNull() && mNameText->lineSegmentIntersect(start, end, position))
@@ -1557,6 +1586,56 @@ BOOL LLVOAvatar::lineSegmentIntersect(const LLVector3& start, const LLVector3& e
return FALSE;
}
+LLViewerObject* LLVOAvatar::lineSegmentIntersectRiggedAttachments(const LLVector3& start, const LLVector3& end,
+ S32 face,
+ BOOL pick_transparent,
+ S32* face_hit,
+ LLVector3* intersection,
+ LLVector2* tex_coord,
+ LLVector3* normal,
+ LLVector3* bi_normal)
+{
+ if (isSelf() && !gAgent.needsRenderAvatar())
+ {
+ return NULL;
+ }
+
+ LLViewerObject* hit = NULL;
+
+ if (lineSegmentBoundingBox(start, end))
+ {
+ LLVector3 local_end = end;
+ LLVector3 local_intersection;
+
+ for (attachment_map_t::iterator iter = mAttachmentPoints.begin();
+ iter != mAttachmentPoints.end();
+ ++iter)
+ {
+ LLViewerJointAttachment* attachment = iter->second;
+
+ for (LLViewerJointAttachment::attachedobjs_vec_t::iterator attachment_iter = attachment->mAttachedObjects.begin();
+ attachment_iter != attachment->mAttachedObjects.end();
+ ++attachment_iter)
+ {
+ LLViewerObject* attached_object = (*attachment_iter);
+
+ if (attached_object->lineSegmentIntersect(start, local_end, face, pick_transparent, face_hit, &local_intersection, tex_coord, normal, bi_normal))
+ {
+ local_end = local_intersection;
+ if (intersection)
+ {
+ *intersection = local_intersection;
+ }
+
+ hit = attached_object;
+ }
+ }
+ }
+ }
+
+ return hit;
+}
+
//-----------------------------------------------------------------------------
// parseSkeletonFile()
//-----------------------------------------------------------------------------
diff --git a/indra/newview/llvoavatar.h b/indra/newview/llvoavatar.h
index 295799fd24..03c0498a2a 100644
--- a/indra/newview/llvoavatar.h
+++ b/indra/newview/llvoavatar.h
@@ -145,6 +145,14 @@ public:
LLVector2* tex_coord = NULL, // return the texture coordinates of the intersection point
LLVector3* normal = NULL, // return the surface normal at the intersection point
LLVector3* bi_normal = NULL); // return the surface bi-normal at the intersection point
+ LLViewerObject* lineSegmentIntersectRiggedAttachments(const LLVector3& start, const LLVector3& end,
+ S32 face = -1, // which face to check, -1 = ALL_SIDES
+ BOOL pick_transparent = FALSE,
+ S32* face_hit = NULL, // which face was hit
+ LLVector3* intersection = NULL, // return the intersection point
+ LLVector2* tex_coord = NULL, // return the texture coordinates of the intersection point
+ LLVector3* normal = NULL, // return the surface normal at the intersection point
+ LLVector3* bi_normal = NULL); // return the surface bi-normal at the intersection point
//--------------------------------------------------------------------
// LLCharacter interface and related
diff --git a/indra/newview/llvovolume.cpp b/indra/newview/llvovolume.cpp
index 39e555f781..6de334eb82 100644
--- a/indra/newview/llvovolume.cpp
+++ b/indra/newview/llvovolume.cpp
@@ -3365,7 +3365,8 @@ BOOL LLVOVolume::lineSegmentIntersect(const LLVector3& start, const LLVector3& e
{
if (LLFloater::isVisible(gFloaterTools) && getAvatar()->isSelf())
{
- gPipeline.markRebuild(mDrawable, LLDrawable::REBUILD_RIGGED, TRUE);
+ updateRiggedVolume();
+ genBBoxes(FALSE);
volume = mRiggedVolume;
transform = false;
}