mirror of
https://gitcode.com/GitHub_Trending/az/azerothcore-wotlk.git
synced 2026-10-10 07:06:38 +08:00
fix(Core/Script): Add SMART_TARGET_SHARED_OWNER_ENTITIES. (#26902)
This commit is contained in:
@@ -44,6 +44,27 @@
|
||||
// see: https://github.com/azerothcore/azerothcore-wotlk/issues/9766
|
||||
#include "GridNotifiersImpl.h"
|
||||
|
||||
namespace
|
||||
{
|
||||
// Returns the GUID of whoever brought this object into the world: its owner/charmer if any,
|
||||
// its summoner otherwise. Empty for objects that were not summoned by anyone.
|
||||
ObjectGuid GetSummonerOrOwnerGUID(WorldObject const* obj)
|
||||
{
|
||||
if (Creature const* creature = obj->ToCreature())
|
||||
{
|
||||
if (ObjectGuid ownerGUID = creature->GetCharmerOrOwnerGUID())
|
||||
return ownerGUID;
|
||||
|
||||
if (TempSummon const* summon = creature->ToTempSummon())
|
||||
return summon->GetSummonerGUID();
|
||||
}
|
||||
else if (GameObject const* gameObject = obj->ToGameObject())
|
||||
return gameObject->GetOwnerGUID();
|
||||
|
||||
return ObjectGuid::Empty;
|
||||
}
|
||||
}
|
||||
|
||||
SmartScript::SmartScript()
|
||||
{
|
||||
go = nullptr;
|
||||
@@ -4158,6 +4179,49 @@ void SmartScript::GetTargets(ObjectVector& targets, SmartScriptHolder const& e,
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SMART_TARGET_SHARED_OWNER_ENTITIES:
|
||||
{
|
||||
WorldObject* ref = GetBaseObject();
|
||||
|
||||
if (!ref)
|
||||
{
|
||||
LOG_ERROR("scripts.ai.sai", "SMART_TARGET_SHARED_OWNER_ENTITIES: Entry {} SourceType {} Event {} Action {} Target {} is missing base object.",
|
||||
e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
|
||||
break;
|
||||
}
|
||||
|
||||
ObjectGuid ownerGUID = GetSummonerOrOwnerGUID(ref);
|
||||
if (!ownerGUID)
|
||||
break;
|
||||
|
||||
bool const wantGameObject = e.target.sharedOwnerEntities.type == 2;
|
||||
uint32 const entry = e.target.sharedOwnerEntities.entry;
|
||||
|
||||
float const dist = e.target.sharedOwnerEntities.maxDist ? (float)e.target.sharedOwnerEntities.maxDist : ref->GetVisibilityRange();
|
||||
|
||||
ObjectVector units;
|
||||
GetWorldObjectsInDist(units, dist);
|
||||
|
||||
for (WorldObject* unit : units)
|
||||
{
|
||||
// an object is never a sibling of itself
|
||||
if (unit->GetGUID() == ref->GetGUID())
|
||||
continue;
|
||||
|
||||
if (wantGameObject ? !IsGameObject(unit) : !IsCreature(unit))
|
||||
continue;
|
||||
|
||||
if (entry && unit->GetEntry() != entry)
|
||||
continue;
|
||||
|
||||
if (GetSummonerOrOwnerGUID(unit) != ownerGUID)
|
||||
continue;
|
||||
|
||||
targets.push_back(unit);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
case SMART_TARGET_NONE:
|
||||
case SMART_TARGET_POSITION:
|
||||
default:
|
||||
|
||||
@@ -537,6 +537,25 @@ bool SmartAIMgr::IsTargetValid(SmartScriptHolder const& e)
|
||||
return false;
|
||||
return IsSAIBoolValid(e, e.target.formation.excludeSelf);
|
||||
}
|
||||
case SMART_TARGET_SHARED_OWNER_ENTITIES:
|
||||
{
|
||||
if (e.target.sharedOwnerEntities.type != 1 && e.target.sharedOwnerEntities.type != 2)
|
||||
{
|
||||
LOG_ERROR("sql.sql", "SmartAIMgr: Entry {} SourceType {} Event {} Action {} has invalid shared owner entities type as target ({}, must be 1 or 2).",
|
||||
e.entryOrGuid, e.GetScriptType(), e.GetEventType(), e.GetActionType(), e.target.sharedOwnerEntities.type);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (e.target.sharedOwnerEntities.entry)
|
||||
{
|
||||
if (e.target.sharedOwnerEntities.type == 1 && !IsCreatureValid(e, e.target.sharedOwnerEntities.entry))
|
||||
return false;
|
||||
|
||||
if (e.target.sharedOwnerEntities.type == 2 && !IsGameObjectValid(e, e.target.sharedOwnerEntities.entry))
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SMART_TARGET_HOSTILE_SECOND_AGGRO:
|
||||
case SMART_TARGET_HOSTILE_LAST_AGGRO:
|
||||
case SMART_TARGET_HOSTILE_RANDOM:
|
||||
@@ -963,6 +982,7 @@ bool SmartAIMgr::CheckUnusedTargetParams(SmartScriptHolder const& e)
|
||||
case SMART_TARGET_SUMMONED_CREATURES: return sizeof(SmartTarget::summonedCreatures);
|
||||
case SMART_TARGET_INSTANCE_STORAGE: return sizeof(SmartTarget::instanceStorage);
|
||||
case SMART_TARGET_FORMATION: return sizeof(SmartTarget::formation);
|
||||
case SMART_TARGET_SHARED_OWNER_ENTITIES: return sizeof(SmartTarget::sharedOwnerEntities);
|
||||
default:
|
||||
LOG_WARN("sql.sql", "SmartAIMgr: entryorguid {} source_type {} id {} action_type {} is using a target {} with no unused params specified in SmartAIMgr::CheckUnusedTargetParams(), please report this.",
|
||||
e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType());
|
||||
|
||||
@@ -1590,8 +1590,9 @@ enum SMARTAI_TARGETS
|
||||
SMART_TARGET_SUMMONED_CREATURES = 204, // Entry
|
||||
SMART_TARGET_INSTANCE_STORAGE = 205, // Instance data index, Type (creature (1), gameobject (2))
|
||||
SMART_TARGET_FORMATION = 206, // Type (0: members only, 1: leader only, 2: all), CreatureEntry (0: any), ExcludeSelf (0/1)
|
||||
SMART_TARGET_SHARED_OWNER_ENTITIES = 207, // Type (creature (1), gameobject (2)), Entry (0: any), MaxDist (0: visibility range)
|
||||
|
||||
SMART_TARGET_AC_END = 207 // placeholder
|
||||
SMART_TARGET_AC_END = 208 // placeholder
|
||||
};
|
||||
|
||||
struct SmartTarget
|
||||
@@ -1779,6 +1780,14 @@ struct SmartTarget
|
||||
{
|
||||
SAIBool includePets;
|
||||
} invokerParty;
|
||||
|
||||
// entities sharing our owner, charmer or summoner, whether they were summoned by it or not
|
||||
struct
|
||||
{
|
||||
uint32 type; // creature (1), gameobject (2)
|
||||
uint32 entry; // entry filter, 0 = any
|
||||
uint32 maxDist; // 0 = visibility range
|
||||
} sharedOwnerEntities;
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user