summaryrefslogtreecommitdiff
path: root/indra/llcharacter
diff options
context:
space:
mode:
Diffstat (limited to 'indra/llcharacter')
-rw-r--r--indra/llcharacter/llheadrotmotion.cpp201
-rw-r--r--indra/llcharacter/llheadrotmotion.h4
-rw-r--r--indra/llcharacter/lljoint.cpp64
-rw-r--r--indra/llcharacter/lljoint.h11
-rw-r--r--indra/llcharacter/llkeyframemotion.cpp5
5 files changed, 183 insertions, 102 deletions
diff --git a/indra/llcharacter/llheadrotmotion.cpp b/indra/llcharacter/llheadrotmotion.cpp
index 812c4201af..e91de7a11d 100644
--- a/indra/llcharacter/llheadrotmotion.cpp
+++ b/indra/llcharacter/llheadrotmotion.cpp
@@ -285,7 +285,10 @@ LLEyeMotion::LLEyeMotion(const LLUUID &id) : LLMotion(id)
mName = "eye_rot";
mLeftEyeState = new LLJointState;
+ mAltLeftEyeState = new LLJointState;
+
mRightEyeState = new LLJointState;
+ mAltRightEyeState = new LLJointState;
}
@@ -318,18 +321,38 @@ LLMotion::LLMotionInitStatus LLEyeMotion::onInitialize(LLCharacter *character)
return STATUS_FAILURE;
}
+ mAltLeftEyeState->setJoint( character->getJoint("mFaceEyeAltLeft") );
+ if ( ! mAltLeftEyeState->getJoint() )
+ {
+ LL_INFOS() << getName() << ": Can't get alt left eyeball joint." << LL_ENDL;
+ return STATUS_FAILURE;
+ }
+
mRightEyeState->setJoint( character->getJoint("mEyeRight") );
if ( ! mRightEyeState->getJoint() )
{
- LL_INFOS() << getName() << ": Can't get Right eyeball joint." << LL_ENDL;
+ LL_INFOS() << getName() << ": Can't get right eyeball joint." << LL_ENDL;
+ return STATUS_FAILURE;
+ }
+
+ mAltRightEyeState->setJoint( character->getJoint("mFaceEyeAltRight") );
+ if ( ! mAltRightEyeState->getJoint() )
+ {
+ LL_INFOS() << getName() << ": Can't get alt right eyeball joint." << LL_ENDL;
return STATUS_FAILURE;
}
mLeftEyeState->setUsage(LLJointState::ROT);
+ mAltLeftEyeState->setUsage(LLJointState::ROT);
+
mRightEyeState->setUsage(LLJointState::ROT);
+ mAltRightEyeState->setUsage(LLJointState::ROT);
addJointState( mLeftEyeState );
+ addJointState( mAltLeftEyeState );
+
addJointState( mRightEyeState );
+ addJointState( mAltRightEyeState );
return STATUS_SUCCESS;
}
@@ -343,17 +366,98 @@ BOOL LLEyeMotion::onActivate()
return TRUE;
}
-
//-----------------------------------------------------------------------------
-// LLEyeMotion::onUpdate()
+// LLEyeMotion::adjustEyeTarget()
//-----------------------------------------------------------------------------
-BOOL LLEyeMotion::onUpdate(F32 time, U8* joint_mask)
+void LLEyeMotion::adjustEyeTarget(LLVector3* targetPos, LLJointState& left_eye_state, LLJointState& right_eye_state)
{
// Compute eye rotation.
+ BOOL has_eye_target = FALSE;
LLQuaternion target_eye_rot;
LLVector3 eye_look_at;
F32 vergence;
+ if (targetPos)
+ {
+ LLVector3 skyward(0.f, 0.f, 1.f);
+ LLVector3 left;
+ LLVector3 up;
+
+ eye_look_at = *targetPos;
+ has_eye_target = TRUE;
+ F32 lookAtDistance = eye_look_at.normVec();
+
+ left.setVec(skyward % eye_look_at);
+ up.setVec(eye_look_at % left);
+
+ target_eye_rot = LLQuaternion(eye_look_at, left, up);
+ // convert target rotation to head-local coordinates
+ target_eye_rot *= ~mHeadJoint->getWorldRotation();
+ // eliminate any Euler roll - we're lucky that roll is applied last.
+ F32 roll, pitch, yaw;
+ target_eye_rot.getEulerAngles(&roll, &pitch, &yaw);
+ target_eye_rot.setQuat(0.0f, pitch, yaw);
+ // constrain target orientation to be in front of avatar's face
+ target_eye_rot.constrain(EYE_ROT_LIMIT_ANGLE);
+
+ // calculate vergence
+ F32 interocular_dist = (left_eye_state.getJoint()->getWorldPosition() - right_eye_state.getJoint()->getWorldPosition()).magVec();
+ vergence = -atan2((interocular_dist / 2.f), lookAtDistance);
+ llclamp(vergence, -F_PI_BY_TWO, 0.f);
+ }
+ else
+ {
+ target_eye_rot = LLQuaternion::DEFAULT;
+ vergence = 0.f;
+ }
+
+ //RN: subtract 4 degrees to account for foveal angular offset relative to pupil
+ vergence += 4.f * DEG_TO_RAD;
+
+ // calculate eye jitter
+ LLQuaternion eye_jitter_rot;
+
+ // vergence not too high...
+ if (vergence > -0.05f)
+ {
+ //...go ahead and jitter
+ eye_jitter_rot.setQuat(0.f, mEyeJitterPitch + mEyeLookAwayPitch, mEyeJitterYaw + mEyeLookAwayYaw);
+ }
+ else
+ {
+ //...or don't
+ eye_jitter_rot.loadIdentity();
+ }
+
+ // calculate vergence of eyes as an object gets closer to the avatar's head
+ LLQuaternion vergence_quat;
+
+ if (has_eye_target)
+ {
+ vergence_quat.setQuat(vergence, LLVector3(0.f, 0.f, 1.f));
+ }
+ else
+ {
+ vergence_quat.loadIdentity();
+ }
+
+ // calculate eye rotations
+ LLQuaternion left_eye_rot = target_eye_rot;
+ left_eye_rot = vergence_quat * eye_jitter_rot * left_eye_rot;
+
+ LLQuaternion right_eye_rot = target_eye_rot;
+ vergence_quat.transQuat();
+ right_eye_rot = vergence_quat * eye_jitter_rot * right_eye_rot;
+
+ left_eye_state.setRotation( left_eye_rot );
+ right_eye_state.setRotation( right_eye_rot );
+}
+
+//-----------------------------------------------------------------------------
+// LLEyeMotion::onUpdate()
+//-----------------------------------------------------------------------------
+BOOL LLEyeMotion::onUpdate(F32 time, U8* joint_mask)
+{
//calculate jitter
if (mEyeJitterTimer.getElapsedTimeF32() > mEyeJitterTime)
{
@@ -426,83 +530,10 @@ BOOL LLEyeMotion::onUpdate(F32 time, U8* joint_mask)
}
}
- BOOL has_eye_target = FALSE;
LLVector3* targetPos = (LLVector3*)mCharacter->getAnimationData("LookAtPoint");
- if (targetPos)
- {
- LLVector3 skyward(0.f, 0.f, 1.f);
- LLVector3 left;
- LLVector3 up;
-
- eye_look_at = *targetPos;
- has_eye_target = TRUE;
- F32 lookAtDistance = eye_look_at.normVec();
-
- left.setVec(skyward % eye_look_at);
- up.setVec(eye_look_at % left);
-
- target_eye_rot = LLQuaternion(eye_look_at, left, up);
- // convert target rotation to head-local coordinates
- target_eye_rot *= ~mHeadJoint->getWorldRotation();
- // eliminate any Euler roll - we're lucky that roll is applied last.
- F32 roll, pitch, yaw;
- target_eye_rot.getEulerAngles(&roll, &pitch, &yaw);
- target_eye_rot.setQuat(0.0f, pitch, yaw);
- // constrain target orientation to be in front of avatar's face
- target_eye_rot.constrain(EYE_ROT_LIMIT_ANGLE);
-
- // calculate vergence
- F32 interocular_dist = (mLeftEyeState->getJoint()->getWorldPosition() - mRightEyeState->getJoint()->getWorldPosition()).magVec();
- vergence = -atan2((interocular_dist / 2.f), lookAtDistance);
- llclamp(vergence, -F_PI_BY_TWO, 0.f);
- }
- else
- {
- target_eye_rot = LLQuaternion::DEFAULT;
- vergence = 0.f;
- }
-
- //RN: subtract 4 degrees to account for foveal angular offset relative to pupil
- vergence += 4.f * DEG_TO_RAD;
-
- // calculate eye jitter
- LLQuaternion eye_jitter_rot;
-
- // vergence not too high...
- if (vergence > -0.05f)
- {
- //...go ahead and jitter
- eye_jitter_rot.setQuat(0.f, mEyeJitterPitch + mEyeLookAwayPitch, mEyeJitterYaw + mEyeLookAwayYaw);
- }
- else
- {
- //...or don't
- eye_jitter_rot.loadIdentity();
- }
-
- // calculate vergence of eyes as an object gets closer to the avatar's head
- LLQuaternion vergence_quat;
-
- if (has_eye_target)
- {
- vergence_quat.setQuat(vergence, LLVector3(0.f, 0.f, 1.f));
- }
- else
- {
- vergence_quat.loadIdentity();
- }
-
- // calculate eye rotations
- LLQuaternion left_eye_rot = target_eye_rot;
- left_eye_rot = vergence_quat * eye_jitter_rot * left_eye_rot;
-
- LLQuaternion right_eye_rot = target_eye_rot;
- vergence_quat.transQuat();
- right_eye_rot = vergence_quat * eye_jitter_rot * right_eye_rot;
-
- mLeftEyeState->setRotation( left_eye_rot );
- mRightEyeState->setRotation( right_eye_rot );
+ adjustEyeTarget(targetPos, *mLeftEyeState, *mRightEyeState);
+ adjustEyeTarget(targetPos, *mAltLeftEyeState, *mAltRightEyeState);
return TRUE;
}
@@ -519,11 +550,23 @@ void LLEyeMotion::onDeactivate()
joint->setRotation(LLQuaternion::DEFAULT);
}
+ joint = mAltLeftEyeState->getJoint();
+ if (joint)
+ {
+ joint->setRotation(LLQuaternion::DEFAULT);
+ }
+
joint = mRightEyeState->getJoint();
if (joint)
{
joint->setRotation(LLQuaternion::DEFAULT);
}
+
+ joint = mAltRightEyeState->getJoint();
+ if (joint)
+ {
+ joint->setRotation(LLQuaternion::DEFAULT);
+ }
}
// End
diff --git a/indra/llcharacter/llheadrotmotion.h b/indra/llcharacter/llheadrotmotion.h
index 569dbef2dd..53ae1813bc 100644
--- a/indra/llcharacter/llheadrotmotion.h
+++ b/indra/llcharacter/llheadrotmotion.h
@@ -176,6 +176,8 @@ public:
// it will be deactivated
virtual BOOL onActivate();
+ void adjustEyeTarget(LLVector3* targetPos, LLJointState& left_eye_state, LLJointState& right_eye_state);
+
// called per time step
// must return TRUE while it is active, and
// must return FALSE when the motion is completed.
@@ -193,6 +195,8 @@ public:
LLJoint *mHeadJoint;
LLPointer<LLJointState> mLeftEyeState;
LLPointer<LLJointState> mRightEyeState;
+ LLPointer<LLJointState> mAltLeftEyeState;
+ LLPointer<LLJointState> mAltRightEyeState;
LLFrameTimer mEyeJitterTimer;
F32 mEyeJitterTime;
diff --git a/indra/llcharacter/lljoint.cpp b/indra/llcharacter/lljoint.cpp
index f764b53ba5..d2a5c59023 100644
--- a/indra/llcharacter/lljoint.cpp
+++ b/indra/llcharacter/lljoint.cpp
@@ -361,8 +361,11 @@ void LLJoint::setPosition( const LLVector3& requested_pos, bool apply_attachment
LL_DEBUGS("Avatar") << "CONTEXT:\n" << "====================\n" << con_status << "====================" << LL_ENDL;
LL_DEBUGS("Avatar") << "STACK:\n" << "====================\n" << cs << "====================" << LL_ENDL;
}
- mXform.setPosition(pos);
- touch(MATRIX_DIRTY | POSITION_DIRTY);
+ if (pos != getPosition())
+ {
+ mXform.setPosition(pos);
+ touch(MATRIX_DIRTY | POSITION_DIRTY);
+ }
}
void LLJoint::setDefaultPosition( const LLVector3& pos )
@@ -418,12 +421,19 @@ bool above_joint_scale_threshold(const LLVector3& diff)
//--------------------------------------------------------------------
// addAttachmentPosOverride()
//--------------------------------------------------------------------
-void LLJoint::addAttachmentPosOverride( const LLVector3& pos, const LLUUID& mesh_id, const std::string& av_info )
+void LLJoint::addAttachmentPosOverride( const LLVector3& pos, const LLUUID& mesh_id, const std::string& av_info, bool& active_override_changed )
{
+ active_override_changed = false;
if (mesh_id.isNull())
{
return;
}
+ // BENTO
+ // Not clear pelvis overrides are meaningful/useful.
+ //if (mName == "mPelvis")
+ //{
+ // return;
+ //}
if (!above_joint_pos_threshold(pos-getDefaultPosition()))
{
if (do_debug_joint(getName()))
@@ -433,6 +443,10 @@ void LLJoint::addAttachmentPosOverride( const LLVector3& pos, const LLUUID& mesh
}
return;
}
+
+ LLVector3 before_pos;
+ LLUUID before_mesh_id;
+ bool has_active_override_before = hasAttachmentPosOverride( before_pos, before_mesh_id );
if (!m_attachmentPosOverrides.count())
{
if (do_debug_joint(getName()))
@@ -442,31 +456,49 @@ void LLJoint::addAttachmentPosOverride( const LLVector3& pos, const LLUUID& mesh
m_posBeforeOverrides = getPosition();
}
m_attachmentPosOverrides.add(mesh_id,pos);
- if (do_debug_joint(getName()))
- {
- LL_DEBUGS("Avatar") << "av " << av_info << " joint " << getName() << " addAttachmentPosOverride for mesh " << mesh_id << " pos " << pos << LL_ENDL;
- }
- updatePos(av_info);
+ LLVector3 after_pos;
+ LLUUID after_mesh_id;
+ hasAttachmentPosOverride(after_pos, after_mesh_id);
+ if (!has_active_override_before || (after_pos != before_pos))
+ {
+ active_override_changed = true;
+ if (do_debug_joint(getName()))
+ {
+ LL_DEBUGS("Avatar") << "av " << av_info << " joint " << getName() << " addAttachmentPosOverride for mesh " << mesh_id << " pos " << pos << LL_ENDL;
+ }
+ updatePos(av_info);
+ }
}
//--------------------------------------------------------------------
// removeAttachmentPosOverride()
//--------------------------------------------------------------------
-void LLJoint::removeAttachmentPosOverride( const LLUUID& mesh_id, const std::string& av_info )
+void LLJoint::removeAttachmentPosOverride( const LLUUID& mesh_id, const std::string& av_info, bool& active_override_changed )
{
+ active_override_changed = false;
if (mesh_id.isNull())
{
return;
}
+ LLVector3 before_pos;
+ LLUUID before_mesh_id;
+ hasAttachmentPosOverride( before_pos, before_mesh_id );
if (m_attachmentPosOverrides.remove(mesh_id))
{
- if (do_debug_joint(getName()))
- {
- LL_DEBUGS("Avatar") << "av " << av_info << " joint " << getName()
- << " removeAttachmentPosOverride for " << mesh_id << LL_ENDL;
- showJointPosOverrides(*this, "remove", av_info);
- }
- updatePos(av_info);
+ LLVector3 after_pos;
+ LLUUID after_mesh_id;
+ bool has_active_override_after = hasAttachmentPosOverride(after_pos, after_mesh_id);
+ if (!has_active_override_after || (after_pos != before_pos))
+ {
+ active_override_changed = true;
+ if (do_debug_joint(getName()))
+ {
+ LL_DEBUGS("Avatar") << "av " << av_info << " joint " << getName()
+ << " removeAttachmentPosOverride for " << mesh_id << LL_ENDL;
+ showJointPosOverrides(*this, "remove", av_info);
+ }
+ updatePos(av_info);
+ }
}
}
diff --git a/indra/llcharacter/lljoint.h b/indra/llcharacter/lljoint.h
index bee968f249..509523ae4b 100644
--- a/indra/llcharacter/lljoint.h
+++ b/indra/llcharacter/lljoint.h
@@ -40,9 +40,10 @@
#include "xform.h"
const S32 LL_CHARACTER_MAX_JOINTS_PER_MESH = 15;
-// BENTO JOINT COUNT LIMIT - need to set this to final skeleton size
-// (bones + attachments) + 2, rounded to next multiple of 4.
-const U32 LL_CHARACTER_MAX_ANIMATED_JOINTS = 192; // must be divisible by 4!
+// Need to set this to count of animate-able joints,
+// currently = #bones + #collision_volumes + #attachments + 2,
+// rounded to next multiple of 4.
+const U32 LL_CHARACTER_MAX_ANIMATED_JOINTS = 216; // must be divisible by 4!
const U32 LL_MAX_JOINTS_PER_MESH_OBJECT = 110;
// These should be higher than the joint_num of any
@@ -265,8 +266,8 @@ public:
virtual BOOL isAnimatable() const { return TRUE; }
- void addAttachmentPosOverride( const LLVector3& pos, const LLUUID& mesh_id, const std::string& av_info );
- void removeAttachmentPosOverride( const LLUUID& mesh_id, const std::string& av_info );
+ void addAttachmentPosOverride( const LLVector3& pos, const LLUUID& mesh_id, const std::string& av_info, bool& active_override_changed );
+ void removeAttachmentPosOverride( const LLUUID& mesh_id, const std::string& av_info, bool& active_override_changed );
bool hasAttachmentPosOverride( LLVector3& pos, LLUUID& mesh_id ) const;
void clearAttachmentPosOverrides();
void showAttachmentPosOverrides(const std::string& av_info) const;
diff --git a/indra/llcharacter/llkeyframemotion.cpp b/indra/llcharacter/llkeyframemotion.cpp
index 052ca3be58..d16c2731b3 100644
--- a/indra/llcharacter/llkeyframemotion.cpp
+++ b/indra/llcharacter/llkeyframemotion.cpp
@@ -498,6 +498,7 @@ LLMotion::LLMotionInitStatus LLKeyframeMotion::onInitialize(LLCharacter *charact
// request asset
mAssetStatus = ASSET_FETCHED;
+ LL_DEBUGS("Animation") << "Requesting data fetch for: " << mID << LL_ENDL;
character_id = new LLUUID(mCharacter->getID());
gAssetStorage->getAssetData(mID,
LLAssetType::AT_ANIMATION,
@@ -2257,8 +2258,8 @@ void LLKeyframeMotion::onLoadComplete(LLVFS *vfs,
U8* buffer = new U8[size];
file.read((U8*)buffer, size); /*Flawfinder: ignore*/
-
- LL_DEBUGS() << "Loading keyframe data for: " << motionp->getName() << ":" << motionp->getID() << " (" << size << " bytes)" << LL_ENDL;
+
+ LL_DEBUGS("Animation") << "Loading keyframe data for: " << motionp->getName() << ":" << motionp->getID() << " (" << size << " bytes)" << LL_ENDL;
LLDataPackerBinaryBuffer dp(buffer, size);
if (motionp->deserialize(dp))