mirror of
https://github.com/blendogames/quadrilateralcowboy.git
synced 2024-12-03 01:13:11 +00:00
701 lines
16 KiB
C++
701 lines
16 KiB
C++
|
|
#include "../idlib/precompiled.h"
|
|
#pragma hdrstop
|
|
|
|
#include "Game_local.h"
|
|
|
|
#define WALKSPEED 9 //was 9
|
|
#define WALKBOUNCE 6 //if hit an obstacle then bounce a bit to dislodge itself.
|
|
#define DIST_MOD 0.11f
|
|
#define MAXPITCH 50
|
|
#define MAXROLL 50
|
|
#define OFFROADTIME 200
|
|
|
|
#define JUMPDISTANCE 192
|
|
#define JUMPHEIGHT 256
|
|
|
|
#define PLUGMOVETIME 0.2f
|
|
|
|
#define JUMP_STARTTIME 400
|
|
|
|
const idEventDef EV_weevil_forward( "weevilforward", "d" );
|
|
const idEventDef EV_weevil_turn( "weevilturn", "d" );
|
|
const idEventDef EV_weevil_stop( "weevilstop" );
|
|
const idEventDef EV_weevil_stand( "weevilstand" );
|
|
const idEventDef EV_weevil_light( "weevillight", "d" );
|
|
const idEventDef EV_weevil_jump( "weeviljump" );
|
|
const idEventDef EV_weevil_gravity( "weevilgravity", "d" );
|
|
const idEventDef EV_weevil_getgravity( "weevilgetgravity", NULL, 'd' );
|
|
const idEventDef EV_weevil_doplug( "weevildoplug", "de" );
|
|
const idEventDef EV_weevil_plugConnected( "<weevilPlugConnected>", "v" );
|
|
const idEventDef EV_weevil_isPlugConnected( "isweevilplugconnected", NULL, 'd' );
|
|
const idEventDef EV_weevil_eyemove("weevileyemove", "ffd", 'd');
|
|
|
|
|
|
CLASS_DECLARATION( idMoveableItem, idWeevil )
|
|
EVENT( EV_weevil_forward, idWeevil::Event_forward )
|
|
EVENT( EV_weevil_turn, idWeevil::Event_turn )
|
|
EVENT( EV_weevil_stop, idWeevil::Event_stop )
|
|
EVENT( EV_weevil_stand, idWeevil::Event_stand )
|
|
EVENT( EV_weevil_light, idWeevil::Event_light )
|
|
EVENT( EV_weevil_jump, idWeevil::Event_jump )
|
|
EVENT( EV_weevil_gravity, idWeevil::Event_gravity )
|
|
EVENT( EV_weevil_getgravity, idWeevil::Event_getgravity )
|
|
EVENT( EV_weevil_doplug, idWeevil::Event_doPlug )
|
|
EVENT( EV_weevil_plugConnected, idWeevil::Event_plugdone)
|
|
EVENT( EV_weevil_isPlugConnected, idWeevil::Event_isweevilplugconnected)
|
|
EVENT( EV_weevil_eyemove, idWeevil::Event_weevilEyeMove)
|
|
END_CLASS
|
|
|
|
|
|
void idWeevil::Save( idSaveGame *savefile ) const
|
|
{
|
|
savefile->WriteBool(isGravity);
|
|
savefile->WriteInt(state);
|
|
savefile->WriteInt(walkDirection);
|
|
savefile->WriteInt(turnCurrent);
|
|
savefile->WriteInt(turnTarget);
|
|
savefile->WriteInt(turnDirection);
|
|
savefile->WriteInt(offroadTimer);
|
|
savefile->WriteInt(jumpstartTimer);
|
|
savefile->WriteVec3(lastPosition);
|
|
|
|
savefile->WriteObject(model);
|
|
savefile->WriteObject(nosecam);
|
|
savefile->WriteObject(light);
|
|
|
|
savefile->WriteObject(plugModel);
|
|
savefile->WriteObject(beamStart);
|
|
savefile->WriteObject(beamEnd);
|
|
savefile->WriteJoint(headJoint);
|
|
}
|
|
|
|
void idWeevil::Restore( idRestoreGame *savefile )
|
|
{
|
|
savefile->ReadBool(isGravity);
|
|
savefile->ReadInt(state);
|
|
savefile->ReadInt(walkDirection);
|
|
savefile->ReadInt(turnCurrent);
|
|
savefile->ReadInt(turnTarget);
|
|
savefile->ReadInt(turnDirection);
|
|
savefile->ReadInt(offroadTimer);
|
|
savefile->ReadInt(jumpstartTimer);
|
|
savefile->ReadVec3(lastPosition);
|
|
|
|
savefile->ReadObject(reinterpret_cast<idClass *&>(model));
|
|
savefile->ReadObject(reinterpret_cast<idClass *&>(nosecam));
|
|
savefile->ReadObject(reinterpret_cast<idClass *&>(light));
|
|
|
|
savefile->ReadObject(reinterpret_cast<idClass *&>(plugModel));
|
|
savefile->ReadObject(reinterpret_cast<idClass *&>(beamStart));
|
|
savefile->ReadObject(reinterpret_cast<idClass *&>(beamEnd));
|
|
savefile->ReadJoint(headJoint);
|
|
}
|
|
|
|
|
|
void idWeevil::Spawn( void )
|
|
{
|
|
idDict args;
|
|
|
|
jointHandle_t noseJoint;
|
|
idVec3 nosePos;
|
|
idMat3 noseAxis;
|
|
idVec3 forward;
|
|
|
|
|
|
state = 0;
|
|
walkDirection = 1;
|
|
turnCurrent = 0;
|
|
turnTarget = 0;
|
|
turnDirection = 1;
|
|
offroadTimer = 0;
|
|
jumpstartTimer = 0;
|
|
lastPosition = vec3_zero;
|
|
isGravity = true;
|
|
|
|
|
|
|
|
BecomeActive( TH_THINK );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//MODEL
|
|
this->GetPhysics()->GetAxis().ToAngles().ToVectors(&forward);
|
|
|
|
args.Clear();
|
|
args.SetVector( "origin", this->GetPhysics()->GetOrigin() );
|
|
args.Set( "model", "monster_weevil" );
|
|
args.Set( "cycle", "-1" );
|
|
//args.Set( "notriggeronanim", "1" );
|
|
model = ( idAnimatedEntity * )gameLocal.SpawnEntityType( idAnimatedEntity::Type, &args );
|
|
model->SetAxis( this->GetPhysics()->GetAxis() );
|
|
|
|
|
|
// BEAMS / PLUGS
|
|
args.Clear();
|
|
args.Set( "model", "models/datajack_plug/tris.ase" );
|
|
args.SetBool( "solid", 0);
|
|
plugModel = ( idMover * )gameLocal.SpawnEntityType( idMover::Type, &args );
|
|
plugModel->Hide();
|
|
|
|
args.Clear();
|
|
args.SetInt( "start_off", 1);
|
|
beamEnd = ( idBeam * )gameLocal.SpawnEntityType( idBeam::Type );
|
|
|
|
args.Clear();
|
|
args.Set( "target", beamEnd->name.c_str() );
|
|
args.Set( "skin", "skins/beam_black");
|
|
args.SetInt( "start_off", 1);
|
|
beamStart = ( idBeam * )gameLocal.SpawnEntityType( idBeam::Type, &args );
|
|
beamStart->Hide();
|
|
beamStart->Event_SetWidth(0.5f);
|
|
|
|
idVec3 selfForward, selfUp;
|
|
idAngles selfAng = this->GetPhysics()->GetAxis().ToAngles();
|
|
selfAng.ToVectors(&selfForward, NULL, &selfUp);
|
|
idVec3 attachPoint = this->GetPhysics()->GetOrigin() + (selfForward * -3) + (selfUp * 7);
|
|
|
|
|
|
|
|
beamStart->SetOrigin(attachPoint );
|
|
beamStart->Bind( this, false );
|
|
|
|
|
|
|
|
|
|
idVec3 plugForward;
|
|
idAngles plugAng = plugModel->GetPhysics()->GetAxis().ToAngles();
|
|
selfAng.ToVectors(&plugForward, NULL, NULL);
|
|
idVec3 plugEndPoint = plugModel->GetPhysics()->GetOrigin() + (plugForward * 0.9f);
|
|
|
|
beamEnd->SetOrigin(plugEndPoint);
|
|
beamEnd->Bind(plugModel, false);
|
|
beamEnd->Hide();
|
|
|
|
|
|
|
|
model->Bind(this, true);
|
|
|
|
|
|
|
|
//nose camera.
|
|
noseJoint = model->GetAnimator()->GetJointHandle( "head" );
|
|
model->GetAnimator()->GetJointTransform( noseJoint, gameLocal.time, nosePos, noseAxis );
|
|
|
|
args.Clear();
|
|
args.SetVector( "origin", nosePos + this->GetPhysics()->GetOrigin() + (forward * -2));
|
|
args.Set( "classname", "func_cameraview" );
|
|
gameLocal.SpawnEntityDef( args, &nosecam );
|
|
nosecam->BindToJoint(model, noseJoint, true);
|
|
nosecam->BecomeActive(TH_PHYSICS);
|
|
this->spawnArgs.Set("nosecamera_name", nosecam->GetName());
|
|
|
|
|
|
//spawn light.
|
|
args.Clear();
|
|
args.SetVector( "origin", nosePos + this->GetPhysics()->GetOrigin() + (forward * 0.9f) );
|
|
args.Set( "light_target", "1 0 -0.3" );
|
|
args.Set( "light_up", "0 0 1" );
|
|
args.Set( "light_right", "0 -1.5 0" );
|
|
args.Set( "light_end", "128 0 0" );
|
|
args.Set( "texture", "lights/monitorglow" );
|
|
args.Set("start_off", "1");
|
|
args.SetInt("alarmlight", 0);
|
|
light = ( idLight * )gameLocal.SpawnEntityType( idLight::Type, &args );
|
|
light->Bind(this, true);
|
|
|
|
|
|
|
|
headJoint = model->GetAnimator()->GetJointHandle( "head" );
|
|
|
|
|
|
}
|
|
|
|
bool idWeevil::isJumping( void )
|
|
{
|
|
if (jumpstartTimer > gameLocal.time)
|
|
return true;
|
|
|
|
return false;
|
|
}
|
|
|
|
void idWeevil::OnGet( void )
|
|
{
|
|
gameLocal.KillCCTVs();
|
|
|
|
beamStart->PostEventMS( &EV_Remove, 0 );
|
|
beamEnd->PostEventMS( &EV_Remove, 0 );
|
|
plugModel->PostEventMS( &EV_Remove, 0 );
|
|
}
|
|
|
|
void idWeevil::Event_isweevilplugconnected( void )
|
|
{
|
|
if (plugModel->IsHidden())
|
|
idThread::ReturnInt(0);
|
|
else
|
|
idThread::ReturnInt(1);
|
|
}
|
|
|
|
void idWeevil::Event_plugdone( idVec3 const &position )
|
|
{
|
|
idDict args;
|
|
|
|
args.Clear();
|
|
args.SetVector( "origin", position );
|
|
args.Set( "model", spawnArgs.GetString("smoke_plug", "plugconnect.prt") );
|
|
args.SetBool( "start_off", false );
|
|
gameLocal.SpawnEntityType( idExplodable::Type, &args );
|
|
|
|
StartSound( "snd_plugin", SND_CHANNEL_ANY, 0, false, NULL );
|
|
}
|
|
|
|
void idWeevil::Event_doPlug( int active, idEntity *jackEnt )
|
|
{
|
|
if (active <= 0)
|
|
{
|
|
//unplug.
|
|
beamStart->Hide();
|
|
plugModel->Hide();
|
|
return;
|
|
}
|
|
|
|
//plug in.
|
|
plugModel->GetPhysics()->SetAxis( jackEnt->GetPhysics()->GetAxis() );
|
|
|
|
idVec3 jackForward, jackUp;
|
|
idAngles selfAng = jackEnt->GetPhysics()->GetAxis().ToAngles();
|
|
selfAng.ToVectors(&jackForward, NULL, &jackUp);
|
|
idVec3 jackEndPos = jackEnt->GetPhysics()->GetOrigin() + (jackForward * 0.4) + (jackUp * 1.1);
|
|
|
|
|
|
//gameRenderWorld->DebugLine(idVec4(0,1,0,1), plugModel->GetPhysics()->GetOrigin(), plugModel->GetPhysics()->GetOrigin() + idVec3(0,0,128), 10000);
|
|
|
|
|
|
//gameRenderWorld->DebugLine(idVec4(1,1,0,1), jackEndPos, jackEndPos + idVec3(0,0,128), 10000);
|
|
|
|
|
|
idVec3 weevilUp;
|
|
idAngles weevilAng = this->GetPhysics()->GetAxis().ToAngles();
|
|
weevilAng.ToVectors(NULL, NULL, &weevilUp);
|
|
plugModel->SetOrigin( this->GetPhysics()->GetOrigin() + (weevilUp * 6) );
|
|
|
|
plugModel->Event_SetMoveTime(PLUGMOVETIME);
|
|
plugModel->Event_MoveToPos(jackEndPos);
|
|
PostEventSec( &EV_weevil_plugConnected, PLUGMOVETIME, jackEndPos);
|
|
|
|
|
|
beamEnd->Show();
|
|
beamStart->Show();
|
|
plugModel->Show();
|
|
}
|
|
|
|
void idWeevil::Event_jump( void )
|
|
{
|
|
Event_stand();
|
|
|
|
state = JUMPSTART;
|
|
this->Event_PlayAnim("jump_start", false);
|
|
jumpstartTimer = gameLocal.time + JUMP_STARTTIME;
|
|
|
|
StartSound( "snd_jump", SND_CHANNEL_ANY, 0, false, NULL );
|
|
}
|
|
|
|
void idWeevil::Event_getgravity( )
|
|
{
|
|
if (this->isGravity <= 0)
|
|
{
|
|
idThread::ReturnInt( 0 );
|
|
}
|
|
else
|
|
{
|
|
idThread::ReturnInt( 1 );
|
|
}
|
|
}
|
|
|
|
void idWeevil::Event_gravity( int value )
|
|
{
|
|
if (value <= 0)
|
|
{
|
|
//gravity is now OFF.
|
|
this->isGravity = 0;
|
|
lastGravityState = false;
|
|
}
|
|
else
|
|
{
|
|
//turn on gravity.
|
|
this->isGravity = 1;
|
|
}
|
|
|
|
if (value >= 1)
|
|
{
|
|
//turn on gravity.
|
|
physicsObj.SetGravity( gameLocal.GetGravity() );
|
|
}
|
|
}
|
|
|
|
void idWeevil::Event_light( int value )
|
|
{
|
|
if (value)
|
|
{
|
|
if ( !light->isOn )
|
|
{
|
|
StartSound( "snd_light", SND_CHANNEL_ANY, 0, false, NULL );
|
|
}
|
|
|
|
light->On();
|
|
}
|
|
else
|
|
{
|
|
if ( light->isOn )
|
|
{
|
|
StartSound( "snd_light", SND_CHANNEL_ANY, 0, false, NULL );
|
|
}
|
|
|
|
light->Off();
|
|
}
|
|
}
|
|
|
|
|
|
void idWeevil::Event_stand( void )
|
|
{
|
|
CancelEvents( &EV_weevil_stop );
|
|
state = IDLE;
|
|
|
|
if (!isGravity)
|
|
{
|
|
return;
|
|
}
|
|
|
|
idAngles ang = this->GetPhysics()->GetAxis().ToAngles();
|
|
ang.pitch = 0;
|
|
ang.roll = 0;
|
|
this->GetPhysics()->SetAxis( ang.ToMat3() );
|
|
this->SetOrigin(this->GetPhysics()->GetOrigin() + idVec3(0,0,3.0f));
|
|
|
|
StartSound( "snd_stand", SND_CHANNEL_ANY, 0, false, NULL );
|
|
}
|
|
|
|
void idWeevil::Event_turn( int degrees )
|
|
{
|
|
if (degrees == 0)
|
|
{
|
|
return;
|
|
}
|
|
|
|
CancelEvents( &EV_weevil_stop );
|
|
state = TURNING;
|
|
|
|
turnCurrent = 0;
|
|
turnTarget = idMath::Abs(degrees);
|
|
|
|
if (degrees > 0)
|
|
{
|
|
turnDirection = -1;
|
|
|
|
}
|
|
else
|
|
{
|
|
turnDirection = 1;
|
|
}
|
|
|
|
Event_PlayAnim("turning", true);
|
|
|
|
//this->Event_PlayAnim( "idle", false );
|
|
}
|
|
|
|
void idWeevil::Event_forward( int distance )
|
|
{
|
|
if (distance == 0)
|
|
{
|
|
return;
|
|
}
|
|
|
|
CancelEvents( &EV_weevil_stop );
|
|
|
|
if (distance > 0)
|
|
{
|
|
walkDirection = 1;
|
|
Event_PlayAnim("walk", true);
|
|
}
|
|
else
|
|
{
|
|
walkDirection = -1;
|
|
Event_PlayAnim("walkbackwards", true);
|
|
}
|
|
|
|
offroadTimer = gameLocal.time + OFFROADTIME;
|
|
|
|
state = WALKING;
|
|
|
|
|
|
PostEventSec( &EV_weevil_stop, idMath::Abs(distance) * DIST_MOD );
|
|
}
|
|
|
|
void idWeevil::Event_stop( void )
|
|
{
|
|
CancelEvents( &EV_weevil_stop );
|
|
state = IDLE;
|
|
Event_PlayAnim("idle", false);
|
|
}
|
|
|
|
void idWeevil::UpdateStates( void )
|
|
{
|
|
if (state == WALKING)
|
|
{
|
|
if (CanMove())
|
|
{
|
|
idVec3 curPos;
|
|
float bounceAmount;
|
|
idVec3 forward;
|
|
this->GetPhysics()->GetAxis().ToAngles().ToVectors(&forward);
|
|
forward.Normalize();
|
|
|
|
curPos = this->GetPhysics()->GetOrigin();
|
|
|
|
|
|
if (HasObstacle() ||
|
|
(idMath::Fabs(lastPosition.x - curPos.x) < 0.0001f
|
|
&& idMath::Fabs(lastPosition.y - curPos.y) < 0.0001f
|
|
&& idMath::Fabs(lastPosition.z - curPos.z) < 0.0001f))
|
|
{
|
|
//"off-road" mode.
|
|
bounceAmount = WALKBOUNCE;
|
|
}
|
|
else
|
|
{
|
|
//normal walk.
|
|
bounceAmount = 0;
|
|
}
|
|
|
|
this->GetPhysics()->SetLinearVelocity(forward * (WALKSPEED * walkDirection) + (idVec3(0,0,1) * bounceAmount));
|
|
lastPosition.x = curPos.x;
|
|
lastPosition.y = curPos.y;
|
|
lastPosition.z = curPos.z;
|
|
}
|
|
}
|
|
else if (state == TURNING)
|
|
{
|
|
idAngles ang = this->GetPhysics()->GetAxis().ToAngles();
|
|
ang.yaw += turnDirection;
|
|
|
|
turnCurrent++;
|
|
if (turnCurrent >= turnTarget)
|
|
{
|
|
Event_stop();
|
|
return;
|
|
}
|
|
|
|
if (CanMove())
|
|
{
|
|
this->GetPhysics()->SetAxis( ang.ToMat3() );
|
|
}
|
|
}
|
|
else if (state == JUMPSTART)
|
|
{
|
|
if (gameLocal.time > jumpstartTimer)
|
|
{
|
|
idVec3 forward;
|
|
idAngles ang = this->GetPhysics()->GetAxis().ToAngles();
|
|
ang.pitch = 0;
|
|
ang.roll = 0;
|
|
ang.ToVectors(&forward);
|
|
|
|
if (this->GetPhysics()->HasGroundContacts())
|
|
{
|
|
Event_stand();
|
|
this->GetPhysics()->SetLinearVelocity((forward * JUMPDISTANCE) + (idVec3(0,0,1) * JUMPHEIGHT));
|
|
}
|
|
|
|
this->Event_PlayAnim( "jump_loop", true );
|
|
state = JUMPING;
|
|
|
|
jumpstartTimer = gameLocal.time + 200; //guarantee some jump time before it is allowed to enter landing state.
|
|
}
|
|
}
|
|
else if (state == JUMPING)
|
|
{
|
|
if (this->IsGrabbed())
|
|
{
|
|
state = IDLE;
|
|
return;
|
|
}
|
|
|
|
if (this->GetPhysics()->HasGroundContacts() && gameLocal.time > jumpstartTimer)
|
|
{
|
|
state = IDLE;
|
|
|
|
Event_stand();
|
|
this->GetPhysics()->PutToRest();
|
|
|
|
this->Event_PlayAnim( "jump_end", false );
|
|
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
|
|
bool idWeevil::HasObstacle( void )
|
|
{
|
|
trace_t forwardTr;
|
|
idVec3 forward, up, right;
|
|
idVec3 traceStart;
|
|
|
|
trace_t downTr1, downTr2, downTr3;
|
|
|
|
this->GetPhysics()->GetAxis().ToAngles().ToVectors(&forward, &right, &up);
|
|
|
|
traceStart = this->GetPhysics()->GetOrigin() + (up * 1);
|
|
gameLocal.clip.TracePoint( forwardTr, traceStart, traceStart + (forward * (16 * walkDirection)), MASK_SOLID, this );
|
|
|
|
if (forwardTr.fraction < 1)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
//do the down trace to see if weevil is on a pit.
|
|
gameLocal.clip.TracePoint( downTr1, traceStart + (forward * 5), traceStart + (forward * 5) + (up * -3), MASK_SOLID, this );
|
|
if (downTr1.fraction >= 1)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
gameLocal.clip.TracePoint( downTr2, traceStart + (forward * -5), traceStart + (forward * -5) + (up * -3), MASK_SOLID, this );
|
|
if (downTr2.fraction >= 1)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
gameLocal.clip.TracePoint( downTr3, traceStart, traceStart + (up * -3), MASK_SOLID, this );
|
|
if (downTr3.fraction >= 1)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
bool idWeevil::CanMove( void )
|
|
{
|
|
idAngles angles = this->GetPhysics()->GetAxis().ToAngles();
|
|
|
|
//return false if: being held, not touching ground, pitch is tilted far, roll is tilted far.
|
|
|
|
if (this->IsGrabbed() || !this->GetPhysics()->HasGroundContacts() || idMath::Abs( angles.pitch) >= MAXPITCH || idMath::Abs(angles.roll) >= MAXROLL)
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
void idWeevil::Think( void )
|
|
{
|
|
//RunPhysics();
|
|
|
|
if (touchTriggers)
|
|
{
|
|
TouchTriggers();
|
|
}
|
|
|
|
//for the vacuum check.
|
|
//if (!isGravity)
|
|
{
|
|
idMoveableItem::Think();
|
|
}
|
|
|
|
UpdateStates();
|
|
Present();
|
|
}
|
|
|
|
|
|
|
|
void idWeevil::Present( void )
|
|
{
|
|
// don't present to the renderer if the entity hasn't changed
|
|
if ( !( thinkFlags & TH_UPDATEVISUALS ) )
|
|
{
|
|
return;
|
|
}
|
|
|
|
BecomeInactive( TH_UPDATEVISUALS );
|
|
|
|
// if set to invisible, skip
|
|
if ( !renderEntity.hModel || IsHidden() )
|
|
{
|
|
return;
|
|
}
|
|
|
|
// add to refresh list
|
|
if ( modelDefHandle == -1 )
|
|
{
|
|
modelDefHandle = gameRenderWorld->AddEntityDef( &renderEntity );
|
|
}
|
|
else
|
|
{
|
|
gameRenderWorld->UpdateEntityDef( modelDefHandle, &renderEntity );
|
|
}
|
|
}
|
|
|
|
void idWeevil::Event_PlayAnim( const char* animname, bool cycle)
|
|
{
|
|
int anim;
|
|
int channel = 0;
|
|
int animBlendFrames = 4;
|
|
int animDoneTime = 0;
|
|
|
|
anim = model->GetAnimator()->GetAnim( animname );
|
|
if ( !anim )
|
|
{
|
|
gameLocal.Warning( "missing '%s' animation on '%s' (%s)", animname, name.c_str(), GetEntityDefName() );
|
|
model->GetAnimator()->Clear( channel, gameLocal.time, FRAME2MS( animBlendFrames ) );
|
|
animDoneTime = 0;
|
|
}
|
|
else
|
|
{
|
|
if (cycle)
|
|
{
|
|
model->GetAnimator()->CycleAnim( channel, anim, gameLocal.time, FRAME2MS( animBlendFrames ) );
|
|
}
|
|
else
|
|
{
|
|
model->GetAnimator()->PlayAnim( channel, anim, gameLocal.time, FRAME2MS( animBlendFrames ) );
|
|
}
|
|
|
|
animDoneTime = model->GetAnimator()->CurrentAnim( channel )->GetEndTime();
|
|
}
|
|
|
|
animBlendFrames = 0;
|
|
}
|
|
|
|
void idWeevil::Event_weevilEyeMove(float pitch, float yaw, bool reset)
|
|
{
|
|
if (reset)
|
|
{
|
|
headAngle = idAngles(0,0,0);
|
|
model->GetAnimator()->SetJointAxis(headJoint, JOINTMOD_WORLD, headAngle.ToMat3());
|
|
idThread::ReturnInt(1);
|
|
return;
|
|
}
|
|
|
|
|
|
float newYaw = idMath::ClampFloat(-90, 90, headAngle.yaw - yaw);
|
|
float newPitch = idMath::ClampFloat(-90, 90, headAngle.roll + pitch);
|
|
|
|
if (idMath::Fabs(headAngle.roll) + idMath::Fabs(pitch) > 90 || idMath::Fabs(headAngle.yaw) + idMath::Fabs(yaw) > 90)
|
|
{
|
|
idThread::ReturnInt(0);
|
|
}
|
|
else
|
|
{
|
|
idThread::ReturnInt(1);
|
|
}
|
|
|
|
headAngle.roll = newPitch;
|
|
headAngle.yaw = newYaw;
|
|
|
|
model->GetAnimator()->SetJointAxis(headJoint, JOINTMOD_LOCAL, headAngle.ToMat3());
|
|
}
|