OvertakingLegend/Assets/UIFrameWork/Script/Rocker.cs

152 lines
3.9 KiB
C#

using Unity.VisualScripting;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.EventSystems;
using UnityEngine.UI;
/// <summary>
/// 移动摇杆类型
/// </summary>
public enum E_RockerType
{
/// <summary>
/// 固定
/// </summary>
Fixed,
/// <summary>
/// 跟随固定
/// </summary>
FollowFixed,
/// <summary>
/// 跟随
/// </summary>
Follow,
}
/// <summary>
/// 移动摇杆
/// </summary>
public class Rocker : MonoBehaviour, IPointerDownHandler, IPointerUpHandler, IDragHandler, IEndDragHandler
{
/// <summary>
/// 边界
/// </summary>
public float maxBoundary;
/// <summary>
/// 是否开始拖拽
/// </summary>
private bool isDrag;
/// <summary>
/// 摇杆底图
/// </summary>
public Image rockerBM;
/// <summary>
/// 事件触发区域
/// </summary>
public Image touchRect;
/// <summary>
/// 摇杆控制
/// </summary>
public Image control;
/// <summary>
/// 摇杆类型
/// </summary>
public E_RockerType e_RockerType;
/// <summary>
/// 方向监听
/// </summary>
public UnityAction<Vector2> dirListener;
/// <summary>
/// 抬起按下监听
/// </summary>
public UnityAction<bool> liftPressListener;
/// <summary>
/// 角度监听
/// </summary>
public UnityAction<float> angleListener;
public void Start()
{
rockerBM.gameObject.SetActive(e_RockerType == E_RockerType.Fixed);
}
/// <summary>
/// 是否拖拽
/// </summary>
/// <returns></returns>
public bool GetIsDrag()
{
return isDrag;
}
/// <summary>
/// 返回摇杆控制到中心点的模长
/// </summary>
/// <returns></returns>
public Vector3 GetMagnitude()
{
return control.transform.position - rockerBM.transform.position;
}
public virtual void OnDrag(PointerEventData eventData)
{
isDrag = true;
Vector2 localPos;
Vector3 vector= this.transform.position + Vector3.one * maxBoundary - control.transform.position;
RectTransformUtility.ScreenPointToLocalPointInRectangle(rockerBM.rectTransform, (eventData as PointerEventData).position, (eventData as PointerEventData).pressEventCamera, out localPos);
if (localPos.magnitude > maxBoundary)
{
if (e_RockerType == E_RockerType.Follow)
{
rockerBM.transform.localPosition += (Vector3)localPos.normalized * (localPos.magnitude - maxBoundary);
}
control.transform.localPosition = localPos.normalized * maxBoundary;
}
else
{
control.transform.localPosition = localPos;
}
dirListener?.Invoke(localPos.normalized);
float angel = Mathf.Atan2(localPos.x, localPos.y);
angleListener?.Invoke(angel * Mathf.Rad2Deg);
}
public void OnEndDrag(PointerEventData eventData)
{
isDrag = false;
control.rectTransform.anchoredPosition = Vector2.zero;
dirListener?.Invoke(Vector2.zero);
}
public void OnPointerDown(PointerEventData eventData)
{
Vector2 localPos;
liftPressListener?.Invoke(true);
rockerBM.gameObject.SetActive(true);
if (e_RockerType != E_RockerType.Fixed)
{
RectTransformUtility.ScreenPointToLocalPointInRectangle(touchRect.rectTransform, (eventData as PointerEventData).position, (eventData as PointerEventData).pressEventCamera, out localPos);
rockerBM.transform.localPosition = localPos;
}
}
public void OnPointerUp(PointerEventData eventData)
{
liftPressListener?.Invoke(false);
if (e_RockerType != E_RockerType.Fixed)
{
rockerBM.gameObject.SetActive(false);
}
}
}