diff --git a/DataSpec/DNACommon/Tweaks/ITweakPlayer.hpp b/DataSpec/DNACommon/Tweaks/ITweakPlayer.hpp index b184b55ec..78e35a1bd 100644 --- a/DataSpec/DNACommon/Tweaks/ITweakPlayer.hpp +++ b/DataSpec/DNACommon/Tweaks/ITweakPlayer.hpp @@ -115,6 +115,10 @@ struct ITweakPlayer : ITweak virtual uint32_t GetGrappleJumpMode() const=0; virtual bool GetOrbitReleaseBreaksGrapple() const=0; virtual bool GetInvertGrappleTurn() const=0; + virtual float GetGrappleBeamSpeed() const=0; + virtual float GetGrappleBeamXWaveAmplitude() const=0; + virtual float GetGrappleBeamZWaveAmplitude() const=0; + virtual float GetGrappleBeamAnglePhaseDelta() const=0; virtual float GetHorizontalFreeLookAngleVel() const=0; virtual float GetVerticalFreeLookAngleVel() const=0; // x134 virtual float GetOrbitCameraSpeed() const=0; // x184 diff --git a/DataSpec/DNAMP1/Tweaks/CTweakPlayer.cpp b/DataSpec/DNAMP1/Tweaks/CTweakPlayer.cpp index bb3857f71..c7b927f2a 100644 --- a/DataSpec/DNAMP1/Tweaks/CTweakPlayer.cpp +++ b/DataSpec/DNAMP1/Tweaks/CTweakPlayer.cpp @@ -369,7 +369,7 @@ void CTweakPlayer::read(athena::io::IStreamReader& __dna_reader) x2a8_grappleSwingPeriod = __dna_reader.readFloatBig(); /* x2ac_grapplePullSpeedMin */ x2ac_grapplePullSpeedMin = __dna_reader.readFloatBig(); - /* x2b0_ */ + /* x2b0_grappleCameraSpeed */ x2b0_grappleCameraSpeed = __dna_reader.readFloatBig(); /* x2b4_maxGrappleLockedTurnAlignDistance */ x2b4_maxGrappleLockedTurnAlignDistance = __dna_reader.readFloatBig(); @@ -391,14 +391,14 @@ void CTweakPlayer::read(athena::io::IStreamReader& __dna_reader) x2d4_orbitReleaseBreaksGrapple = __dna_reader.readBool(); /* x2d5_invertGrappleTurn */ x2d5_invertGrappleTurn = __dna_reader.readBool(); - /* x2d8_ */ - x2d8_ = __dna_reader.readFloatBig(); - /* x2dc_ */ - x2dc_ = __dna_reader.readFloatBig(); - /* x2e0_ */ - x2e0_ = __dna_reader.readFloatBig(); - /* x2e4_ */ - x2e4_ = __dna_reader.readFloatBig(); + /* x2d8_grappleBeamSpeed */ + x2d8_grappleBeamSpeed = __dna_reader.readFloatBig(); + /* x2dc_grappleBeamXWaveAmplitude */ + x2dc_grappleBeamXWaveAmplitude = __dna_reader.readFloatBig(); + /* x2e0_grappleBeamZWaveAmplitude */ + x2e0_grappleBeamZWaveAmplitude = __dna_reader.readFloatBig(); + /* x2e4_grappleBeamAnglePhaseDelta */ + x2e4_grappleBeamAnglePhaseDelta = __dna_reader.readFloatBig(); /* x26c_playerHeight */ x26c_playerHeight = __dna_reader.readFloatBig(); /* x270_playerXYHalfExtent */ @@ -809,7 +809,7 @@ void CTweakPlayer::write(athena::io::IStreamWriter& __dna_writer) const __dna_writer.writeFloatBig(x2a8_grappleSwingPeriod); /* x2ac_grapplePullSpeedMin */ __dna_writer.writeFloatBig(x2ac_grapplePullSpeedMin); - /* x2b0_ */ + /* x2b0_grappleCameraSpeed */ __dna_writer.writeFloatBig(x2b0_grappleCameraSpeed); /* x2b4_maxGrappleLockedTurnAlignDistance */ __dna_writer.writeFloatBig(x2b4_maxGrappleLockedTurnAlignDistance); @@ -831,14 +831,14 @@ void CTweakPlayer::write(athena::io::IStreamWriter& __dna_writer) const __dna_writer.writeBool(x2d4_orbitReleaseBreaksGrapple); /* x2d5_invertGrappleTurn */ __dna_writer.writeBool(x2d5_invertGrappleTurn); - /* x2d8_ */ - __dna_writer.writeFloatBig(x2d8_); - /* x2dc_ */ - __dna_writer.writeFloatBig(x2dc_); - /* x2e0_ */ - __dna_writer.writeFloatBig(x2e0_); - /* x2e4_ */ - __dna_writer.writeFloatBig(x2e4_); + /* x2d8_grappleBeamSpeed */ + __dna_writer.writeFloatBig(x2d8_grappleBeamSpeed); + /* x2dc_grappleBeamXWaveAmplitude */ + __dna_writer.writeFloatBig(x2dc_grappleBeamXWaveAmplitude); + /* x2e0_grappleBeamZWaveAmplitude */ + __dna_writer.writeFloatBig(x2e0_grappleBeamZWaveAmplitude); + /* x2e4_grappleBeamAnglePhaseDelta */ + __dna_writer.writeFloatBig(x2e4_grappleBeamAnglePhaseDelta); /* x26c_playerHeight */ __dna_writer.writeFloatBig(x26c_playerHeight); /* x270_playerXYHalfExtent */ @@ -1324,8 +1324,8 @@ void CTweakPlayer::read(athena::io::YAMLDocReader& __dna_docin) x2a8_grappleSwingPeriod = __dna_docin.readFloat("x2a8_grappleSwingPeriod"); /* x2ac_grapplePullSpeedMin */ x2ac_grapplePullSpeedMin = __dna_docin.readFloat("x2ac_grapplePullSpeedMin"); - /* x2b0_ */ - x2b0_grappleCameraSpeed = __dna_docin.readFloat("x2b0_"); + /* x2b0_grappleCameraSpeed */ + x2b0_grappleCameraSpeed = __dna_docin.readFloat("x2b0_grappleCameraSpeed"); /* x2b4_maxGrappleLockedTurnAlignDistance */ x2b4_maxGrappleLockedTurnAlignDistance = __dna_docin.readFloat("x2b4_maxGrappleLockedTurnAlignDistance"); /* x2b8_grapplePullSpeedProportion */ @@ -1346,14 +1346,14 @@ void CTweakPlayer::read(athena::io::YAMLDocReader& __dna_docin) x2d4_orbitReleaseBreaksGrapple = __dna_docin.readBool("x2d4_orbitReleaseBreaksGrapple"); /* x2d5_invertGrappleTurn */ x2d5_invertGrappleTurn = __dna_docin.readBool("x2d5_invertGrappleTurn"); - /* x2d8_ */ - x2d8_ = __dna_docin.readFloat("x2d8_"); - /* x2dc_ */ - x2dc_ = __dna_docin.readFloat("x2dc_"); - /* x2e0_ */ - x2e0_ = __dna_docin.readFloat("x2e0_"); - /* x2e4_ */ - x2e4_ = __dna_docin.readFloat("x2e4_"); + /* x2d8_grappleBeamSpeed */ + x2d8_grappleBeamSpeed = __dna_docin.readFloat("x2d8_grappleBeamSpeed"); + /* x2dc_grappleBeamXWaveAmplitude */ + x2dc_grappleBeamXWaveAmplitude = __dna_docin.readFloat("x2dc_grappleBeamXWaveAmplitude"); + /* x2e0_grappleBeamZWaveAmplitude */ + x2e0_grappleBeamZWaveAmplitude = __dna_docin.readFloat("x2e0_grappleBeamZWaveAmplitude"); + /* x2e4_grappleBeamAnglePhaseDelta */ + x2e4_grappleBeamAnglePhaseDelta = __dna_docin.readFloat("x2e4_grappleBeamAnglePhaseDelta"); /* x26c_playerHeight */ x26c_playerHeight = __dna_docin.readFloat("x26c_playerHeight"); /* x270_playerXYHalfExtent */ @@ -1824,8 +1824,8 @@ void CTweakPlayer::write(athena::io::YAMLDocWriter& __dna_docout) const __dna_docout.writeFloat("x2a8_grappleSwingPeriod", x2a8_grappleSwingPeriod); /* x2ac_grapplePullSpeedMin */ __dna_docout.writeFloat("x2ac_grapplePullSpeedMin", x2ac_grapplePullSpeedMin); - /* x2b0_ */ - __dna_docout.writeFloat("x2b0_", x2b0_grappleCameraSpeed); + /* x2b0_grappleCameraSpeed */ + __dna_docout.writeFloat("x2b0_grappleCameraSpeed", x2b0_grappleCameraSpeed); /* x2b4_maxGrappleLockedTurnAlignDistance */ __dna_docout.writeFloat("x2b4_maxGrappleLockedTurnAlignDistance", x2b4_maxGrappleLockedTurnAlignDistance); /* x2b8_grapplePullSpeedProportion */ @@ -1846,14 +1846,14 @@ void CTweakPlayer::write(athena::io::YAMLDocWriter& __dna_docout) const __dna_docout.writeBool("x2d4_orbitReleaseBreaksGrapple", x2d4_orbitReleaseBreaksGrapple); /* x2d5_invertGrappleTurn */ __dna_docout.writeBool("x2d5_invertGrappleTurn", x2d5_invertGrappleTurn); - /* x2d8_ */ - __dna_docout.writeFloat("x2d8_", x2d8_); - /* x2dc_ */ - __dna_docout.writeFloat("x2dc_", x2dc_); - /* x2e0_ */ - __dna_docout.writeFloat("x2e0_", x2e0_); - /* x2e4_ */ - __dna_docout.writeFloat("x2e4_", x2e4_); + /* x2d8_grappleBeamSpeed */ + __dna_docout.writeFloat("x2d8_grappleBeamSpeed", x2d8_grappleBeamSpeed); + /* x2dc_grappleBeamXWaveAmplitude */ + __dna_docout.writeFloat("x2dc_grappleBeamXWaveAmplitude", x2dc_grappleBeamXWaveAmplitude); + /* x2e0_grappleBeamZWaveAmplitude */ + __dna_docout.writeFloat("x2e0_grappleBeamZWaveAmplitude", x2e0_grappleBeamZWaveAmplitude); + /* x2e4_grappleBeamAnglePhaseDelta */ + __dna_docout.writeFloat("x2e4_grappleBeamAnglePhaseDelta", x2e4_grappleBeamAnglePhaseDelta); /* x26c_playerHeight */ __dna_docout.writeFloat("x26c_playerHeight", x26c_playerHeight); /* x270_playerXYHalfExtent */ diff --git a/DataSpec/DNAMP1/Tweaks/CTweakPlayer.hpp b/DataSpec/DNAMP1/Tweaks/CTweakPlayer.hpp index 016efb60c..464046c8d 100644 --- a/DataSpec/DNAMP1/Tweaks/CTweakPlayer.hpp +++ b/DataSpec/DNAMP1/Tweaks/CTweakPlayer.hpp @@ -162,10 +162,10 @@ struct CTweakPlayer final : ITweakPlayer Value x2d0_grappleJumpMode; Value x2d4_orbitReleaseBreaksGrapple; Value x2d5_invertGrappleTurn; - Value x2d8_; - Value x2dc_; - Value x2e0_; - Value x2e4_; + Value x2d8_grappleBeamSpeed; + Value x2dc_grappleBeamXWaveAmplitude; + Value x2e0_grappleBeamZWaveAmplitude; + Value x2e4_grappleBeamAnglePhaseDelta; Value x2e8_; Value x2ec_; Value x2f0_; @@ -280,6 +280,10 @@ struct CTweakPlayer final : ITweakPlayer uint32_t GetGrappleJumpMode() const { return x2d0_grappleJumpMode; } bool GetOrbitReleaseBreaksGrapple() const { return x2d4_orbitReleaseBreaksGrapple; } bool GetInvertGrappleTurn() const { return x2d5_invertGrappleTurn; } + float GetGrappleBeamSpeed() const { return x2d8_grappleBeamSpeed; } + float GetGrappleBeamXWaveAmplitude() const { return x2dc_grappleBeamXWaveAmplitude; } + float GetGrappleBeamZWaveAmplitude() const { return x2e0_grappleBeamZWaveAmplitude; } + float GetGrappleBeamAnglePhaseDelta() const { return x2e4_grappleBeamAnglePhaseDelta; } float GetHorizontalFreeLookAngleVel() const { return x130_horizontalFreeLookAngleVel; } float GetVerticalFreeLookAngleVel() const { return x134_verticalFreeLookAngleVel; } float GetOrbitCameraSpeed() const { return x184_orbitCameraSpeed; } diff --git a/Runtime/CPlayerState.hpp b/Runtime/CPlayerState.hpp index a70a730cc..15e21b7b5 100644 --- a/Runtime/CPlayerState.hpp +++ b/Runtime/CPlayerState.hpp @@ -75,8 +75,9 @@ public: Max }; - enum class EPlayerSuit : u32 + enum class EPlayerSuit : s32 { + Invalid = -1, Power, Gravity, Varia, diff --git a/Runtime/Character/CAnimData.hpp b/Runtime/Character/CAnimData.hpp index 4f16bffbd..75ac19838 100644 --- a/Runtime/Character/CAnimData.hpp +++ b/Runtime/Character/CAnimData.hpp @@ -86,6 +86,7 @@ class CAnimData friend class CModelData; friend class CActor; friend class CPlayerGun; + friend class CGrappleArm; public: enum class EAnimDir { diff --git a/Runtime/Graphics/CRainSplashGenerator.hpp b/Runtime/Graphics/CRainSplashGenerator.hpp index 00d937130..0de559509 100644 --- a/Runtime/Graphics/CRainSplashGenerator.hpp +++ b/Runtime/Graphics/CRainSplashGenerator.hpp @@ -66,6 +66,7 @@ public: void Update(float dt, CStateManager& mgr); void GeneratePoints(const std::vector>& vn); void Draw(const zeus::CTransform& xf) const; + bool IsRaining() const { return x48_25_raining; } }; } diff --git a/Runtime/Graphics/CSkinnedModel.hpp b/Runtime/Graphics/CSkinnedModel.hpp index 15b0a1797..71891c471 100644 --- a/Runtime/Graphics/CSkinnedModel.hpp +++ b/Runtime/Graphics/CSkinnedModel.hpp @@ -52,6 +52,10 @@ public: g_PointGenFunc = func; g_PointGenCtx = ctx; } + static void ClearPointGeneratorFunc() + { + g_PointGenFunc = nullptr; + } static FPointGenerator g_PointGenFunc; static void* g_PointGenCtx; }; diff --git a/Runtime/Graphics/Shaders/CAABoxShader.hpp b/Runtime/Graphics/Shaders/CAABoxShader.hpp index 8ebd65344..48a9eedb7 100644 --- a/Runtime/Graphics/Shaders/CAABoxShader.hpp +++ b/Runtime/Graphics/Shaders/CAABoxShader.hpp @@ -39,4 +39,4 @@ public: } -#endif // __URDE_CAABOXSHADER_HPP__ \ No newline at end of file +#endif // __URDE_CAABOXSHADER_HPP__ diff --git a/Runtime/Input/CRumbleVoice.hpp b/Runtime/Input/CRumbleVoice.hpp index 0969d55ed..a0c9ad387 100644 --- a/Runtime/Input/CRumbleVoice.hpp +++ b/Runtime/Input/CRumbleVoice.hpp @@ -10,7 +10,9 @@ enum class ERumbleFxId Seven = 7, Eleven = 11, Twelve = 12, - Fifteen = 15 + Fourteen = 14, + Fifteen = 15, + Seventeen = 17 }; enum class ERumblePriority { diff --git a/Runtime/Particle/CParticleSwoosh.hpp b/Runtime/Particle/CParticleSwoosh.hpp index ba494168a..d43a2b3cc 100644 --- a/Runtime/Particle/CParticleSwoosh.hpp +++ b/Runtime/Particle/CParticleSwoosh.hpp @@ -171,13 +171,40 @@ public: void DoElectricCreate(const std::vector& offsets) { - int curIdx = x158_curParticle; + u32 curIdx = x158_curParticle; for (int i=0 ; i 0) + vec = rotation * zeus::CVector3f(std::cos(i + anglePhase) * xAmplitude, 0.f, + std::sin(float(i)) * zAmplitude); + data.xc_translation = trans + vec; + trans += swooshSegDelta; + std::swap(rot, data.x30_irot); + } + } }; } diff --git a/Runtime/Weapon/CFidget.cpp b/Runtime/Weapon/CFidget.cpp index dd2def5ca..52d965496 100644 --- a/Runtime/Weapon/CFidget.cpp +++ b/Runtime/Weapon/CFidget.cpp @@ -1,31 +1,160 @@ #include "CFidget.hpp" +#include "CStateManager.hpp" +#include "World/CPlayer.hpp" namespace urde { -CFidget::EState CFidget::Update(int fire, bool bobbing, bool inStrikeCooldown, float dt, CStateManager& mgr) +static float kMinorFidgetDelay = 20.f; +static float kMajorFidgetDelay = 20.f; + +CFidget::EState CFidget::Update(int fireButtonStates, bool bobbing, + bool inStrikeCooldown, float dt, CStateManager& mgr) { - return EState::Zero; + switch (x0_state) + { + case EState::NoFidget: + break; + case EState::MinorFidget: + return x34_24_loading ? EState::Loading : EState::StillMinorFidget; + case EState::MajorFidget: + return x34_24_loading ? EState::Loading : EState::StillMajorFidget; + case EState::HolsterBeam: + return x34_24_loading ? EState::Loading : EState::StillHolsterBeam; + default: + x0_state = EState::NoFidget; + break; + } + + if (fireButtonStates != 0) + { + x14_timeSinceFire = 0.f; + x2c_holsterTimeSinceFire = 0.f; + } + else + { + if (x14_timeSinceFire < 6.f) + x14_timeSinceFire += dt; + if (x2c_holsterTimeSinceFire < x30_timeUntilHolster + 1.f) + x2c_holsterTimeSinceFire += dt; + } + + if (inStrikeCooldown) + x18_timeSinceStrikeCooldown = 0.f; + else if (x18_timeSinceStrikeCooldown < 11.f) + x18_timeSinceStrikeCooldown += dt; + + if (mgr.GetPlayer().GetMorphballTransitionState() == CPlayer::EPlayerMorphBallState::Unmorphed) + { + if (x1c_timeSinceUnmorph < 21.f) + x1c_timeSinceUnmorph += dt; + } + else + { + x1c_timeSinceUnmorph = 0.f; + } + + if (bobbing) + x20_timeSinceBobbing = 0.f; + else if (x20_timeSinceBobbing < 21.f) + x20_timeSinceBobbing += dt; + + u32 pendingTriggerBits = 0; + if (x0_state == EState::NoFidget) + { + if ((x10_delayTimerEnableBits & 0x1) != 0) + { + x24_minorDelayTimer += dt; + if (x24_minorDelayTimer > kMinorFidgetDelay) + { + pendingTriggerBits |= 0x1; + x24_minorDelayTimer = 0.f; + } + } + + if ((x10_delayTimerEnableBits & 0x2) != 0) + { + x28_majorDelayTimer += dt; + if (x28_majorDelayTimer > kMajorFidgetDelay) + { + pendingTriggerBits |= 0x2; + x28_majorDelayTimer = 0.f; + } + } + } + + if (x2c_holsterTimeSinceFire > x30_timeUntilHolster) + { + x0_state = EState::HolsterBeam; + } + else + { + if (x18_timeSinceStrikeCooldown > 10.f && x1c_timeSinceUnmorph > 20.f && x20_timeSinceBobbing > 20.f) + { + if ((pendingTriggerBits & 0x1) != 0) + x8_delayTriggerBits |= 0x1; + else if ((pendingTriggerBits & 0x2) != 0) + x8_delayTriggerBits |= 0x2; + } + + if ((x8_delayTriggerBits & 0x3) == 0x3) + x0_state = (mgr.GetActiveRandom()->Next() % 100) >= 50 ? EState::MajorFidget : EState::MinorFidget; + else if ((x8_delayTriggerBits & 0x1) == 0x1) + x0_state = EState::MinorFidget; + else if ((x8_delayTriggerBits & 0x2) == 0x2) + x0_state = EState::MajorFidget; + else + x0_state = EState::NoFidget; + } + + switch (x0_state) + { + case EState::MinorFidget: + x34_24_loading = true; + x10_delayTimerEnableBits = 2; + x8_delayTriggerBits &= ~0x1; + kMinorFidgetDelay = mgr.GetActiveRandom()->Range(20.f, 29.f); + x4_type = SamusGun::EFidgetType::Minor; + xc_animSet = mgr.GetActiveRandom()->Range(0, 4); + break; + case EState::MajorFidget: + x34_24_loading = true; + x10_delayTimerEnableBits = 1; + x8_delayTriggerBits &= ~0x2; + kMajorFidgetDelay = mgr.GetActiveRandom()->Range(20.f, 30.f); + x4_type = SamusGun::EFidgetType::Major; + xc_animSet = mgr.GetActiveRandom()->Range(0, 5); + break; + case EState::HolsterBeam: + x4_type = SamusGun::EFidgetType::Minor; + x34_24_loading = true; + xc_animSet = 0; + break; + default: + break; + } + + return x0_state; } void CFidget::ResetMinor() { - + x0_state = EState::NoFidget; } void CFidget::ResetAll() { - x0_state = EState::Zero; + x0_state = EState::NoFidget; x4_type = SamusGun::EFidgetType::Invalid; - x18_ = 0.f; - x1c_ = 0.f; - x14_ = 0.f; - x24_ = 0.f; - x28_ = 0.f; - x2c_ = 0.f; - x8_ = 0; - xc_parm2 = -1; - x10_ = 3; + x18_timeSinceStrikeCooldown = 0.f; + x1c_timeSinceUnmorph = 0.f; + x14_timeSinceFire = 0.f; + x24_minorDelayTimer = 0.f; + x28_majorDelayTimer = 0.f; + x2c_holsterTimeSinceFire = 0.f; + x8_delayTriggerBits = 0; + xc_animSet = -1; + x10_delayTimerEnableBits = 3; x34_24_loading = false; } diff --git a/Runtime/Weapon/CFidget.hpp b/Runtime/Weapon/CFidget.hpp index 3391181bc..5791456e5 100644 --- a/Runtime/Weapon/CFidget.hpp +++ b/Runtime/Weapon/CFidget.hpp @@ -13,35 +13,36 @@ class CFidget public: enum class EState { - Zero, - One, - Two, - Three, - Four, - Five, - Six, - Seven + NoFidget, + MinorFidget, + MajorFidget, + HolsterBeam, + StillMinorFidget, + StillMajorFidget, + StillHolsterBeam, + Loading }; private: - EState x0_state = EState::Zero; + EState x0_state = EState::NoFidget; SamusGun::EFidgetType x4_type = SamusGun::EFidgetType::Invalid; - u32 x8_ = 0; - s32 xc_parm2 = -1; - u32 x10_ = 3; - float x14_ = 0.f; - float x18_ = 0.f; - float x1c_ = 0.f; - float x20_ = 0.f; - float x24_ = 0.f; - float x28_ = 0.f; - float x2c_ = 0.f; - float x30_ = 105.f; + u32 x8_delayTriggerBits = 0; + // 0: panel, 1: panel reset, 2: adjust nozzle, 3: panel buttons + s32 xc_animSet = -1; + u32 x10_delayTimerEnableBits = 3; + float x14_timeSinceFire = 0.f; + float x18_timeSinceStrikeCooldown = 0.f; + float x1c_timeSinceUnmorph = 0.f; + float x20_timeSinceBobbing = 0.f; + float x24_minorDelayTimer = 0.f; + float x28_majorDelayTimer = 0.f; + float x2c_holsterTimeSinceFire = 0.f; + float x30_timeUntilHolster = 105.f; bool x34_24_loading = false; public: EState GetState() const { return x0_state; } SamusGun::EFidgetType GetType() const { return x4_type; } - s32 GetParm2() const { return xc_parm2; } - EState Update(int fire, bool bobbing, bool inStrikeCooldown, float dt, CStateManager& mgr); + s32 GetAnimSet() const { return xc_animSet; } + EState Update(int fireButtonStates, bool bobbing, bool inStrikeCooldown, float dt, CStateManager& mgr); void ResetMinor(); void ResetAll(); void DoneLoading() { x34_24_loading = false; } diff --git a/Runtime/Weapon/CGSFidget.cpp b/Runtime/Weapon/CGSFidget.cpp index 5bd8652b0..61de44276 100644 --- a/Runtime/Weapon/CGSFidget.cpp +++ b/Runtime/Weapon/CGSFidget.cpp @@ -11,15 +11,15 @@ bool CGSFidget::Update(CAnimData& data, float dt, CStateManager& mgr) return !data.IsAnimTimeRemaining(0.001f, "Whole Body"); } -s32 CGSFidget::SetAnim(CAnimData& data, s32 type, s32 gunId, s32 parm2, CStateManager& mgr) +s32 CGSFidget::SetAnim(CAnimData& data, s32 type, s32 gunId, s32 animSet, CStateManager& mgr) { const CPASDatabase& pas = data.GetCharacterInfo().GetPASDatabase(); CPASAnimParmData parms(1, CPASAnimParm::FromEnum(type), CPASAnimParm::FromInt32(gunId), - CPASAnimParm::FromInt32(parm2)); + CPASAnimParm::FromInt32(animSet)); auto anim = pas.FindBestAnimation(parms, *mgr.GetActiveRandom(), -1); bool loop = pas.GetAnimState(1)->GetAnimParmData(anim.second, 3).GetBoolValue(); x14_gunId = gunId; - x18_parm2 = parm2; + x18_animSet = animSet; if (anim.second != -1) { data.EnableLooping(loop); @@ -30,10 +30,10 @@ s32 CGSFidget::SetAnim(CAnimData& data, s32 type, s32 gunId, s32 parm2, CStateMa return anim.second; } -void CGSFidget::LoadAnimAsync(CAnimData& data, s32 type, s32 gunId, s32 parm2, CStateManager& mgr) +void CGSFidget::LoadAnimAsync(CAnimData& data, s32 type, s32 gunId, s32 animSet, CStateManager& mgr) { CPASAnimParmData parms(1, CPASAnimParm::FromEnum(type), CPASAnimParm::FromInt32(gunId), - CPASAnimParm::FromInt32(parm2)); + CPASAnimParm::FromInt32(animSet)); auto anim = data.GetCharacterInfo().GetPASDatabase().FindBestAnimation(parms, *mgr.GetActiveRandom(), -1); if (anim.second != -1) NWeaponTypes::get_token_vector(data, anim.second, x0_anims, true); diff --git a/Runtime/Weapon/CGSFidget.hpp b/Runtime/Weapon/CGSFidget.hpp index 407eb1a9e..8c3b5865c 100644 --- a/Runtime/Weapon/CGSFidget.hpp +++ b/Runtime/Weapon/CGSFidget.hpp @@ -13,11 +13,11 @@ class CGSFidget std::vector x0_anims; s32 x10_ = -1; s32 x14_gunId = -1; - s32 x18_parm2 = -1; + s32 x18_animSet = -1; public: bool Update(CAnimData& data, float dt, CStateManager& mgr); - s32 SetAnim(CAnimData& data, s32 type, s32 gunId, s32 parm2, CStateManager& mgr); - void LoadAnimAsync(CAnimData& data, s32 type, s32 gunId, s32 parm2, CStateManager& mgr); + s32 SetAnim(CAnimData& data, s32 type, s32 gunId, s32 animSet, CStateManager& mgr); + void LoadAnimAsync(CAnimData& data, s32 type, s32 gunId, s32 animSet, CStateManager& mgr); void UnLoadAnim(); bool IsAnimLoaded() const; }; diff --git a/Runtime/Weapon/CGrappleArm.cpp b/Runtime/Weapon/CGrappleArm.cpp index 78395c1f3..74ca2be8e 100644 --- a/Runtime/Weapon/CGrappleArm.cpp +++ b/Runtime/Weapon/CGrappleArm.cpp @@ -1,95 +1,694 @@ +#include "Particle/CElementGen.hpp" +#include "CDependencyGroup.hpp" #include "CGrappleArm.hpp" +#include "GameGlobalObjects.hpp" +#include "CSimplePool.hpp" +#include "World/CPlayer.hpp" +#include "TCastTo.hpp" +#include "Camera/CGameCamera.hpp" +#include "Graphics/CSkinnedModel.hpp" +#include "Graphics/CVertexMorphEffect.hpp" namespace urde { -CGrappleArm::CGrappleArm(const zeus::CVector3f& vec) +float CGrappleArm::g_GrappleBeamAnglePhaseDelta = 0.875f; +float CGrappleArm::g_GrappleBeamXWaveAmplitude = 0.25f; +float CGrappleArm::g_GrappleBeamZWaveAmplitude = 0.125f; +float CGrappleArm::g_GrappleBeamSpeed = 5.f; + +CGrappleArm::CGrappleArm(const zeus::CVector3f& scale) +: x0_grappleArmModel(CAnimRes(g_tweakGunRes->x8_grappleArm, 0, scale, 41, false)), + xa0_grappleGearModel(CStaticRes(NWeaponTypes::get_asset_id_from_name("GrappleGear"), scale)), + xec_grapNoz1Model(CStaticRes(NWeaponTypes::get_asset_id_from_name("GrapNoz1"), scale)), + x138_grapNoz2Model(CStaticRes(NWeaponTypes::get_asset_id_from_name("GrapNoz2"), scale)), + x184_grappleArm(g_SimplePool->GetObj(SObjectTag{FOURCC('ANCS'), g_tweakGunRes->x8_grappleArm})), + x31c_scale(scale), + x354_grappleSegmentDesc(g_SimplePool->GetObj(SObjectTag{FOURCC('PART'), g_tweakGunRes->xb4_grappleSegment})), + x360_grappleClawDesc(g_SimplePool->GetObj(SObjectTag{FOURCC('PART'), g_tweakGunRes->xb8_grappleClaw})), + x36c_grappleHitDesc(g_SimplePool->GetObj(SObjectTag{FOURCC('PART'), g_tweakGunRes->xbc_grappleHit})), + x378_grappleMuzzleDesc(g_SimplePool->GetObj(SObjectTag{FOURCC('PART'), g_tweakGunRes->xc0_grappleMuzzle})), + x384_grappleSwooshDesc(g_SimplePool->GetObj(SObjectTag{FOURCC('PART'), g_tweakGunRes->xc4_grappleSwoosh})), + x390_grappleSegmentGen(std::make_unique(x354_grappleSegmentDesc, + CElementGen::EModelOrientationType::Normal, + CElementGen::EOptionalSystemFlags::One)), + x394_grappleClawGen(std::make_unique(x360_grappleClawDesc, + CElementGen::EModelOrientationType::Normal, + CElementGen::EOptionalSystemFlags::One)), + x398_grappleHitGen(std::make_unique(x36c_grappleHitDesc, + CElementGen::EModelOrientationType::Normal, + CElementGen::EOptionalSystemFlags::One)), + x39c_grappleMuzzleGen(std::make_unique(x378_grappleMuzzleDesc, + CElementGen::EModelOrientationType::Normal, + CElementGen::EOptionalSystemFlags::One)), + x3a0_grappleSwooshGen(std::make_unique(x384_grappleSwooshDesc, 0)), + x3a4_rainSplashGenerator(std::make_unique(scale, 20, 2, 0.f, 0.125f)) { + x0_grappleArmModel->SetSortThermal(true); + xa0_grappleGearModel.SetSortThermal(true); + xec_grapNoz1Model.SetSortThermal(true); + x138_grapNoz2Model.SetSortThermal(true); + + g_GrappleBeamAnglePhaseDelta = g_tweakPlayer->GetGrappleBeamAnglePhaseDelta(); + g_GrappleBeamXWaveAmplitude = g_tweakPlayer->GetGrappleBeamXWaveAmplitude(); + g_GrappleBeamZWaveAmplitude = g_tweakPlayer->GetGrappleBeamZWaveAmplitude(); + g_GrappleBeamSpeed = g_tweakPlayer->GetGrappleBeamSpeed(); + + x39c_grappleMuzzleGen->SetParticleEmission(false); + x390_grappleSegmentGen->SetParticleEmission(false); + x3a0_grappleSwooshGen->DoGrappleWarmup(); + + BuildSuitDependencyList(); + LoadAnimations(); +} + +static const char* skDependencyNames[] = +{ + "PowerSuit_DGRP", + "GravitySuit_DGRP", + "VariaSuit_DGRP", + "PhazonSuit_DGRP", + "FusionSuit_DGRP", + "FusionSuitG_DGRP", + "FusionSuitV_DGRP", + "FusionSuitP_DGRP", +}; + +void CGrappleArm::FillTokenVector(const std::vector& tags, std::vector& objects) +{ + objects.reserve(tags.size()); + for (const SObjectTag& tag : tags) + objects.push_back(g_SimplePool->GetObj(tag)); +} + +void CGrappleArm::BuildSuitDependencyList() +{ + x184_grappleArm.Lock(); + for (const char* name : skDependencyNames) + { + TLockedToken dgrp = g_SimplePool->GetObj(name); + x19c_suitDeps.emplace_back(); + std::vector& depsOut = x19c_suitDeps.back(); + FillTokenVector(dgrp->GetObjectTagVector(), depsOut); + } +} + +void CGrappleArm::LoadAnimations() +{ + NWeaponTypes::get_token_vector(*x0_grappleArmModel->GetAnimationData(), 0, 42, x18c_anims, true); + x0_grappleArmModel = std::experimental::nullopt; } void CGrappleArm::AsyncLoadSuit(CStateManager& mgr) { + CPlayerState::EPlayerSuit suit = NWeaponTypes::get_current_suit(mgr); + if (suit == x3a8_loadedSuit) + return; + + x0_grappleArmModel = std::experimental::nullopt; + x3b2_29_suitLoading = true; + if (x3a8_loadedSuit != CPlayerState::EPlayerSuit::Invalid) + { + NWeaponTypes::unlock_tokens(x19c_suitDeps[int(x3a8_loadedSuit)]); + x19c_suitDeps[int(x3a8_loadedSuit)].clear(); + } + + if (suit < CPlayerState::EPlayerSuit::Power || suit > CPlayerState::EPlayerSuit::FusionPhazon) + x3a8_loadedSuit = CPlayerState::EPlayerSuit::Power; + else + x3a8_loadedSuit = suit; + + NWeaponTypes::lock_tokens(x19c_suitDeps[int(x3a8_loadedSuit)]); +} + +void CGrappleArm::ResetAuxParams(bool resetGunController) +{ + x3b2_24_active = false; + x3b2_27_armMoving = false; + x2e0_auxXf = zeus::CTransform::Identity(); + if (resetGunController) + x328_gunController->Reset(); +} + +void CGrappleArm::DisconnectGrappleBeam() +{ + x394_grappleClawGen->SetParticleEmission(false); + x3b2_25_beamActive = false; + GrappleBeamDisconnected(); } void CGrappleArm::SetAnimState(EArmState state) { + if (x334_animState == state) + return; + x0_grappleArmModel->AnimationData()->EnableLooping(false); + x3b2_28_isGrappling = true; + + switch (state) + { + case EArmState::IntoGrapple: + { + ResetAuxParams(true); + CAnimPlaybackParms parms(0, -1, 1.f, true); + x0_grappleArmModel->AnimationData()->SetAnimation(parms, false); + x3b2_25_beamActive = false; + x3b2_24_active = true; + break; + } + case EArmState::IntoGrappleIdle: + { + CAnimPlaybackParms parms(1, -1, 1.f, true); + x0_grappleArmModel->AnimationData()->EnableLooping(true); + x0_grappleArmModel->AnimationData()->SetAnimation(parms, false); + break; + } + case EArmState::FireGrapple: + { + CAnimPlaybackParms parms(2, -1, 1.f, true); + x0_grappleArmModel->AnimationData()->SetAnimation(parms, false); + break; + } + case EArmState::ConnectGrapple: + { + CAnimPlaybackParms parms(3, -1, 1.f, true); + x0_grappleArmModel->AnimationData()->SetAnimation(parms, false); + break; + } + case EArmState::Connected: + { + CAnimPlaybackParms parms(3, -1, 1.f, true); + x0_grappleArmModel->AnimationData()->SetAnimation(parms, false); + break; + } + case EArmState::OutOfGrapple: + { + CAnimPlaybackParms parms(4, -1, 1.f, true); + x0_grappleArmModel->AnimationData()->SetAnimation(parms, false); + DisconnectGrappleBeam(); + break; + } + case EArmState::Done: + x3b2_28_isGrappling = false; + break; + default: + break; + } + + x334_animState = state; } -void CGrappleArm::Activate(bool) +void CGrappleArm::Activate(bool intoGrapple) { - + SetAnimState(intoGrapple ? EArmState::IntoGrapple : EArmState::OutOfGrapple); } void CGrappleArm::GrappleBeamDisconnected() { - + if (x32c_grappleLoopSfx) + { + CSfxManager::SfxStop(x32c_grappleLoopSfx); + x32c_grappleLoopSfx.reset(); + } } void CGrappleArm::GrappleBeamConnected() { - + if (!x32c_grappleLoopSfx) + x32c_grappleLoopSfx = NWeaponTypes::play_sfx(1527, false, true, -0.15f); } void CGrappleArm::RenderGrappleBeam(const CStateManager& mgr, const zeus::CVector3f& pos) { - + if (x3b2_24_active && !x3b2_29_suitLoading) + { + zeus::CTransform tmpXf = zeus::CTransform::Translate(pos) * x220_xf; + if (x3b2_25_beamActive) + { + if (x3b2_26_grappleHit) + x398_grappleHitGen->Render(); + x394_grappleClawGen->Render(); + x3a0_grappleSwooshGen->Render(); + x390_grappleSegmentGen->Render(); + zeus::CTransform backupViewMtx = CGraphics::g_ViewMatrix; + CGraphics::SetViewPointMatrix(tmpXf.inverse() * backupViewMtx); + CGraphics::SetModelMatrix(zeus::CTransform::Identity()); + x39c_grappleMuzzleGen->Render(); + CGraphics::SetViewPointMatrix(backupViewMtx); + } + } } void CGrappleArm::TouchModel(const CStateManager& mgr) const { + if (x3b2_24_active && !x3b2_29_suitLoading) + { + x0_grappleArmModel->Touch(mgr, 0); + if (x50_grappleArmSkeletonModel) + x50_grappleArmSkeletonModel->Touch(mgr, 0); + if (mgr.GetPlayerState()->HasPowerUp(CPlayerState::EItemType::GrappleBeam)) + { + xa0_grappleGearModel.Touch(mgr, 0); + xec_grapNoz1Model.Touch(mgr, 0); + x138_grapNoz2Model.Touch(mgr, 0); + } + } +} +void CGrappleArm::LoadSuitPoll() +{ + if (NWeaponTypes::are_tokens_ready(x19c_suitDeps[int(x3a8_loadedSuit)])) + { + x0_grappleArmModel.emplace(CAnimRes(g_tweakGunRes->x8_grappleArm, 0, x31c_scale, 41, false)); + x0_grappleArmModel->SetSortThermal(true); + x328_gunController = std::make_unique(*x0_grappleArmModel); + x3b2_29_suitLoading = false; + } +} + +void CGrappleArm::BuildXRayModel() +{ + x50_grappleArmSkeletonModel.emplace(CAnimRes(g_tweakGunRes->x8_grappleArm, 8, x31c_scale, + !x328_gunController ? 41 : x328_gunController->GetCurAnimId(), false)); + x50_grappleArmSkeletonModel->SetSortThermal(true); +} + +void CGrappleArm::DoUserAnimEvent(CStateManager& mgr, const CInt32POINode& node, EUserEventType type) +{ + switch (type) + { + case EUserEventType::Projectile: + if (x3b2_27_armMoving) + return; + x398_grappleHitGen = std::make_unique(x36c_grappleHitDesc, + CElementGen::EModelOrientationType::Normal, + CElementGen::EOptionalSystemFlags::One); + x39c_grappleMuzzleGen = std::make_unique(x378_grappleMuzzleDesc, + CElementGen::EModelOrientationType::Normal, + CElementGen::EOptionalSystemFlags::One); + x338_beamT = 0.f; + x33c_beamDist = 0.f; + x340_anglePhase = 0.f; + x344_xAmplitude = g_GrappleBeamXWaveAmplitude; + x348_zAmplitude = g_GrappleBeamZWaveAmplitude; + x398_grappleHitGen->SetParticleEmission(false); + x394_grappleClawGen->SetParticleEmission(true); + NWeaponTypes::play_sfx(1526, false, false, -0.15f); + mgr.GetRumbleManager().Rumble(mgr, ERumbleFxId::Fourteen, 1.f, ERumblePriority::Three); + break; + default: + break; + } +} + +void CGrappleArm::DoUserAnimEvents(CStateManager& mgr) +{ + zeus::CVector3f armToCam = mgr.GetCameraManager()->GetCurrentCamera(mgr)->GetTranslation() - x220_xf.origin; + const CAnimData& animData = *x0_grappleArmModel->GetAnimationData(); + for (int i=0 ; iUpdate(dt, mgr)) + ResetAuxParams(false); +} + +void CGrappleArm::UpdateGrappleBeamFx(const zeus::CVector3f& beamGunPos, + const zeus::CVector3f& beamAirPos, CStateManager& mgr) +{ + x394_grappleClawGen->SetTranslation(beamAirPos); + x390_grappleSegmentGen->SetParticleEmission(true); + + zeus::CVector3f segmentDelta = beamAirPos - beamGunPos; + zeus::CVector3f swooshSegmentDelta = segmentDelta * 0.02f; + int numSegments = int(2.f * segmentDelta.magnitude() + 1.f); + segmentDelta = (1.f / float(numSegments)) * segmentDelta; + + zeus::CVector3f segmentPos = beamGunPos; + zeus::CTransform rotation = x220_xf.getRotation(); + for (int i=0 ; i 0) + vec = rotation * zeus::CVector3f(std::cos(i + x340_anglePhase) * x344_xAmplitude, 0.f, + std::sin(float(i)) * x348_zAmplitude); + x390_grappleSegmentGen->SetTranslation(vec * segmentPos); + x390_grappleSegmentGen->ForceParticleCreation(1); + segmentPos += segmentDelta; + } + + x390_grappleSegmentGen->SetParticleEmission(false); + x3a0_grappleSwooshGen->DoGrappleUpdate(beamGunPos, rotation, x340_anglePhase, x344_xAmplitude, + x348_zAmplitude, swooshSegmentDelta); +} + +bool CGrappleArm::UpdateGrappleBeam(float dt, const zeus::CTransform& beamLoc, CStateManager& mgr) +{ + bool beamConnected = false; + if (TCastToConstPtr act = mgr.GetObjectById(mgr.GetPlayer().GetOrbitTargetId())) + x310_grapplePointPos = act->GetTranslation(); + else + x310_grapplePointPos = x220_xf.origin; + + zeus::CVector3f beamGunPos = (x220_xf * beamLoc).origin; + zeus::CVector3f beamAirPos = beamGunPos * (1.f - x338_beamT) + x310_grapplePointPos * x338_beamT; + + switch (x334_animState) + { + case EArmState::FireGrapple: + case EArmState::Three: + { + float gunToPointMag = (x310_grapplePointPos - beamGunPos).magnitude(); + if (gunToPointMag > 0.f) + x338_beamT = x33c_beamDist / gunToPointMag; + else + x338_beamT = 1.f; + float speedMult = + mgr.GetPlayer().GetPlayerMovementState() != CPlayer::EPlayerMovementState::OnGround ? 2.f : 1.f; + x33c_beamDist += speedMult * (dt * g_GrappleBeamSpeed); + if (x338_beamT >= 1.f) + { + x338_beamT = 1.f; + beamConnected = true; + } + break; + } + case EArmState::ConnectGrapple: + { + float delta = 4.f * dt; + x344_xAmplitude -= delta; + x348_zAmplitude -= delta; + if (x344_xAmplitude < 0.f) + x344_xAmplitude = 0.f; + if (x348_zAmplitude < 0.f) + x348_zAmplitude = 0.f; + break; + } + default: + break; + } + + if (x3b2_25_beamActive) + { + x340_anglePhase += g_GrappleBeamAnglePhaseDelta; + UpdateGrappleBeamFx(beamGunPos, beamAirPos, mgr); + x394_grappleClawGen->Update(dt); + x390_grappleSegmentGen->Update(dt); + } + + return beamConnected; +} + +void CGrappleArm::UpdateSwingAction(float grappleSwingT, float dt, CStateManager& mgr) +{ + if (x3b2_29_suitLoading) + return; + + if (x334_animState == EArmState::FireGrapple) + DoUserAnimEvents(mgr); + + zeus::CTransform beamLocXf = x0_grappleArmModel->GetScaledLocatorTransform("LGBeam"); + bool grappleConnected = UpdateGrappleBeam(dt, beamLocXf, mgr); + + if ((grappleSwingT > 0.175f && grappleSwingT < 0.3f) || + (grappleSwingT > 0.7f && grappleSwingT < 0.9f)) + { + if (!CSfxManager::IsPlaying(x330_swooshSfx)) + { + x330_swooshSfx = NWeaponTypes::play_sfx(1528, false, false, -0.15f); + if (x3b0_rumbleHandle != -1) + mgr.GetRumbleManager().StopRumble(x3b0_rumbleHandle); + x3b0_rumbleHandle = mgr.GetRumbleManager().Rumble(mgr, ERumbleFxId::Seventeen, 1.f, ERumblePriority::Three); + } + } + + if (!x0_grappleArmModel->GetAnimationData()->IsAnimTimeRemaining(dt, "Whole Body")) + { + switch (x334_animState) + { + case EArmState::IntoGrapple: + case EArmState::Seven: + SetAnimState(EArmState::IntoGrappleIdle); + break; + case EArmState::FireGrapple: + if (grappleConnected) + { + SetAnimState(EArmState::ConnectGrapple); + x3b2_26_grappleHit = true; + x398_grappleHitGen->SetParticleEmission(true); + GrappleBeamConnected(); + if (x3b0_rumbleHandle != -1) + mgr.GetRumbleManager().StopRumble(x3b0_rumbleHandle); + } + break; + case EArmState::ConnectGrapple: + if (x344_xAmplitude == 0.f) + SetAnimState(EArmState::Connected); + break; + case EArmState::OutOfGrapple: + if (x3b0_rumbleHandle != -1) + mgr.GetRumbleManager().StopRumble(x3b0_rumbleHandle); + SetAnimState(EArmState::Done); + x3b2_24_active = false; + break; + default: + break; + } + } + + if (x3b2_25_beamActive) + { + x39c_grappleMuzzleGen->SetTranslation(beamLocXf.origin); + x39c_grappleMuzzleGen->Update(dt); + if (x3b2_26_grappleHit) + { + x3b2_26_grappleHit = !x398_grappleHitGen->IsSystemDeletable(); + x398_grappleHitGen->SetTranslation(x310_grapplePointPos); + x398_grappleHitGen->Update(dt); + } + } } void CGrappleArm::Update(float grappleSwingT, float dt, CStateManager& mgr) { + if (!(x3b2_24_active && !x3b2_29_suitLoading)) + { + if (x3b2_29_suitLoading) + LoadSuitPoll(); + return; + } + if (mgr.GetPlayerState()->GetCurrentVisor() == CPlayerState::EPlayerVisor::XRay) + { + if (!x50_grappleArmSkeletonModel) + BuildXRayModel(); + } + else + { + if (x50_grappleArmSkeletonModel) + x50_grappleArmSkeletonModel = std::experimental::nullopt; + } + + float speed = 1.f; + if (!x3b2_27_armMoving) + speed = (mgr.GetPlayer().GetPlayerMovementState() != CPlayer::EPlayerMovementState::OnGround && + x334_animState != EArmState::OutOfGrapple) ? 4.f : 1.f; + x0_grappleArmModel->AdvanceAnimation(speed * dt, mgr, kInvalidAreaId, true); + if (mgr.GetPlayerState()->HasPowerUp(CPlayerState::EItemType::GrappleBeam)) + { + x250_grapLocatorXf = x0_grappleArmModel->GetScaledLocatorTransformDynamic("grapLocator_SDK", nullptr); + x280_grapNozLoc1Xf = x0_grappleArmModel->GetScaledLocatorTransform("gNozLoc1_SDK"); + x2b0_grapNozLoc2Xf = x0_grappleArmModel->GetScaledLocatorTransform("gNozLoc1_SDK"); + } + + if (x3b2_27_armMoving) + UpdateArmMovement(dt, mgr); + else + UpdateSwingAction(grappleSwingT, dt, mgr); + + if (x3a4_rainSplashGenerator) + x3a4_rainSplashGenerator->Update(dt, mgr); } void CGrappleArm::PreRender(const CStateManager& mgr, const zeus::CFrustum& frustum, const zeus::CVector3f& camPos) { + if (x3b2_24_active && !x3b2_29_suitLoading) + { + x0_grappleArmModel->AnimationData()->PreRender(); + if (x50_grappleArmSkeletonModel) + x50_grappleArmSkeletonModel->AnimationData()->PreRender(); + } } +void CGrappleArm::RenderXRayModel(const CStateManager& mgr, const zeus::CTransform& modelXf, + const CModelFlags& flags) const +{ + CGraphics::SetModelMatrix(modelXf * zeus::CTransform::Scale(x0_grappleArmModel->GetScale())); + //CGraphics::DisableAllLights(); + //g_Renderer->SetAmbientColor(zeus::CColor::skWhite); + CSkinnedModel& model = + const_cast(*x50_grappleArmSkeletonModel->GetAnimationData()->GetModelData()); + model.GetModelInst()->ActivateLights({CLight::BuildLocalAmbient({}, zeus::CColor::skWhite)}); + const_cast(this)->x0_grappleArmModel->AnimationData()->Render(model, flags, {}, nullptr); + //g_Renderer->SetAmbientColor(zeus::CColor::skWhite); + //CGraphics::DisableAllLights(); +} + +void CGrappleArm::PointGenerator(void* ctx, const std::vector>& vn) +{ + reinterpret_cast(ctx)->GeneratePoints(vn); +} + void CGrappleArm::Render(const CStateManager& mgr, const zeus::CVector3f& pos, const CModelFlags& flags, const CActorLights* lights) const { + if (x3b2_24_active && !x3b2_29_suitLoading) + { + zeus::CTransform modelXf = zeus::CTransform::Translate(pos) * x220_xf * x2e0_auxXf; + if (x50_grappleArmSkeletonModel) + RenderXRayModel(mgr, modelXf, flags); + CModelFlags useFlags; + const CActorLights* useLights; + if (mgr.GetPlayerState()->GetCurrentVisor() == CPlayerState::EPlayerVisor::XRay) + { + useFlags = CModelFlags(5, 0, 3, zeus::CColor(1.f, 0.25f)); + useLights = nullptr; + } + else + { + useFlags = flags; + useLights = lights; + } + + if (x3a4_rainSplashGenerator && x3a4_rainSplashGenerator->IsRaining()) + CSkinnedModel::SetPointGeneratorFunc(x3a4_rainSplashGenerator.get(), PointGenerator); + + x0_grappleArmModel->Render(mgr, modelXf, useLights, useFlags); + + if (x3a4_rainSplashGenerator && x3a4_rainSplashGenerator->IsRaining()) + { + CSkinnedModel::ClearPointGeneratorFunc(); + x3a4_rainSplashGenerator->Draw(modelXf); + } + + if (mgr.GetPlayerState()->HasPowerUp(CPlayerState::EItemType::GrappleBeam)) + { + xa0_grappleGearModel.Render(mgr, modelXf * x250_grapLocatorXf, useLights, useFlags); + xec_grapNoz1Model.Render(mgr, modelXf * x280_grapNozLoc1Xf, useLights, useFlags); + x138_grapNoz2Model.Render(mgr, modelXf * x2b0_grapNozLoc2Xf, useLights, useFlags); + } + } } -void CGrappleArm::AcceptScriptMsg(EScriptObjectMessage, TUniqueId, CStateManager&) +void CGrappleArm::AcceptScriptMsg(EScriptObjectMessage msg, TUniqueId sender, CStateManager& mgr) { - + if (msg == EScriptObjectMessage::Registered) + AsyncLoadSuit(mgr); } -void CGrappleArm::EnterStruck(CStateManager& mgr, float angle, bool attack, bool b2) +void CGrappleArm::EnterStruck(CStateManager& mgr, float angle, bool bigStrike, bool notInFreeLook) { + if (x3b2_29_suitLoading) + return; + if (x3b2_28_isGrappling) + { + DisconnectGrappleBeam(); + x3b2_28_isGrappling = false; + } + + if (!x3b2_27_armMoving) + { + x3b2_24_active = true; + x3b2_27_armMoving = true; + x334_animState = EArmState::GunControllerAnimation; + } + + x328_gunController->EnterStruck(mgr, angle, bigStrike, notInFreeLook); } void CGrappleArm::EnterIdle(CStateManager& mgr) { + if (x3b2_29_suitLoading) + return; + x328_gunController->EnterIdle(mgr); } -void CGrappleArm::EnterFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 gunId, s32 parm2) +void CGrappleArm::EnterFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 gunId, s32 animSet) { + if (x3b2_29_suitLoading) + return; + x3b2_24_active = true; + x3b2_27_armMoving = true; + x334_animState = EArmState::GunControllerAnimation; + + x328_gunController->EnterFidget(mgr, s32(type), gunId, animSet); } void CGrappleArm::EnterFreeLook(s32 gunId, s32 setId, CStateManager& mgr) { + if (x3b2_29_suitLoading) + return; + x3b2_24_active = true; + x3b2_27_armMoving = true; + x334_animState = EArmState::GunControllerAnimation; + + x328_gunController->EnterFreeLook(mgr, gunId, setId); } void CGrappleArm::EnterComboFire(s32 gunId, CStateManager& mgr) { + if (x3b2_29_suitLoading) + return; + x3b2_24_active = true; + x3b2_27_armMoving = true; + x334_animState = EArmState::GunControllerAnimation; + + x328_gunController->EnterComboFire(mgr, gunId); } -void CGrappleArm::ReturnToDefault(CStateManager& mgr, float f1, bool b1) +void CGrappleArm::ReturnToDefault(CStateManager& mgr, float dt, bool setState) { + if (x3b2_29_suitLoading) + return; + x328_gunController->ReturnToDefault(mgr, dt, setState); } } diff --git a/Runtime/Weapon/CGrappleArm.hpp b/Runtime/Weapon/CGrappleArm.hpp index 166ae27cc..29cd81b64 100644 --- a/Runtime/Weapon/CGrappleArm.hpp +++ b/Runtime/Weapon/CGrappleArm.hpp @@ -4,6 +4,7 @@ #include "RetroTypes.hpp" #include "zeus/CVector3f.hpp" #include "Character/CModelData.hpp" +#include "Character/CAnimCharacterSet.hpp" #include "CStateManager.hpp" #include "CGunController.hpp" #include "CGunMotion.hpp" @@ -11,7 +12,7 @@ namespace urde { class CStateManager; -class CModelFlags; +struct CModelFlags; class CActorLights; class CGrappleArm @@ -19,30 +20,65 @@ class CGrappleArm public: enum class EArmState { - Zero, - One, - Two, + IntoGrapple, + IntoGrappleIdle, + FireGrapple, Three, - Four, + ConnectGrapple, Five, - Six, + Connected, Seven, - Eight, - Nine, - Ten + OutOfGrapple, + GunControllerAnimation, + Done }; private: - CModelData x0_modelData; + std::experimental::optional x0_grappleArmModel; + std::experimental::optional x50_grappleArmSkeletonModel; + CModelData xa0_grappleGearModel; + CModelData xec_grapNoz1Model; + CModelData x138_grapNoz2Model; + TCachedToken x184_grappleArm; + std::vector x18c_anims; + rstl::reserved_vector, 8> x19c_suitDeps; zeus::CTransform x220_xf; + zeus::CTransform x250_grapLocatorXf; + zeus::CTransform x280_grapNozLoc1Xf; + zeus::CTransform x2b0_grapNozLoc2Xf; zeus::CTransform x2e0_auxXf; + zeus::CVector3f x310_grapplePointPos; + zeus::CVector3f x31c_scale; std::unique_ptr x328_gunController; - EArmState x334_animState; + CSfxHandle x32c_grappleLoopSfx; + CSfxHandle x330_swooshSfx; + EArmState x334_animState = EArmState::Done; + float x338_beamT = 0.f; + float x33c_beamDist = 0.f; + float x340_anglePhase = 0.f; + float x344_xAmplitude = 0.f; + float x348_zAmplitude = 0.f; + std::pair x34c_animSfx = {0xffff, {}}; + TCachedToken x354_grappleSegmentDesc; + TCachedToken x360_grappleClawDesc; + TCachedToken x36c_grappleHitDesc; + TCachedToken x378_grappleMuzzleDesc; + TCachedToken x384_grappleSwooshDesc; + std::unique_ptr x390_grappleSegmentGen; + std::unique_ptr x394_grappleClawGen; + std::unique_ptr x398_grappleHitGen; + std::unique_ptr x39c_grappleMuzzleGen; + std::unique_ptr x3a0_grappleSwooshGen; + std::unique_ptr x3a4_rainSplashGenerator; + CPlayerState::EPlayerSuit x3a8_loadedSuit = CPlayerState::EPlayerSuit::Invalid; + float x3ac_pitchBend = 0.f; + s16 x3b0_rumbleHandle = -1; union { struct { bool x3b2_24_active : 1; bool x3b2_25_beamActive : 1; + bool x3b2_26_grappleHit : 1; bool x3b2_27_armMoving : 1; bool x3b2_28_isGrappling : 1; bool x3b2_29_suitLoading : 1; @@ -50,8 +86,30 @@ private: u32 _dummy = 0; }; + static float g_GrappleBeamAnglePhaseDelta; + static float g_GrappleBeamXWaveAmplitude; + static float g_GrappleBeamZWaveAmplitude; + static float g_GrappleBeamSpeed; + + void FillTokenVector(const std::vector& tags, std::vector& objects); + void BuildSuitDependencyList(); + void LoadAnimations(); + void ResetAuxParams(bool resetGunController); + void DisconnectGrappleBeam(); + void LoadSuitPoll(); + void BuildXRayModel(); + void DoUserAnimEvent(CStateManager& mgr, const CInt32POINode& node, EUserEventType type); + void DoUserAnimEvents(CStateManager& mgr); + void UpdateArmMovement(float dt, CStateManager& mgr); + void UpdateGrappleBeamFx(const zeus::CVector3f& beamGunPos, const zeus::CVector3f& beamAirPos, CStateManager& mgr); + bool UpdateGrappleBeam(float dt, const zeus::CTransform& beamLoc, CStateManager& mgr); + void UpdateSwingAction(float grappleSwingT, float dt, CStateManager& mgr); + void RenderXRayModel(const CStateManager& mgr, const zeus::CTransform& modelXf, const CModelFlags& flags) const; + + static void PointGenerator(void* ctx, const std::vector>& vn); + public: - explicit CGrappleArm(const zeus::CVector3f& vec); + explicit CGrappleArm(const zeus::CVector3f& scale); void AsyncLoadSuit(CStateManager& mgr); void SetTransform(const zeus::CTransform& xf) { x220_xf = xf; } const zeus::CTransform& GetTransform() const { return x220_xf; } @@ -73,12 +131,12 @@ public: void Render(const CStateManager& mgr, const zeus::CVector3f& pos, const CModelFlags& flags, const CActorLights* lights) const; void AcceptScriptMsg(EScriptObjectMessage, TUniqueId, CStateManager&); - void EnterStruck(CStateManager& mgr, float angle, bool attack, bool b2); + void EnterStruck(CStateManager& mgr, float angle, bool bigStrike, bool notInFreeLook); void EnterIdle(CStateManager& mgr); - void EnterFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 gunId, s32 parm2); + void EnterFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 gunId, s32 animSet); void EnterFreeLook(s32 gunId, s32 setId, CStateManager& mgr); void EnterComboFire(s32 gunId, CStateManager& mgr); - void ReturnToDefault(CStateManager& mgr, float f1, bool b1); + void ReturnToDefault(CStateManager& mgr, float dt, bool setState); CGunController* GunController() { return x328_gunController.get(); } }; diff --git a/Runtime/Weapon/CGunController.cpp b/Runtime/Weapon/CGunController.cpp index 7eaa9278c..cd5b62bd2 100644 --- a/Runtime/Weapon/CGunController.cpp +++ b/Runtime/Weapon/CGunController.cpp @@ -6,14 +6,14 @@ namespace urde { -void CGunController::LoadFidgetAnimAsync(CStateManager& mgr, s32 type, s32 gunId, s32 parm2) +void CGunController::LoadFidgetAnimAsync(CStateManager& mgr, s32 type, s32 gunId, s32 animSet) { - x30_fidget.LoadAnimAsync(*x0_modelData.AnimationData(), type, gunId, parm2, mgr); + x30_fidget.LoadAnimAsync(*x0_modelData.AnimationData(), type, gunId, animSet, mgr); } -void CGunController::EnterFidget(CStateManager& mgr, s32 type, s32 gunId, s32 parm2) +void CGunController::EnterFidget(CStateManager& mgr, s32 type, s32 gunId, s32 animSet) { - x54_curAnimId = x30_fidget.SetAnim(*x0_modelData.AnimationData(), type, gunId, parm2, mgr); + x54_curAnimId = x30_fidget.SetAnim(*x0_modelData.AnimationData(), type, gunId, animSet, mgr); x50_gunState = EGunState::Fidget; } diff --git a/Runtime/Weapon/CGunController.hpp b/Runtime/Weapon/CGunController.hpp index 07856f7d0..da3a73712 100644 --- a/Runtime/Weapon/CGunController.hpp +++ b/Runtime/Weapon/CGunController.hpp @@ -40,8 +40,8 @@ public: } void UnLoadFidget() { x30_fidget.UnLoadAnim(); } - void LoadFidgetAnimAsync(CStateManager& mgr, s32 type, s32 gunId, s32 parm2); - void EnterFidget(CStateManager& mgr, s32 type, s32 gunId, s32 parm2); + void LoadFidgetAnimAsync(CStateManager& mgr, s32 type, s32 gunId, s32 animSet); + void EnterFidget(CStateManager& mgr, s32 type, s32 gunId, s32 animSet); bool IsFidgetLoaded() const { return x30_fidget.IsAnimLoaded(); } s32 GetFreeLookSetId() const { return x4_freeLook.GetSetId(); } bool IsComboOver() const { return x1c_comboFire.IsComboOver(); } @@ -53,6 +53,7 @@ public: void ReturnToDefault(CStateManager& mgr, float dt, bool setState); void ReturnToBasePosition(CStateManager&, float); void Reset(); + s32 GetCurAnimId() const { return x54_curAnimId; } }; } diff --git a/Runtime/Weapon/CGunMotion.hpp b/Runtime/Weapon/CGunMotion.hpp index 3485edf87..ecf6d7b7d 100644 --- a/Runtime/Weapon/CGunMotion.hpp +++ b/Runtime/Weapon/CGunMotion.hpp @@ -24,8 +24,8 @@ enum class EAnimationState enum class EFidgetType { Invalid = -1, - Zero, - One + Minor, + Major }; } diff --git a/Runtime/Weapon/CGunWeapon.hpp b/Runtime/Weapon/CGunWeapon.hpp index c1802dd4b..2ebfd9627 100644 --- a/Runtime/Weapon/CGunWeapon.hpp +++ b/Runtime/Weapon/CGunWeapon.hpp @@ -127,8 +127,8 @@ public: bool PlayPasAnim(SamusGun::EAnimationState state, CStateManager& mgr, float angle) { return false; } void UnLoadFidget() {} bool IsFidgetLoaded() const { return x100_gunController->IsFidgetLoaded(); } - void AsyncLoadFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 parm2) - { x100_gunController->LoadFidgetAnimAsync(mgr, s32(type), s32(x200_beamId), parm2); } + void AsyncLoadFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 animSet) + { x100_gunController->LoadFidgetAnimAsync(mgr, s32(type), s32(x200_beamId), animSet); } void EnterFidget(CStateManager& mgr, SamusGun::EFidgetType type, s32 parm2) { x100_gunController->EnterFidget(mgr, s32(type), s32(x200_beamId), parm2); } bool HasSolidModelData() const { return x10_solidModelData.operator bool(); } diff --git a/Runtime/Weapon/CPlayerGun.cpp b/Runtime/Weapon/CPlayerGun.cpp index 7b20fbcd2..4cf66265d 100644 --- a/Runtime/Weapon/CPlayerGun.cpp +++ b/Runtime/Weapon/CPlayerGun.cpp @@ -530,7 +530,7 @@ void CPlayerGun::HandleBeamChange(const CFinalInput& input, CStateManager& mgr) if (ExitMissile()) { if (!CSfxManager::IsPlaying(x2e4_invalidSfx)) - x2e4_invalidSfx = PlaySfx(1763, x834_27_underwater, false, 0.165f); + x2e4_invalidSfx = NWeaponTypes::play_sfx(1763, x834_27_underwater, false, 0.165f); } else { @@ -588,15 +588,6 @@ void CPlayerGun::ResetBeamParams(CStateManager& mgr, const CPlayerState& playerS x833_30_canShowAuxMuzzleEffect = true; } -CSfxHandle CPlayerGun::PlaySfx(u16 sfx, bool underwater, bool looped, float pan) -{ - CSfxHandle hnd = CSfxManager::SfxStart(sfx, 1.f, pan, true, 0x7f, looped, kInvalidAreaId); - CSfxManager::SfxSpan(hnd, 0.f); - if (underwater) - CSfxManager::PitchBend(hnd, -1.f); - return hnd; -} - static const u16 skFromMissileSound[] = { 1824, 1849, 1851, 1853 }; static const u16 skFromBeamSound[] = { 0, 1822, 1828, 1826 }; static const u16 skToMissileSound[] = { 1823, 1829, 1850, 1852 }; @@ -628,7 +619,7 @@ void CPlayerGun::PlayAnim(NWeaponTypes::EGunAnimType type, bool loop) } if (sfx != 0xffff) - PlaySfx(sfx, x834_27_underwater, false, 0.165f); + NWeaponTypes::play_sfx(sfx, x834_27_underwater, false, 0.165f); } void CPlayerGun::CancelCharge(CStateManager& mgr, bool withEffect) @@ -776,9 +767,9 @@ void CPlayerGun::ReturnToRestPose() void CPlayerGun::ResetIdle(CStateManager& mgr) { x550_camBob.SetState(CPlayerCameraBob::ECameraBobState::GunFireNoBob, mgr); - if (x3a4_fidget.GetState() != CFidget::EState::Zero) + if (x3a4_fidget.GetState() != CFidget::EState::NoFidget) { - if (x3a4_fidget.GetState() == CFidget::EState::Seven) + if (x3a4_fidget.GetState() == CFidget::EState::Loading) UnLoadFidget(); ReturnArmAndGunToDefault(mgr, true); } @@ -1118,7 +1109,7 @@ void CPlayerGun::ProcessGunMorph(float dt, CStateManager& mgr) x730_outgoingBeam = nullptr; } if (isUnmorphed) - PlaySfx(skIntoBeamSound[int(x310_currentBeam)], x834_27_underwater, false, 0.165f); + NWeaponTypes::play_sfx(skIntoBeamSound[int(x310_currentBeam)], x834_27_underwater, false, 0.165f); x72c_currentBeam->SetRainSplashGenerator(x748_rainSplashGenerator.get()); x72c_currentBeam->EnableFx(true); PlayAnim(NWeaponTypes::EGunAnimType::ToBeam, false); @@ -1149,7 +1140,7 @@ void CPlayerGun::SetPhazonBeamFeedback(bool active) CSfxManager::SfxStop(x2e8_phazonBeamSfx); x2e8_phazonBeamSfx.reset(); if (active) - x2e8_phazonBeamSfx = PlaySfx(3141, x834_27_underwater, false, 0.165f); + x2e8_phazonBeamSfx = NWeaponTypes::play_sfx(3141, x834_27_underwater, false, 0.165f); } void CPlayerGun::StartPhazonBeamTransition(bool active, CStateManager& mgr, CPlayerState& playerState) @@ -1284,7 +1275,7 @@ void CPlayerGun::UpdateChargeState(float dt, CStateManager& mgr) { PlayAnim(NWeaponTypes::EGunAnimType::ChargeUp, false); if (!x2e0_chargeSfx) - x2e0_chargeSfx = PlaySfx(skBeamChargeUpSound[int(x310_currentBeam)], + x2e0_chargeSfx = NWeaponTypes::play_sfx(skBeamChargeUpSound[int(x310_currentBeam)], x834_27_underwater, true, 0.165f); if (x830_chargeRumbleHandle == -1) x830_chargeRumbleHandle = mgr.GetRumbleManager().Rumble(mgr, ERumbleFxId::Twelve, 1.f, @@ -1503,7 +1494,7 @@ void CPlayerGun::FireSecondary(float dt, CStateManager& mgr) if (x835_25_inPhazonBeam || x318_comboAmmoIdx == 0 || !mgr.GetPlayerState()->HasPowerUp(skItemArr[x318_comboAmmoIdx]) || (x2f8_stateFlags & 0x4) != 0x4) { - PlaySfx(1781, x834_27_underwater, false, 0.165f); + NWeaponTypes::play_sfx(1781, x834_27_underwater, false, 0.165f); return; } @@ -1551,7 +1542,7 @@ void CPlayerGun::FireSecondary(float dt, CStateManager& mgr) } else { - PlaySfx(skItemEmptySound[x318_comboAmmoIdx], x834_27_underwater, false, 0.165f); + NWeaponTypes::play_sfx(skItemEmptySound[x318_comboAmmoIdx], x834_27_underwater, false, 0.165f); } } @@ -1599,13 +1590,13 @@ void CPlayerGun::ActivateCombo(CStateManager& mgr) } x72c_currentBeam->EnableCharge(true); StopChargeSound(mgr); - PlaySfx(1762, x834_27_underwater, false, 0.165f); + NWeaponTypes::play_sfx(1762, x834_27_underwater, false, 0.165f); x32c_chargePhase = EChargePhase::ComboXfer; } } else { - PlaySfx(1781, x834_27_underwater, false, 0.165f); + NWeaponTypes::play_sfx(1781, x834_27_underwater, false, 0.165f); } } @@ -1780,7 +1771,7 @@ void CPlayerGun::UpdateWeaponFire(float dt, const CPlayerState& playerState, CSt else { if (!CSfxManager::IsPlaying(x2e4_invalidSfx)) - x2e4_invalidSfx = PlaySfx(1781, x834_27_underwater, false, 0.165f); + x2e4_invalidSfx = NWeaponTypes::play_sfx(1781, x834_27_underwater, false, 0.165f); else x2e4_invalidSfx.reset(); } @@ -1788,7 +1779,7 @@ void CPlayerGun::UpdateWeaponFire(float dt, const CPlayerState& playerState, CSt } else { - if (x3a4_fidget.GetState() == CFidget::EState::Zero) + if (x3a4_fidget.GetState() == CFidget::EState::NoFidget) { if ((x2f8_stateFlags & 0x10) == 0x10 && x744_auxWeapon->IsComboFxActive(mgr)) { @@ -1819,7 +1810,7 @@ void CPlayerGun::EnterFreeLook(CStateManager& mgr) x73c_gunMotion->GetFreeLookSetId(), mgr); } -void CPlayerGun::SetFidgetAnimBits(int parm2, bool beamOnly) +void CPlayerGun::SetFidgetAnimBits(int animSet, bool beamOnly) { x2fc_fidgetAnimBits = 0; if (beamOnly) @@ -1830,14 +1821,14 @@ void CPlayerGun::SetFidgetAnimBits(int parm2, bool beamOnly) switch (x3a4_fidget.GetType()) { - case SamusGun::EFidgetType::Zero: + case SamusGun::EFidgetType::Minor: x2fc_fidgetAnimBits = 1; - if (parm2 != 1) + if (animSet != 1) return; x2fc_fidgetAnimBits |= 4; break; - case SamusGun::EFidgetType::One: - if (parm2 >= 6 || parm2 < 4) + case SamusGun::EFidgetType::Major: + if (animSet >= 6 || animSet < 4) x2fc_fidgetAnimBits = 2; else x2fc_fidgetAnimBits = 1; @@ -1850,21 +1841,21 @@ void CPlayerGun::SetFidgetAnimBits(int parm2, bool beamOnly) void CPlayerGun::AsyncLoadFidget(CStateManager& mgr) { - SetFidgetAnimBits(x3a4_fidget.GetParm2(), x3a4_fidget.GetState() == CFidget::EState::Three); + SetFidgetAnimBits(x3a4_fidget.GetAnimSet(), x3a4_fidget.GetState() == CFidget::EState::HolsterBeam); if ((x2fc_fidgetAnimBits & 0x1) == 0x1) x73c_gunMotion->GunController().LoadFidgetAnimAsync(mgr, s32(x3a4_fidget.GetType()), - s32(x310_currentBeam), x3a4_fidget.GetParm2()); + s32(x310_currentBeam), x3a4_fidget.GetAnimSet()); if ((x2fc_fidgetAnimBits & 0x2) == 0x2) { - x72c_currentBeam->AsyncLoadFidget(mgr, (x3a4_fidget.GetState() == CFidget::EState::Three ? - SamusGun::EFidgetType::Zero : x3a4_fidget.GetType()), x3a4_fidget.GetParm2()); + x72c_currentBeam->AsyncLoadFidget(mgr, (x3a4_fidget.GetState() == CFidget::EState::HolsterBeam ? + SamusGun::EFidgetType::Minor : x3a4_fidget.GetType()), x3a4_fidget.GetAnimSet()); x832_31_inRestPose = false; } if ((x2fc_fidgetAnimBits & 0x4) == 0x4) if (CGunController* gc = x740_grappleArm->GunController()) gc->LoadFidgetAnimAsync(mgr, s32(x3a4_fidget.GetType()), - x3a4_fidget.GetType() != SamusGun::EFidgetType::Zero ? s32(x310_currentBeam) : 0, - x3a4_fidget.GetParm2()); + x3a4_fidget.GetType() != SamusGun::EFidgetType::Minor ? s32(x310_currentBeam) : 0, + x3a4_fidget.GetAnimSet()); } bool CPlayerGun::IsFidgetLoaded() const @@ -1885,7 +1876,7 @@ void CPlayerGun::EnterFidget(CStateManager& mgr) { if ((x2fc_fidgetAnimBits & 0x1) == 0x1) { - x73c_gunMotion->EnterFidget(mgr, x3a4_fidget.GetType(), x3a4_fidget.GetParm2()); + x73c_gunMotion->EnterFidget(mgr, x3a4_fidget.GetType(), x3a4_fidget.GetAnimSet()); x834_25_gunMotionFidgeting = true; } else @@ -1894,12 +1885,12 @@ void CPlayerGun::EnterFidget(CStateManager& mgr) } if ((x2fc_fidgetAnimBits & 0x2) == 0x2) - x72c_currentBeam->EnterFidget(mgr, x3a4_fidget.GetType(), x3a4_fidget.GetParm2()); + x72c_currentBeam->EnterFidget(mgr, x3a4_fidget.GetType(), x3a4_fidget.GetAnimSet()); if ((x2fc_fidgetAnimBits & 0x4) == 0x4) x740_grappleArm->EnterFidget(mgr, x3a4_fidget.GetType(), - x3a4_fidget.GetType() != SamusGun::EFidgetType::Zero ? s32(x310_currentBeam) : 0, - x3a4_fidget.GetParm2()); + x3a4_fidget.GetType() != SamusGun::EFidgetType::Minor ? s32(x310_currentBeam) : 0, + x3a4_fidget.GetAnimSet()); UnLoadFidget(); x3a4_fidget.DoneLoading(); @@ -1909,7 +1900,7 @@ void CPlayerGun::UpdateGunIdle(bool inStrikeCooldown, float camBobT, float dt, C { CPlayer& player = mgr.GetPlayer(); if (player.IsInFreeLook() && !x832_29_lockedOn && !x740_grappleArm->IsGrappling() && - x3a4_fidget.GetState() != CFidget::EState::Three && + x3a4_fidget.GetState() != CFidget::EState::HolsterBeam && player.GetGunHolsterState() == CPlayer::EGunHolsterState::Drawn && !x834_30_inBigStrike) { if ((x2f8_stateFlags & 0x8) != 0x8) @@ -1999,7 +1990,7 @@ void CPlayerGun::UpdateGunIdle(bool inStrikeCooldown, float camBobT, float dt, C { switch (x3a4_fidget.Update(x2ec_lastFireButtonStates, camBobT > 0.01f, inStrikeCooldown, dt, mgr)) { - case CFidget::EState::Zero: + case CFidget::EState::NoFidget: if (x324_idleState != EIdleState::Idle) { x73c_gunMotion->PlayPasAnim(SamusGun::EAnimationState::Idle, mgr, 0.f, false); @@ -2007,9 +1998,9 @@ void CPlayerGun::UpdateGunIdle(bool inStrikeCooldown, float camBobT, float dt, C } x550_camBob.SetState(CPlayerCameraBob::ECameraBobState::WalkNoBob, mgr); break; - case CFidget::EState::One: - case CFidget::EState::Two: - case CFidget::EState::Three: + case CFidget::EState::MinorFidget: + case CFidget::EState::MajorFidget: + case CFidget::EState::HolsterBeam: if (x324_idleState != EIdleState::NotIdle) { x73c_gunMotion->BasePosition(false); @@ -2017,12 +2008,12 @@ void CPlayerGun::UpdateGunIdle(bool inStrikeCooldown, float camBobT, float dt, C } AsyncLoadFidget(mgr); break; - case CFidget::EState::Seven: + case CFidget::EState::Loading: if (IsFidgetLoaded()) EnterFidget(mgr); break; - case CFidget::EState::Four: - case CFidget::EState::Five: + case CFidget::EState::StillMinorFidget: + case CFidget::EState::StillMajorFidget: x550_camBob.SetState(CPlayerCameraBob::ECameraBobState::Walk, mgr); x833_24_isFidgeting = false; x834_26_animPlaying = x834_25_gunMotionFidgeting ? x73c_gunMotion->IsAnimPlaying() : @@ -2432,7 +2423,7 @@ void CPlayerGun::RenderEnergyDrainEffects(const CStateManager& mgr) const void CPlayerGun::DrawArm(const CStateManager& mgr, const zeus::CVector3f& pos, const CModelFlags& flags) const { const CPlayer& player = mgr.GetPlayer(); - if (!x740_grappleArm->GetActive() || x740_grappleArm->GetAnimState() == CGrappleArm::EArmState::Ten) + if (!x740_grappleArm->GetActive() || x740_grappleArm->GetAnimState() == CGrappleArm::EArmState::Done) return; if (player.GetGrappleState() != CPlayer::EGrappleState::None || diff --git a/Runtime/Weapon/CPlayerGun.hpp b/Runtime/Weapon/CPlayerGun.hpp index 7c00d68b9..10f2e9ac1 100644 --- a/Runtime/Weapon/CPlayerGun.hpp +++ b/Runtime/Weapon/CPlayerGun.hpp @@ -328,7 +328,6 @@ private: void SetPhazonBeamMorph(bool intoPhazonBeam); void Reset(CStateManager& mgr, bool b1); void ResetBeamParams(CStateManager& mgr, const CPlayerState& playerState, bool playSelectionSfx); - CSfxHandle PlaySfx(u16 sfx, bool underwater, bool looped, float pan); void PlayAnim(NWeaponTypes::EGunAnimType type, bool loop); void CancelCharge(CStateManager& mgr, bool withEffect); bool ExitMissile(); @@ -360,7 +359,7 @@ private: void ProcessNormalState(u32 releasedStates, u32 pressedStates, CStateManager& mgr, float dt); void UpdateWeaponFire(float dt, const CPlayerState& playerState, CStateManager& mgr); void EnterFreeLook(CStateManager& mgr); - void SetFidgetAnimBits(int parm2, bool beamOnly); + void SetFidgetAnimBits(int animSet, bool beamOnly); void AsyncLoadFidget(CStateManager& mgr); bool IsFidgetLoaded() const; void EnterFidget(CStateManager& mgr); diff --git a/Runtime/Weapon/WeaponCommon.cpp b/Runtime/Weapon/WeaponCommon.cpp index c7cf3e15e..a2386eb07 100644 --- a/Runtime/Weapon/WeaponCommon.cpp +++ b/Runtime/Weapon/WeaponCommon.cpp @@ -61,7 +61,7 @@ bool are_tokens_ready(const std::vector& anims) return true; } -void get_token_vector(CAnimData& animData, int begin, int end, std::vector& tokensOut, bool preLock) +void get_token_vector(const CAnimData& animData, int begin, int end, std::vector& tokensOut, bool preLock) { std::set prims; for (int i=begin ; i& tokensOut, bool preLock) +void get_token_vector(const CAnimData& animData, int animIdx, std::vector& tokensOut, bool preLock) { std::set prims; CAnimPlaybackParms parms(animIdx, -1, 1.f, true); @@ -158,5 +158,32 @@ void do_sound_event(std::pair& sfxHandle, float& pitch, bool do } } +CAssetId get_asset_id_from_name(const char* name) +{ + const SObjectTag* tag = g_ResFactory->GetResourceIdByName(name); + if (!tag) + return {}; + return tag->id; +} + +CPlayerState::EPlayerSuit get_current_suit(const CStateManager& mgr) +{ + CPlayerState::EPlayerSuit suit = mgr.GetPlayerState()->GetCurrentSuit(); + if (suit < CPlayerState::EPlayerSuit::Power || suit > CPlayerState::EPlayerSuit::FusionGravity) + suit = CPlayerState::EPlayerSuit::Power; + if (suit == CPlayerState::EPlayerSuit::FusionPower) + suit = CPlayerState::EPlayerSuit(int(suit) + int(mgr.GetPlayerState()->GetCurrentSuitRaw())); + return suit; +} + +CSfxHandle play_sfx(u16 sfx, bool underwater, bool looped, float pan) +{ + CSfxHandle hnd = CSfxManager::SfxStart(sfx, 1.f, pan, true, 0x7f, looped, kInvalidAreaId); + CSfxManager::SfxSpan(hnd, 0.f); + if (underwater) + CSfxManager::PitchBend(hnd, -1.f); + return hnd; +} + } } diff --git a/Runtime/Weapon/WeaponCommon.hpp b/Runtime/Weapon/WeaponCommon.hpp index 7ab9dfdb3..2d3e73dba 100644 --- a/Runtime/Weapon/WeaponCommon.hpp +++ b/Runtime/Weapon/WeaponCommon.hpp @@ -5,6 +5,7 @@ #include "DataSpec/DNACommon/Tweaks/ITweakPlayerGun.hpp" #include "Audio/CSfxManager.hpp" #include +#include namespace urde { @@ -56,12 +57,15 @@ void primitive_set_to_token_vector(const CAnimData& animData, const std::set& anims); void lock_tokens(std::vector& anims); bool are_tokens_ready(const std::vector& anims); -void get_token_vector(CAnimData& animData, int begin, int end, std::vector& tokensOut, bool preLock); -void get_token_vector(CAnimData& animData, int animIdx, std::vector& tokensOut, bool preLock); +void get_token_vector(const CAnimData& animData, int begin, int end, std::vector& tokensOut, bool preLock); +void get_token_vector(const CAnimData& animData, int animIdx, std::vector& tokensOut, bool preLock); void do_sound_event(std::pair& sfxHandle, float& pitch, bool doPitchBend, u32 soundId, float weight, u32 flags, float falloff, float maxDist, float minVol, float maxVol, const zeus::CVector3f& posToCam, const zeus::CVector3f& pos, TAreaId aid, CStateManager& mgr); +CAssetId get_asset_id_from_name(const char* name); +CPlayerState::EPlayerSuit get_current_suit(const CStateManager& mgr); +CSfxHandle play_sfx(u16 sfx, bool underwater, bool looped, float pan); } diff --git a/Runtime/World/CPlayer.cpp b/Runtime/World/CPlayer.cpp index de649cdbd..12436e0f6 100644 --- a/Runtime/World/CPlayer.cpp +++ b/Runtime/World/CPlayer.cpp @@ -1310,7 +1310,7 @@ void CPlayer::RenderGun(const CStateManager& mgr, const zeus::CVector3f& pos) co return; if (x490_gun->GetGrappleArm().GetActive() && - x490_gun->GetGrappleArm().GetAnimState() != CGrappleArm::EArmState::Ten) + x490_gun->GetGrappleArm().GetAnimState() != CGrappleArm::EArmState::Done) x490_gun->GetGrappleArm().RenderGrappleBeam(mgr, pos); if (mgr.GetPlayerState()->GetActiveVisor(mgr) == CPlayerState::EPlayerVisor::Scan && @@ -3834,11 +3834,11 @@ void CPlayer::UpdateGrappleState(const CFinalInput& input, CStateManager& mgr) case 0: switch (x490_gun->GetGrappleArm().GetAnimState()) { - case CGrappleArm::EArmState::One: + case CGrappleArm::EArmState::IntoGrappleIdle: if (ControlMapper::GetDigitalInput(ControlMapper::ECommands::FireOrBomb, input)) - x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::Two); + x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::FireGrapple); break; - case CGrappleArm::EArmState::Six: + case CGrappleArm::EArmState::Connected: BeginGrapple(playerToPoint, mgr); break; default: @@ -3850,10 +3850,10 @@ void CPlayer::UpdateGrappleState(const CFinalInput& input, CStateManager& mgr) { switch (x490_gun->GetGrappleArm().GetAnimState()) { - case CGrappleArm::EArmState::One: - x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::Two); + case CGrappleArm::EArmState::IntoGrappleIdle: + x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::FireGrapple); break; - case CGrappleArm::EArmState::Six: + case CGrappleArm::EArmState::Connected: BeginGrapple(playerToPoint, mgr); break; default: @@ -3865,10 +3865,10 @@ void CPlayer::UpdateGrappleState(const CFinalInput& input, CStateManager& mgr) case 2: switch (x490_gun->GetGrappleArm().GetAnimState()) { - case CGrappleArm::EArmState::One: - x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::Two); + case CGrappleArm::EArmState::IntoGrappleIdle: + x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::FireGrapple); break; - case CGrappleArm::EArmState::Six: + case CGrappleArm::EArmState::Connected: BeginGrapple(playerToPoint, mgr); break; default: @@ -4022,7 +4022,7 @@ void CPlayer::BreakGrapple(EPlayerOrbitRequest req, CStateManager& mgr) SetOrbitRequest(req, mgr); x3b8_grappleState = EGrappleState::None; AddMaterial(EMaterialTypes::GroundCollider, mgr); - x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::Eight); + x490_gun->GetGrappleArm().SetAnimState(CGrappleArm::EArmState::OutOfGrapple); if (!InGrappleJumpCooldown() && x3b8_grappleState != EGrappleState::JumpOff) DrawGun(mgr); }