• 카테고리

    질문 & 답변
  • 세부 분야

    게임 프로그래밍

  • 해결 여부

    미해결

UI_Popup을 상속받은 개체가 IPointerDownHandler, IPointerUpHandler를 기능을 사용하려면 어떻게 해야할까요?

22.02.21 19:00 작성 조회수 247

1

안녕하세요,

선생님의 강의를 참고하여 클리커 프로젝트를 제작중인데, 난관에 부딛혀서 질문을 드립니다 ㅜㅜ

  1. 일반적인 클리커 게임들처럼 길게 터치를 해서 업그레이드 하는 기능을 구현하고 싶었습니다.
  2. UI_Popup을 상속받은 Canvas 개체의 Button 을 통해 BindEvent를 해주었고, 클릭 이벤트를 통해 캐릭터의 능력을 업그레이드 하는 기능은 구현 되었습니다. 

여기서부터 문젠데... 

일단 UI_Base에 작성되어 있는 내용으로는, Click과 Drag만 구현되어 있길래 패기롭게 Up과 Down을 자체적으로 구현해보고자 했는데요... 장렬하게 실패했습니다... 

별의별 삽질을 다해보다가 UI_Popup을 상속받은 Canvas 개체에다가 IPointerDownHandler와 Uphandler을 다시 상속을 시켜서 인터페이스를 구현해보고 별의별 바보짓을 다해봤는데 얘들은 아예 터치다운과 업이 받아와지지도 않았습니다 ㅜ

UI_Base를 수정하자니 갑자기 탈트가 오는데 아래 람다식을 통해 필요한 기능을 써야되는건가 했는데 어떤식으로 외부와 연결을 지어줘야 되는지 갑자기 아득해졌습니다... 하드코딩등 이것저것 삽질을 해보았지만 제 실력으론 도저히 풀리지가 않네요...

 

UI_Base 중

    public static void BindEvent(GameObject go, Action<PointerEventData> action, Define.UIEvent type = Define.UIEvent.Click)
    {
       
        UI_EventHandler evt = MyUtil.GetOrAddComponent<UI_EventHandler>(go);
        switch (type)
        {
            case Define.UIEvent.Click:
                evt.OnClickHandler -= action; 
                evt.OnClickHandler += action;

                break;

            case Define.UIEvent.Drag:
                evt.OnDragHandler -= action;
                evt.OnDragHandler += action;

                break;

            case Define.UIEvent.LongTouch:        
                evt.OnLongTouchHandler -= action;   
                evt.OnLongTouchHandler += action;

                break;

            case Define.UIEvent.LongTouchUp:
                evt.OnLongTouchUpHandler -= action;
                evt.OnLongTouchUpHandler += action;
                
                break;
        }

        evt.OnDragHandler += ((PointerEventData data) => { evt.gameObject.transform.position = data.position; });
        evt.OnLongTouchHandler += ((PointerEventData data) => { Debug.Log("롱터치 구현해야되는 부분같은데 모르겠어서 보류"); });
        evt.OnLongTouchUpHandler += ((PointerEventData data) => { Debug.Log("손떼면 어떻게 할지 구현해야되는 부분같은데 모르겠어서 보류"); });

UI_Handler  중

using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;

public class UI_EventHandler : MonoBehaviour, IPointerClickHandler, IPointerDownHandler, IPointerUpHandler/*, IDragHandler*//*, IPointerUpHandler*/
{
    public Action<PointerEventData> OnClickHandler = null;
    public Action<PointerEventData> OnDragHandler = null;
    public Action<PointerEventData> OnLongTouchHandler = null;
    public Action<PointerEventData> OnLongTouchUpHandler = null;
    public bool isTouched = false;

    private void Update()
    {
        if (isTouched)
                Debug.Log("롱터치중입니다요");
        else
            isTouched = false;
    }

    public void OnPointerClick(PointerEventData eventData)
    {
        if (OnClickHandler != null)
            OnClickHandler.Invoke(eventData);
        Debug.Log("OnPointerClick");
    }

    public void OnDrag(PointerEventData eventData)
    {
        transform.position = eventData.position;

        if (OnDragHandler != null)
            OnDragHandler.Invoke(eventData);
        Debug.Log("OnDrag");
        } 

    public void OnPointerDown(PointerEventData eventData)
    {
        if (OnLongTouchHandler != null)
            OnLongTouchHandler.Invoke(eventData);

        isTouched = true;
        Debug.Log("롱터치중이다");
    }


    public void OnPointerUp(PointerEventData eventData)
    {
        if (OnLongTouchUpHandler != null)
            OnLongTouchUpHandler.Invoke(eventData);

        isTouched = false;
        Debug.Log("롱터치에서 손뗐다");
    }
}

이부분은 언제나 어려웠어가지고... ㅜㅜ 어떻게 공부해나가면 좋을지 힌트라도 좀 얻고 싶습니다.

그럼 답변 부탁드리겠습니다. 언제나 건강 유의하시구요 좋은 강의 너무 감사합니다!

답변 1

답변을 작성해보세요.

0

롱터치라는게 누르고 있으면 계속 호출이 되는건가요,
아니면 특정 시간 (ex 2초) 누르고 있으면 한 번 호출이 되는건가요?

아무튼 구현은 굉장히 방법이 다양히 있을 수 있는데요.
OnPointerDown/Up에 필요한 bool 마킹을 해주고 Update문에서 체크해서 이벤트를 발생한다거나, 
OnPointerDown 시점에 Coroutine을 예약하고 Up하는 시점에 취소한다거나,
...

무엇을 하고 싶으신지 정확히 이해가 안 가서 답변을 확실히 드리긴 힘드네요.
Drag가 필요 없으면 IDragHandler 등은 제거하는 것도 괜찮습니다.
(Drag를 넣으면 일부 UI에서 이벤트가 먹히는 이슈 등이 살짝 있긴 합니다.)

AISH님의 프로필

AISH

질문자

2022.02.22

안녕하세요, 말씀하신것의 첫번째와 같이 누르고 있으면 계속 호출되는 기능을 생각하고 있습니다!

제가 구현하고싶었던건 [UI base 클래스]를 상속한 [UI Popup 클래스] > 이를 상속받은 [팝업 유아이 클래스]에서 IPointerDownHandler, IPointerUpHandler 인터페이스를 사용해서 프레스하는 동안 특정 함수를 호출하는 기능을 구현하고 싶었는데,

그래서 말씀주신대로 [팝업 유아이 클래스]에서 Update > bool 체크를 해보는 방식을 시도해봤었는데,

분명 UI_EventHandler에서는 PointerUp, Down 감지는 잘 되고 디버깅 메시지도 잘 오고 있는데, 자식 클래스에서는 Pointer Up Down bool 체크가 안되고있고... 여기서부터 당황해서 자식클래스에 핸들러를 따로 붙여도 보았지만 붙이든 떼든 Up Down 이벤트 전혀 먹지않고... 방향은 맞는데 제가 구현에서 실수를 한걸까요?

자식 클래스에서 pointerUp과 Down을 어떻게 활용을 해야되는지가 헷갈립니다. Drag 기능의 구현 코드를 보면 [UI base] 클래스의 람다식을 이용해야 될것같아 보였는데 이 부분에 대한 이해가 부족해서 자식한테 어떤 내용을 보내줘야 되는지가 좀 어렵더라구요... 그래서 이부분 구현에 대한 힌트를 좀 얻고싶었습니다! 장황하게 질문 드린점 죄송합니다. ㅜㅜ 답변도 감사드려요!