Version: Unity 6.0 (6000.0)
언어 : 한국어
커스텀 컨트롤로 이벤트에 응답
이벤트 합성 및 전송

매니퓰레이터

UI 코드에서 이벤트 로직을 분리하려면 매니퓰레이터를 사용하여 이벤트를 처리합니다. 매니퓰레이터는__ UI__(사용자 인터페이스) 사용자가 애플리케이션과 상호 작용하도록 해 줍니다. Unity는 현재 3개의 UI 시스템을 지원합니다. 자세한 정보
See in Glossary
요소와의 사용자 상호 작용을 처리하는 상태 머신입니다. 매니퓰레이터는 이벤트 콜백을 저장, 등록, 등록 취소합니다. 해당 사용자 상호 작용 설정을 간소화하므로 각 콜백을 하나씩 처리할 필요가 없습니다. 이벤트를 처리하려면 UI 툴킷이 지원하는 매니퓰레이터 중 하나를 사용하거나 상속합니다.

매니퓰레이터를 생성하고 사용하려면 다음을 수행합니다.

  1. UI 툴킷이 지원하는 매니퓰레이터 클래스에서 상속하는 전용 클래스를 정의합니다. 이 클래스는 관리하려는 특정 사용자 상호 작용에 맞게 구성된 이벤트 처리 로직을 캡슐화합니다.
  2. 클래스 내에서 마우스 클릭 또는 드래그와 같은 관련 상호 작용에 반응하는 메서드를 구현합니다. 이러한 메서드는 원하는 동작을 실행하는 데 필요한 정보를 캡처하고 처리합니다.
  3. 매니퓰레이터 클래스 설계를 마치면 이를 인스턴스화하고 타겟 UI 요소에 연결합니다. 이 연결을 통해 매니퓰레이터가 특정 이벤트를 인터셉트하고 관리하여 UI 코드와 명확한 분리 상태를 유지하면서 사용자 상호 작용을 오케스트레이션할 수 있습니다.

지원되는 매니퓰레이터

다음 표에는 지원되는 매니퓰레이터 클래스가 나열되어 있습니다.

매니퓰레이터 다음에서 상속 설명
Manipulator 제공된 모든 매니퓰레이터의 기본 클래스입니다.
KeyboardNavigationManipulator Manipulator 기기별 입력 이벤트를 키보드를 사용하여 상위 레벨의 탐색 작업으로 변환합니다.
MouseManipulator Manipulator 마우스 입력을 처리합니다. 활성화 필터 리스트가 있습니다.
ContextualMenuManipulator MouseManipulator 사용자가 오른쪽 클릭하거나 키보드의 메뉴 키를 누르면 컨텍스트 메뉴가 표시됩니다.
PointerManipulator MouseManipulator 포인터 입력을 처리합니다. 활성화 필터 리스트가 있습니다.
Clickable PointerManipulator 요소의 마우스 이벤트를 추적하고 동일한 요소에서 포인터를 눌렀다 놓는 클릭이 발생하는 시점을 식별합니다.

예제

다음 예시는 매니퓰레이터를 사용하여 이벤트를 처리하는 방법을 보여 줍니다. 매니퓰레이터는 다음을 수행합니다.

  • 마우스 입력을 처리하는 PointerManipulators 클래스에서 매니퓰레이터를 상속합니다.
  • activators 리스트를 사용하여 매니퓰레이터를 활성화하는 조건을 지정합니다. 예를 들어 사용자가 왼쪽 클릭할 때 매니퓰레이터를 활성화하려면 button 필드가 MouseButton.LeftMouse로 설정된 activators 리스트에 ManipulatorActivationFilter를 추가합니다.
  • target 프로퍼티를 사용하여 매니퓰레이터가 연결된 요소에 액세스합니다.
  • 이벤트 콜백을 등록하거나 등록 취소하려면 RegisterCallbacksOnTargetUnregisterCallbacksFromTarget 메서드를 오버라이드합니다.

ExampleDragger 매니퓰레이터 생성

다음 예시에서는 클릭하고 드래그할 때 요소를 움직이는 매니퓰레이터를 생성합니다.

using UnityEngine;
using UnityEngine.UIElements;

public class ExampleDragger : PointerManipulator
{
    private Vector3 m_Start;
    protected bool m_Active;
    private int m_PointerId;
    private Vector2 m_StartSize;

    public ExampleDragger()
    {
        m_PointerId = -1;
        activators.Add(new ManipulatorActivationFilter { button = MouseButton.LeftMouse });
        m_Active = false;
    }

    protected override void RegisterCallbacksOnTarget()
    {
        target.RegisterCallback<PointerDownEvent>(OnPointerDown);
        target.RegisterCallback<PointerMoveEvent>(OnPointerMove);
        target.RegisterCallback<PointerUpEvent>(OnPointerUp);
    }

