foamyesque Posted April 3, 2019 Share Posted April 3, 2019 I'm poking at trying to make a version of the Command Animal power that is usable (and used) by NPCs. Unfortunately several chunks of the standard one are implemented in player-specific fashion that doesn't have a generic equivalent. Right now, the power will pacify (all, not just one, but I think I can solve that) animals within the spell's AoE. So far so good, but I'd like them to help out the caster, as they would the player. This is where I get stuck. I can't seem to find a combination of faction relations and AI settings that will: 1. By default make the animal nonaggressive against everyone2. Make them attack actors if, and only if, they're in combat with the casting actor Right now I'm looking at adding a cloak spell to the casting actor to find everybody who is hostile to them, and stuffing them into a faction set as an enemy to the pacified faction, but that's a very kludgey thing to try. Anyone have some experience in the area and/or pointers? Link to comment Share on other sites More sharing options...
ReDragon2013 Posted April 3, 2019 Share Posted April 3, 2019 (edited) Probably you'll find that too. Something can be tweaked in next sample script, take it as a base!I believe if an actor has been attacked, and another actor with the same faction (with good faction rank) is nearby this actor is going to combat too. foamAnimalScript Scriptname foamAnimalScript extends ActiveMagicEffect {make the animal nonaggressive against everyone and attack actors, if they are in combat with the caster} ; https://forums.nexusmods.com/index.php?/topic/7535376-ai-aggression-problem/ ; 0 - Unaggressive - will not initiate combat ; 1 - Aggressive - will attack enemies on sight ; 2 - Very Aggressive - will attack enemies and neutrals on sight ; 3 - Frenzied - will attack anyone else Keyword PROPERTY ActorTypeAnimal auto ; use autofill Faction PROPERTY mySpecialFaction auto ; new created faction ; -- EVENTs -- EVENT OnEffectStart(Actor akTarget, Actor akCaster) IF akTarget.HasKeyword(ActorTypeAnimal) ELSE self.Dispel() RETURN ; - STOP - this is not an animal, remove effect ENDIF ;--------------------- ; pacify animal to everyone akTarget.RemoveFromAllFactions() akTarget.SetActorValue("Aggression", 0) akTarget.StopCombatAlarm() akTarget.StopCombat() ; caster and target should be in unique faction (to support each other) akCaster.AddToFaction(mySpecialFaction) akTarget.AddToFaction(mySpecialFaction) ;;; akTarget.SetFactionRank(mySpecialFaction, 0) ; valid range is -128 to 127 gotoState("Waiting") ; ### STATE ### ENDEVENT EVENT OnEffectFinish(Actor akTarget, Actor akCaster) gotoState("") ; ### STATE ### Debug.Trace("foamAnimal: OnEffectFinish() - for " +akTarget+", " +self) ENDEVENT ;========================== state Waiting ;============ ;/ *** EVENT OnHit(ObjectReference akAggressor, Form akSource, Projectile akProjectile, Bool abPowerAttack, Bool abSneakAttack, Bool abBashAttack, Bool abHitBlocked) IF (akAggressor as Actor) ELSE RETURN ; - STOP - no actor ENDIF ;--------------------- IF ((akAggressor as Actor) == self.GetCasterActor()) ; handle casters friendly hits ELSE ; other hits ENDIF ENDEVENT *** /; EVENT OnDeath(Actor akKiller) gotoState("") ; ### STATE ### Debug.Notification("Animal is dead!") Debug.Trace("foamAnimal: OnDeath() - for " +self.GetTargetActor()+", " +self) ENDEVENT EVENT OnEndState() myF_Revert() ENDEVENT ;======= endState ; -- FUNCTION -- ;-------------------- FUNCTION myF_Revert() ;-------------------- self.GetTargetActor().RemoveFromFaction(mySpecialFaction) self.GetCasterActor().RemoveFromFaction(mySpecialFaction) ENDFUNCTION Edited April 3, 2019 by ReDragon2013 Link to comment Share on other sites More sharing options...
foamyesque Posted April 3, 2019 Author Share Posted April 3, 2019 There's a couple of problems with that approach: The first, as I have discovered through other attempts at this, is that the Aggro Radius behaviour will override Aggression 0 or 1 and animals with it set will attack Neutrals regardless of that setting. The second is that it irrevocably wipes any prior factions the animal has, which isn't a huge thing since 99% of animals are non-unique, respawning references, but is something I'd prefer to avoid. (I also would have to set the Assistance AV to 'helps allies', just to be sure, and include both Aggression and Assistance revert-to-saved bits, but that's all trivial) Link to comment Share on other sites More sharing options...
foamyesque Posted April 4, 2019 Author Share Posted April 4, 2019 This is getting kinda frustrating. No matter what I try I can't seem to find a way to make the damn things aggro against stuff in the Friend faction other than setting aggression to 3+, which has the undesired behaviour of making them hostile to *everything*, including the person using the pacification spell. StartCombat() does nothing. Setting an individual relationship rank or adding an enemy faction does not create hostility or combat. They don't come to the assistance of allies against friends. I thought I could trigger a cast of a hostile spell against the commanded animal, but a. a Cast() call on people in combat doesn't use the supplied target parameter and b. even when the spell does process it doesn't make them hostile! Link to comment Share on other sites More sharing options...
ReDragon2013 Posted April 5, 2019 Share Posted April 5, 2019 (edited) What is about this?Player can summon some kind of attronach. You could use such spell like frost attronach, but instead of attronach you summon an animal (selected by formlist) and disable the real animal that you want to pacify.After the spell has been finished by time out or the summoned animal is dead, enable the real animal again.Or cast to the real animal a second spell that will auto enable them after 24 hours ingame. Edited April 5, 2019 by ReDragon2013 Link to comment Share on other sites More sharing options...
foamyesque Posted April 5, 2019 Author Share Posted April 5, 2019 What is about this?Player can summon some kind of attronach. You could use such spell like frost attronach, but instead of attronach you summon an animal (selected by formlist) and disable the real animal that you want to pacify.After the spell has been finished by time out or the summoned animal is dead, enable the real animal again.Or cast to the real animal a second spell that will auto enable them after 24 hours ingame. Hm. That might be possible, with maybe some work to make sure things like actor values and factions get copied, but there's a lot of animals I'd need to make summonable versions of. Link to comment Share on other sites More sharing options...
foamyesque Posted April 6, 2019 Author Share Posted April 6, 2019 I think I found a solution!It appears that aggro radius (which isn't overridden by relationships but is by factions) appears to apply solely to the player. I had thought it applied to everyone. This let me do some individual relationship management. If they're hostile towards the caster of the spell, they have the relationship to the commanded animal set to enemy, and if they are not, it is set to friendly. For non-player actors this is done through SetRelationshipRank; for the player, it is by adding and removing the animal from a PlayerFriendFaction I created, which is friendly to a PlayerFaction, but neutral to other factions including itself. The animal's own AI data and factions are saved (factions required SKSE, but oh well), then the factions are cleared (so that the only thing impacting aggro is the spell itself) and the AI data set to Helps Allies / Foolhardy / Attacks Enemies. When the spell expires the saved data is restored. Unfortunately it relies on the caster also being given a cloak ability to monitor for nearby actors, so there could be some pretty substantial load on the engine, but so far I haven't found a way around that. Link to comment Share on other sites More sharing options...
Recommended Posts