CinemachineExtension.cs 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. using System.Collections.Generic;
  2. using UnityEngine;
  3. namespace Cinemachine
  4. {
  5. /// <summary>
  6. /// Base class for a Cinemachine Virtual Camera extension module.
  7. /// Hooks into the Cinemachine Pipeline. Use this to add extra processing
  8. /// to the vcam, modifying its generated state
  9. /// </summary>
  10. [DocumentationSorting(DocumentationSortingAttribute.Level.API)]
  11. public abstract class CinemachineExtension : MonoBehaviour
  12. {
  13. /// <summary>Useful constant for very small floats</summary>
  14. protected const float Epsilon = Utility.UnityVectorExtensions.Epsilon;
  15. /// <summary>Get the CinemachineVirtualCamera to which this extension is attached</summary>
  16. public CinemachineVirtualCameraBase VirtualCamera
  17. {
  18. get
  19. {
  20. if (m_vcamOwner == null)
  21. m_vcamOwner = GetComponent<CinemachineVirtualCameraBase>();
  22. return m_vcamOwner;
  23. }
  24. }
  25. CinemachineVirtualCameraBase m_vcamOwner;
  26. /// <summary>Connect to virtual camera pipeline.
  27. /// Override implementations must call this base implementation</summary>
  28. protected virtual void Awake()
  29. {
  30. ConnectToVcam(true);
  31. }
  32. /// <summary>Does nothing. It's here for the little checkbox in the inspector.</summary>
  33. protected virtual void OnEnable() {}
  34. #if UNITY_EDITOR
  35. [UnityEditor.Callbacks.DidReloadScripts]
  36. static void OnScriptReload()
  37. {
  38. var extensions = Resources.FindObjectsOfTypeAll(
  39. typeof(CinemachineExtension)) as CinemachineExtension[];
  40. foreach (var e in extensions)
  41. e.ConnectToVcam(true);
  42. }
  43. #endif
  44. /// <summary>Disconnect from virtual camera pipeline.
  45. /// Override implementations must call this base implementation</summary>
  46. protected virtual void OnDestroy()
  47. {
  48. ConnectToVcam(false);
  49. }
  50. internal void EnsureStarted() { ConnectToVcam(true); }
  51. /// <summary>Connect to virtual camera. Implementation must be safe to be called
  52. /// redundantly. Override implementations must call this base implementation</summary>
  53. /// <param name="connect">True if connecting, false if disconnecting</param>
  54. protected virtual void ConnectToVcam(bool connect)
  55. {
  56. if (connect && VirtualCamera == null)
  57. Debug.LogError("CinemachineExtension requires a Cinemachine Virtual Camera component");
  58. if (VirtualCamera != null)
  59. {
  60. if (connect)
  61. VirtualCamera.AddExtension(this);
  62. else
  63. VirtualCamera.RemoveExtension(this);
  64. }
  65. mExtraState = null;
  66. }
  67. /// <summary>Override this to do such things as offset the RefereceLookAt.
  68. /// Base class implementation does nothing.</summary>
  69. /// <param name="vcam">The virtual camera being processed</param>
  70. /// <param name="curState">Input state that must be mutated</param>
  71. /// <param name="deltaTime">The current applicable deltaTime</param>
  72. public virtual void PrePipelineMutateCameraStateCallback(
  73. CinemachineVirtualCameraBase vcam, ref CameraState curState, float deltaTime) {}
  74. /// <summary>Legacy support. This is only here to avoid changing the API
  75. /// to make PostPipelineStageCallback() public</summary>
  76. /// <param name="vcam">The virtual camera being processed</param>
  77. /// <param name="stage">The current pipeline stage</param>
  78. /// <param name="state">The current virtual camera state</param>
  79. /// <param name="deltaTime">The current applicable deltaTime</param>
  80. public void InvokePostPipelineStageCallback(
  81. CinemachineVirtualCameraBase vcam,
  82. CinemachineCore.Stage stage, ref CameraState state, float deltaTime)
  83. {
  84. PostPipelineStageCallback(vcam, stage, ref state, deltaTime);
  85. }
  86. /// <summary>
  87. /// This callback will be called after the virtual camera has implemented
  88. /// each stage in the pipeline. This method may modify the referenced state.
  89. /// If deltaTime less than 0, reset all state info and perform no damping.
  90. /// </summary>
  91. /// <param name="vcam">The virtual camera being processed</param>
  92. /// <param name="stage">The current pipeline stage</param>
  93. /// <param name="state">The current virtual camera state</param>
  94. /// <param name="deltaTime">The current applicable deltaTime</param>
  95. protected abstract void PostPipelineStageCallback(
  96. CinemachineVirtualCameraBase vcam,
  97. CinemachineCore.Stage stage, ref CameraState state, float deltaTime);
  98. /// <summary>This is called to notify the extension that a target got warped,
  99. /// so that the extension can update its internal state to make the camera
  100. /// also warp seamlessy. Base class implementation does nothing.</summary>
  101. /// <param name="target">The object that was warped</param>
  102. /// <param name="positionDelta">The amount the target's position changed</param>
  103. public virtual void OnTargetObjectWarped(Transform target, Vector3 positionDelta) {}
  104. /// <summary>
  105. /// Force the virtual camera to assume a given position and orientation
  106. /// </summary>
  107. /// <param name="pos">Worldspace pposition to take</param>
  108. /// <param name="rot">Worldspace orientation to take</param>
  109. public virtual void ForceCameraPosition(Vector3 pos, Quaternion rot) {}
  110. /// <summary>Notification that this virtual camera is going live.
  111. /// Base class implementation must be called by any overridden method.</summary>
  112. /// <param name="fromCam">The camera being deactivated. May be null.</param>
  113. /// <param name="worldUp">Default world Up, set by the CinemachineBrain</param>
  114. /// <param name="deltaTime">Delta time for time-based effects (ignore if less than or equal to 0)</param>
  115. /// <returns>True to request a vcam update of internal state</returns>
  116. public virtual bool OnTransitionFromCamera(
  117. ICinemachineCamera fromCam, Vector3 worldUp, float deltaTime) { return false; }
  118. /// <summary>
  119. /// Report maximum damping time needed for this extension.
  120. /// Only used in editor for timeline scrubbing.
  121. /// </summary>
  122. /// <returns>Highest damping setting in this extension</returns>
  123. public virtual float GetMaxDampTime() { return 0; }
  124. /// <summary>Because extensions can be placed on manager cams and will in that
  125. /// case be called for all the vcam children, vcam-specific state information
  126. /// should be stored here. Just define a class to hold your state info
  127. /// and use it exclusively when calling this.</summary>
  128. /// /// <typeparam name="T">The type of the extra state class</typeparam>
  129. /// <param name="vcam">The virtual camera being processed</param>
  130. /// <returns>The extra state, cast as type T</returns>
  131. protected T GetExtraState<T>(ICinemachineCamera vcam) where T : class, new()
  132. {
  133. if (mExtraState == null)
  134. mExtraState = new Dictionary<ICinemachineCamera, System.Object>();
  135. System.Object extra = null;
  136. if (!mExtraState.TryGetValue(vcam, out extra))
  137. extra = mExtraState[vcam] = new T();
  138. return extra as T;
  139. }
  140. /// <summary>Inefficient method to get all extra state info for all vcams.
  141. /// Intended for Editor use only, not runtime!
  142. /// </summary>
  143. /// <typeparam name="T">The extra state type</typeparam>
  144. /// <returns>A dynamically-allocated list with all the extra states</returns>
  145. protected List<T> GetAllExtraStates<T>() where T : class, new()
  146. {
  147. var list = new List<T>();
  148. if (mExtraState != null)
  149. foreach (var v in mExtraState)
  150. list.Add(v.Value as T);
  151. return list;
  152. }
  153. private Dictionary<ICinemachineCamera, System.Object> mExtraState;
  154. }
  155. }