diff --git a/com.unity.cinemachine/Editor/Editors/CinemachineSplineDollyLookAtTargetsEditor.cs b/com.unity.cinemachine/Editor/Editors/CinemachineSplineDollyLookAtTargetsEditor.cs index addaafe40..c110ff6d0 100644 --- a/com.unity.cinemachine/Editor/Editors/CinemachineSplineDollyLookAtTargetsEditor.cs +++ b/com.unity.cinemachine/Editor/Editors/CinemachineSplineDollyLookAtTargetsEditor.cs @@ -185,7 +185,7 @@ void SetOffset(Vector3 offset) // local function void OnIndexDraggerCreated(IDelayedFriendlyDragger dragger) { - dragger.OnStartDrag = () => list.selectedIndex = index; + //dragger.OnStartDrag = () => list.selectedIndex = index; dragger.OnDragValueChangedFloat = (v) => BringCameraToCustomSplinePoint(splineData, v); } }; diff --git a/com.unity.cinemachine/Editor/Editors/CinemachineSplineRollEditor.cs b/com.unity.cinemachine/Editor/Editors/CinemachineSplineRollEditor.cs index 9b5ed69ea..94d143f69 100644 --- a/com.unity.cinemachine/Editor/Editors/CinemachineSplineRollEditor.cs +++ b/com.unity.cinemachine/Editor/Editors/CinemachineSplineRollEditor.cs @@ -39,31 +39,49 @@ public override VisualElement CreateInspectorGUI() var arrayProp = rollProp.FindPropertyRelative("m_DataPoints"); - list.makeItem = () => new BindableElement() { style = { flexDirection = FlexDirection.Row, marginRight = 4 }}; - list.bindItem = (ux, index) => + list.makeItem = () => { - // Remove children - items get recycled - for (int i = ux.childCount - 1; i >= 0; --i) - ux.RemoveAt(i); + var itemRootName = "ItemRoot"; + var row = new BindableElement() { name = itemRootName, style = { flexDirection = FlexDirection.Row, marginRight = 4 }}; const string indexTooltip = "The position on the Spline at which this data point will take effect. " + "The value is interpreted according to the Index Unit setting."; - var element = index < arrayProp.arraySize ? arrayProp.GetArrayElementAtIndex(index) : null; - var def = new CinemachineSplineRoll.RollData(); - var indexProp = element.FindPropertyRelative("m_Index"); - var valueProp = element.FindPropertyRelative("m_Value"); - - ux.Add(new VisualElement { pickingMode = PickingMode.Ignore, style = { width = 12 }}); // pass-through for selecting row in list - var label = ux.AddChild(new Label(indexProp.displayName) { tooltip = indexTooltip, style = { alignSelf = Align.Center }}); - var indexField = ux.AddChild(new PropertyField(indexProp, "") { style = { flexGrow = 1, flexBasis = 20 }}); - indexField.OnInitialGeometry(() => indexField.SafeSetIsDelayed()); - label.AddDelayedFriendlyPropertyDragger(indexProp, indexField, (dragger) => dragger.OnStartDrag = () => list.selectedIndex = index); - - ux.Add(new VisualElement { pickingMode = PickingMode.Ignore, style = { width = 12 }}); // pass-through for selecting row in list - ux.Add(new InspectorUtility.CompactPropertyField(valueProp.FindPropertyRelative(() => def.Value), "Roll") { style = { flexGrow = 1 }}); + row.Add(new VisualElement { pickingMode = PickingMode.Ignore, style = { flexBasis = 12 }}); // pass-through for selecting row in list + var indexField = row.AddChild(InspectorUtility.CreateDraggableField( + typeof(float), "m_Index", indexTooltip, row.AddChild(new Label("Index")), out var dragger)); + indexField.style.flexGrow = 1; + indexField.style.flexBasis = 50; + indexField.SafeSetIsDelayed(); + if (dragger is IDelayedFriendlyDragger delayedDragger) + delayedDragger.OnStartDrag = (d) => SelectListElementContainingAnElement(list, d.DragElement, itemRootName); - ((BindableElement)ux).BindProperty(element); // bind must be done at the end + var def = new CinemachineSplineRoll.RollData(); + var rollTooltip = SerializedPropertyHelper.PropertyTooltip(() => def.Value); + row.Add(new VisualElement { pickingMode = PickingMode.Ignore, style = { flexBasis = 12 }}); // pass-through for selecting row in list + var rollField = row.AddChild(InspectorUtility.CreateDraggableField( + typeof(float), "m_Value.Value", rollTooltip, row.AddChild(new Label("Roll")), out dragger)); + rollField.style.flexGrow = 1; + rollField.style.flexBasis = 50; + if (dragger is IDelayedFriendlyDragger delayedDragger2) + delayedDragger2.OnStartDrag = (d) => SelectListElementContainingAnElement(list, d.DragElement, itemRootName); + + return row; + + static void SelectListElementContainingAnElement(ListView list, VisualElement element, string itemRootName) + { + var container = list.Q("unity-content-container"); + if (container == null) + return; + while (element != null && element.name != itemRootName) + element = element.parent; + if (element != null) + { + var index = container.IndexOf(element); + if (index >= 0) + list.selectedIndex = index; + } + } }; SplineRollTool.s_OnDataLookAtDragged += OnToolDragged; diff --git a/com.unity.cinemachine/Editor/Utility/CmCameraInspectorUtility.cs b/com.unity.cinemachine/Editor/Utility/CmCameraInspectorUtility.cs index 6a9bf11ba..ae2d9ffc5 100644 --- a/com.unity.cinemachine/Editor/Utility/CmCameraInspectorUtility.cs +++ b/com.unity.cinemachine/Editor/Utility/CmCameraInspectorUtility.cs @@ -535,17 +535,13 @@ public static void AddChildCameras( style = { flexBasis = 20, flexGrow = 1 } }).SetEnabled(false); - var tooltip = "The child camera's Priority"; - var dragger = row.AddChild(new Label(" ") { tooltip = tooltip }); - dragger.AddToClassList("unity-base-field__label--with-dragger"); - var priorityField = row.AddChild(new IntegerField - { - name = "priorityField", - tooltip = tooltip, - isDelayed = true, - style = { flexBasis = floatFieldWidth, flexGrow = 0, marginRight = 4 } - }); - new DelayedFriendlyFieldDragger(priorityField).SetDragZone(dragger); + var priorityField = row.AddChild(InspectorUtility.CreateDraggableField( + typeof(int), "", "The child camera's Priority", row.AddChild(new Label(" ")), out _)); + priorityField.name = "priorityField"; + priorityField.style.flexBasis = floatFieldWidth; + priorityField.style.flexGrow = 0; + priorityField.style.marginRight = 4; + priorityField.SafeSetIsDelayed(); return row; }; diff --git a/com.unity.cinemachine/Editor/Utility/DelayedFriendlyFieldDragger.cs b/com.unity.cinemachine/Editor/Utility/DelayedFriendlyFieldDragger.cs index 48538f46b..43b0dff88 100644 --- a/com.unity.cinemachine/Editor/Utility/DelayedFriendlyFieldDragger.cs +++ b/com.unity.cinemachine/Editor/Utility/DelayedFriendlyFieldDragger.cs @@ -12,16 +12,19 @@ interface IDelayedFriendlyDragger public bool CancelDelayedWhenDragging { get; set; } /// Called when dragging starts. - public Action OnStartDrag { get; set; } + public Action OnStartDrag { get; set; } /// Called when dragging stops. - public Action OnStopDrag { get; set; } + public Action OnStopDrag { get; set; } /// Called when the value changes during dragging. public Action OnDragValueChangedInt { get; set; } /// Called when the value changes during dragging. public Action OnDragValueChangedFloat { get; set; } + + /// Get the VisualElement being dragged + public VisualElement DragElement { get; } } /// @@ -48,24 +51,27 @@ public DelayedFriendlyFieldDragger(IValueField drivenField) /// Is dragging. public bool dragging { get; set; } - /// Start value before drag. + /// public T startValue { get; set; } - /// If true, temporarily disable isDelayed when draggin + /// public bool CancelDelayedWhenDragging { get; set; } - /// Called when dragging starts. - public Action OnStartDrag { get; set; } + /// + public Action OnStartDrag { get; set; } - /// Called when dragging stops. - public Action OnStopDrag { get; set; } + /// + public Action OnStopDrag { get; set; } - /// Called when the value changes during dragging. + /// public Action OnDragValueChangedInt { get; set; } - /// Called when the value changes during dragging. + /// public Action OnDragValueChangedFloat { get; set; } + /// + public VisualElement DragElement => m_DragElement; + /// public sealed override void SetDragZone(VisualElement dragElement, Rect hotZone) { @@ -136,7 +142,7 @@ private void ProcessDownEvent(EventBase evt) m_DrivenField.StartDragging(); EditorGUIUtility.SetWantsMouseJumping(1); - OnStartDrag?.Invoke(); + OnStartDrag?.Invoke(this); } private void UpdateValueOnPointerMove(PointerMoveEvent evt) @@ -175,7 +181,7 @@ private void ProcessUpEvent(EventBase evt, int pointerId) { if (dragging) { - OnStopDrag?.Invoke(); + OnStopDrag?.Invoke(this); dragging = false; m_DragElement.UnregisterCallback(UpdateValueOnPointerMove); m_DragElement.ReleasePointer(pointerId); diff --git a/com.unity.cinemachine/Editor/Utility/InspectorUtility.cs b/com.unity.cinemachine/Editor/Utility/InspectorUtility.cs index 1620a2dcc..e24b2deb1 100644 --- a/com.unity.cinemachine/Editor/Utility/InspectorUtility.cs +++ b/com.unity.cinemachine/Editor/Utility/InspectorUtility.cs @@ -295,32 +295,36 @@ public static void AddDelayedFriendlyPropertyDragger( public static VisualElement CreateDraggableField(Expression> exp, Label label, out BaseFieldMouseDragger dragger) { - VisualElement field; - var name = SerializedPropertyHelper.PropertyName(exp); + var bindingPath = SerializedPropertyHelper.PropertyName(exp); var tooltip = SerializedPropertyHelper.PropertyTooltip(exp); + return CreateDraggableField(SerializedPropertyHelper.PropertyType(exp), bindingPath, tooltip, label, out dragger); + } - label.tooltip = tooltip; + public static VisualElement CreateDraggableField(Type type, string bindingPath, string tooltip, Label label, out BaseFieldMouseDragger dragger) + { + VisualElement field; label.AddToClassList("unity-base-field__label--with-dragger"); - - var type = SerializedPropertyHelper.PropertyType(exp); + label.tooltip = tooltip; + label.style.alignSelf = Align.Center; if (type == typeof(float)) { - field = new FloatField { bindingPath = name }; + field = new FloatField { bindingPath = bindingPath, tooltip = tooltip }; dragger = new DelayedFriendlyFieldDragger((FloatField)field); } else if (type == typeof(int)) { - field = new IntegerField { bindingPath = name }; + field = new IntegerField { bindingPath = bindingPath, tooltip = tooltip }; dragger = new DelayedFriendlyFieldDragger((IntegerField)field); } else { - field = new PropertyField(null, "") { bindingPath = name }; + field = new PropertyField(null, "") { bindingPath = bindingPath, tooltip = tooltip }; dragger = null; } dragger?.SetDragZone(label); return field; } + /// A small warning sybmol, suitable for embedding in an inspector row /// The tooltip text