Periodically check player proximity to outdoor pvp objectives.

--HG--
branch : trunk
This commit is contained in:
w12x
2008-12-23 10:00:03 +01:00
parent 96e35de691
commit f40479e87f
4 changed files with 59 additions and 43 deletions

View File

@@ -27,42 +27,29 @@
#include "WorldPacket.h"
OutdoorPvPObjective::OutdoorPvPObjective(OutdoorPvP * pvp)
: m_PvP(pvp), m_AllianceActivePlayerCount(0), m_HordeActivePlayerCount(0),
m_ShiftPhase(0), m_ShiftMaxPhase(0), m_OldPhase(0),
m_State(0), m_OldState(0), m_CapturePoint(0), m_NeutralValue(0), m_ShiftMaxCaptureSpeed(0), m_CapturePointCreature(0)
: m_PvP(pvp), m_ShiftPhase(0), m_ShiftMaxPhase(0), m_OldPhase(0),
m_State(0), m_OldState(0), m_CapturePoint(0), m_NeutralValue(0),
m_ShiftMaxCaptureSpeed(0), m_CapturePointCreature(0)
{
}
bool OutdoorPvPObjective::HandlePlayerEnter(Player * plr)
{
uint32 team = (plr->GetTeam() == HORDE) ? 1 : 0;
// only called if really entered, so no use in the return value anymore
// player distance and activity state was checked already in the AI
std::set<uint64>::iterator pitr = m_ActivePlayerGuids.find(plr->GetGUID());
// if not already counted as active, add player
if(pitr == m_ActivePlayerGuids.end())
{
if(plr->GetTeam() == ALLIANCE)
++m_AllianceActivePlayerCount;
else
++m_HordeActivePlayerCount;
m_ActivePlayerGuids.insert(plr->GetGUID());
std::pair<std::set<uint64>::iterator,bool> newinsert = m_ActivePlayerGuids[team].insert(plr->GetGUID());
if(newinsert.second)
sLog.outDebug("player %u entered an outdoorpvpobjective", plr->GetGUIDLow());
return true;
}
return true;
}
void OutdoorPvPObjective::HandlePlayerLeave(Player * plr)
{
uint32 team = (plr->GetTeam() == HORDE) ? 1 : 0;
// only decrease the count if the player is in the active list
if(m_ActivePlayerGuids.find(plr->GetGUID())!=m_ActivePlayerGuids.end())
{
if(plr->GetTeam() == ALLIANCE)
--m_AllianceActivePlayerCount;
else
--m_HordeActivePlayerCount;
m_ActivePlayerGuids.erase(plr->GetGUID());
}
if(m_ActivePlayerGuids[team].erase(plr->GetGUID()) > 0)
sLog.outDebug("player %u left an outdoorpvpobjective", plr->GetGUIDLow());
}
void OutdoorPvPObjective::HandlePlayerActivityChanged(Player * plr)
@@ -453,12 +440,37 @@ bool OutdoorPvP::Update(uint32 diff)
return objective_changed;
}
void OutdoorPvPObjective::UpdateActivePlayerProximityCheck()
{
if(GameObject *cp = HashMapHolder<GameObject>::Find(m_CapturePoint))
{
for(int team = 0; team < 2; ++team)
{
for(std::set<uint64>::iterator itr = m_ActivePlayerGuids[team].begin(); itr != m_ActivePlayerGuids[team].end(); ++ itr)
{
// if the player is online
if(Player * pl = objmgr.GetPlayer(*itr))
{
if(!cp->IsWithinDistInMap(pl,cp->GetGOInfo()->raw.data[0]))
HandleCapturePointEvent(pl, cp->GetGOInfo()->raw.data[9]); //i_objective->HandlePlayerLeave((Player*)u);
}
else
{
sLog.outError("Player ("I64FMTD") offline, bit still in outdoor pvp, this should never happen.",(*itr));
}
}
}
}
}
bool OutdoorPvPObjective::Update(uint32 diff)
{
UpdateActivePlayerProximityCheck();
uint32 Challenger = 0;
// get the difference of numbers
float fact_diff = (m_AllianceActivePlayerCount - m_HordeActivePlayerCount);
float fact_diff = ((float)m_ActivePlayerGuids[0].size() - (float)m_ActivePlayerGuids[1].size());
if(fact_diff<0)
{
@@ -568,27 +580,30 @@ void OutdoorPvP::SendUpdateWorldState(uint32 field, uint32 value)
void OutdoorPvPObjective::SendUpdateWorldState(uint32 field, uint32 value)
{
// send to all players present in the area
for(std::set<uint64>::iterator itr = m_ActivePlayerGuids.begin(); itr != m_ActivePlayerGuids.end(); ++itr)
for(uint32 team = 0; team < 2; ++team)
{
Player * plr = objmgr.GetPlayer(*itr);
if(plr)
// send to all players present in the area
for(std::set<uint64>::iterator itr = m_ActivePlayerGuids[team].begin(); itr != m_ActivePlayerGuids[team].end(); ++itr)
{
plr->SendUpdateWorldState(field,value);
Player * plr = objmgr.GetPlayer(*itr);
if(plr)
{
plr->SendUpdateWorldState(field,value);
}
}
}
}
void OutdoorPvPObjective::SendObjectiveComplete(uint32 id,uint64 guid)
{
uint32 controlling_faction;
uint32 team;
switch(m_State)
{
case OBJECTIVESTATE_ALLIANCE:
controlling_faction = ALLIANCE;
team = 0;
break;
case OBJECTIVESTATE_HORDE:
controlling_faction = HORDE;
team = 1;
break;
default:
return;
@@ -596,10 +611,10 @@ void OutdoorPvPObjective::SendObjectiveComplete(uint32 id,uint64 guid)
}
// send to all players present in the area
for(std::set<uint64>::iterator itr = m_ActivePlayerGuids.begin(); itr != m_ActivePlayerGuids.end(); ++itr)
for(std::set<uint64>::iterator itr = m_ActivePlayerGuids[team].begin(); itr != m_ActivePlayerGuids[team].end(); ++itr)
{
Player * plr = objmgr.GetPlayer(*itr);
if(plr && plr->GetTeam() == controlling_faction)
if(plr)
{
plr->KilledMonster(id,guid);
}
@@ -657,8 +672,9 @@ bool OutdoorPvP::IsInsideObjective(Player *plr)
bool OutdoorPvPObjective::IsInsideObjective(Player *plr)
{
std::set<uint64>::iterator itr = m_ActivePlayerGuids.find(plr->GetGUID());
return itr != m_ActivePlayerGuids.end();
uint32 team = (plr->GetTeam() == HORDE) ? 1 : 0;
std::set<uint64>::iterator itr = m_ActivePlayerGuids[team].find(plr->GetGUID());
return itr != m_ActivePlayerGuids[team].end();
}
bool OutdoorPvP::HandleCustomSpell(Player *plr, uint32 spellId, GameObject * go)

View File

@@ -126,11 +126,11 @@ protected:
virtual bool DelObject(uint32 type);
virtual bool DelCapturePoint();
virtual void UpdateActivePlayerProximityCheck();
protected:
// active players in the area of the objective
std::set<uint64> m_ActivePlayerGuids;
int32 m_AllianceActivePlayerCount;
int32 m_HordeActivePlayerCount;
// active players in the area of the objective, 0 - alliance, 1 - horde
std::set<uint64> m_ActivePlayerGuids[2];
// total shift needed to capture the objective
float m_ShiftMaxPhase;
// maximum speed of capture

View File

@@ -577,9 +577,9 @@ bool OutdoorPvPObjectiveNA::Update(uint32 diff)
{
// let the controlling faction advance in phase
bool capturable = false;
if(m_ControllingFaction == ALLIANCE && m_AllianceActivePlayerCount > m_HordeActivePlayerCount)
if(m_ControllingFaction == ALLIANCE && m_ActivePlayerGuids[0].size() > m_ActivePlayerGuids[1].size())
capturable = true;
else if(m_ControllingFaction == HORDE && m_AllianceActivePlayerCount < m_HordeActivePlayerCount)
else if(m_ControllingFaction == HORDE && m_ActivePlayerGuids[0].size() < m_ActivePlayerGuids[1].size())
capturable = true;
if(m_GuardCheckTimer < diff)

View File

@@ -290,8 +290,8 @@ bool OutdoorPvPTF::SetupOutdoorPvP()
bool OutdoorPvPObjectiveTF::Update(uint32 diff)
{
// can update even in locked state if gathers the controlling faction
bool canupdate = ((((OutdoorPvPTF*)m_PvP)->m_AllianceTowersControlled > 0) && this->m_AllianceActivePlayerCount > this->m_HordeActivePlayerCount) ||
((((OutdoorPvPTF*)m_PvP)->m_HordeTowersControlled > 0) && this->m_AllianceActivePlayerCount < this->m_HordeActivePlayerCount);
bool canupdate = ((((OutdoorPvPTF*)m_PvP)->m_AllianceTowersControlled > 0) && this->m_ActivePlayerGuids[0].size() > this->m_ActivePlayerGuids[1].size()) ||
((((OutdoorPvPTF*)m_PvP)->m_HordeTowersControlled > 0) && this->m_ActivePlayerGuids[0].size() < this->m_ActivePlayerGuids[1].size());
// if gathers the other faction, then only update if the pvp is unlocked
canupdate = canupdate || !((OutdoorPvPTF*)m_PvP)->m_IsLocked;
if(canupdate && OutdoorPvPObjective::Update(diff))