StressReceiver.cs 3.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576
  1. using OfficeOpenXml.FormulaParsing.Excel.Functions.Math;
  2. using UnityEngine;
  3. public class StressReceiver : MonoBehaviour
  4. {
  5. public float trauma;
  6. private float _trauma;
  7. private Vector3 _lastPosition;
  8. private Vector3 _lastRotation;
  9. [Tooltip("Exponent for calculating the shake factor. Useful for creating different effect fade outs")]
  10. public float TraumaExponent = 1;
  11. [Tooltip("Maximum angle that the gameobject can shake. In euler angles.")]
  12. public Vector3 MaximumAngularShake = Vector3.one * 5;
  13. [Tooltip("Maximum translation that the gameobject can receive when applying the shake effect.")]
  14. public Vector3 MaximumTranslationShake = Vector3.one * .75f;
  15. private System.Action callBack;
  16. [ContextMenu("asdasda")]
  17. public void Test()
  18. {
  19. InduceStress(trauma,null);
  20. }
  21. private void Update()
  22. {
  23. float shake = Mathf.Pow(_trauma, TraumaExponent);
  24. /* Only apply this when there is active trauma */
  25. if(shake > 0.01f)
  26. {
  27. var previousRotation = _lastRotation;
  28. var previousPosition = _lastPosition;
  29. /* In order to avoid affecting the transform current position and rotation each frame we substract the previous translation and rotation */
  30. _lastPosition = new Vector3(
  31. MaximumTranslationShake.x * (Mathf.PerlinNoise(0, Time.time * 25) * 2 - 1),
  32. MaximumTranslationShake.y * (Mathf.PerlinNoise(1, Time.time * 25) * 2 - 1),
  33. MaximumTranslationShake.z * (Mathf.PerlinNoise(2, Time.time * 25) * 2 - 1)
  34. ) * shake;
  35. _lastRotation = new Vector3(
  36. MaximumAngularShake.x * (Mathf.PerlinNoise(3, Time.time * 25) * 2 - 1),
  37. MaximumAngularShake.y * (Mathf.PerlinNoise(4, Time.time * 25) * 2 - 1),
  38. MaximumAngularShake.z * (Mathf.PerlinNoise(5, Time.time * 25) * 2 - 1)
  39. ) * shake;
  40. transform.localPosition += _lastPosition - previousPosition;
  41. transform.localRotation = Quaternion.Euler(transform.localRotation.eulerAngles + _lastRotation - previousRotation);
  42. _trauma = Mathf.Clamp01(_trauma - Time.deltaTime);
  43. }
  44. else
  45. {
  46. if (_lastPosition == Vector3.zero && _lastRotation == Vector3.zero)
  47. {
  48. callBack?.Invoke();
  49. return;
  50. }
  51. /* Clear the transform of any left over translation and rotations */
  52. transform.localPosition -= _lastPosition;
  53. transform.localRotation = Quaternion.Euler(transform.localRotation.eulerAngles - _lastRotation);
  54. _lastPosition = Vector3.zero;
  55. _lastRotation = Vector3.zero;
  56. callBack?.Invoke();
  57. }
  58. }
  59. /// <summary>
  60. /// Applies a stress value to the current object.
  61. /// </summary>
  62. /// <param name="Stress">[0,1] Amount of stress to apply to the object</param>
  63. public void InduceStress(float Stress,System.Action callBack)
  64. {
  65. this.callBack = callBack;
  66. _trauma = Mathf.Clamp01(_trauma + Stress);
  67. }
  68. }