RibbonTrail.cs 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554
  1. using System;
  2. using System.Collections.Generic;
  3. using UnityEngine;
  4. namespace Xft
  5. {
  6. public class RibbonTrail : RenderObject
  7. {
  8. public RibbonTrail(VertexPool.VertexSegment segment, bool useFaceObj, Transform faceobj, float width, int maxelemnt, float len, Vector3 pos, float maxFps)
  9. {
  10. if (maxelemnt <= 2)
  11. {
  12. UnityEngine.Debug.LogError("ribbon trail's maxelement should > 2!");
  13. }
  14. this.MaxElements = maxelemnt;
  15. this.Vertexsegment = segment;
  16. this.ElementArray = new RibbonTrail.Element[this.MaxElements];
  17. this.Head = (this.Tail = 99999);
  18. this.OriHeadPos = pos;
  19. this.SetTrailLen(len);
  20. this.UnitWidth = width;
  21. this.HeadPosition = pos;
  22. Vector3 vector;
  23. if (this.UseFaceObject)
  24. {
  25. vector = faceobj.position - this.HeadPosition;
  26. }
  27. else
  28. {
  29. vector = Vector3.zero;
  30. }
  31. RibbonTrail.Element element = new RibbonTrail.Element(this.HeadPosition, this.UnitWidth);
  32. element.Normal = vector.normalized;
  33. this.IndexDirty = false;
  34. this.AddElememt(element);
  35. this.AddElememt(new RibbonTrail.Element(this.HeadPosition, this.UnitWidth)
  36. {
  37. Normal = vector.normalized
  38. });
  39. for (int i = 0; i < this.MaxElements; i++)
  40. {
  41. this.ElementPool.Add(new RibbonTrail.Element(this.HeadPosition, this.UnitWidth));
  42. }
  43. this.UseFaceObject = useFaceObj;
  44. this.FaceObject = faceobj;
  45. }
  46. public override void ApplyShaderParam(float x, float y)
  47. {
  48. Vector2 one = Vector2.one;
  49. one.x = x;
  50. one.y = y;
  51. VertexPool pool = this.Vertexsegment.Pool;
  52. int vertStart = this.Vertexsegment.VertStart;
  53. for (int i = 0; i < this.Vertexsegment.VertCount; i++)
  54. {
  55. pool.UVs2[vertStart + i] = one;
  56. }
  57. this.Vertexsegment.Pool.UV2Changed = true;
  58. }
  59. public override void Initialize(EffectNode node)
  60. {
  61. base.Initialize(node);
  62. this.SetUVCoord(node.LowerLeftUV, node.UVDimensions);
  63. this.SetColor(node.Color);
  64. this.SetHeadPosition(node.GetRealClientPos() + node.Position);
  65. this.ResetElementsPos();
  66. this.mLastClientPos = node.Owner.ClientTransform.position;
  67. }
  68. public override void Reset()
  69. {
  70. Vector3 headPosition;
  71. if (this.Node.Owner.AlwaysSyncRotation)
  72. {
  73. headPosition = this.Node.ClientTrans.rotation * (this.Node.GetRealClientPos() + this.Node.Owner.EmitPoint);
  74. }
  75. else
  76. {
  77. headPosition = this.Node.GetRealClientPos() + this.Node.Owner.EmitPoint;
  78. }
  79. this.SetHeadPosition(headPosition);
  80. this.ResetElementsPos();
  81. this.StretchCount = 0;
  82. this.SetColor(Color.clear);
  83. this.UpdateVertices(Vector3.zero);
  84. this.mLastClientPos = this.Node.Owner.ClientTransform.position;
  85. }
  86. public override void Update(float deltaTime)
  87. {
  88. this.SetHeadPosition(this.Node.CurWorldPos);
  89. if (this.Node.Owner.UVAffectorEnable || this.Node.Owner.UVRotAffectorEnable || this.Node.Owner.UVScaleAffectorEnable)
  90. {
  91. this.SetUVCoord(this.Node.LowerLeftUV, this.Node.UVDimensions);
  92. }
  93. if (this.Node.Owner.SyncTrailWithClient)
  94. {
  95. this.CheckUpdateSync();
  96. }
  97. this.SetColor(this.Node.Color);
  98. this.MyUpdate(deltaTime);
  99. }
  100. private void CheckUpdateSync()
  101. {
  102. Vector3 b = this.Node.Owner.ClientTransform.position - this.mLastClientPos;
  103. this.mLastClientPos = this.Node.Owner.ClientTransform.position;
  104. if (this.Head != 99999 && this.Head != this.Tail)
  105. {
  106. int num = this.Head + 1;
  107. for (;;)
  108. {
  109. int num2 = num;
  110. if (num2 == this.MaxElements)
  111. {
  112. num2 = 0;
  113. }
  114. this.ElementArray[num2].Position += b;
  115. if (num2 == this.Tail)
  116. {
  117. break;
  118. }
  119. num = num2 + 1;
  120. }
  121. }
  122. }
  123. public void ResetElementsPos()
  124. {
  125. if (this.Head != 99999 && this.Head != this.Tail)
  126. {
  127. int num = this.Head;
  128. for (;;)
  129. {
  130. int num2 = num;
  131. if (num2 == this.MaxElements)
  132. {
  133. num2 = 0;
  134. }
  135. this.ElementArray[num2].Position = this.OriHeadPos;
  136. if (num2 == this.Tail)
  137. {
  138. break;
  139. }
  140. num = num2 + 1;
  141. }
  142. }
  143. }
  144. public void SetUVCoord(Vector2 lowerleft, Vector2 dimensions)
  145. {
  146. this.LowerLeftUV = lowerleft;
  147. this.UVDimensions = dimensions;
  148. XftTools.TopLeftUVToLowerLeft(ref this.LowerLeftUV, ref this.UVDimensions);
  149. }
  150. public void SetColor(Color color)
  151. {
  152. this.Color = color;
  153. }
  154. public void SetTrailLen(float len)
  155. {
  156. this.TrailLength = len;
  157. this.ElemLength = this.TrailLength / (float)(this.MaxElements - 2);
  158. this.SquaredElemLength = this.ElemLength * this.ElemLength;
  159. }
  160. public void SetHeadPosition(Vector3 pos)
  161. {
  162. this.HeadPosition = pos;
  163. }
  164. public int GetStretchCount()
  165. {
  166. return this.StretchCount;
  167. }
  168. public void Smooth()
  169. {
  170. if (this.ElemCount <= 3)
  171. {
  172. return;
  173. }
  174. RibbonTrail.Element element = this.ElementArray[this.Head];
  175. int num = this.Head + 1;
  176. if (num == this.MaxElements)
  177. {
  178. num = 0;
  179. }
  180. int num2 = num + 1;
  181. if (num2 == this.MaxElements)
  182. {
  183. num2 = 0;
  184. }
  185. RibbonTrail.Element element2 = this.ElementArray[num];
  186. RibbonTrail.Element element3 = this.ElementArray[num2];
  187. Vector3 from = element.Position - element2.Position;
  188. Vector3 to = element2.Position - element3.Position;
  189. float num3 = Vector3.Angle(from, to);
  190. if (num3 > 60f)
  191. {
  192. Vector3 a = (element.Position + element3.Position) / 2f;
  193. Vector3 vector = a - element2.Position;
  194. Vector3 zero = Vector3.zero;
  195. float smoothTime = 0.1f / (num3 / 60f);
  196. element2.Position = Vector3.SmoothDamp(element2.Position, element2.Position + vector.normalized * element2.Width, ref zero, smoothTime);
  197. }
  198. }
  199. private void ScaleLength()
  200. {
  201. float num = this.Node.Scale.y;
  202. num = Mathf.Clamp(num, 0.1f, num);
  203. this.SetTrailLen(this.Node.Owner.RibbonLen * num);
  204. }
  205. public void MyUpdate(float deltaTime)
  206. {
  207. this.ElapsedTime += deltaTime;
  208. if (this.ElapsedTime < base.Fps)
  209. {
  210. return;
  211. }
  212. this.ElapsedTime -= base.Fps;
  213. if (this.Node.Owner.ScaleAffectorEnable)
  214. {
  215. this.ScaleLength();
  216. }
  217. bool flag = false;
  218. Vector3 b = Vector3.one * this.Node.Owner.Owner.Scale;
  219. while (!flag)
  220. {
  221. RibbonTrail.Element element = this.ElementArray[this.Head];
  222. int num = this.Head + 1;
  223. if (num == this.MaxElements)
  224. {
  225. num = 0;
  226. }
  227. RibbonTrail.Element element2 = this.ElementArray[num];
  228. Vector3 headPosition = this.HeadPosition;
  229. Vector3 a = headPosition - element2.Position;
  230. float sqrMagnitude = a.sqrMagnitude;
  231. if (sqrMagnitude >= this.SquaredElemLength)
  232. {
  233. this.StretchCount++;
  234. Vector3 b2 = a * (this.ElemLength / a.magnitude);
  235. element.Position = element2.Position + b2;
  236. RibbonTrail.Element element3 = this.ElementPool[0];
  237. this.ElementPool.RemoveAt(0);
  238. element3.Position = headPosition;
  239. element3.Width = this.UnitWidth;
  240. if (this.UseFaceObject)
  241. {
  242. element3.Normal = this.FaceObject.position - Vector3.Scale(headPosition, b);
  243. }
  244. else
  245. {
  246. element3.Normal = Vector3.zero;
  247. }
  248. this.AddElememt(element3);
  249. a = headPosition - element.Position;
  250. if (a.sqrMagnitude <= this.SquaredElemLength)
  251. {
  252. flag = true;
  253. }
  254. }
  255. else
  256. {
  257. element.Position = headPosition;
  258. flag = true;
  259. }
  260. if ((this.Tail + 1) % this.MaxElements == this.Head)
  261. {
  262. RibbonTrail.Element element4 = this.ElementArray[this.Tail];
  263. int num2;
  264. if (this.Tail == 0)
  265. {
  266. num2 = this.MaxElements - 1;
  267. }
  268. else
  269. {
  270. num2 = this.Tail - 1;
  271. }
  272. RibbonTrail.Element element5 = this.ElementArray[num2];
  273. Vector3 vector = element4.Position - element5.Position;
  274. float magnitude = vector.magnitude;
  275. if ((double)magnitude > 1E-06)
  276. {
  277. float num3 = this.ElemLength - a.magnitude;
  278. vector *= num3 / magnitude;
  279. element4.Position = element5.Position + vector;
  280. }
  281. }
  282. }
  283. Vector3 position = this.Node.MyCamera.transform.position;
  284. this.UpdateVertices(position);
  285. this.UpdateIndices();
  286. }
  287. public void UpdateIndices()
  288. {
  289. if (!this.IndexDirty)
  290. {
  291. return;
  292. }
  293. VertexPool pool = this.Vertexsegment.Pool;
  294. if (this.Head != 99999 && this.Head != this.Tail)
  295. {
  296. int num = this.Head;
  297. int num2 = 0;
  298. for (;;)
  299. {
  300. int num3 = num + 1;
  301. if (num3 == this.MaxElements)
  302. {
  303. num3 = 0;
  304. }
  305. if (num3 * 2 >= 65536)
  306. {
  307. UnityEngine.Debug.LogError("Too many elements!");
  308. }
  309. int num4 = this.Vertexsegment.VertStart + num3 * 2;
  310. int num5 = this.Vertexsegment.VertStart + num * 2;
  311. int num6 = this.Vertexsegment.IndexStart + num2 * 6;
  312. pool.Indices[num6] = num5;
  313. pool.Indices[num6 + 1] = num5 + 1;
  314. pool.Indices[num6 + 2] = num4;
  315. pool.Indices[num6 + 3] = num5 + 1;
  316. pool.Indices[num6 + 4] = num4 + 1;
  317. pool.Indices[num6 + 5] = num4;
  318. if (num3 == this.Tail)
  319. {
  320. break;
  321. }
  322. num = num3;
  323. num2++;
  324. }
  325. pool.IndiceChanged = true;
  326. }
  327. this.IndexDirty = false;
  328. }
  329. public void UpdateVertices(Vector3 eyePos)
  330. {
  331. float num = 0f;
  332. float num2 = this.ElemLength * (float)(this.MaxElements - 2);
  333. Vector3 b = Vector3.one * this.Node.Owner.Owner.Scale;
  334. if (this.Head != 99999 && this.Head != this.Tail)
  335. {
  336. int num3 = this.Head;
  337. int num4 = this.Head;
  338. for (;;)
  339. {
  340. if (num4 == this.MaxElements)
  341. {
  342. num4 = 0;
  343. }
  344. RibbonTrail.Element element = this.ElementArray[num4];
  345. if (num4 * 2 >= 65536)
  346. {
  347. UnityEngine.Debug.LogError("Too many elements!");
  348. }
  349. int num5 = this.Vertexsegment.VertStart + num4 * 2;
  350. int num6 = num4 + 1;
  351. if (num6 == this.MaxElements)
  352. {
  353. num6 = 0;
  354. }
  355. Vector3 lhs;
  356. if (num4 == this.Head)
  357. {
  358. lhs = Vector3.Scale(this.ElementArray[num6].Position, b) - Vector3.Scale(element.Position, b);
  359. }
  360. else if (num4 == this.Tail)
  361. {
  362. lhs = Vector3.Scale(element.Position, b) - Vector3.Scale(this.ElementArray[num3].Position, b);
  363. }
  364. else
  365. {
  366. lhs = Vector3.Scale(this.ElementArray[num6].Position, b) - Vector3.Scale(this.ElementArray[num3].Position, b);
  367. }
  368. Vector3 rhs;
  369. if (!this.UseFaceObject)
  370. {
  371. rhs = eyePos - Vector3.Scale(element.Position, b);
  372. }
  373. else
  374. {
  375. rhs = element.Normal;
  376. }
  377. Vector3 vector = Vector3.Cross(lhs, rhs);
  378. vector.Normalize();
  379. vector *= element.Width * 0.5f * this.Node.Scale.x;
  380. Vector3 vector2 = element.Position - vector;
  381. Vector3 vector3 = element.Position + vector;
  382. VertexPool pool = this.Vertexsegment.Pool;
  383. float num7;
  384. if (this.Node.Owner.RibbonUVStretch == UV_STRETCH.Vertical)
  385. {
  386. num7 = num / num2 * Mathf.Abs(this.UVDimensions.y);
  387. }
  388. else
  389. {
  390. num7 = num / num2 * Mathf.Abs(this.UVDimensions.x);
  391. }
  392. Vector2 zero = Vector2.zero;
  393. pool.Vertices[num5] = vector2;
  394. pool.Colors[num5] = this.Color;
  395. if (this.Node.Owner.RibbonUVStretch == UV_STRETCH.Vertical)
  396. {
  397. zero.x = this.LowerLeftUV.x + this.UVDimensions.x;
  398. zero.y = this.LowerLeftUV.y - num7;
  399. }
  400. else
  401. {
  402. zero.x = this.LowerLeftUV.x + num7;
  403. zero.y = this.LowerLeftUV.y;
  404. }
  405. pool.UVs[num5] = zero;
  406. pool.Vertices[num5 + 1] = vector3;
  407. pool.Colors[num5 + 1] = this.Color;
  408. if (this.Node.Owner.RibbonUVStretch == UV_STRETCH.Vertical)
  409. {
  410. zero.x = this.LowerLeftUV.x;
  411. zero.y = this.LowerLeftUV.y - num7;
  412. }
  413. else
  414. {
  415. zero.x = this.LowerLeftUV.x + num7;
  416. zero.y = this.LowerLeftUV.y - Mathf.Abs(this.UVDimensions.y);
  417. }
  418. pool.UVs[num5 + 1] = zero;
  419. if (num4 == this.Tail)
  420. {
  421. break;
  422. }
  423. num3 = num4;
  424. num += (this.ElementArray[num6].Position - element.Position).magnitude;
  425. num4++;
  426. }
  427. this.Vertexsegment.Pool.UVChanged = true;
  428. this.Vertexsegment.Pool.VertChanged = true;
  429. this.Vertexsegment.Pool.ColorChanged = true;
  430. }
  431. }
  432. public void AddElememt(RibbonTrail.Element dtls)
  433. {
  434. if (this.Head == 99999)
  435. {
  436. this.Tail = this.MaxElements - 1;
  437. this.Head = this.Tail;
  438. this.IndexDirty = true;
  439. this.ElemCount++;
  440. }
  441. else
  442. {
  443. if (this.Head == 0)
  444. {
  445. this.Head = this.MaxElements - 1;
  446. }
  447. else
  448. {
  449. this.Head--;
  450. }
  451. if (this.Head == this.Tail)
  452. {
  453. if (this.Tail == 0)
  454. {
  455. this.Tail = this.MaxElements - 1;
  456. }
  457. else
  458. {
  459. this.Tail--;
  460. }
  461. }
  462. else
  463. {
  464. this.ElemCount++;
  465. }
  466. }
  467. if (this.ElementArray[this.Head] != null)
  468. {
  469. this.ElementPool.Add(this.ElementArray[this.Head]);
  470. }
  471. this.ElementArray[this.Head] = dtls;
  472. this.IndexDirty = true;
  473. }
  474. protected List<RibbonTrail.Element> ElementPool = new List<RibbonTrail.Element>();
  475. protected VertexPool.VertexSegment Vertexsegment;
  476. public int MaxElements;
  477. public RibbonTrail.Element[] ElementArray;
  478. public const int CHAIN_EMPTY = 99999;
  479. public int Head;
  480. public int Tail;
  481. protected Vector3 HeadPosition;
  482. protected float TrailLength;
  483. protected float ElemLength;
  484. public float SquaredElemLength;
  485. protected float UnitWidth;
  486. protected bool IndexDirty;
  487. protected Vector2 LowerLeftUV;
  488. protected Vector2 UVDimensions;
  489. protected Color Color = Color.white;
  490. public int ElemCount;
  491. protected float ElapsedTime;
  492. protected int StretchCount;
  493. public Vector3 OriHeadPos;
  494. private bool UseFaceObject;
  495. private Transform FaceObject;
  496. protected Vector3 mLastClientPos;
  497. public class Element
  498. {
  499. public Element(Vector3 position, float width)
  500. {
  501. this.Position = position;
  502. this.Width = width;
  503. }
  504. public Vector3 Position;
  505. public Vector3 Normal;
  506. public float Width;
  507. }
  508. }
  509. }