BakingCamera.cs 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. using UnityEngine;
  2. #if UNITY_EDITOR
  3. using UnityEditor.SceneManagement;
  4. using UnityEditor.Experimental.SceneManagement;
  5. #endif
  6. namespace Coffee.UIParticleExtensions
  7. {
  8. [AddComponentMenu("")]
  9. internal class BakingCamera : MonoBehaviour
  10. {
  11. static BakingCamera s_Instance;
  12. private static readonly Vector3 s_OrthoPosition = new Vector3(0, 0, -1000);
  13. private static readonly Quaternion s_OrthoRotation = Quaternion.identity;
  14. #if UNITY_2018_3_OR_NEWER && UNITY_EDITOR
  15. static BakingCamera s_InstanceForPrefab;
  16. private static BakingCamera InstanceForPrefab
  17. {
  18. get
  19. {
  20. // If current scene is prefab mode, create OverlayCamera for editor.
  21. var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();
  22. if (prefabStage == null || !prefabStage.scene.isLoaded) return null;
  23. if (s_InstanceForPrefab) return s_InstanceForPrefab;
  24. s_InstanceForPrefab = Create();
  25. s_InstanceForPrefab.name += " (For Prefab Stage)";
  26. UnityEngine.SceneManagement.SceneManager.MoveGameObjectToScene(s_InstanceForPrefab.gameObject, prefabStage.scene);
  27. return s_InstanceForPrefab;
  28. }
  29. }
  30. #endif
  31. private static BakingCamera Instance
  32. {
  33. get
  34. {
  35. #if UNITY_2018_3_OR_NEWER && UNITY_EDITOR
  36. var inst = InstanceForPrefab;
  37. if (inst) return inst;
  38. #endif
  39. // Find instance in scene, or create new one.
  40. return s_Instance
  41. ? s_Instance
  42. : (s_Instance = Create());
  43. }
  44. }
  45. private Camera _camera;
  46. private static BakingCamera Create()
  47. {
  48. var gameObject = new GameObject(typeof(BakingCamera).Name);
  49. // This camera object is just for internal use
  50. gameObject.hideFlags = HideFlags.HideAndDontSave;
  51. var inst = gameObject.AddComponent<BakingCamera>();
  52. inst._camera = gameObject.AddComponent<Camera>();
  53. inst._camera.enabled = false;
  54. inst._camera.orthographic = true;
  55. // Turn camera off because particle mesh baker will use only camera matrix
  56. gameObject.SetActive(false);
  57. return inst;
  58. }
  59. private void Awake()
  60. {
  61. if (this == s_Instance)
  62. DontDestroyOnLoad(gameObject);
  63. }
  64. public static Camera GetCamera(Canvas canvas)
  65. {
  66. if (!canvas) return Camera.main;
  67. canvas = canvas.rootCanvas;
  68. // Adjust camera orthographic size to canvas size
  69. // for canvas-based coordinates of particles' size and speed.
  70. var size = ((RectTransform) canvas.transform).rect.size;
  71. Instance._camera.orthographicSize = Mathf.Max(size.x, size.y) * canvas.scaleFactor;
  72. var camera = canvas.worldCamera;
  73. var transform = Instance.transform;
  74. var rotation = canvas.renderMode != RenderMode.ScreenSpaceOverlay && camera
  75. ? camera.transform.rotation
  76. : s_OrthoRotation;
  77. transform.SetPositionAndRotation(s_OrthoPosition, rotation);
  78. Instance._camera.orthographic = true;
  79. Instance._camera.farClipPlane = 2000f;
  80. return Instance._camera;
  81. }
  82. }
  83. }