From e4cae35edb9885177439a4a2b08e644e43b6b949 Mon Sep 17 00:00:00 2001 From: David Markowitz <39972741+EmosewaMC@users.noreply.github.com> Date: Mon, 16 Oct 2023 05:55:57 -0700 Subject: [PATCH] PhantomPhysics: Fix gravity (#1221) Fix gravity not being adjusted when colliding with a phantom physics object Tested that while on moonbase, the players gravity is no longer reset to 1 when they change their cheat info. --- dGame/dComponents/PhantomPhysicsComponent.cpp | 30 ++++++++++- dGame/dGameMessages/GameMessages.cpp | 54 +++++++++++-------- dGame/dGameMessages/GameMessages.h | 2 + 3 files changed, 64 insertions(+), 22 deletions(-) diff --git a/dGame/dComponents/PhantomPhysicsComponent.cpp b/dGame/dComponents/PhantomPhysicsComponent.cpp index 7b7eaf6b..66030de2 100644 --- a/dGame/dComponents/PhantomPhysicsComponent.cpp +++ b/dGame/dComponents/PhantomPhysicsComponent.cpp @@ -215,7 +215,7 @@ PhantomPhysicsComponent::PhantomPhysicsComponent(Entity* parent) : PhysicsCompon m_dpEntity->SetRotation(m_Rotation); m_dpEntity->SetPosition(m_Position); dpWorld::Instance().AddEntity(m_dpEntity); - } else if (info->physicsAsset == "env\\env_won_fv_gas-blocking-volume.hkx"){ + } else if (info->physicsAsset == "env\\env_won_fv_gas-blocking-volume.hkx") { m_dpEntity = new dpEntity(m_Parent->GetObjectID(), 390.496826f, 111.467964f, 600.821534f, true); m_dpEntity->SetScale(m_Scale); m_dpEntity->SetRotation(m_Rotation); @@ -336,11 +336,37 @@ void PhantomPhysicsComponent::Serialize(RakNet::BitStream* outBitStream, bool bI } } +// Even if we were to implement Friction server side, +// it also defaults to 1.0f in the last argument, so we dont need two functions to do the same thing. +void ApplyCollisionEffect(const LWOOBJID& target, const ePhysicsEffectType effectType, const float effectScale) { + switch (effectType) { + case ePhysicsEffectType::GRAVITY_SCALE: { + auto* targetEntity = Game::entityManager->GetEntity(target); + if (targetEntity) { + auto* controllablePhysicsComponent = targetEntity->GetComponent(); + // dont want to apply an effect to nothing. + if (!controllablePhysicsComponent) return; + controllablePhysicsComponent->SetGravityScale(effectScale); + GameMessages::SendSetGravityScale(target, effectScale, targetEntity->GetSystemAddress()); + } + } + // The other types are not handled by the server + case ePhysicsEffectType::ATTRACT: + case ePhysicsEffectType::FRICTION: + case ePhysicsEffectType::PUSH: + case ePhysicsEffectType::REPULSE: + default: + break; + } +} + void PhantomPhysicsComponent::Update(float deltaTime) { if (!m_dpEntity) return; //Process enter events for (auto en : m_dpEntity->GetNewObjects()) { + if (!en) continue; + ApplyCollisionEffect(en->GetObjectID(), m_EffectType, m_DirectionalMultiplier); m_Parent->OnCollisionPhantom(en->GetObjectID()); //If we are a respawn volume, inform the client: @@ -357,6 +383,8 @@ void PhantomPhysicsComponent::Update(float deltaTime) { //Process exit events for (auto en : m_dpEntity->GetRemovedObjects()) { + if (!en) continue; + ApplyCollisionEffect(en->GetObjectID(), m_EffectType, 1.0f); m_Parent->OnCollisionLeavePhantom(en->GetObjectID()); } } diff --git a/dGame/dGameMessages/GameMessages.cpp b/dGame/dGameMessages/GameMessages.cpp index fa858ab7..1e0fe2d8 100644 --- a/dGame/dGameMessages/GameMessages.cpp +++ b/dGame/dGameMessages/GameMessages.cpp @@ -943,7 +943,7 @@ void GameMessages::SendResurrect(Entity* entity) { destroyableComponent->SetImagination(imaginationToRestore); } } - }); + }); auto cont = static_cast(entity->GetComponent(eReplicaComponentType::CONTROLLABLE_PHYSICS)); @@ -2964,14 +2964,14 @@ void GameMessages::SendSetStunned(LWOOBJID objectId, eStateChangeType stateChang } void GameMessages::SendSetStunImmunity(LWOOBJID target, eStateChangeType state, const SystemAddress& sysAddr, - LWOOBJID originator, - bool bImmuneToStunAttack, - bool bImmuneToStunEquip, - bool bImmuneToStunInteract, - bool bImmuneToStunJump, - bool bImmuneToStunMove, - bool bImmuneToStunTurn, - bool bImmuneToStunUseItem) { + LWOOBJID originator, + bool bImmuneToStunAttack, + bool bImmuneToStunEquip, + bool bImmuneToStunInteract, + bool bImmuneToStunJump, + bool bImmuneToStunMove, + bool bImmuneToStunTurn, + bool bImmuneToStunUseItem) { CBITSTREAM; CMSGHEADER; @@ -2996,15 +2996,15 @@ void GameMessages::SendSetStunImmunity(LWOOBJID target, eStateChangeType state, } void GameMessages::SendSetStatusImmunity(LWOOBJID objectId, eStateChangeType state, const SystemAddress& sysAddr, - bool bImmuneToBasicAttack, - bool bImmuneToDamageOverTime, - bool bImmuneToKnockback, - bool bImmuneToInterrupt, - bool bImmuneToSpeed, - bool bImmuneToImaginationGain, - bool bImmuneToImaginationLoss, - bool bImmuneToQuickbuildInterrupt, - bool bImmuneToPullToPoint) { + bool bImmuneToBasicAttack, + bool bImmuneToDamageOverTime, + bool bImmuneToKnockback, + bool bImmuneToInterrupt, + bool bImmuneToSpeed, + bool bImmuneToImaginationGain, + bool bImmuneToImaginationLoss, + bool bImmuneToQuickbuildInterrupt, + bool bImmuneToPullToPoint) { CBITSTREAM; CMSGHEADER; @@ -5473,6 +5473,18 @@ void GameMessages::HandleRemoveItemFromInventory(RakNet::BitStream* inStream, En } } +void GameMessages::SendSetGravityScale(const LWOOBJID& target, const float effectScale, const SystemAddress& sysAddr) { + CBITSTREAM; + CMSGHEADER; + + bitStream.Write(target); + bitStream.Write(eGameMessageType::SET_GRAVITY_SCALE); + + bitStream.Write(effectScale); + + SEND_PACKET; +} + void GameMessages::HandleMoveItemInInventory(RakNet::BitStream* inStream, Entity* entity) { bool destInvTypeIsDefault = false; int32_t destInvType = eInventoryType::INVALID; @@ -6269,7 +6281,7 @@ void GameMessages::HandleConfirmDonationOnPlayer(RakNet::BitStream* inStream, En auto* donationEntity = Game::entityManager->GetEntity(characterComponent->GetCurrentInteracting()); if (!donationEntity) return; auto* donationVendorComponent = donationEntity->GetComponent(); - if(!donationVendorComponent) return; + if (!donationVendorComponent) return; if (donationVendorComponent->GetActivityID() == 0) { Game::logger->Log("GameMessages", "WARNING: Trying to dontate to a vendor with no activity"); return; @@ -6279,7 +6291,7 @@ void GameMessages::HandleConfirmDonationOnPlayer(RakNet::BitStream* inStream, En auto items = inventory->GetItems(); if (!items.empty()) { uint32_t count = 0; - for (auto& [itemID, item] : items){ + for (auto& [itemID, item] : items) { count += item->GetCount(); item->RemoveFromInventory(); } @@ -6297,7 +6309,7 @@ void GameMessages::HandleCancelDonationOnPlayer(RakNet::BitStream* inStream, Ent auto* inventory = inventoryComponent->GetInventory(eInventoryType::DONATION); if (!inventory) return; auto items = inventory->GetItems(); - for (auto& [itemID, item] : items){ + for (auto& [itemID, item] : items) { inventoryComponent->MoveItemToInventory(item, eInventoryType::BRICKS, item->GetCount(), false, false, true); } auto* characterComponent = entity->GetComponent(); diff --git a/dGame/dGameMessages/GameMessages.h b/dGame/dGameMessages/GameMessages.h index 93db23c1..6a572d97 100644 --- a/dGame/dGameMessages/GameMessages.h +++ b/dGame/dGameMessages/GameMessages.h @@ -109,6 +109,8 @@ namespace GameMessages { void SendSetInventorySize(Entity* entity, int invType, int size); + void SendSetGravityScale(const LWOOBJID& target, const float effectScale, const SystemAddress& sysAddr); + void SendSetEmoteLockState(Entity* entity, bool bLock, int emoteID); void SendSetJetPackMode(Entity* entity, bool use, bool bypassChecks = false, bool doHover = false, int effectID = -1, float airspeed = 10, float maxAirspeed = 15, float verticalVelocity = 1, int warningEffectID = -1); void SendResurrect(Entity* entity);