mirror of
https://github.com/DarkflameUniverse/DarkflameServer.git
synced 2024-11-26 23:47:21 +00:00
Fully re-implemented initialize
This commit is contained in:
parent
fc719cbb0a
commit
36c44ecc83
@ -56,7 +56,10 @@ const uint32_t LWOCLONEID_INVALID = -1; //!< Invalid LWOCLONEID
|
|||||||
const uint16_t LWOINSTANCEID_INVALID = -1; //!< Invalid LWOINSTANCEID
|
const uint16_t LWOINSTANCEID_INVALID = -1; //!< Invalid LWOINSTANCEID
|
||||||
const uint16_t LWOMAPID_INVALID = -1; //!< Invalid LWOMAPID
|
const uint16_t LWOMAPID_INVALID = -1; //!< Invalid LWOMAPID
|
||||||
const uint64_t LWOZONEID_INVALID = 0; //!< Invalid LWOZONEID
|
const uint64_t LWOZONEID_INVALID = 0; //!< Invalid LWOZONEID
|
||||||
const uint32_t ZONE_CONTROL_LOT = 2365;
|
const LOT LOT_ZONE_CONTROL = 2365;
|
||||||
|
const LOT LOT_3D_AMBIENT_SOUND = 6368;
|
||||||
|
const LOT LOT_MODEL_IN_WORLD = 14;
|
||||||
|
|
||||||
|
|
||||||
const float PI = 3.14159f;
|
const float PI = 3.14159f;
|
||||||
|
|
||||||
|
112
dGame/Entity.cpp
112
dGame/Entity.cpp
@ -205,6 +205,29 @@ void Entity::ApplyComponentConfig(TemplateComponents& components) const {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Entity::AddPathComponent(TemplateComponents& components) const {
|
||||||
|
const Path* path = dZoneManager::Instance()->GetZone()->GetPath(GetVarAsString(u"attached_path"));
|
||||||
|
//Check to see if we have an attached path and add the appropiate component to handle it:
|
||||||
|
if (path) {
|
||||||
|
// if we have a moving platform path, then we need a moving platform component
|
||||||
|
if (path->pathType == PathType::MovingPlatform) {
|
||||||
|
bool hasMovingPlatform = std::count_if(components.begin(), components.end(), [](const auto& componentCandidate) {
|
||||||
|
return componentCandidate.first == eReplicaComponentType::MOVING_PLATFORM;
|
||||||
|
}) > 0;
|
||||||
|
if (!hasMovingPlatform) components.emplace_back(eReplicaComponentType::MOVING_PLATFORM, 0U);
|
||||||
|
} else if (path->pathType == PathType::Movement) {
|
||||||
|
bool hasMovementAi = std::count_if(components.begin(), components.end(), [](const auto& componentCandidate) {
|
||||||
|
return componentCandidate.first == eReplicaComponentType::MOVEMENT_AI;
|
||||||
|
}) > 0;
|
||||||
|
if (!hasMovementAi) {
|
||||||
|
components.emplace_back(eReplicaComponentType::MOVEMENT_AI, 0U);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
Game::logger->Log("Entity", "Unsupported path type %i provided for lot %i.", path->pathType, GetLOT());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Entity::Initialize() {
|
void Entity::Initialize() {
|
||||||
// A few edge cases to tackle first
|
// A few edge cases to tackle first
|
||||||
const auto triggerInfo = GetVarAsString(u"trigger_id");
|
const auto triggerInfo = GetVarAsString(u"trigger_id");
|
||||||
@ -222,11 +245,11 @@ void Entity::Initialize() {
|
|||||||
TemplateComponents components = componentsRegistry->GetTemplateComponents(m_TemplateID);
|
TemplateComponents components = componentsRegistry->GetTemplateComponents(m_TemplateID);
|
||||||
ApplyComponentWhitelist(components);
|
ApplyComponentWhitelist(components);
|
||||||
ApplyComponentBlacklist(components);
|
ApplyComponentBlacklist(components);
|
||||||
|
AddPathComponent(components);
|
||||||
// Brick-by-Brick models use custom physics depending on _something_ but the client uses 4246 as the simple
|
// Brick-by-Brick models use custom physics depending on _something_ but the client uses 4246 as the simple
|
||||||
// physics component id and 4247 for phantom physics. We'll just use the simple physics component for now
|
// physics component id and 4247 for phantom physics. We'll just use the simple physics component for now
|
||||||
// since we dont know what the phantom physics are for at the moment.
|
// since we dont know what the phantom physics are for at the moment.
|
||||||
if (GetLOT() == 14) components.emplace_back(eReplicaComponentType::SIMPLE_PHYSICS, 4246U);
|
if (GetLOT() == LOT_MODEL_IN_WORLD) components.emplace_back(eReplicaComponentType::SIMPLE_PHYSICS, 4246U);
|
||||||
|
|
||||||
for (const auto& [componentTemplate, componentId] : components) {
|
for (const auto& [componentTemplate, componentId] : components) {
|
||||||
switch (componentTemplate) {
|
switch (componentTemplate) {
|
||||||
case eReplicaComponentType::CONTROLLABLE_PHYSICS:
|
case eReplicaComponentType::CONTROLLABLE_PHYSICS:
|
||||||
@ -247,7 +270,7 @@ void Entity::Initialize() {
|
|||||||
break;
|
break;
|
||||||
case eReplicaComponentType::SCRIPT: {
|
case eReplicaComponentType::SCRIPT: {
|
||||||
AddComponent<ScriptComponent>(ScriptComponent::GetScriptName(this, componentId));
|
AddComponent<ScriptComponent>(ScriptComponent::GetScriptName(this, componentId));
|
||||||
if (m_TemplateID == ZONE_CONTROL_LOT) {
|
if (m_TemplateID == LOT_ZONE_CONTROL) {
|
||||||
const auto zoneScript = ScriptComponent::GetZoneScriptName(componentId);
|
const auto zoneScript = ScriptComponent::GetZoneScriptName(componentId);
|
||||||
if (!zoneScript.empty()) AddComponent<ScriptComponent>(zoneScript);
|
if (!zoneScript.empty()) AddComponent<ScriptComponent>(zoneScript);
|
||||||
}
|
}
|
||||||
@ -257,7 +280,7 @@ void Entity::Initialize() {
|
|||||||
AddComponent<BouncerComponent>();
|
AddComponent<BouncerComponent>();
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::DESTROYABLE:
|
case eReplicaComponentType::DESTROYABLE:
|
||||||
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) AddComponent<DestroyableComponent>();
|
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) AddComponent<DestroyableComponent>(componentId);
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::SKILL:
|
case eReplicaComponentType::SKILL:
|
||||||
AddComponent<SkillComponent>();
|
AddComponent<SkillComponent>();
|
||||||
@ -279,13 +302,14 @@ void Entity::Initialize() {
|
|||||||
break;
|
break;
|
||||||
case eReplicaComponentType::COLLECTIBLE:
|
case eReplicaComponentType::COLLECTIBLE:
|
||||||
AddComponent<CollectibleComponent>();
|
AddComponent<CollectibleComponent>();
|
||||||
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) AddComponent<DestroyableComponent>();
|
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) AddComponent<DestroyableComponent>(componentId);
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::MOVING_PLATFORM:
|
case eReplicaComponentType::MOVING_PLATFORM:
|
||||||
AddComponent<MovingPlatformComponent>(GetVarAsString(u"attached_path"));
|
AddComponent<MovingPlatformComponent>(GetVarAsString(u"attached_path"));
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::PET:
|
case eReplicaComponentType::PET:
|
||||||
AddComponent<PetComponent>(componentId);
|
AddComponent<PetComponent>(componentId);
|
||||||
|
AddComponent<MovementAIComponent>();
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::HAVOK_VEHICLE_PHYSICS: {
|
case eReplicaComponentType::HAVOK_VEHICLE_PHYSICS: {
|
||||||
auto* havokVehiclePhysicsComponent = AddComponent<HavokVehiclePhysicsComponent>();
|
auto* havokVehiclePhysicsComponent = AddComponent<HavokVehiclePhysicsComponent>();
|
||||||
@ -295,6 +319,9 @@ void Entity::Initialize() {
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case eReplicaComponentType::MOVEMENT_AI:
|
||||||
|
AddComponent<MovementAIComponent>();
|
||||||
|
break;
|
||||||
case eReplicaComponentType::PROPERTY:
|
case eReplicaComponentType::PROPERTY:
|
||||||
AddComponent<PropertyComponent>();
|
AddComponent<PropertyComponent>();
|
||||||
break;
|
break;
|
||||||
@ -309,7 +336,7 @@ void Entity::Initialize() {
|
|||||||
case eReplicaComponentType::MODEL_BEHAVIOR: {
|
case eReplicaComponentType::MODEL_BEHAVIOR: {
|
||||||
AddComponent<ModelBehaviorComponent>();
|
AddComponent<ModelBehaviorComponent>();
|
||||||
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) {
|
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) {
|
||||||
auto* destroyableComponent = AddComponent<DestroyableComponent>();
|
auto* destroyableComponent = AddComponent<DestroyableComponent>(componentId);
|
||||||
if (destroyableComponent) {
|
if (destroyableComponent) {
|
||||||
destroyableComponent->SetHealth(1);
|
destroyableComponent->SetHealth(1);
|
||||||
destroyableComponent->SetMaxHealth(1.0f);
|
destroyableComponent->SetMaxHealth(1.0f);
|
||||||
@ -327,7 +354,7 @@ void Entity::Initialize() {
|
|||||||
break;
|
break;
|
||||||
case eReplicaComponentType::QUICK_BUILD:
|
case eReplicaComponentType::QUICK_BUILD:
|
||||||
AddComponent<QuickBuildComponent>(componentId);
|
AddComponent<QuickBuildComponent>(componentId);
|
||||||
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) AddComponent<DestroyableComponent>();
|
if (!HasComponent(eReplicaComponentType::DESTROYABLE)) AddComponent<DestroyableComponent>(componentId);
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::SWITCH:
|
case eReplicaComponentType::SWITCH:
|
||||||
AddComponent<SwitchComponent>();
|
AddComponent<SwitchComponent>();
|
||||||
@ -335,9 +362,22 @@ void Entity::Initialize() {
|
|||||||
case eReplicaComponentType::MINIGAME_CONTROL:
|
case eReplicaComponentType::MINIGAME_CONTROL:
|
||||||
AddComponent<MinigameControlComponent>();
|
AddComponent<MinigameControlComponent>();
|
||||||
break;
|
break;
|
||||||
case eReplicaComponentType::BASE_COMBAT_AI:
|
case eReplicaComponentType::BASE_COMBAT_AI: {
|
||||||
AddComponent<BaseCombatAIComponent>(componentId);
|
auto* baseCombatAiComponent = AddComponent<BaseCombatAIComponent>(componentId);
|
||||||
|
if (baseCombatAiComponent && baseCombatAiComponent->GetTetherSpeed() > 0.0f) {
|
||||||
|
auto* movementAiComponent = AddComponent<MovementAIComponent>();
|
||||||
|
if (!movementAiComponent) break;
|
||||||
|
MovementAIInfo movementAiInfo{};
|
||||||
|
movementAiInfo.movementType = "";
|
||||||
|
movementAiInfo.wanderChance = 0;
|
||||||
|
movementAiInfo.wanderRadius = 16;
|
||||||
|
movementAiInfo.wanderSpeed = 2.5f;
|
||||||
|
movementAiInfo.wanderDelayMax = 5;
|
||||||
|
movementAiInfo.wanderDelayMin = 2;
|
||||||
|
movementAiComponent->SetMoveInfo(movementAiInfo);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
case eReplicaComponentType::MODULE_ASSEMBLY:
|
case eReplicaComponentType::MODULE_ASSEMBLY:
|
||||||
AddComponent<ModuleAssemblyComponent>();
|
AddComponent<ModuleAssemblyComponent>();
|
||||||
break;
|
break;
|
||||||
@ -362,6 +402,9 @@ void Entity::Initialize() {
|
|||||||
case eReplicaComponentType::SOUND_TRIGGER:
|
case eReplicaComponentType::SOUND_TRIGGER:
|
||||||
AddComponent<SoundTriggerComponent>();
|
AddComponent<SoundTriggerComponent>();
|
||||||
break;
|
break;
|
||||||
|
case eReplicaComponentType::PROXIMITY_MONITOR:
|
||||||
|
AddComponent<ProximityMonitorComponent>();
|
||||||
|
break;
|
||||||
case eReplicaComponentType::MULTI_ZONE_ENTRANCE:
|
case eReplicaComponentType::MULTI_ZONE_ENTRANCE:
|
||||||
AddComponent<MultiZoneEntranceComponent>();
|
AddComponent<MultiZoneEntranceComponent>();
|
||||||
break;
|
break;
|
||||||
@ -390,7 +433,6 @@ void Entity::Initialize() {
|
|||||||
case eReplicaComponentType::PLATFORM_BOUNDARY:
|
case eReplicaComponentType::PLATFORM_BOUNDARY:
|
||||||
case eReplicaComponentType::MODULE:
|
case eReplicaComponentType::MODULE:
|
||||||
case eReplicaComponentType::JETPACKPAD:
|
case eReplicaComponentType::JETPACKPAD:
|
||||||
case eReplicaComponentType::MOVEMENT_AI:
|
|
||||||
case eReplicaComponentType::EXHIBIT:
|
case eReplicaComponentType::EXHIBIT:
|
||||||
case eReplicaComponentType::OVERHEAD_ICON:
|
case eReplicaComponentType::OVERHEAD_ICON:
|
||||||
case eReplicaComponentType::PET_CONTROL:
|
case eReplicaComponentType::PET_CONTROL:
|
||||||
@ -419,7 +461,6 @@ void Entity::Initialize() {
|
|||||||
case eReplicaComponentType::DROPPED_LOOT:
|
case eReplicaComponentType::DROPPED_LOOT:
|
||||||
case eReplicaComponentType::FACTION_TRIGGER:
|
case eReplicaComponentType::FACTION_TRIGGER:
|
||||||
case eReplicaComponentType::BBB:
|
case eReplicaComponentType::BBB:
|
||||||
case eReplicaComponentType::PROXIMITY_MONITOR:
|
|
||||||
case eReplicaComponentType::RACING_SOUND_TRIGGER:
|
case eReplicaComponentType::RACING_SOUND_TRIGGER:
|
||||||
case eReplicaComponentType::CHAT_BUBBLE:
|
case eReplicaComponentType::CHAT_BUBBLE:
|
||||||
case eReplicaComponentType::FRIENDS_LIST:
|
case eReplicaComponentType::FRIENDS_LIST:
|
||||||
@ -460,6 +501,13 @@ void Entity::Initialize() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
AddCallbackTimer(0.0f, [this]() {
|
||||||
|
auto scripts = CppScripts::GetEntityScripts(this);
|
||||||
|
std::for_each(scripts.begin(), scripts.end(), [this](const auto& script) {
|
||||||
|
script->OnStartup(this);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
std::for_each(m_Components.begin(), m_Components.end(), [this](auto& component) {
|
std::for_each(m_Components.begin(), m_Components.end(), [this](auto& component) {
|
||||||
component.second->LoadTemplateData();
|
component.second->LoadTemplateData();
|
||||||
});
|
});
|
||||||
@ -471,11 +519,47 @@ void Entity::Initialize() {
|
|||||||
std::for_each(m_Components.begin(), m_Components.end(), [this](auto& component) {
|
std::for_each(m_Components.begin(), m_Components.end(), [this](auto& component) {
|
||||||
component.second->Startup();
|
component.second->Startup();
|
||||||
});
|
});
|
||||||
if (!IsPlayer()) return; // No save data to load for non players
|
// No save data to load for non players
|
||||||
|
if (!IsPlayer()) std::for_each(m_Components.begin(), m_Components.end(), [this](auto& component) {
|
||||||
std::for_each(m_Components.begin(), m_Components.end(), [this](auto& component) {
|
|
||||||
component.second->LoadFromXml(m_Character->GetXMLDoc());
|
component.second->LoadFromXml(m_Character->GetXMLDoc());
|
||||||
});
|
});
|
||||||
|
|
||||||
|
TriggerEvent(eTriggerEventType::CREATE, this);
|
||||||
|
IsGhosted();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Entity::IsGhosted() {
|
||||||
|
if (!m_Character && EntityManager::Instance()->GetGhostingEnabled()) {
|
||||||
|
// Don't ghost what is likely large scene elements
|
||||||
|
if (HasComponent(eReplicaComponentType::SIMPLE_PHYSICS) && HasComponent(eReplicaComponentType::RENDER) && (m_Components.size() == 2 || (HasComponent(eReplicaComponentType::TRIGGER) && m_Components.size() == 3))) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Filter for ghosting candidates.
|
||||||
|
*
|
||||||
|
* Don't ghost moving platforms, until we've got proper syncing for those.
|
||||||
|
* Don't ghost big phantom physics triggers, as putting those to sleep might prevent interactions.
|
||||||
|
* Don't ghost property related objects, as the client expects those to always be loaded.
|
||||||
|
*/
|
||||||
|
if (
|
||||||
|
!EntityManager::IsExcludedFromGhosting(GetLOT()) &&
|
||||||
|
!HasComponent(eReplicaComponentType::SCRIPTED_ACTIVITY) &&
|
||||||
|
!HasComponent(eReplicaComponentType::MOVING_PLATFORM) &&
|
||||||
|
!HasComponent(eReplicaComponentType::PHANTOM_PHYSICS) &&
|
||||||
|
!HasComponent(eReplicaComponentType::PROPERTY) &&
|
||||||
|
!HasComponent(eReplicaComponentType::RACING_CONTROL) &&
|
||||||
|
!HasComponent(eReplicaComponentType::VEHICLE_PHYSICS)
|
||||||
|
) {
|
||||||
|
m_IsGhostingCandidate = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (GetLOT() == LOT_3D_AMBIENT_SOUND) m_IsGhostingCandidate = true;
|
||||||
|
|
||||||
|
// Special case for collectibles in Ninjago
|
||||||
|
if (HasComponent(eReplicaComponentType::COLLECTIBLE) && Game::server->GetZoneID() == 2000) {
|
||||||
|
m_IsGhostingCandidate = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Entity::operator==(const Entity& other) const {
|
bool Entity::operator==(const Entity& other) const {
|
||||||
|
@ -66,6 +66,11 @@ public:
|
|||||||
|
|
||||||
// For adding and removing components based on LDF keys
|
// For adding and removing components based on LDF keys
|
||||||
void ApplyComponentConfig(TemplateComponents& components) const;
|
void ApplyComponentConfig(TemplateComponents& components) const;
|
||||||
|
|
||||||
|
// Paths have several components they could add. This function will add them.
|
||||||
|
void AddPathComponent(TemplateComponents& components) const;
|
||||||
|
|
||||||
|
void IsGhosted();
|
||||||
virtual void Initialize();
|
virtual void Initialize();
|
||||||
|
|
||||||
bool operator==(const Entity& other) const;
|
bool operator==(const Entity& other) const;
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
Entity::Initialize() {
|
// Entity::Initialize() {
|
||||||
/**
|
/**
|
||||||
* Setup trigger
|
* Setup trigger
|
||||||
*/
|
*/
|
||||||
@ -204,75 +204,75 @@ Entity::Initialize() {
|
|||||||
|
|
||||||
// if (destroyableComponentID > 0 || collectibleComponentID > 0) {
|
// if (destroyableComponentID > 0 || collectibleComponentID > 0) {
|
||||||
// DestroyableComponent* comp = new DestroyableComponent(this);
|
// DestroyableComponent* comp = new DestroyableComponent(this);
|
||||||
if (m_Character) {
|
// if (m_Character) {
|
||||||
comp->LoadFromXml(m_Character->GetXMLDoc());
|
// comp->LoadFromXml(m_Character->GetXMLDoc());
|
||||||
} else {
|
// } else {
|
||||||
if (componentID > 0) {
|
// if (componentID > 0) {
|
||||||
// std::vector<CDDestructibleComponent> destCompData = destCompTable->Query([=](CDDestructibleComponent entry) { return (entry.id == componentID); });
|
// // std::vector<CDDestructibleComponent> destCompData = destCompTable->Query([=](CDDestructibleComponent entry) { return (entry.id == componentID); });
|
||||||
|
|
||||||
if (destCompData.size() > 0) {
|
// if (destCompData.size() > 0) {
|
||||||
if (HasComponent(eReplicaComponentType::RACING_STATS)) {
|
// if (HasComponent(eReplicaComponentType::RACING_STATS)) {
|
||||||
destCompData[0].imagination = 60;
|
// destCompData[0].imagination = 60;
|
||||||
}
|
// }
|
||||||
|
|
||||||
comp->SetHealth(destCompData[0].life);
|
// comp->SetHealth(destCompData[0].life);
|
||||||
comp->SetImagination(destCompData[0].imagination);
|
// comp->SetImagination(destCompData[0].imagination);
|
||||||
comp->SetArmor(destCompData[0].armor);
|
// comp->SetArmor(destCompData[0].armor);
|
||||||
|
|
||||||
comp->SetMaxHealth(destCompData[0].life);
|
// comp->SetMaxHealth(destCompData[0].life);
|
||||||
comp->SetMaxImagination(destCompData[0].imagination);
|
// comp->SetMaxImagination(destCompData[0].imagination);
|
||||||
comp->SetMaxArmor(destCompData[0].armor);
|
// comp->SetMaxArmor(destCompData[0].armor);
|
||||||
|
|
||||||
comp->SetIsSmashable(destCompData[0].isSmashable);
|
// comp->SetIsSmashable(destCompData[0].isSmashable);
|
||||||
|
|
||||||
comp->SetLootMatrixID(destCompData[0].LootMatrixIndex);
|
// comp->SetLootMatrixID(destCompData[0].LootMatrixIndex);
|
||||||
|
|
||||||
// Now get currency information
|
// // Now get currency information
|
||||||
uint32_t npcMinLevel = destCompData[0].level;
|
// uint32_t npcMinLevel = destCompData[0].level;
|
||||||
uint32_t currencyIndex = destCompData[0].CurrencyIndex;
|
// uint32_t currencyIndex = destCompData[0].CurrencyIndex;
|
||||||
|
|
||||||
CDCurrencyTableTable* currencyTable = CDClientManager::Instance().GetTable<CDCurrencyTableTable>();
|
// CDCurrencyTableTable* currencyTable = CDClientManager::Instance().GetTable<CDCurrencyTableTable>();
|
||||||
std::vector<CDCurrencyTable> currencyValues = currencyTable->Query([=](CDCurrencyTable entry) { return (entry.currencyIndex == currencyIndex && entry.npcminlevel == npcMinLevel); });
|
// std::vector<CDCurrencyTable> currencyValues = currencyTable->Query([=](CDCurrencyTable entry) { return (entry.currencyIndex == currencyIndex && entry.npcminlevel == npcMinLevel); });
|
||||||
|
|
||||||
if (currencyValues.size() > 0) {
|
// if (currencyValues.size() > 0) {
|
||||||
// Set the coins
|
// // Set the coins
|
||||||
comp->SetMinCoins(currencyValues[0].minvalue);
|
// comp->SetMinCoins(currencyValues[0].minvalue);
|
||||||
comp->SetMaxCoins(currencyValues[0].maxvalue);
|
// comp->SetMaxCoins(currencyValues[0].maxvalue);
|
||||||
}
|
// }
|
||||||
|
|
||||||
// extraInfo overrides
|
// // extraInfo overrides
|
||||||
comp->SetIsSmashable(GetVarAs<int32_t>(u"is_smashable") != 0);
|
// // comp->SetIsSmashable(GetVarAs<int32_t>(u"is_smashable") != 0);
|
||||||
}
|
// }
|
||||||
} else {
|
// } else {
|
||||||
comp->SetHealth(1);
|
// comp->SetHealth(1);
|
||||||
comp->SetArmor(0);
|
// comp->SetArmor(0);
|
||||||
|
|
||||||
comp->SetMaxHealth(1);
|
// comp->SetMaxHealth(1);
|
||||||
comp->SetMaxArmor(0);
|
// comp->SetMaxArmor(0);
|
||||||
|
|
||||||
comp->SetIsSmashable(true);
|
// comp->SetIsSmashable(true);
|
||||||
comp->AddFaction(-1);
|
// comp->AddFaction(-1);
|
||||||
comp->AddFaction(6); //Smashables
|
// comp->AddFaction(6); //Smashables
|
||||||
|
|
||||||
// A race car has 60 imagination, other entities defaults to 0.
|
// // A race car has 60 imagination, other entities defaults to 0.
|
||||||
comp->SetImagination(HasComponent(eReplicaComponentType::RACING_STATS) ? 60 : 0);
|
// comp->SetImagination(HasComponent(eReplicaComponentType::RACING_STATS) ? 60 : 0);
|
||||||
comp->SetMaxImagination(HasComponent(eReplicaComponentType::RACING_STATS) ? 60 : 0);
|
// comp->SetMaxImagination(HasComponent(eReplicaComponentType::RACING_STATS) ? 60 : 0);
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
if (destCompData.size() > 0) {
|
// if (destCompData.size() > 0) {
|
||||||
comp->AddFaction(destCompData[0].faction);
|
// comp->AddFaction(destCompData[0].faction);
|
||||||
std::stringstream ss(destCompData[0].factionList);
|
// std::stringstream ss(destCompData[0].factionList);
|
||||||
std::string token;
|
// std::string token;
|
||||||
|
|
||||||
while (std::getline(ss, token, ',')) {
|
// while (std::getline(ss, token, ',')) {
|
||||||
if (std::stoi(token) == destCompData[0].faction) continue;
|
// if (std::stoi(token) == destCompData[0].faction) continue;
|
||||||
|
|
||||||
if (token != "") {
|
// if (token != "") {
|
||||||
comp->AddFaction(std::stoi(token));
|
// comp->AddFaction(std::stoi(token));
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
// m_Components.insert(std::make_pair(eReplicaComponentType::DESTROYABLE, comp));
|
// m_Components.insert(std::make_pair(eReplicaComponentType::DESTROYABLE, comp));
|
||||||
}
|
}
|
||||||
@ -505,64 +505,64 @@ Entity::Initialize() {
|
|||||||
// m_Components.insert(std::make_pair(eReplicaComponentType::RAIL_ACTIVATOR, new RailActivatorComponent(this, railComponentID)));
|
// m_Components.insert(std::make_pair(eReplicaComponentType::RAIL_ACTIVATOR, new RailActivatorComponent(this, railComponentID)));
|
||||||
// }
|
// }
|
||||||
|
|
||||||
int movementAIID = compRegistryTable->GetByIDAndType(m_TemplateID, eReplicaComponentType::MOVEMENT_AI);
|
// int movementAIID = compRegistryTable->GetByIDAndType(m_TemplateID, eReplicaComponentType::MOVEMENT_AI);
|
||||||
if (movementAIID > 0) {
|
// if (movementAIID > 0) {
|
||||||
CDMovementAIComponentTable* moveAITable = CDClientManager::Instance().GetTable<CDMovementAIComponentTable>();
|
// CDMovementAIComponentTable* moveAITable = CDClientManager::Instance().GetTable<CDMovementAIComponentTable>();
|
||||||
std::vector<CDMovementAIComponent> moveAIComp = moveAITable->Query([=](CDMovementAIComponent entry) {return (entry.id == movementAIID); });
|
// std::vector<CDMovementAIComponent> moveAIComp = moveAITable->Query([=](CDMovementAIComponent entry) {return (entry.id == movementAIID); });
|
||||||
|
|
||||||
if (moveAIComp.size() > 0) {
|
// if (moveAIComp.size() > 0) {
|
||||||
MovementAIInfo moveInfo = MovementAIInfo();
|
// MovementAIInfo moveInfo = MovementAIInfo();
|
||||||
|
|
||||||
moveInfo.movementType = moveAIComp[0].MovementType;
|
// moveInfo.movementType = moveAIComp[0].MovementType;
|
||||||
moveInfo.wanderChance = moveAIComp[0].WanderChance;
|
// moveInfo.wanderChance = moveAIComp[0].WanderChance;
|
||||||
moveInfo.wanderRadius = moveAIComp[0].WanderRadius;
|
// moveInfo.wanderRadius = moveAIComp[0].WanderRadius;
|
||||||
moveInfo.wanderSpeed = moveAIComp[0].WanderSpeed;
|
// moveInfo.wanderSpeed = moveAIComp[0].WanderSpeed;
|
||||||
moveInfo.wanderDelayMax = moveAIComp[0].WanderDelayMax;
|
// moveInfo.wanderDelayMax = moveAIComp[0].WanderDelayMax;
|
||||||
moveInfo.wanderDelayMin = moveAIComp[0].WanderDelayMin;
|
// moveInfo.wanderDelayMin = moveAIComp[0].WanderDelayMin;
|
||||||
|
|
||||||
bool useWanderDB = GetVar<bool>(u"usewanderdb");
|
// bool useWanderDB = GetVar<bool>(u"usewanderdb");
|
||||||
|
|
||||||
if (!useWanderDB) {
|
// if (!useWanderDB) {
|
||||||
const auto wanderOverride = GetVarAs<float>(u"wanderRadius");
|
// const auto wanderOverride = GetVarAs<float>(u"wanderRadius");
|
||||||
|
|
||||||
if (wanderOverride != 0.0f) {
|
// if (wanderOverride != 0.0f) {
|
||||||
moveInfo.wanderRadius = wanderOverride;
|
// moveInfo.wanderRadius = wanderOverride;
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
m_Components.insert(std::make_pair(eReplicaComponentType::MOVEMENT_AI, new MovementAIComponent(this, moveInfo)));
|
// m_Components.insert(std::make_pair(eReplicaComponentType::MOVEMENT_AI, new MovementAIComponent(this, moveInfo)));
|
||||||
}
|
// }
|
||||||
} else if (petComponentId > 0 || combatAiId > 0 && GetComponent<BaseCombatAIComponent>()->GetTetherSpeed() > 0) {
|
// } else if (petComponentId > 0 || combatAiId > 0 && GetComponent<BaseCombatAIComponent>()->GetTetherSpeed() > 0) {
|
||||||
MovementAIInfo moveInfo = MovementAIInfo();
|
// MovementAIInfo moveInfo = MovementAIInfo();
|
||||||
moveInfo.movementType = "";
|
// moveInfo.movementType = "";
|
||||||
moveInfo.wanderChance = 0;
|
// moveInfo.wanderChance = 0;
|
||||||
moveInfo.wanderRadius = 16;
|
// moveInfo.wanderRadius = 16;
|
||||||
moveInfo.wanderSpeed = 2.5f;
|
// moveInfo.wanderSpeed = 2.5f;
|
||||||
moveInfo.wanderDelayMax = 5;
|
// moveInfo.wanderDelayMax = 5;
|
||||||
moveInfo.wanderDelayMin = 2;
|
// moveInfo.wanderDelayMin = 2;
|
||||||
|
|
||||||
m_Components.insert(std::make_pair(eReplicaComponentType::MOVEMENT_AI, new MovementAIComponent(this, moveInfo)));
|
// // m_Components.insert(std::make_pair(eReplicaComponentType::MOVEMENT_AI, new MovementAIComponent(this, moveInfo)));
|
||||||
}
|
// }
|
||||||
|
|
||||||
std::string pathName = GetVarAsString(u"attached_path");
|
// std::string pathName = GetVarAsString(u"attached_path");
|
||||||
const Path* path = dZoneManager::Instance()->GetZone()->GetPath(pathName);
|
// const Path* path = dZoneManager::Instance()->GetZone()->GetPath(pathName);
|
||||||
|
|
||||||
//Check to see if we have an attached path and add the appropiate component to handle it:
|
// //Check to see if we have an attached path and add the appropiate component to handle it:
|
||||||
if (path){
|
// if (path){
|
||||||
// if we have a moving platform path, then we need a moving platform component
|
// // if we have a moving platform path, then we need a moving platform component
|
||||||
if (path->pathType == PathType::MovingPlatform) {
|
// if (path->pathType == PathType::MovingPlatform) {
|
||||||
MovingPlatformComponent* plat = new MovingPlatformComponent(this, pathName);
|
// MovingPlatformComponent* plat = new MovingPlatformComponent(this, pathName);
|
||||||
m_Components.insert(std::make_pair(eReplicaComponentType::MOVING_PLATFORM, plat));
|
// m_Components.insert(std::make_pair(eReplicaComponentType::MOVING_PLATFORM, plat));
|
||||||
// else if we are a movement path
|
// // else if we are a movement path
|
||||||
} /*else if (path->pathType == PathType::Movement) {
|
// } /*else if (path->pathType == PathType::Movement) {
|
||||||
auto movementAIcomp = GetComponent<MovementAIComponent>();
|
// auto movementAIcomp = GetComponent<MovementAIComponent>();
|
||||||
if (movementAIcomp){
|
// if (movementAIcomp){
|
||||||
// TODO: set path in existing movementAIComp
|
// // TODO: set path in existing movementAIComp
|
||||||
} else {
|
// } else {
|
||||||
// TODO: create movementAIcomp and set path
|
// // TODO: create movementAIcomp and set path
|
||||||
}
|
// }
|
||||||
}*/
|
// }*/
|
||||||
}
|
// }
|
||||||
// else {
|
// else {
|
||||||
// else we still need to setup moving platform if it has a moving platform comp but no path
|
// else we still need to setup moving platform if it has a moving platform comp but no path
|
||||||
// int32_t movingPlatformComponentId = compRegistryTable->GetByIDAndType(m_TemplateID, eReplicaComponentType::MOVING_PLATFORM, -1);
|
// int32_t movingPlatformComponentId = compRegistryTable->GetByIDAndType(m_TemplateID, eReplicaComponentType::MOVING_PLATFORM, -1);
|
||||||
@ -572,70 +572,67 @@ Entity::Initialize() {
|
|||||||
// }
|
// }
|
||||||
// }
|
// }
|
||||||
|
|
||||||
int proximityMonitorID = compRegistryTable->GetByIDAndType(m_TemplateID, eReplicaComponentType::PROXIMITY_MONITOR);
|
// int proximityMonitorID = compRegistryTable->GetByIDAndType(m_TemplateID, eReplicaComponentType::PROXIMITY_MONITOR);
|
||||||
if (proximityMonitorID > 0) {
|
// if (proximityMonitorID > 0) {
|
||||||
CDProximityMonitorComponentTable* proxCompTable = CDClientManager::Instance().GetTable<CDProximityMonitorComponentTable>();
|
// CDProximityMonitorComponentTable* proxCompTable = CDClientManager::Instance().GetTable<CDProximityMonitorComponentTable>();
|
||||||
std::vector<CDProximityMonitorComponent> proxCompData = proxCompTable->Query([=](CDProximityMonitorComponent entry) { return (entry.id == proximityMonitorID); });
|
// std::vector<CDProximityMonitorComponent> proxCompData = proxCompTable->Query([=](CDProximityMonitorComponent entry) { return (entry.id == proximityMonitorID); });
|
||||||
if (proxCompData.size() > 0) {
|
// if (proxCompData.size() > 0) {
|
||||||
std::vector<std::string> proximityStr = GeneralUtils::SplitString(proxCompData[0].Proximities, ',');
|
// std::vector<std::string> proximityStr = GeneralUtils::SplitString(proxCompData[0].Proximities, ',');
|
||||||
ProximityMonitorComponent* comp = new ProximityMonitorComponent(this, std::stoi(proximityStr[0]), std::stoi(proximityStr[1]));
|
// ProximityMonitorComponent* comp = new ProximityMonitorComponent(this, std::stoi(proximityStr[0]), std::stoi(proximityStr[1]));
|
||||||
m_Components.insert(std::make_pair(eReplicaComponentType::PROXIMITY_MONITOR, comp));
|
// m_Components.insert(std::make_pair(eReplicaComponentType::PROXIMITY_MONITOR, comp));
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
// Hacky way to trigger these when the object has had a chance to get constructed
|
// Hacky way to trigger these when the object has had a chance to get constructed
|
||||||
AddCallbackTimer(0, [this]() {
|
// AddCallbackTimer(0, [this]() {
|
||||||
for (CppScripts::Script* script : CppScripts::GetEntityScripts(this)) {
|
// for (CppScripts::Script* script : CppScripts::GetEntityScripts(this)) {
|
||||||
script->OnStartup(this);
|
// script->OnStartup(this);
|
||||||
}
|
// }
|
||||||
});
|
// });
|
||||||
|
|
||||||
if (!m_Character && EntityManager::Instance()->GetGhostingEnabled()) {
|
// if (!m_Character && EntityManager::Instance()->GetGhostingEnabled()) {
|
||||||
// Don't ghost what is likely large scene elements
|
// // Don't ghost what is likely large scene elements
|
||||||
if (HasComponent(eReplicaComponentType::SIMPLE_PHYSICS) && HasComponent(eReplicaComponentType::RENDER) && (m_Components.size() == 2 || (HasComponent(eReplicaComponentType::TRIGGER) && m_Components.size() == 3))) {
|
// if (HasComponent(eReplicaComponentType::SIMPLE_PHYSICS) && HasComponent(eReplicaComponentType::RENDER) && (m_Components.size() == 2 || (HasComponent(eReplicaComponentType::TRIGGER) && m_Components.size() == 3))) {
|
||||||
goto no_ghosting;
|
// goto no_ghosting;
|
||||||
}
|
// }
|
||||||
|
|
||||||
/* Filter for ghosting candidates.
|
// /* Filter for ghosting candidates.
|
||||||
*
|
// *
|
||||||
* Don't ghost moving platforms, until we've got proper syncing for those.
|
// * Don't ghost moving platforms, until we've got proper syncing for those.
|
||||||
* Don't ghost big phantom physics triggers, as putting those to sleep might prevent interactions.
|
// * Don't ghost big phantom physics triggers, as putting those to sleep might prevent interactions.
|
||||||
* Don't ghost property related objects, as the client expects those to always be loaded.
|
// * Don't ghost property related objects, as the client expects those to always be loaded.
|
||||||
*/
|
// */
|
||||||
if (
|
// if (
|
||||||
!EntityManager::IsExcludedFromGhosting(GetLOT()) &&
|
// !EntityManager::IsExcludedFromGhosting(GetLOT()) &&
|
||||||
!HasComponent(eReplicaComponentType::SCRIPTED_ACTIVITY) &&
|
// !HasComponent(eReplicaComponentType::SCRIPTED_ACTIVITY) &&
|
||||||
!HasComponent(eReplicaComponentType::MOVING_PLATFORM) &&
|
// !HasComponent(eReplicaComponentType::MOVING_PLATFORM) &&
|
||||||
!HasComponent(eReplicaComponentType::PHANTOM_PHYSICS) &&
|
// !HasComponent(eReplicaComponentType::PHANTOM_PHYSICS) &&
|
||||||
!HasComponent(eReplicaComponentType::PROPERTY) &&
|
// !HasComponent(eReplicaComponentType::PROPERTY) &&
|
||||||
!HasComponent(eReplicaComponentType::RACING_CONTROL) &&
|
// !HasComponent(eReplicaComponentType::RACING_CONTROL) &&
|
||||||
!HasComponent(eReplicaComponentType::VEHICLE_PHYSICS)
|
// !HasComponent(eReplicaComponentType::VEHICLE_PHYSICS)
|
||||||
)
|
// )
|
||||||
//if (HasComponent(eReplicaComponentType::BASE_COMBAT_AI))
|
// {
|
||||||
{
|
// m_IsGhostingCandidate = true;
|
||||||
m_IsGhostingCandidate = true;
|
// }
|
||||||
}
|
|
||||||
|
|
||||||
if (GetLOT() == 6368) {
|
// if (GetLOT() == 6368) m_IsGhostingCandidate = true;
|
||||||
m_IsGhostingCandidate = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Special case for collectibles in Ninjago
|
// // Special case for collectibles in Ninjago
|
||||||
if (HasComponent(eReplicaComponentType::COLLECTIBLE) && Game::server->GetZoneID() == 2000) {
|
// if (HasComponent(eReplicaComponentType::COLLECTIBLE) && Game::server->GetZoneID() == 2000) {
|
||||||
m_IsGhostingCandidate = true;
|
// m_IsGhostingCandidate = true;
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
no_ghosting:
|
// no_ghosting:
|
||||||
|
|
||||||
TriggerEvent(eTriggerEventType::CREATE, this);
|
// TriggerEvent(eTriggerEventType::CREATE, this);
|
||||||
|
|
||||||
if (m_Character) {
|
// if (m_Character) {
|
||||||
auto controllablePhysicsComponent = GetComponent<ControllablePhysicsComponent>();
|
// auto controllablePhysicsComponent = GetComponent<ControllablePhysicsComponent>();
|
||||||
auto levelComponent = GetComponent<LevelProgressionComponent>();
|
// auto levelComponent = GetComponent<LevelProgressionComponent>();
|
||||||
|
|
||||||
if (controllablePhysicsComponent && levelComponent) {
|
// if (controllablePhysicsComponent && levelComponent) {
|
||||||
controllablePhysicsComponent->SetSpeedMultiplier(levelComponent->GetSpeedBase() / 500.0f);
|
// controllablePhysicsComponent->SetSpeedMultiplier(levelComponent->GetSpeedBase() / 500.0f);
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
@ -37,8 +37,9 @@
|
|||||||
#include "eGameActivity.h"
|
#include "eGameActivity.h"
|
||||||
|
|
||||||
#include "CDComponentsRegistryTable.h"
|
#include "CDComponentsRegistryTable.h"
|
||||||
|
#include "CDCurrencyTableTable.h"
|
||||||
|
|
||||||
DestroyableComponent::DestroyableComponent(Entity* parent) : Component(parent) {
|
DestroyableComponent::DestroyableComponent(Entity* parent, int32_t componentId) : Component(parent) {
|
||||||
m_iArmor = 0;
|
m_iArmor = 0;
|
||||||
m_fMaxArmor = 0.0f;
|
m_fMaxArmor = 0.0f;
|
||||||
m_iImagination = 0;
|
m_iImagination = 0;
|
||||||
@ -62,6 +63,7 @@ DestroyableComponent::DestroyableComponent(Entity* parent) : Component(parent) {
|
|||||||
m_MinCoins = 0;
|
m_MinCoins = 0;
|
||||||
m_MaxCoins = 0;
|
m_MaxCoins = 0;
|
||||||
m_DamageReduction = 0;
|
m_DamageReduction = 0;
|
||||||
|
m_ComponentId = componentId;
|
||||||
|
|
||||||
m_ImmuneToBasicAttackCount = 0;
|
m_ImmuneToBasicAttackCount = 0;
|
||||||
m_ImmuneToDamageOverTimeCount = 0;
|
m_ImmuneToDamageOverTimeCount = 0;
|
||||||
@ -73,49 +75,71 @@ DestroyableComponent::DestroyableComponent(Entity* parent) : Component(parent) {
|
|||||||
m_ImmuneToQuickbuildInterruptCount = 0;
|
m_ImmuneToQuickbuildInterruptCount = 0;
|
||||||
m_ImmuneToPullToPointCount = 0;
|
m_ImmuneToPullToPointCount = 0;
|
||||||
}
|
}
|
||||||
|
void DestroyableComponent::Startup() {
|
||||||
|
|
||||||
DestroyableComponent::~DestroyableComponent() {
|
|
||||||
}
|
}
|
||||||
|
void DestroyableComponent::LoadConfigData() {
|
||||||
void DestroyableComponent::Reinitialize(LOT templateID) {
|
SetIsSmashable(m_ParentEntity->GetVarAs<int32_t>(u"is_smashable") != 0);
|
||||||
CDComponentsRegistryTable* compRegistryTable = CDClientManager::Instance().GetTable<CDComponentsRegistryTable>();
|
}
|
||||||
|
void DestroyableComponent::LoadTemplateData() {
|
||||||
int32_t buffComponentID = compRegistryTable->GetByIDAndType(templateID, eReplicaComponentType::BUFF);
|
[[unlikely]] if (m_ParentEntity->IsPlayer()) return;
|
||||||
int32_t collectibleComponentID = compRegistryTable->GetByIDAndType(templateID, eReplicaComponentType::COLLECTIBLE);
|
auto* destroyableComponentTable = CDClientManager::Instance().GetTable<CDDestructibleComponentTable>();
|
||||||
int32_t quickBuildComponentID = compRegistryTable->GetByIDAndType(templateID, eReplicaComponentType::QUICK_BUILD);
|
auto destroyableDataLookup = destroyableComponentTable->Query([this](CDDestructibleComponent entry) { return (entry.id == this->m_ComponentId); });
|
||||||
|
if (m_ComponentId == -1 || destroyableDataLookup.empty()) {
|
||||||
int32_t componentID = 0;
|
|
||||||
if (collectibleComponentID > 0) componentID = collectibleComponentID;
|
|
||||||
if (quickBuildComponentID > 0) componentID = quickBuildComponentID;
|
|
||||||
if (buffComponentID > 0) componentID = buffComponentID;
|
|
||||||
|
|
||||||
CDDestructibleComponentTable* destCompTable = CDClientManager::Instance().GetTable<CDDestructibleComponentTable>();
|
|
||||||
std::vector<CDDestructibleComponent> destCompData = destCompTable->Query([=](CDDestructibleComponent entry) { return (entry.id == componentID); });
|
|
||||||
|
|
||||||
if (componentID > 0) {
|
|
||||||
std::vector<CDDestructibleComponent> destCompData = destCompTable->Query([=](CDDestructibleComponent entry) { return (entry.id == componentID); });
|
|
||||||
|
|
||||||
if (destCompData.size() > 0) {
|
|
||||||
SetHealth(destCompData[0].life);
|
|
||||||
SetImagination(destCompData[0].imagination);
|
|
||||||
SetArmor(destCompData[0].armor);
|
|
||||||
|
|
||||||
SetMaxHealth(destCompData[0].life);
|
|
||||||
SetMaxImagination(destCompData[0].imagination);
|
|
||||||
SetMaxArmor(destCompData[0].armor);
|
|
||||||
|
|
||||||
SetIsSmashable(destCompData[0].isSmashable);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
SetHealth(1);
|
SetHealth(1);
|
||||||
SetImagination(0);
|
|
||||||
SetArmor(0);
|
SetArmor(0);
|
||||||
|
|
||||||
SetMaxHealth(1);
|
SetMaxHealth(1);
|
||||||
SetMaxImagination(0);
|
|
||||||
SetMaxArmor(0);
|
SetMaxArmor(0);
|
||||||
|
|
||||||
SetIsSmashable(true);
|
SetIsSmashable(true);
|
||||||
|
AddFaction(-1);
|
||||||
|
AddFaction(6); //Smashables
|
||||||
|
|
||||||
|
// A race car has 60 imagination, other entities defaults to 0.
|
||||||
|
SetImagination(m_ParentEntity->HasComponent(eReplicaComponentType::RACING_STATS) ? 60 : 0);
|
||||||
|
SetMaxImagination(m_ParentEntity->HasComponent(eReplicaComponentType::RACING_STATS) ? 60 : 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto destroyableData = destroyableDataLookup.at(0);
|
||||||
|
if (m_ParentEntity->HasComponent(eReplicaComponentType::RACING_STATS)) {
|
||||||
|
destroyableData.imagination = 60;
|
||||||
|
}
|
||||||
|
|
||||||
|
SetHealth(destroyableData.life);
|
||||||
|
SetImagination(destroyableData.imagination);
|
||||||
|
SetArmor(destroyableData.armor);
|
||||||
|
|
||||||
|
SetMaxHealth(destroyableData.life);
|
||||||
|
SetMaxImagination(destroyableData.imagination);
|
||||||
|
SetMaxArmor(destroyableData.armor);
|
||||||
|
|
||||||
|
SetIsSmashable(destroyableData.isSmashable);
|
||||||
|
|
||||||
|
SetLootMatrixID(destroyableData.LootMatrixIndex);
|
||||||
|
|
||||||
|
// Now get currency information
|
||||||
|
uint32_t npcMinLevel = destroyableData.level;
|
||||||
|
uint32_t currencyIndex = destroyableData.CurrencyIndex;
|
||||||
|
|
||||||
|
auto* currencyTable = CDClientManager::Instance().GetTable<CDCurrencyTableTable>();
|
||||||
|
auto currencyValues = currencyTable->Query([=](CDCurrencyTable entry) { return (entry.currencyIndex == currencyIndex && entry.npcminlevel == npcMinLevel); });
|
||||||
|
|
||||||
|
if (currencyValues.size() > 0) {
|
||||||
|
// Set the coins
|
||||||
|
SetMinCoins(currencyValues.at(0).minvalue);
|
||||||
|
SetMaxCoins(currencyValues.at(0).maxvalue);
|
||||||
|
}
|
||||||
|
AddFaction(destroyableData.faction);
|
||||||
|
std::stringstream ss(destroyableData.factionList);
|
||||||
|
std::string tokenStr;
|
||||||
|
|
||||||
|
while (std::getline(ss, tokenStr, ',')) {
|
||||||
|
int32_t factionToAdd = -2;
|
||||||
|
if (!GeneralUtils::TryParse(tokenStr, factionToAdd) || factionToAdd == -2 || factionToAdd == destroyableData.faction) continue;
|
||||||
|
|
||||||
|
AddFaction(factionToAdd);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -845,7 +869,7 @@ void DestroyableComponent::SetStatusImmunity(
|
|||||||
if (bImmuneToQuickbuildInterrupt && m_ImmuneToQuickbuildInterruptCount > 0) m_ImmuneToQuickbuildInterruptCount -= 1;
|
if (bImmuneToQuickbuildInterrupt && m_ImmuneToQuickbuildInterruptCount > 0) m_ImmuneToQuickbuildInterruptCount -= 1;
|
||||||
if (bImmuneToPullToPoint && m_ImmuneToPullToPointCount > 0) m_ImmuneToPullToPointCount -= 1;
|
if (bImmuneToPullToPoint && m_ImmuneToPullToPointCount > 0) m_ImmuneToPullToPointCount -= 1;
|
||||||
|
|
||||||
} else if (state == eStateChangeType::PUSH){
|
} else if (state == eStateChangeType::PUSH) {
|
||||||
if (bImmuneToBasicAttack) m_ImmuneToBasicAttackCount += 1;
|
if (bImmuneToBasicAttack) m_ImmuneToBasicAttackCount += 1;
|
||||||
if (bImmuneToDamageOverTime) m_ImmuneToDamageOverTimeCount += 1;
|
if (bImmuneToDamageOverTime) m_ImmuneToDamageOverTimeCount += 1;
|
||||||
if (bImmuneToKnockback) m_ImmuneToKnockbackCount += 1;
|
if (bImmuneToKnockback) m_ImmuneToKnockbackCount += 1;
|
||||||
@ -972,7 +996,7 @@ void DestroyableComponent::AddOnHitCallback(const std::function<void(Entity*)>&
|
|||||||
m_OnHitCallbacks.push_back(callback);
|
m_OnHitCallbacks.push_back(callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
void DestroyableComponent::DoHardcoreModeDrops(const LWOOBJID source){
|
void DestroyableComponent::DoHardcoreModeDrops(const LWOOBJID source) {
|
||||||
//check if this is a player:
|
//check if this is a player:
|
||||||
if (m_ParentEntity->IsPlayer()) {
|
if (m_ParentEntity->IsPlayer()) {
|
||||||
//remove hardcore_lose_uscore_on_death_percent from the player's uscore:
|
//remove hardcore_lose_uscore_on_death_percent from the player's uscore:
|
||||||
@ -990,9 +1014,9 @@ void DestroyableComponent::DoHardcoreModeDrops(const LWOOBJID source){
|
|||||||
if (inventory) {
|
if (inventory) {
|
||||||
//get the items inventory:
|
//get the items inventory:
|
||||||
auto items = inventory->GetInventory(eInventoryType::ITEMS);
|
auto items = inventory->GetInventory(eInventoryType::ITEMS);
|
||||||
if (items){
|
if (items) {
|
||||||
auto itemMap = items->GetItems();
|
auto itemMap = items->GetItems();
|
||||||
if (!itemMap.empty()){
|
if (!itemMap.empty()) {
|
||||||
for (const auto& item : itemMap) {
|
for (const auto& item : itemMap) {
|
||||||
//drop the item:
|
//drop the item:
|
||||||
if (!item.second) continue;
|
if (!item.second) continue;
|
||||||
|
@ -21,19 +21,15 @@ class DestroyableComponent : public Component {
|
|||||||
public:
|
public:
|
||||||
inline static const eReplicaComponentType ComponentType = eReplicaComponentType::DESTROYABLE;
|
inline static const eReplicaComponentType ComponentType = eReplicaComponentType::DESTROYABLE;
|
||||||
|
|
||||||
DestroyableComponent(Entity* parentEntity);
|
DestroyableComponent(Entity* parentEntity, int32_t componentId = -1);
|
||||||
~DestroyableComponent() override;
|
|
||||||
|
|
||||||
|
void Startup() override;
|
||||||
|
void LoadConfigData() override;
|
||||||
|
void LoadTemplateData() override;
|
||||||
void Serialize(RakNet::BitStream* outBitStream, bool bIsInitialUpdate, uint32_t& flags);
|
void Serialize(RakNet::BitStream* outBitStream, bool bIsInitialUpdate, uint32_t& flags);
|
||||||
void LoadFromXml(tinyxml2::XMLDocument* doc) override;
|
void LoadFromXml(tinyxml2::XMLDocument* doc) override;
|
||||||
void UpdateXml(tinyxml2::XMLDocument* doc) override;
|
void UpdateXml(tinyxml2::XMLDocument* doc) override;
|
||||||
|
|
||||||
/**
|
|
||||||
* Initializes the component using a different LOT
|
|
||||||
* @param templateID the ID to use for initialization
|
|
||||||
*/
|
|
||||||
void Reinitialize(LOT templateID);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sets the health of this entity. Makes sure this is serialized on the next tick and if this is a character its
|
* Sets the health of this entity. Makes sure this is serialized on the next tick and if this is a character its
|
||||||
* stats will also update.
|
* stats will also update.
|
||||||
@ -458,6 +454,8 @@ public:
|
|||||||
void DoHardcoreModeDrops(const LWOOBJID source);
|
void DoHardcoreModeDrops(const LWOOBJID source);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
// The ID of this component
|
||||||
|
int32_t m_ComponentId;
|
||||||
/**
|
/**
|
||||||
* Whether or not the health should be serialized
|
* Whether or not the health should be serialized
|
||||||
*/
|
*/
|
||||||
|
@ -35,6 +35,10 @@ void LevelProgressionComponent::LoadFromXml(tinyxml2::XMLDocument* doc) {
|
|||||||
uint32_t characterVersion;
|
uint32_t characterVersion;
|
||||||
level->QueryAttribute("cv", &characterVersion);
|
level->QueryAttribute("cv", &characterVersion);
|
||||||
m_CharacterVersion = static_cast<eCharacterVersion>(characterVersion);
|
m_CharacterVersion = static_cast<eCharacterVersion>(characterVersion);
|
||||||
|
auto* controllablePhysicsComponent = m_ParentEntity->GetComponent<ControllablePhysicsComponent>();
|
||||||
|
|
||||||
|
if (!controllablePhysicsComponent) return;
|
||||||
|
controllablePhysicsComponent->SetSpeedMultiplier(GetSpeedBase() / 500.0f);
|
||||||
}
|
}
|
||||||
|
|
||||||
void LevelProgressionComponent::Serialize(RakNet::BitStream* outBitStream, bool bIsInitialUpdate, unsigned int& flags) {
|
void LevelProgressionComponent::Serialize(RakNet::BitStream* outBitStream, bool bIsInitialUpdate, unsigned int& flags) {
|
||||||
@ -68,7 +72,7 @@ void LevelProgressionComponent::HandleLevelUp() {
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 9:
|
case 9:
|
||||||
SetSpeedBase(static_cast<float>(reward->value) );
|
SetSpeedBase(static_cast<float>(reward->value));
|
||||||
controllablePhysicsComponent->SetSpeedMultiplier(GetSpeedBase() / 500.0f);
|
controllablePhysicsComponent->SetSpeedMultiplier(GetSpeedBase() / 500.0f);
|
||||||
break;
|
break;
|
||||||
case 11:
|
case 11:
|
||||||
@ -82,7 +86,7 @@ void LevelProgressionComponent::HandleLevelUp() {
|
|||||||
if (rewardingItem) GameMessages::NotifyLevelRewards(m_ParentEntity->GetObjectID(), m_ParentEntity->GetSystemAddress(), m_Level, !rewardingItem);
|
if (rewardingItem) GameMessages::NotifyLevelRewards(m_ParentEntity->GetObjectID(), m_ParentEntity->GetSystemAddress(), m_Level, !rewardingItem);
|
||||||
}
|
}
|
||||||
|
|
||||||
void LevelProgressionComponent::SetRetroactiveBaseSpeed(){
|
void LevelProgressionComponent::SetRetroactiveBaseSpeed() {
|
||||||
if (m_Level >= 20) m_SpeedBase = 525.0f;
|
if (m_Level >= 20) m_SpeedBase = 525.0f;
|
||||||
auto* controllablePhysicsComponent = m_ParentEntity->GetComponent<ControllablePhysicsComponent>();
|
auto* controllablePhysicsComponent = m_ParentEntity->GetComponent<ControllablePhysicsComponent>();
|
||||||
if (controllablePhysicsComponent) controllablePhysicsComponent->SetSpeedMultiplier(m_SpeedBase / 500.0f);
|
if (controllablePhysicsComponent) controllablePhysicsComponent->SetSpeedMultiplier(m_SpeedBase / 500.0f);
|
||||||
|
@ -13,22 +13,18 @@
|
|||||||
|
|
||||||
#include "CDComponentsRegistryTable.h"
|
#include "CDComponentsRegistryTable.h"
|
||||||
#include "CDPhysicsComponentTable.h"
|
#include "CDPhysicsComponentTable.h"
|
||||||
|
#include "CDMovementAIComponentTable.h"
|
||||||
|
|
||||||
std::map<LOT, float> MovementAIComponent::m_PhysicsSpeedCache = {};
|
std::map<LOT, float> MovementAIComponent::m_PhysicsSpeedCache = {};
|
||||||
|
|
||||||
MovementAIComponent::MovementAIComponent(Entity* parent, MovementAIInfo info) : Component(parent) {
|
MovementAIComponent::MovementAIComponent(Entity* parent, int32_t componentId) : Component(parent) {
|
||||||
m_Info = std::move(info);
|
m_ComponentId = componentId;
|
||||||
m_Done = true;
|
m_Done = true;
|
||||||
|
|
||||||
m_BaseCombatAI = nullptr;
|
m_BaseCombatAI = nullptr;
|
||||||
|
|
||||||
m_BaseCombatAI = m_ParentEntity->GetComponent<BaseCombatAIComponent>();
|
m_BaseCombatAI = m_ParentEntity->GetComponent<BaseCombatAIComponent>();
|
||||||
|
|
||||||
//Try and fix the insane values:
|
|
||||||
if (m_Info.wanderRadius > 5.0f) m_Info.wanderRadius = m_Info.wanderRadius * 0.5f;
|
|
||||||
if (m_Info.wanderRadius > 8.0f) m_Info.wanderRadius = 8.0f;
|
|
||||||
if (m_Info.wanderSpeed > 0.5f) m_Info.wanderSpeed = m_Info.wanderSpeed * 0.5f;
|
|
||||||
|
|
||||||
m_BaseSpeed = GetBaseSpeed(m_ParentEntity->GetLOT());
|
m_BaseSpeed = GetBaseSpeed(m_ParentEntity->GetLOT());
|
||||||
|
|
||||||
m_NextWaypoint = GetCurrentPosition();
|
m_NextWaypoint = GetCurrentPosition();
|
||||||
@ -43,7 +39,48 @@ MovementAIComponent::MovementAIComponent(Entity* parent, MovementAIInfo info) :
|
|||||||
m_LockRotation = false;
|
m_LockRotation = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
MovementAIComponent::~MovementAIComponent() = default;
|
void MovementAIComponent::Startup() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void MovementAIComponent::LoadConfigData() {
|
||||||
|
bool useWanderDB = m_ParentEntity->GetVar<bool>(u"usewanderdb");
|
||||||
|
|
||||||
|
if (!useWanderDB) {
|
||||||
|
const auto wanderOverride = m_ParentEntity->GetVarAs<float>(u"wanderRadius");
|
||||||
|
|
||||||
|
if (wanderOverride != 0.0f) {
|
||||||
|
m_Info.wanderRadius = wanderOverride;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void MovementAIComponent::LoadTemplateData() {
|
||||||
|
if (m_ComponentId == -1) return;
|
||||||
|
auto* movementAiComponentTable = CDClientManager::Instance().GetTable<CDMovementAIComponentTable>();
|
||||||
|
auto movementEntries = movementAiComponentTable->Query([this](CDMovementAIComponent entry) {return (entry.id == this->m_ComponentId); });
|
||||||
|
if (movementEntries.empty()) return;
|
||||||
|
auto movementEntry = movementEntries.at(0);
|
||||||
|
MovementAIInfo moveInfo{};
|
||||||
|
|
||||||
|
moveInfo.movementType = movementEntry.MovementType;
|
||||||
|
moveInfo.wanderChance = movementEntry.WanderChance;
|
||||||
|
moveInfo.wanderRadius = movementEntry.WanderRadius;
|
||||||
|
moveInfo.wanderSpeed = movementEntry.WanderSpeed;
|
||||||
|
moveInfo.wanderDelayMax = movementEntry.WanderDelayMax;
|
||||||
|
moveInfo.wanderDelayMin = movementEntry.WanderDelayMin;
|
||||||
|
|
||||||
|
this->SetMoveInfo(moveInfo);
|
||||||
|
}
|
||||||
|
|
||||||
|
void MovementAIComponent::SetMoveInfo(const MovementAIInfo& info) {
|
||||||
|
m_Info = info;
|
||||||
|
|
||||||
|
//Try and fix the insane values:
|
||||||
|
if (m_Info.wanderRadius > 5.0f) m_Info.wanderRadius *= 0.5f;
|
||||||
|
if (m_Info.wanderRadius > 8.0f) m_Info.wanderRadius = 8.0f;
|
||||||
|
if (m_Info.wanderSpeed > 0.5f) m_Info.wanderSpeed *= 0.5f;
|
||||||
|
}
|
||||||
|
|
||||||
void MovementAIComponent::Update(const float deltaTime) {
|
void MovementAIComponent::Update(const float deltaTime) {
|
||||||
if (m_Interrupted) {
|
if (m_Interrupted) {
|
||||||
|
@ -23,6 +23,10 @@ class BaseCombatAIComponent;
|
|||||||
* Information that describes the different variables used to make an entity move around
|
* Information that describes the different variables used to make an entity move around
|
||||||
*/
|
*/
|
||||||
struct MovementAIInfo {
|
struct MovementAIInfo {
|
||||||
|
|
||||||
|
// copy assignment
|
||||||
|
MovementAIInfo& operator=(const MovementAIInfo& other) = default;
|
||||||
|
|
||||||
std::string movementType;
|
std::string movementType;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -59,8 +63,10 @@ class MovementAIComponent : public Component {
|
|||||||
public:
|
public:
|
||||||
inline static const eReplicaComponentType ComponentType = eReplicaComponentType::MOVEMENT_AI;
|
inline static const eReplicaComponentType ComponentType = eReplicaComponentType::MOVEMENT_AI;
|
||||||
|
|
||||||
MovementAIComponent(Entity* parentEntity, MovementAIInfo info);
|
MovementAIComponent(Entity* parentEntity, int32_t componentId = -1);
|
||||||
~MovementAIComponent() override;
|
void Startup() override;
|
||||||
|
void LoadTemplateData() override;
|
||||||
|
void LoadConfigData() override;
|
||||||
|
|
||||||
void Update(float deltaTime) override;
|
void Update(float deltaTime) override;
|
||||||
|
|
||||||
@ -217,6 +223,7 @@ public:
|
|||||||
*/
|
*/
|
||||||
static float GetBaseSpeed(LOT lot);
|
static float GetBaseSpeed(LOT lot);
|
||||||
|
|
||||||
|
void SetMoveInfo(const MovementAIInfo& value);
|
||||||
private:
|
private:
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -326,6 +333,8 @@ private:
|
|||||||
* Cache of all lots and their respective speeds
|
* Cache of all lots and their respective speeds
|
||||||
*/
|
*/
|
||||||
static std::map<LOT, float> m_PhysicsSpeedCache;
|
static std::map<LOT, float> m_PhysicsSpeedCache;
|
||||||
|
|
||||||
|
int32_t m_ComponentId;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // MOVEMENTAICOMPONENT_H
|
#endif // MOVEMENTAICOMPONENT_H
|
||||||
|
@ -4,14 +4,13 @@
|
|||||||
#include "ControllablePhysicsComponent.h"
|
#include "ControllablePhysicsComponent.h"
|
||||||
#include "EntityManager.h"
|
#include "EntityManager.h"
|
||||||
#include "SimplePhysicsComponent.h"
|
#include "SimplePhysicsComponent.h"
|
||||||
|
#include "CDClientManager.h"
|
||||||
|
#include "CDProximityMonitorComponentTable.h"
|
||||||
|
|
||||||
const std::map<LWOOBJID, dpEntity*> ProximityMonitorComponent::m_EmptyObjectMap = {};
|
const std::map<LWOOBJID, dpEntity*> ProximityMonitorComponent::m_EmptyObjectMap = {};
|
||||||
|
|
||||||
ProximityMonitorComponent::ProximityMonitorComponent(Entity* parent, int radiusSmall, int radiusLarge) : Component(parent) {
|
ProximityMonitorComponent::ProximityMonitorComponent(Entity* parent, int32_t componentId) : Component(parent) {
|
||||||
if (radiusSmall != -1 && radiusLarge != -1) {
|
m_ComponentId = componentId;
|
||||||
SetProximityRadius(radiusSmall, "rocketSmall");
|
|
||||||
SetProximityRadius(radiusLarge, "rocketLarge");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ProximityMonitorComponent::~ProximityMonitorComponent() {
|
ProximityMonitorComponent::~ProximityMonitorComponent() {
|
||||||
@ -24,6 +23,25 @@ ProximityMonitorComponent::~ProximityMonitorComponent() {
|
|||||||
m_ProximitiesData.clear();
|
m_ProximitiesData.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ProximityMonitorComponent::LoadTemplateData() {
|
||||||
|
if (m_ComponentId == -1) return;
|
||||||
|
auto* proxCompTable = CDClientManager::Instance().GetTable<CDProximityMonitorComponentTable>();
|
||||||
|
auto proxCompData = proxCompTable->Query([this](CDProximityMonitorComponent entry) { return (entry.id == this->m_ComponentId); });
|
||||||
|
|
||||||
|
if (!proxCompData.empty()) {
|
||||||
|
float radiusSmall = -1.0f;
|
||||||
|
float radiusLarge = -1.0f;
|
||||||
|
auto proximitySplit = GeneralUtils::SplitString(proxCompData[0].Proximities, ',');
|
||||||
|
if (proximitySplit.size() < 2) return;
|
||||||
|
GeneralUtils::TryParse(proximitySplit.at(0), radiusSmall);
|
||||||
|
GeneralUtils::TryParse(proximitySplit.at(1), radiusLarge);
|
||||||
|
if (radiusSmall != -1.0f && radiusLarge != -1.0f) {
|
||||||
|
SetProximityRadius(radiusSmall, "rocketSmall");
|
||||||
|
SetProximityRadius(radiusLarge, "rocketLarge");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void ProximityMonitorComponent::SetProximityRadius(float proxRadius, const std::string& name) {
|
void ProximityMonitorComponent::SetProximityRadius(float proxRadius, const std::string& name) {
|
||||||
dpEntity* en = new dpEntity(m_ParentEntity->GetObjectID(), proxRadius);
|
dpEntity* en = new dpEntity(m_ParentEntity->GetObjectID(), proxRadius);
|
||||||
en->SetPosition(m_ParentEntity->GetPosition());
|
en->SetPosition(m_ParentEntity->GetPosition());
|
||||||
|
@ -21,8 +21,10 @@ class ProximityMonitorComponent : public Component {
|
|||||||
public:
|
public:
|
||||||
inline static const eReplicaComponentType ComponentType = eReplicaComponentType::PROXIMITY_MONITOR;
|
inline static const eReplicaComponentType ComponentType = eReplicaComponentType::PROXIMITY_MONITOR;
|
||||||
|
|
||||||
ProximityMonitorComponent(Entity* parentEntity, int smallRadius = -1, int largeRadius = -1);
|
ProximityMonitorComponent(Entity* parentEntity, int32_t componentId = -1);
|
||||||
~ProximityMonitorComponent() override;
|
~ProximityMonitorComponent() override;
|
||||||
|
|
||||||
|
void LoadTemplateData() override;
|
||||||
void Update(float deltaTime) override;
|
void Update(float deltaTime) override;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -71,6 +73,8 @@ private:
|
|||||||
* Default value for the proximity data
|
* Default value for the proximity data
|
||||||
*/
|
*/
|
||||||
static const std::map<LWOOBJID, dpEntity*> m_EmptyObjectMap;
|
static const std::map<LWOOBJID, dpEntity*> m_EmptyObjectMap;
|
||||||
|
|
||||||
|
int32_t m_ComponentId = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // PROXIMITYMONITORCOMPONENT_H
|
#endif // PROXIMITYMONITORCOMPONENT_H
|
||||||
|
@ -12,5 +12,6 @@ void AgStromlingProperty::OnStartup(Entity* self) {
|
|||||||
4
|
4
|
||||||
};
|
};
|
||||||
|
|
||||||
self->AddComponent<MovementAIComponent>(movementInfo);
|
auto* movementAiComponent = self->AddComponent<MovementAIComponent>(0U);
|
||||||
|
if (movementAiComponent) movementAiComponent->SetMoveInfo(movementInfo);
|
||||||
}
|
}
|
||||||
|
@ -287,11 +287,11 @@ void SGCannon::OnActivityTimerDone(Entity* self, const std::string& name) {
|
|||||||
auto* enemy = EntityManager::Instance()->CreateEntity(info, nullptr, self);
|
auto* enemy = EntityManager::Instance()->CreateEntity(info, nullptr, self);
|
||||||
EntityManager::Instance()->ConstructEntity(enemy);
|
EntityManager::Instance()->ConstructEntity(enemy);
|
||||||
|
|
||||||
auto movementAI = enemy->AddComponent<MovementAIComponent, MovementAIInfo>({});
|
auto movementAiComponent = enemy->AddComponent<MovementAIComponent>(0U);
|
||||||
|
|
||||||
movementAI->SetSpeed(toSpawn.initialSpeed);
|
movementAiComponent->SetSpeed(toSpawn.initialSpeed);
|
||||||
movementAI->SetCurrentSpeed(toSpawn.initialSpeed);
|
movementAiComponent->SetCurrentSpeed(toSpawn.initialSpeed);
|
||||||
movementAI->SetHaltDistance(0.0f);
|
movementAiComponent->SetHaltDistance(0.0f);
|
||||||
|
|
||||||
std::vector<NiPoint3> pathWaypoints;
|
std::vector<NiPoint3> pathWaypoints;
|
||||||
|
|
||||||
@ -303,7 +303,7 @@ void SGCannon::OnActivityTimerDone(Entity* self, const std::string& name) {
|
|||||||
std::reverse(pathWaypoints.begin(), pathWaypoints.end());
|
std::reverse(pathWaypoints.begin(), pathWaypoints.end());
|
||||||
}
|
}
|
||||||
|
|
||||||
movementAI->SetPath(pathWaypoints);
|
movementAiComponent->SetPath(pathWaypoints);
|
||||||
|
|
||||||
enemy->AddDieCallback([this, self, enemy, name]() {
|
enemy->AddDieCallback([this, self, enemy, name]() {
|
||||||
RegisterHit(self, enemy, name);
|
RegisterHit(self, enemy, name);
|
||||||
|
Loading…
Reference in New Issue
Block a user