For some reason Blackrock Battle Worg stops attacking Stormwind Infantry right after engaged. Not sure wether it has something to do with Stormwind Infantry's CREATURE_FLAG_EXTRA_CIVILIAN flag or Blackrock Battle Worg's faction, which is neutral.
WORLD: Sent SMSG_ATTACKSTART
WORLD: Send SMSG_THREAT_CLEAR Message
WORLD: Sent SMSG_ATTACKSTOP
Creature 280006 stopped attacking creature 280008
Guid 280006 is Blackrock Battle Worg (49871).
Guid 280008 is Stormwind Infantry (49869).
To reproduce use this query to make Stormwind Infantry attack Blackrock Battle Worg and visit human starting area.
UPDATE `creature_template` SET `AIName` = "SmartAI" WHERE `entry` = 49869;
DELETE FROM `smart_scripts` WHERE `entryorguid` = 49869 AND `source_type` = 0;
INSERT INTO `smart_scripts` (`entryorguid`, `source_type`, `id`, `link`, `event_type`, `event_phase_mask`, `event_chance`, `event_flags`, `event_param1`, `event_param2`, `event_param3`, `event_param4`, `action_type`, `action_param1`, `action_param2`, `action_param3`, `action_param4`, `action_param5`, `action_param6`, `target_type`, `target_param1`, `target_param2`, `target_param3`, `target_x`, `target_y`, `target_z`, `target_o`, `comment`) VALUES
(49869, 0, 0, 0, 1, 0, 100, 0, 3000, 3000, 3000, 3000, 49, 0, 0, 0, 0, 0, 0, 11, 49871, 10, 0, 0, 0, 0, 0, 'Stormwind Infantry - out of combat - attack nearby Blackrock Battle Worg'),
Core: f3f81f6
Want to back this issue? Post a bounty on it! We accept bounties via Bountysource.
problem: the stormwind infantry is not allowed to move nor does one of those npc take damage. they attack each other without taking damage so its more c++ that helps here in a proper case
This is an issue in many locations.
1) One of the npc's cannot move on offi.
2) They have to start combat on spawn with no movement inform.
3) The melee attacks and spells are real but should do 0% - 1% damage to each other.
same issue exists with the horde and alliance trash npcs in icc on the 'ramaprt of skulls'-floor.
the npcs should attack each other, but if there is no player-support which 'helps' to kill the hostile factionnpcs, they should not kill each other. (just as sidenote, that this is also important for the 3.3.5 branch)
class npc_rampart_of_skulls_trash : public CreatureScript
{
public:
npc_rampart_of_skulls_trash() : CreatureScript("npc_rampart_of_skulls_trash") { }
struct npc_rampart_of_skulls_trashAI : public SmartAI
{
npc_rampart_of_skulls_trashAI(Creature* creature) : SmartAI(creature) { }
void Reset()
{
ResetThread = false;
me->setActive(true);
me->SetReactState(REACT_AGGRESSIVE);
me->Respawn();
AttackStart(me->GetVictim());
}
void DamageTaken(Unit* attacker, uint32 &damage)
{
if (attacker->GetTypeId() != TYPEID_PLAYER)
{
if (me->GetHealthPct() < 30.0f)
if (!ResetThread)
me->SetHealth(me->GetMaxHealth());
}
if (attacker->GetTypeId() == TYPEID_PLAYER)
{
if (!ResetThread)
{
AttackStart(me->FindNearestPlayer(10.0f));
ResetThread = true;
}
}
}
bool CanAIAttack(Unit const* target) const
{
// sometimes these npcs try to attack marrowgar - so let them reset
return (me->GetPositionZ() < 143.541122f) == (target->GetPositionZ() < 143.541122f) && SmartAI::CanAIAttack(target);
}
private:
bool ResetThread;
};
CreatureAI* GetAI(Creature* creature) const
{
return new npc_rampart_of_skulls_trashAI(creature);
}
};
i did this, so they attack each other and don't kill themself. but that's hacky at all.
-- can be converted for all other npcs
I can confirm this for 6.x too: those 2 NPCs should fight each other but they don't do that.
Faction values are correct (checked from sniff)
https://github.com/TrinityCore/TrinityCore/commit/50707fcbd1bb846ce226e7a65fa94e9b1cacd9c6
https://gist.github.com/Rushor/897126d0ccd9319d414f partly for:
3) The melee attacks and spells are real but should do 0% - 1% damage to each other.
There should be more a assignable c++ ai and a creature variable to set the starting health % and the maximum damage until it becomes 0.
sth like
'npc_generic_fake_combat'
void SetFakeCombatWith(uint32 creatureId, startingHealth, maxDamagedHealth);
for the function call there should be a case switching or so on the AI initialization within the core.
The c++ is required because some fake combats are having different health points while fighting each other. like one worgen in gilnas has more or less hp.
IMHO better some SAI thing or flag, because those mobs needs scripting a lot of times.
dunno if a completely new table would be even better. simply add the attacker entry, the nearby target entry, starting health when engaging and the maximum damage degree. would be better in things of readability.
We need this feature implemented maybe via a flag_extra: cannot_be_damaged_by_npcs
Looks like there are several free addresses available in flags_extra
, between 256 and 16384 etc.
edit: You can find a "recipe" for adding a new flags_extra
flag value to the source in PR #17543
303066509d907d4836a935371492092f05d47c7e
This is not fully implemented.
I see the PR title Core/AI: initial support for monster sparring #17673 more or less specifies that it is only initial work, I take it that the old 6.x/master issue has not been solved yet. Reopen or keep this closed?
void SmartAI::DamageTaken(Unit* doneBy, uint32& damage)
{
GetScript()->ProcessEventsFor(SMART_EVENT_DAMAGED, doneBy, damage);
if (mInvincibilityHpLevel && (damage >= me->GetHealth() - mInvincibilityHpLevel))
damage = me->GetHealth() - mInvincibilityHpLevel; // damage should not be nullified, because of player damage req.
else if (mInvincibilityHpLevel && (damage >= me->GetHealth() - mInvincibilityHpLevel) && me->IsImpossible() && doneBy->GetTypeId() != TYPEID_PLAYER)
damage = 0;
else if (me->HasAuraType(SPELL_AURA_393) && me->isInFront(doneBy))
damage = 0;
else if (me->HasAuraType(SPELL_AURA_414) && me->isInFront(doneBy))
damage = 0;
else if (me->HasAuraType(SPELL_AURA_393) && me->HasAuraType(SPELL_AURA_414) && me->isInFront(doneBy))
damage = 0;
else if (me->HasAura(144819) && (damage >= me->GetHealth()))
damage = 0;
else if (me->HasAura(147754) && (damage >= me->GetHealth()))
damage = 0;
else if (me->HasAura(129419) && (damage >= me->GetHealth()))
damage = 0;
else if (me->HasAura(158799))
damage = 0;
else if (me->HasAura(159435))
damage = 0;
else if (me->HasAura(159569))
damage = 0;
else if (me->HasAura(159610))
damage = 0;
else if (me->HasAura(159656))
damage = 0;
else if (me->HasAura(159657))
damage = 0;
else if (me->HasAura(159658))
damage = 0;
else if (me->HasAura(159660))
damage = 0;
else if (me->HasAura(164322))
damage = 0;
else if (me->HasAura(165814))
damage = 0;
else if (me->HasAura(165880))
damage = 0;
else if (me->HasAura(185249))
damage = 0;
}
CREATURE_FLAG_EXTRA_IMMUNITY_UNIT = 0x80000000 // creature is immune to damage from unit.
``` CPP
#define CREATURE_FLAG_EXTRA_DB_ALLOWED (CREATURE_FLAG_EXTRA_INSTANCE_BIND | CREATURE_FLAG_EXTRA_CIVILIAN | \
CREATURE_FLAG_EXTRA_NO_PARRY | CREATURE_FLAG_EXTRA_NO_PARRY_HASTEN | CREATURE_FLAG_EXTRA_NO_BLOCK | \
CREATURE_FLAG_EXTRA_NO_CRUSH | CREATURE_FLAG_EXTRA_NO_XP_AT_KILL | CREATURE_FLAG_EXTRA_TRIGGER | \
CREATURE_FLAG_EXTRA_NO_TAUNT | CREATURE_FLAG_EXTRA_WORLDEVENT | CREATURE_FLAG_EXTRA_NO_CRIT | \
CREATURE_FLAG_EXTRA_NO_SKILLGAIN | CREATURE_FLAG_EXTRA_TAUNT_DIMINISH | CREATURE_FLAG_EXTRA_ALL_DIMINISH | \
CREATURE_FLAG_EXTRA_GUARD | CREATURE_FLAG_EXTRA_IGNORE_PATHFINDING | CREATURE_FLAG_EXTRA_NO_PLAYER_DAMAGE_REQ | CREATURE_FLAG_EXTRA_IMMUNITY_KNOCKBACK | CREATURE_FLAG_EXTRA_IMMUNITY_UNIT)
``` CPP
bool IsImpossible() const { return (GetCreatureTemplate()->flags_extra & CREATURE_FLAG_EXTRA_IMMUNITY_UNIT) != 0; }
You can solve problem. Npc if needed don't take damage from any npc, but can take damage from player.
@Ulduar: Is that what they call "drunk Russian coding"?
@Kinzcool Can you suggest something else?
example:
creature A attacks creature B with such a feature "flag extra" 2 hours.
Then player C joins the fight and attacks creature A.
Problem: Creature A will not attack Player C because Creature B created a very high amount of threat on creature A.
Some kind of aggro reset is needed in the feature :)
Most helpful comment
@Kinzcool Can you suggest something else?