diff options
author | Shauren <shauren.trinity@gmail.com> | 2022-01-15 23:30:00 +0100 |
---|---|---|
committer | Shauren <shauren.trinity@gmail.com> | 2022-01-15 23:30:00 +0100 |
commit | bf357312e0c4d0a68a95379ecdcbed817b136c31 (patch) | |
tree | 4aef1149d2e23aa816ddafe7a74500236072c838 /src | |
parent | bff5ae51fec8bfb5ca28ea65866bed9558e6f8ae (diff) |
Core/Conditions: Implemented many more UnitCondition types
Diffstat (limited to 'src')
-rw-r--r-- | src/server/game/Conditions/ConditionMgr.cpp | 134 | ||||
-rw-r--r-- | src/server/game/DataStores/DBCEnums.h | 92 |
2 files changed, 134 insertions, 92 deletions
diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index 4f68ce82535..cba55f5e126 100644 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -34,6 +34,7 @@ #include "Log.h" #include "LootMgr.h" #include "Map.h" +#include "ObjectAccessor.h" #include "ObjectMgr.h" #include "PhasingHandler.h" #include "Player.h" @@ -42,7 +43,9 @@ #include "Realm.h" #include "ReputationMgr.h" #include "ScriptMgr.h" +#include "Spell.h" #include "SpellAuras.h" +#include "SpellAuraEffects.h" #include "SpellMgr.h" #include "World.h" #include "WorldSession.h" @@ -3651,33 +3654,44 @@ int32 GetUnitConditionVariable(Unit const* unit, Unit const* otherUnit, UnitCond case UnitConditionVariable::DamageArcanePct: break; case UnitConditionVariable::InCombat: - break; + return unit->IsInCombat(); case UnitConditionVariable::IsMoving: - break; + return unit->HasUnitMovementFlag(MOVEMENTFLAG_FORWARD | MOVEMENTFLAG_BACKWARD | MOVEMENTFLAG_STRAFE_LEFT | MOVEMENTFLAG_STRAFE_RIGHT); case UnitConditionVariable::IsCasting: - break; - case UnitConditionVariable::IsCastingSpell: - break; + case UnitConditionVariable::IsCastingSpell: // this is supposed to return spell id by client code but data always has 0 or 1 + return unit->GetCurrentSpell(CURRENT_GENERIC_SPELL) != nullptr; case UnitConditionVariable::IsChanneling: - break; - case UnitConditionVariable::IsChannelingSpell: - break; + case UnitConditionVariable::IsChannelingSpell: // this is supposed to return spell id by client code but data always has 0 or 1 + return unit->GetChannelSpellId() != 0; case UnitConditionVariable::NumberOfMeleeAttackers: - break; + return std::count_if(unit->getAttackers().begin(), unit->getAttackers().end(), [unit](Unit* attacker) + { + float distance = std::max(unit->GetCombatReach() + attacker->GetCombatReach() + 1.3333334f, 5.0f); + if (unit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED) || attacker->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED)) + distance += 1.0f; + return unit->GetExactDistSq(attacker) < distance * distance; + }); case UnitConditionVariable::IsAttackingMe: - break; + return otherUnit && unit->GetTarget() == otherUnit->GetGUID(); case UnitConditionVariable::Range: - break; + return otherUnit ? int32(unit->GetExactDist(otherUnit)) : 0; case UnitConditionVariable::InMeleeRange: - break; + if (otherUnit) + { + float distance = std::max(unit->GetCombatReach() + otherUnit->GetCombatReach() + 1.3333334f, 5.0f); + if (unit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED) || otherUnit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED)) + distance += 1.0f; + return unit->GetExactDistSq(otherUnit) < distance * distance; + } + return 0; case UnitConditionVariable::PursuitTime: break; case UnitConditionVariable::HasHarmfulAuraCanceledByDamage: - break; + return unit->HasNegativeAuraWithInterruptFlag(SpellAuraInterruptFlags::Damage); case UnitConditionVariable::HasHarmfulAuraWithPeriodicDamage: - break; + return unit->HasAuraType(SPELL_AURA_PERIODIC_DAMAGE); case UnitConditionVariable::NumberOfEnemies: - break; + return unit->GetThreatManager().GetThreatListSize(); case UnitConditionVariable::NumberOfFriends: break; case UnitConditionVariable::ThreatPhysicalPct: @@ -3697,25 +3711,48 @@ int32 GetUnitConditionVariable(Unit const* unit, Unit const* otherUnit, UnitCond case UnitConditionVariable::IsInterruptible: break; case UnitConditionVariable::NumberOfAttackers: - break; + return unit->getAttackers().size(); case UnitConditionVariable::NumberOfRangedAttackers: - break; + return std::count_if(unit->getAttackers().begin(), unit->getAttackers().end(), [unit](Unit* attacker) + { + float distance = std::max(unit->GetCombatReach() + attacker->GetCombatReach() + 1.3333334f, 5.0f); + if (unit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED) || attacker->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED)) + distance += 1.0f; + return unit->GetExactDistSq(attacker) >= distance * distance; + }); case UnitConditionVariable::CreatureType: - break; + return unit->GetCreatureType(); case UnitConditionVariable::IsMeleeAttacking: - break; + if (Unit const* target = ObjectAccessor::GetUnit(*unit, unit->GetTarget())) + { + float distance = std::max(unit->GetCombatReach() + target->GetCombatReach() + 1.3333334f, 5.0f); + if (unit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED) || target->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED)) + distance += 1.0f; + return unit->GetExactDistSq(target) < distance * distance; + } + return 0; case UnitConditionVariable::IsRangedAttacking: - break; + if (Unit const* target = ObjectAccessor::GetUnit(*unit, unit->GetTarget())) + { + float distance = std::max(unit->GetCombatReach() + target->GetCombatReach() + 1.3333334f, 5.0f); + if (unit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED) || target->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED)) + distance += 1.0f; + return unit->GetExactDistSq(target) >= distance * distance; + } + return 0; case UnitConditionVariable::Health: - break; + return unit->GetHealth(); case UnitConditionVariable::SpellKnown: - break; + return unit->HasSpell(value) ? value : 0; case UnitConditionVariable::HasHarmfulAuraEffect: - break; + return value >= 0 && value < int32(TOTAL_AURAS) && std::find_if(unit->GetAuraEffectsByType(AuraType(value)).begin(), unit->GetAuraEffectsByType(AuraType(value)).end(), [unit](AuraEffect const* aurEff) + { + return (aurEff->GetBase()->GetApplicationOfTarget(unit->GetGUID())->GetFlags() & AFLAG_NEGATIVE) != 0; + }) != unit->GetAuraEffectsByType(AuraType(value)).end(); case UnitConditionVariable::IsImmuneToAreaOfEffect: break; case UnitConditionVariable::IsPlayer: - break; + return unit->IsPlayer(); case UnitConditionVariable::DamageMagicPct: break; case UnitConditionVariable::DamageTotalPct: @@ -3727,57 +3764,62 @@ int32 GetUnitConditionVariable(Unit const* unit, Unit const* otherUnit, UnitCond case UnitConditionVariable::HasCritter: return !unit->GetCritterGUID().IsEmpty(); case UnitConditionVariable::HasTotemInSlot1: - break; + return !unit->m_SummonSlot[SUMMON_SLOT_TOTEM].IsEmpty(); case UnitConditionVariable::HasTotemInSlot2: - break; + return !unit->m_SummonSlot[SUMMON_SLOT_TOTEM_2].IsEmpty(); case UnitConditionVariable::HasTotemInSlot3: - break; + return !unit->m_SummonSlot[SUMMON_SLOT_TOTEM_3].IsEmpty(); case UnitConditionVariable::HasTotemInSlot4: - break; + return !unit->m_SummonSlot[SUMMON_SLOT_TOTEM_4].IsEmpty(); case UnitConditionVariable::HasTotemInSlot5: break; case UnitConditionVariable::Creature: - break; + return unit->GetEntry(); case UnitConditionVariable::StringID: break; case UnitConditionVariable::HasAura: - break; + return unit->HasAura(value) ? value : 0; case UnitConditionVariable::IsEnemy: - break; + return otherUnit && unit->GetReactionTo(otherUnit) <= REP_HOSTILE; case UnitConditionVariable::IsSpecMelee: - break; + return unit->IsPlayer() && sChrSpecializationStore.AssertEntry(unit->ToPlayer()->GetPrimarySpecialization())->Flags & CHR_SPECIALIZATION_FLAG_MELEE; case UnitConditionVariable::IsSpecTank: - break; + return unit->IsPlayer() && sChrSpecializationStore.AssertEntry(unit->ToPlayer()->GetPrimarySpecialization())->Role == 0; case UnitConditionVariable::IsSpecRanged: - break; + return unit->IsPlayer() && sChrSpecializationStore.AssertEntry(unit->ToPlayer()->GetPrimarySpecialization())->Flags & CHR_SPECIALIZATION_FLAG_RANGED; case UnitConditionVariable::IsSpecHealer: - break; + return unit->IsPlayer() && sChrSpecializationStore.AssertEntry(unit->ToPlayer()->GetPrimarySpecialization())->Role == 1; case UnitConditionVariable::IsPlayerControlledNPC: - break; + return unit->IsCreature() && unit->HasUnitFlag(UNIT_FLAG_PLAYER_CONTROLLED); case UnitConditionVariable::IsDying: - break; + return unit->GetHealth() == 0; case UnitConditionVariable::PathFailCount: break; case UnitConditionVariable::IsMounted: - break; + return unit->GetMountDisplayId() != 0; case UnitConditionVariable::Label: break; case UnitConditionVariable::IsMySummon: - break; + return otherUnit && (otherUnit->GetCharmerGUID() == unit->GetGUID() || otherUnit->GetCreatorGUID() == unit->GetGUID()); case UnitConditionVariable::IsSummoner: - break; + return otherUnit && (unit->GetCharmerGUID() == otherUnit->GetGUID() || unit->GetCreatorGUID() == otherUnit->GetGUID()); case UnitConditionVariable::IsMyTarget: - break; + return otherUnit && unit->GetTarget() == otherUnit->GetGUID(); case UnitConditionVariable::Sex: - break; + return unit->GetGender(); case UnitConditionVariable::LevelWithinContentTuning: - break; + if (Optional<ContentTuningLevels> levelRange = sDB2Manager.GetContentTuningData(value, 0)) + return unit->GetLevel() >= levelRange->MinLevel && unit->GetLevel() <= levelRange->MaxLevel ? value : 0; + return 0; case UnitConditionVariable::IsFlying: - break; + return unit->IsFlying(); case UnitConditionVariable::IsHovering: - break; + return unit->IsHovering(); case UnitConditionVariable::HasHelpfulAuraEffect: - break; + return value >= 0 && value < int32(TOTAL_AURAS) && std::find_if(unit->GetAuraEffectsByType(AuraType(value)).begin(), unit->GetAuraEffectsByType(AuraType(value)).end(), [unit](AuraEffect const* aurEff) + { + return (aurEff->GetBase()->GetApplicationOfTarget(unit->GetGUID())->GetFlags() & AFLAG_NEGATIVE) == 0; + }) != unit->GetAuraEffectsByType(AuraType(value)).end(); case UnitConditionVariable::HasHelpfulAuraSchool: return unit->GetAuraApplication([value](AuraApplication const* aurApp) { diff --git a/src/server/game/DataStores/DBCEnums.h b/src/server/game/DataStores/DBCEnums.h index c6dd8266cd6..534fb9b0861 100644 --- a/src/server/game/DataStores/DBCEnums.h +++ b/src/server/game/DataStores/DBCEnums.h @@ -1744,20 +1744,20 @@ enum class UnitConditionVariable : uint8 DamageFrostPct = 28, // NYI Damage (Frost) {$Relative Op} {#Frost Damage %}% DamageShadowPct = 29, // NYI Damage (Shadow) {$Relative Op} {#Shadow Damage %}% DamageArcanePct = 30, // NYI Damage (Arcane) {$Relative Op} {#Arcane Damage %}% - InCombat = 31, // NYI In combat? {$Yes/No}{=1} - IsMoving = 32, // NYI Is moving? {$Yes/No}{=1} - IsCasting = 33, // NYI Is casting? {$Yes/No}{=1} - IsCastingSpell = 34, // NYI Is casting spell? {$Yes/No}{=1} - IsChanneling = 35, // NYI Is channeling? {$Yes/No}{=1} - IsChannelingSpell = 36, // NYI Is channeling spell? {$Yes/No}{=1} - NumberOfMeleeAttackers = 37, // NYI Number of melee attackers {$Relative Op} {#Attackers} - IsAttackingMe = 38, // NYI Is attacking me? {$Yes/No}{=1} - Range = 39, // NYI Range {$Relative Op} {#Yards} - InMeleeRange = 40, // NYI In melee range? {$Yes/No}{=1} + InCombat = 31, // In combat? {$Yes/No}{=1} + IsMoving = 32, // Is moving? {$Yes/No}{=1} + IsCasting = 33, // Is casting? {$Yes/No}{=1} + IsCastingSpell = 34, // Is casting spell? {$Yes/No}{=1} + IsChanneling = 35, // Is channeling? {$Yes/No}{=1} + IsChannelingSpell = 36, // Is channeling spell? {$Yes/No}{=1} + NumberOfMeleeAttackers = 37, // Number of melee attackers {$Relative Op} {#Attackers} + IsAttackingMe = 38, // Is attacking me? {$Yes/No}{=1} + Range = 39, // Range {$Relative Op} {#Yards} + InMeleeRange = 40, // In melee range? {$Yes/No}{=1} PursuitTime = 41, // NYI Pursuit time {$Relative Op} {#Seconds} - HasHarmfulAuraCanceledByDamage = 42, // NYI Has harmful aura canceled by damage? {$Yes/No}{=1} - HasHarmfulAuraWithPeriodicDamage = 43, // NYI Has harmful aura with periodic damage? {$Yes/No}{=1} - NumberOfEnemies = 44, // NYI Number of enemies {$Relative Op} {#Enemies} + HasHarmfulAuraCanceledByDamage = 42, // Has harmful aura canceled by damage? {$Yes/No}{=1} + HasHarmfulAuraWithPeriodicDamage = 43, // Has harmful aura with periodic damage? {$Yes/No}{=1} + NumberOfEnemies = 44, // Number of enemies {$Relative Op} {#Enemies} NumberOfFriends = 45, // NYI Number of friends {$Relative Op} {#Friends} ThreatPhysicalPct = 46, // NYI Threat (Physical) {$Relative Op} {#Physical Threat %}% ThreatHolyPct = 47, // NYI Threat (Holy) {$Relative Op} {#Holy Threat %}% @@ -1767,48 +1767,48 @@ enum class UnitConditionVariable : uint8 ThreatShadowPct = 51, // NYI Threat (Shadow) {$Relative Op} {#Shadow Threat %}% ThreatArcanePct = 52, // NYI Threat (Arcane) {$Relative Op} {#Arcane Threat %}% IsInterruptible = 53, // NYI Is interruptible? {$Yes/No}{=1} - NumberOfAttackers = 54, // NYI Number of attackers {$Relative Op} {#Attackers} - NumberOfRangedAttackers = 55, // NYI Number of ranged attackers {$Relative Op} {#Ranged Attackers} - CreatureType = 56, // NYI Creature type {$Is/Is Not} "{CreatureType}" - IsMeleeAttacking = 57, // NYI Is melee-attacking? {$Yes/No}{=1} - IsRangedAttacking = 58, // NYI Is ranged-attacking? {$Yes/No}{=1} - Health = 59, // NYI Health {$Relative Op} {#HP} HP - SpellKnown = 60, // NYI Spell known? {$Yes/No} "{Spell}" - HasHarmfulAuraEffect = 61, // NYI Has harmful aura effect? {$Yes/No} "{#Spell Aura}" + NumberOfAttackers = 54, // Number of attackers {$Relative Op} {#Attackers} + NumberOfRangedAttackers = 55, // Number of ranged attackers {$Relative Op} {#Ranged Attackers} + CreatureType = 56, // Creature type {$Is/Is Not} "{CreatureType}" + IsMeleeAttacking = 57, // Is melee-attacking? {$Yes/No}{=1} + IsRangedAttacking = 58, // Is ranged-attacking? {$Yes/No}{=1} + Health = 59, // Health {$Relative Op} {#HP} HP + SpellKnown = 60, // Spell known? {$Yes/No} "{Spell}" + HasHarmfulAuraEffect = 61, // Has harmful aura effect? {$Yes/No} "{#Spell Aura}" IsImmuneToAreaOfEffect = 62, // NYI Is immune to area-of-effect? {$Yes/No}{=1} - IsPlayer = 63, // NYI Is player? {$Yes/No}{=1} + IsPlayer = 63, // Is player? {$Yes/No}{=1} DamageMagicPct = 64, // NYI Damage (Magic) {$Relative Op} {#Magic Damage %}% DamageTotalPct = 65, // NYI Damage (Total) {$Relative Op} {#Damage %}% ThreatMagicPct = 66, // NYI Threat (Magic) {$Relative Op} {#Magic Threat %}% ThreatTotalPct = 67, // NYI Threat (Total) {$Relative Op} {#Threat %}% - HasCritter = 68, // NYI Has critter? {$Yes/No}{=1} - HasTotemInSlot1 = 69, // NYI Has totem in slot 1? {$Yes/No}{=1} - HasTotemInSlot2 = 70, // NYI Has totem in slot 2? {$Yes/No}{=1} - HasTotemInSlot3 = 71, // NYI Has totem in slot 3? {$Yes/No}{=1} - HasTotemInSlot4 = 72, // NYI Has totem in slot 4? {$Yes/No}{=1} + HasCritter = 68, // Has critter? {$Yes/No}{=1} + HasTotemInSlot1 = 69, // Has totem in slot 1? {$Yes/No}{=1} + HasTotemInSlot2 = 70, // Has totem in slot 2? {$Yes/No}{=1} + HasTotemInSlot3 = 71, // Has totem in slot 3? {$Yes/No}{=1} + HasTotemInSlot4 = 72, // Has totem in slot 4? {$Yes/No}{=1} HasTotemInSlot5 = 73, // NYI Has totem in slot 5? {$Yes/No}{=1} - Creature = 74, // NYI Creature {$Is/Is Not} "{Creature}" + Creature = 74, // Creature {$Is/Is Not} "{Creature}" StringID = 75, // NYI String ID {$Is/Is Not} "{StringID}" - HasAura = 76, // NYI Has aura? {$Yes/No} {Spell} - IsEnemy = 77, // NYI Is enemy? {$Yes/No}{=1} - IsSpecMelee = 78, // NYI Is spec - melee? {$Yes/No}{=1} - IsSpecTank = 79, // NYI Is spec - tank? {$Yes/No}{=1} - IsSpecRanged = 80, // NYI Is spec - ranged? {$Yes/No}{=1} - IsSpecHealer = 81, // NYI Is spec - healer? {$Yes/No}{=1} - IsPlayerControlledNPC = 82, // NYI Is player controlled NPC? {$Yes/No}{=1} - IsDying = 83, // NYI Is dying? {$Yes/No}{=1} + HasAura = 76, // Has aura? {$Yes/No} {Spell} + IsEnemy = 77, // Is enemy? {$Yes/No}{=1} + IsSpecMelee = 78, // Is spec - melee? {$Yes/No}{=1} + IsSpecTank = 79, // Is spec - tank? {$Yes/No}{=1} + IsSpecRanged = 80, // Is spec - ranged? {$Yes/No}{=1} + IsSpecHealer = 81, // Is spec - healer? {$Yes/No}{=1} + IsPlayerControlledNPC = 82, // Is player controlled NPC? {$Yes/No}{=1} + IsDying = 83, // Is dying? {$Yes/No}{=1} PathFailCount = 84, // NYI Path fail count {$Relative Op} {#Path Fail Count} - IsMounted = 85, // NYI Is mounted? {$Yes/No}{=1} + IsMounted = 85, // Is mounted? {$Yes/No}{=1} Label = 86, // NYI Label {$Is/Is Not} "{Label}" - IsMySummon = 87, // NYI - IsSummoner = 88, // NYI - IsMyTarget = 89, // NYI - Sex = 90, // NYI Sex {$Is/Is Not} "{UnitSex}" - LevelWithinContentTuning = 91, // NYI Level is within {$Is/Is Not} {ContentTuning} - - IsFlying = 93, // NYI Is flying? {$Yes/No}{=1} - IsHovering = 94, // NYI Is hovering? {$Yes/No}{=1} - HasHelpfulAuraEffect = 95, // NYI Has helpful aura effect? {$Yes/No} "{#Spell Aura}" + IsMySummon = 87, // + IsSummoner = 88, // + IsMyTarget = 89, // + Sex = 90, // Sex {$Is/Is Not} "{UnitSex}" + LevelWithinContentTuning = 91, // Level is within {$Is/Is Not} {ContentTuning} + + IsFlying = 93, // Is flying? {$Yes/No}{=1} + IsHovering = 94, // Is hovering? {$Yes/No}{=1} + HasHelpfulAuraEffect = 95, // Has helpful aura effect? {$Yes/No} "{#Spell Aura}" HasHelpfulAuraSchool = 96, // Has helpful aura school? {$Yes/No} "{Resistances}" }; |