MegaFlowMovingSource.cs 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228
  1. 
  2. using UnityEngine;
  3. using System.Collections.Generic;
  4. [System.Serializable]
  5. public class MegaFlowPosFrame
  6. {
  7. public float time;
  8. public int frame;
  9. }
  10. public class MegaFlowMovingSource : MonoBehaviour
  11. {
  12. public MegaFlow source;
  13. public int framenum;
  14. public Transform target;
  15. public float flowtime = 10.0f;
  16. public float flowtimestep = 0.25f;
  17. public float flowscale = 1.0f;
  18. public float mindist = 1.0f;
  19. public bool drawpath = true;
  20. List<MegaFlowPos> flowpositions = new List<MegaFlowPos>();
  21. MegaFlowFrame flow;
  22. float ftime = 0.0f;
  23. Vector3 lastpos;
  24. Matrix4x4 framegizmotm;
  25. Matrix4x4 frametm;
  26. public bool usefalloff = false;
  27. public AnimationCurve falloffcrv = new AnimationCurve(new Keyframe(0, 1), new Keyframe(1, 1));
  28. public List<MegaFlowPosFrame> frames = new List<MegaFlowPosFrame>();
  29. [ContextMenu("Help")]
  30. public void Help()
  31. {
  32. Application.OpenURL("http://www.west-racing.com/mf/?page_id=6105");
  33. }
  34. void Start()
  35. {
  36. if ( target )
  37. lastpos = target.position;
  38. }
  39. void Update()
  40. {
  41. if ( source && target )
  42. {
  43. flow = source.frames[framenum];
  44. SaveFlowPosition(target.position, target.rotation, (target.position - lastpos) / Time.deltaTime, flowscale);
  45. lastpos = target.position;
  46. }
  47. }
  48. void ProcessPos()
  49. {
  50. for ( int i = 0; i < flowpositions.Count; i++ )
  51. {
  52. MegaFlowPos fpos = flowpositions[i];
  53. fpos.fpos += fpos.vel * Time.deltaTime;
  54. fpos.time -= Time.deltaTime;
  55. fpos.alpha = 1.0f - (fpos.time / fpos.stime);
  56. if ( usefalloff )
  57. fpos.falloff = falloffcrv.Evaluate(fpos.alpha);
  58. else
  59. fpos.falloff = 1.0f;
  60. if ( fpos.time < 0.0f )
  61. {
  62. flowpositions.RemoveAt(i);
  63. i--;
  64. }
  65. else
  66. {
  67. if ( frames.Count > 0 )
  68. {
  69. fpos.frame = 0;
  70. for ( int f = frames.Count - 1; f >= 0; f-- )
  71. {
  72. if ( fpos.alpha > frames[f].time )
  73. {
  74. fpos.frame = f;
  75. break;
  76. }
  77. }
  78. }
  79. }
  80. }
  81. }
  82. void AddPos(Vector3 pos, Vector3 vel, Matrix4x4 tm, Matrix4x4 tm1, float flowscale)
  83. {
  84. MegaFlowPos fpos = new MegaFlowPos();
  85. fpos.Set(pos, vel, tm, tm1, flowscale, flowtime);
  86. flowpositions.Add(fpos);
  87. }
  88. void UpdateLast(Vector3 pos, Vector3 vel, Matrix4x4 tm, Matrix4x4 tm1, float flowscale)
  89. {
  90. MegaFlowPos fpos = flowpositions[flowpositions.Count - 1];
  91. fpos.Set(pos, vel, tm, tm1, flowscale, flowtime);
  92. }
  93. public void SaveFlowPosition(Vector3 pos, Quaternion rot, Vector3 vel, float flowscale)
  94. {
  95. Matrix4x4 offtm = Matrix4x4.TRS(-flow.size * 0.5f, Quaternion.identity, Vector3.one);
  96. framegizmotm = transform.localToWorldMatrix * offtm;
  97. Matrix4x4 offtm1 = Matrix4x4.TRS(flow.size * 0.5f, Quaternion.identity, Vector3.one);
  98. frametm = offtm1 * transform.worldToLocalMatrix;
  99. ProcessPos();
  100. if ( flowpositions.Count == 0 )
  101. AddPos(pos, vel, framegizmotm, frametm, flowscale);
  102. if ( flowpositions.Count == 1 )
  103. AddPos(pos, vel, framegizmotm, frametm, flowscale);
  104. ftime += Time.deltaTime;
  105. if ( ftime >= flowtimestep )
  106. {
  107. if ( (pos - flowpositions[flowpositions.Count - 2].pos).magnitude > mindist )
  108. {
  109. ftime -= flowtimestep;
  110. AddPos(pos, vel, framegizmotm, frametm, flowscale);
  111. }
  112. else
  113. {
  114. UpdateLast(pos, vel, framegizmotm, frametm, flowscale);
  115. ftime += Time.deltaTime;
  116. }
  117. }
  118. else
  119. UpdateLast(pos, vel, framegizmotm, frametm, flowscale);
  120. }
  121. public Vector3 FindFlowPos(Vector3 pos, ref bool inbounds, ref Matrix4x4 tm, ref float fvel, ref int frame, ref float falloff)
  122. {
  123. Vector3 fpos = Vector3.zero;
  124. float closest = float.MaxValue;
  125. int index = -1;
  126. for ( int i = 0; i < flowpositions.Count; i++ )
  127. {
  128. fpos = flowpositions[i].pos;
  129. fpos.x -= pos.x;
  130. fpos.y -= pos.y;
  131. fpos.z -= pos.z;
  132. float sdist = (fpos.x * fpos.x) + (fpos.y * fpos.y) + (fpos.z * fpos.z);
  133. if ( sdist < closest )
  134. {
  135. closest = sdist;
  136. index = i;
  137. }
  138. }
  139. if ( index >= 0 )
  140. {
  141. inbounds = true;
  142. tm = flowpositions[index].invtm1;
  143. fpos = flowpositions[index].tm1.MultiplyPoint3x4(pos);
  144. fpos.y += flowpositions[index].fpos;
  145. fvel = flowpositions[index].vel;
  146. frame = flowpositions[index].frame;
  147. falloff = flowpositions[index].falloff;
  148. }
  149. else
  150. inbounds = false;
  151. return fpos;
  152. }
  153. public void DrawMoveGizmo()
  154. {
  155. if ( source )
  156. flow = source.frames[framenum];
  157. if ( flow )
  158. {
  159. Matrix4x4 offtm = Matrix4x4.TRS(-flow.size * 0.5f, Quaternion.identity, Vector3.one);
  160. framegizmotm = transform.localToWorldMatrix * offtm;
  161. Gizmos.matrix = framegizmotm;
  162. Vector3 min = Vector3.zero;
  163. Vector3 max = flow.size;
  164. MegaFlow.DrawBox(min, max);
  165. Gizmos.matrix = Matrix4x4.identity;
  166. }
  167. }
  168. void OnDrawGizmos()
  169. {
  170. if ( drawpath )
  171. {
  172. Gizmos.color = Color.grey;
  173. if ( flowpositions.Count > 0 )
  174. {
  175. Vector3 lpos = Vector3.zero;
  176. for ( int i = 0; i < flowpositions.Count; i++ )
  177. {
  178. MegaFlowPos fpos = flowpositions[i];
  179. Gizmos.color = Color.white;
  180. if ( i > 0 )
  181. Gizmos.DrawLine(lpos, fpos.pos);
  182. Gizmos.color = Color.green;
  183. Gizmos.DrawSphere(fpos.pos, 0.1f);
  184. lpos = fpos.pos;
  185. }
  186. }
  187. DrawMoveGizmo();
  188. }
  189. Gizmos.DrawIcon(transform.position, "MegaFlowIcon.png", true);
  190. }
  191. }