




1using System.Collections;
2using Inputs;
3using SystemUtilities;
4using UnityEngine;
5
6namespace Interactions
7{
8 public class Drawer_Interaction : Interaction
9 {
10 // ----- Serialized Fields
11 [SerializeField] private Rigidbody rb;
12 [SerializeField] private float strength = 2f;
13 [SerializeField] private float distanceToApplyForce = 0.2f;
14
15 // ----- Unity Events
16 void OnEnable()
17 {
18 InputManager.Instance.OnInteractCanceled += StopInteracting;
19 }
20
21 void OnDisable()
22 {
23 InputManager.Instance.OnInteractCanceled -= StopInteracting;
24 }
25
26 // ----- Private Methods
27 private void StopInteracting()
28 {
29 StopAllCoroutines();
30 }
31
32 private IEnumerator MoveObject(Transform cam)
33 {
34 while (true)
35 {
36 float pointDistance = Vector3.Distance(transform.position, cam.position);
37 Vector3 camPoint = cam.position + cam.forward * pointDistance;
38
39 Vector3 lineDir = rb.transform.forward;
40 float projectionAmount = Vector3.Dot(camPoint - transform.position, lineDir);
41 Vector3 targetPoint = transform.position + lineDir * projectionAmount;
42
43 if (Vector3.Distance(cam.position, targetPoint) > InteractDistance)
44 {
45 float clampedProjection = Vector3.Dot(cam.position + cam.forward * InteractDistance - transform.position, lineDir);
46 targetPoint = transform.position + lineDir * clampedProjection;
47 }
48
49 DebugHelper.DebugDrawCube(targetPoint, 0.1f, Color.cyan);
50
51 Vector3 forceDir = (targetPoint - transform.position).normalized;
52 float targetDistance = Vector3.Distance(transform.position, targetPoint);
53
54 float forceMagnitude = targetDistance.MapClamp(0f, distanceToApplyForce, 0f, strength);
55 rb.linearVelocity = forceDir * forceMagnitude;
56
57 yield return null;
58 }
59 }
60
61 // ----- Public Methods
62 public override void Interact(InteractInfo info)
63 {
64 StartCoroutine(MoveObject(info.cam));
65 }
66
67 public override void DisabledInteract()
68 {
69
70 }
71 }
72}1#if UNITY_EDITOR
2using UnityEditor;
3using SystemUtilities;
4using UnityEngine;
5
6namespace Interactions
7{
8 [CustomEditor(typeof(Interaction), true), CanEditMultipleObjects]
9 public class InteractionEditor : Editor
10 {
11 // ----- Fields
12 private bool showSettings;
13
14 private SerializedProperty outOfRangeTex;
15 private SerializedProperty unselectedTex;
16 private SerializedProperty selectedTex;
17 private SerializedProperty unselectedDisabledTex;
18 private SerializedProperty selectedDisabledTex;
19
20 private SerializedProperty interactionType;
21 private SerializedProperty showDistance;
22 private SerializedProperty interactDistance;
23 private SerializedProperty showAngle;
24 private SerializedProperty interactAngle;
25 private SerializedProperty showHeight;
26 private SerializedProperty interactHeight;
27 private SerializedProperty showOffsetHeight;
28 private SerializedProperty interactOffsetHeight;
29 private SerializedProperty interactRange;
30
31 private SerializedProperty mantainInitialRotation;
32 private SerializedProperty interactOnKeyPressed;
33 private SerializedProperty onlySeeWithRaycast;
34 private SerializedProperty conditions;
35
36 // ----- Unity Events
37 void OnEnable()
38 {
39 outOfRangeTex = serializedObject.FindProperty("outOfRangeTex");
40 unselectedTex = serializedObject.FindProperty("unselectedTex");
41 selectedTex = serializedObject.FindProperty("selectedTex");
42 unselectedDisabledTex = serializedObject.FindProperty("unselectedDisabledTex");
43 selectedDisabledTex = serializedObject.FindProperty("selectedDisabledTex");
44
45 interactionType = serializedObject.FindProperty("interactionType");
46 showDistance = serializedObject.FindProperty("showDistance");
47 interactDistance = serializedObject.FindProperty("interactDistance");
48 showAngle = serializedObject.FindProperty("showAngle");
49 interactAngle = serializedObject.FindProperty("interactAngle");
50 showHeight = serializedObject.FindProperty("showHeight");
51 interactHeight = serializedObject.FindProperty("interactHeight");
52 showOffsetHeight = serializedObject.FindProperty("showOffsetHeight");
53 interactOffsetHeight = serializedObject.FindProperty("interactOffsetHeight");
54 interactRange = serializedObject.FindProperty("interactRange");
55
56 mantainInitialRotation = serializedObject.FindProperty("mantainInitialRotation");
57 interactOnKeyPressed = serializedObject.FindProperty("interactOnKeyPressed");
58 onlySeeWithRaycast = serializedObject.FindProperty("onlySeeWithRaycast");
59 conditions = serializedObject.FindProperty("conditions");
60 }
61
62 // ----- Private Methods
63 private static void DrawArc(Vector3 pos, Vector3 forward, Vector3 right, float angle, float distance)
64 {
65 Vector3 dir1 = Quaternion.AngleAxis(-angle, right) * forward;
66 Vector3 dir2 = Quaternion.AngleAxis(angle, right) * forward;
67
68 Handles.DrawLine(pos, pos + dir1 * distance);
69 Handles.DrawLine(pos, pos + dir2 * distance);
70
71 Handles.DrawWireArc(pos, right, dir1, angle * 2f, distance);
72 }
73
74 private static void DrawDisc(Vector3 startPos, Vector3 forward, Vector3 right, float angle, float distance)
75 {
76 Vector3 dir1 = Quaternion.AngleAxis(angle, right) * forward;
77 Vector3 dir2 = Quaternion.AngleAxis(-angle, right) * forward;
78
79 Vector3 pos = Vector3.Lerp(startPos + dir1 * distance, startPos + dir2 * distance, 0.5f);
80 float radius = Vector3.Distance(pos, startPos + dir1 * distance);
81
82 Handles.DrawWireDisc(pos, forward, radius);
83 }
84
85 private static void DrawLines(Vector3 startPos, Vector3 forward, Vector3 up, float angle, float distance, float height, float offset)
86 {
87 Vector3 dir1 = Quaternion.AngleAxis(-angle, up) * forward;
88 Vector3 dir2 = Quaternion.AngleAxis(angle, up) * forward;
89
90 Vector3 add = up * (0.5f * height - offset);
91 Vector3 pos1 = startPos + dir1 * distance - add;
92 Vector3 pos2 = startPos + dir2 * distance - add;
93
94 Handles.DrawLine(pos1, pos1 + up * height);
95 Handles.DrawLine(pos2, pos2 + up * height);
96 }
97
98 private static void DrawDirectional3D(Interaction script)
99 {
100 Vector3 pos = script.transform.position;
101 Vector3 forward = script.transform.forward;
102 Vector3 up = script.transform.up;
103 Vector3 right = script.transform.right;
104
105 Handles.color = "FFCE33".HexToColor();
106 DrawArc(pos, forward, up, script.ShowAngle, script.ShowDistance);
107 DrawArc(pos, forward, right, script.ShowAngle, script.ShowDistance);
108 DrawDisc(pos, forward, right, script.ShowAngle, script.ShowDistance);
109
110 Handles.color = "FF8633".HexToColor();
111 DrawArc(pos, forward, up, script.InteractAngle, script.InteractDistance);
112 DrawArc(pos, forward, right, script.InteractAngle, script.InteractDistance);
113 DrawDisc(pos, forward, right, script.InteractAngle, script.InteractDistance);
114 }
115
116 private static void DrawDirectional2D(Interaction script)
117 {
118 Vector3 pos = script.transform.position;
119 Vector3 forward = script.transform.forward;
120 Vector3 up = script.transform.up;
121
122 Handles.color = "FFCE33".HexToColor();
123 DrawArc(pos + up * (0.5f * script.ShowHeight + script.ShowOffsetHeight), forward, up, script.ShowAngle, script.ShowDistance);
124 DrawArc(pos - up * (0.5f * script.ShowHeight - script.ShowOffsetHeight), forward, up, script.ShowAngle, script.ShowDistance);
125 DrawLines(pos, forward, up, script.ShowAngle, script.ShowDistance, script.ShowHeight, script.ShowOffsetHeight);
126
127 Handles.color = "FF8633".HexToColor();
128 float interactHeight = 0.5f * script.InteractHeight;
129 DrawArc(pos + up * (interactHeight + script.InteractOffsetHeight), forward, up, script.InteractAngle, script.InteractDistance);
130 DrawArc(pos - up * (interactHeight - script.InteractOffsetHeight), forward, up, script.InteractAngle, script.InteractDistance);
131 DrawLines(pos, forward, up, script.InteractAngle, script.InteractDistance, 2f * interactHeight, script.InteractOffsetHeight);
132
133 Vector3 pos1 = pos - up * (0.5f * script.ShowHeight - script.ShowOffsetHeight);
134 Vector3 pos2 = pos - up * (interactHeight - script.InteractOffsetHeight);
135 Vector3 pos3 = pos + up * (0.5f * script.ShowHeight + script.ShowOffsetHeight);
136 Vector3 pos4 = pos + up * (interactHeight + script.InteractOffsetHeight);
137
138 Handles.color = "FFCE33".HexToColor();
139 Handles.DrawLine(pos1, pos2);
140 Handles.DrawLine(pos3, pos4);
141 Handles.color = "FF8633".HexToColor();
142 Handles.DrawLine(pos2, pos4);
143 }
144
145 private static void DrawOmnidirectional(Interaction script)
146 {
147 Vector3 pos = script.transform.position;
148
149 Handles.color = "FFCE33".HexToColor();
150 Handles.DrawWireDisc(pos, Vector3.up, script.ShowDistance);
151 Handles.DrawWireDisc(pos, Vector3.right, script.ShowDistance);
152 Handles.DrawWireDisc(pos, Vector3.forward, script.ShowDistance);
153
154 Handles.color = "FF8633".HexToColor();
155 Handles.DrawWireDisc(pos, Vector3.up, script.InteractDistance);
156 Handles.DrawWireDisc(pos, Vector3.right, script.InteractDistance);
157 Handles.DrawWireDisc(pos, Vector3.forward, script.InteractDistance);
158 }
159
160 // ----- Public Methods
161 public void OnSceneGUI()
162 {
163 Interaction script = (Interaction)target;
164
165 if (script.InteractionType == Interaction.Type.Directional3D) DrawDirectional3D(script);
166 else if (script.InteractionType == Interaction.Type.Directional2D) DrawDirectional2D(script);
167 else DrawOmnidirectional(script);
168
169 if (!SceneView.lastActiveSceneView || !SceneView.lastActiveSceneView.camera) return;
170 Vector3 cameraDir = (SceneView.lastActiveSceneView.camera.transform.position - script.transform.position).normalized;
171 Handles.color = "FF4933".HexToColor();
172 Handles.DrawWireDisc(script.transform.position, cameraDir, script.InteractRange);
173 }
174
175 public override void OnInspectorGUI()
176 {
177 serializedObject.Update();
178
179 showSettings = EditorGUILayout.Foldout(showSettings, "Interaction Settings");
180 if (showSettings)
181 {
182 EditorGUI.indentLevel++;
183
184 EditorGUILayout.PropertyField(outOfRangeTex);
185 EditorGUILayout.PropertyField(unselectedTex);
186 EditorGUILayout.PropertyField(selectedTex);
187 EditorGUILayout.PropertyField(unselectedDisabledTex);
188 EditorGUILayout.PropertyField(selectedDisabledTex);
189
190 EditorGUILayout.PropertyField(interactionType);
191 EditorGUILayout.PropertyField(showDistance);
192 EditorGUILayout.Slider(interactDistance, 0f, showDistance.floatValue);
193
194 if ((Interaction.Type)interactionType.enumValueIndex != Interaction.Type.Omnidirectional)
195 {
196 EditorGUILayout.PropertyField(showAngle);
197 EditorGUILayout.Slider(interactAngle, 0f, showAngle.floatValue);
198 }
199
200 if ((Interaction.Type)interactionType.enumValueIndex == Interaction.Type.Directional2D)
201 {
202 EditorGUILayout.PropertyField(showHeight);
203 EditorGUILayout.Slider(interactHeight, 0f, showHeight.floatValue);
204 EditorGUILayout.PropertyField(showOffsetHeight);
205 EditorGUILayout.Slider(interactOffsetHeight,
206 showOffsetHeight.floatValue - (0.5f * showHeight.floatValue - 0.5f * interactHeight.floatValue),
207 showOffsetHeight.floatValue + (0.5f * showHeight.floatValue - 0.5f * interactHeight.floatValue));
208 }
209
210 EditorGUILayout.PropertyField(interactRange);
211
212 EditorGUILayout.PropertyField(mantainInitialRotation);
213 EditorGUILayout.PropertyField(interactOnKeyPressed);
214 EditorGUILayout.PropertyField(onlySeeWithRaycast);
215 EditorGUILayout.PropertyField(conditions);
216
217 EditorGUI.indentLevel--;
218 }
219
220 EditorGUILayout.Space(8f);
221
222 DrawPropertiesExcluding(serializedObject,
223 "m_Script", "outOfRangeTex", "unselectedTex", "selectedTex", "unselectedDisabledTex", "selectedDisabledTex",
224 "interactionType", "showDistance", "interactDistance", "showAngle", "interactAngle", "showHeight", "interactHeight", "showOffsetHeight",
225 "interactOffsetHeight", "interactRange", "mantainInitialRotation", "interactOnKeyPressed", "onlySeeWithRaycast", "conditions");
226
227 serializedObject.ApplyModifiedProperties();
228 }
229 }
230}
231#endif