2020-01-15 12:07:48 +00:00
|
|
|
#include "Runtime/MP1/World/CPuffer.hpp"
|
|
|
|
|
|
|
|
#include "Runtime/CSimplePool.hpp"
|
|
|
|
#include "Runtime/CStateManager.hpp"
|
|
|
|
#include "Runtime/GameGlobalObjects.hpp"
|
|
|
|
#include "Runtime/World/CFire.hpp"
|
|
|
|
#include "Runtime/World/CKnockBackController.hpp"
|
|
|
|
#include "Runtime/World/CPlayer.hpp"
|
|
|
|
|
2019-09-21 13:07:13 +00:00
|
|
|
#include "TCastTo.hpp" // Generated file, do not modify include path
|
2018-10-11 22:57:05 +00:00
|
|
|
|
2021-04-10 08:42:06 +00:00
|
|
|
namespace metaforce::MP1 {
|
2018-10-11 22:57:05 +00:00
|
|
|
|
2020-03-16 20:31:31 +00:00
|
|
|
constexpr std::array GasLocators{
|
|
|
|
"Gas_01_LCTR"sv, "Gas_02_LCTR"sv, "Gas_03_LCTR"sv, "Gas_04_LCTR"sv, "Gas_05_LCTR"sv,
|
|
|
|
"Gas_06_LCTR"sv, "Gas_07_LCTR"sv, "Gas_08_LCTR"sv, "Gas_09_LCTR"sv, "Gas_10_LCTR"sv,
|
|
|
|
"Gas_11_LCTR"sv, "Gas_12_LCTR"sv, "Gas_13_LCTR"sv, "Gas_14_LCTR"sv,
|
|
|
|
};
|
|
|
|
|
|
|
|
constexpr std::array GesJetLocators{
|
|
|
|
"GasJet01"sv, "GasJet02"sv, "GasJet03"sv, "GasJet04"sv, "GasJet05"sv, "GasJet06"sv, "GasJet07"sv,
|
|
|
|
"GasJet08"sv, "GasJet09"sv, "GasJet10"sv, "GasJet11"sv, "GasJet12"sv, "GasJet13"sv, "GasJet14"sv,
|
|
|
|
};
|
|
|
|
|
2018-10-11 22:57:05 +00:00
|
|
|
CPuffer::CPuffer(TUniqueId uid, std::string_view name, const CEntityInfo& info, const zeus::CTransform& xf,
|
2018-11-14 04:16:11 +00:00
|
|
|
CModelData&& modelData, const CActorParameters& actorParameters, const CPatternedInfo& patternedInfo,
|
|
|
|
float hoverSpeed, CAssetId cloudEffect, const CDamageInfo& cloudDamage, CAssetId cloudSteam, float f2,
|
2018-10-11 22:57:05 +00:00
|
|
|
bool b1, bool b2, bool b3, const CDamageInfo& explosionDamage, s16 sfxId)
|
2018-12-08 05:30:43 +00:00
|
|
|
: CPatterned(ECharacter::Puffer, uid, name, EFlavorType::Zero, info, xf, std::move(modelData), patternedInfo,
|
|
|
|
EMovementType::Flyer, EColliderType::One, EBodyType::RestrictedFlyer, actorParameters,
|
|
|
|
EKnockBackVariant::Small)
|
|
|
|
, x568_face(xf.frontVector())
|
|
|
|
, x574_cloudEffect(g_SimplePool->GetObj({SBIG('PART'), cloudEffect}))
|
|
|
|
, x57c_cloudDamage(cloudDamage)
|
|
|
|
, x598_24_(b1)
|
|
|
|
, x598_25_(b3)
|
|
|
|
, x598_26_(b2)
|
|
|
|
, x59a_(CSfxManager::TranslateSFXID(sfxId))
|
|
|
|
, x59c_explosionDamage(explosionDamage)
|
|
|
|
, x5b8_(f2)
|
|
|
|
, x5bc_cloudSteam(cloudSteam) {
|
|
|
|
CreateShadow(false);
|
|
|
|
x460_knockBackController.SetImpulseDurationIdx(1);
|
|
|
|
x574_cloudEffect.Lock();
|
2020-03-04 00:49:13 +00:00
|
|
|
x450_bodyController->SetRestrictedFlyerMoveSpeed(hoverSpeed);
|
2018-11-14 04:16:11 +00:00
|
|
|
}
|
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
void CPuffer::Accept(IVisitor& visitor) { visitor.Visit(this); }
|
|
|
|
|
|
|
|
void CPuffer::AcceptScriptMsg(EScriptObjectMessage msg, TUniqueId uid, CStateManager& mgr) {
|
|
|
|
CPatterned::AcceptScriptMsg(msg, uid, mgr);
|
|
|
|
|
|
|
|
switch (msg) {
|
|
|
|
case EScriptObjectMessage::Registered:
|
|
|
|
x450_bodyController->Activate(mgr);
|
|
|
|
SetMaterialFilter(
|
|
|
|
CMaterialFilter::MakeIncludeExclude({EMaterialTypes::Player}, {EMaterialTypes::NoStaticCollision}));
|
|
|
|
break;
|
|
|
|
case EScriptObjectMessage::Action:
|
|
|
|
if (GetActive())
|
|
|
|
x401_30_pendingDeath = true;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
2018-11-14 04:16:11 +00:00
|
|
|
}
|
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
void CPuffer::Think(float dt, CStateManager& mgr) {
|
|
|
|
CPatterned::Think(dt, mgr);
|
|
|
|
sub8025bfa4(mgr);
|
|
|
|
zeus::CVector3f moveVector = x450_bodyController->GetCommandMgr().GetMoveVector();
|
|
|
|
|
|
|
|
if (x5cc_ != x2dc_destObj) {
|
|
|
|
x5cc_ = x2dc_destObj;
|
|
|
|
CSfxManager::AddEmitter(x59a_, GetTranslation(), {}, true, false, 127, -1);
|
|
|
|
}
|
|
|
|
|
|
|
|
x450_bodyController->GetCommandMgr().ClearLocomotionCmds();
|
|
|
|
if (moveVector.canBeNormalized()) {
|
2020-03-04 00:49:13 +00:00
|
|
|
x5c0_move = (x5c0_move * (1.f - (dt / 0.5f)) + (moveVector * (dt / 0.5f))).normalized();
|
2018-12-08 05:30:43 +00:00
|
|
|
x450_bodyController->GetCommandMgr().DeliverCmd(CBCLocomotionCmd(x5c0_move, x568_face, 1.f));
|
|
|
|
}
|
2018-11-14 04:16:11 +00:00
|
|
|
}
|
|
|
|
|
2019-06-12 02:05:17 +00:00
|
|
|
std::optional<zeus::CAABox> CPuffer::GetTouchBounds() const {
|
2018-12-08 05:30:43 +00:00
|
|
|
auto touchBounds = CPatterned::GetTouchBounds();
|
|
|
|
if (touchBounds) {
|
|
|
|
touchBounds->accumulateBounds(touchBounds->min - 0.5f);
|
|
|
|
touchBounds->accumulateBounds(touchBounds->max + 0.5f);
|
|
|
|
}
|
2018-11-14 04:16:11 +00:00
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
return touchBounds;
|
2018-11-14 04:16:11 +00:00
|
|
|
}
|
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
void CPuffer::Touch(CActor& act, CStateManager& mgr) {
|
|
|
|
CPatterned::Touch(act, mgr);
|
2018-11-14 04:16:11 +00:00
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
if (x400_25_alive && act.GetUniqueId() == mgr.GetPlayer().GetUniqueId())
|
|
|
|
x401_30_pendingDeath = true;
|
2018-11-14 04:16:11 +00:00
|
|
|
}
|
|
|
|
|
2019-04-07 05:14:48 +00:00
|
|
|
void CPuffer::Death(CStateManager& mgr, const zeus::CVector3f& vec, EScriptObjectState state) {
|
2018-12-08 05:30:43 +00:00
|
|
|
CPatterned::Death(mgr, vec, state);
|
|
|
|
mgr.ApplyDamageToWorld(GetUniqueId(), *this, GetTranslation(), x59c_explosionDamage,
|
|
|
|
CMaterialFilter::MakeIncludeExclude({EMaterialTypes::Solid}, {}));
|
|
|
|
zeus::CTransform xf = GetTransform() * zeus::CTransform::Scale(x57c_cloudDamage.GetRadius());
|
|
|
|
zeus::CAABox aabox(-1.f, 1.f);
|
|
|
|
mgr.AddObject(new CFire(x574_cloudEffect, mgr.AllocateUniqueId(), GetAreaIdAlways(), true, GetUniqueId(),
|
|
|
|
GetTransform(), x57c_cloudDamage, aabox.getTransformedAABox(xf), {1.f, 1.f, 1.f}, true,
|
|
|
|
x5bc_cloudSteam, x598_24_, x598_26_, x598_25_, 1.f, x5b8_, 1.f, 1.f));
|
2018-11-14 04:16:11 +00:00
|
|
|
}
|
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
void CPuffer::sub8025bfa4(CStateManager& mgr) {
|
2020-03-16 20:31:31 +00:00
|
|
|
const zeus::CVector3f moveVector = x450_bodyController->GetCommandMgr().GetMoveVector();
|
2018-12-08 05:30:43 +00:00
|
|
|
|
|
|
|
if (x5d4_gasLocators.empty()) {
|
2020-03-16 20:31:31 +00:00
|
|
|
for (const auto& gasLocator : GasLocators) {
|
|
|
|
x5d4_gasLocators.push_back(GetScaledLocatorTransform(gasLocator).basis[1]);
|
|
|
|
}
|
2018-12-08 05:30:43 +00:00
|
|
|
}
|
|
|
|
|
2020-03-04 00:49:13 +00:00
|
|
|
if (moveVector.canBeNormalized()) {
|
2020-03-16 20:31:31 +00:00
|
|
|
const zeus::CVector3f moveNorm = -moveVector.normalized();
|
|
|
|
for (size_t i = 0; i < GesJetLocators.size(); ++i) {
|
|
|
|
const zeus::CVector3f tmp = GetTransform().rotate(x5d4_gasLocators[i]);
|
|
|
|
const bool enable = std::cos(zeus::degToRad(45.f)) < moveNorm.dot(tmp);
|
|
|
|
|
2020-03-04 00:49:13 +00:00
|
|
|
if ((x5d0_enabledParticles & (1 << i)) != enable) {
|
|
|
|
GetModelData()->GetAnimationData()->SetParticleEffectState(GesJetLocators[i], enable, mgr);
|
|
|
|
}
|
2020-03-16 20:31:31 +00:00
|
|
|
if (enable) {
|
2020-03-04 00:49:13 +00:00
|
|
|
x5d0_enabledParticles |= (1 << i);
|
2020-03-16 20:31:31 +00:00
|
|
|
} else {
|
2020-03-04 00:49:13 +00:00
|
|
|
x5d0_enabledParticles &= ~(1 << i);
|
2020-03-16 20:31:31 +00:00
|
|
|
}
|
2020-03-04 00:49:13 +00:00
|
|
|
}
|
|
|
|
} else {
|
2020-03-16 20:31:31 +00:00
|
|
|
for (size_t i = 0; i < GesJetLocators.size(); ++i) {
|
|
|
|
if ((x5d0_enabledParticles & (1 << i)) != 0) {
|
2020-03-04 00:49:13 +00:00
|
|
|
GetModelData()->GetAnimationData()->SetParticleEffectState(GesJetLocators[i], false, mgr);
|
2020-03-16 20:31:31 +00:00
|
|
|
}
|
2020-03-04 00:49:13 +00:00
|
|
|
}
|
|
|
|
x5d0_enabledParticles = 0;
|
|
|
|
}
|
2018-10-11 22:57:05 +00:00
|
|
|
}
|
2021-04-10 08:42:06 +00:00
|
|
|
} // namespace metaforce::MP1
|