Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- // TeaTimer v0.1
- // Unity MonoBehaviour Extension Set for a quick coroutine callback timer.
- //
- // #author Andrés Villalobos
- // #contact andresalvivar@gmail.com > twitter.com/matnesis
- // #created 2014/12/26 12:21 am
- //
- // #usage In any MonoBehaviour:
- //
- // #1 ttAppend - Appends a timed task into a queue to be executed in order.
- // this.ttAppend(2, () => Debug.Log(Time.time)); // prints 2
- // this.ttAppend(1, () => Debug.Log(Time.time)); // prints 3
- //
- // #2 ttInsert - Executes a timed task.
- // this.ttInsert(2, () => Debug.Log(Time.time)); // prints 2
- // this.ttInsert(1, () => Debug.Log(Time.time)); // prints 1
- //
- // #3 A more complex example.
- // this.ttAppend(1, () =>
- // {
- // Debug.Log(Time.time); // prints 1
- // }).ttInsert(1, () =>
- // {
- // Debug.Log(Time.time); // prints 1
- // }).ttAppend(0, () =>
- // {
- // Debug.Log(Time.time); // prints 1
- // });
- using System;
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- /// <summary>
- /// Timed task data.
- /// </summary>
- public class TeaTask
- {
- public float atTime = 0;
- public YieldInstruction atYield = null;
- public Action callback = null;
- public TeaTask(float atTime, Action callback)
- {
- this.atTime = atTime;
- this.callback = callback;
- }
- public TeaTask(YieldInstruction atYield, Action callback)
- {
- this.atYield = atYield;
- this.callback = callback;
- }
- }
- /// <summary>
- /// MonoBehaviour Extension Set for a quick coroutine callback timer.
- /// </summary>
- public static class TeaTimer
- {
- public static Dictionary<MonoBehaviour, List<TeaTask>> queue;
- public static List<MonoBehaviour> currentlyRunning;
- /// <summary>
- /// Appends a timed task into a queue to be executed in order.
- /// </summary>
- /// <param name="instance"></param>
- /// <param name="atTime"></param>
- /// <param name="callback"></param>
- /// <returns></returns>
- public static MonoBehaviour ttAppend(this MonoBehaviour instance, float atTime, Action callback)
- {
- // Create dictionary
- if (queue == null)
- queue = new Dictionary<MonoBehaviour, List<TeaTask>>();
- // Create key and value
- if (!queue.ContainsKey(instance))
- queue.Add(instance, new List<TeaTask>());
- // Append
- List<TeaTask> taskList = queue[instance];
- taskList.Add(new TeaTask(atTime, callback));
- // Execute queue
- instance.StartCoroutine(ExecuteQueue(instance));
- return instance;
- }
- /// <summary>
- /// Appends a timed task into a queue to be executed in order.
- /// </summary>
- /// <param name="instance"></param>
- /// <param name="atYield"></param>
- /// <param name="callback"></param>
- /// <returns></returns>
- public static MonoBehaviour ttAppend(this MonoBehaviour instance, YieldInstruction atYield, Action callback)
- {
- // Create dictionary
- if (queue == null)
- queue = new Dictionary<MonoBehaviour, List<TeaTask>>();
- // Create key and value
- if (!queue.ContainsKey(instance))
- queue.Add(instance, new List<TeaTask>());
- // Append
- List<TeaTask> taskList = queue[instance];
- taskList.Add(new TeaTask(atYield, callback));
- // Execute queue
- instance.StartCoroutine(ExecuteQueue(instance));
- return instance;
- }
- /// <summary>
- /// Executes a timed task.
- /// </summary>
- /// <param name="instance"></param>
- /// <param name="atTime"></param>
- /// <param name="callback"></param>
- /// <returns></returns>
- public static MonoBehaviour ttInsert(this MonoBehaviour instance, float atTime, Action callback)
- {
- // Create dictionary
- if (queue == null)
- queue = new Dictionary<MonoBehaviour, List<TeaTask>>();
- // Create key and value
- if (!queue.ContainsKey(instance))
- queue.Add(instance, new List<TeaTask>());
- // Executes now
- instance.StartCoroutine(ExecuteOnce(atTime, null, callback));
- return instance;
- }
- /// <summary>
- /// Executes a timed task.
- /// </summary>
- /// <param name="instance"></param>
- /// <param name="atYield"></param>
- /// <param name="callback"></param>
- /// <returns></returns>
- public static MonoBehaviour ttInsert(this MonoBehaviour instance, YieldInstruction atYield, Action callback)
- {
- // Create dictionary
- if (queue == null)
- queue = new Dictionary<MonoBehaviour, List<TeaTask>>();
- // Create key and value
- if (!queue.ContainsKey(instance))
- queue.Add(instance, new List<TeaTask>());
- // Executes now
- instance.StartCoroutine(ExecuteOnce(0, atYield, callback));
- return instance;
- }
- /// <summary>
- /// Clear all queued callbacks.
- /// </summary>
- /// <param name="instance"></param>
- /// <returns></returns>
- private static MonoBehaviour ttClear(this MonoBehaviour instance)
- {
- // Ignore empty
- if (queue.ContainsKey(instance) == false)
- return instance;
- // Clone list
- queue[instance].Clear();
- return instance;
- }
- /// <summary>
- /// Execute all queued tasks for the instance.
- /// </summary>
- /// <param name="instance"></param>
- /// <returns></returns>
- private static IEnumerator ExecuteQueue(MonoBehaviour instance)
- {
- // Ignore empty
- if (queue.ContainsKey(instance) == false)
- yield break;
- // Create runners list
- if (currentlyRunning == null)
- currentlyRunning = new List<MonoBehaviour>();
- // Ignore if already running
- if (currentlyRunning.Contains(instance))
- yield break;
- // Run a clone list of tasks until depleted
- List<TeaTask> batch = new List<TeaTask>();
- batch.AddRange(queue[instance]);
- currentlyRunning.Add(instance);
- foreach (TeaTask c in batch)
- {
- // execute & remove tasks
- yield return instance.StartCoroutine(ExecuteOnce(c.atTime, c.atYield, c.callback));
- queue[instance].Remove(c);
- }
- currentlyRunning.Remove(instance);
- // Try again is there are new items
- if (queue[instance].Count > 0)
- instance.StartCoroutine(ExecuteQueue(instance));
- }
- /// <summary>
- /// Executes a timed coroutine.
- /// </summary>
- /// <param name="atTime"></param>
- /// <param name="atYield"></param>
- /// <param name="callback"></param>
- /// <returns></returns>
- private static IEnumerator ExecuteOnce(float atTime, YieldInstruction atYield, Action callback)
- {
- // Wait until
- if (atTime > 0)
- yield return new WaitForSeconds(atTime);
- if (atYield != null)
- yield return atYield;
- // Task
- if (callback != null)
- callback();
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement