| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226 |
- #if !UNITY_2019_3_OR_NEWER
- #define CINEMACHINE_PHYSICS
- #define CINEMACHINE_PHYSICS_2D
- #endif
- using UnityEditor;
- using UnityEngine;
- namespace Cinemachine.Editor
- {
- #if CINEMACHINE_PHYSICS
- [CustomEditor(typeof(CinemachineClearShot))]
- [CanEditMultipleObjects]
- internal sealed class CinemachineClearShotEditor
- : CinemachineVirtualCameraBaseEditor<CinemachineClearShot>
- {
- EmbeddeAssetEditor<CinemachineBlenderSettings> m_BlendsEditor;
- ColliderState m_ColliderState;
- private UnityEditorInternal.ReorderableList mChildList;
- protected override void OnEnable()
- {
- base.OnEnable();
- m_BlendsEditor = new EmbeddeAssetEditor<CinemachineBlenderSettings>(
- FieldPath(x => x.m_CustomBlends), this);
- m_BlendsEditor.OnChanged = (CinemachineBlenderSettings b) =>
- {
- InspectorUtility.RepaintGameView();
- };
- m_BlendsEditor.OnCreateEditor = (UnityEditor.Editor ed) =>
- {
- CinemachineBlenderSettingsEditor editor = ed as CinemachineBlenderSettingsEditor;
- if (editor != null)
- editor.GetAllVirtualCameras = () => { return Target.ChildCameras; };
- };
- mChildList = null;
- }
- protected override void OnDisable()
- {
- base.OnDisable();
- if (m_BlendsEditor != null)
- m_BlendsEditor.OnDisable();
- }
- public override void OnInspectorGUI()
- {
- BeginInspector();
- if (mChildList == null)
- SetupChildList();
- m_ColliderState = GetColliderState();
- switch (m_ColliderState)
- {
- case ColliderState.ColliderOnParent:
- case ColliderState.ColliderOnAllChildren:
- break;
- case ColliderState.NoCollider:
- EditorGUILayout.HelpBox(
- "ClearShot requires a Collider extension to rank the shots. Either add one to the ClearShot itself, or to each of the child cameras.",
- MessageType.Warning);
- break;
- case ColliderState.ColliderOnSomeChildren:
- EditorGUILayout.HelpBox(
- "Some child cameras do not have a Collider extension. ClearShot requires a Collider on all the child cameras, or alternatively on the ClearShot iself.",
- MessageType.Warning);
- break;
- case ColliderState.ColliderOnChildrenAndParent:
- EditorGUILayout.HelpBox(
- "There is a Collider extension on the ClearShot camera, and also on some of its child cameras. You can't have both.",
- MessageType.Error);
- break;
- }
- DrawHeaderInInspector();
- DrawPropertyInInspector(FindProperty(x => x.m_Priority));
- DrawTargetsInInspector(FindProperty(x => x.m_Follow), FindProperty(x => x.m_LookAt));
- DrawRemainingPropertiesInInspector();
- // Blends
- m_BlendsEditor.DrawEditorCombo(
- "Create New Blender Asset",
- Target.gameObject.name + " Blends", "asset", string.Empty,
- "Custom Blends", false);
- // vcam children
- EditorGUILayout.Separator();
- if (Selection.objects.Length == 1)
- {
- EditorGUI.BeginChangeCheck();
- mChildList.DoLayoutList();
- if (EditorGUI.EndChangeCheck())
- serializedObject.ApplyModifiedProperties();
- }
- else
- {
- EditorGUILayout.HelpBox(Styles.virtualCameraChildrenInfoMsg.text, MessageType.Info);
- }
-
- // Extensions
- DrawExtensionsWidgetInInspector();
- }
- enum ColliderState
- {
- NoCollider,
- ColliderOnAllChildren,
- ColliderOnSomeChildren,
- ColliderOnParent,
- ColliderOnChildrenAndParent
- }
- ColliderState GetColliderState()
- {
- int numChildren = 0;
- int numColliderChildren = 0;
- bool colliderOnParent = ObjectHasCollider(Target);
- var children = Target.m_ChildCameras;
- numChildren = children == null ? 0 : children.Length;
- for (int i = 0; i < numChildren; ++i)
- if (ObjectHasCollider(children[i]))
- ++numColliderChildren;
- if (colliderOnParent)
- return (numColliderChildren > 0)
- ? ColliderState.ColliderOnChildrenAndParent : ColliderState.ColliderOnParent;
- if (numColliderChildren > 0)
- return (numColliderChildren == numChildren)
- ? ColliderState.ColliderOnAllChildren : ColliderState.ColliderOnSomeChildren;
- return ColliderState.NoCollider;
- }
- bool ObjectHasCollider(object obj)
- {
- CinemachineVirtualCameraBase vcam = obj as CinemachineVirtualCameraBase;
- var collider = (vcam == null) ? null : vcam.GetComponent<CinemachineCollider>();
- return (collider != null && collider.enabled);
- }
- void SetupChildList()
- {
- float vSpace = 2;
- float hSpace = 3;
- float floatFieldWidth = EditorGUIUtility.singleLineHeight * 2.5f;
- mChildList = new UnityEditorInternal.ReorderableList(
- serializedObject, FindProperty(x => x.m_ChildCameras), true, true, true, true);
- mChildList.drawHeaderCallback = (Rect rect) =>
- {
- EditorGUI.LabelField(rect, "Virtual Camera Children");
- GUIContent priorityText = new GUIContent("Priority");
- var textDimensions = GUI.skin.label.CalcSize(priorityText);
- rect.x += rect.width - textDimensions.x;
- rect.width = textDimensions.x;
- EditorGUI.LabelField(rect, priorityText);
- };
- mChildList.drawElementCallback
- = (Rect rect, int index, bool isActive, bool isFocused) =>
- {
- rect.y += vSpace;
- rect.width -= floatFieldWidth + hSpace;
- rect.height = EditorGUIUtility.singleLineHeight;
- SerializedProperty element = mChildList.serializedProperty.GetArrayElementAtIndex(index);
- if (m_ColliderState == ColliderState.ColliderOnSomeChildren
- || m_ColliderState == ColliderState.ColliderOnChildrenAndParent)
- {
- bool hasCollider = ObjectHasCollider(element.objectReferenceValue);
- if ((m_ColliderState == ColliderState.ColliderOnSomeChildren && !hasCollider)
- || (m_ColliderState == ColliderState.ColliderOnChildrenAndParent && hasCollider))
- {
- float width = rect.width;
- rect.width = rect.height;
- GUIContent label = new GUIContent("");
- label.image = EditorGUIUtility.IconContent("console.warnicon.sml").image;
- EditorGUI.LabelField(rect, label);
- width -= rect.width; rect.x += rect.width; rect.width = width;
- }
- }
- EditorGUI.PropertyField(rect, element, GUIContent.none);
- SerializedObject obj = new SerializedObject(element.objectReferenceValue);
- rect.x += rect.width + hSpace; rect.width = floatFieldWidth;
- SerializedProperty priorityProp = obj.FindProperty(() => Target.m_Priority);
- float oldWidth = EditorGUIUtility.labelWidth;
- EditorGUIUtility.labelWidth = hSpace * 2;
- EditorGUI.PropertyField(rect, priorityProp, new GUIContent(" "));
- EditorGUIUtility.labelWidth = oldWidth;
- obj.ApplyModifiedProperties();
- };
- mChildList.onChangedCallback = (UnityEditorInternal.ReorderableList l) =>
- {
- if (l.index < 0 || l.index >= l.serializedProperty.arraySize)
- return;
- Object o = l.serializedProperty.GetArrayElementAtIndex(
- l.index).objectReferenceValue;
- CinemachineVirtualCameraBase vcam = (o != null)
- ? (o as CinemachineVirtualCameraBase) : null;
- if (vcam != null)
- vcam.transform.SetSiblingIndex(l.index);
- };
- mChildList.onAddCallback = (UnityEditorInternal.ReorderableList l) =>
- {
- var index = l.serializedProperty.arraySize;
- var vcam = CinemachineMenu.CreateDefaultVirtualCamera();
- Undo.SetTransformParent(vcam.transform, Target.transform, "");
- var collider = Undo.AddComponent<CinemachineCollider>(vcam.gameObject);
- collider.m_AvoidObstacles = false;
- Undo.RecordObject(collider, "create ClearShot child");
- vcam.transform.SetSiblingIndex(index);
- };
- mChildList.onRemoveCallback = (UnityEditorInternal.ReorderableList l) =>
- {
- Object o = l.serializedProperty.GetArrayElementAtIndex(
- l.index).objectReferenceValue;
- CinemachineVirtualCameraBase vcam = (o != null)
- ? (o as CinemachineVirtualCameraBase) : null;
- if (vcam != null)
- Undo.DestroyObjectImmediate(vcam.gameObject);
- };
- }
- }
- #endif
- }
|