mirror of
https://github.com/PrimeDecomp/prime.git
synced 2025-08-06 02:55:35 +00:00
136 lines
5.1 KiB
C++
136 lines
5.1 KiB
C++
#include "MetroidPrime/ScriptObjects/CScriptActorKeyframe.hpp"
|
|
|
|
#include "MetroidPrime/BodyState/CBodyController.hpp"
|
|
#include "MetroidPrime/BodyState/CBodyStateInfo.hpp"
|
|
#include "MetroidPrime/CAnimData.hpp"
|
|
#include "MetroidPrime/CStateManager.hpp"
|
|
#include "MetroidPrime/Enemies/CPatterned.hpp"
|
|
#include "MetroidPrime/ScriptObjects/CScriptActor.hpp"
|
|
#include "MetroidPrime/ScriptObjects/CScriptPlatform.hpp"
|
|
|
|
CScriptActorKeyframe::CScriptActorKeyframe(TUniqueId uid, const rstl::string& name,
|
|
const CEntityInfo& info, int animId, bool looping,
|
|
float lifetime, bool isPassive, int fadeOut, bool active,
|
|
float totalPlayback)
|
|
: CEntity(uid, info, active, name)
|
|
, x34_animationId(animId)
|
|
, x38_initialLifetime(lifetime)
|
|
, x3c_playbackRate(totalPlayback)
|
|
, x40_lifetime(lifetime)
|
|
, x44_24_isLooped(looping)
|
|
, x44_25_isPassive(isPassive)
|
|
, x44_26_fadeOut((fadeOut << 5) & 0x20)
|
|
, x44_27_timedLoop((fadeOut << 3) & 0x10)
|
|
, x44_28_playing(false) {}
|
|
|
|
void CScriptActorKeyframe::AcceptScriptMsg(EScriptObjectMessage msg, TUniqueId uid,
|
|
CStateManager& mgr) {
|
|
switch (msg) {
|
|
case kSM_Action:
|
|
if (GetActive()) {
|
|
if (!x44_25_isPassive) {
|
|
rstl::vector< SConnection >::const_iterator conn = GetConnectionList().begin();
|
|
for (; conn != GetConnectionList().end(); ++conn) {
|
|
if (conn->x0_state != kSS_Play || conn->x4_msg != kSM_Play) {
|
|
continue;
|
|
}
|
|
|
|
CStateManager::TIdListResult search = mgr.GetIdListForScript(conn->x8_objId);
|
|
for (CStateManager::TIdList::const_iterator it = search.first; it != search.second;
|
|
++it) {
|
|
UpdateEntity(it->second, mgr);
|
|
}
|
|
}
|
|
}
|
|
|
|
x44_28_playing = true;
|
|
x40_lifetime = x38_initialLifetime;
|
|
SendScriptMsgs(kSS_Play, mgr, kSM_None);
|
|
}
|
|
break;
|
|
case kSM_InitializedInArea:
|
|
if (x34_animationId == -1)
|
|
x34_animationId = 0;
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
|
|
CEntity::AcceptScriptMsg(msg, uid, mgr);
|
|
}
|
|
|
|
void CScriptActorKeyframe::Accept(IVisitor& visitor) { visitor.Visit(*this); }
|
|
|
|
void CScriptActorKeyframe::UpdateEntity(TUniqueId uid, CStateManager& mgr) {
|
|
CEntity* ent = mgr.ObjectById(uid);
|
|
CActor* act = TCastToPtr< CScriptActor >(ent);
|
|
if (!act) {
|
|
act = TCastToPtr< CScriptPlatform >(ent);
|
|
}
|
|
if (act) {
|
|
if (!act->GetActive()) {
|
|
mgr.SendScriptMsg(act, GetUniqueId(), kSM_Activate);
|
|
}
|
|
act->SetModelFlags(CModelFlags::Normal());
|
|
if (act->HasAnimation()) {
|
|
if (act->AnimationData()->IsAdditiveAnimation(x34_animationId)) {
|
|
act->AnimationData()->AddAdditiveAnimation(x34_animationId, 1.f, x44_24_isLooped,
|
|
x44_26_fadeOut);
|
|
} else {
|
|
act->AnimationData()->SetAnimation(CAnimPlaybackParms(x34_animationId, -1, 1.f, true),
|
|
false);
|
|
act->ModelData()->EnableLooping(x44_24_isLooped);
|
|
act->AnimationData()->MultiplyPlaybackRate(x3c_playbackRate);
|
|
}
|
|
}
|
|
} else if (CPatterned* ai = TCastToPtr< CPatterned >(ent)) {
|
|
if (ai->AnimationData()->IsAdditiveAnimation(x34_animationId)) {
|
|
ai->AnimationData()->AddAdditiveAnimation(x34_animationId, 1.f, x44_24_isLooped,
|
|
x44_26_fadeOut);
|
|
} else {
|
|
CBodyStateCmdMgr& cmdMgr = ai->BodyCtrl()->CommandMgr();
|
|
cmdMgr.DeliverCmd(
|
|
CBCScriptedCmd(x34_animationId, x44_24_isLooped, x44_27_timedLoop, x38_initialLifetime));
|
|
}
|
|
}
|
|
}
|
|
|
|
void CScriptActorKeyframe::Think(float dt, CStateManager& mgr) {
|
|
if (!x44_25_isPassive && x44_24_isLooped && x44_27_timedLoop && x44_28_playing &&
|
|
x40_lifetime > 0.f) {
|
|
|
|
x40_lifetime -= dt;
|
|
if (x40_lifetime <= 0.f) {
|
|
|
|
x44_28_playing = false;
|
|
rstl::vector< SConnection >::const_iterator conn = GetConnectionList().begin();
|
|
for (; conn != GetConnectionList().end(); ++conn) {
|
|
if (conn->x0_state != kSS_Play || conn->x4_msg != kSM_Play) {
|
|
continue;
|
|
}
|
|
TUniqueId uid = mgr.GetIdForScript(conn->x8_objId);
|
|
CEntity* ent = mgr.ObjectById(uid);
|
|
if (CScriptActor* act = TCastToPtr< CScriptActor >(ent)) {
|
|
if (act->HasAnimation()) {
|
|
if (act->AnimationData()->IsAdditiveAnimation(x34_animationId)) {
|
|
act->AnimationData()->DelAdditiveAnimation(x34_animationId);
|
|
} else if (act->AnimationData()->GetCurrentAnimation() == x34_animationId) {
|
|
act->ModelData()->EnableLooping(false);
|
|
}
|
|
}
|
|
} else if (CPatterned* ai = TCastToPtr< CPatterned >(ent)) {
|
|
if (ai->AnimationData()->IsAdditiveAnimation(x34_animationId)) {
|
|
ai->AnimationData()->DelAdditiveAnimation(x34_animationId);
|
|
|
|
} else if (ai->BodyCtrl()->GetBodyStateInfo().GetCurrentStateId() == pas::kAS_Scripted &&
|
|
ai->AnimationData()->GetCurrentAnimation() == x34_animationId) {
|
|
ai->BodyCtrl()->CommandMgr().DeliverCmd(CBodyStateCmd(kBSC_ExitState));
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
CEntity::Think(dt, mgr);
|
|
}
|