A game about forced loneliness, made by TACStudios
at master 213 lines 7.3 kB view raw
1using System; 2using System.Diagnostics; 3using UnityEngine.InputSystem.LowLevel; 4#if UNITY_EDITOR 5using UnityEditor; 6#endif 7 8////REVIEW: this *really* should be renamed to TouchPolling or something like that 9 10////REVIEW: Should this auto-enable itself when the API is used? Problem with this is that it means the first touch inputs will get missed 11//// as by the time the API is polled, we're already into the first frame. 12 13////TODO: gesture support 14////TODO: high-frequency touch support 15 16////REVIEW: have TouchTap, TouchSwipe, etc. wrapper MonoBehaviours like LeanTouch? 17 18////TODO: as soon as we can break the API, remove the EnhancedTouchSupport class altogether and rename UnityEngine.InputSystem.EnhancedTouch to TouchPolling 19 20////FIXME: does not survive domain reloads 21 22namespace UnityEngine.InputSystem.EnhancedTouch 23{ 24 /// <summary> 25 /// API to control enhanced touch facilities like <see cref="Touch"/> that are not 26 /// enabled by default. 27 /// </summary> 28 /// <remarks> 29 /// Enhanced touch support provides automatic finger tracking and touch history recording. 30 /// It is an API designed for polling, i.e. for querying touch state directly in methods 31 /// such as <c>MonoBehaviour.Update</c>. Enhanced touch support cannot be used in combination 32 /// with <see cref="InputAction"/>s though both can be used side-by-side. 33 /// 34 /// <example> 35 /// <code> 36 /// public class MyBehavior : MonoBehaviour 37 /// { 38 /// protected void OnEnable() 39 /// { 40 /// EnhancedTouchSupport.Enable(); 41 /// } 42 /// 43 /// protected void OnDisable() 44 /// { 45 /// EnhancedTouchSupport.Disable(); 46 /// } 47 /// 48 /// protected void Update() 49 /// { 50 /// var activeTouches = Touch.activeTouches; 51 /// for (var i = 0; i &lt; activeTouches.Count; ++i) 52 /// Debug.Log("Active touch: " + activeTouches[i]); 53 /// } 54 /// } 55 /// </code> 56 /// </example> 57 /// </remarks> 58 /// <seealso cref="Touch"/> 59 /// <seealso cref="Finger"/> 60 public static class EnhancedTouchSupport 61 { 62 /// <summary> 63 /// Whether enhanced touch support is currently enabled. 64 /// </summary> 65 /// <value>True if EnhancedTouch support has been enabled.</value> 66 public static bool enabled => s_Enabled > 0; 67 68 private static int s_Enabled; 69 private static InputSettings.UpdateMode s_UpdateMode; 70 71 /// <summary> 72 /// Enable enhanced touch support. 73 /// </summary> 74 /// <remarks> 75 /// Calling this method is necessary to enable the functionality provided 76 /// by <see cref="Touch"/> and <see cref="Finger"/>. These APIs add extra 77 /// processing to touches and are thus disabled by default. 78 /// 79 /// Calls to <c>Enable</c> and <see cref="Disable"/> balance each other out. 80 /// If <c>Enable</c> is called repeatedly, it will take as many calls to 81 /// <see cref="Disable"/> to disable the system again. 82 /// </remarks> 83 public static void Enable() 84 { 85 ++s_Enabled; 86 if (s_Enabled > 1) 87 return; 88 89 InputSystem.onDeviceChange += OnDeviceChange; 90 InputSystem.onBeforeUpdate += Touch.BeginUpdate; 91 InputSystem.onSettingsChange += OnSettingsChange; 92 93 #if UNITY_EDITOR 94 AssemblyReloadEvents.beforeAssemblyReload += OnBeforeDomainReload; 95 #endif 96 97 SetUpState(); 98 } 99 100 /// <summary> 101 /// Disable enhanced touch support. 102 /// </summary> 103 /// <remarks> 104 /// This method only undoes a single call to <see cref="Enable"/>. 105 /// </remarks> 106 public static void Disable() 107 { 108 if (!enabled) 109 return; 110 --s_Enabled; 111 if (s_Enabled > 0) 112 return; 113 114 InputSystem.onDeviceChange -= OnDeviceChange; 115 InputSystem.onBeforeUpdate -= Touch.BeginUpdate; 116 InputSystem.onSettingsChange -= OnSettingsChange; 117 118 #if UNITY_EDITOR 119 AssemblyReloadEvents.beforeAssemblyReload -= OnBeforeDomainReload; 120 #endif 121 122 TearDownState(); 123 } 124 125 internal static void Reset() 126 { 127 Touch.s_GlobalState.touchscreens = default; 128 Touch.s_GlobalState.playerState.Destroy(); 129 Touch.s_GlobalState.playerState = default; 130 #if UNITY_EDITOR 131 Touch.s_GlobalState.editorState.Destroy(); 132 Touch.s_GlobalState.editorState = default; 133 #endif 134 s_Enabled = 0; 135 } 136 137 private static void SetUpState() 138 { 139 Touch.s_GlobalState.playerState.updateMask = InputUpdateType.Dynamic | InputUpdateType.Manual | InputUpdateType.Fixed; 140 #if UNITY_EDITOR 141 Touch.s_GlobalState.editorState.updateMask = InputUpdateType.Editor; 142 #endif 143 144 s_UpdateMode = InputSystem.settings.updateMode; 145 146 foreach (var device in InputSystem.devices) 147 OnDeviceChange(device, InputDeviceChange.Added); 148 } 149 150 internal static void TearDownState() 151 { 152 foreach (var device in InputSystem.devices) 153 OnDeviceChange(device, InputDeviceChange.Removed); 154 155 Touch.s_GlobalState.playerState.Destroy(); 156 #if UNITY_EDITOR 157 Touch.s_GlobalState.editorState.Destroy(); 158 #endif 159 160 Touch.s_GlobalState.playerState = default; 161 #if UNITY_EDITOR 162 Touch.s_GlobalState.editorState = default; 163 #endif 164 } 165 166 private static void OnDeviceChange(InputDevice device, InputDeviceChange change) 167 { 168 switch (change) 169 { 170 case InputDeviceChange.Added: 171 { 172 if (device is Touchscreen touchscreen) 173 Touch.AddTouchscreen(touchscreen); 174 break; 175 } 176 177 case InputDeviceChange.Removed: 178 { 179 if (device is Touchscreen touchscreen) 180 Touch.RemoveTouchscreen(touchscreen); 181 break; 182 } 183 } 184 } 185 186 private static void OnSettingsChange() 187 { 188 var currentUpdateMode = InputSystem.settings.updateMode; 189 if (s_UpdateMode == currentUpdateMode) 190 return; 191 TearDownState(); 192 SetUpState(); 193 } 194 195 #if UNITY_EDITOR 196 private static void OnBeforeDomainReload() 197 { 198 // We need to release NativeArrays we're holding before losing track of them during domain reloads. 199 Touch.s_GlobalState.playerState.Destroy(); 200 Touch.s_GlobalState.editorState.Destroy(); 201 } 202 203 #endif 204 205 [Conditional("DEVELOPMENT_BUILD")] 206 [Conditional("UNITY_EDITOR")] 207 internal static void CheckEnabled() 208 { 209 if (!enabled) 210 throw new InvalidOperationException("EnhancedTouch API is not enabled; call EnhancedTouchSupport.Enable()"); 211 } 212 } 213}