Files
Cyd 2b8ca921cb Initial full mirror of c:\VWE (source + assets + toolchain + outputs) via Git LFS
Complete disaster-recovery snapshot: engine/game source, game data assets,
VC6 toolchain + DX SDKs, build outputs, deployed game, and _UNUSED archive.
Large binaries in Git LFS; text preserved byte-for-byte (core.autocrlf=false,
no eol attributes). See RECOVERY.md for the one-clone rebuild procedure.
2026-06-24 21:28:16 -05:00

370 lines
9.5 KiB
C++

//===========================================================================//
// File: EyePointManager.hpp
// Project: MechWarrior 4
// Contents:
//
//---------------------------------------------------------------------------//
// Date Who Modification //
// -------- --- ---------------------------------------------------------- //
// 03/20/00 JSE Initial coding,
//---------------------------------------------------------------------------//
// Copyright (C) 2000, Microsoft Corp.
// All Rights reserved worldwide
// This unpublished sourcecode is PROPRIETARY and CONFIDENTIAL
//===========================================================================//
#include "MW4Headers.hpp"
#include "EyePointManager.hpp"
#include "mech.hpp"
//#############################################################################
//########################### EyePointManager ###############################
//#############################################################################
EyePointManager::ClassData*
EyePointManager::DefaultData = NULL;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void
EyePointManager::InitializeClass()
{
Verify(!DefaultData);
DefaultData =
new ClassData(
EyePointManagerClassID,
"MechWarrior4::EyePointManager",
Receiver::DefaultData,
0,
NULL
);
Check_Object(DefaultData);
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void
EyePointManager::TerminateClass()
{
Check_Object(DefaultData);
delete DefaultData;
DefaultData = NULL;
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
EyePointManager::EyePointManager(Mech *parent) :
Adept::Receiver(DefaultData)
{
m_parentMech = parent;
initilized = false;
m_eyeJoint = NULL;
m_jointWorld = NULL;
m_eyeParent = NULL;
m_springOffset = LinearMatrix4D::Identity;
m_eyeDirection = LinearMatrix4D::Identity;
m_originalEyeToParent = LinearMatrix4D::Identity;
m_originalEyeToTorso = LinearMatrix4D::Identity;
m_originalTorsoToRoot = LinearMatrix4D::Identity;
m_torsoRotation = LinearMatrix4D::Identity;
eyeState = StabalizedMode;
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
EyePointManager::~EyePointManager()
{
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void EyePointManager::Stabalize(Stuff::Scalar time)
{
if (eyeState == ToFollowMode || eyeState == FollowMode)
{
eyeState = ToStabalizedMode;
transitionTimer = 0.0f;
transitionTime = time;
}
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void EyePointManager::Follow(Stuff::Scalar time)
{
if (eyeState == ToStabalizedMode || eyeState == StabalizedMode)
{
eyeState = ToFollowMode;
transitionTimer = 0.0f;
transitionTime = time;
}
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void EyePointManager::PostCollisionExecute(Stuff::Scalar time_slice)
{
POSTCOLLISION_LOGIC("EyePoint Manager");
if (!initilized)
{
initilized = true;
m_jointWorld = m_parentMech->FindChildMover("joint_WORLD");
Check_Object(m_jointWorld);
m_eyeJoint = m_parentMech->FindChildMover("site_eyepoint");
Check_Object(m_eyeJoint);
MWMover *torso_joint = m_parentMech->FindChildMover("joint_torso");
Check_Object(torso_joint);
m_eyeParent = Cast_Object(MWMover *, m_eyeJoint->GetParentEntity());
m_springOffset = LinearMatrix4D::Identity;
m_eyeDirection = LinearMatrix4D::Identity;
m_originalEyeToParent = m_eyeJoint->GetLocalToParent();
LinearMatrix4D world_to_root;
world_to_root.Invert(m_jointWorld->GetLocalToWorld());
LinearMatrix4D world_to_torso;
world_to_torso.Invert(torso_joint->GetLocalToWorld());
m_originalEyeToTorso.Multiply(m_eyeJoint->GetLocalToWorld(), world_to_torso);
m_originalTorsoToRoot.Multiply(torso_joint->GetLocalToWorld(), world_to_root);
}
if (!m_parentMech->usingEyeSpring)
{
POSTCOLLISION_LOGIC("EyePoint Manager::External");
LinearMatrix4D eye_to_parent;
eye_to_parent.Multiply(m_eyeDirection, m_originalEyeToParent);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
return;
}
switch(eyeState)
{
case StabalizedMode:
{
POSTCOLLISION_LOGIC("EyePoint Manager::Stabalized Mode");
LinearMatrix4D eye_to_parent;
CalculateStabalizedEye(eye_to_parent);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
}
break;
case FollowMode:
{
POSTCOLLISION_LOGIC("EyePoint Manager::Follow Mode");
LinearMatrix4D eye_to_parent;
CalculateFollowEye(eye_to_parent);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
}
break;
case ToFollowMode:
{
POSTCOLLISION_LOGIC("EyePoint Manager::To Follow Mode");
transitionTimer += time_slice;
if (transitionTimer > transitionTime)
{
eyeState = FollowMode;
LinearMatrix4D eye_to_parent;
CalculateFollowEye(eye_to_parent);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
time_slice = transitionTime;
}
else
{
LinearMatrix4D stab_eye_to_parent;
CalculateStabalizedEye(stab_eye_to_parent);
LinearMatrix4D fol_eye_to_parent;
CalculateFollowEye(fol_eye_to_parent);
Scalar lerp = transitionTimer/transitionTime;
UnitQuaternion start_rot;
start_rot = stab_eye_to_parent;
UnitQuaternion stop_rot;
stop_rot = fol_eye_to_parent;
UnitQuaternion lerp_rot;
lerp_rot.Lerp(start_rot, stop_rot, lerp);
Point3D start_pos(stab_eye_to_parent);
Point3D end_pos(fol_eye_to_parent);
Point3D lerp_pos;
lerp_pos.Lerp(start_pos, end_pos, lerp);
LinearMatrix4D eye_to_parent;
eye_to_parent.BuildRotation(lerp_rot);
eye_to_parent.BuildTranslation(lerp_pos);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
}
}
break;
case ToStabalizedMode:
{
POSTCOLLISION_LOGIC("EyePoint Manager::To Stabalized Mode");
transitionTimer += time_slice;
if (transitionTimer > transitionTime)
{
eyeState = StabalizedMode;
LinearMatrix4D eye_to_parent;
CalculateStabalizedEye(eye_to_parent);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
time_slice = transitionTime;
}
else
{
LinearMatrix4D stab_eye_to_parent;
CalculateStabalizedEye(stab_eye_to_parent);
LinearMatrix4D fol_eye_to_parent;
CalculateFollowEye(fol_eye_to_parent);
Scalar lerp = transitionTimer/transitionTime;
UnitQuaternion start_rot;
start_rot = fol_eye_to_parent;
UnitQuaternion stop_rot;
stop_rot = stab_eye_to_parent;
UnitQuaternion lerp_rot;
lerp_rot.Lerp(start_rot, stop_rot, lerp);
Point3D start_pos(fol_eye_to_parent);
Point3D end_pos(stab_eye_to_parent);
Point3D lerp_pos;
lerp_pos.Lerp(start_pos, end_pos, lerp);
LinearMatrix4D eye_to_parent;
eye_to_parent.BuildRotation(lerp_rot);
eye_to_parent.BuildTranslation(lerp_pos);
m_eyeJoint->SetNewLocalToParent(eye_to_parent);
m_eyeJoint->SyncMatrices(true);
}
}
break;
}
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void EyePointManager::CalculateStabalizedEye(LinearMatrix4D &eye_to_parent)
{
// build the matrix for the eye to root matrix
POSTCOLLISION_LOGIC("EyePoint Manager::Calc Stabalized");
LinearMatrix4D eye_to_root;
LinearMatrix4D temp1;
LinearMatrix4D temp2;
// move to the torso and rotate
temp1.Multiply(m_torsoRotation, m_originalTorsoToRoot);
// move up the chain to the eye
temp2.Multiply(m_originalEyeToTorso, temp1);
// put in the spring
temp1.Multiply(m_springOffset, temp2);
// put in the eye direction
eye_to_root.Multiply(m_eyeDirection, temp1);
// move the eye into world space
LinearMatrix4D eye_to_world;
eye_to_world.Multiply(eye_to_root, m_jointWorld->GetLocalToWorld());
// make the matrix to move the world point into parent space
LinearMatrix4D world_to_parent;
world_to_parent.Invert(m_eyeParent->GetLocalToWorld());
// move the world eye point into eye space
eye_to_parent.Multiply(eye_to_world, world_to_parent);
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void EyePointManager::CalculateFollowEye(LinearMatrix4D &eye_to_parent)
{
POSTCOLLISION_LOGIC("EyePoint Manager::Calc Follow");
LinearMatrix4D temp1;
LinearMatrix4D temp2;
//start with the generic position
temp1 = m_originalEyeToParent;
// put in the spring
temp2.Multiply(m_springOffset, temp1);
// put in the eye direction
eye_to_parent.Multiply(m_eyeDirection, temp2);
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void
EyePointManager::Reuse()
{
Check_Object(this);
m_springOffset = LinearMatrix4D::Identity;
m_eyeDirection = LinearMatrix4D::Identity;
m_torsoRotation = LinearMatrix4D::Identity;
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void
EyePointManager::TestInstance()
{
Verify(IsDerivedFrom(DefaultData));
}