using System; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.UI; namespace UVC.UI { /// /// Unity의 기본 Slider 컴포넌트를 확장하여 드래그 시작, 드래그 중, 드래그 종료 및 클릭 이벤트를 제공하는 클래스입니다. /// 이를 통해 슬라이더 상호작용에 대한 더 세밀한 제어가 가능합니다. /// [ExecuteAlways] [RequireComponent(typeof(RectTransform))] public class SliderWithEvent : Slider, IEndDragHandler { private bool isDragging = false; /// /// 슬라이더가 현재 드래그 중인지 여부를 나타냅니다. /// public bool IsDragging { get => isDragging; } private Vector2 downPosition = Vector2.zero; /// /// 슬라이더를 클릭했을 때 호출될 액션입니다. /// 드래그가 아닌, 포인터를 눌렀다 뗄 때 위치가 동일한 경우에만 발생합니다. /// public Action OnClickAction { get; set; } /// /// 슬라이더를 드래그하는 동안 계속해서 호출될 액션입니다. /// public Action OnDragAction { get; set; } /// /// 슬라이더 드래그를 마쳤을 때 호출될 액션입니다. /// public Action OnEndDragAction { get; set; } /// /// 슬라이더를 드래그할 때 호출되는 Unity 이벤트 메서드입니다. /// IsDragging 상태를 true로 설정하고 OnDragAction을 호출합니다. /// /// 포인터 이벤트 데이터입니다. public override void OnDrag(PointerEventData eventData) { if (!MayDrag(eventData)) return; base.OnDrag(eventData); isDragging = true; if (OnDragAction != null) OnDragAction.Invoke(); } /// /// 슬라이더 드래그를 마쳤을 때 호출되는 IEndDragHandler 인터페이스의 메서드입니다. /// IsDragging 상태를 false로 설정하고 OnEndDragAction을 호출합니다. /// /// 포인터 이벤트 데이터입니다. public void OnEndDrag(PointerEventData eventData) { isDragging = false; if (OnEndDragAction != null) OnEndDragAction.Invoke(); } /// /// 슬라이더 위에서 포인터를 눌렀을 때 호출되는 Unity 이벤트 메서드입니다. /// 클릭 판정을 위해 시작 위치를 저장합니다. /// /// 포인터 이벤트 데이터입니다. public override void OnPointerDown(PointerEventData eventData) { if (!MayDrag(eventData)) return; base.OnPointerDown(eventData); downPosition = eventData.position; } /// /// 슬라이더 위에서 포인터를 뗄 때 호출되는 Unity 이벤트 메서드입니다. /// 포인터를 누른 위치와 뗀 위치가 같으면 클릭으로 간주하고 OnClickAction을 호출합니다. /// /// 포인터 이벤트 데이터입니다. public override void OnPointerUp(PointerEventData eventData) { base.OnPointerUp(eventData); if (downPosition == eventData.position) { if (OnClickAction != null) OnClickAction.Invoke(); } } /// /// 드래그가 가능한 상태인지 확인합니다. (활성화, 상호작용 가능, 왼쪽 마우스 버튼) /// /// 포인터 이벤트 데이터입니다. /// 드래그 가능 여부를 반환합니다. private bool MayDrag(PointerEventData eventData) { return IsActive() && IsInteractable() && eventData.button == PointerEventData.InputButton.Left; } } }