mirror of
https://github.com/mod-playerbots/azerothcore-wotlk.git
synced 2026-01-21 20:56:23 +00:00
Merge branch 'azerothcore:master' into Playerbot
This commit is contained in:
@@ -4502,8 +4502,7 @@ void SmartScript::ProcessEvent(SmartScriptHolder& e, Unit* unit, uint32 var0, ui
|
||||
if (!me || !me->IsInCombat())
|
||||
return;
|
||||
|
||||
ObjectList* _targets = nullptr;
|
||||
|
||||
Unit* target = nullptr;
|
||||
switch (e.GetTargetType())
|
||||
{
|
||||
case SMART_TARGET_CREATURE_RANGE:
|
||||
@@ -4513,33 +4512,36 @@ void SmartScript::ProcessEvent(SmartScriptHolder& e, Unit* unit, uint32 var0, ui
|
||||
case SMART_TARGET_CLOSEST_PLAYER:
|
||||
case SMART_TARGET_PLAYER_RANGE:
|
||||
case SMART_TARGET_PLAYER_DISTANCE:
|
||||
_targets = GetTargets(e);
|
||||
{
|
||||
ObjectList* targets = GetTargets(e);
|
||||
if (!targets)
|
||||
return;
|
||||
for (WorldObject* target : *targets)
|
||||
{
|
||||
if (IsUnit(target) && me->IsFriendlyTo(target->ToUnit()) && target->ToUnit()->IsAlive() && target->ToUnit()->IsInCombat())
|
||||
{
|
||||
uint32 healthPct = uint32(target->ToUnit()->GetHealthPct());
|
||||
if (healthPct > e.event.friendlyHealthPct.maxHpPct || healthPct < e.event.friendlyHealthPct.minHpPct)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
target = target->ToUnit();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
delete targets;
|
||||
break;
|
||||
}
|
||||
case SMART_TARGET_SELF:
|
||||
case SMART_TARGET_ACTION_INVOKER:
|
||||
target = DoSelectLowestHpPercentFriendly((float)e.event.friendlyHealthPct.radius, e.event.friendlyHealthPct.minHpPct, e.event.friendlyHealthPct.maxHpPct);
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
|
||||
if (!_targets)
|
||||
return;
|
||||
|
||||
Unit* target = nullptr;
|
||||
|
||||
for (ObjectList::const_iterator itr = _targets->begin(); itr != _targets->end(); ++itr)
|
||||
{
|
||||
if (IsUnit(*itr) && me->IsFriendlyTo((*itr)->ToUnit()) && (*itr)->ToUnit()->IsAlive() && (*itr)->ToUnit()->IsInCombat())
|
||||
{
|
||||
uint32 healthPct = uint32((*itr)->ToUnit()->GetHealthPct());
|
||||
|
||||
if (healthPct > e.event.friendlyHealthPct.maxHpPct || healthPct < e.event.friendlyHealthPct.minHpPct)
|
||||
continue;
|
||||
|
||||
target = (*itr)->ToUnit();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
delete _targets;
|
||||
|
||||
if (!target)
|
||||
return;
|
||||
|
||||
@@ -5033,6 +5035,20 @@ Unit* SmartScript::DoSelectLowestHpFriendly(float range, uint32 MinHPDiff)
|
||||
return unit;
|
||||
}
|
||||
|
||||
Unit* SmartScript::DoSelectLowestHpPercentFriendly(float range, uint32 minHpPct, uint32 maxHpPct) const
|
||||
{
|
||||
if (!me)
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Unit* unit = nullptr;
|
||||
Acore::MostHPPercentMissingInRange u_check(me, range, minHpPct, maxHpPct);
|
||||
Acore::UnitLastSearcher<Acore::MostHPPercentMissingInRange> searcher(me, unit, u_check);
|
||||
Cell::VisitGridObjects(me, searcher, range);
|
||||
return unit;
|
||||
}
|
||||
|
||||
void SmartScript::DoFindFriendlyCC(std::list<Creature*>& _list, float range)
|
||||
{
|
||||
if (!me)
|
||||
|
||||
@@ -85,6 +85,7 @@ public:
|
||||
void OnMoveInLineOfSight(Unit* who);
|
||||
|
||||
Unit* DoSelectLowestHpFriendly(float range, uint32 MinHPDiff);
|
||||
Unit* DoSelectLowestHpPercentFriendly(float range, uint32 minHpPct, uint32 maxHpPct) const;
|
||||
void DoFindFriendlyCC(std::list<Creature*>& _list, float range);
|
||||
void DoFindFriendlyMissingBuff(std::list<Creature*>& list, float range, uint32 spellid);
|
||||
Unit* DoFindClosestFriendlyInRange(float range, bool playerOnly);
|
||||
|
||||
@@ -1138,6 +1138,13 @@ bool SmartAIMgr::IsEventValid(SmartScriptHolder& e)
|
||||
case SMART_TARGET_PLAYER_RANGE:
|
||||
case SMART_TARGET_PLAYER_DISTANCE:
|
||||
break;
|
||||
case SMART_TARGET_SELF:
|
||||
case SMART_TARGET_ACTION_INVOKER:
|
||||
if (!NotNULL(e, e.event.friendlyHealthPct.radius))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
LOG_ERROR("sql.sql", "SmartAIMgr: Entry {} SourceType {} Event {} Action {} uses invalid target_type {}, skipped.", e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
|
||||
return false;
|
||||
|
||||
@@ -419,6 +419,7 @@ struct SmartEvent
|
||||
uint32 maxHpPct;
|
||||
uint32 repeatMin;
|
||||
uint32 repeatMax;
|
||||
uint32 radius;
|
||||
} friendlyHealthPct;
|
||||
|
||||
struct
|
||||
|
||||
@@ -500,6 +500,26 @@ bool Condition::Meets(ConditionSourceInfo& sourceInfo)
|
||||
condMeets = unit->HasAuraType(AuraType(ConditionValue1));
|
||||
break;
|
||||
}
|
||||
case CONDITION_STAND_STATE:
|
||||
{
|
||||
if (Unit* unit = object->ToUnit())
|
||||
{
|
||||
if (ConditionValue1 == 0)
|
||||
{
|
||||
condMeets = (unit->getStandState() == ConditionValue2);
|
||||
}
|
||||
else if (ConditionValue2 == 0)
|
||||
{
|
||||
condMeets = unit->IsStandState();
|
||||
}
|
||||
else if (ConditionValue2 == 1)
|
||||
{
|
||||
condMeets = unit->IsSitState();
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
case CONDITION_DIFFICULTY_ID:
|
||||
{
|
||||
condMeets = object->GetMap()->GetDifficulty() == ConditionValue1;
|
||||
@@ -721,6 +741,9 @@ uint32 Condition::GetSearcherTypeMaskForCondition()
|
||||
case CONDITION_HAS_AURA_TYPE:
|
||||
mask |= GRID_MAP_TYPE_MASK_CREATURE | GRID_MAP_TYPE_MASK_PLAYER;
|
||||
break;
|
||||
case CONDITION_STAND_STATE:
|
||||
mask |= GRID_MAP_TYPE_MASK_CREATURE | GRID_MAP_TYPE_MASK_PLAYER;
|
||||
break;
|
||||
case CONDITION_DIFFICULTY_ID:
|
||||
mask |= GRID_MAP_TYPE_MASK_ALL;
|
||||
break;
|
||||
@@ -1799,9 +1822,6 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond)
|
||||
case CONDITION_TERRAIN_SWAP:
|
||||
LOG_ERROR("sql.sql", "SourceEntry {} in `condition` table has a ConditionType that is not supported on 3.3.5a ({}), ignoring.", cond->SourceEntry, uint32(cond->ConditionType));
|
||||
return false;
|
||||
case CONDITION_STAND_STATE:
|
||||
LOG_ERROR("sql.sql", "SourceEntry {} in `condition` table has a ConditionType that is not yet supported on AzerothCore ({}), ignoring.", cond->SourceEntry, uint32(cond->ConditionType));
|
||||
return false;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -2383,6 +2403,28 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond)
|
||||
}
|
||||
break;
|
||||
}
|
||||
case CONDITION_STAND_STATE:
|
||||
{
|
||||
bool valid = false;
|
||||
switch (cond->ConditionValue1)
|
||||
{
|
||||
case 0:
|
||||
valid = cond->ConditionValue2 <= UNIT_STAND_STATE_SUBMERGED;
|
||||
break;
|
||||
case 1:
|
||||
valid = cond->ConditionValue2 <= 1;
|
||||
break;
|
||||
default:
|
||||
valid = false;
|
||||
break;
|
||||
}
|
||||
if (!valid)
|
||||
{
|
||||
LOG_ERROR("sql.sql", "CONDITION_STAND_STATE has non-existing stand state ({},{}), skipped.", cond->ConditionValue1, cond->ConditionValue2);
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case CONDITION_DIFFICULTY_ID:
|
||||
if (cond->ConditionValue1 >= MAX_DIFFICULTY)
|
||||
{
|
||||
|
||||
@@ -74,7 +74,7 @@ enum ConditionTypes
|
||||
CONDITION_REALM_ACHIEVEMENT = 39, // achievement_id 0 0 true if realm achievement is complete
|
||||
CONDITION_IN_WATER = 40, // 0 0 0 true if unit in water
|
||||
CONDITION_TERRAIN_SWAP = 41, // don't use on 3.3.5a
|
||||
CONDITION_STAND_STATE = 42, // TODO: NOT SUPPORTED YET
|
||||
CONDITION_STAND_STATE = 42, // stateType state 0 true if unit matches specified sitstate (0,x: has exactly state x; 1,0: any standing state; 1,1: any sitting state;)
|
||||
CONDITION_DAILY_QUEST_DONE = 43, // quest id 0 0 true if daily quest has been completed for the day
|
||||
CONDITION_CHARMED = 44, // 0 0 0 true if unit is currently charmed
|
||||
CONDITION_PET_TYPE = 45, // mask 0 0 true if player has a pet of given type(s)
|
||||
|
||||
@@ -787,6 +787,30 @@ namespace Acore
|
||||
uint32 i_hp;
|
||||
};
|
||||
|
||||
class MostHPPercentMissingInRange
|
||||
{
|
||||
public:
|
||||
MostHPPercentMissingInRange(Unit const* obj, float range, uint32 minHpPct, uint32 maxHpPct) :
|
||||
i_obj(obj), i_range(range), i_minHpPct(minHpPct), i_maxHpPct(maxHpPct), i_hpPct(101.f) { }
|
||||
|
||||
bool operator()(Unit* u)
|
||||
{
|
||||
if (u->IsAlive() && u->IsInCombat() && !i_obj->IsHostileTo(u) && i_obj->IsWithinDistInMap(u, i_range) &&
|
||||
i_minHpPct <= u->GetHealthPct() && u->GetHealthPct() <= i_maxHpPct && u->GetHealthPct() < i_hpPct)
|
||||
{
|
||||
i_hpPct = u->GetHealthPct();
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private:
|
||||
Unit const* i_obj;
|
||||
float i_range;
|
||||
float i_minHpPct, i_maxHpPct, i_hpPct;
|
||||
};
|
||||
|
||||
class FriendlyCCedInRange
|
||||
{
|
||||
public:
|
||||
|
||||
@@ -3808,13 +3808,6 @@ void Spell::EffectScriptEffect(SpellEffIndex effIndex)
|
||||
m_caster->CastSpell(unitTarget, 22682, true);
|
||||
return;
|
||||
}
|
||||
case 20589: // Escape artist
|
||||
case 30918: // Improved Sprint
|
||||
{
|
||||
// Removes snares and roots.
|
||||
unitTarget->RemoveMovementImpairingAuras(true);
|
||||
break;
|
||||
}
|
||||
// Plant Warmaul Ogre Banner
|
||||
case 32307:
|
||||
if (Player* caster = m_caster->ToPlayer())
|
||||
|
||||
@@ -49,8 +49,8 @@ enum Spells
|
||||
SPELL_CHROMATIC_MUT_1 = 23174, //Spell cast on player if they get all 5 debuffs
|
||||
|
||||
SPELL_ELEMENTAL_SHIELD = 22276,
|
||||
SPELL_FRENZY = 28371, //The frenzy spell may be wrong
|
||||
SPELL_ENRAGE = 28747
|
||||
SPELL_FRENZY = 23128,
|
||||
SPELL_ENRAGE = 23537
|
||||
};
|
||||
|
||||
enum Events
|
||||
@@ -239,7 +239,7 @@ public:
|
||||
// Cast new random vulnerabilty on self
|
||||
DoCast(me, SPELL_ELEMENTAL_SHIELD);
|
||||
Talk(EMOTE_SHIMMER);
|
||||
events.ScheduleEvent(EVENT_SHIMMER, 45000);
|
||||
events.ScheduleEvent(EVENT_SHIMMER, urand(17000, 25000));
|
||||
break;
|
||||
}
|
||||
case EVENT_BREATH_1:
|
||||
|
||||
@@ -62,7 +62,6 @@ public:
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
me->RemoveAurasDueToSpell(SPELL_MARK_OF_FROST_AURA);
|
||||
_scheduler.CancelAll();
|
||||
me->SetNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
me->RestoreFaction();
|
||||
@@ -71,7 +70,6 @@ public:
|
||||
if (p->GetZoneId() == me->GetZoneId())
|
||||
{
|
||||
|
||||
p->RemoveAurasDueToSpell(SPELL_MARK_OF_FROST);
|
||||
p->RemoveAurasDueToSpell(SPELL_AURA_OF_FROST);
|
||||
p->RemoveAurasDueToSpell(SPELL_CHILL);
|
||||
p->RemoveAurasDueToSpell(SPELL_FROST_BREATH);
|
||||
|
||||
@@ -664,8 +664,12 @@ public:
|
||||
{
|
||||
Map::PlayerList const& pList = instance->GetPlayers();
|
||||
for (Map::PlayerList::const_iterator itr = pList.begin(); itr != pList.end(); ++itr)
|
||||
if (Vehicle* veh = itr->GetSource()->GetVehicle())
|
||||
veh->Dismiss();
|
||||
{
|
||||
if (Creature* vehicleCreature = itr->GetSource()->GetVehicleCreatureBase())
|
||||
{
|
||||
vehicleCreature->DespawnOrUnsummon();
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case TYPE_IGNIS:
|
||||
@@ -837,8 +841,12 @@ public:
|
||||
{
|
||||
Map::PlayerList const& pList = instance->GetPlayers();
|
||||
for (Map::PlayerList::const_iterator itr = pList.begin(); itr != pList.end(); ++itr)
|
||||
if (Vehicle* veh = itr->GetSource()->GetVehicle())
|
||||
veh->Dismiss();
|
||||
{
|
||||
if (Creature* vehicleCreature = itr->GetSource()->GetVehicleCreatureBase())
|
||||
{
|
||||
vehicleCreature->DespawnOrUnsummon();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1239,9 +1247,12 @@ void instance_ulduar::instance_ulduar_InstanceMapScript::SpawnLeviathanEncounter
|
||||
if (!_leviathanVehicles.empty())
|
||||
{
|
||||
for (ObjectGuid const& guid : _leviathanVehicles)
|
||||
{
|
||||
if (Creature* cr = instance->GetCreature(guid))
|
||||
if (Vehicle* veh = cr->GetVehicleKit())
|
||||
veh->Dismiss();
|
||||
{
|
||||
cr->DespawnOrUnsummon();
|
||||
}
|
||||
}
|
||||
|
||||
_leviathanVehicles.clear();
|
||||
}
|
||||
|
||||
@@ -4389,6 +4389,23 @@ class spell_gen_arcane_charge : public SpellScript
|
||||
}
|
||||
};
|
||||
|
||||
// 20589 - Escape artist
|
||||
// 30918 - Improved Sprint
|
||||
class spell_gen_remove_impairing_auras : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_gen_remove_impairing_auras);
|
||||
|
||||
void HandleScriptEffect(SpellEffIndex /* effIndex */)
|
||||
{
|
||||
GetHitUnit()->RemoveMovementImpairingAuras(true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_gen_remove_impairing_auras::HandleScriptEffect, EFFECT_0, SPELL_EFFECT_SCRIPT_EFFECT);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_generic_spell_scripts()
|
||||
{
|
||||
RegisterSpellScript(spell_silithyst);
|
||||
@@ -4522,4 +4539,5 @@ void AddSC_generic_spell_scripts()
|
||||
RegisterSpellScript(spell_contagion_of_rot);
|
||||
RegisterSpellScript(spell_gen_holiday_buff_food);
|
||||
RegisterSpellScript(spell_gen_arcane_charge);
|
||||
RegisterSpellScript(spell_gen_remove_impairing_auras);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user