[svn] Improve TargetedMovement (TODO: let mob find "near angle" rather than "random angle").
Delete a repeated check in instance canenter(). Fix some spell targets. Add some sunwell spell sql. Fix Magtheridons earthquake. (TODO: need to find out why soul transfer has no effect when casted by mobs) Let Brutallus dual wield. Enable burn (still no script effect). Quick fix for shadowmoon valley illidan quest crash (wait for author's fix). --HG-- branch : trunk
This commit is contained in:
+8
-8
@@ -1419,13 +1419,6 @@ InstanceMap::~InstanceMap()
|
||||
*/
|
||||
bool InstanceMap::CanEnter(Player *player)
|
||||
{
|
||||
if(!player->isGameMaster() && i_data && i_data->IsEncounterInProgress())
|
||||
{
|
||||
sLog.outDebug("InstanceMap::CanEnter - Player '%s' can't enter instance '%s' while an encounter is in progress.", player->GetName(), GetMapName());
|
||||
player->SendTransferAborted(GetId(), TRANSFER_ABORT_ZONE_IN_COMBAT);
|
||||
return false;
|
||||
}
|
||||
|
||||
if(std::find(i_Players.begin(),i_Players.end(),player)!=i_Players.end())
|
||||
{
|
||||
sLog.outError("InstanceMap::CanEnter - player %s(%u) already in map %d,%d,%d!", player->GetName(), player->GetGUIDLow(), GetId(), GetInstanceId(), GetSpawnMode());
|
||||
@@ -1444,12 +1437,19 @@ bool InstanceMap::CanEnter(Player *player)
|
||||
|
||||
// cannot enter while players in the instance are in combat
|
||||
Group *pGroup = player->GetGroup();
|
||||
if(pGroup && pGroup->InCombatToInstance(GetInstanceId()) && player->isAlive() && player->GetMapId() != GetId())
|
||||
if(!player->isGameMaster() && pGroup && pGroup->InCombatToInstance(GetInstanceId()) && player->isAlive() && player->GetMapId() != GetId())
|
||||
{
|
||||
player->SendTransferAborted(GetId(), TRANSFER_ABORT_ZONE_IN_COMBAT);
|
||||
return false;
|
||||
}
|
||||
|
||||
/*if(!player->isGameMaster() && i_data && i_data->IsEncounterInProgress())
|
||||
{
|
||||
sLog.outDebug("InstanceMap::CanEnter - Player '%s' can't enter instance '%s' while an encounter is in progress.", player->GetName(), GetMapName());
|
||||
player->SendTransferAborted(GetId(), TRANSFER_ABORT_ZONE_IN_COMBAT);
|
||||
return false;
|
||||
}*/
|
||||
|
||||
return Map::CanEnter(player);
|
||||
}
|
||||
|
||||
|
||||
+1
-11
@@ -1531,14 +1531,4 @@ void WorldObject::GetNearPoint(WorldObject const* searcher, float &x, float &y,
|
||||
z = GetPositionZ();
|
||||
|
||||
UpdateGroundPositionZ(x,y,z);
|
||||
}
|
||||
|
||||
void WorldObject::GetRandomContactPoint( const WorldObject* obj, float &x, float &y, float &z, float distance2dMin, float distance2dMax ) const
|
||||
{
|
||||
float object_size = obj->GetObjectSize();//here we use object_size to determine the angle offset, the bigger object the smaller angle offset, then this makes mob move naturally in visual.
|
||||
//let assume 12.0f is the max size for object to have 0 angle offset.
|
||||
float angle_offset_ratio = 1 - object_size/12.0f;
|
||||
if (angle_offset_ratio < 0.05) angle_offset_ratio = 0.05;
|
||||
// angle to face `obj` to `this`plus a random angle offset(from -90 degree to 90 degree)*angle_offset_ratio using distance from distance2dMin to distance2dMax includes size of `obj`
|
||||
GetNearPoint(obj,x,y,z,object_size,distance2dMin+(distance2dMax-distance2dMin)*rand_norm(), GetAngle( obj ) + (M_PI/2 - M_PI * rand_norm()) * angle_offset_ratio);
|
||||
}
|
||||
}
|
||||
@@ -377,7 +377,6 @@ class TRINITY_DLL_SPEC WorldObject : public Object
|
||||
// angle to face `obj` to `this` using distance includes size of `obj`
|
||||
GetNearPoint(obj,x,y,z,obj->GetObjectSize(),distance2d,GetAngle( obj ));
|
||||
}
|
||||
void GetRandomContactPoint( const WorldObject* obj, float &x, float &y, float &z, float distance2dMin, float distance2dMax ) const;
|
||||
|
||||
float GetObjectSize() const
|
||||
{
|
||||
|
||||
+4
-4
@@ -1443,7 +1443,6 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||
break;
|
||||
|
||||
// area targets
|
||||
case TARGET_AREAEFFECT_CUSTOM:
|
||||
case TARGET_ALL_ENEMY_IN_AREA_INSTANT:
|
||||
if(m_spellInfo->Effect[i] == SPELL_EFFECT_PERSISTENT_AREA_AURA)
|
||||
break;
|
||||
@@ -1456,15 +1455,16 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||
case TARGET_ALL_FRIENDLY_UNITS_AROUND_CASTER:
|
||||
SearchAreaTarget(TagUnitMap, radius, PUSH_DEST_CENTER, SPELL_TARGETS_FRIENDLY);
|
||||
break;
|
||||
//case TARGET_AREAEFFECT_CUSTOM:
|
||||
// m_targets.m_targetMask |= TARGET_FLAG_DEST_LOCATION;
|
||||
case TARGET_AREAEFFECT_CUSTOM:
|
||||
m_targets.m_targetMask |= TARGET_FLAG_DEST_LOCATION;
|
||||
case TARGET_UNIT_AREA_ENTRY:
|
||||
{
|
||||
SpellScriptTarget::const_iterator lower = spellmgr.GetBeginSpellScriptTarget(m_spellInfo->Id);
|
||||
SpellScriptTarget::const_iterator upper = spellmgr.GetEndSpellScriptTarget(m_spellInfo->Id);
|
||||
if(lower==upper)
|
||||
{
|
||||
sLog.outErrorDb("Spell (ID: %u) has effect EffectImplicitTargetA/EffectImplicitTargetB = TARGET_SCRIPT, but does not have record in `spell_script_target`",m_spellInfo->Id);
|
||||
SearchAreaTarget(TagUnitMap, radius, PUSH_DEST_CENTER, SPELL_TARGETS_AOE_DAMAGE);
|
||||
//sLog.outErrorDb("Spell (ID: %u) has effect EffectImplicitTargetA/EffectImplicitTargetB = TARGET_SCRIPT, but does not have record in `spell_script_target`",m_spellInfo->Id);
|
||||
break;
|
||||
}
|
||||
// let it be done in one check?
|
||||
|
||||
@@ -1982,24 +1982,10 @@ void Spell::EffectTeleportUnits(uint32 i)
|
||||
((Player*)unitTarget)->TeleportTo(((Player*)unitTarget)->m_homebindMapId,((Player*)unitTarget)->m_homebindX,((Player*)unitTarget)->m_homebindY,((Player*)unitTarget)->m_homebindZ,unitTarget->GetOrientation(),unitTarget==m_caster ? TELE_TO_SPELL : 0);
|
||||
return;
|
||||
}
|
||||
case TARGET_TABLE_X_Y_Z_COORDINATES:
|
||||
{
|
||||
// TODO: Only players can teleport?
|
||||
if (unitTarget->GetTypeId() != TYPEID_PLAYER)
|
||||
return;
|
||||
SpellTargetPosition const* st = spellmgr.GetSpellTargetPosition(m_spellInfo->Id);
|
||||
if(!st)
|
||||
{
|
||||
sLog.outError( "Spell::EffectTeleportUnits - unknown Teleport coordinates for spell ID %u\n", m_spellInfo->Id );
|
||||
return;
|
||||
}
|
||||
((Player*)unitTarget)->TeleportTo(st->target_mapId,st->target_X,st->target_Y,st->target_Z,st->target_Orientation,unitTarget==m_caster ? TELE_TO_SPELL : 0);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
// If not exist data for dest location - return
|
||||
if(!(m_targets.m_targetMask & TARGET_FLAG_DEST_LOCATION))
|
||||
if(!m_targets.HasDest())
|
||||
{
|
||||
sLog.outError( "Spell::EffectTeleportUnits - unknown EffectImplicitTargetB[%u] = %u for spell ID %u\n", i, m_spellInfo->EffectImplicitTargetB[i], m_spellInfo->Id );
|
||||
return;
|
||||
|
||||
@@ -60,7 +60,7 @@ TargetedMovementGenerator<T>::_setTargetLocation(T &owner)
|
||||
if(!i_offset)
|
||||
{
|
||||
// to nearest random contact position
|
||||
i_target->GetRandomContactPoint( &owner, x, y, z,0.5f,4.5f );
|
||||
i_target->GetRandomContactPoint( &owner, x, y, z, 0.5f, ATTACK_DISTANCE - 0.5f );
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -164,7 +164,7 @@ TargetedMovementGenerator<T>::Update(T &owner, const uint32 & time_diff)
|
||||
if (owner.GetObjectSize())
|
||||
i_destinationHolder.ResetUpdate(50);
|
||||
|
||||
float dist = i_target->GetObjectSize() + owner.GetObjectSize() + sWorld.getRate(RATE_TARGET_POS_RECALCULATION_RANGE);
|
||||
float dist = owner.GetFloatValue(UNIT_FIELD_COMBATREACH) + i_target.getTarget()->GetFloatValue(UNIT_FIELD_COMBATREACH) + sWorld.getRate(RATE_TARGET_POS_RECALCULATION_RANGE);
|
||||
|
||||
//More distance let have better performance, less distance let have more sensitive reaction at target move.
|
||||
|
||||
@@ -185,7 +185,7 @@ TargetedMovementGenerator<T>::Update(T &owner, const uint32 & time_diff)
|
||||
owner.SetInFront(i_target.getTarget());
|
||||
|
||||
owner.StopMoving();
|
||||
if(owner.canReachWithAttack(i_target.getTarget()) && !owner.hasUnitState(UNIT_STAT_FOLLOW))
|
||||
if(owner.IsWithinCombatDist(i_target.getTarget(), ATTACK_DISTANCE) && !owner.hasUnitState(UNIT_STAT_FOLLOW))
|
||||
owner.Attack(i_target.getTarget(),true);
|
||||
}
|
||||
}
|
||||
|
||||
+9
-1
@@ -420,12 +420,20 @@ bool Unit::IsWithinCombatDist(Unit *obj, float dist2compare) const
|
||||
float dz = GetPositionZ() - obj->GetPositionZ();
|
||||
float distsq = dx*dx + dy*dy + dz*dz;
|
||||
//not sure here, or combatreach + combatreach?
|
||||
float sizefactor = GetObjectSize() + obj->GetFloatValue(UNIT_FIELD_COMBATREACH);
|
||||
float sizefactor = GetFloatValue(UNIT_FIELD_COMBATREACH) + obj->GetFloatValue(UNIT_FIELD_COMBATREACH);
|
||||
float maxdist = dist2compare + sizefactor;
|
||||
|
||||
return distsq < maxdist * maxdist;
|
||||
}
|
||||
|
||||
void Unit::GetRandomContactPoint( const Unit* obj, float &x, float &y, float &z, float distance2dMin, float distance2dMax ) const
|
||||
{
|
||||
uint32 attacker_number = getAttackers().size();
|
||||
if(attacker_number > 0) --attacker_number;
|
||||
GetNearPoint(obj,x,y,z,obj->GetFloatValue(UNIT_FIELD_COMBATREACH),distance2dMin+(distance2dMax-distance2dMin)*rand_norm()
|
||||
, GetAngle(obj) + (attacker_number ? (M_PI/2 - M_PI * rand_norm()) * (float)attacker_number / GetFloatValue(UNIT_FIELD_COMBATREACH) / 3 : 0));
|
||||
}
|
||||
|
||||
void Unit::RemoveSpellsCausingAura(AuraType auraType)
|
||||
{
|
||||
if (auraType >= TOTAL_AURAS) return;
|
||||
|
||||
@@ -721,6 +721,7 @@ class TRINITY_DLL_SPEC Unit : public WorldObject
|
||||
void SetCanDualWield(bool value) { m_canDualWield = value; }
|
||||
bool canReachWithAttack(Unit *pVictim) const;
|
||||
bool IsWithinCombatDist(Unit *obj, float dist2compare) const;
|
||||
void GetRandomContactPoint( const Unit* target, float &x, float &y, float &z, float distance2dMin, float distance2dMax ) const;
|
||||
uint32 m_extraAttacks;
|
||||
bool m_canDualWield;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user