- Home /
Enemies spawn with multiple of the same animation events
Hey all,
I am having issues with spawning enemies and their related "attack" animation events. The more enemies I have spawn in, the more animation events get added to their attack animation.
I add the animation event to their attack on Start(). Then I instantiate my enemy characters. If I change the spawn values to spawn 1 enemy everything works out well. If I spawn multiple enemies, that number corresponds to the number of animation events that get added. So as you progress in the game enemies get much harder as they exponentially do more damage. This is not what I want. I tried changing where I added the animation event. I tried adding it once a character was spawned but no luck.
Here is my animation event Function code:
function addAnimEvent( t_eventTime : float, animName : String, funcName : String, eTrans : Transform, takeDam : float)
{
var aEvent : AnimationEvent = new AnimationEvent(); //create animation event
aEvent.time = t_eventTime; // add a time value to the animation event
//aEvent.messageOptions = SendMessageOptions.DontRequireReceiver;
aEvent.functionName = funcName; // add the function to call from the animation event
aEvent.floatParameter = takeDam;
if(animName != null)
{
var aState : AnimationState; //create variable to hold my animation state
aState = eTrans.animation[animName]; //find the correct anim name to add the animation event to
aState.clip.AddEvent(aEvent); // add the animation event to the animation clip
}
}
Here is my spawn code:
function spawnEnemy()
{
if(spawn == true)
{
while(enemyCnt <= enemy1cnt && spawnPoints != null && isDead != true)
{
spawn = false;
var i : int = Random.Range(0,spawnPoints.length);
Instantiate(enemy1, spawnPoints[i].transform.position, spawnPoints[i].transform.rotation);
enemyCnt++;
yield new WaitForSeconds(enemy1Off);
}
spawn = true;
}
}
Any help would be greatly appreciated. I'm an animator by trade so please forgive my coding skills :)
Thanks in advance! Alex
Answer by Paulius-Liekis · Jun 07, 2011 at 09:15 AM
aState.clip.AddEvent(aEvent);
You're adding event to AnimationClip. AnimtionClips are shared between animation states and your characters, so every time you add an event it gets added to the same clip. Just add events when you spawn first enemy, and do not add events when spawning other enemies.
Thank you so much! Paulius. I understand what I was doing wrong now.
Answer by frederik_krogh · Mar 28, 2021 at 12:34 PM
This is so wrong... Unity should fix it. Animators should only call the object they are attached to. I wrote my own animation event handler (AnimationTrigger) and it works very well.. Don't know why Unity couldn't make it like this.. Just attach this class to the gameObject with the Animator and add eventlisteners to the component like this
animation_trigger = gameObject.GetComponent<AnimationTrigger>();
animation_trigger.addListener(animationTriggerEvent);
and make a function
public void animationTriggerEvent(AnimationTriggerEvent e)
{
if (e.type == AnimationTriggerEvent.ANIMATION_EVENT)
{
//Debug.Log("Humanoid: ANIMATION TRIGGER");
}
animation_trigger.stopListening();
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
namespace MarchingCubesProject
{
public class AnimationTriggerEvent {
public static readonly int ANIMATION_EVENT = 10;
public static readonly int ANIMATION_EVENT_ERROR = 20;
public int type { get; set; } = 10;
public AnimationEvent animation_event { get; set; }
}
/* Class to curcumvent the Unity AnimationEvent system where events are sent to all objects with that Animator
*
* When startListening() is called. Update looks for events in Animator.GetCurrentAnimatorClipInfo and sends an AnimationTriggerEvent when
* Animator.GetCurrentAnimatorStateInfo.normalizedTime*Length > AnimationEvent.time
*
* IMPORTANT - AnimationTrigger must be turned on and off with startListening() and stopListening()
*/
public class AnimationTrigger: MonoBehaviour
{
public delegate void animationTriggerCallback(AnimationTriggerEvent e);
private List<animationTriggerCallback> listeners;
private Animator anim; // Animator component
private bool is_listening;
// Private variables initialized when event is found
private AnimationEvent detected_event;
private AnimationClip detected_clip;
private bool wait_for_event = false; // true when event has been found and counting down to event
private float event_time_offset = 0;
private void Awake()
{
listeners = new List<animationTriggerCallback>();
}
private void Start()
{
anim = GetComponent<Animator>();
}
public void addListener(animationTriggerCallback listener)
{
listeners.Add(listener);
}
public void startListening()
{
is_listening = true;
}
public void stopListening()
{
is_listening = false;
}
private void callListeners(AnimationTriggerEvent e)
{
for (int i = 0, il = listeners.Count; i < il; i++)
{
listeners[i](e);
}
}
// Update is called once per frame
void Update()
{
// When Event is found and waiting till event_time_offset > detected_event.time
if (wait_for_event)
{
if (detected_event == null)
{
wait_for_event = false;
callListeners(new AnimationTriggerEvent() { type = AnimationTriggerEvent.ANIMATION_EVENT_ERROR });
}
else
{
event_time_offset += Time.deltaTime;
if (event_time_offset > detected_event.time)
{
callListeners(new AnimationTriggerEvent() { animation_event = detected_event });
wait_for_event = false;
//is_listening = false;
}
}
}
// When is_listening, looking for events in Animator.GetCurrentAnimatorClipInfo
if (is_listening && !wait_for_event)
{
if (anim != null)
{
AnimatorClipInfo[] infos = anim.GetCurrentAnimatorClipInfo(0);
for (int i = 0, il = anim.GetCurrentAnimatorClipInfoCount(0); i < il; i++)
{
AnimatorClipInfo info = infos[i];
AnimationClip clip = info.clip;
AnimationEvent[] events = clip.events;
if (events != null)
{
if (events.Length > 0)
{
AnimationEvent e = events[0];
if (e != null)
{
AnimatorStateInfo state_info = anim.GetCurrentAnimatorStateInfo(0);
event_time_offset = (state_info.normalizedTime * state_info.length);
detected_event = e;
detected_clip = clip;
wait_for_event = true;
}
}
}
}
}
}
}
}
}
Your answer
Follow this Question
Related Questions
How to add new curves or animation events to an imported animation? 6 Answers
Removing or Editting an animationEvent 2 Answers
Player lose damage when enemy is attacking (animation) 1 Answer
AnimationEvent triggers twice 3 Answers
Transform Of GameObject getting changed incorrectly after updating RuntimeAnimatorController 0 Answers