You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

254 lines
7.6 KiB

5 years ago
  1. using System.Collections;
  2. using System.Collections.Generic;
  3. using UnityEngine;
  4. #if UNITY_EDITOR
  5. using UnityEditor;
  6. #endif
  7. public class CastleAnimator : MonoBehaviour {
  8. public float WaitAtStart = 2;
  9. public float MoveSpeed = 30;
  10. public float MaxWaitTime = 5;
  11. [SerializeField]
  12. public AnimationCurve SpeedCurve;
  13. public float BridgeSpeed = 30;
  14. public float maxBridgeWaitTime = 0.5f;
  15. [SerializeField]
  16. public AnimationCurve ScaleCurve;
  17. [System.Serializable]
  18. public struct Base {
  19. public GameObject gameObject;
  20. public Bounds BaseBound;
  21. public Tower tower;
  22. }
  23. [System.Serializable]
  24. public struct Tower {
  25. public Vector3 originalPos;
  26. public GameObject gameObject;
  27. public List<GameObject> TowerPieces;
  28. public GameObject[] ScalePoints;
  29. }
  30. [HideInInspector]
  31. public List<Base> Bases = new List<Base>();
  32. public enum ScaleDirection {PositiveX, PositiveZ, NegativeX, NegativeZ }
  33. public void Start()
  34. {
  35. if (MoveSpeed == 0) {
  36. Debug.LogWarning("Tower Movement set to 0");
  37. return;
  38. }
  39. foreach(Base Base in Bases) {
  40. StartCoroutine(MoveTower(Base.tower, MoveSpeed, MaxWaitTime));
  41. }
  42. }
  43. private IEnumerator MoveTower(Tower tower, float moveSpeed, float startRandomizer)
  44. {
  45. foreach (GameObject scalePoint in tower.ScalePoints) {
  46. scalePoint.SetActive(false);
  47. scalePoint.transform.localScale = Vector3.zero;
  48. }
  49. Vector3 endPos = tower.gameObject.transform.position;
  50. tower.gameObject.transform.localPosition = Vector3.zero;
  51. Vector3 startPos = tower.gameObject.transform.position;
  52. float elapsedTime = 0;
  53. float randomWait = Random.Range(0, startRandomizer);
  54. float animationTime = (Vector3.Distance(endPos, startPos) / moveSpeed);
  55. yield return new WaitForSeconds(randomWait + WaitAtStart);
  56. while (elapsedTime < animationTime) {
  57. float curvePercent = SpeedCurve.Evaluate((elapsedTime / animationTime));
  58. tower.gameObject.transform.position = UnclampedLerp(startPos, endPos, curvePercent);
  59. elapsedTime += Time.deltaTime;
  60. yield return new WaitForEndOfFrame();
  61. }
  62. tower.gameObject.transform.position = endPos;
  63. StartCoroutine(scaleBridge(tower.ScalePoints[0], ScaleDirection.PositiveX, BridgeSpeed,maxBridgeWaitTime));
  64. StartCoroutine(scaleBridge(tower.ScalePoints[1], ScaleDirection.PositiveZ, BridgeSpeed,maxBridgeWaitTime));
  65. StartCoroutine(scaleBridge(tower.ScalePoints[2], ScaleDirection.NegativeX, BridgeSpeed,maxBridgeWaitTime));
  66. StartCoroutine(scaleBridge(tower.ScalePoints[3], ScaleDirection.NegativeZ, BridgeSpeed,maxBridgeWaitTime));
  67. }
  68. private IEnumerator scaleBridge(GameObject scalePoint, ScaleDirection direction, float scaleSpeed, float startRandomizer)
  69. {
  70. float randomWait = Random.Range(0, startRandomizer);
  71. yield return new WaitForSeconds(randomWait);
  72. scalePoint.SetActive(true);
  73. Vector3 scaleVector = Vector3.zero;
  74. if (direction == ScaleDirection.NegativeX || direction == ScaleDirection.PositiveX) {
  75. scaleVector = Vector3.right;
  76. scalePoint.transform.localScale = new Vector3(0, 1, 1);
  77. } else {
  78. scaleVector = Vector3.forward;
  79. scalePoint.transform.localScale = new Vector3(1, 1, 0);
  80. }
  81. Vector3 startScale = scalePoint.transform.localScale;
  82. float elapsedTime = 0;
  83. float animationTime = 10 / scaleSpeed;
  84. while (elapsedTime < animationTime) {
  85. float curvePercent = ScaleCurve.Evaluate((elapsedTime / animationTime));
  86. scalePoint.gameObject.transform.localScale = UnclampedLerp(startScale, Vector3.one, curvePercent);
  87. elapsedTime += Time.deltaTime;
  88. yield return new WaitForEndOfFrame();
  89. }
  90. scalePoint.transform.localScale = Vector3.one;
  91. }
  92. public static Vector3 UnclampedLerp(Vector3 a, Vector3 b, float t)
  93. {
  94. return t * b + (1 - t) * a;
  95. }
  96. private Bounds getWorldBounds(GameObject input)
  97. {
  98. Bounds retVal = new Bounds(input.transform.position, Vector3.zero);
  99. foreach (Renderer renderer in input.GetComponentsInChildren<Renderer>()) {
  100. retVal.Encapsulate(renderer.bounds);
  101. }
  102. return retVal;
  103. }
  104. private void MoveParent(GameObject input, Vector3 moveTo)
  105. {
  106. Vector3 movement = moveTo - input.transform.position;
  107. input.transform.position = moveTo;
  108. foreach (Transform child in input.transform) {
  109. child.position -= movement;
  110. }
  111. }
  112. #if UNITY_EDITOR
  113. public void AddBase(Transform input)
  114. {
  115. Base newBase = new Base();
  116. GameObject Base = new GameObject();
  117. Undo.RegisterCreatedObjectUndo(Base, "Created Base");
  118. Base.transform.position = getWorldBounds(input.gameObject).center;
  119. Base.transform.parent = transform;
  120. Base.name = "Base" + Bases.Count;
  121. Undo.SetTransformParent(input.transform, Base.transform, "Created Base");
  122. //newBaseObject.parent = Base.transform;
  123. newBase.gameObject = Base;
  124. Undo.RecordObject(this, "Created Base");
  125. GameObject towerHolder = new GameObject();
  126. towerHolder.transform.parent = Base.transform;
  127. towerHolder.transform.localPosition = Vector3.zero;
  128. towerHolder.name = "Tower Holder" + Bases.Count;
  129. newBase.tower = new Tower();
  130. newBase.tower.gameObject = towerHolder;
  131. newBase.tower.TowerPieces = new List<GameObject>();
  132. newBase.tower.ScalePoints = new GameObject[4];
  133. for (int i = 0; i < 4; i++) {
  134. newBase.tower.ScalePoints[i] = new GameObject();
  135. newBase.tower.ScalePoints[i].transform.parent = Base.transform;
  136. newBase.tower.ScalePoints[i].transform.localPosition = Vector3.zero;
  137. newBase.tower.ScalePoints[i].name = "ScalePoint" + Bases.Count + ", " + i;
  138. }
  139. Bases.Add(newBase);
  140. }
  141. public void AddTower(Base selectedBase, Transform[] input)
  142. {
  143. Undo.RecordObject(this, "Added Tower");
  144. foreach (Transform towerObject in input) {
  145. if (towerObject == selectedBase.gameObject.transform)
  146. continue;
  147. if (selectedBase.tower.TowerPieces.Contains(towerObject.gameObject))
  148. continue;
  149. selectedBase.tower.TowerPieces.Add(towerObject.gameObject);
  150. Undo.SetTransformParent(towerObject.transform, selectedBase.tower.gameObject.transform, "Added Tower");
  151. }
  152. Undo.RecordObject(selectedBase.tower.gameObject, "Added Tower");
  153. MoveParent(selectedBase.tower.gameObject, selectedBase.gameObject.transform.position + ((getWorldBounds(selectedBase.tower.gameObject).size.y) * Vector3.up));
  154. selectedBase.tower.originalPos = selectedBase.tower.gameObject.transform.position;
  155. }
  156. public void AddBridge(Base selectedBase,ScaleDirection direction, Transform[] input)
  157. {
  158. foreach (Transform bridgeObject in input) {
  159. if (bridgeObject == selectedBase.gameObject)
  160. continue;
  161. if (selectedBase.tower.TowerPieces.Contains(bridgeObject.gameObject))
  162. continue;
  163. Undo.SetTransformParent(bridgeObject.transform, selectedBase.tower.ScalePoints[(int)direction].transform, "Added Bridge");
  164. }
  165. }
  166. public string[] GetBaseNames()
  167. {
  168. string[] retVal = new string[Bases.Count];
  169. for (int i = 0; i < retVal.Length; i++) {
  170. retVal[i] = "Tower" + i;
  171. }
  172. return retVal;
  173. }
  174. #endif
  175. }