Moved all actions to coa4u namespace.

Added methods caching for quick message processing.
Integrated MeshActor into Actor.

new Actions:
ActionStop.cs
ActionSetDirection.cs
This commit is contained in:
2014-06-22 02:57:08 +04:00
parent 5f5d7b423e
commit 2a5f20879b
40 changed files with 1801 additions and 1155 deletions

View File

@@ -63,8 +63,6 @@ Base actions
Interval actions
- [ ] Follow - follows another actor with the given speed for the given amount of time (of forever).
- [ ] LookAt - rotates the object to look at the given actor.
*These two actions requires the using of MeshActor script instead of Actor.*
- [x] SkewBy - skews the mesh by given values.
- [ ] SkewTo - skews the mesh to the given values.

View File

@@ -2,32 +2,37 @@
using System.Collections.Generic;
using UnityEngine;
public class Action
namespace coa4u
{
/// <summary>
/// Basic action class for subclassing. To inherit interval actions, consider using the ActionInterval as the base class.
/// </summary>
public class ActionInstant
{
protected Actor target;
public float duration = 0;
protected Transform transform;
protected Renderer renderer;
protected bool is2d = false;
private float durationValue = 0;
private float dtrValue = 0;
private bool isRunning = false;
public Action()
public ActionInstant()
{
}
public virtual Action clone()
{
return new Action();
}
public virtual bool isRunning()
{
return false;
}
/// <summary>
/// This method is called at the action start. Usable for instant and interval actions.
/// Returns a copy of the action.
/// </summary>
public virtual Action reverse()
public virtual ActionInstant clone()
{
return new ActionInstant();
}
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public virtual ActionInstant reverse()
{
throw new Exception("Can reverse only the reversable interval actions");
}
@@ -39,8 +44,8 @@ public class Action
{
if (target == null)
throw new Exception("Can start the action only after it's atached to the actor");
transform = target.gameObject.transform;
renderer = target.gameObject.renderer;
transform = target.transformCached;
renderer = target.rendererCached;
}
/// <summary>
@@ -61,21 +66,60 @@ public class Action
throw new Exception("Can stop the action only after it's atached to the actor");
}
/// <summary>
/// This method sets the actor for the action.
/// </summary>
public void setActor(Actor actor)
{
target = actor;
}
public virtual float dtr
/// <summary>
/// Readonly property. Shows the remaining time of the action.
/// </summary>
public float duration
{
get
{
return 0;
return durationValue;
}
protected set
{
durationValue = value;
}
}
/// <summary>
/// Readonly property. Shows if the action is running or not.
/// </summary>
public bool running
{
get
{
return isRunning;
}
protected set
{
isRunning = value;
}
}
/// <summary>
/// Readonly property. Contains the remaining tick time after action finished.
/// </summary>
public float dtr
{
get
{
return dtrValue;
}
protected set
{
dtrValue = value;
}
}
}
}

View File

@@ -2,11 +2,15 @@
using System.Collections.Generic;
using UnityEngine;
class ActionInterval : Action
namespace coa4u
{
/// <summary>
/// Interval action class for subclassing.
/// </summary>
public class ActionInterval : ActionInstant
{
protected float timer;
protected float timeScale;
protected bool running;
private float dtrdata;
public ActionInterval(float tgtDuration)
@@ -17,21 +21,25 @@ class ActionInterval : Action
dtr = 0;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionInterval(duration);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
throw new Exception("Can reverse only the reversable interval actions");
}
public override bool isRunning()
{
return running;
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -39,6 +47,9 @@ class ActionInterval : Action
timer = 0F;
}
/// <summary>
/// This method is called after the interval action is stopped.
/// </summary>
public override void stop()
{
base.stop();
@@ -46,7 +57,7 @@ class ActionInterval : Action
}
/// <summary>
/// Step method for interval actions. Don't override this method, when inheriting, put your code in stepInterval instead.
/// This method is called every frame update. Don't override this method, when inheriting, put your code in stepInterval instead.
/// </summary>
public override void step(float dt)
{
@@ -71,28 +82,12 @@ class ActionInterval : Action
}
/// <summary>
/// Step method for interval actions. Put your code here.
/// This method is called every frame update. Put your code here.
/// </summary>
public virtual void stepInterval(float dt)
{
}
/// <summary>
/// Property to get the remaining tick time after the action has ended.
/// </summary>
public override float dtr
{
get
{
return dtrdata;
}
protected set
{
dtrdata = value;
}
}
/// <summary>
/// Immediately changes the time scale for this action and all nested ones.
/// </summary>
@@ -100,4 +95,5 @@ class ActionInterval : Action
{
timeScale = ts;
}
}
}

View File

