*Make mtmaps a bit more stable, particularly when it updates players.

*Do some better cleanup on spec switching (should no longer strip away all auras, forcing a relog), unsummon totems, clear combo points, etc.
*Cleanup and optimization.

--HG--
branch : trunk
This commit is contained in:
maximius
2009-10-30 22:52:37 -07:00
parent 22f349d2b5
commit 73fd6dbba6
4 changed files with 237 additions and 273 deletions

View File

@@ -223,8 +223,11 @@ void Unit::Update( uint32 p_time )
// WARNING! Order of execution here is important, do not change.
// Spells must be processed with event system BEFORE they go to _UpdateSpells.
// Or else we may have some SPELL_STATE_FINISHED spells stalled in pointers, that is bad.
m_Events.Update( p_time );
_UpdateSpells( p_time );
#pragma omp critical(UpdateThreadSafety)
{
m_Events.Update( p_time );
_UpdateSpells( p_time );
}
// If this is set during update SetCantProc(false) call is missing somewhere in the code
// Having this would prevent spells from being proced, so let's crash
@@ -253,11 +256,11 @@ void Unit::Update( uint32 p_time )
//if(!hasUnitState(UNIT_STAT_CASTING))
{
if(uint32 base_att = getAttackTimer(BASE_ATTACK))
setAttackTimer(BASE_ATTACK, (p_time >= base_att ? 0 : base_att - p_time) );
setAttackTimer(BASE_ATTACK, (p_time >= base_att ? 0 : base_att - p_time));
if(uint32 ranged_att = getAttackTimer(RANGED_ATTACK))
setAttackTimer(RANGED_ATTACK, (p_time >= ranged_att ? 0 : ranged_att - p_time) );
setAttackTimer(RANGED_ATTACK, (p_time >= ranged_att ? 0 : ranged_att - p_time));
if(uint32 off_att = getAttackTimer(OFF_ATTACK))
setAttackTimer(OFF_ATTACK, (p_time >= off_att ? 0 : off_att - p_time) );
setAttackTimer(OFF_ATTACK, (p_time >= off_att ? 0 : off_att - p_time));
}
// update abilities available only for fraction of time
@@ -4131,7 +4134,7 @@ void Unit::RemoveAllAuras()
void Unit::RemoveAllAuras(uint64 casterGUID, Aura * except /*=NULL*/, bool negative /*=true*/, bool positive /*=true*/)
{
for (AuraMap::iterator iter = m_Auras.begin(); iter != m_Auras.end(); )
for (AuraMap::iterator iter = m_Auras.begin(); iter != m_Auras.end();)
{
if (iter->second != except && (!casterGUID || iter->second->GetCasterGUID()==casterGUID)
&& ((negative && !iter->second->IsPositive()) || (positive && iter->second->IsPositive())))
@@ -8865,20 +8868,20 @@ int32 Unit::DealHeal(Unit *pVictim, uint32 addhealth, SpellEntry const *spellPro
Unit* Unit::SelectMagnetTarget(Unit *victim, SpellEntry const *spellInfo)
{
if(!victim)
if (!victim)
return NULL;
// Magic case
if(spellInfo && (spellInfo->DmgClass == SPELL_DAMAGE_CLASS_NONE || spellInfo->DmgClass == SPELL_DAMAGE_CLASS_MAGIC))
if (spellInfo && (spellInfo->DmgClass == SPELL_DAMAGE_CLASS_NONE || spellInfo->DmgClass == SPELL_DAMAGE_CLASS_MAGIC))
{
//I am not sure if this should be redirected.
if(spellInfo->DmgClass == SPELL_DAMAGE_CLASS_NONE)
if (spellInfo->DmgClass == SPELL_DAMAGE_CLASS_NONE)
return victim;
Unit::AuraEffectList const& magnetAuras = victim->GetAurasByType(SPELL_AURA_SPELL_MAGNET);
for (Unit::AuraEffectList::const_iterator itr = magnetAuras.begin(); itr != magnetAuras.end(); ++itr)
if(Unit* magnet = (*itr)->GetParentAura()->GetUnitSource())
if(magnet->isAlive())
if (Unit* magnet = (*itr)->GetParentAura()->GetUnitSource())
if (magnet->isAlive())
{
(*itr)->GetParentAura()->DropAuraCharge();
return magnet;
@@ -8889,9 +8892,9 @@ Unit* Unit::SelectMagnetTarget(Unit *victim, SpellEntry const *spellInfo)
{
AuraEffectList const& hitTriggerAuras = victim->GetAurasByType(SPELL_AURA_ADD_CASTER_HIT_TRIGGER);
for (AuraEffectList::const_iterator i = hitTriggerAuras.begin(); i != hitTriggerAuras.end(); ++i)
if(Unit* magnet = (*i)->GetParentAura()->GetUnitSource())
if(magnet->isAlive() && magnet->IsWithinLOSInMap(this))
if(roll_chance_i((*i)->GetAmount()))
if (Unit* magnet = (*i)->GetParentAura()->GetUnitSource())
if (magnet->isAlive() && magnet->IsWithinLOSInMap(this))
if (roll_chance_i((*i)->GetAmount()))
{
(*i)->GetParentAura()->DropAuraCharge();
return magnet;
@@ -8905,42 +8908,35 @@ Unit* Unit::GetFirstControlled() const
{
//Sequence: charmed, pet, other guardians
Unit *unit = GetCharm();
if(!unit)
{
if(uint64 guid = GetUInt64Value(UNIT_FIELD_SUMMON))
if (!unit)
if (uint64 guid = GetUInt64Value(UNIT_FIELD_SUMMON))
unit = ObjectAccessor::GetUnit(*this, guid);
}
return unit;
}
void Unit::RemoveAllControlled()
{
//possessed pet and vehicle
if(GetTypeId() == TYPEID_PLAYER)
if (GetTypeId() == TYPEID_PLAYER)
((Player*)this)->StopCastingCharm();
while(!m_Controlled.empty())
while (!m_Controlled.empty())
{
Unit *target = *m_Controlled.begin();
m_Controlled.erase(m_Controlled.begin());
if(target->GetCharmerGUID() == GetGUID())
{
target->RemoveCharmAuras();
}
else if(target->GetOwnerGUID() == GetGUID() && target->isSummon())
{
else if (target->GetOwnerGUID() == GetGUID() && target->isSummon())
((TempSummon*)target)->UnSummon();
}
else
{
sLog.outError("Unit %u is trying to release unit %u which is neither charmed nor owned by it", GetEntry(), target->GetEntry());
}
}
if(GetPetGUID())
if (GetPetGUID())
sLog.outCrash("Unit %u is not able to release its pet " I64FMT, GetEntry(), GetPetGUID());
if(GetMinionGUID())
if (GetMinionGUID())
sLog.outCrash("Unit %u is not able to release its minion " I64FMT, GetEntry(), GetMinionGUID());
if(GetCharmGUID())
if (GetCharmGUID())
sLog.outCrash("Unit %u is not able to release its charm " I64FMT, GetEntry(), GetCharmGUID());
}
@@ -8951,7 +8947,7 @@ Unit* Unit::GetNextRandomRaidMemberOrPet(float radius)
player = (Player*)this;
// Should we enable this also for charmed units?
else if (GetTypeId() == TYPEID_UNIT && ((Creature*)this)->isPet())
player=(Player*)GetOwner();
player = (Player*)GetOwner();
if (!player)
return NULL;
@@ -11154,14 +11150,14 @@ void Unit::SetHover(bool on)
void Unit::setDeathState(DeathState s)
{
if (s != ALIVE && s!= JUST_ALIVED)
if (s != ALIVE && s != JUST_ALIVED)
{
CombatStop();
DeleteThreatList();
getHostilRefManager().deleteReferences();
ClearComboPointHolders(); // any combo points pointed to unit lost at it death
if(IsNonMeleeSpellCasted(false))
if (IsNonMeleeSpellCasted(false))
InterruptNonMeleeSpells(false);
UnsummonAllTotems();
@@ -11184,10 +11180,8 @@ void Unit::setDeathState(DeathState s)
//do not why since in IncreaseMaxHealth currenthealth is checked
SetHealth(0);
}
else if(s == JUST_ALIVED)
{
else if (s == JUST_ALIVED)
RemoveFlag (UNIT_FIELD_FLAGS, UNIT_FLAG_SKINNABLE); // clear skinnable for creature and player (at battleground)
}
if (m_deathState != ALIVE && s == ALIVE)
{