Unity & C#

C# event에서 listener들을 unsubscribe하는 법

왼손잡이개발자 2021. 10. 19. 03:33

유니티에서 제공하는 UnityEvent 클래스에서는 RemoveAllListeners()라고 하는 함수가 subsribe 되어있는 listener들을 다 unsubscribe 해주는 역할을 합니다. 그렇다면 c# 의 event에서는 subscribers 들을 어떻게 unsubscribe 할 수 있을까요?

 

 

 

C# event에서도 등록되어있는 delegate를 array로 가져올 수 있는 함수가 있습니다. 바로 GetInvocationList()입니다. subsriber들을 array로 가져올 수 있다면 쉽게 그냥 foreach 문을 돌면서 -= 로 unsubsribe 해주면 되겠죠?

 

테스트를 위해 EventSubscriber class와 Monobehaviour 를 상속받는 EventInvoker class 를 만들어줍니다. 

using UnityEngine;

public class EventSubscriber
{
    private string name;
    public string Name => name;
    public EventSubscriber(string _name)
	{
        name = _name;
	}

    public void OnEvent()
	{
        Debug.Log(Name + " is listening!");
	}
}

EventSubsriber class에서는 이벤트가 발생되면 호출될 OnEvent() method만 만들어주었습니다.

 

 

 

using UnityEngine;


public class EventInvoker : MonoBehaviour
{
    public delegate void MyEventHandler();
    public static event MyEventHandler myEvent;

	private void OnEnable()
	{
		for(int i=0; i< 5;i++)
		{
			EventSubscriber eventSubscriber = new EventSubscriber(string.Format("No.{0} Subsriber", i));

			myEvent += eventSubscriber.OnEvent;
		}
	}

	private void OnDisable()
	{
		int i = 0;
		foreach(MyEventHandler listener in myEvent.GetInvocationList())
		{
			myEvent -= listener;
			print(i++ + "th Subsriber is UnSubsribed");
		}
	}

	private void Update()
	{
		if(Input.GetMouseButtonDown(0))
		{
			myEvent?.Invoke(); //subscribe 잘 됐는지 확인용
		}
	}
}

OnEnable() 에 보시면 EventSubsriver 를 for loop를 돌면서 5개를 생성하고 myEvent에 subscribe 해 주었습니다. 잘 subscribe 되었는지 확인 할 수 있게 Update()에서 마우스를 클릭했을 때 잘 호출 되는지 확인 할 수 있습니다. 

그리고 오늘의 주제인 event 에서 unsubscribe을 할 수있는 방법이 OnDisable()에 구현 되어있습니다. OnDisable()에서 myEvent.GetInvocationList()를 foreach를 돌면서 각 listener들을 받아와서 myEvent에서 -= 해주면 됩니다.