From cca48bcda220f79f142938b729f6a52fcf056e5a Mon Sep 17 00:00:00 2001 From: RedKitsune <29517406+RedTheKitsune@users.noreply.github.com> Date: Mon, 22 Sep 2025 16:21:21 +0200 Subject: [PATCH 1/2] - Use key instead of clip play position for firing event - Added bool to toggle automatic event register on Awake --- .../Editor/AnimationEventHandlerEditor.cs | 4 +++ .../Source/Runtime/AnimationEventHandler.cs | 4 +++ .../Source/Runtime/AnimationEventUtils.cs | 9 ++++++ .../Runtime/AnimationEventUtils.cs.meta | 3 ++ .../Source/Runtime/EventReceiver.cs | 29 ++++++++++--------- .../Extensions/AnimationClipExtensions.cs | 10 ++++--- 6 files changed, 41 insertions(+), 18 deletions(-) create mode 100644 Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs create mode 100644 Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs.meta diff --git a/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs b/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs index d6c35c9..fc90bcf 100644 --- a/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs +++ b/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs @@ -187,6 +187,10 @@ public override void OnInspectorGUI() GUILayout.EndHorizontal(); GUILayout.Space(10); // Add some more spacing + + script.initializeOnAwake = GUILayout.Toggle(script.initializeOnAwake, "Initialize On Awake"); + + GUILayout.Space(5); // Add some more spacing if (animator != null && animator.runtimeAnimatorController != null) { diff --git a/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs b/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs index a5caafc..5f42e2b 100644 --- a/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs +++ b/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs @@ -15,8 +15,12 @@ public class AnimationEventHandler : MonoBehaviour /// List of AnimationEventData instances representing animation events to manage. public List animationEvents = new List(); + public bool initializeOnAwake = true; + private void Awake() { + if(!initializeOnAwake) return; + animator = GetComponent(); } diff --git a/Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs b/Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs new file mode 100644 index 0000000..e3d9f8d --- /dev/null +++ b/Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs @@ -0,0 +1,9 @@ +using UnityEngine; + +namespace EasyAnimationEvent +{ + public class AnimationEventUtils + { + public static string ConstructKey(AnimationClip clip, float time) => $"{clip.name}_{time}"; + } +} \ No newline at end of file diff --git a/Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs.meta b/Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs.meta new file mode 100644 index 0000000..45bcae1 --- /dev/null +++ b/Assets/Easy Animation Event/Source/Runtime/AnimationEventUtils.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: ad0cee0b07e04847807e752471e5a0cf +timeCreated: 1758549007 \ No newline at end of file diff --git a/Assets/Easy Animation Event/Source/Runtime/EventReceiver.cs b/Assets/Easy Animation Event/Source/Runtime/EventReceiver.cs index a759276..aaef7df 100644 --- a/Assets/Easy Animation Event/Source/Runtime/EventReceiver.cs +++ b/Assets/Easy Animation Event/Source/Runtime/EventReceiver.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; +using Sirenix.OdinInspector; using UnityEngine; namespace EasyAnimationEvent @@ -16,7 +17,7 @@ namespace EasyAnimationEvent public class EventReceiver : MonoBehaviour { // Dictionary storing callbacks and their names for each timeline position. - private readonly Dictionary> CallbacksPoll = new Dictionary>(); + private readonly Dictionary> CallbacksPoll = new Dictionary>(); /// /// Registers a callback to be invoked at a specific timeline position. @@ -24,7 +25,7 @@ public class EventReceiver : MonoBehaviour /// The timeline position at which the callback should be invoked. /// The callback to register. /// The name of the callback. - public void RegisterEvent(float position, Action callback, string name) + public void RegisterEvent(string key, Action callback, string name) { if (callback == null) { @@ -37,13 +38,13 @@ public void RegisterEvent(float position, Action callback, string name) Debug.LogWarning("Attempted to register a callback with a null or empty name."); return; } - - if (!CallbacksPoll.ContainsKey(position)) + + if (!CallbacksPoll.ContainsKey(key)) { - CallbacksPoll[position] = new List<(Action callback, string name)>(); + CallbacksPoll[key] = new List<(Action callback, string name)>(); } - CallbacksPoll[position].Add((callback, name)); + CallbacksPoll[key].Add((callback, name)); } /// @@ -52,17 +53,17 @@ public void RegisterEvent(float position, Action callback, string name) /// The timeline position from which the callback should be unregistered. /// The name of the callback to unregister. /// True if it was the last callback for the position and the position was removed; otherwise, false. - public bool UnregisterEvent(float position, string name) + public bool UnregisterEvent(string key) { - if (string.IsNullOrEmpty(name)) + if (string.IsNullOrEmpty(key)) { Debug.LogWarning("Attempted to unregister a callback with a null or empty name."); return false; } - if (!CallbacksPoll.TryGetValue(position, out var callbacks)) + if (!CallbacksPoll.TryGetValue(key, out var callbacks)) { - Debug.LogWarning($"Attempted to unregister a callback not registered at position {position}."); + Debug.LogWarning($"Attempted to unregister a callback not registered at key {key}."); return false; } @@ -78,7 +79,7 @@ public bool UnregisterEvent(float position, string name) if (callbacks.Count == 0) { - CallbacksPoll.Remove(position); + CallbacksPoll.Remove(key); return true; } @@ -89,11 +90,11 @@ public bool UnregisterEvent(float position, string name) /// Invoked by Unity's animation system to trigger callbacks at a specific timeline position. /// /// The timeline position at which to trigger callbacks. - private void OnEvent(float position) + private void OnEvent(string key) { - if (!CallbacksPoll.TryGetValue(position, out var callbacks)) + if (!CallbacksPoll.TryGetValue(key, out var callbacks)) { - Debug.LogWarning($"No callbacks registered for timeline position {position}."); + Debug.LogWarning($"No callbacks registered for timeline position {key}."); return; } diff --git a/Assets/Easy Animation Event/Source/Runtime/Extensions/AnimationClipExtensions.cs b/Assets/Easy Animation Event/Source/Runtime/Extensions/AnimationClipExtensions.cs index 32ac19d..a416bff 100644 --- a/Assets/Easy Animation Event/Source/Runtime/Extensions/AnimationClipExtensions.cs +++ b/Assets/Easy Animation Event/Source/Runtime/Extensions/AnimationClipExtensions.cs @@ -84,7 +84,7 @@ private static void BindOrUnbindEvent(this AnimationClip clip, GameObject animEv } // Register the callback at the specified timeline position - eventReceiver.RegisterEvent(position, callback, methodName); + eventReceiver.RegisterEvent(AnimationEventUtils.ConstructKey(clip, position), callback, methodName); // Add an AnimationEvent to the AnimationClip if it doesn't already exist clip.AddEventIfNotExists(OnEvent, position, position); @@ -98,7 +98,7 @@ private static void BindOrUnbindEvent(this AnimationClip clip, GameObject animEv } // Unregister the callback from the EventReceiver - var lastEventForPositionRemoved = eventReceiver.UnregisterEvent(position, methodName); + var lastEventForPositionRemoved = eventReceiver.UnregisterEvent(AnimationEventUtils.ConstructKey(clip, position)); if (lastEventForPositionRemoved) { // Remove the AnimationEvent from the AnimationClip if it was the last event at that position @@ -116,16 +116,18 @@ private static void BindOrUnbindEvent(this AnimationClip clip, GameObject animEv /// The time in the animation clip timeline associated with the event. private static void AddEventIfNotExists(this AnimationClip clip, string methodName, float floatParameter, float time) { + var key = AnimationEventUtils.ConstructKey(clip, floatParameter); + var clipAnimationEvents = clip.events; var animationEvent = Array.Find(clipAnimationEvents, - e => e.functionName == methodName && e.floatParameter == floatParameter && e.time == time); + e => e.functionName == methodName && e.stringParameter == key && e.time == time); if (animationEvent == null) { // Create a new AnimationEvent and add it to the AnimationClip animationEvent = new AnimationEvent(); animationEvent.functionName = methodName; - animationEvent.floatParameter = floatParameter; + animationEvent.stringParameter = key; animationEvent.time = time; clip.AddEvent(animationEvent); } From 96e35b7aab90ff95020eeebe88529be69b839fc8 Mon Sep 17 00:00:00 2001 From: RedKitsune <29517406+RedTheKitsune@users.noreply.github.com> Date: Wed, 24 Sep 2025 12:08:48 +0200 Subject: [PATCH 2/2] - Inspector fix - Initialization fix --- .../Source/Editor/AnimationEventHandlerEditor.cs | 2 +- .../Source/Runtime/AnimationEventHandler.cs | 7 ++----- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs b/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs index fc90bcf..fc23d6f 100644 --- a/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs +++ b/Assets/Easy Animation Event/Source/Editor/AnimationEventHandlerEditor.cs @@ -188,7 +188,7 @@ public override void OnInspectorGUI() GUILayout.Space(10); // Add some more spacing - script.initializeOnAwake = GUILayout.Toggle(script.initializeOnAwake, "Initialize On Awake"); + EditorGUILayout.PropertyField(serializedObject.FindProperty("initializeOnAwake"), new GUIContent("Initialize on Awake")); GUILayout.Space(5); // Add some more spacing diff --git a/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs b/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs index 5f42e2b..2c1f238 100644 --- a/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs +++ b/Assets/Easy Animation Event/Source/Runtime/AnimationEventHandler.cs @@ -19,13 +19,10 @@ public class AnimationEventHandler : MonoBehaviour private void Awake() { + animator = GetComponent(); + if(!initializeOnAwake) return; - animator = GetComponent(); - } - - private void Start() - { AddEvents(); }