diff options
Diffstat (limited to 'Assets/uGUI-2017.1/UnityEngine.UI/EventSystem')
46 files changed, 3423 insertions, 0 deletions
diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData.meta new file mode 100644 index 0000000..6a26991 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData.meta @@ -0,0 +1,10 @@ +fileFormatVersion: 2 +guid: 2a7965b878e0c3c4abdb68deac365981 +folderAsset: yes +timeCreated: 1602119280 +licenseType: Free +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/AxisEventData.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/AxisEventData.cs new file mode 100644 index 0000000..3278d6d --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/AxisEventData.cs @@ -0,0 +1,15 @@ +namespace UnityEngine.EventSystems +{ + public class AxisEventData : BaseEventData + { + public Vector2 moveVector { get; set; } + public MoveDirection moveDir { get; set; } + + public AxisEventData(EventSystem eventSystem) + : base(eventSystem) + { + moveVector = Vector2.zero; + moveDir = MoveDirection.None; + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/AxisEventData.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/AxisEventData.cs.meta new file mode 100644 index 0000000..d770a40 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/AxisEventData.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 068c7c2e61fdac34ebd23b76779526fd +timeCreated: 1602119377 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/BaseEventData.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/BaseEventData.cs new file mode 100644 index 0000000..f353314 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/BaseEventData.cs @@ -0,0 +1,42 @@ +namespace UnityEngine.EventSystems +{ + public abstract class AbstractEventData + { + protected bool m_Used; // 当前事件是否被处理(被吞) + + public virtual void Reset() + { + m_Used = false; + } + + public virtual void Use() + { + m_Used = true; + } + + public virtual bool used + { + get { return m_Used; } + } + } + + public class BaseEventData : AbstractEventData + { + private readonly EventSystem m_EventSystem; + public BaseEventData(EventSystem eventSystem) + { + m_EventSystem = eventSystem; + } + + public BaseInputModule currentInputModule + { + get { return m_EventSystem.currentInputModule; } + } + + public GameObject selectedObject + { + get { return m_EventSystem.currentSelectedGameObject; } + set { m_EventSystem.SetSelectedGameObject(value, this); } // 会发送一个selecthandler事件 + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/BaseEventData.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/BaseEventData.cs.meta new file mode 100644 index 0000000..5265b51 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/BaseEventData.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 8249b81d25be82b4388cb41d127fe369 +timeCreated: 1602119379 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/PointerEventData.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/PointerEventData.cs new file mode 100644 index 0000000..9b94e00 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/PointerEventData.cs @@ -0,0 +1,138 @@ +using System; +using System.Text; +using System.Collections.Generic; + +namespace UnityEngine.EventSystems +{ + /// <summary> + /// Each touch event creates one of these containing all the relevant information. + /// </summary> + public class PointerEventData : BaseEventData + { + public enum InputButton + { + Left = 0, + Right = 1, + Middle = 2 + } + + public enum FramePressState + { + Pressed, + Released, + PressedAndReleased, + NotChanged + } + + public GameObject pointerEnter { get; set; } + + // The object that received OnPointerDown + private GameObject m_PointerPress; + // The object last received OnPointerDown + public GameObject lastPress { get; private set; } + // The object that the press happened on even if it can not handle the press event + public GameObject rawPointerPress { get; set; } + // The object that received OnDrag + public GameObject pointerDrag { get; set; } + + public RaycastResult pointerCurrentRaycast { get; set; } + public RaycastResult pointerPressRaycast { get; set; } + + public List<GameObject> hovered = new List<GameObject>(); + + public bool eligibleForClick { get; set; } + + public int pointerId { get; set; } + + // Current position of the mouse or touch event + public Vector2 position { get; set; } + // Delta since last update + public Vector2 delta { get; set; } + // Position of the press event + public Vector2 pressPosition { get; set; } + // World-space position where a ray cast into the screen hits something + [Obsolete("Use either pointerCurrentRaycast.worldPosition or pointerPressRaycast.worldPosition")] + public Vector3 worldPosition { get; set; } + // World-space normal where a ray cast into the screen hits something + [Obsolete("Use either pointerCurrentRaycast.worldNormal or pointerPressRaycast.worldNormal")] + public Vector3 worldNormal { get; set; } + // The last time a click event was sent out (used for double-clicks) + public float clickTime { get; set; } + // Number of clicks in a row. 2 for a double-click for example. + public int clickCount { get; set; } + + public Vector2 scrollDelta { get; set; } + public bool useDragThreshold { get; set; } + public bool dragging { get; set; } + + public InputButton button { get; set; } + + public PointerEventData(EventSystem eventSystem) : base(eventSystem) + { + eligibleForClick = false; + + pointerId = -1; + position = Vector2.zero; // Current position of the mouse or touch event + delta = Vector2.zero; // Delta since last update + pressPosition = Vector2.zero; // Delta since the event started being tracked + clickTime = 0.0f; // The last time a click event was sent out (used for double-clicks) + clickCount = 0; // Number of clicks in a row. 2 for a double-click for example. + + scrollDelta = Vector2.zero; + useDragThreshold = true; + dragging = false; + button = InputButton.Left; + } + + public bool IsPointerMoving() + { + return delta.sqrMagnitude > 0.0f; + } + + public bool IsScrolling() + { + return scrollDelta.sqrMagnitude > 0.0f; + } + + public Camera enterEventCamera + { + get { return pointerCurrentRaycast.module == null ? null : pointerCurrentRaycast.module.eventCamera; } + } + + public Camera pressEventCamera + { + get { return pointerPressRaycast.module == null ? null : pointerPressRaycast.module.eventCamera; } + } + + public GameObject pointerPress + { + get { return m_PointerPress; } + set + { + if (m_PointerPress == value) + return; + + lastPress = m_PointerPress; + m_PointerPress = value; + } + } + + public override string ToString() + { + var sb = new StringBuilder(); + sb.AppendLine("<b>Position</b>: " + position); + sb.AppendLine("<b>delta</b>: " + delta); + sb.AppendLine("<b>eligibleForClick</b>: " + eligibleForClick); + sb.AppendLine("<b>pointerEnter</b>: " + pointerEnter); + sb.AppendLine("<b>pointerPress</b>: " + pointerPress); + sb.AppendLine("<b>lastPointerPress</b>: " + lastPress); + sb.AppendLine("<b>pointerDrag</b>: " + pointerDrag); + sb.AppendLine("<b>Use Drag Threshold</b>: " + useDragThreshold); + sb.AppendLine("<b>Current Rayast:</b>"); + sb.AppendLine(pointerCurrentRaycast.ToString()); + sb.AppendLine("<b>Press Rayast:</b>"); + sb.AppendLine(pointerPressRaycast.ToString()); + return sb.ToString(); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/PointerEventData.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/PointerEventData.cs.meta new file mode 100644 index 0000000..866eab8 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventData/PointerEventData.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 721b5956a0219d74b9aa58b2fd44ffe3 +timeCreated: 1602119379 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler.meta new file mode 100644 index 0000000..732637d --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 146a9b1a2f14b51468a9381c1562257e +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventHandle.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventHandle.cs new file mode 100644 index 0000000..977514f --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventHandle.cs @@ -0,0 +1,11 @@ +using System; + +namespace UnityEngine.EventSystems +{ + [Flags] + public enum EventHandle + { + Unused = 0, + Used = 1 + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventHandle.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventHandle.cs.meta new file mode 100644 index 0000000..1e2c52f --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventHandle.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 0c5751e0f52a2d9459e76555a888ad06 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventInterfaces.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventInterfaces.cs new file mode 100644 index 0000000..b808e6c --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventInterfaces.cs @@ -0,0 +1,91 @@ +namespace UnityEngine.EventSystems +{ + public interface IEventSystemHandler + { + } + + public interface IPointerEnterHandler : IEventSystemHandler + { + void OnPointerEnter(PointerEventData eventData); + } + + public interface IPointerExitHandler : IEventSystemHandler + { + void OnPointerExit(PointerEventData eventData); + } + + public interface IPointerDownHandler : IEventSystemHandler + { + void OnPointerDown(PointerEventData eventData); + } + + public interface IPointerUpHandler : IEventSystemHandler + { + void OnPointerUp(PointerEventData eventData); + } + + public interface IPointerClickHandler : IEventSystemHandler + { + void OnPointerClick(PointerEventData eventData); + } + + public interface IBeginDragHandler : IEventSystemHandler + { + void OnBeginDrag(PointerEventData eventData); + } + + public interface IInitializePotentialDragHandler : IEventSystemHandler + { + void OnInitializePotentialDrag(PointerEventData eventData); + } + + public interface IDragHandler : IEventSystemHandler + { + void OnDrag(PointerEventData eventData); + } + + public interface IEndDragHandler : IEventSystemHandler + { + void OnEndDrag(PointerEventData eventData); + } + + public interface IDropHandler : IEventSystemHandler + { + void OnDrop(PointerEventData eventData); + } + + public interface IScrollHandler : IEventSystemHandler + { + void OnScroll(PointerEventData eventData); + } + + public interface IUpdateSelectedHandler : IEventSystemHandler + { + void OnUpdateSelected(BaseEventData eventData); + } + + public interface ISelectHandler : IEventSystemHandler + { + void OnSelect(BaseEventData eventData); + } + + public interface IDeselectHandler : IEventSystemHandler + { + void OnDeselect(BaseEventData eventData); + } + + public interface IMoveHandler : IEventSystemHandler + { + void OnMove(AxisEventData eventData); + } + + public interface ISubmitHandler : IEventSystemHandler + { + void OnSubmit(BaseEventData eventData); + } + + public interface ICancelHandler : IEventSystemHandler + { + void OnCancel(BaseEventData eventData); + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventInterfaces.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventInterfaces.cs.meta new file mode 100644 index 0000000..2a369ae --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventInterfaces.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 7bb73ff56f2f85b4ca62f8cb5ea59840 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventSystem.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventSystem.cs new file mode 100644 index 0000000..1440547 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventSystem.cs @@ -0,0 +1,328 @@ +using System; +using System.Collections.Generic; +using System.Text; +using UnityEngine; +using UnityEngine.Serialization; + +namespace UnityEngine.EventSystems +{ + [AddComponentMenu("Event/Event System")] + public class EventSystem : UIBehaviour + { + // 获得当前EventSystem挂着的BaseInputModule的派生类,一般来说只会挂一个StandableInputModule + private List<BaseInputModule> m_SystemInputModules = new List<BaseInputModule>(); + + private BaseInputModule m_CurrentInputModule; + + public static EventSystem current { get; set; } + + [SerializeField] + [FormerlySerializedAs("m_Selected")] + private GameObject m_FirstSelected; + + [SerializeField] + private bool m_sendNavigationEvents = true; // Should the EventSystem allow navigation events (move / submit / cancel). + + public bool sendNavigationEvents + { + get { return m_sendNavigationEvents; } + set { m_sendNavigationEvents = value; } + } + + [SerializeField] + private int m_DragThreshold = 5; + public int pixelDragThreshold + { + get { return m_DragThreshold; } + set { m_DragThreshold = value; } + } + + private GameObject m_CurrentSelected; + + public BaseInputModule currentInputModule + { + get { return m_CurrentInputModule; } + } + + /// <summary> + /// Only one object can be selected at a time. Think: controller-selected button. + /// </summary> + public GameObject firstSelectedGameObject + { + get { return m_FirstSelected; } + set { m_FirstSelected = value; } + } + + public GameObject currentSelectedGameObject + { + get { return m_CurrentSelected; } + } + + [Obsolete("lastSelectedGameObject is no longer supported")] + public GameObject lastSelectedGameObject + { + get { return null; } + } + + private bool m_HasFocus = true; + + public bool isFocused + { + get { return m_HasFocus; } + } + + protected EventSystem() + {} + + //c 把挂着的input modules加入m_SystemInputModules + public void UpdateModules() + { + // 拿到当前EventSystem下面挂着的inputmodule,通常来说只会挂一个standaloneInputModule + GetComponents(m_SystemInputModules); + for (int i = m_SystemInputModules.Count - 1; i >= 0; i--) + { + if (m_SystemInputModules[i] && m_SystemInputModules[i].IsActive()) + continue; + m_SystemInputModules.RemoveAt(i); + } + } + + private bool m_SelectionGuard; + public bool alreadySelecting + { + get { return m_SelectionGuard; } + } + + public void SetSelectedGameObject(GameObject selected, BaseEventData pointer) + { + if (m_SelectionGuard) + { + Debug.LogError("Attempting to select " + selected + "while already selecting an object."); + return; + } + + m_SelectionGuard = true; + if (selected == m_CurrentSelected) + { + m_SelectionGuard = false; + return; + } + + // Debug.Log("Selection: new (" + selected + ") old (" + m_CurrentSelected + ")"); + ExecuteEvents.Execute(m_CurrentSelected, pointer, ExecuteEvents.deselectHandler); + m_CurrentSelected = selected; + ExecuteEvents.Execute(m_CurrentSelected, pointer, ExecuteEvents.selectHandler); + m_SelectionGuard = false; + } + + private BaseEventData m_DummyData; + private BaseEventData baseEventDataCache + { + get + { + if (m_DummyData == null) + m_DummyData = new BaseEventData(this); + + return m_DummyData; + } + } + + public void SetSelectedGameObject(GameObject selected) + { + SetSelectedGameObject(selected, baseEventDataCache); + } + + private static int RaycastComparer(RaycastResult lhs, RaycastResult rhs) + { + if (lhs.module != rhs.module) + { + var lhsEventCamera = lhs.module.eventCamera; + var rhsEventCamera = rhs.module.eventCamera; + if (lhsEventCamera != null && rhsEventCamera != null && lhsEventCamera.depth != rhsEventCamera.depth) + { + // need to reverse the standard compareTo + if (lhsEventCamera.depth < rhsEventCamera.depth) + return 1; + if (lhsEventCamera.depth == rhsEventCamera.depth) + return 0; + + return -1; + } + + if (lhs.module.sortOrderPriority != rhs.module.sortOrderPriority) + return rhs.module.sortOrderPriority.CompareTo(lhs.module.sortOrderPriority); + + if (lhs.module.renderOrderPriority != rhs.module.renderOrderPriority) + return rhs.module.renderOrderPriority.CompareTo(lhs.module.renderOrderPriority); + } + + if (lhs.sortingLayer != rhs.sortingLayer) + { + // Uses the layer value to properly compare the relative order of the layers. + var rid = SortingLayer.GetLayerValueFromID(rhs.sortingLayer); + var lid = SortingLayer.GetLayerValueFromID(lhs.sortingLayer); + return rid.CompareTo(lid); + } + + + if (lhs.sortingOrder != rhs.sortingOrder) + return rhs.sortingOrder.CompareTo(lhs.sortingOrder); + + if (lhs.depth != rhs.depth) + return rhs.depth.CompareTo(lhs.depth); + + if (lhs.distance != rhs.distance) + return lhs.distance.CompareTo(rhs.distance); + + return lhs.index.CompareTo(rhs.index); + }
+
+ #region 射线检测 +
+ private static readonly Comparison<RaycastResult> s_RaycastComparer = RaycastComparer; + + // 从PointerInputModule.GetTouchPointerEventData()来的触摸数据 + public void RaycastAll(PointerEventData eventData, List<RaycastResult> raycastResults) + { + raycastResults.Clear(); + //包括场景中所有的raycaster + var modules = RaycasterManager.GetRaycasters(); + for (int i = 0; i < modules.Count; ++i) + { + var module = modules[i]; + if (module == null || !module.IsActive()) + continue; + + module.Raycast(eventData, raycastResults); + } + + raycastResults.Sort(s_RaycastComparer); + }
+
+ #endregion +
+ //c 是否点击到某个物体
+ public bool IsPointerOverGameObject() + { + return IsPointerOverGameObject(PointerInputModule.kMouseLeftId); + } + + //c 是否点击到某个物体 + public bool IsPointerOverGameObject(int pointerId) + { + if (m_CurrentInputModule == null) + return false; + + return m_CurrentInputModule.IsPointerOverGameObject(pointerId); + } + + protected override void OnEnable() + { + base.OnEnable(); + if (EventSystem.current == null) + EventSystem.current = this; +#if UNITY_EDITOR + else + { + Debug.LogWarning("Multiple EventSystems in scene... this is not supported"); + } +#endif + } + + protected override void OnDisable() + { + if (m_CurrentInputModule != null) + { + m_CurrentInputModule.DeactivateModule(); + m_CurrentInputModule = null; + } + + if (EventSystem.current == this) + EventSystem.current = null; + + base.OnDisable(); + } + + protected virtual void OnApplicationFocus(bool hasFocus) + { + m_HasFocus = hasFocus; + } + + private void TickModules() + { + // 只有standaloneInputModule一个 + for (var i = 0; i < m_SystemInputModules.Count; i++) + { + if (m_SystemInputModules[i] != null) + m_SystemInputModules[i].UpdateModule(); + } + } + + //c 事件处理跑在一个update里,以轮训的方式检测输入 + protected virtual void Update() + { + if (current != this) + return; + + // 只更新鼠标位置 + TickModules(); + + // 将m_CurrentInputModule设置为m_SystemInputModules第一个可用的module + bool changedModule = false; + for (var i = 0; i < m_SystemInputModules.Count; i++) + { + var module = m_SystemInputModules[i]; + if (module.IsModuleSupported() && module.ShouldActivateModule()) + { + if (m_CurrentInputModule != module) + { + ChangeEventModule(module); + changedModule = true; + } + break; + } + } + // no event module set... set the first valid one... + if (m_CurrentInputModule == null) + { + for (var i = 0; i < m_SystemInputModules.Count; i++) + { + var module = m_SystemInputModules[i]; + if (module.IsModuleSupported()) + { + ChangeEventModule(module); + changedModule = true; + break; + } + } + } + + //c! 执行事件处理主入口,通常情况下,如果没有自定义的inputModule,就是走StandaloneInputModule的Process + if (!changedModule && m_CurrentInputModule != null) + m_CurrentInputModule.Process(); + } + + private void ChangeEventModule(BaseInputModule module) + { + if (m_CurrentInputModule == module) + return; + + if (m_CurrentInputModule != null) + m_CurrentInputModule.DeactivateModule(); + + if (module != null) + module.ActivateModule(); + m_CurrentInputModule = module; + } + + public override string ToString() + { + var sb = new StringBuilder(); + sb.AppendLine("<b>Selected:</b>" + currentSelectedGameObject); + sb.AppendLine(); + sb.AppendLine(); + sb.AppendLine(m_CurrentInputModule != null ? m_CurrentInputModule.ToString() : "No module"); + return sb.ToString(); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventSystem.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventSystem.cs.meta new file mode 100644 index 0000000..8ff114e --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventSystem.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 153642a2f08376d4daebdf63af9e161a +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTrigger.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTrigger.cs new file mode 100644 index 0000000..11d1c1c --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTrigger.cs @@ -0,0 +1,159 @@ +using System; +using System.Collections.Generic; +using UnityEngine.Events; +using UnityEngine.Serialization; + +namespace UnityEngine.EventSystems +{ + //c 一个辅助组件,给一个事件添加自定义的回调函数 + //继承了所有接口,效率不高,慎用。只是比较方便 + + [AddComponentMenu("Event/Event Trigger")] + public class EventTrigger : + MonoBehaviour, + IPointerEnterHandler, + IPointerExitHandler, + IPointerDownHandler, + IPointerUpHandler, + IPointerClickHandler, + IInitializePotentialDragHandler, + IBeginDragHandler, + IDragHandler, + IEndDragHandler, + IDropHandler, + IScrollHandler, + IUpdateSelectedHandler, + ISelectHandler, + IDeselectHandler, + IMoveHandler, + ISubmitHandler, + ICancelHandler + { + [Serializable] + public class TriggerEvent : UnityEvent<BaseEventData> + {} + + [Serializable] + public class Entry + { + public EventTriggerType eventID = EventTriggerType.PointerClick; + public TriggerEvent callback = new TriggerEvent(); + } + + [FormerlySerializedAs("delegates")] + [SerializeField] + private List<Entry> m_Delegates; + + [Obsolete("Please use triggers instead (UnityUpgradable) -> triggers", true)] + public List<Entry> delegates; + + protected EventTrigger() + {} + + public List<Entry> triggers + { + get + { + if (m_Delegates == null) + m_Delegates = new List<Entry>(); + return m_Delegates; + } + set { m_Delegates = value; } + } + + private void Execute(EventTriggerType id, BaseEventData eventData) + { + for (int i = 0, imax = triggers.Count; i < imax; ++i) + { + var ent = triggers[i]; + if (ent.eventID == id && ent.callback != null) + ent.callback.Invoke(eventData); + } + } + + public virtual void OnPointerEnter(PointerEventData eventData) + { + Execute(EventTriggerType.PointerEnter, eventData); + } + + public virtual void OnPointerExit(PointerEventData eventData) + { + Execute(EventTriggerType.PointerExit, eventData); + } + + public virtual void OnDrag(PointerEventData eventData) + { + Execute(EventTriggerType.Drag, eventData); + } + + public virtual void OnDrop(PointerEventData eventData) + { + Execute(EventTriggerType.Drop, eventData); + } + + public virtual void OnPointerDown(PointerEventData eventData) + { + Execute(EventTriggerType.PointerDown, eventData); + } + + public virtual void OnPointerUp(PointerEventData eventData) + { + Execute(EventTriggerType.PointerUp, eventData); + } + + public virtual void OnPointerClick(PointerEventData eventData) + { + Execute(EventTriggerType.PointerClick, eventData); + } + + public virtual void OnSelect(BaseEventData eventData) + { + Execute(EventTriggerType.Select, eventData); + } + + public virtual void OnDeselect(BaseEventData eventData) + { + Execute(EventTriggerType.Deselect, eventData); + } + + public virtual void OnScroll(PointerEventData eventData) + { + Execute(EventTriggerType.Scroll, eventData); + } + + public virtual void OnMove(AxisEventData eventData) + { + Execute(EventTriggerType.Move, eventData); + } + + public virtual void OnUpdateSelected(BaseEventData eventData) + { + Execute(EventTriggerType.UpdateSelected, eventData); + } + + public virtual void OnInitializePotentialDrag(PointerEventData eventData) + { + Execute(EventTriggerType.InitializePotentialDrag, eventData); + } + + public virtual void OnBeginDrag(PointerEventData eventData) + { + Execute(EventTriggerType.BeginDrag, eventData); + } + + public virtual void OnEndDrag(PointerEventData eventData) + { + Execute(EventTriggerType.EndDrag, eventData); + } + + public virtual void OnSubmit(BaseEventData eventData) + { + Execute(EventTriggerType.Submit, eventData); + } + + public virtual void OnCancel(BaseEventData eventData) + { + Execute(EventTriggerType.Cancel, eventData); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTrigger.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTrigger.cs.meta new file mode 100644 index 0000000..af5beba --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTrigger.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: bacfe5cf756f51b4f8c77a4addae254e +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTriggerType.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTriggerType.cs new file mode 100644 index 0000000..11c232c --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTriggerType.cs @@ -0,0 +1,29 @@ +namespace UnityEngine.EventSystems +{ + /// <summary> + /// This class is capable of triggering one or more remote functions from a specified event. + /// Usage: Attach it to an object with a collider, or to a GUI Graphic of your choice. + /// NOTE: Doing this will make this object intercept ALL events, and no event bubbling will occur from this object! + /// </summary> + + public enum EventTriggerType + { + PointerEnter = 0, + PointerExit = 1, + PointerDown = 2, + PointerUp = 3, + PointerClick = 4, + Drag = 5, + Drop = 6, + Scroll = 7, + UpdateSelected = 8, + Select = 9, + Deselect = 10, + Move = 11, + InitializePotentialDrag = 12, + BeginDrag = 13, + EndDrag = 14, + Submit = 15, + Cancel = 16 + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTriggerType.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTriggerType.cs.meta new file mode 100644 index 0000000..4647857 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/EventTriggerType.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: ec8af6a988832aa46844f9df796dfc4c +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/ExecuteEvents.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/ExecuteEvents.cs new file mode 100644 index 0000000..a749ce8 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/ExecuteEvents.cs @@ -0,0 +1,368 @@ +using System; +using System.Collections.Generic; +using UnityEngine.UI; + +namespace UnityEngine.EventSystems +{ + // 最关键的类,调用gameobject对应的回调函数 + public static class ExecuteEvents + { + public delegate void EventFunction<T1>(T1 handler, BaseEventData eventData); + + public static T ValidateEventData<T>(BaseEventData data) where T : class + { + if ((data as T) == null) + throw new ArgumentException(String.Format("Invalid type: {0} passed to event expecting {1}", data.GetType(), typeof(T))); + return data as T; + } + + private static readonly EventFunction<IPointerEnterHandler> s_PointerEnterHandler = Execute; + + private static void Execute(IPointerEnterHandler handler, BaseEventData eventData) + { + handler.OnPointerEnter(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IPointerExitHandler> s_PointerExitHandler = Execute; + + private static void Execute(IPointerExitHandler handler, BaseEventData eventData) + { + handler.OnPointerExit(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IPointerDownHandler> s_PointerDownHandler = Execute; + + private static void Execute(IPointerDownHandler handler, BaseEventData eventData) + { + handler.OnPointerDown(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IPointerUpHandler> s_PointerUpHandler = Execute; + + private static void Execute(IPointerUpHandler handler, BaseEventData eventData) + { + handler.OnPointerUp(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IPointerClickHandler> s_PointerClickHandler = Execute; + + private static void Execute(IPointerClickHandler handler, BaseEventData eventData) + { + handler.OnPointerClick(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IInitializePotentialDragHandler> s_InitializePotentialDragHandler = Execute; + + private static void Execute(IInitializePotentialDragHandler handler, BaseEventData eventData) + { + handler.OnInitializePotentialDrag(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IBeginDragHandler> s_BeginDragHandler = Execute; + + private static void Execute(IBeginDragHandler handler, BaseEventData eventData) + { + handler.OnBeginDrag(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IDragHandler> s_DragHandler = Execute; + + private static void Execute(IDragHandler handler, BaseEventData eventData) + { + handler.OnDrag(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IEndDragHandler> s_EndDragHandler = Execute; + + private static void Execute(IEndDragHandler handler, BaseEventData eventData) + { + handler.OnEndDrag(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IDropHandler> s_DropHandler = Execute; + + private static void Execute(IDropHandler handler, BaseEventData eventData) + { + handler.OnDrop(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IScrollHandler> s_ScrollHandler = Execute; + + private static void Execute(IScrollHandler handler, BaseEventData eventData) + { + handler.OnScroll(ValidateEventData<PointerEventData>(eventData)); + } + + private static readonly EventFunction<IUpdateSelectedHandler> s_UpdateSelectedHandler = Execute; + + private static void Execute(IUpdateSelectedHandler handler, BaseEventData eventData) + { + handler.OnUpdateSelected(eventData); + } + + private static readonly EventFunction<ISelectHandler> s_SelectHandler = Execute; + + private static void Execute(ISelectHandler handler, BaseEventData eventData) + { + handler.OnSelect(eventData); + } + + private static readonly EventFunction<IDeselectHandler> s_DeselectHandler = Execute; + + private static void Execute(IDeselectHandler handler, BaseEventData eventData) + { + handler.OnDeselect(eventData); + } + + private static readonly EventFunction<IMoveHandler> s_MoveHandler = Execute; + + private static void Execute(IMoveHandler handler, BaseEventData eventData) + { + handler.OnMove(ValidateEventData<AxisEventData>(eventData)); + } + + private static readonly EventFunction<ISubmitHandler> s_SubmitHandler = Execute; + + private static void Execute(ISubmitHandler handler, BaseEventData eventData) + { + handler.OnSubmit(eventData); + } + + private static readonly EventFunction<ICancelHandler> s_CancelHandler = Execute; + + private static void Execute(ICancelHandler handler, BaseEventData eventData) + { + handler.OnCancel(eventData); + } + + public static EventFunction<IPointerEnterHandler> pointerEnterHandler + { + get { return s_PointerEnterHandler; } + } + + public static EventFunction<IPointerExitHandler> pointerExitHandler + { + get { return s_PointerExitHandler; } + } + + public static EventFunction<IPointerDownHandler> pointerDownHandler + { + get { return s_PointerDownHandler; } + } + + public static EventFunction<IPointerUpHandler> pointerUpHandler + { + get { return s_PointerUpHandler; } + } + + public static EventFunction<IPointerClickHandler> pointerClickHandler + { + get { return s_PointerClickHandler; } + } + + public static EventFunction<IInitializePotentialDragHandler> initializePotentialDrag + { + get { return s_InitializePotentialDragHandler; } + } + + public static EventFunction<IBeginDragHandler> beginDragHandler + { + get { return s_BeginDragHandler; } + } + + public static EventFunction<IDragHandler> dragHandler + { + get { return s_DragHandler; } + } + + public static EventFunction<IEndDragHandler> endDragHandler + { + get { return s_EndDragHandler; } + } + + public static EventFunction<IDropHandler> dropHandler + { + get { return s_DropHandler; } + } + + public static EventFunction<IScrollHandler> scrollHandler + { + get { return s_ScrollHandler; } + } + + public static EventFunction<IUpdateSelectedHandler> updateSelectedHandler + { + get { return s_UpdateSelectedHandler; } + } + + public static EventFunction<ISelectHandler> selectHandler + { + get { return s_SelectHandler; } + } + + public static EventFunction<IDeselectHandler> deselectHandler + { + get { return s_DeselectHandler; } + } + + public static EventFunction<IMoveHandler> moveHandler + { + get { return s_MoveHandler; } + } + + public static EventFunction<ISubmitHandler> submitHandler + { + get { return s_SubmitHandler; } + } + + public static EventFunction<ICancelHandler> cancelHandler + { + get { return s_CancelHandler; } + } + + private static void GetEventChain(GameObject root, IList<Transform> eventChain) + { + eventChain.Clear(); + if (root == null) + return; + + var t = root.transform; + while (t != null) + { + eventChain.Add(t); + t = t.parent; + } + } + + //IEventSystemHandler是所有接口的基类 + private static readonly ObjectPool<List<IEventSystemHandler>> s_HandlerListPool = new ObjectPool<List<IEventSystemHandler>>(null, l => l.Clear()); + + // 向target gameobject发送一个事件,对每个实现了T接口的类执行functor方法(就是接口中定义的回调) + public static bool Execute<T>(GameObject target, BaseEventData eventData, EventFunction<T> functor) where T : IEventSystemHandler + { + var internalHandlers = s_HandlerListPool.Get(); + GetEventList<T>(target, internalHandlers); + // if (s_InternalHandlers.Count > 0) + // Debug.Log("Executinng " + typeof (T) + " on " + target); + + // 拿到实现了T接口的组件,调用对应的方法 + + for (var i = 0; i < internalHandlers.Count; i++) + { + T arg; + try + { + arg = (T)internalHandlers[i]; + } + catch (Exception e) + { + var temp = internalHandlers[i]; + Debug.LogException(new Exception(string.Format("Type {0} expected {1} received.", typeof(T).Name, temp.GetType().Name), e)); + continue; + } + + try + { + functor(arg, eventData); + } + catch (Exception e) + { + Debug.LogException(e); + } + } + + var handlerCount = internalHandlers.Count; + s_HandlerListPool.Release(internalHandlers); + return handlerCount > 0; + } + + /// <summary> + /// Execute the specified event on the first game object underneath the current touch. + /// </summary> + private static readonly List<Transform> s_InternalTransformList = new List<Transform>(30); + + public static GameObject ExecuteHierarchy<T>(GameObject root, BaseEventData eventData, EventFunction<T> callbackFunction) where T : IEventSystemHandler + { + GetEventChain(root, s_InternalTransformList); + + for (var i = 0; i < s_InternalTransformList.Count; i++) + { + var transform = s_InternalTransformList[i]; + if (Execute(transform.gameObject, eventData, callbackFunction)) + return transform.gameObject; + } + return null; + } + + //c component是否匹配类型T且是否被激活 + private static bool ShouldSendToComponent<T>(Component component) where T : IEventSystemHandler + { + var valid = component is T; + if (!valid) + return false; + + var behaviour = component as Behaviour; + if (behaviour != null) + return behaviour.isActiveAndEnabled; + return true; + } + + /// <summary> + /// Get the specified object's event event. + /// </summary> + private static void GetEventList<T>(GameObject go, IList<IEventSystemHandler> results) where T : IEventSystemHandler + { + // Debug.LogWarning("GetEventList<" + typeof(T).Name + ">"); + if (results == null) + throw new ArgumentException("Results array is null", "results"); + + if (go == null || !go.activeInHierarchy) + return; + + var components = ListPool<Component>.Get(); + go.GetComponents(components); + // 遍历所有的组件,找到匹配类型T的 + for (var i = 0; i < components.Count; i++) + { + // 如果不匹配类型T,跳过这个 + if (!ShouldSendToComponent<T>(components[i])) + continue; + + // Debug.Log(string.Format("{2} found! On {0}.{1}", go, s_GetComponentsScratch[i].GetType(), typeof(T))); + results.Add(components[i] as IEventSystemHandler); + } + ListPool<Component>.Release(components); + // Debug.LogWarning("end GetEventList<" + typeof(T).Name + ">"); + } + + /// <summary> + /// Whether the specified game object will be able to handle the specified event. + /// </summary> + public static bool CanHandleEvent<T>(GameObject go) where T : IEventSystemHandler + { + var internalHandlers = s_HandlerListPool.Get(); + GetEventList<T>(go, internalHandlers); + var handlerCount = internalHandlers.Count; + s_HandlerListPool.Release(internalHandlers); + return handlerCount != 0; + } + + /// <summary> + /// Bubble the specified event on the game object, figuring out which object will actually receive the event. + /// </summary> + public static GameObject GetEventHandler<T>(GameObject root) where T : IEventSystemHandler + { + if (root == null) + return null; + + Transform t = root.transform; + while (t != null) + { + if (CanHandleEvent<T>(t.gameObject)) + return t.gameObject; + t = t.parent; + } + return null; + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/ExecuteEvents.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/ExecuteEvents.cs.meta new file mode 100644 index 0000000..6317afb --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/ExecuteEvents.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 06bc2e6f5036fa848bb09004f4ab4e54 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/MoveDirection.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/MoveDirection.cs new file mode 100644 index 0000000..4f4147c --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/MoveDirection.cs @@ -0,0 +1,11 @@ +namespace UnityEngine.EventSystems +{ + public enum MoveDirection + { + Left, + Up, + Right, + Down, + None + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/MoveDirection.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/MoveDirection.cs.meta new file mode 100644 index 0000000..ba67175 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/EventHandler/MoveDirection.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: a1de2f5af1cc8aa4aa68afe78b9c671e +timeCreated: 1602119379 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules.meta new file mode 100644 index 0000000..377e98b --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules.meta @@ -0,0 +1,10 @@ +fileFormatVersion: 2 +guid: 01c44af785d19084ba79209e04e7e3b3 +folderAsset: yes +timeCreated: 1602119280 +licenseType: Free +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInput.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInput.cs new file mode 100644 index 0000000..8d22d04 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInput.cs @@ -0,0 +1,80 @@ +namespace UnityEngine.EventSystems +{ + + //c 对UnityEngine.Input进行一次简单包装,方便调试 + // 另外如果希望自定义输入,继承这个类,并实现这些属性 + public class BaseInput : UIBehaviour + { + public virtual string compositionString + { + get { return Input.compositionString; } + } + + public virtual IMECompositionMode imeCompositionMode + { + get { return Input.imeCompositionMode; } + set { Input.imeCompositionMode = value; } + } + + public virtual Vector2 compositionCursorPos + { + get { return Input.compositionCursorPos; } + set { Input.compositionCursorPos = value; } + } + + public virtual bool mousePresent + { + get { return Input.mousePresent; } + } + + public virtual bool GetMouseButtonDown(int button) + { + return Input.GetMouseButtonDown(button); + } + + public virtual bool GetMouseButtonUp(int button) + { + return Input.GetMouseButtonUp(button); + } + + public virtual bool GetMouseButton(int button) + { + return Input.GetMouseButton(button); + } + + public virtual Vector2 mousePosition + { + get { return Input.mousePosition; } + } + + public virtual Vector2 mouseScrollDelta + { + get { return Input.mouseScrollDelta; } + } + + public virtual bool touchSupported + { + get { return Input.touchSupported; } + } + + public virtual int touchCount + { + get { return Input.touchCount; } + } + + public virtual Touch GetTouch(int index) + { + return Input.GetTouch(index); + } + + public virtual float GetAxisRaw(string axisName) + { + return Input.GetAxisRaw(axisName); + } + + public virtual bool GetButtonDown(string buttonName) + { + return Input.GetButtonDown(buttonName); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInput.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInput.cs.meta new file mode 100644 index 0000000..57a6da5 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInput.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 6b9bc579ce1ae3148add9cf327b4ff2e +timeCreated: 1602119378 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInputModule.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInputModule.cs new file mode 100644 index 0000000..afb4678 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInputModule.cs @@ -0,0 +1,238 @@ +using System; +using System.Collections.Generic; + +namespace UnityEngine.EventSystems +{ + [RequireComponent(typeof(EventSystem))] + public abstract class BaseInputModule : UIBehaviour + { + [NonSerialized] + protected List<RaycastResult> m_RaycastResultCache = new List<RaycastResult>(); + + private AxisEventData m_AxisEventData; + + private EventSystem m_EventSystem; + private BaseEventData m_BaseEventData; + +#region 输入系统 + // 如果m_InputOverride不为空就用它,否则用默认的m_DefaultInput + // 如果要自己实现BaseInput,继承此类并给这个字段赋值 + // StandaloneInputModule没有自定义,直接采用的是BaseInput + protected BaseInput m_InputOverride; + private BaseInput m_DefaultInput; + public BaseInput input + { + get + { + if (m_InputOverride != null) + return m_InputOverride; + + if (m_DefaultInput == null) + { + var inputs = GetComponents<BaseInput>(); + foreach (var baseInput in inputs) + { + // We dont want to use any classes that derrive from BaseInput for default. + if (baseInput != null && baseInput.GetType() == typeof(BaseInput)) + { + m_DefaultInput = baseInput; + break; + } + } + + if (m_DefaultInput == null) + m_DefaultInput = gameObject.AddComponent<BaseInput>(); + } + return m_DefaultInput; + } + } +#endregion + + protected EventSystem eventSystem + { + get { return m_EventSystem; } + } + + protected override void OnEnable() + { + base.OnEnable(); + if(input != null)
+ {
+ } + m_EventSystem = GetComponent<EventSystem>(); + m_EventSystem.UpdateModules(); // 把此input module加入EventSystem + } + + protected override void OnDisable() + { + m_EventSystem.UpdateModules();// 把此input module移出EventSystem + base.OnDisable(); + } + + public abstract void Process(); + + protected static RaycastResult FindFirstRaycast(List<RaycastResult> candidates) + { + for (var i = 0; i < candidates.Count; ++i) + { + if (candidates[i].gameObject == null) + continue; + + return candidates[i]; + } + return new RaycastResult(); + } + + protected static MoveDirection DetermineMoveDirection(float x, float y) + { + return DetermineMoveDirection(x, y, 0.6f); + } + + protected static MoveDirection DetermineMoveDirection(float x, float y, float deadZone) + { + // if vector is too small... just return + if (new Vector2(x, y).sqrMagnitude < deadZone * deadZone) + return MoveDirection.None; + + if (Mathf.Abs(x) > Mathf.Abs(y)) + { + if (x > 0) + return MoveDirection.Right; + return MoveDirection.Left; + } + else + { + if (y > 0) + return MoveDirection.Up; + return MoveDirection.Down; + } + } + + protected static GameObject FindCommonRoot(GameObject g1, GameObject g2) + { + if (g1 == null || g2 == null) + return null; + + var t1 = g1.transform; + while (t1 != null) + { + var t2 = g2.transform; + while (t2 != null) + { + if (t1 == t2) + return t1.gameObject; + t2 = t2.parent; + } + t1 = t1.parent; + } + return null; + } + + // walk up the tree till a common root between the last entered and the current entered is foung + // send exit events up to (but not inluding) the common root. Then send enter events up to + // (but not including the common root). + protected void HandlePointerExitAndEnter(PointerEventData currentPointerData, GameObject newEnterTarget) + { + // if we have no target / pointerEnter has been deleted + // just send exit events to anything we are tracking + // then exit + if (newEnterTarget == null || currentPointerData.pointerEnter == null) + { + for (var i = 0; i < currentPointerData.hovered.Count; ++i) + ExecuteEvents.Execute(currentPointerData.hovered[i], currentPointerData, ExecuteEvents.pointerExitHandler); + + currentPointerData.hovered.Clear(); + + if (newEnterTarget == null) + { + currentPointerData.pointerEnter = newEnterTarget; + return; + } + } + + // if we have not changed hover target + if (currentPointerData.pointerEnter == newEnterTarget && newEnterTarget) + return; + + GameObject commonRoot = FindCommonRoot(currentPointerData.pointerEnter, newEnterTarget); + + // and we already an entered object from last time + if (currentPointerData.pointerEnter != null) + { + // send exit handler call to all elements in the chain + // until we reach the new target, or null! + Transform t = currentPointerData.pointerEnter.transform; + + while (t != null) + { + // if we reach the common root break out! + if (commonRoot != null && commonRoot.transform == t) + break; + + ExecuteEvents.Execute(t.gameObject, currentPointerData, ExecuteEvents.pointerExitHandler); + currentPointerData.hovered.Remove(t.gameObject); + t = t.parent; + } + } + + // now issue the enter call up to but not including the common root + currentPointerData.pointerEnter = newEnterTarget; + if (newEnterTarget != null) + { + Transform t = newEnterTarget.transform; + + while (t != null && t.gameObject != commonRoot) + { + ExecuteEvents.Execute(t.gameObject, currentPointerData, ExecuteEvents.pointerEnterHandler); + currentPointerData.hovered.Add(t.gameObject); + t = t.parent; + } + } + } + + protected virtual AxisEventData GetAxisEventData(float x, float y, float moveDeadZone) + { + if (m_AxisEventData == null) + m_AxisEventData = new AxisEventData(eventSystem); + + m_AxisEventData.Reset(); + m_AxisEventData.moveVector = new Vector2(x, y); + m_AxisEventData.moveDir = DetermineMoveDirection(x, y, moveDeadZone); + return m_AxisEventData; + } + + protected virtual BaseEventData GetBaseEventData() + { + if (m_BaseEventData == null) + m_BaseEventData = new BaseEventData(eventSystem); + + m_BaseEventData.Reset(); + return m_BaseEventData; + } + + public virtual bool IsPointerOverGameObject(int pointerId) + { + return false; + } + + public virtual bool ShouldActivateModule() + { + return enabled && gameObject.activeInHierarchy; + } + + public virtual void DeactivateModule() + {} + + public virtual void ActivateModule() + {} + + // 模块更新入口,在这里里面调用Input检测事件 + public virtual void UpdateModule() + {} + + public virtual bool IsModuleSupported() + { + return true; + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInputModule.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInputModule.cs.meta new file mode 100644 index 0000000..5108b8b --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/BaseInputModule.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 87c800b13211f034e90e29ad88dd2d60 +timeCreated: 1602119379 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/PointerInputModule.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/PointerInputModule.cs new file mode 100644 index 0000000..3aa8e09 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/PointerInputModule.cs @@ -0,0 +1,342 @@ +using System.Collections.Generic; +using System.Text; +using UnityEngine.UI; + +namespace UnityEngine.EventSystems +{ + + // 会处理触屏和鼠标 + public abstract class PointerInputModule : BaseInputModule + { + public const int kMouseLeftId = -1; + public const int kMouseRightId = -2; + public const int kMouseMiddleId = -3; + + public const int kFakeTouchesId = -4; + + // 一个池子 + protected Dictionary<int, PointerEventData> m_PointerData = new Dictionary<int, PointerEventData>(); + + protected bool GetPointerData(int id, out PointerEventData data, bool create) + { + if (!m_PointerData.TryGetValue(id, out data) && create) // 一个池子 + { + data = new PointerEventData(eventSystem) + { + pointerId = id, + }; + m_PointerData.Add(id, data); + return true; + } + return false; + } + + protected void RemovePointerData(PointerEventData data) + { + m_PointerData.Remove(data.pointerId); + } + + //c 根据touch数据得到pointEventData,并且保存raycaster结果 + protected PointerEventData GetTouchPointerEventData(Touch input, out bool pressed, out bool released) + { + PointerEventData pointerData; + // 从池子里拿到存储结构,返回是否是新建结构 + var created = GetPointerData(input.fingerId, out pointerData, true); + + pointerData.Reset(); + + // pressed和released用来判断抬起或者放下 + + pressed = created || (input.phase == TouchPhase.Began); // 如果结构是新建的或input phase是bagan,说明是刚按下 + released = (input.phase == TouchPhase.Canceled) || (input.phase == TouchPhase.Ended); // 如果phase是这两种,说明是抬起来了 + + if (created)//如果是新建的,记录下起始位置,否则还保留旧值,下面用来计算delta + pointerData.position = input.position; + + if (pressed)//如果是刚按下,delta置为0 + pointerData.delta = Vector2.zero; + else + pointerData.delta = input.position - pointerData.position; // 计算delta + + pointerData.position = input.position; // 计算完delta后覆盖 + + pointerData.button = PointerEventData.InputButton.Left; // 这里不知道为什么 + + // 用这个触摸数据做射线检测,检测结果在m_RaycastResultCache + eventSystem.RaycastAll(pointerData, m_RaycastResultCache); + + // 只取第一个,舍弃其他的 + var raycast = FindFirstRaycast(m_RaycastResultCache); + Debug.Log("raycast: " + raycast.index); + pointerData.pointerCurrentRaycast = raycast; + m_RaycastResultCache.Clear(); + return pointerData; + } + + protected void CopyFromTo(PointerEventData @from, PointerEventData @to) + { + @to.position = @from.position; + @to.delta = @from.delta; + @to.scrollDelta = @from.scrollDelta; + @to.pointerCurrentRaycast = @from.pointerCurrentRaycast; + @to.pointerEnter = @from.pointerEnter; + } + + protected PointerEventData.FramePressState StateForMouseButton(int buttonId) + { + var pressed = input.GetMouseButtonDown(buttonId); + var released = input.GetMouseButtonUp(buttonId); + if (pressed && released) + return PointerEventData.FramePressState.PressedAndReleased; + if (pressed) + return PointerEventData.FramePressState.Pressed; + if (released) + return PointerEventData.FramePressState.Released; + return PointerEventData.FramePressState.NotChanged; + } + + protected class ButtonState + { + private PointerEventData.InputButton m_Button = PointerEventData.InputButton.Left; + + public MouseButtonEventData eventData + { + get { return m_EventData; } + set { m_EventData = value; } + } + + public PointerEventData.InputButton button + { + get { return m_Button; } + set { m_Button = value; } + } + + private MouseButtonEventData m_EventData; + } + + protected class MouseState + { + private List<ButtonState> m_TrackedButtons = new List<ButtonState>(); + + public bool AnyPressesThisFrame() + { + for (int i = 0; i < m_TrackedButtons.Count; i++) + { + if (m_TrackedButtons[i].eventData.PressedThisFrame()) + return true; + } + return false; + } + + public bool AnyReleasesThisFrame() + { + for (int i = 0; i < m_TrackedButtons.Count; i++) + { + if (m_TrackedButtons[i].eventData.ReleasedThisFrame()) + return true; + } + return false; + } + + public ButtonState GetButtonState(PointerEventData.InputButton button) + { + ButtonState tracked = null; + for (int i = 0; i < m_TrackedButtons.Count; i++) + { + if (m_TrackedButtons[i].button == button) + { + tracked = m_TrackedButtons[i]; + break; + } + } + + if (tracked == null) + { + tracked = new ButtonState { button = button, eventData = new MouseButtonEventData() }; + m_TrackedButtons.Add(tracked); + } + return tracked; + } + + public void SetButtonState(PointerEventData.InputButton button, PointerEventData.FramePressState stateForMouseButton, PointerEventData data) + { + var toModify = GetButtonState(button); + toModify.eventData.buttonState = stateForMouseButton; + toModify.eventData.buttonData = data; + } + } + + public class MouseButtonEventData + { + public PointerEventData.FramePressState buttonState; + public PointerEventData buttonData; + + public bool PressedThisFrame() + { + return buttonState == PointerEventData.FramePressState.Pressed || buttonState == PointerEventData.FramePressState.PressedAndReleased; + } + + public bool ReleasedThisFrame() + { + return buttonState == PointerEventData.FramePressState.Released || buttonState == PointerEventData.FramePressState.PressedAndReleased; + } + } + + private readonly MouseState m_MouseState = new MouseState(); + + protected virtual MouseState GetMousePointerEventData() + { + return GetMousePointerEventData(0); + } + + protected virtual MouseState GetMousePointerEventData(int id) + { + // Populate the left button... + PointerEventData leftData; + var created = GetPointerData(kMouseLeftId, out leftData, true); + + leftData.Reset(); + + if (created) + leftData.position = input.mousePosition; + + Vector2 pos = input.mousePosition; + if (Cursor.lockState == CursorLockMode.Locked) + { + // We don't want to do ANY cursor-based interaction when the mouse is locked + leftData.position = new Vector2(-1.0f, -1.0f); + leftData.delta = Vector2.zero; + } + else + { + leftData.delta = pos - leftData.position; + leftData.position = pos; + } + leftData.scrollDelta = input.mouseScrollDelta; + leftData.button = PointerEventData.InputButton.Left; + eventSystem.RaycastAll(leftData, m_RaycastResultCache); + + // 只要第一个raycast结果 + var raycast = FindFirstRaycast(m_RaycastResultCache); + leftData.pointerCurrentRaycast = raycast; + m_RaycastResultCache.Clear(); + + // copy the apropriate data into right and middle slots + PointerEventData rightData; + GetPointerData(kMouseRightId, out rightData, true); + CopyFromTo(leftData, rightData); + rightData.button = PointerEventData.InputButton.Right; + + PointerEventData middleData; + GetPointerData(kMouseMiddleId, out middleData, true); + CopyFromTo(leftData, middleData); + middleData.button = PointerEventData.InputButton.Middle; + + // 设置按键状态 + m_MouseState.SetButtonState(PointerEventData.InputButton.Left, StateForMouseButton(0), leftData); + m_MouseState.SetButtonState(PointerEventData.InputButton.Right, StateForMouseButton(1), rightData); + m_MouseState.SetButtonState(PointerEventData.InputButton.Middle, StateForMouseButton(2), middleData); + + return m_MouseState; + } + + protected PointerEventData GetLastPointerEventData(int id) + { + PointerEventData data; + GetPointerData(id, out data, false); + return data; + } + + private static bool ShouldStartDrag(Vector2 pressPos, Vector2 currentPos, float threshold, bool useDragThreshold) + { + if (!useDragThreshold) + return true; + + return (pressPos - currentPos).sqrMagnitude >= threshold * threshold; + } + + protected virtual void ProcessMove(PointerEventData pointerEvent) + { + var targetGO = (Cursor.lockState == CursorLockMode.Locked ? null : pointerEvent.pointerCurrentRaycast.gameObject); + HandlePointerExitAndEnter(pointerEvent, targetGO); + } + + // 发送drag事件 + protected virtual void ProcessDrag(PointerEventData pointerEvent) + { + if (!pointerEvent.IsPointerMoving() || + Cursor.lockState == CursorLockMode.Locked || + pointerEvent.pointerDrag == null) + return; + + if (!pointerEvent.dragging + && ShouldStartDrag(pointerEvent.pressPosition, pointerEvent.position, eventSystem.pixelDragThreshold, pointerEvent.useDragThreshold)) + { + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.beginDragHandler); + pointerEvent.dragging = true; + } + + // Drag notification + if (pointerEvent.dragging) + { + // Before doing drag we should cancel any pointer down state + // And clear selection! + if (pointerEvent.pointerPress != pointerEvent.pointerDrag) + { + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerUpHandler); + + pointerEvent.eligibleForClick = false; + pointerEvent.pointerPress = null; + pointerEvent.rawPointerPress = null; + } + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.dragHandler); + } + } + + public override bool IsPointerOverGameObject(int pointerId) + { + var lastPointer = GetLastPointerEventData(pointerId); + if (lastPointer != null) + return lastPointer.pointerEnter != null; + return false; + } + + protected void ClearSelection() + { + var baseEventData = GetBaseEventData(); + + foreach (var pointer in m_PointerData.Values) + { + // clear all selection + HandlePointerExitAndEnter(pointer, null); + } + + m_PointerData.Clear(); + eventSystem.SetSelectedGameObject(null, baseEventData); + } + + public override string ToString() + { + var sb = new StringBuilder("<b>Pointer Input Module of type: </b>" + GetType()); + sb.AppendLine(); + foreach (var pointer in m_PointerData) + { + if (pointer.Value == null) + continue; + sb.AppendLine("<B>Pointer:</b> " + pointer.Key); + sb.AppendLine(pointer.Value.ToString()); + } + return sb.ToString(); + } + + protected void DeselectIfSelectionChanged(GameObject currentOverGo, BaseEventData pointerEvent) + { + // Selection tracking + var selectHandlerGO = ExecuteEvents.GetEventHandler<ISelectHandler>(currentOverGo); + // if we have clicked something new, deselect the old thing + // leave 'selection handling' up to the press event though. + if (selectHandlerGO != eventSystem.currentSelectedGameObject) + eventSystem.SetSelectedGameObject(null, pointerEvent); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/PointerInputModule.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/PointerInputModule.cs.meta new file mode 100644 index 0000000..e4f85e9 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/PointerInputModule.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: ca2a80b2630ad814e85c9b5d17e69cbf +timeCreated: 1602119380 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/StandaloneInputModule.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/StandaloneInputModule.cs new file mode 100644 index 0000000..592ea4d --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/StandaloneInputModule.cs @@ -0,0 +1,623 @@ +/* + * StandaloneInputModule : + * PointerInputModule : + * BaseInputModule + */ + +using System; +using UnityEngine; +using UnityEngine.Serialization; + +namespace UnityEngine.EventSystems +{ + [AddComponentMenu("Event/Standalone Input Module")] + public class StandaloneInputModule : PointerInputModule + { + private float m_PrevActionTime; + private Vector2 m_LastMoveVector; + private int m_ConsecutiveMoveCount = 0; + + // 上一个鼠标位置和当前鼠标位置,每帧更新 + private Vector2 m_LastMousePosition; + private Vector2 m_MousePosition; + + private GameObject m_CurrentFocusedGameObject; + + protected StandaloneInputModule() + { + } + + [Obsolete("Mode is no longer needed on input module as it handles both mouse and keyboard simultaneously.", false)] + public enum InputMode + { + Mouse, + Buttons + } + + [Obsolete("Mode is no longer needed on input module as it handles both mouse and keyboard simultaneously.", false)] + public InputMode inputMode + { + get { return InputMode.Mouse; } + } + + [SerializeField] + private string m_HorizontalAxis = "Horizontal"; + + /// <summary> + /// Name of the vertical axis for movement (if axis events are used). + /// </summary> + [SerializeField] + private string m_VerticalAxis = "Vertical"; + + /// <summary> + /// Name of the submit button. + /// </summary> + [SerializeField] + private string m_SubmitButton = "Submit"; + + /// <summary> + /// Name of the submit button. + /// </summary> + [SerializeField] + private string m_CancelButton = "Cancel"; + + [SerializeField] + private float m_InputActionsPerSecond = 10; + + [SerializeField] + private float m_RepeatDelay = 0.5f; + + [SerializeField] + [FormerlySerializedAs("m_AllowActivationOnMobileDevice")] + private bool m_ForceModuleActive; + + [Obsolete("allowActivationOnMobileDevice has been deprecated. Use forceModuleActive instead (UnityUpgradable) -> forceModuleActive")] + public bool allowActivationOnMobileDevice + { + get { return m_ForceModuleActive; } + set { m_ForceModuleActive = value; } + } + + public bool forceModuleActive + { + get { return m_ForceModuleActive; } + set { m_ForceModuleActive = value; } + } + + public float inputActionsPerSecond + { + get { return m_InputActionsPerSecond; } + set { m_InputActionsPerSecond = value; } + } + + public float repeatDelay + { + get { return m_RepeatDelay; } + set { m_RepeatDelay = value; } + } + + /// <summary> + /// Name of the horizontal axis for movement (if axis events are used). + /// </summary> + public string horizontalAxis + { + get { return m_HorizontalAxis; } + set { m_HorizontalAxis = value; } + } + + /// <summary> + /// Name of the vertical axis for movement (if axis events are used). + /// </summary> + public string verticalAxis + { + get { return m_VerticalAxis; } + set { m_VerticalAxis = value; } + } + + public string submitButton + { + get { return m_SubmitButton; } + set { m_SubmitButton = value; } + } + + public string cancelButton + { + get { return m_CancelButton; } + set { m_CancelButton = value; } + } + + private bool ShouldIgnoreEventsOnNoFocus() + { + switch (SystemInfo.operatingSystemFamily) + { + case OperatingSystemFamily.Windows: + case OperatingSystemFamily.Linux: + case OperatingSystemFamily.MacOSX: +#if UNITY_EDITOR + if (UnityEditor.EditorApplication.isRemoteConnected) + return false; +#endif + return true; + default: + return false; + } + }
+
+ //c! 这里只更新鼠标位置
+ public override void UpdateModule() + { + // 如果没有获取焦点,且忽略没有焦点时的事件,返回(除非开启远程连接,否则会这样) + if (!eventSystem.isFocused && ShouldIgnoreEventsOnNoFocus()) + return; + + // 更新鼠标位置 + m_LastMousePosition = m_MousePosition; + m_MousePosition = input.mousePosition; + } + + public override bool IsModuleSupported() + { + return m_ForceModuleActive || input.mousePresent || input.touchSupported; + } + + public override bool ShouldActivateModule() + { + if (!base.ShouldActivateModule()) + return false; + + var shouldActivate = m_ForceModuleActive; + shouldActivate |= input.GetButtonDown(m_SubmitButton); + shouldActivate |= input.GetButtonDown(m_CancelButton); + shouldActivate |= !Mathf.Approximately(input.GetAxisRaw(m_HorizontalAxis), 0.0f); + shouldActivate |= !Mathf.Approximately(input.GetAxisRaw(m_VerticalAxis), 0.0f); + shouldActivate |= (m_MousePosition - m_LastMousePosition).sqrMagnitude > 0.0f; + shouldActivate |= input.GetMouseButtonDown(0); + + if (input.touchCount > 0) + shouldActivate = true; + + return shouldActivate; + } + + public override void ActivateModule() + { + if (!eventSystem.isFocused && ShouldIgnoreEventsOnNoFocus()) + return; + + base.ActivateModule(); + m_MousePosition = input.mousePosition; + m_LastMousePosition = input.mousePosition; + + var toSelect = eventSystem.currentSelectedGameObject; + if (toSelect == null) + toSelect = eventSystem.firstSelectedGameObject; + + eventSystem.SetSelectedGameObject(toSelect, GetBaseEventData()); + } + + public override void DeactivateModule() + { + base.DeactivateModule(); + ClearSelection(); + } + + //c! input module事件处理主入口,每帧更新 + public override void Process() + { + // 如果没有获取焦点,不需要处理 + if (!eventSystem.isFocused && ShouldIgnoreEventsOnNoFocus()) + return; + + //event 给选中的对象发布更新事件 + bool usedEvent = SendUpdateEventToSelectedObject(); + + // 如果勾上了Send Navigation Events,发送move , submit, cancel事件 + if (eventSystem.sendNavigationEvents) + { + if (!usedEvent) + usedEvent |= SendMoveEventToSelectedObject(); //event 键盘方向键移动时给eventSystem选中的对象发布IMoveHandler事件 + + if (!usedEvent) + SendSubmitEventToSelectedObject(); //event 如果按了相应按键,发布submit或者cancel事件 + } + + // 模拟触摸或鼠标输入 + // touch needs to take precedence because of the mouse emulation layer + usedEvent = ProcessTouchEvents(); //event 检测屏幕触摸,PC上没有 + + if(!usedEvent && input.mousePresent) + ProcessMouseEvent(); // 处理鼠标事件 + } + + //c 触摸事件 + private bool ProcessTouchEvents() + { + for (int i = 0; i < input.touchCount; ++i) //多点触控 + { + Debug.Log("Touch"); + + Touch touch = input.GetTouch(i); + + if (touch.type == TouchType.Indirect) + continue; + + bool released; // 这是一个手指抬起操作 + bool pressed; // 这是一个手指放下操作 + // + PointerEventData pointer = GetTouchPointerEventData(touch, out pressed, out released); // 射线检测并保存检测结果 + + // 处理触摸或抬起反馈,已经准备好了被触摸的物体 + ProcessTouchPress(pointer, pressed, released); + + if (!released) + { + ProcessMove(pointer); + ProcessDrag(pointer); + } + else + RemovePointerData(pointer); + } + return input.touchCount > 0; + } + + //c 处理触摸\抬起 + protected void ProcessTouchPress(PointerEventData pointerEvent, bool pressed, bool released) + { + var currentOverGo = pointerEvent.pointerCurrentRaycast.gameObject; + + // 触摸反馈 + // PointerDown notification + if (pressed) + { + pointerEvent.eligibleForClick = true; + pointerEvent.delta = Vector2.zero; + pointerEvent.dragging = false; + pointerEvent.useDragThreshold = true; + pointerEvent.pressPosition = pointerEvent.position; + pointerEvent.pointerPressRaycast = pointerEvent.pointerCurrentRaycast; + + DeselectIfSelectionChanged(currentOverGo, pointerEvent); + + if (pointerEvent.pointerEnter != currentOverGo) + { + // send a pointer enter to the touched element if it isn't the one to select... + HandlePointerExitAndEnter(pointerEvent, currentOverGo); + pointerEvent.pointerEnter = currentOverGo; + } + + //event IPointerDownHandler + // search for the control that will receive the press + // if we can't find a press handler set the press + // handler to be what would receive a click. + var newPressed = ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerEvent, ExecuteEvents.pointerDownHandler); + + // didnt find a press handler... search for a click handler + if (newPressed == null) + newPressed = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo); + + // Debug.Log("Pressed: " + newPressed); + + float time = Time.unscaledTime; + + if (newPressed == pointerEvent.lastPress) + { + var diffTime = time - pointerEvent.clickTime; + if (diffTime < 0.3f) + ++pointerEvent.clickCount; + else + pointerEvent.clickCount = 1; + + pointerEvent.clickTime = time; + } + else + { + pointerEvent.clickCount = 1; + } + + pointerEvent.pointerPress = newPressed; + pointerEvent.rawPointerPress = currentOverGo; + + pointerEvent.clickTime = time; + + // Save the drag handler as well + pointerEvent.pointerDrag = ExecuteEvents.GetEventHandler<IDragHandler>(currentOverGo); + + if (pointerEvent.pointerDrag != null) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.initializePotentialDrag); + } + + // 抬起反馈 + // PointerUp notification + if (released) + { + // Debug.Log("Executing pressup on: " + pointer.pointerPress); + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerUpHandler); + + // Debug.Log("KeyCode: " + pointer.eventData.keyCode); + + // see if we mouse up on the same element that we clicked on... + var pointerUpHandler = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo); // 从这个对象开始往上找,直到一个挂了继承了IPointerClickHandler的组件 + + // PointerClick and Drop events + if (pointerEvent.pointerPress == pointerUpHandler && pointerEvent.eligibleForClick) //只有在pointerPress == pointerUpHandler时才会触发click事件 + { + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerClickHandler); + } + else if (pointerEvent.pointerDrag != null && pointerEvent.dragging) // 如果两者不相等,触发drop事件 + { + ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerEvent, ExecuteEvents.dropHandler); + } + + pointerEvent.eligibleForClick = false; + pointerEvent.pointerPress = null; + pointerEvent.rawPointerPress = null; + + if (pointerEvent.pointerDrag != null && pointerEvent.dragging) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.endDragHandler); + + pointerEvent.dragging = false; + pointerEvent.pointerDrag = null; + + // send exit events as we need to simulate this on touch up on touch device + ExecuteEvents.ExecuteHierarchy(pointerEvent.pointerEnter, pointerEvent, ExecuteEvents.pointerExitHandler); + pointerEvent.pointerEnter = null; + } + } + + /// <summary> + /// Process submit keys. + /// </summary> + protected bool SendSubmitEventToSelectedObject() + { + if (eventSystem.currentSelectedGameObject == null) + return false; + + // 发布submit事件或者cancel事件 + + var data = GetBaseEventData(); + if (input.GetButtonDown(m_SubmitButton)) // 这里是Project>Input里面配置的 + ExecuteEvents.Execute(eventSystem.currentSelectedGameObject, data, ExecuteEvents.submitHandler); + + if (input.GetButtonDown(m_CancelButton)) + ExecuteEvents.Execute(eventSystem.currentSelectedGameObject, data, ExecuteEvents.cancelHandler); + return data.used; + } + + private Vector2 GetRawMoveVector() + { + Vector2 move = Vector2.zero; + move.x = input.GetAxisRaw(m_HorizontalAxis); + move.y = input.GetAxisRaw(m_VerticalAxis); + + if (input.GetButtonDown(m_HorizontalAxis)) + { + if (move.x < 0) + move.x = -1f; + if (move.x > 0) + move.x = 1f; + } + if (input.GetButtonDown(m_VerticalAxis)) + { + if (move.y < 0) + move.y = -1f; + if (move.y > 0) + move.y = 1f; + } + return move; + } + + /// <summary> + /// Process keyboard events. + /// </summary> + protected bool SendMoveEventToSelectedObject() + { + float time = Time.unscaledTime; + + Vector2 movement = GetRawMoveVector(); + if (Mathf.Approximately(movement.x, 0f) && Mathf.Approximately(movement.y, 0f)) // 如果键盘方向键没动,返回 + { + m_ConsecutiveMoveCount = 0; + return false; + } + + //allow即是否允许发布事件 + // If user pressed key again, always allow event + bool allow = input.GetButtonDown(m_HorizontalAxis) || input.GetButtonDown(m_VerticalAxis); + bool similarDir = (Vector2.Dot(movement, m_LastMoveVector) > 0); // 和之前的方向是否夹角在90°以内,如果是的话说明很接近 + if (!allow) + { + // Otherwise, user held down key or axis. + // If direction didn't change at least 90 degrees, wait for delay before allowing consequtive event. + if (similarDir && m_ConsecutiveMoveCount == 1) + allow = (time > m_PrevActionTime + m_RepeatDelay); + // If direction changed at least 90 degree, or we already had the delay, repeat at repeat rate. + else + allow = (time > m_PrevActionTime + 1f / m_InputActionsPerSecond); + } + if (!allow) + return false; + + // 发布IMoveHandler事件 + + // Debug.Log(m_ProcessingEvent.rawType + " axis:" + m_AllowAxisEvents + " value:" + "(" + x + "," + y + ")"); + var axisEventData = GetAxisEventData(movement.x, movement.y, 0.6f); + + if (axisEventData.moveDir != MoveDirection.None) + { + ExecuteEvents.Execute(eventSystem.currentSelectedGameObject, axisEventData, ExecuteEvents.moveHandler); // IMoveHandler.OnMove + if (!similarDir) + m_ConsecutiveMoveCount = 0; + m_ConsecutiveMoveCount++; + + m_PrevActionTime = time; + m_LastMoveVector = movement; + } + else + { + m_ConsecutiveMoveCount = 0; + } + + return axisEventData.used; + } + + protected void ProcessMouseEvent() + { + ProcessMouseEvent(0); + } + + [Obsolete("This method is no longer checked, overriding it with return true does nothing!")] + protected virtual bool ForceAutoSelect() + { + return false; + } + + /// <summary> + /// Process all mouse events. + /// </summary> + protected void ProcessMouseEvent(int id) + { + var mouseData = GetMousePointerEventData(id); + var leftButtonData = mouseData.GetButtonState(PointerEventData.InputButton.Left).eventData; + + m_CurrentFocusedGameObject = leftButtonData.buttonData.pointerCurrentRaycast.gameObject; + + // Process the first mouse button fully + ProcessMousePress(leftButtonData); + ProcessMove(leftButtonData.buttonData); + ProcessDrag(leftButtonData.buttonData); + + // Now process right / middle clicks + ProcessMousePress(mouseData.GetButtonState(PointerEventData.InputButton.Right).eventData); + ProcessDrag(mouseData.GetButtonState(PointerEventData.InputButton.Right).eventData.buttonData); + ProcessMousePress(mouseData.GetButtonState(PointerEventData.InputButton.Middle).eventData); + ProcessDrag(mouseData.GetButtonState(PointerEventData.InputButton.Middle).eventData.buttonData); + + if (!Mathf.Approximately(leftButtonData.buttonData.scrollDelta.sqrMagnitude, 0.0f)) + { + var scrollHandler = ExecuteEvents.GetEventHandler<IScrollHandler>(leftButtonData.buttonData.pointerCurrentRaycast.gameObject); + ExecuteEvents.ExecuteHierarchy(scrollHandler, leftButtonData.buttonData, ExecuteEvents.scrollHandler); + } + } + + // 每帧发送一个OnUpdateSelected事件 + protected bool SendUpdateEventToSelectedObject() + { + if (eventSystem.currentSelectedGameObject == null) + return false; + + var data = GetBaseEventData(); + //event 向eventSystem当前选中的gameobject发布一个更新事件IUpdateSelectedHandler,比如inputfield + ExecuteEvents.Execute(eventSystem.currentSelectedGameObject, data, ExecuteEvents.updateSelectedHandler); + return data.used; + } + + // 处理鼠标按下事件,发送消息,调用回调 + /// <summary> + /// Process the current mouse press. + /// </summary> + protected void ProcessMousePress(MouseButtonEventData data) + { + var pointerEvent = data.buttonData; + var currentOverGo = pointerEvent.pointerCurrentRaycast.gameObject; + + // PointerDown notification + if (data.PressedThisFrame()) + { + pointerEvent.eligibleForClick = true; + pointerEvent.delta = Vector2.zero; + pointerEvent.dragging = false; + pointerEvent.useDragThreshold = true; + pointerEvent.pressPosition = pointerEvent.position; + pointerEvent.pointerPressRaycast = pointerEvent.pointerCurrentRaycast; + + DeselectIfSelectionChanged(currentOverGo, pointerEvent); + + // search for the control that will receive the press + // if we can't find a press handler set the press + // handler to be what would receive a click. + var newPressed = ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerEvent, ExecuteEvents.pointerDownHandler); + + // didnt find a press handler... search for a click handler + if (newPressed == null) + newPressed = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo); + + // Debug.Log("Pressed: " + newPressed); + + float time = Time.unscaledTime; + + if (newPressed == pointerEvent.lastPress) + { + var diffTime = time - pointerEvent.clickTime; + if (diffTime < 0.3f) + ++pointerEvent.clickCount; + else + pointerEvent.clickCount = 1; + + pointerEvent.clickTime = time; + } + else + { + pointerEvent.clickCount = 1; + } + + pointerEvent.pointerPress = newPressed; + pointerEvent.rawPointerPress = currentOverGo; + + pointerEvent.clickTime = time; + + // Save the drag handler as well + pointerEvent.pointerDrag = ExecuteEvents.GetEventHandler<IDragHandler>(currentOverGo); + + if (pointerEvent.pointerDrag != null) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.initializePotentialDrag); + } + + // PointerUp notification + if (data.ReleasedThisFrame()) + { + // Debug.Log("Executing pressup on: " + pointer.pointerPress); + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerUpHandler); + + // Debug.Log("KeyCode: " + pointer.eventData.keyCode); + + // see if we mouse up on the same element that we clicked on... + var pointerUpHandler = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo); + + // PointerClick and Drop events + if (pointerEvent.pointerPress == pointerUpHandler && pointerEvent.eligibleForClick) + { + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerClickHandler); + } + else if (pointerEvent.pointerDrag != null && pointerEvent.dragging) + { + ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerEvent, ExecuteEvents.dropHandler); + } + + pointerEvent.eligibleForClick = false; + pointerEvent.pointerPress = null; + pointerEvent.rawPointerPress = null; + + if (pointerEvent.pointerDrag != null && pointerEvent.dragging) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.endDragHandler); + + pointerEvent.dragging = false; + pointerEvent.pointerDrag = null; + + // redo pointer enter / exit to refresh state + // so that if we moused over somethign that ignored it before + // due to having pressed on something else + // it now gets it. + if (currentOverGo != pointerEvent.pointerEnter) + { + HandlePointerExitAndEnter(pointerEvent, null); + HandlePointerExitAndEnter(pointerEvent, currentOverGo); + } + } + } + + protected GameObject GetCurrentFocusedGameObject() + { + return m_CurrentFocusedGameObject; + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/StandaloneInputModule.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/StandaloneInputModule.cs.meta new file mode 100644 index 0000000..dde31b7 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/StandaloneInputModule.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: e2665fa6a1fb2474d8a5c19f72f8d0c6 +timeCreated: 1602119380 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/TouchInputModule.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/TouchInputModule.cs new file mode 100644 index 0000000..58ac97c --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/TouchInputModule.cs @@ -0,0 +1,263 @@ +using System; +using System.Text; +using UnityEngine.Serialization; + +namespace UnityEngine.EventSystems +{ + //c TouchInputModule被废弃了,统一在standaloneInputModule中处理 + [Obsolete("TouchInputModule is no longer required as Touch input is now handled in StandaloneInputModule.")] + [AddComponentMenu("Event/Touch Input Module")] + public class TouchInputModule : PointerInputModule + { + protected TouchInputModule() + {} + + // 触摸点位置 + private Vector2 m_LastMousePosition; + private Vector2 m_MousePosition; + + [SerializeField] + [FormerlySerializedAs("m_AllowActivationOnStandalone")] + private bool m_ForceModuleActive; + + [Obsolete("allowActivationOnStandalone has been deprecated. Use forceModuleActive instead (UnityUpgradable) -> forceModuleActive")] + public bool allowActivationOnStandalone + { + get { return m_ForceModuleActive; } + set { m_ForceModuleActive = value; } + } + + public bool forceModuleActive + { + get { return m_ForceModuleActive; } + set { m_ForceModuleActive = value; } + } + + //c 更新鼠标(触摸点)位置 + public override void UpdateModule() + { + m_LastMousePosition = m_MousePosition; + m_MousePosition = input.mousePosition; + } + + public override bool IsModuleSupported() + { + return forceModuleActive || input.touchSupported; + } + + public override bool ShouldActivateModule() + { + if (!base.ShouldActivateModule()) + return false; + + if (m_ForceModuleActive) + return true; + + if (UseFakeInput()) + { + bool wantsEnable = input.GetMouseButtonDown(0); + + wantsEnable |= (m_MousePosition - m_LastMousePosition).sqrMagnitude > 0.0f; + return wantsEnable; + } + + if (input.touchCount > 0) + return true; + + return false; + } + + private bool UseFakeInput() + { + return !input.touchSupported; + } + + public override void Process() + { + if (UseFakeInput()) + FakeTouches(); + else + ProcessTouchEvents(); + } + + /// <summary> + /// For debugging touch-based devices using the mouse. + /// </summary> + private void FakeTouches() + { + var pointerData = GetMousePointerEventData(0); + + var leftPressData = pointerData.GetButtonState(PointerEventData.InputButton.Left).eventData; + + // fake touches... on press clear delta + if (leftPressData.PressedThisFrame()) + leftPressData.buttonData.delta = Vector2.zero; + + ProcessTouchPress(leftPressData.buttonData, leftPressData.PressedThisFrame(), leftPressData.ReleasedThisFrame()); + + // only process move if we are pressed... + if (input.GetMouseButton(0)) + { + ProcessMove(leftPressData.buttonData); + ProcessDrag(leftPressData.buttonData); + } + } + + /// <summary> + /// Process all touch events. + /// </summary> + private void ProcessTouchEvents() + { + for (int i = 0; i < input.touchCount; ++i) + { + Touch touch = input.GetTouch(i); + + if (touch.type == TouchType.Indirect) + continue; + + bool released; + bool pressed; + var pointer = GetTouchPointerEventData(touch, out pressed, out released); + + ProcessTouchPress(pointer, pressed, released); + + if (!released) + { + ProcessMove(pointer); + ProcessDrag(pointer); + } + else + RemovePointerData(pointer); + } + } + + protected void ProcessTouchPress(PointerEventData pointerEvent, bool pressed, bool released) + { + var currentOverGo = pointerEvent.pointerCurrentRaycast.gameObject; + + // PointerDown notification + if (pressed) + { + pointerEvent.eligibleForClick = true; + pointerEvent.delta = Vector2.zero; + pointerEvent.dragging = false; + pointerEvent.useDragThreshold = true; + pointerEvent.pressPosition = pointerEvent.position; + pointerEvent.pointerPressRaycast = pointerEvent.pointerCurrentRaycast; + + DeselectIfSelectionChanged(currentOverGo, pointerEvent); + + if (pointerEvent.pointerEnter != currentOverGo) + { + // send a pointer enter to the touched element if it isn't the one to select... + HandlePointerExitAndEnter(pointerEvent, currentOverGo); + pointerEvent.pointerEnter = currentOverGo; + } + + // search for the control that will receive the press + // if we can't find a press handler set the press + // handler to be what would receive a click. + var newPressed = ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerEvent, ExecuteEvents.pointerDownHandler); + + // didnt find a press handler... search for a click handler + if (newPressed == null) + newPressed = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo); + + // Debug.Log("Pressed: " + newPressed); + + float time = Time.unscaledTime; + + if (newPressed == pointerEvent.lastPress) + { + var diffTime = time - pointerEvent.clickTime; + if (diffTime < 0.3f) + ++pointerEvent.clickCount; + else + pointerEvent.clickCount = 1; + + pointerEvent.clickTime = time; + } + else + { + pointerEvent.clickCount = 1; + } + + pointerEvent.pointerPress = newPressed; + pointerEvent.rawPointerPress = currentOverGo; + + pointerEvent.clickTime = time; + + // Save the drag handler as well + pointerEvent.pointerDrag = ExecuteEvents.GetEventHandler<IDragHandler>(currentOverGo); + + if (pointerEvent.pointerDrag != null) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.initializePotentialDrag); + } + + // PointerUp notification + if (released) + { + // Debug.Log("Executing pressup on: " + pointer.pointerPress); + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerUpHandler); + + // Debug.Log("KeyCode: " + pointer.eventData.keyCode); + + // see if we mouse up on the same element that we clicked on... + var pointerUpHandler = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo); + + // PointerClick and Drop events + if (pointerEvent.pointerPress == pointerUpHandler && pointerEvent.eligibleForClick) + { + ExecuteEvents.Execute(pointerEvent.pointerPress, pointerEvent, ExecuteEvents.pointerClickHandler); + } + else if (pointerEvent.pointerDrag != null && pointerEvent.dragging) + { + ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerEvent, ExecuteEvents.dropHandler); + } + + pointerEvent.eligibleForClick = false; + pointerEvent.pointerPress = null; + pointerEvent.rawPointerPress = null; + + if (pointerEvent.pointerDrag != null && pointerEvent.dragging) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.endDragHandler); + + pointerEvent.dragging = false; + pointerEvent.pointerDrag = null; + + if (pointerEvent.pointerDrag != null) + ExecuteEvents.Execute(pointerEvent.pointerDrag, pointerEvent, ExecuteEvents.endDragHandler); + + pointerEvent.pointerDrag = null; + + // send exit events as we need to simulate this on touch up on touch device + ExecuteEvents.ExecuteHierarchy(pointerEvent.pointerEnter, pointerEvent, ExecuteEvents.pointerExitHandler); + pointerEvent.pointerEnter = null; + } + } + + public override void DeactivateModule() + { + base.DeactivateModule(); + ClearSelection(); + } + + public override string ToString() + { + var sb = new StringBuilder(); + sb.AppendLine(UseFakeInput() ? "Input: Faked" : "Input: Touch"); + if (UseFakeInput()) + { + var pointerData = GetLastPointerEventData(kMouseLeftId); + if (pointerData != null) + sb.AppendLine(pointerData.ToString()); + } + else + { + foreach (var pointerEventData in m_PointerData) + sb.AppendLine(pointerEventData.ToString()); + } + return sb.ToString(); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/TouchInputModule.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/TouchInputModule.cs.meta new file mode 100644 index 0000000..facfc33 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/InputModules/TouchInputModule.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 27cc0457fb3bcbe4eb6038275fbdde36 +timeCreated: 1602119378 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters.meta new file mode 100644 index 0000000..104ea1f --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters.meta @@ -0,0 +1,10 @@ +fileFormatVersion: 2 +guid: c57aabd138e5b164ebd06107a0c19483 +folderAsset: yes +timeCreated: 1602119280 +licenseType: Free +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/BaseRaycaster.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/BaseRaycaster.cs new file mode 100644 index 0000000..d58c358 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/BaseRaycaster.cs @@ -0,0 +1,48 @@ +using System; +using System.Collections.Generic; + +namespace UnityEngine.EventSystems +{ + public abstract class BaseRaycaster : UIBehaviour + { + public abstract void Raycast(PointerEventData eventData, List<RaycastResult> resultAppendList); + public abstract Camera eventCamera { get; } + + [Obsolete("Please use sortOrderPriority and renderOrderPriority", false)] + public virtual int priority + { + get { return 0; } + } + + public virtual int sortOrderPriority + { + get { return int.MinValue; } + } + + public virtual int renderOrderPriority + { + get { return int.MinValue; } + } + + public override string ToString() + { + return "Name: " + gameObject + "\n" + + "eventCamera: " + eventCamera + "\n" + + "sortOrderPriority: " + sortOrderPriority + "\n" + + "renderOrderPriority: " + renderOrderPriority; + } + + // 只要是继承了BaseRaycaster的都会自动加到raycaster的列表里面 + protected override void OnEnable() + { + base.OnEnable(); + RaycasterManager.AddRaycaster(this); + } + + protected override void OnDisable() + { + RaycasterManager.RemoveRaycasters(this); + base.OnDisable(); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/BaseRaycaster.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/BaseRaycaster.cs.meta new file mode 100644 index 0000000..eb8b89a --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/BaseRaycaster.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 89c5c6ccaa917c94a864388cc962e706 +timeCreated: 1602119379 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/Physics2DRaycaster.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/Physics2DRaycaster.cs new file mode 100644 index 0000000..6346938 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/Physics2DRaycaster.cs @@ -0,0 +1,54 @@ +using System.Collections.Generic; +using UnityEngine.UI; + +namespace UnityEngine.EventSystems +{ + /// <summary> + /// Simple event system using physics raycasts. + /// </summary> + [AddComponentMenu("Event/Physics 2D Raycaster")] + [RequireComponent(typeof(Camera))] + public class Physics2DRaycaster : PhysicsRaycaster + { + protected Physics2DRaycaster() + {} + + // 发射线 + public override void Raycast(PointerEventData eventData, List<RaycastResult> resultAppendList) + { + if (eventCamera == null) + return; + + Ray ray; + float distanceToClipPlane; + ComputeRayAndDistance(eventData, out ray, out distanceToClipPlane); + + if (ReflectionMethodsCache.Singleton.getRayIntersectionAll == null) + return; + + var hits = ReflectionMethodsCache.Singleton.getRayIntersectionAll(ray, distanceToClipPlane, finalEventMask); + + if (hits.Length != 0) + { + for (int b = 0, bmax = hits.Length; b < bmax; ++b) + { + var sr = hits[b].collider.gameObject.GetComponent<SpriteRenderer>(); + + var result = new RaycastResult + { + gameObject = hits[b].collider.gameObject, + module = this, + distance = Vector3.Distance(eventCamera.transform.position, hits[b].point), + worldPosition = hits[b].point, + worldNormal = hits[b].normal, + screenPosition = eventData.position, + index = resultAppendList.Count, + sortingLayer = sr != null ? sr.sortingLayerID : 0, + sortingOrder = sr != null ? sr.sortingOrder : 0 + }; + resultAppendList.Add(result); + } + } + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/Physics2DRaycaster.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/Physics2DRaycaster.cs.meta new file mode 100644 index 0000000..828be37 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/Physics2DRaycaster.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: 055a0cdd9d5d3e0489f854f7bdf22ded +timeCreated: 1602119377 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/PhysicsRaycaster.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/PhysicsRaycaster.cs new file mode 100644 index 0000000..c7d431c --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/PhysicsRaycaster.cs @@ -0,0 +1,117 @@ +using System.Collections.Generic; +using UnityEngine.UI; + +namespace UnityEngine.EventSystems +{ + //c 投射3D物体的相机挂这个脚本 + + /// <summary> + /// Simple event system using physics raycasts. + /// </summary> + [AddComponentMenu("Event/Physics Raycaster")] + [RequireComponent(typeof(Camera))] + public class PhysicsRaycaster : BaseRaycaster + { + /// <summary> + /// Const to use for clarity when no event mask is set + /// </summary> + protected const int kNoEventMaskSet = -1; + + protected Camera m_EventCamera; + + /// <summary> + /// Layer mask used to filter events. Always combined with the camera's culling mask if a camera is used. + /// </summary> + [SerializeField] + protected LayerMask m_EventMask = kNoEventMaskSet; + + protected PhysicsRaycaster() + {} + + public override Camera eventCamera + { + get + { + if (m_EventCamera == null) + m_EventCamera = GetComponent<Camera>(); + return m_EventCamera ?? Camera.main; + } + } + + + /// <summary> + /// Depth used to determine the order of event processing. + /// </summary> + public virtual int depth + { + get { return (eventCamera != null) ? (int)eventCamera.depth : 0xFFFFFF; } + } + + /// <summary> + /// Event mask used to determine which objects will receive events. + /// </summary> + public int finalEventMask + { + get { return (eventCamera != null) ? eventCamera.cullingMask & m_EventMask : kNoEventMaskSet; } + } + + /// <summary> + /// Layer mask used to filter events. Always combined with the camera's culling mask if a camera is used. + /// </summary> + public LayerMask eventMask + { + get { return m_EventMask; } + set { m_EventMask = value; } + } + + protected void ComputeRayAndDistance(PointerEventData eventData, out Ray ray, out float distanceToClipPlane) + { + ray = eventCamera.ScreenPointToRay(eventData.position); + // compensate far plane distance - see MouseEvents.cs + float projectionDirection = ray.direction.z; // ray.direction是归一化了的 + distanceToClipPlane = Mathf.Approximately(0.0f, projectionDirection) + ? Mathf.Infinity + : Mathf.Abs((eventCamera.farClipPlane - eventCamera.nearClipPlane) / projectionDirection); + } + + public override void Raycast(PointerEventData eventData, List<RaycastResult> resultAppendList) + { + // Cull ray casts that are outside of the view rect. (case 636595) + if (eventCamera == null || !eventCamera.pixelRect.Contains(eventData.position)) + return; + + // 根据触摸数据拿到射线 + Ray ray; + float distanceToClipPlane; + ComputeRayAndDistance(eventData, out ray, out distanceToClipPlane); + + if (ReflectionMethodsCache.Singleton.raycast3DAll == null) + return; + + var hits = ReflectionMethodsCache.Singleton.raycast3DAll(ray, distanceToClipPlane, finalEventMask); + + if (hits.Length > 1) + System.Array.Sort(hits, (r1, r2) => r1.distance.CompareTo(r2.distance)); + + if (hits.Length != 0) + { + for (int b = 0, bmax = hits.Length; b < bmax; ++b) + { + var result = new RaycastResult + { + gameObject = hits[b].collider.gameObject, + module = this, + distance = hits[b].distance, + worldPosition = hits[b].point, + worldNormal = hits[b].normal, + screenPosition = eventData.position, + index = resultAppendList.Count, + sortingLayer = 0, + sortingOrder = 0 + }; + resultAppendList.Add(result); + } + } + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/PhysicsRaycaster.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/PhysicsRaycaster.cs.meta new file mode 100644 index 0000000..848c302 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/PhysicsRaycaster.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: b2bb18305a46ea44686ad8cdffbb3a58 +timeCreated: 1602119379 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycastResult.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycastResult.cs new file mode 100644 index 0000000..666ef8d --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycastResult.cs @@ -0,0 +1,65 @@ +namespace UnityEngine.EventSystems +{ + // UGUI射线检测结果 + public struct RaycastResult + { + private GameObject m_GameObject; // Game object hit by the raycast + + public GameObject gameObject + { + get { return m_GameObject; } + set { m_GameObject = value; } + } + + public BaseRaycaster module; // Event system that hit this object + public float distance; // The distance from the origin this hit was. + public float index; // The index this element is in the raycastList (used for sorting) + public int depth; + public int sortingLayer; + public int sortingOrder; + // World-space position where a ray cast into the screen hits something + public Vector3 worldPosition; + // World-space normal where a ray cast into the screen hits something + public Vector3 worldNormal; + + public Vector2 screenPosition; + + public bool isValid + { + get { return module != null && gameObject != null; } + } + + public void Clear() + { + gameObject = null; + module = null; + distance = 0; + index = 0; + depth = 0; + sortingLayer = 0; + sortingOrder = 0; + worldNormal = Vector3.up; + worldPosition = Vector3.zero; + screenPosition = Vector2.zero; + } + + public override string ToString() + { + if (!isValid) + return ""; + + return "Name: " + gameObject + "\n" + + "module: " + module + "\n" + + "distance: " + distance + "\n" + + "index: " + index + "\n" + + "depth: " + depth + "\n" + + "worldNormal: " + worldNormal + "\n" + + "worldPosition: " + worldPosition + "\n" + + "screenPosition: " + screenPosition + "\n" + + "module.sortOrderPriority: " + module.sortOrderPriority + "\n" + + "module.renderOrderPriority: " + module.renderOrderPriority + "\n" + + "sortingLayer: " + sortingLayer + "\n" + + "sortingOrder: " + sortingOrder; + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycastResult.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycastResult.cs.meta new file mode 100644 index 0000000..c2d01ba --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycastResult.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 5f5a2c96e65809c43ad8a958f062ef1f +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycasterManager.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycasterManager.cs new file mode 100644 index 0000000..c3480b4 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycasterManager.cs @@ -0,0 +1,29 @@ +using System.Collections.Generic; + +namespace UnityEngine.EventSystems +{ + internal static class RaycasterManager + { + private static readonly List<BaseRaycaster> s_Raycasters = new List<BaseRaycaster>(); + + public static void AddRaycaster(BaseRaycaster baseRaycaster) + { + if (s_Raycasters.Contains(baseRaycaster)) + return; + + s_Raycasters.Add(baseRaycaster); + } + + public static List<BaseRaycaster> GetRaycasters() + { + return s_Raycasters; + } + + public static void RemoveRaycasters(BaseRaycaster baseRaycaster) + { + if (!s_Raycasters.Contains(baseRaycaster)) + return; + s_Raycasters.Remove(baseRaycaster); + } + } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycasterManager.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycasterManager.cs.meta new file mode 100644 index 0000000..594b8d2 --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/Raycasters/RaycasterManager.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 5c12b7bf7a4800945ba532802a36b165 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/UIBehaviour.cs b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/UIBehaviour.cs new file mode 100644 index 0000000..fa24cff --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/UIBehaviour.cs @@ -0,0 +1,77 @@ +namespace UnityEngine.EventSystems +{ + public abstract class UIBehaviour : MonoBehaviour + {
+#region MonoBehaviour共有生命周期 +
+ protected virtual void Awake() + {} + + protected virtual void OnEnable() + {} + + protected virtual void Start() + {} + + protected virtual void OnDisable() + {} + + protected virtual void OnDestroy() + {}
+
+ // 父节点(包括非直接父节点的祖先节点)在hierachy中的父子层级改变前调用
+ protected virtual void OnBeforeTransformParentChanged() + { } + + // 父节点(包括非直接父节点的祖先节点)在hierachy中的父子层级改变完调用 + protected virtual void OnTransformParentChanged() + { }
+
+#endregion +
+ public virtual bool IsActive() + { + return isActiveAndEnabled; + } + +#if UNITY_EDITOR + // 组件值在inspector中被修改时调用 + protected virtual void OnValidate() + {} + + // inspector中右键reset调用 + protected virtual void Reset() + {}
+#endif +
+#region UGUI特有回调函数 +
+ // 当gRectTransform大小改变(不包括位置)的时候回调。且如果子物体由于锚点的设置也会导致
+ // 大小改变时也会调用子物体的这个回调。如果子物体大小不会因此改变,那么不会触发这个回调
+ protected virtual void OnRectTransformDimensionsChange() + {} + + // 用animation clip修此脚本属性值的时候触发。可以用于修正动画结果 + protected virtual void OnDidApplyAnimationProperties() + {} + + // 祖先节点CanvasGroup参数变化或enable\disable或canvasGroup下面的canvas的层级变化 + protected virtual void OnCanvasGroupChanged() + {} + + // 祖先节点Canvas enable\disable或OverrideSorting状态改变 + protected virtual void OnCanvasHierarchyChanged() + {}
+
+#endregion +
+ public bool IsDestroyed() + { + // Workaround for Unity native side of the object + // having been destroyed but accessing via interface + // won't call the overloaded == + return this == null; + }
+
+ } +} diff --git a/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/UIBehaviour.cs.meta b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/UIBehaviour.cs.meta new file mode 100644 index 0000000..8a8845a --- /dev/null +++ b/Assets/uGUI-2017.1/UnityEngine.UI/EventSystem/UIBehaviour.cs.meta @@ -0,0 +1,13 @@ +fileFormatVersion: 2 +guid: c17b5e621296cc74ca0fdc04a3cb30d0 +timeCreated: 1602119380 +licenseType: Free +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: |