mirror of
https://github.com/DarkflameUniverse/DarkflameServer.git
synced 2024-12-23 14:03:34 +00:00
203 lines
4.6 KiB
C++
203 lines
4.6 KiB
C++
|
#include "BaseRandomServer.h"
|
||
|
#include "EntityManager.h"
|
||
|
#include "dZoneManager.h"
|
||
|
#include "DestroyableComponent.h"
|
||
|
#include "Spawner.h"
|
||
|
|
||
|
void BaseRandomServer::BaseStartup(Entity* self)
|
||
|
{
|
||
|
self->SetVar<std::string>(u"SpawnState", "min");
|
||
|
self->SetVar<bool>(u"JustChanged", false);
|
||
|
|
||
|
CheckEvents(self);
|
||
|
SpawnMapZones(self);
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::CheckEvents(Entity* self)
|
||
|
{
|
||
|
// TODO: Add events?
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::SpawnMapZones(Entity* self)
|
||
|
{
|
||
|
for (const auto& pair : sectionMultipliers)
|
||
|
{
|
||
|
const auto sectionName = zonePrefix + "_" + zoneName + "_" + pair.first;
|
||
|
|
||
|
SpawnSection(self, sectionName, pair.second);
|
||
|
}
|
||
|
|
||
|
if (zoneName == "str")
|
||
|
{
|
||
|
SpawnNamedEnemy(self);
|
||
|
}
|
||
|
|
||
|
self->SetVar(u"bInit", true);
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::SpawnSection(Entity* self, const std::string& sectionName, float iMultiplier)
|
||
|
{
|
||
|
Zone* spawnLoad = GetRandomLoad(self, sectionName);
|
||
|
|
||
|
if (spawnLoad == nullptr)
|
||
|
{
|
||
|
Game::logger->Log("BaseRandomServer", "Failed to find section: %s\n", sectionName.c_str());
|
||
|
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
for (const auto& spawnerData : spawnLoad->entries)
|
||
|
{
|
||
|
if (spawnerData.name.empty())
|
||
|
{
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
const auto spawnNum = std::floor(spawnerData.num * iMultiplier);
|
||
|
const auto spawnerName = sectionName + "_" + spawnerData.name;
|
||
|
|
||
|
SetSpawnerNetwork(self, spawnerName, spawnNum, spawnerData.lot);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::SetSpawnerNetwork(Entity* self, const std::string& spawnerName, int32_t spawnNum, LOT spawnLOT)
|
||
|
{
|
||
|
const auto& spawners = dZoneManager::Instance()->GetSpawnersByName(spawnerName);
|
||
|
|
||
|
if (spawnLOT == 11217 && spawnNum > 1)
|
||
|
{
|
||
|
spawnNum = 1;
|
||
|
}
|
||
|
|
||
|
if (spawners.empty())
|
||
|
{
|
||
|
Game::logger->Log("BaseRandomServer", "Failed to find spawner: %s\n", spawnerName.c_str());
|
||
|
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
auto* spawner = spawners[0];
|
||
|
|
||
|
if (spawnLOT != 0)
|
||
|
{
|
||
|
spawner->SetSpawnLot(spawnLOT);
|
||
|
spawner->SetRespawnTime(respawnTime);
|
||
|
}
|
||
|
|
||
|
if (spawnNum != 0)
|
||
|
{
|
||
|
spawner->SetNumToMaintain(spawnNum);
|
||
|
}
|
||
|
|
||
|
if (spawnerName == "Named_Enemies")
|
||
|
{
|
||
|
//spawner->Reset();
|
||
|
}
|
||
|
|
||
|
spawner->Activate();
|
||
|
|
||
|
if (std::find(spawnersWatched.begin(), spawnersWatched.end(), spawner) != spawnersWatched.end())
|
||
|
{
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
spawner->AddSpawnedEntityDieCallback([this, self, spawner] () {
|
||
|
NotifySpawnerOfDeath(self, spawner);
|
||
|
});
|
||
|
|
||
|
spawnersWatched.push_back(spawner);
|
||
|
}
|
||
|
|
||
|
BaseRandomServer::Zone* BaseRandomServer::GetRandomLoad(Entity* self, const std::string& sectionName)
|
||
|
{
|
||
|
const auto zoneInfo = GeneralUtils::SplitString(sectionName, '_');
|
||
|
|
||
|
int32_t totalWeight = 0;
|
||
|
|
||
|
for (const auto& load : zones)
|
||
|
{
|
||
|
totalWeight += load.iChance;
|
||
|
}
|
||
|
|
||
|
const auto randWeight = GeneralUtils::GenerateRandomNumber<int32_t>(0, totalWeight);
|
||
|
|
||
|
int32_t weight = 0;
|
||
|
for (auto& zone : zones)
|
||
|
{
|
||
|
weight += zone.iChance;
|
||
|
|
||
|
if (randWeight <= weight)
|
||
|
{
|
||
|
return &zone;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return nullptr;
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::NotifySpawnerOfDeath(Entity* self, Spawner* spawner)
|
||
|
{
|
||
|
const auto& spawnerName = spawner->GetName();
|
||
|
|
||
|
if (spawnerName == "Named_Enemies")
|
||
|
{
|
||
|
NamedEnemyDeath(self, spawner);
|
||
|
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
const auto& sectionName = spawnerName.substr(0, spawnerName.size() - 7);
|
||
|
|
||
|
const auto variableName = u"mobsDead" + GeneralUtils::ASCIIToUTF16(sectionName);
|
||
|
|
||
|
auto mobDeathCount = self->GetVar<int32_t>(variableName);
|
||
|
|
||
|
mobDeathCount++;
|
||
|
|
||
|
if (mobDeathCount >= mobDeathResetNumber)
|
||
|
{
|
||
|
const auto& zoneInfo = GeneralUtils::SplitString(sectionName, '_');
|
||
|
|
||
|
SpawnSection(self, sectionName, sectionMultipliers[zoneInfo[sectionIDConst - 1]]);
|
||
|
}
|
||
|
|
||
|
self->SetVar(variableName, mobDeathCount);
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::NamedEnemyDeath(Entity* self, Spawner* spawner)
|
||
|
{
|
||
|
const auto spawnDelay = GeneralUtils::GenerateRandomNumber<float>(1, 2) * 450;
|
||
|
|
||
|
self->AddTimer("SpawnNewEnemy", spawnDelay);
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::SpawnersUp(Entity* self)
|
||
|
{
|
||
|
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::SpawnersDown(Entity* self)
|
||
|
{
|
||
|
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::BaseOnTimerDone(Entity* self, const std::string& timerName)
|
||
|
{
|
||
|
NamedTimerDone(self, timerName);
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::SpawnNamedEnemy(Entity* self)
|
||
|
{
|
||
|
const auto enemy = namedMobs[GeneralUtils::GenerateRandomNumber<int32_t>(0, namedMobs.size() - 1)];
|
||
|
|
||
|
SetSpawnerNetwork(self, "Named_Enemies", 1, enemy);
|
||
|
}
|
||
|
|
||
|
void BaseRandomServer::NamedTimerDone(Entity* self, const std::string& timerName)
|
||
|
{
|
||
|
if (timerName == "SpawnNewEnemy")
|
||
|
{
|
||
|
SpawnNamedEnemy(self);
|
||
|
}
|
||
|
}
|