    protected override void UnregisterCallbacksFromTarget()
    {
        target.UnregisterCallback<PointerDownEvent>(OnPointerDown);
        target.UnregisterCallback<PointerMoveEvent>(OnPointerMove);
        target.UnregisterCallback<PointerUpEvent>(OnPointerUp);
    }

    protected void OnPointerDown(PointerDownEvent e)
    {
        if (m_Active)
        {
            e.StopImmediatePropagation();
            return;
        }

        if (CanStartManipulation(e))
        {
            m_Start = e.localPosition;
            m_PointerId = e.pointerId;

            m_Active = true;
            target.CapturePointer(m_PointerId);
            e.StopPropagation();
        }
    }

    protected void OnPointerMove(PointerMoveEvent e)
    {
        if (!m_Active || !target.HasPointerCapture(m_PointerId))
            return;

        Vector2 diff = e.localPosition - m_Start;

        target.style.top = target.layout.y + diff.y;
        target.style.left = target.layout.x + diff.x;

        e.StopPropagation();
    }

    protected void OnPointerUp(PointerUpEvent e)
    {
        if (!m_Active || !target.HasPointerCapture(m_PointerId) || !CanStopManipulation(e))
            return;

        m_Active = false;
        target.ReleaseMouse();
        e.StopPropagation();
    }
}

ExampleResizer 매니퓰레이터 생성

다음 예시에서는 요소를 드래그할 때 요소의 크기를 조절하는 매니퓰레이터를 생성합니다.

using UnityEngine;
using UnityEngine.UIElements;

public class ExampleResizer : PointerManipulator
{
    private Vector3 m_Start;
    protected bool m_Active;
    private int m_PointerId;
    private Vector2 m_StartSize;
    public ExampleResizer()
    {
        m_PointerId = -1;
        activators.Add(new ManipulatorActivationFilter { button = MouseButton.LeftMouse });
        m_Active = false;
    }

    protected override void RegisterCallbacksOnTarget()
    {
        target.RegisterCallback<PointerDownEvent>(OnPointerDown);
        target.RegisterCallback<PointerMoveEvent>(OnPointerMove);
        target.RegisterCallback<PointerUpEvent>(OnPointerUp);
    }

    protected override void UnregisterCallbacksFromTarget()
    {
        target.UnregisterCallback<PointerDownEvent>(OnPointerDown);
        target.UnregisterCallback<PointerMoveEvent>(OnPointerMove);
        target.UnregisterCallback<PointerUpEvent>(OnPointerUp);
    }

    protected void OnPointerDown(PointerDownEvent e)
    {
        if (m_Active)
        {
            e.StopImmediatePropagation();
            return;
        }

        if (CanStartManipulation(e))
        {
            m_Start = e.localPosition;
            m_StartSize = target.layout.size;
            m_PointerId = e.pointerId;
            m_Active = true;
            target.CapturePointer(m_PointerId);
            e.StopPropagation();
        }
    }

    protected void OnPointerMove(PointerMoveEvent e)
    {
        if (!m_Active || !target.HasPointerCapture(m_PointerId))
            return;

        Vector2 diff = e.localPosition - m_Start;

        target.style.height = m_StartSize.y + diff.y;
        target.style.width = m_StartSize.x + diff.x;

        e.StopPropagation();
    }

    protected void OnPointerUp(PointerUpEvent e)
    {
        if (!m_Active || !target.HasPointerCapture(m_PointerId) || !CanStopManipulation(e))
            return;

        m_Active = false;
        target.ReleasePointer(m_PointerId);
        m_PointerId = -1;
        e.StopPropagation();
    }
}

매니퓰레이터 추가 또는 제거

요소에 매니퓰레이터를 추가하려면 AddManipulator 메서드를 사용합니다. 요소에서 매니퓰레이터를 제거하려면 RemoveManipulator 메서드를 사용합니다.

다음 예시에서는 VisualElementExampleDragger를 추가하고 제거합니다.

// Create a VisualElement.
var myElement = new VisualElement();

// Add manipulators to the VisualElement.
myElement.AddManipulator(new ExampleDragger());

// Remove manipulators from the VisualElement.
myElement.RemoveManipulator<ExampleDragger>();

다음 예시에서는 VisualElementExampleResizer를 추가합니다.

var box = new VisualElement()
{
    style =
    {
        left = 100,
        top = 100,
        width = 100,
        height = 100,
        backgroundColor = Color.red
    },
    pickingMode = PickingMode.Position,
};

box.AddManipulator(new ExampleResizer());

추가 리소스

커스텀 컨트롤로 이벤트에 응답
이벤트 합성 및 전송