mirror of
https://github.com/DarkflameUniverse/DarkflameServer.git
synced 2025-12-11 18:48:26 +00:00
Merge branch 'main' into raw-parsing-for-scene-data
This commit is contained in:
@@ -424,6 +424,7 @@ void Entity::Initialize() {
|
|||||||
comp->SetIsSmashable(destCompData[0].isSmashable);
|
comp->SetIsSmashable(destCompData[0].isSmashable);
|
||||||
|
|
||||||
comp->SetLootMatrixID(destCompData[0].LootMatrixIndex);
|
comp->SetLootMatrixID(destCompData[0].LootMatrixIndex);
|
||||||
|
comp->SetCurrencyIndex(destCompData[0].CurrencyIndex);
|
||||||
Loot::CacheMatrix(destCompData[0].LootMatrixIndex);
|
Loot::CacheMatrix(destCompData[0].LootMatrixIndex);
|
||||||
|
|
||||||
// Now get currency information
|
// Now get currency information
|
||||||
@@ -2252,6 +2253,7 @@ bool Entity::MsgRequestServerObjectInfo(GameMessages::GameMsg& msg) {
|
|||||||
response.Insert("objectID", std::to_string(m_ObjectID));
|
response.Insert("objectID", std::to_string(m_ObjectID));
|
||||||
response.Insert("serverInfo", true);
|
response.Insert("serverInfo", true);
|
||||||
GameMessages::GetObjectReportInfo info{};
|
GameMessages::GetObjectReportInfo info{};
|
||||||
|
info.clientID = requestInfo.clientId;
|
||||||
info.bVerbose = requestInfo.bVerbose;
|
info.bVerbose = requestInfo.bVerbose;
|
||||||
info.info = response.InsertArray("data");
|
info.info = response.InsertArray("data");
|
||||||
auto& objectInfo = info.info->PushDebug("Object Details");
|
auto& objectInfo = info.info->PushDebug("Object Details");
|
||||||
|
|||||||
@@ -3,6 +3,9 @@
|
|||||||
#include "Logger.h"
|
#include "Logger.h"
|
||||||
#include "Game.h"
|
#include "Game.h"
|
||||||
#include "dConfig.h"
|
#include "dConfig.h"
|
||||||
|
#include "CDLootMatrixTable.h"
|
||||||
|
#include "CDLootTableTable.h"
|
||||||
|
#include "CDRarityTableTable.h"
|
||||||
|
|
||||||
#include "Amf3.h"
|
#include "Amf3.h"
|
||||||
#include "AmfSerialize.h"
|
#include "AmfSerialize.h"
|
||||||
@@ -773,7 +776,15 @@ void DestroyableComponent::Smash(const LWOOBJID source, const eKillType killType
|
|||||||
|
|
||||||
coinsTotal -= coinsToLose;
|
coinsTotal -= coinsToLose;
|
||||||
|
|
||||||
Loot::DropLoot(m_Parent, m_Parent->GetObjectID(), -1, coinsToLose, coinsToLose);
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = m_Parent->GetObjectID();
|
||||||
|
lootMsg.ownerID = m_Parent->GetObjectID();
|
||||||
|
lootMsg.currency = coinsToLose;
|
||||||
|
lootMsg.spawnPos = m_Parent->GetPosition();
|
||||||
|
lootMsg.sourceID = source;
|
||||||
|
lootMsg.item = LOT_NULL;
|
||||||
|
lootMsg.Send();
|
||||||
|
lootMsg.Send(m_Parent->GetSystemAddress());
|
||||||
character->SetCoins(coinsTotal, eLootSourceType::PICKUP);
|
character->SetCoins(coinsTotal, eLootSourceType::PICKUP);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -974,7 +985,14 @@ void DestroyableComponent::DoHardcoreModeDrops(const LWOOBJID source) {
|
|||||||
for (const auto item : itemMap | std::views::values) {
|
for (const auto item : itemMap | std::views::values) {
|
||||||
// Don't drop excluded items or null ones
|
// Don't drop excluded items or null ones
|
||||||
if (!item || Game::entityManager->GetHardcoreExcludedItemDrops().contains(item->GetLot())) continue;
|
if (!item || Game::entityManager->GetHardcoreExcludedItemDrops().contains(item->GetLot())) continue;
|
||||||
GameMessages::SendDropClientLoot(m_Parent, source, item->GetLot(), 0, m_Parent->GetPosition(), item->GetCount());
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = m_Parent->GetObjectID();
|
||||||
|
lootMsg.ownerID = m_Parent->GetObjectID();
|
||||||
|
lootMsg.sourceID = m_Parent->GetObjectID();
|
||||||
|
lootMsg.item = item->GetLot();
|
||||||
|
lootMsg.count = 1;
|
||||||
|
lootMsg.spawnPos = m_Parent->GetPosition();
|
||||||
|
for (int i = 0; i < item->GetCount(); i++) Loot::DropItem(*m_Parent, lootMsg);
|
||||||
item->SetCount(0, false, false);
|
item->SetCount(0, false, false);
|
||||||
}
|
}
|
||||||
Game::entityManager->SerializeEntity(m_Parent);
|
Game::entityManager->SerializeEntity(m_Parent);
|
||||||
@@ -997,12 +1015,24 @@ void DestroyableComponent::DoHardcoreModeDrops(const LWOOBJID source) {
|
|||||||
|
|
||||||
//drop all coins:
|
//drop all coins:
|
||||||
constexpr auto MAX_TO_DROP_PER_GM = 100'000;
|
constexpr auto MAX_TO_DROP_PER_GM = 100'000;
|
||||||
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = m_Parent->GetObjectID();
|
||||||
|
lootMsg.ownerID = m_Parent->GetObjectID();
|
||||||
|
lootMsg.spawnPos = m_Parent->GetPosition();
|
||||||
|
lootMsg.sourceID = source;
|
||||||
|
lootMsg.item = LOT_NULL;
|
||||||
|
lootMsg.Send();
|
||||||
|
lootMsg.Send(m_Parent->GetSystemAddress());
|
||||||
while (coinsToDrop > MAX_TO_DROP_PER_GM) {
|
while (coinsToDrop > MAX_TO_DROP_PER_GM) {
|
||||||
LOG("Dropping 100,000, %llu left", coinsToDrop);
|
LOG("Dropping 100,000, %llu left", coinsToDrop);
|
||||||
GameMessages::SendDropClientLoot(m_Parent, source, LOT_NULL, MAX_TO_DROP_PER_GM, m_Parent->GetPosition());
|
lootMsg.currency = 100'000;
|
||||||
coinsToDrop -= MAX_TO_DROP_PER_GM;
|
lootMsg.Send();
|
||||||
|
lootMsg.Send(m_Parent->GetSystemAddress());
|
||||||
|
coinsToDrop -= 100'000;
|
||||||
}
|
}
|
||||||
GameMessages::SendDropClientLoot(m_Parent, source, LOT_NULL, coinsToDrop, m_Parent->GetPosition());
|
lootMsg.currency = coinsToDrop;
|
||||||
|
lootMsg.Send();
|
||||||
|
lootMsg.Send(m_Parent->GetSystemAddress());
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -1033,38 +1063,89 @@ void DestroyableComponent::DoHardcoreModeDrops(const LWOOBJID source) {
|
|||||||
|
|
||||||
bool DestroyableComponent::OnGetObjectReportInfo(GameMessages::GameMsg& msg) {
|
bool DestroyableComponent::OnGetObjectReportInfo(GameMessages::GameMsg& msg) {
|
||||||
auto& reportInfo = static_cast<GameMessages::GetObjectReportInfo&>(msg);
|
auto& reportInfo = static_cast<GameMessages::GetObjectReportInfo&>(msg);
|
||||||
|
|
||||||
auto& destroyableInfo = reportInfo.info->PushDebug("Destroyable");
|
auto& destroyableInfo = reportInfo.info->PushDebug("Destroyable");
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Health") = m_iHealth;
|
destroyableInfo.PushDebug<AMFIntValue>("DestructibleComponent DB Table Template ID") = m_ComponentID;
|
||||||
destroyableInfo.PushDebug<AMFDoubleValue>("Max Health") = m_fMaxHealth;
|
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Armor") = m_iArmor;
|
if (m_CurrencyIndex == -1) {
|
||||||
destroyableInfo.PushDebug<AMFDoubleValue>("Max Armor") = m_fMaxArmor;
|
destroyableInfo.PushDebug<AMFBoolValue>("Has Loot Currency") = false;
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Imagination") = m_iImagination;
|
} else {
|
||||||
destroyableInfo.PushDebug<AMFDoubleValue>("Max Imagination") = m_fMaxImagination;
|
destroyableInfo.PushDebug<AMFIntValue>("Loot Currency ID") = m_CurrencyIndex;
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Damage To Absorb") = m_DamageToAbsorb;
|
auto& detailedCoinInfo = destroyableInfo.PushDebug("Coin Info");
|
||||||
|
detailedCoinInfo.PushDebug<AMFIntValue>("Min Coins") = m_MinCoins;
|
||||||
|
detailedCoinInfo.PushDebug<AMFIntValue>("Max Coins") = m_MaxCoins;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (m_LootMatrixID == -1 || m_LootMatrixID == 0) {
|
||||||
|
destroyableInfo.PushDebug<AMFBoolValue>("Has Loot Matrix") = false;
|
||||||
|
} else {
|
||||||
|
auto& lootInfo = destroyableInfo.PushDebug("Loot Info");
|
||||||
|
lootInfo.PushDebug<AMFIntValue>("Loot Matrix ID") = m_LootMatrixID;
|
||||||
|
auto* const componentsRegistryTable = CDClientManager::GetTable<CDComponentsRegistryTable>();
|
||||||
|
auto* const itemComponentTable = CDClientManager::GetTable<CDItemComponentTable>();
|
||||||
|
auto* const lootMatrixTable = CDClientManager::GetTable<CDLootMatrixTable>();
|
||||||
|
auto* const lootTableTable = CDClientManager::GetTable<CDLootTableTable>();
|
||||||
|
auto* const rarityTableTable = CDClientManager::GetTable<CDRarityTableTable>();
|
||||||
|
|
||||||
|
const auto& matrix = lootMatrixTable->GetMatrix(m_LootMatrixID);
|
||||||
|
|
||||||
|
for (const auto& entry : matrix) {
|
||||||
|
auto& thisEntry = lootInfo.PushDebug("Loot table Index - " + std::to_string(entry.LootTableIndex));
|
||||||
|
thisEntry.PushDebug<AMFDoubleValue>("Percent chance to drop") = entry.percent * 100.0f;
|
||||||
|
thisEntry.PushDebug<AMFDoubleValue>("Minimum amount to drop") = entry.minToDrop;
|
||||||
|
thisEntry.PushDebug<AMFDoubleValue>("Maximum amount to drop") = entry.maxToDrop;
|
||||||
|
const auto& lootTable = lootTableTable->GetTable(entry.LootTableIndex);
|
||||||
|
const auto& rarityTable = rarityTableTable->GetRarityTable(entry.RarityTableIndex);
|
||||||
|
|
||||||
|
auto& thisRarity = thisEntry.PushDebug("Rarity");
|
||||||
|
for (const auto& rarity : rarityTable) {
|
||||||
|
thisRarity.PushDebug<AMFDoubleValue>("Rarity " + std::to_string(rarity.rarity)) = rarity.randmax;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto& thisItems = thisEntry.PushDebug("Drop(s) Info");
|
||||||
|
for (const auto& loot : lootTable) {
|
||||||
|
uint32_t itemComponentId = componentsRegistryTable->GetByIDAndType(loot.itemid, eReplicaComponentType::ITEM);
|
||||||
|
uint32_t rarity = itemComponentTable->GetItemComponentByID(itemComponentId).rarity;
|
||||||
|
auto title = "%[Objects_" + std::to_string(loot.itemid) + "_name] " + std::to_string(loot.itemid);
|
||||||
|
if (loot.MissionDrop) title += " - Mission Drop";
|
||||||
|
thisItems.PushDebug(title);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
auto* const entity = Game::entityManager->GetEntity(reportInfo.clientID);
|
||||||
|
destroyableInfo.PushDebug<AMFBoolValue>("Is on your team") = entity ? IsFriend(entity) : false;
|
||||||
|
auto& stats = destroyableInfo.PushDebug("Statistics");
|
||||||
|
stats.PushDebug<AMFIntValue>("Health") = m_iHealth;
|
||||||
|
stats.PushDebug<AMFDoubleValue>("Maximum Health") = m_fMaxHealth;
|
||||||
|
stats.PushDebug<AMFIntValue>("Armor") = m_iArmor;
|
||||||
|
stats.PushDebug<AMFDoubleValue>("Maximum Armor") = m_fMaxArmor;
|
||||||
|
stats.PushDebug<AMFIntValue>("Imagination") = m_iImagination;
|
||||||
|
stats.PushDebug<AMFDoubleValue>("Maximum Imagination") = m_fMaxImagination;
|
||||||
|
stats.PushDebug<AMFIntValue>("Damage Absorption Points") = m_DamageToAbsorb;
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Is GM Immune") = m_IsGMImmune;
|
destroyableInfo.PushDebug<AMFBoolValue>("Is GM Immune") = m_IsGMImmune;
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Is Shielded") = m_IsShielded;
|
destroyableInfo.PushDebug<AMFBoolValue>("Is Shielded") = m_IsShielded;
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Attacks To Block") = m_AttacksToBlock;
|
destroyableInfo.PushDebug<AMFIntValue>("Attacks To Block") = m_AttacksToBlock;
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Damage Reduction") = m_DamageReduction;
|
destroyableInfo.PushDebug<AMFIntValue>("Damage Reduction") = m_DamageReduction;
|
||||||
auto& factions = destroyableInfo.PushDebug("Factions");
|
std::stringstream factionsStream;
|
||||||
size_t i = 0;
|
|
||||||
for (const auto factionID : m_FactionIDs) {
|
for (const auto factionID : m_FactionIDs) {
|
||||||
factions.PushDebug<AMFStringValue>(std::to_string(i++) + " " + std::to_string(factionID)) = "";
|
factionsStream << factionID << " ";
|
||||||
}
|
}
|
||||||
auto& enemyFactions = destroyableInfo.PushDebug("Enemy Factions");
|
|
||||||
i = 0;
|
destroyableInfo.PushDebug<AMFStringValue>("Factions") = factionsStream.str();
|
||||||
|
|
||||||
|
factionsStream.str("");
|
||||||
for (const auto enemyFactionID : m_EnemyFactionIDs) {
|
for (const auto enemyFactionID : m_EnemyFactionIDs) {
|
||||||
enemyFactions.PushDebug<AMFStringValue>(std::to_string(i++) + " " + std::to_string(enemyFactionID)) = "";
|
factionsStream << enemyFactionID << " ";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
destroyableInfo.PushDebug<AMFStringValue>("Enemy Factions") = factionsStream.str();
|
||||||
|
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Is Smashable") = m_IsSmashable;
|
destroyableInfo.PushDebug<AMFBoolValue>("Is Smashable") = m_IsSmashable;
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Is Dead") = m_IsDead;
|
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Is Smashed") = m_IsSmashed;
|
destroyableInfo.PushDebug<AMFBoolValue>("Is Smashed") = m_IsSmashed;
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Is Module Assembly") = m_IsModuleAssembly;
|
destroyableInfo.PushDebug<AMFBoolValue>("Is Module Assembly") = m_IsModuleAssembly;
|
||||||
destroyableInfo.PushDebug<AMFDoubleValue>("Explode Factor") = m_ExplodeFactor;
|
destroyableInfo.PushDebug<AMFDoubleValue>("Explode Factor") = m_ExplodeFactor;
|
||||||
destroyableInfo.PushDebug<AMFBoolValue>("Has Threats") = m_HasThreats;
|
destroyableInfo.PushDebug<AMFBoolValue>("Has Threats") = m_HasThreats;
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Loot Matrix ID") = m_LootMatrixID;
|
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Min Coins") = m_MinCoins;
|
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Max Coins") = m_MaxCoins;
|
|
||||||
destroyableInfo.PushDebug<AMFStringValue>("Killer ID") = std::to_string(m_KillerID);
|
destroyableInfo.PushDebug<AMFStringValue>("Killer ID") = std::to_string(m_KillerID);
|
||||||
|
|
||||||
// "Scripts"; idk what to do about scripts yet
|
// "Scripts"; idk what to do about scripts yet
|
||||||
@@ -1079,7 +1160,25 @@ bool DestroyableComponent::OnGetObjectReportInfo(GameMessages::GameMsg& msg) {
|
|||||||
immuneCounts.PushDebug<AMFIntValue>("Quickbuild Interrupt") = m_ImmuneToQuickbuildInterruptCount;
|
immuneCounts.PushDebug<AMFIntValue>("Quickbuild Interrupt") = m_ImmuneToQuickbuildInterruptCount;
|
||||||
immuneCounts.PushDebug<AMFIntValue>("Pull To Point") = m_ImmuneToPullToPointCount;
|
immuneCounts.PushDebug<AMFIntValue>("Pull To Point") = m_ImmuneToPullToPointCount;
|
||||||
|
|
||||||
destroyableInfo.PushDebug<AMFIntValue>("Death Behavior") = m_DeathBehavior;
|
auto& deathInfo = destroyableInfo.PushDebug("Death Info");
|
||||||
|
deathInfo.PushDebug<AMFBoolValue>("Is Dead") = m_IsDead;
|
||||||
|
switch (m_DeathBehavior) {
|
||||||
|
case 0:
|
||||||
|
deathInfo.PushDebug<AMFStringValue>("Death Behavior") = "Fade";
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
deathInfo.PushDebug<AMFStringValue>("Death Behavior") = "Stay";
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
deathInfo.PushDebug<AMFStringValue>("Death Behavior") = "Immediate";
|
||||||
|
break;
|
||||||
|
case -1:
|
||||||
|
deathInfo.PushDebug<AMFStringValue>("Death Behavior") = "Invulnerable";
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
deathInfo.PushDebug<AMFStringValue>("Death Behavior") = "Other";
|
||||||
|
break;
|
||||||
|
}
|
||||||
destroyableInfo.PushDebug<AMFDoubleValue>("Damage Cooldown Timer") = m_DamageCooldownTimer;
|
destroyableInfo.PushDebug<AMFDoubleValue>("Damage Cooldown Timer") = m_DamageCooldownTimer;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -370,6 +370,8 @@ public:
|
|||||||
*/
|
*/
|
||||||
uint32_t GetLootMatrixID() const { return m_LootMatrixID; }
|
uint32_t GetLootMatrixID() const { return m_LootMatrixID; }
|
||||||
|
|
||||||
|
void SetCurrencyIndex(int32_t currencyIndex) { m_CurrencyIndex = currencyIndex; }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the ID of the entity that killed this entity, if any
|
* Returns the ID of the entity that killed this entity, if any
|
||||||
* @return the ID of the entity that killed this entity, if any
|
* @return the ID of the entity that killed this entity, if any
|
||||||
@@ -587,6 +589,9 @@ private:
|
|||||||
*/
|
*/
|
||||||
uint32_t m_LootMatrixID;
|
uint32_t m_LootMatrixID;
|
||||||
|
|
||||||
|
// The currency index to determine how much loot to drop
|
||||||
|
int32_t m_CurrencyIndex{ -1 };
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The min amount of coins that will drop when this entity is smashed
|
* The min amount of coins that will drop when this entity is smashed
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -282,7 +282,14 @@ void InventoryComponent::AddItem(
|
|||||||
|
|
||||||
case 1:
|
case 1:
|
||||||
for (size_t i = 0; i < size; i++) {
|
for (size_t i = 0; i < size; i++) {
|
||||||
GameMessages::SendDropClientLoot(this->m_Parent, this->m_Parent->GetObjectID(), lot, 0, this->m_Parent->GetPosition(), 1);
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = m_Parent->GetObjectID();
|
||||||
|
lootMsg.ownerID = m_Parent->GetObjectID();
|
||||||
|
lootMsg.sourceID = m_Parent->GetObjectID();
|
||||||
|
lootMsg.item = lot;
|
||||||
|
lootMsg.count = 1;
|
||||||
|
lootMsg.spawnPos = m_Parent->GetPosition();
|
||||||
|
Loot::DropItem(*m_Parent, lootMsg);
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|||||||
@@ -1067,44 +1067,6 @@ void GameMessages::SendSetNetworkScriptVar(Entity* entity, const SystemAddress&
|
|||||||
SEND_PACKET;
|
SEND_PACKET;
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameMessages::SendDropClientLoot(Entity* entity, const LWOOBJID& sourceID, LOT item, int currency, NiPoint3 spawnPos, int count) {
|
|
||||||
if (Game::config->GetValue("disable_drops") == "1" || !entity) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool bUsePosition = false;
|
|
||||||
NiPoint3 finalPosition;
|
|
||||||
LWOOBJID lootID = LWOOBJID_EMPTY;
|
|
||||||
LWOOBJID owner = entity->GetObjectID();
|
|
||||||
|
|
||||||
if (item != LOT_NULL && item != 0) {
|
|
||||||
lootID = ObjectIDManager::GenerateObjectID();
|
|
||||||
|
|
||||||
Loot::Info info;
|
|
||||||
info.id = lootID;
|
|
||||||
info.count = count;
|
|
||||||
info.lot = item;
|
|
||||||
entity->AddLootItem(info);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (item == LOT_NULL && currency != 0) {
|
|
||||||
entity->RegisterCoinDrop(currency);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (spawnPos != NiPoint3Constant::ZERO) {
|
|
||||||
bUsePosition = true;
|
|
||||||
|
|
||||||
//Calculate where the loot will go:
|
|
||||||
uint16_t degree = GeneralUtils::GenerateRandomNumber<uint16_t>(0, 360);
|
|
||||||
|
|
||||||
double rad = degree * 3.14 / 180;
|
|
||||||
double sin_v = sin(rad) * 4.2;
|
|
||||||
double cos_v = cos(rad) * 4.2;
|
|
||||||
|
|
||||||
finalPosition = NiPoint3(static_cast<float>(spawnPos.GetX() + sin_v), spawnPos.GetY(), static_cast<float>(spawnPos.GetZ() + cos_v));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GameMessages::SendSetPlayerControlScheme(Entity* entity, eControlScheme controlScheme) {
|
void GameMessages::SendSetPlayerControlScheme(Entity* entity, eControlScheme controlScheme) {
|
||||||
CBITSTREAM;
|
CBITSTREAM;
|
||||||
CMSGHEADER;
|
CMSGHEADER;
|
||||||
|
|||||||
@@ -153,7 +153,6 @@ namespace GameMessages {
|
|||||||
void SendStop2DAmbientSound(Entity* entity, bool force, std::string audioGUID, bool result = false);
|
void SendStop2DAmbientSound(Entity* entity, bool force, std::string audioGUID, bool result = false);
|
||||||
void SendPlay2DAmbientSound(Entity* entity, std::string audioGUID, bool result = false);
|
void SendPlay2DAmbientSound(Entity* entity, std::string audioGUID, bool result = false);
|
||||||
void SendSetNetworkScriptVar(Entity* entity, const SystemAddress& sysAddr, std::string data);
|
void SendSetNetworkScriptVar(Entity* entity, const SystemAddress& sysAddr, std::string data);
|
||||||
void SendDropClientLoot(Entity* entity, const LWOOBJID& sourceID, LOT item, int currency, NiPoint3 spawnPos = NiPoint3Constant::ZERO, int count = 1);
|
|
||||||
|
|
||||||
void SendSetPlayerControlScheme(Entity* entity, eControlScheme controlScheme);
|
void SendSetPlayerControlScheme(Entity* entity, eControlScheme controlScheme);
|
||||||
void SendPlayerReachedRespawnCheckpoint(Entity* entity, const NiPoint3& position, const NiQuaternion& rotation);
|
void SendPlayerReachedRespawnCheckpoint(Entity* entity, const NiPoint3& position, const NiQuaternion& rotation);
|
||||||
@@ -794,6 +793,7 @@ namespace GameMessages {
|
|||||||
AMFArrayValue* info{};
|
AMFArrayValue* info{};
|
||||||
AMFArrayValue* subCategory{};
|
AMFArrayValue* subCategory{};
|
||||||
bool bVerbose{};
|
bool bVerbose{};
|
||||||
|
LWOOBJID clientID{};
|
||||||
|
|
||||||
GetObjectReportInfo() : GameMsg(MessageType::Game::GET_OBJECT_REPORT_INFO, eGameMasterLevel::DEVELOPER) {}
|
GetObjectReportInfo() : GameMsg(MessageType::Game::GET_OBJECT_REPORT_INFO, eGameMasterLevel::DEVELOPER) {}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -13,6 +13,7 @@
|
|||||||
#include "dChatFilter.h"
|
#include "dChatFilter.h"
|
||||||
|
|
||||||
#include "DluAssert.h"
|
#include "DluAssert.h"
|
||||||
|
#include "Loot.h"
|
||||||
|
|
||||||
template <>
|
template <>
|
||||||
void Strip::HandleMsg(AddStripMessage& msg) {
|
void Strip::HandleMsg(AddStripMessage& msg) {
|
||||||
@@ -148,7 +149,14 @@ void Strip::Spawn(LOT lot, Entity& entity) {
|
|||||||
// Spawns a specific drop for all
|
// Spawns a specific drop for all
|
||||||
void Strip::SpawnDrop(LOT dropLOT, Entity& entity) {
|
void Strip::SpawnDrop(LOT dropLOT, Entity& entity) {
|
||||||
for (auto* const player : PlayerManager::GetAllPlayers()) {
|
for (auto* const player : PlayerManager::GetAllPlayers()) {
|
||||||
GameMessages::SendDropClientLoot(player, entity.GetObjectID(), dropLOT, 0, entity.GetPosition());
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = player->GetObjectID();
|
||||||
|
lootMsg.ownerID = player->GetObjectID();
|
||||||
|
lootMsg.sourceID = entity.GetObjectID();
|
||||||
|
lootMsg.item = dropLOT;
|
||||||
|
lootMsg.count = 1;
|
||||||
|
lootMsg.spawnPos = entity.GetPosition();
|
||||||
|
Loot::DropItem(*player, lootMsg);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -93,6 +93,7 @@ std::map<LOT, LootDropInfo> RollLootMatrix(uint32_t matrixIndex) {
|
|||||||
|
|
||||||
// Generates a 'random' final position for the loot drop based on its input spawn position.
|
// Generates a 'random' final position for the loot drop based on its input spawn position.
|
||||||
void CalcFinalDropPos(GameMessages::DropClientLoot& lootMsg) {
|
void CalcFinalDropPos(GameMessages::DropClientLoot& lootMsg) {
|
||||||
|
if (lootMsg.spawnPos != NiPoint3Constant::ZERO) {
|
||||||
lootMsg.bUsePosition = true;
|
lootMsg.bUsePosition = true;
|
||||||
|
|
||||||
//Calculate where the loot will go:
|
//Calculate where the loot will go:
|
||||||
@@ -104,6 +105,7 @@ void CalcFinalDropPos(GameMessages::DropClientLoot& lootMsg) {
|
|||||||
|
|
||||||
const auto [x, y, z] = lootMsg.spawnPos;
|
const auto [x, y, z] = lootMsg.spawnPos;
|
||||||
lootMsg.finalPosition = NiPoint3(static_cast<float>(x + sin_v), y, static_cast<float>(z + cos_v));
|
lootMsg.finalPosition = NiPoint3(static_cast<float>(x + sin_v), y, static_cast<float>(z + cos_v));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Visually drop the loot to all team members, though only the lootMsg.ownerID can pick it up
|
// Visually drop the loot to all team members, though only the lootMsg.ownerID can pick it up
|
||||||
|
|||||||
@@ -7,6 +7,7 @@
|
|||||||
#include "eReplicaComponentType.h"
|
#include "eReplicaComponentType.h"
|
||||||
#include "RenderComponent.h"
|
#include "RenderComponent.h"
|
||||||
#include "eTerminateType.h"
|
#include "eTerminateType.h"
|
||||||
|
#include "Loot.h"
|
||||||
|
|
||||||
void GfTikiTorch::OnStartup(Entity* self) {
|
void GfTikiTorch::OnStartup(Entity* self) {
|
||||||
LightTorch(self);
|
LightTorch(self);
|
||||||
@@ -22,7 +23,14 @@ void GfTikiTorch::OnUse(Entity* self, Entity* killer) {
|
|||||||
self->SetI64(u"userID", killer->GetObjectID());
|
self->SetI64(u"userID", killer->GetObjectID());
|
||||||
|
|
||||||
for (int i = 0; i < m_numspawn; i++) {
|
for (int i = 0; i < m_numspawn; i++) {
|
||||||
GameMessages::SendDropClientLoot(killer, self->GetObjectID(), 935, 0, self->GetPosition());
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = killer->GetObjectID();
|
||||||
|
lootMsg.ownerID = killer->GetObjectID();
|
||||||
|
lootMsg.sourceID = self->GetObjectID();
|
||||||
|
lootMsg.item = 935;
|
||||||
|
lootMsg.count = 1;
|
||||||
|
lootMsg.spawnPos = self->GetPosition();
|
||||||
|
Loot::DropItem(*killer, lootMsg);
|
||||||
}
|
}
|
||||||
|
|
||||||
self->AddTimer("InteractionCooldown", 4);
|
self->AddTimer("InteractionCooldown", 4);
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
#include "GameMessages.h"
|
#include "GameMessages.h"
|
||||||
#include "SkillComponent.h"
|
#include "SkillComponent.h"
|
||||||
#include "TeamManager.h"
|
#include "TeamManager.h"
|
||||||
|
#include "Loot.h"
|
||||||
|
|
||||||
void AgSurvivalBuffStation::OnQuickBuildComplete(Entity* self, Entity* target) {
|
void AgSurvivalBuffStation::OnQuickBuildComplete(Entity* self, Entity* target) {
|
||||||
auto destroyableComponent = self->GetComponent<DestroyableComponent>();
|
auto destroyableComponent = self->GetComponent<DestroyableComponent>();
|
||||||
@@ -55,7 +56,14 @@ void AgSurvivalBuffStation::OnTimerDone(Entity* self, std::string timerName) {
|
|||||||
for (auto memberID : team) {
|
for (auto memberID : team) {
|
||||||
auto member = Game::entityManager->GetEntity(memberID);
|
auto member = Game::entityManager->GetEntity(memberID);
|
||||||
if (member != nullptr && !member->GetIsDead()) {
|
if (member != nullptr && !member->GetIsDead()) {
|
||||||
GameMessages::SendDropClientLoot(member, self->GetObjectID(), powerupToDrop, 0, self->GetPosition());
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = member->GetObjectID();
|
||||||
|
lootMsg.ownerID = member->GetObjectID();
|
||||||
|
lootMsg.sourceID = self->GetObjectID();
|
||||||
|
lootMsg.item = powerupToDrop;
|
||||||
|
lootMsg.count = 1;
|
||||||
|
lootMsg.spawnPos = self->GetPosition();
|
||||||
|
Loot::DropItem(*member, lootMsg, true, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,6 +5,7 @@
|
|||||||
#include "EntityInfo.h"
|
#include "EntityInfo.h"
|
||||||
#include "DestroyableComponent.h"
|
#include "DestroyableComponent.h"
|
||||||
#include "eReplicaComponentType.h"
|
#include "eReplicaComponentType.h"
|
||||||
|
#include "Loot.h"
|
||||||
|
|
||||||
void AgImagSmashable::OnDie(Entity* self, Entity* killer) {
|
void AgImagSmashable::OnDie(Entity* self, Entity* killer) {
|
||||||
bool maxImagGreaterThanZero = false;
|
bool maxImagGreaterThanZero = false;
|
||||||
@@ -18,7 +19,14 @@ void AgImagSmashable::OnDie(Entity* self, Entity* killer) {
|
|||||||
if (maxImagGreaterThanZero) {
|
if (maxImagGreaterThanZero) {
|
||||||
int amount = GeneralUtils::GenerateRandomNumber<int>(0, 3);
|
int amount = GeneralUtils::GenerateRandomNumber<int>(0, 3);
|
||||||
for (int i = 0; i < amount; ++i) {
|
for (int i = 0; i < amount; ++i) {
|
||||||
GameMessages::SendDropClientLoot(killer, self->GetObjectID(), 935, 0, self->GetPosition());
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
|
lootMsg.target = killer->GetObjectID();
|
||||||
|
lootMsg.ownerID = killer->GetObjectID();
|
||||||
|
lootMsg.sourceID = self->GetObjectID();
|
||||||
|
lootMsg.item = 935;
|
||||||
|
lootMsg.count = 1;
|
||||||
|
lootMsg.spawnPos = self->GetPosition();
|
||||||
|
Loot::DropItem(*killer, lootMsg);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
#include "NsQbImaginationStatue.h"
|
#include "NsQbImaginationStatue.h"
|
||||||
#include "EntityManager.h"
|
#include "EntityManager.h"
|
||||||
#include "GameMessages.h"
|
#include "GameMessages.h"
|
||||||
|
#include "Loot.h"
|
||||||
|
|
||||||
void NsQbImaginationStatue::OnStartup(Entity* self) {
|
void NsQbImaginationStatue::OnStartup(Entity* self) {
|
||||||
|
|
||||||
@@ -35,6 +36,12 @@ void NsQbImaginationStatue::SpawnLoot(Entity* self) {
|
|||||||
|
|
||||||
if (player == nullptr) return;
|
if (player == nullptr) return;
|
||||||
|
|
||||||
GameMessages::SendDropClientLoot(player, self->GetObjectID(), 935, 0);
|
GameMessages::DropClientLoot lootMsg{};
|
||||||
GameMessages::SendDropClientLoot(player, self->GetObjectID(), 935, 0);
|
lootMsg.target = player->GetObjectID();
|
||||||
|
lootMsg.ownerID = player->GetObjectID();
|
||||||
|
lootMsg.sourceID = self->GetObjectID();
|
||||||
|
lootMsg.item = 935;
|
||||||
|
lootMsg.count = 1;
|
||||||
|
Loot::DropItem(*player, lootMsg);
|
||||||
|
Loot::DropItem(*player, lootMsg);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user