@@ -2,26 +2,34 @@
using System.Collections.Generic;
using UnityEngine;
class ActionParallel : ActionInterval
namespace coa4u
{
protected Action[] actions;
/// <summary>
/// Runs several actions at the same time.
/// </summary>
public class ActionParallel : ActionInterval
{
protected ActionInstant[] actions;
public ActionParallel(Action action1, Action action2)
public ActionParallel(ActionInstant action1, ActionInstant action2)
: base(0)
{
actions = new Action[] {action1, action2};
actions = new ActionInstant[] { action1, action2 };
}
public ActionParallel(Action[] actionsList)
public ActionParallel(ActionInstant[] actionsList)
: base(0)
{
actions = actionsList;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
Action[] aList = new Action[actions.Length];
ActionInstant[] aList = new ActionInstant[actions.Length];
for (int i = 0; i < actions.Length; i++)
{
aList[i] = actions[i].clone();
@@ -29,9 +37,12 @@ class ActionParallel : ActionInterval
return new ActionSequence(aList);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
Action[] aList = new Action[actions.Length];
ActionInstant[] aList = new ActionInstant[actions.Length];
for (int i = 0; i < actions.Length; i++)
{
aList[i] = actions[i].reverse();
@@ -39,6 +50,9 @@ class ActionParallel : ActionInterval
return new ActionSequence(aList);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -49,19 +63,22 @@ class ActionParallel : ActionInterval
}
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void step(float dt)
{
dt *= timeScale;
for (int i = 0; i < actions.Length; i++)
{
if (actions[i].isRunning())
if (actions[i].running)
actions[i].step(dt);
}
bool canStopNow = true;
float dtrdata = 0;
for (int i = 0; i < actions.Length; i++)
{
if (actions[i].isRunning())
if (actions[i].running)
{
canStopNow = false;
dtrdata = Math.Max(actions[i].dtr, dtrdata);
@@ -74,6 +91,9 @@ class ActionParallel : ActionInterval
}
}
/// <summary>
/// This method is called after the interval action is stopped.
/// </summary>
public override void stop()
{
base.stop();
@@ -82,4 +102,5 @@ class ActionParallel : ActionInterval
actions[i].stop();
}
}
}
}

View File

@@ -2,28 +2,36 @@
using System.Collections.Generic;
using UnityEngine;
class ActionRandom : ActionInterval
namespace coa4u
{
/// <summary>
/// Runs one random action from the given list.
/// </summary>
class ActionRandom : ActionInterval
{
protected Action[] actions;
protected ActionInstant[] actions;
protected int index;
public ActionRandom(Action action1, Action action2)
public ActionRandom(ActionInstant action1, ActionInstant action2)
: base(0)
{
actions = new Action[] {action1, action2};
actions = new ActionInstant[] { action1, action2 };
}
public ActionRandom(Action[] actionsList)
public ActionRandom(ActionInstant[] actionsList)
: base(0)
{
actions = actionsList;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
Action[] aList = new Action[actions.Length];
ActionInstant[] aList = new ActionInstant[actions.Length];
for (int i = 0; i < actions.Length; i++)
{
aList[i] = actions[i].clone();
@@ -31,9 +39,12 @@ class ActionRandom : ActionInterval
return new ActionRandom(aList);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
Action[] aList = new Action[actions.Length];
ActionInstant[] aList = new ActionInstant[actions.Length];
for (int i = 0; i < actions.Length; i++)
{
aList[i] = actions[i].reverse();
@@ -41,6 +52,9 @@ class ActionRandom : ActionInterval
return new ActionRandom(aList);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -49,21 +63,28 @@ class ActionRandom : ActionInterval
actions[index].start();
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void step(float dt)
{
dt *= timeScale;
if (actions[index].isRunning())
if (actions[index].running)
actions[index].step(dt);
if (!actions[index].isRunning())
if (!actions[index].running)
{
stop();
dtr = actions[index].dtr;
}
}
/// <summary>
/// This method is called after the interval action is stopped.
/// </summary>
public override void stop()
{
base.stop();
actions[index].stop();
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionRepeat : ActionInterval
namespace coa4u
{
/// <summary>
/// Runs the given action the several times. Also can repeat the action forever.
/// </summary>
class ActionRepeat : ActionInterval
{
protected ActionInterval action;
protected int count;
protected int counter;
@@ -27,16 +32,25 @@ class ActionRepeat : ActionInterval
forever = true;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionRepeat((ActionInterval) action.clone(), count);
return new ActionRepeat((ActionInterval)action.clone(), count);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionRepeat((ActionInterval) action.reverse(), count);
return new ActionRepeat((ActionInterval)action.reverse(), count);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -45,14 +59,17 @@ class ActionRepeat : ActionInterval
counter = 0;
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void step(float dt)
{
dt *= timeScale;
if (action.isRunning())
if (action.running)
{
action.step(dt);
}
if (!action.isRunning() && (forever || counter < count - 1))
if (!action.running && (forever || counter < count - 1))
{
float dtrdata = action.dtr;
action.start();
@@ -60,10 +77,11 @@ class ActionRepeat : ActionInterval
action.step(dtrdata);
counter += 1;
}
else if (!action.isRunning() && counter >= count - 1)
else if (!action.running && counter >= count - 1)
{
dtr = action.dtr;
stop();
}
}
}
}

View File

@@ -2,27 +2,35 @@
using System.Collections.Generic;
using UnityEngine;
class ActionSequence : ActionInterval
namespace coa4u
{
protected Action[] actions;
/// <summary>
/// Runs several actions in a sequence.
/// </summary>
class ActionSequence : ActionInterval
{
protected ActionInstant[] actions;
protected int index;
public ActionSequence(Action action1, Action action2)
public ActionSequence(ActionInstant action1, ActionInstant action2)
: base(0)
{
actions = new Action[] {action1, action2};
actions = new ActionInstant[] { action1, action2 };
}
public ActionSequence(Action[] actionsList)
public ActionSequence(ActionInstant[] actionsList)
: base(0)
{
actions = actionsList;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
Action[] aList = new Action[actions.Length];
ActionInstant[] aList = new ActionInstant[actions.Length];
for (int i = 0; i < actions.Length; i++)
{
aList[i] = actions[i].clone();
@@ -30,9 +38,12 @@ class ActionSequence : ActionInterval
return new ActionSequence(aList);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
Action[] aList = new Action[actions.Length];
ActionInstant[] aList = new ActionInstant[actions.Length];
for (int i = 0; i < actions.Length; i++)
{
aList[actions.Length - 1 - i] = actions[i].reverse();
@@ -40,13 +51,16 @@ class ActionSequence : ActionInterval
return new ActionSequence(aList);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
index = 0;
actions[0].setActor(target);
actions[0].start();
while (!actions[index].isRunning() && index < actions.Length)
while (!actions[index].running && index < actions.Length)
{
index += 1;
actions[index].setActor(target);
@@ -54,31 +68,37 @@ class ActionSequence : ActionInterval
}
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void step(float dt)
{
dt *= timeScale;
float dtrdata = 0;
if (actions[index].isRunning())
if (actions[index].running)
{
actions[index].step(dt);
if (!actions[index].isRunning())
if (!actions[index].running)
dtrdata = actions[index].dtr;
}
while (!actions[index].isRunning() && index < actions.Length - 1)
while (!actions[index].running && index < actions.Length - 1)
{
index += 1;
actions[index].setActor(target);
actions[index].start();
if (actions[index].isRunning() && dtrdata > 0)
if (actions[index].running && dtrdata > 0)
actions[index].step(dtrdata);
}
if (!actions[index].isRunning())
if (!actions[index].running)
{
stop();
dtr = dtrdata;
}
}
/// <summary>
/// This method is called after the interval action is stopped.
/// </summary>
public override void stop()
{
base.stop();
@@ -87,4 +107,5 @@ class ActionSequence : ActionInterval
actions[i].stop();
}
}
}
}

View File

@@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using UnityEngine;
namespace coa4u
{
/// <summary>
/// This action stops all actions for the current target.
/// </summary>
class ActionStop : ActionInstant
{
public ActionStop()
: base()
{
}
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionStop();
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
target.StopAction();
}
}
}

View File

@@ -2,22 +2,42 @@
using System.Collections.Generic;
using UnityEngine;
class ActionHide : Action
namespace coa4u
{
/// <summary>
/// Instantly hides the target. This action does not require the transparency support in shaders.
/// </summary>
class ActionHide : ActionInstant
{
public ActionHide()
: base()
{
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionHide();
}
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionShow();
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
renderer.enabled = false;
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionLog : Action
namespace coa4u
{
/// <summary>
/// Prints a message in Unity debug console.
/// </summary>
class ActionLog : ActionInstant
{
string message;
public ActionLog(string tgtMessage)
@@ -12,9 +17,29 @@ class ActionLog : Action
message = tgtMessage;
}
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionLog(message);
}
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionLog(message);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
Debug.Log(message);
}
}
}

View File

@@ -2,8 +2,15 @@
using System.Collections.Generic;
using UnityEngine;
class ActionSendMessage : Action
namespace coa4u
{
/// <summary>
/// Sends the message to the current target. First, it checks the Actor's methods cache.
/// If the receiving method found in cache, it will be called directly without passing the message to the GameObject.
/// If there's no listener in cache, message will be sent GameObject (and Unity does it VERY slow).
/// </summary>
class ActionSendMessage : ActionInstant
{
protected string message;
protected object param;
protected SendMessageOptions options = SendMessageOptions.DontRequireReceiver;
@@ -29,16 +36,36 @@ class ActionSendMessage : Action
options = tgtOptions;
}
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionSendMessage(message, param, options);
}
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionSendMessage(message, param, options);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
if (param != null)
{
target.SendMessage(message, param);
target.ReceiveMessage(message, param, options);
}
else
{
target.SendMessage(message);
target.ReceiveMessage(message, options);
}
}
}
}

View File

@@ -0,0 +1,58 @@
using System;
using System.Collections.Generic;
using UnityEngine;
namespace coa4u
{
/// <summary>
/// Instantly rotates the target to face the given point or actor.
/// </summary>
class ActionSetDirection : ActionInstant
{
protected Vector3 value;
protected Actor other;
public ActionSetDirection(Vector3 tgtValue)
: base()
{
value = tgtValue;
}
public ActionSetDirection(Vector2 tgtValue)
: this((Vector3)tgtValue)
{
is2d = true;
}
public ActionSetDirection(Actor tgtActor)
: base()
{
other = tgtActor;
}
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionSetDirection(value);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
if (other != null)
{
value = other.transform.position;
}
if (is2d)
{
value.z = transform.position.z;
}
transform.rotation = Quaternion.LookRotation(transform.position - value);
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionSetPlace : Action
namespace coa4u
{
/// <summary>
/// Instantly moves the target to the given point.
/// </summary>
class ActionSetPlace : ActionInstant
{
protected Vector3 value;
public ActionSetPlace(Vector3 tgtPlace)
@@ -13,16 +18,22 @@ class ActionSetPlace : Action
}
public ActionSetPlace(Vector2 tgtPlace)
: this((Vector3) tgtPlace)
: this((Vector3)tgtPlace)
{
is2d = true;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionSetPlace(value);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -30,4 +41,5 @@ class ActionSetPlace : Action
value.z = transform.position.z;
transform.position = value;
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionSetRotation : Action
namespace coa4u
{
/// <summary>
/// Instantly rotates the target.
/// </summary>
class ActionSetRotation : ActionInstant
{
protected Vector3 value;
public ActionSetRotation(Vector3 tgtValue)
@@ -18,15 +23,21 @@ class ActionSetRotation : Action
is2d = true;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionSetRotation(value);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
transform.rotation = Quaternion.Euler(value);
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionSetTint : Action
namespace coa4u
{
/// <summary>
/// Instantly tints the target to the given color.
/// </summary>
class ActionSetTint : ActionInstant
{
public Vector4 color;
protected const float coeff = 1F / 255F;
@@ -13,9 +18,21 @@ class ActionSetTint : Action
color = tgtColor * coeff;
}
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionSetTint(color * 255F);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
renderer.material.color = new Color(color[0], color[1], color[2], color[3]);
}
}
}

View File

@@ -2,22 +2,42 @@
using System.Collections.Generic;
using UnityEngine;
class ActionShow : Action
namespace coa4u
{
/// <summary>
/// Instantly shows the hidden target. This action does not require the transparency support in shaders.
/// </summary>
class ActionShow : ActionInstant
{
public ActionShow()
: base()
{
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionShow();
}
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionHide();
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
renderer.enabled = true;
}
}
}

View File

@@ -2,17 +2,42 @@
using System.Collections.Generic;
using UnityEngine;
class ActionToggleVisibility : Action
namespace coa4u
{
/// <summary>
/// Instantly hides the target or showes it, if it's hidden. This action does not require the transparency support in shaders.
/// </summary>
class ActionToggleVisibility : ActionInstant
{
public ActionToggleVisibility()
: base()
{
}
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionToggleVisibility();
}
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionToggleVisibility();
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
renderer.enabled = !renderer.enabled;
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionBezierAbs : ActionInterval
namespace coa4u
{
/// <summary>
/// Moves the target with a cubic Bezier in absolute coordinates (if the target is not in the start point, it'll be positioned there when the action starts).
/// </summary>
class ActionBezierAbs : ActionInterval
{
protected Vector3 startPoint;
protected Vector3 endPoint;
protected Vector3 startControlPoint;
@@ -19,21 +24,30 @@ class ActionBezierAbs : ActionInterval
}
public ActionBezierAbs(Vector2 tgtStart, Vector2 tgtSCP, Vector2 tgtECP, Vector2 tgtEnd, float tgtDuration)
: this((Vector3) tgtStart, (Vector3) tgtSCP, (Vector3) tgtECP, (Vector3) tgtEnd, tgtDuration)
: this((Vector3)tgtStart, (Vector3)tgtSCP, (Vector3)tgtECP, (Vector3)tgtEnd, tgtDuration)
{
is2d = true;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionBezierAbs(startPoint, startControlPoint, endControlPoint, endPoint, duration);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionBezierAbs(endPoint, endControlPoint, startControlPoint, startPoint, duration);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -47,6 +61,9 @@ class ActionBezierAbs : ActionInterval
}
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void stepInterval(float dt)
{
float t = timer / duration;
@@ -56,4 +73,5 @@ class ActionBezierAbs : ActionInterval
3 * (startControlPoint - startPoint)) * t + startPoint;
transform.position = newPosition;
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionBezierRel : ActionInterval
namespace coa4u
{
/// <summary>
/// Moves the target with a cubic Bezier in relative coordinates.
/// </summary>
class ActionBezierRel : ActionInterval
{
protected Vector3 ep;
protected Vector3 cp1;
protected Vector3 cp2;
@@ -26,16 +31,25 @@ class ActionBezierRel : ActionInterval
is2d = true;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionBezierRel(startControlPoint, endControlPoint, endPoint, duration);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionBezierRel(-startControlPoint, -endControlPoint, -endPoint, duration);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -45,6 +59,9 @@ class ActionBezierRel : ActionInterval
endControlPoint = startControlPoint + cp2;
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void stepInterval(float dt)
{
float t = timer / duration;
@@ -54,4 +71,5 @@ class ActionBezierRel : ActionInterval
3 * (startControlPoint - startPoint)) * t + startPoint;
transform.position = newPosition;
}
}
}

View File

@@ -2,11 +2,16 @@
using System.Collections.Generic;
using UnityEngine;
class ActionBlink : ActionRepeat
namespace coa4u
{
/// <summary>
/// Blinks the target.
/// </summary>
class ActionBlink : ActionRepeat
{
protected bool randomDelay;
protected ActionDelay delay = new ActionDelay(0);
protected Action[] blinkSeq;
protected ActionInstant[] blinkSeq;
protected float durationMin;
protected float durationMax;
@@ -16,7 +21,7 @@ class ActionBlink : ActionRepeat
durationMin = tgtDuration;
durationMax = tgtDuration;
count = (tgtBlinks) * 2;
blinkSeq = new Action[]
blinkSeq = new ActionInstant[]
{
new ActionToggleVisibility(),
new ActionDelay(tgtDuration / tgtBlinks)
@@ -30,7 +35,7 @@ class ActionBlink : ActionRepeat
durationMin = tgtDurationMin;
durationMax = tgtDurationMax;
count = (tgtBlinks) * 2;
blinkSeq = new Action[]
blinkSeq = new ActionInstant[]
{
new ActionToggleVisibility(),
new ActionDelay(tgtDurationMin / tgtBlinks, tgtDurationMax / tgtBlinks)
@@ -38,13 +43,20 @@ class ActionBlink : ActionRepeat
action = new ActionSequence(blinkSeq);
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionBlink(count / 2 - 1, durationMin, durationMax);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionBlink(count / 2 - 1, durationMin, durationMax);
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionDelay : ActionInterval
namespace coa4u
{
/// <summary>
/// Delays the action for the given amount of seconds.
/// </summary>
class ActionDelay : ActionInterval
{
protected float durationMin;
protected float durationMax;
@@ -21,6 +26,9 @@ class ActionDelay : ActionInterval
durationMax = tgtDurationMax;
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
@@ -29,4 +37,5 @@ class ActionDelay : ActionInterval
duration = UnityEngine.Random.Range(durationMin, durationMax);
}
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionFadeBy : ActionInterval
namespace coa4u
{
/// <summary>
/// Fades the target by the given alpha value. The tartet shaders should support transparency in order to use this action.
/// </summary>
class ActionFadeBy : ActionInterval
{
protected float delta;
public ActionFadeBy(float tgtDelta, float tgtDuration)
@@ -12,16 +17,25 @@ class ActionFadeBy : ActionInterval
delta = tgtDelta;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionFadeBy(delta, duration);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionFadeBy(-delta, duration);
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void stepInterval(float dt)
{
float d = dt / duration;
@@ -29,4 +43,5 @@ class ActionFadeBy : ActionInterval
tgtColor[3] += delta * d;
renderer.material.color = tgtColor;
}
}
}

View File

@@ -2,21 +2,33 @@
using System.Collections.Generic;
using UnityEngine;
class ActionFadeIn : ActionFadeTo
namespace coa4u
{
/// <summary>
/// Fades in the target. The tartet shaders should support transparency in order to use this action.
/// </summary>
class ActionFadeIn : ActionFadeTo
{
public ActionFadeIn(float tgtDuration)
: base(1, tgtDuration)
{
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionFadeIn(duration);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionFadeIn(duration);
return new ActionFadeOut(duration);
}
}
}

View File

@@ -2,21 +2,33 @@
using System.Collections.Generic;
using UnityEngine;
class ActionFadeOut : ActionFadeTo
namespace coa4u
{
/// <summary>
/// Fades out the target. The tartet shaders should support transparency in order to use this action.
/// </summary>
class ActionFadeOut : ActionFadeTo
{
public ActionFadeOut(float tgtDuration)
: base(0, tgtDuration)
{
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionFadeOut(duration);
}
public override Action reverse()
/// <summary>
/// Returns the reversed version of the action, if it is possible.
/// </summary>
public override ActionInstant reverse()
{
return new ActionFadeOut(duration);
return new ActionFadeIn(duration);
}
}
}

View File

@@ -2,8 +2,13 @@
using System.Collections.Generic;
using UnityEngine;
class ActionFadeTo : ActionInterval
namespace coa4u
{
/// <summary>
/// Fades the target to the given alpha value. The tartet shaders should support transparency in order to use this action.
/// </summary>
class ActionFadeTo : ActionInterval
{
protected float value;
protected float delta;
@@ -13,17 +18,26 @@ class ActionFadeTo : ActionInterval
value = tgtValue;
}
public override Action clone()
/// <summary>
/// Returns a copy of the action.
/// </summary>
public override ActionInstant clone()
{
return new ActionFadeTo(value, duration);
}
/// <summary>
/// This method is called at the action start.
/// </summary>
public override void start()
{
base.start();
delta = value - renderer.material.color.a;
}
/// <summary>
/// This method is called every frame update.
/// </summary>
public override void stepInterval(float dt)
{
float d = dt / duration;
@@ -31,4 +45,5 @@ class ActionFadeTo : ActionInterval
tgtColor[3] += delta * d;
renderer.material.color = tgtColor;
}
}
}

View File

@@ -2,14 +2,16 @@
using System.Collections.Generic;
using UnityEngine;
class ActionJumpBy : ActionSequence
namespace coa4u
{
class ActionJumpBy : ActionSequence
{
protected Vector3 point;
float height;
int jumps;
public ActionJumpBy(Vector3 tgtPoint, float tgtHeight, int tgtJumps, float tgtDuration)
: base(new Action[tgtJumps])
: base(new ActionInstant[tgtJumps])
{
point = tgtPoint;
jumps = tgtJumps;
@@ -23,12 +25,12 @@ class ActionJumpBy : ActionSequence
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionJumpBy(point, height, jumps, duration);
}
public override Action reverse()
public override ActionInstant reverse()
{
return new ActionJumpBy(-point, height, jumps, duration);
}
@@ -46,4 +48,5 @@ class ActionJumpBy : ActionSequence
}
base.start();
}
}
}

View File

@@ -2,14 +2,16 @@
using System.Collections.Generic;
using UnityEngine;
class ActionJumpTo : ActionSequence
namespace coa4u
{
class ActionJumpTo : ActionSequence
{
protected Vector3 point;
float height;
int jumps;
public ActionJumpTo(Vector3 tgtPoint, float tgtHeight, int tgtJumps, float tgtDuration)
: base(new Action[tgtJumps])
: base(new ActionInstant[tgtJumps])
{
point = tgtPoint;
jumps = tgtJumps;
@@ -23,7 +25,7 @@ class ActionJumpTo : ActionSequence
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionJumpTo(point, height, jumps, duration);
}
@@ -44,4 +46,5 @@ class ActionJumpTo : ActionSequence
}
base.start();
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionMoveBy : ActionInterval
namespace coa4u
{
class ActionMoveBy : ActionInterval
{
protected Vector3 delta;
public ActionMoveBy(Vector3 tgtDelta, float tgtDuration)
@@ -13,17 +15,17 @@ class ActionMoveBy : ActionInterval
}
public ActionMoveBy(Vector2 tgtValue, float tgtDuration)
: this((Vector3) tgtValue, tgtDuration)
: this((Vector3)tgtValue, tgtDuration)
{
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionMoveBy(delta, duration);
}
public override Action reverse()
public override ActionInstant reverse()
{
return new ActionMoveBy(delta * -1F, duration);
}
@@ -34,4 +36,5 @@ class ActionMoveBy : ActionInterval
Vector3 tgt = delta * d;
transform.Translate(tgt, Space.World);
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionMoveTo : ActionInterval
namespace coa4u
{
class ActionMoveTo : ActionInterval
{
protected Vector3 value;
protected Vector3 path;
@@ -14,12 +16,12 @@ class ActionMoveTo : ActionInterval
}
public ActionMoveTo(Vector2 tgtValue, float tgtDuration)
: this((Vector3) tgtValue, tgtDuration)
: this((Vector3)tgtValue, tgtDuration)
{
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionMoveBy(value, duration);
}
@@ -38,4 +40,5 @@ class ActionMoveTo : ActionInterval
Vector3 tgt = path * d;
transform.Translate(tgt, Space.World);
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionRotateBy : ActionInterval
namespace coa4u
{
class ActionRotateBy : ActionInterval
{
protected Vector3 delta;
public ActionRotateBy(Vector3 tgtDelta, float tgtDuration)
@@ -18,12 +20,12 @@ class ActionRotateBy : ActionInterval
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionRotateBy(delta, duration);
}
public override Action reverse()
public override ActionInstant reverse()
{
return new ActionRotateBy(delta * -1F, duration);
}
@@ -34,4 +36,5 @@ class ActionRotateBy : ActionInterval
Vector3 tgt = delta * d;
transform.rotation = Quaternion.Euler(transform.rotation.eulerAngles + tgt);
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionRotateTo : ActionInterval
namespace coa4u
{
class ActionRotateTo : ActionInterval
{
protected Vector3 value;
protected Vector3 path;
@@ -19,7 +21,7 @@ class ActionRotateTo : ActionInterval
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionRotateTo(value, duration);
}
@@ -44,4 +46,5 @@ class ActionRotateTo : ActionInterval
Vector3 tgt = path * d;
transform.rotation = Quaternion.Euler(transform.rotation.eulerAngles + tgt);
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionScaleBy : ActionInterval
namespace coa4u
{
class ActionScaleBy : ActionInterval
{
protected Vector3 delta;
protected Vector3 path;
@@ -19,12 +21,12 @@ class ActionScaleBy : ActionInterval
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionScaleBy(delta, duration);
}
public override Action reverse()
public override ActionInstant reverse()
{
return new ActionScaleBy(delta * -1F, duration);
}
@@ -50,4 +52,5 @@ class ActionScaleBy : ActionInterval
{
base.stop();
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionScaleTo : ActionInterval
namespace coa4u
{
class ActionScaleTo : ActionInterval
{
protected Vector3 value;
protected Vector3 path;
@@ -14,12 +16,12 @@ class ActionScaleTo : ActionInterval
}
public ActionScaleTo(Vector2 tgtValue, float tgtDuration)
: this((Vector3) tgtValue, tgtDuration)
: this((Vector3)tgtValue, tgtDuration)
{
is2d = true;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionScaleTo(value, duration);
}
@@ -38,4 +40,5 @@ class ActionScaleTo : ActionInterval
Vector3 tgt = path * d;
transform.localScale += tgt;
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionSkewBy : ActionInterval
namespace coa4u
{
class ActionSkewBy : ActionInterval
{
protected Vector3 skewAngles1;
protected Vector3 skewAngles2;
protected Mesh mesh;
@@ -15,12 +17,12 @@ class ActionSkewBy : ActionInterval
skewAngles2 = tgtAngles2;
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionSkewBy(skewAngles1, skewAngles2, duration);
}
public override Action reverse()
public override ActionInstant reverse()
{
return new ActionSkewBy(-skewAngles1, -skewAngles2, duration);
}
@@ -28,9 +30,9 @@ class ActionSkewBy : ActionInterval
public override void start()
{
base.start();
if (!(target is MeshActor))
if (!(target is Actor))
{
throw new Exception("You should use MeshActor class instead of Actor, if you want to skew your object.");
throw new Exception("You should use Actor class instead of Actor, if you want to skew your object.");
}
}
@@ -38,8 +40,9 @@ class ActionSkewBy : ActionInterval
{
float d = dt / duration;
Vector3 tgt = skewAngles1 * d;
((MeshActor)target).skewAngles1 += tgt;
((Actor)target).skewAngles1 += tgt;
tgt = skewAngles2 * d;
((MeshActor)target).skewAngles2 += tgt;
((Actor)target).skewAngles2 += tgt;
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionTintBy : ActionInterval
namespace coa4u
{
class ActionTintBy : ActionInterval
{
protected Vector4 color;
protected const float coeff = 1F / 255F;
@@ -18,12 +20,12 @@ class ActionTintBy : ActionInterval
{
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionTintBy(color / coeff, duration);
}
public override Action reverse()
public override ActionInstant reverse()
{
return new ActionTintBy(-color / coeff, duration);
}
@@ -39,4 +41,5 @@ class ActionTintBy : ActionInterval
tgtColor[3] += tgt[3];
renderer.material.color = tgtColor;
}
}
}

View File

@@ -2,8 +2,10 @@
using System.Collections.Generic;
using UnityEngine;
class ActionTintTo : ActionInterval
namespace coa4u
{
class ActionTintTo : ActionInterval
{
protected Vector4 color;
protected Vector4 path;
protected const float coeff = 1F / 255F;
@@ -20,7 +22,7 @@ class ActionTintTo : ActionInterval
{
}
public override Action clone()
public override ActionInstant clone()
{
return new ActionTintTo(color / coeff, duration);
}
@@ -46,4 +48,5 @@ class ActionTintTo : ActionInterval
tgtColor[3] += tgt[3];
renderer.material.color = tgtColor;
}
}
}

View File

@@ -0,0 +1,53 @@
using System;
using System.Collections.Generic;
using UnityEngine;
namespace coa4u
{
public class MethodHolder
{
protected Action method;
protected string methodName;
public MethodHolder()
{
}
public MethodHolder(Action tgtMethod)
{
method = tgtMethod;
methodName = tgtMethod.Method.Name;
}
public virtual void run(object param = null)
{
if (method != null)
method.Invoke();
}
public string name
{
get
{
return methodName;
}
}
}
public class MethodHolder<T> : MethodHolder
{
protected Action<T> methodParam;
public MethodHolder(Action<T> tgtMethod)
{
methodParam = tgtMethod;
methodName = tgtMethod.Method.Name;
}
public override void run(object param)
{
if (methodParam != null)
methodParam.Invoke((T)param);
}
}
}

View File

@@ -1,42 +1,126 @@
using UnityEngine;
using System;
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using coa4u;
/// <summary>
/// The default Actor class for the Action system.
/// </summary>
public class Actor : MonoBehaviour
{
protected Action action;
protected Dictionary<string, MethodHolder> methodsCache = new Dictionary<string, MethodHolder>();
protected ActionInstant action;
private bool paused = false;
protected Vector3 angles1prev = Vector3.zero;
protected Vector3 angles2prev = Vector3.zero;
protected const float coeff = Mathf.PI / 180;
protected Vector3[] initialState;
public Transform transformCached;
public Renderer rendererCached;
public Mesh meshCached;
public Vector3 skewAngles1;
public Vector3 skewAngles2;
/// <summary>
/// This method is called when the script instance is being loaded.
/// </summary>
protected void Awake()
{
transformCached = gameObject.transform;
rendererCached = gameObject.renderer;
meshCached = gameObject.GetComponent<MeshFilter>().mesh;
initialState = meshCached.vertices;
}
/// <summary>
/// This method is called at every frame update.
/// </summary>
protected void Update()
{
if (paused || action == null)
return;
if (action.isRunning())
if (action.running)
action.step(Time.deltaTime);
if (skewAngles1 != angles1prev || skewAngles2 != angles2prev)
updateSkew();
}
public void AttachAction(Action tgtAction)
/// <summary>
/// Updates the skew for the mesh.
/// </summary>
void updateSkew()
{
Matrix4x4 m = Matrix4x4.zero;
m[0, 0] = 1;
m[1, 1] = 1;
m[2, 2] = 1;
m[3, 3] = 1;
m[0, 1] = Mathf.Tan(skewAngles1.x * coeff); // skewing in xy
m[0, 2] = Mathf.Tan(skewAngles2.x * coeff); // skewing in xz
m[1, 0] = Mathf.Tan(skewAngles1.y * coeff); // skewing in yx
m[1, 2] = Mathf.Tan(skewAngles2.y * coeff); // skewing in yz
m[2, 0] = Mathf.Tan(skewAngles1.z * coeff); // skewing in zx
m[2, 1] = Mathf.Tan(skewAngles2.z * coeff); // skewing in zy
Vector3[] verts = new Vector3[initialState.Length];
int i = 0;
while (i < verts.Length)
{
verts[i] = m.MultiplyPoint3x4(initialState[i]);
i++;
}
meshCached.vertices = verts;
angles1prev = skewAngles1;
angles2prev = skewAngles2;
}
/// <summary>
/// Attaches and starts the action.
/// </summary>
public void AttachAction(ActionInstant tgtAction)
{
if (action != null)
{
action.stop();
}
action = tgtAction;
action.setActor(this);
action.start();
}
/// <summary>
/// Stops all running actions for this actor.
/// </summary>
public void StopAction()
{
if (action == null)
return;
if (action.running)
action.stop();
action = null;
}
/// <summary>
/// Pauses actions for this actor.
/// </summary>
public void PauseAction()
{
paused = true;
}
/// <summary>
/// Unpauses actions for this actor.
/// </summary>
public void UnpauseAction()
{
paused = false;
}
/// <summary>
/// Sets the timescale for current action.
/// </summary>
public void SetTimeScale(float ts)
{
if (action is ActionInterval)
@@ -44,4 +128,40 @@ public class Actor : MonoBehaviour
((ActionInterval)action).setTimeScale(ts);
}
}
/// <summary>
/// Adds method to cache to speed-up
/// </summary>
public void AddMethodToCache(MethodHolder method)
{
methodsCache.Add(method.name, method);
}
public void RemoveMethodFromCache(string key)
{
if (methodsCache.ContainsKey(key))
{
methodsCache.Remove(key);
}
else
{
throw new Exception("Method " + key + " not found in cache.");
}
}
public void ReceiveMessage(string key, object param = null, SendMessageOptions options = SendMessageOptions.DontRequireReceiver)
{
if (methodsCache.ContainsKey(key))
{
if (param == null)
methodsCache[key].run();
else
methodsCache[key].run(param);
}
else
{
gameObject.SendMessage(key, param, options);
}
}
}

View File

@@ -1,14 +1,15 @@
using UnityEngine;
using System.Collections;
using coa4u;
public class ActorSampleActions : MeshActor
public class ActorSampleActions : Actor
{
public void Start()
{
Action seq = new ActionRepeat (new ActionSequence(new Action[]
ActionInstant seq = new ActionRepeat (new ActionSequence(new ActionInstant[]
{
new ActionFadeIn(2),
new ActionParallel(new Action[] {
new ActionParallel(new ActionInstant[] {
new ActionMoveBy(new Vector3(10, 10, 0), 1),
new ActionRotateBy(new Vector3(90, 90, 0), 1),
new ActionTintBy(new Vector4(-50, 50, -150), 1)
@@ -32,9 +33,23 @@ public class ActorSampleActions : MeshActor
new ActionScaleTo(new Vector3(2, 2, 2), 1),
new ActionRotateTo(new Vector3(0, 0, 0), 1),
new ActionFadeOut(2),
new ActionSetTint(new Vector4(67, 105, 181))
new ActionSetTint(new Vector4(67, 105, 181)),
new ActionSendMessage("msgHello"),
new ActionSendMessage("msgHelloTo", "world"),
}), 5);
SetTimeScale(2);
this.AttachAction(seq);
AddMethodToCache(new MethodHolder(msgHello));
AddMethodToCache(new MethodHolder<string>(msgHelloTo));
}
void msgHello()
{
Debug.Log("Hello!");
}
void msgHelloTo(string who)
{
Debug.Log("Hello " + who.ToString() + "!");
}
}

View File

@@ -1,54 +0,0 @@
using UnityEngine;
using System.Collections;
[System.Serializable]
public class MeshActor : Actor
{
public Vector3 skewAngles1;
public Vector3 skewAngles2;
protected Vector3 angles1prev = Vector3.zero;
protected Vector3 angles2prev = Vector3.zero;
protected const float coeff = Mathf.PI/180;
protected Mesh mesh;
protected Vector3[] initialState;
void Awake()
{
mesh = gameObject.GetComponent<MeshFilter>().mesh;
initialState = mesh.vertices;
}
protected void Update()
{
base.Update();
if (skewAngles1 != angles1prev || skewAngles2 != angles2prev)
updateMesh();
}
protected void updateMesh()
{
Matrix4x4 m = Matrix4x4.zero;
m[0, 0] = 1;
m[1, 1] = 1;
m[2, 2] = 1;
m[3, 3] = 1;
m[0, 1] = Mathf.Tan(skewAngles1.x * coeff); // skewing in xy
m[0, 2] = Mathf.Tan(skewAngles2.x * coeff); // skewing in xz
m[1, 0] = Mathf.Tan(skewAngles1.y * coeff); // skewing in yx
m[1, 2] = Mathf.Tan(skewAngles2.y * coeff); // skewing in yz
m[2, 0] = Mathf.Tan(skewAngles1.z * coeff); // skewing in zx
m[2, 1] = Mathf.Tan(skewAngles2.z * coeff); // skewing in zy
Vector3[] verts = new Vector3[initialState.Length];
int i = 0;
while (i < verts.Length)
{
verts[i] = m.MultiplyPoint3x4(initialState[i]);
i++;
}
mesh.vertices = verts;
angles1prev = skewAngles1;
angles2prev = skewAngles2;
}
}