Skip to content

Instantly share code, notes, and snippets.

@hww
Last active December 31, 2015 21:59
Show Gist options
  • Save hww/8050800 to your computer and use it in GitHub Desktop.
Save hww/8050800 to your computer and use it in GitHub Desktop.
Futils extension
using UnityEngine;
using System.Collections;
using System;
public class FTextEffect {
public class BaseSequence {
public bool enabled; // enimation enabled
public float duration; // duration of the animation
public float startTime; // start time of the animation
public float endTime; // end time
public Func<float, float, float, float, float> easeFunction; // ease function
}
public abstract class BaseKey {
public BaseKey () {
}
public abstract bool Tween(BaseSequence seq, float time) ;
public abstract void Lerp(float lerp);
}
public class ColorKey : BaseKey {
public Color val;
public Color valStart;
public Color valDiff;
public ColorKey () : this (Color.white) {
}
public ColorKey (ColorKey newcolor) {
val = newcolor.val;
}
public ColorKey (Color newcolor) {
val = newcolor;
}
public void ValueTo(Color colorTo) {
valStart = val;
valDiff = colorTo - val;
}
override public void Lerp(float lerp) {
val = Color.Lerp(val, valStart + valDiff, lerp);
}
override public bool Tween(BaseSequence seq, float time) {
float easedTime = seq.easeFunction(time, 0, 1, seq.duration );
val = GoTweenUtils.unclampedColorLerp( valStart, valDiff, easedTime );
return easedTime>=1;
}
}
public class Vector2Key : BaseKey {
public Vector2 val;
public Vector2 valStart;
public Vector2 valDiff;
public Vector2Key () : this (Vector2.zero) {
}
public Vector2Key (Vector2Key newvector) {
val = newvector.val;
}
public Vector2Key (Vector2 newvector) {
val = newvector;
}
public void ValueTo(Vector2 vectorTo) {
valStart = val;
valDiff = vectorTo - val;
}
override public void Lerp(float lerp) {
val = Vector2.Lerp(val, valStart + valDiff, lerp);
}
override public bool Tween(BaseSequence seq, float time) {
float easedTime = seq.easeFunction(time, 0, 1, seq.duration );
val = GoTweenUtils.unclampedVector2Lerp( valStart, valDiff, easedTime );
return easedTime>=1;
}
}
public class FloatKey : BaseKey {
public float val;
public float valStart;
public float valDiff;
public FloatKey() : this (0) {
}
public FloatKey(FloatKey newval) {
val = newval.val;
}
public FloatKey(float newval) {
val = newval;
}
public void ValueTo(float floatTo) {
valStart = val;
valDiff = floatTo - val;
}
override public void Lerp(float lerp) {
val = Mathf.Lerp(val, valStart + valDiff, lerp);
}
override public bool Tween(BaseSequence seq, float time) {
val = seq.easeFunction(time, valStart, valDiff, seq.duration );
return seq.endTime < time;
}
}
public class Sequence<T> : BaseSequence where T : BaseKey {
public BetterList<T> nodes; // animation keys
public Sequence() {
nodes = new BetterList<T>();
}
/// <summary>
/// Initializes a new instance of the <see cref="FTextEffect+Animation`1"/> class.
/// </summary>
/// <param name="element">Element used to copy data from.</param>
/// <param name="size">Size.</param>
public void Init(T element, int size) {
nodes.Clear();
for (int i=0; i< size; i++) {
T el = (T)Activator.CreateInstance(typeof(T), element);
nodes.Add(el);
}
enabled = false;
}
public void Lerp(float lerp) {
for (int i=0; i<nodes.size; i++)
nodes[i].Lerp(lerp);
}
/// <summary>
/// Apply. It make tween for 0 seconds
/// </summary>
public void Apply () {
if (!enabled) return;
Lerp (1);
enabled = false;
}
/// <summary>
/// Direct access to the buffer. Note that you should not use its 'Length' parameter, but instead use BetterList.size.
/// </summary>
public T this[int i]
{
get { return nodes[i]; }
set { nodes[i] = value; }
}
/// <summary>
/// Gets the size.
/// </summary>
/// <value>The size.</value>
public int size { get { return nodes.size; } }
/// <summary>
/// Tween the specified dur and easeType.
/// </summary>
/// <param name="dur">Dur.</param>
/// <param name="easeType">Ease type.</param>
public void Tween(float dur, GoEaseType easeType = GoEaseType.Linear) {
easeFunction = GoTweenUtils.easeFunctionForType( easeType );
duration = dur;
startTime = Time.time;
endTime = startTime + duration;
enabled = true;
}
/// <summary>
/// Update the specified time.
/// </summary>
/// <param name="time">Time.</param>
/// <param name="time">PhaseShift shift time per each character</param>
public void Update (float time, float phaseShift) {
if (!enabled) return;
float phase = 0;
bool complete = true;
for (int i=0; i<nodes.size; i++) {
complete &= (nodes[i] as BaseKey).Tween(this, Mathf.Clamp(time - phase - startTime,0,duration));
phase += phaseShift;
}
enabled = !complete;
}
}
Sequence<ColorKey> colorNodes;
Sequence<Vector2Key> positionNodes;
Sequence<FloatKey> rotationNodes;
Sequence<Vector2Key> scaleNodes;
public FTextEffect() {
colorNodes = new Sequence<ColorKey>();
positionNodes = new Sequence<Vector2Key>();
rotationNodes = new Sequence<FloatKey>();
scaleNodes = new Sequence<Vector2Key>();
}
public void Init (string text) {
// get size of string minus amount of CR
int size = 0;
for (int i=0; i< text.Length; i++) {
if (text[i]!='\n') size++;
}
colorNodes.Init(new ColorKey(Color.white), size);
positionNodes.Init(new Vector2Key(Vector2.zero), size);
rotationNodes.Init(new FloatKey(0), size);
scaleNodes.Init(new Vector2Key(Vector2.one), size);
}
/// <summary>
/// Set target colors to random value from the list
/// </summary>
/// <param name="colorsTo">Colors to. Random colors list</param>
/// <param name="duration">Duration.</param>
/// <param name="easeType">Ease type.</param>
public void ColorTo(Color[] colorsTo, float duration=1, GoEaseType easeType = GoEaseType.Linear) {
for (int i=0; i<colorNodes.size; i++) {
colorNodes[i].ValueTo(RXRandom.AnyItem<Color>(colorsTo));
}
colorNodes.Tween(duration, easeType);
}
/// <summary>
/// Set target colors to random value
/// </summary>
/// <param name="colorsTo">Colors to.</param>
/// <param name="duration">Duration.</param>
/// <param name="easeType">Ease type.</param>
///
public void ColorTo(Color colorsTo, float duration=1, GoEaseType easeType = GoEaseType.Linear) {
ColorTo(new Color[] {colorsTo}, duration, easeType);
}
/// <summary>
/// Set random target position for each character in the circle
/// </summary>
/// <param name="position">Position.</param>
/// <param name="radius">Radius.</param>
public void PositionTo(Vector2 position, float radius, float duration=1, GoEaseType easeType = GoEaseType.Linear) {
for (int i=0; i<positionNodes.size; i++) {
positionNodes[i].ValueTo(position + UnityEngine.Random.insideUnitCircle * radius);
}
positionNodes.Tween(duration, easeType);
}
/// <summary>
/// Rotations to random value
/// </summary>
/// <param name="rotation">rotationMin.</param>
/// <param name="randomRotation">rotationMax.</param>
/// <param name="duration">Duration.</param>
/// <param name="easeType">Ease type.</param>
public void RotationTo(float rotationMin, float randomRotation, float duration=1, GoEaseType easeType = GoEaseType.Linear) {
for (int i=0; i<rotationNodes.size; i++) {
rotationNodes[i].ValueTo(UnityEngine.Random.Range(rotationMin,randomRotation));
}
rotationNodes.Tween(duration, easeType);
}
/// <summary>
/// Scales to random values
/// </summary>
/// <param name="scaleMin">Scale minimum.</param>
/// <param name="scaleMax">Scale max.</param>
/// <param name="duration">Duration.</param>
/// <param name="easeType">Ease type.</param>
public void ScaleTo(Vector2 scaleMin, Vector2 scaleMax, float duration=1, GoEaseType easeType = GoEaseType.Linear) {
for (int i=0; i<scaleNodes.size; i++) {
scaleNodes[i].ValueTo(new Vector2(UnityEngine.Random.Range(scaleMin.x,scaleMax.x), UnityEngine.Random.Range(scaleMin.y,scaleMax.y)));
}
scaleNodes.Tween(duration, easeType);
}
/// <summary>
/// Make current transform as the target with some lerp
/// </summary>
/// <param name="lerp">Lerp.</param>
public void Lerp(float lerp = 1) {
colorNodes.Lerp(lerp);
positionNodes.Lerp(lerp);
rotationNodes.Lerp(lerp);
scaleNodes.Lerp(lerp);
}
public void Appply() {
colorNodes.Apply();
positionNodes.Apply();
rotationNodes.Apply();
scaleNodes.Apply();
}
public void Update(float time, float phase) {
colorNodes.Update(time, phase);
positionNodes.Update(time, phase);
rotationNodes.Update(time, phase);
scaleNodes.Update(time, phase);
}
public Color GetColor(int idx) {
return colorNodes[idx].val;
}
public FMatrix GetTransform(int idx) {
FMatrix m = new FMatrix();
Vector2 position = GetPosition(idx);
float rotation = GetRotation(idx);
Vector2 scale = GetScale(idx);
m.SetRotateThenScale(0, 0, scale.x, scale.y, rotation);
return m;
}
public Vector2 GetPosition(int idx) {
return positionNodes[idx].val;
}
public float GetRotation(int idx) {
return rotationNodes[idx].val;
}
public Vector2 GetScale(int idx) {
return scaleNodes[idx].val;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment