/ UNITY

유니티 토막 지식_07

어제는 싱글톤 패턴을 알아보았다. 오늘 알아볼 것은 옵저버 패턴이다.

옵저버 패턴

옵저버 패턴은 특정 객체의 상태가 변화하면, 해당 객체와 연결 되어있는 다른 객체들이 영향을 받도록 하는 패턴이다. 1 : N 의 의존성을 가진다.

이때, 상태 변화를 알려주는 객체를 Subject 라고 하고, 메시지를 받아 동작을 수행하는 객체를 Observer 라고 한다.

Unity_01

위 처럼 옵저버 패턴을 이용하면 옵저버들이 주체자의 상태변화를 감지하고 각각의 동작을 개별적으로 수행할 수 있다.

옵저버 패턴의 장단점
  1. 장점 : 객체간 결합도 낮추고, 응집도를 높인다. 이는 객체지향적인 면에서 큰 이점이 있다. 또한 일대다 객체간의 상호작용에서 이벤트 단위로 처리하는 상황에 유용하게 쓰인다.

  2. 단점 : 코드의 상호작용이 일어나는지 한눈에 알아보기 어려워 디버깅을 통해 확인하는 방법을 사용해야 한다.

옵저버 패턴의 특징
  1. 주체자가 옵저버 각각의 객체에 대해 정보를 가지고 있을 필요가 없다.

  2. 옵저버는 언제든지 새롭게 추가할 수 있다.

  3. 새로운 기능을 사용하는 옵저버를 추가한다 하더라도 주체자는 바뀌는 것이 없다.

  4. 주체자와 옵저버는 서로 독립적으로 재사용 가능하다.

  5. 주체자나 옵저버가 변경되더라도 서로에게 영향을 끼치지 않는다. (낮은 의존성)

옵저버 패턴의 사용

유니티, C#에서는 delegate, event를 이용해 옵저버 패턴을 구현할 수 있다. 하지만 델리게이트에 대해서 아직 잘 모르기 때문에, 기본 형식으로 옵저버 패턴을 구현해보도록 하겠다. 간단하게 오브젝트의 색깔을 바꾸는 기능을 구현해보겠다.

먼저 옵저버의 추상 클래스를 구현한다.

Observer.cs

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

public abstract class Observer : MonoBehaviour
{
    public abstract void colorChange();
}

이제 위 추상클래스를 상속받을 객체 4개를 생성하겠다.

Unity_02

구체를 4개 생성했다. 이제 각각의 구체가 위 추상클래스를 상속받아 정의되어있는 추상메서드를 재정의하여 구현할 것이다.

ChangeRed.cs

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

public class ChangeRed : Observer
{
    public override void colorChange()
    {
        GetComponent<Renderer>().material.color = Color.red;
    }

}

추상메서드를 Overriding 하여 내부를 구현하였다. 구체가 4개 있으니 각각 다른 색깔로 만들어보자.

이제 옵저버를 관리할 Subject를 만들어보자. 음, 스페이스바 버튼을 누르면 각 옵저버들에 구현되어있는 colorChange 메서드를 실행시키도록 해보자.

Subject.cs

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


public class Subject : MonoBehaviour
{
    public List<Observer> observers = new List<Observer>();


    public void observerAdd(Observer obs)
    {
        observers.Add(obs);
    }

    public void observerRemove(Observer obs)
    {
        if (observers.IndexOf(obs) > 0)
        {
            observers.Remove(obs);
        }
    }

    public void Notify()
    {
        foreach (Observer obs in observers)
        {
            obs.colorChange();
        }
    }

    void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            Notify();
        }
    }
}

Unity_03

위 스크립트를 빈 오브젝트를 생성해 이름은 Subject으로 바꿔주고 컴포넌트에 추가해주었다. Observer를 Public로 설정해두었기 때문에 위처럼 엘리멘트 추가가 가능하다. 변경한 김에 구의 이름도 바꿔주었다.

Unity_04

각 옵저버에 만들었던 스크립트들을 색깔별로 4개 구 게임오브젝트에 각각 집어넣어 주었다.

Unity_05

스크립트를 컴포넌트로 추가한 구 게임 오브젝트를 드래그앤 드롭하여 Subject 오브젝트의 Observer 목록에 추가시킨다.

Unity_06

SpaceBar 키를 누름과 동시에 각 구체들의 colorChange 메서드가 실행되는 화면이다.

C#에서 제공하는 delegate와 event를 사용하는 방법은 다음에 실습해보도록 하자.