A game about forced loneliness, made by TACStudios
1#if UNITY_EDITOR && UNITY_INPUT_SYSTEM_PROJECT_WIDE_ACTIONS
2using System;
3using System.Collections.Generic;
4using System.Linq;
5using UnityEditor;
6using UnityEditor.UIElements;
7using UnityEngine.UIElements;
8
9namespace UnityEngine.InputSystem.Editor
10{
11 internal class ActionPropertiesView : ViewBase<(SerializedInputAction?, List<string>)>
12 {
13 private readonly Foldout m_ParentFoldout;
14 private readonly int m_DropdownLabelWidth = 90;
15
16 public ActionPropertiesView(VisualElement root, Foldout foldout, StateContainer stateContainer)
17 : base(root, stateContainer)
18 {
19 m_ParentFoldout = foldout;
20
21 // TODO: Consider IEquatable<T> and how to compare selector data
22 CreateSelector(Selectors.GetSelectedAction,
23 (inputAction, _) =>
24 {
25 if (!inputAction.HasValue)
26 return (null, new List<string>());
27 return (inputAction.Value, Selectors.BuildControlTypeList(inputAction.Value.type).ToList());
28 });
29 }
30
31 public override void RedrawUI((SerializedInputAction ? , List<string>) viewState)
32 {
33 if (!viewState.Item1.HasValue)
34 return;
35
36 m_ParentFoldout.text = "Action";
37 var inputAction = viewState.Item1.Value;
38
39 rootElement.Clear();
40
41 var actionType = new EnumField("Action Type", inputAction.type)
42 {
43 tooltip = inputAction.actionTypeTooltip
44 };
45
46 // Tighten up the gap between the label and dropdown so the latter is more readable when the parent pane is at min width.
47 var actionLabel = actionType.Q<Label>();
48 actionLabel.style.minWidth = m_DropdownLabelWidth;
49 actionLabel.style.width = m_DropdownLabelWidth;
50
51 actionType.RegisterValueChangedCallback(evt =>
52 {
53 Dispatch(Commands.ChangeActionType(inputAction, (InputActionType)evt.newValue));
54 });
55 rootElement.Add(actionType);
56
57 if (inputAction.type != InputActionType.Button)
58 {
59 var controlTypes = viewState.Item2;
60 var controlType = new DropdownField("Control Type");
61
62 // Tighten up the gap between the label and dropdown so the latter is more readable when the parent pane is at min width.
63 var controlLabel = controlType.Q<Label>();
64 controlLabel.style.minWidth = m_DropdownLabelWidth;
65 controlLabel.style.width = m_DropdownLabelWidth;
66
67 controlType.choices.Clear();
68 controlType.choices.AddRange(controlTypes.Select(ObjectNames.NicifyVariableName).ToList());
69 var controlTypeIndex = controlTypes.FindIndex(s => s == inputAction.expectedControlType);
70 //if type changed and index is -1 clamp to 0, prevent overflowing indices
71 controlTypeIndex = Math.Clamp(controlTypeIndex, 0, controlTypes.Count - 1);
72 controlType.SetValueWithoutNotify(controlType.choices[controlTypeIndex]);
73 controlType.tooltip = inputAction.expectedControlTypeTooltip;
74
75 controlType.RegisterValueChangedCallback(evt =>
76 {
77 Dispatch(Commands.ChangeActionControlType(inputAction, controlType.index));
78 });
79
80 // ISX-1916 - When changing ActionType to a non-Button type, we must also update the ControlType
81 // to the currently selected value; the ValueChangedCallback is not fired in this scenario.
82 Dispatch(Commands.ChangeActionControlType(inputAction, controlType.index));
83
84 rootElement.Add(controlType);
85 }
86 else
87 {
88 // ISX-1916 - When changing ActionType to a Button, we must also reset the ControlType
89 Dispatch(Commands.ChangeActionControlType(inputAction, 0));
90 }
91
92 if (inputAction.type != InputActionType.Value)
93 {
94 var initialStateCheck = new Toggle("Initial State Check")
95 {
96 tooltip = InputActionsEditorConstants.InitialStateCheckTooltip
97 };
98 initialStateCheck.SetValueWithoutNotify(inputAction.initialStateCheck);
99 initialStateCheck.RegisterValueChangedCallback(evt =>
100 {
101 Dispatch(Commands.ChangeInitialStateCheck(inputAction, evt.newValue));
102 });
103 rootElement.Add(initialStateCheck);
104 }
105 }
106 }
107}
108
109#endif