Skip to content

Commit

Permalink
Merge pull request #1639 from DarkflameUniverse/FixPetCrash
Browse files Browse the repository at this point in the history
fix: nullptr crashes in PetComponent AddDrainImaginationTimer and Deactivate
  • Loading branch information
DarwinAnim8or authored Oct 27, 2024
2 parents 102e355 + 0d218fc commit bfe6900
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 18 deletions.
35 changes: 18 additions & 17 deletions dGame/dComponents/PetComponent.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -795,8 +795,6 @@ void PetComponent::Wander() {
}

void PetComponent::Activate(Item* item, bool registerPet, bool fromTaming) {
AddDrainImaginationTimer(item, fromTaming);

m_ItemId = item->GetId();
m_DatabaseId = item->GetSubKey();

Expand All @@ -807,6 +805,7 @@ void PetComponent::Activate(Item* item, bool registerPet, bool fromTaming) {
inventoryComponent->DespawnPet();

m_Owner = inventoryComponent->GetParent()->GetObjectID();
AddDrainImaginationTimer(fromTaming);

auto* owner = GetOwner();

Expand Down Expand Up @@ -859,17 +858,14 @@ void PetComponent::Activate(Item* item, bool registerPet, bool fromTaming) {
}
}

void PetComponent::AddDrainImaginationTimer(Item* item, bool fromTaming) {
void PetComponent::AddDrainImaginationTimer(bool fromTaming) {
if (Game::config->GetValue("pets_take_imagination") != "1") return;

auto playerInventory = item->GetInventory();
if (!playerInventory) return;

auto playerInventoryComponent = playerInventory->GetComponent();
if (!playerInventoryComponent) return;

auto playerEntity = playerInventoryComponent->GetParent();
if (!playerEntity) return;
auto* playerEntity = Game::entityManager->GetEntity(m_Owner);
if (!playerEntity) {
LOG("owner was null or didnt exist!");
return;
}

auto playerDestroyableComponent = playerEntity->GetComponent<DestroyableComponent>();
if (!playerDestroyableComponent) return;
Expand All @@ -878,12 +874,16 @@ void PetComponent::AddDrainImaginationTimer(Item* item, bool fromTaming) {
if (!fromTaming) playerDestroyableComponent->Imagine(-1);

// Set this to a variable so when this is called back from the player the timer doesn't fire off.
m_Parent->AddCallbackTimer(m_PetInfo.imaginationDrainRate, [playerDestroyableComponent, this, item]() {
if (!playerDestroyableComponent) {
LOG("No petComponent and/or no playerDestroyableComponent");
m_Parent->AddCallbackTimer(m_PetInfo.imaginationDrainRate, [this]() {
const auto* owner = Game::entityManager->GetEntity(m_Owner);
if (!owner) {
LOG("owner was null or didnt exist!");
return;
}

const auto* playerDestroyableComponent = owner->GetComponent<DestroyableComponent>();
if (!playerDestroyableComponent) return;

// If we are out of imagination despawn the pet.
if (playerDestroyableComponent->GetImagination() == 0) {
this->Deactivate();
Expand All @@ -893,15 +893,13 @@ void PetComponent::AddDrainImaginationTimer(Item* item, bool fromTaming) {
GameMessages::SendUseItemRequirementsResponse(playerEntity->GetObjectID(), playerEntity->GetSystemAddress(), eUseItemResponse::NoImaginationForPet);
}

this->AddDrainImaginationTimer(item);
this->AddDrainImaginationTimer();
});
}

void PetComponent::Deactivate() {
GameMessages::SendPlayFXEffect(m_Parent->GetObjectID(), -1, u"despawn", "", LWOOBJID_EMPTY, 1, 1, true);

GameMessages::SendMarkInventoryItemAsActive(m_Owner, false, eUnequippableActiveType::PET, m_ItemId, GetOwner()->GetSystemAddress());

activePets.erase(m_Owner);

m_Parent->Kill();
Expand All @@ -910,6 +908,8 @@ void PetComponent::Deactivate() {

if (owner == nullptr) return;

GameMessages::SendMarkInventoryItemAsActive(m_Owner, false, eUnequippableActiveType::PET, m_ItemId, owner->GetSystemAddress());

GameMessages::SendAddPetToPlayer(m_Owner, 0, u"", LWOOBJID_EMPTY, LOT_NULL, owner->GetSystemAddress());

GameMessages::SendRegisterPetID(m_Owner, LWOOBJID_EMPTY, owner->GetSystemAddress());
Expand Down Expand Up @@ -1034,6 +1034,7 @@ Entity* PetComponent::GetParentEntity() const {
}

PetComponent::~PetComponent() {
m_Owner = LWOOBJID_EMPTY;
}

void PetComponent::SetPetNameForModeration(const std::string& petName) {
Expand Down
2 changes: 1 addition & 1 deletion dGame/dComponents/PetComponent.h
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,7 @@ class PetComponent final : public Component
*
* @param item The item that represents this pet in the inventory.
*/
void AddDrainImaginationTimer(Item* item, bool fromTaming = false);
void AddDrainImaginationTimer(bool fromTaming = false);

private:

Expand Down

0 comments on commit bfe6900

Please sign in to comment.