SOAP란 유니티의 Scriptable Object를 이용한 Scriptable Objects Architecture Pattern을 의미한다.
유니티의 ScriptableObject는 변경되지 않는 데이터를 담는 컨테이너로 자주 쓰이지만, SOAP는 이 SriptableObject(이하 SO)를 다양한 방식으로 활용한다.
객체 간 통신을 위한 이벤트 채널로 활용하기도, 객체의 행동 로직을 정의하기도 하고 심지어 런타임에 변경되는 데이터들도 SO로 변경하여 활용하기도 한다.
컴포지트 패턴을 활용해 게임을 개발하도록 설계된 유니티에서 컴포넌트 간의 직접 연결을 줄이고 런타임에 하나의 데이터만 있도록 보장된 SO를 활용해 간접적으로 통신할 수 있다.
유니티 에디터 상에서 직접 생성과 변경이 가능해 재사용성이 높고 직관적이다.
SO는 프로젝트 자산으로 존재하기 때문에 씬 레벨에 종속되지 않고 데이터 공유가 가능하다.
SO는 런타임 중 변경된 값이 그대로 변경에 적용되고 이를 수정하기가 까다롭다.
이벤트 추적이 힘들고 수많은 구조가 커질수록 수많은 SO와 관련 스크립트를 생성해야하기 때문에 더욱 복잡해질 수 있다.
개인적으로는 SO에 변경되는 데이터 값이나 행동 로직을 담는 것이 위험할 수 있다는 것에 동의하지만 싱글톤이나 서비스 로케이터같은 런타임 중 특정 객체에 전역적인 접근을 위한 패턴이 가지는 종속성 문제의 대안으로는 나쁘지 않아 보인다.
다음은 SO를 활용한 오브젝트 풀의 구현이다.
public abstract class ObjectPoolConfig<T> : ScriptableObject where T : Component
{
[SerializeField] protected GameObject prefab;
[SerializeField] protected int initialSize;
[SerializeField] protected int maxSize;
[SerializeField] protected bool collectionCheck = false;
private static Dictionary<ObjectPoolConfig<T>, ObjectPoolEntity<T>> poolCache = new();
public virtual ObjectPoolEntity<T> GetPool()
{
if (!poolCache.TryGetValue(this, out var value))
{
value = new ObjectPoolEntity<T>(prefab, initialSize, maxSize, collectionCheck);
poolCache.Add(this, value);
}
return value;
}
}
위 클래스는 풀링할 객체와 풀의 정보를 담는 데이터 컨테이너 SO를 정의하는 클래스이다.
해당 클래스를 제네릭 타입의 를 지정해 구현함으로써 SO화 시킬 수 있다.
이 클래스는 전역 Dictionary를 선언하고 이 SO의 GetPool()함수를 불렀을 때 풀이 있다면 풀을 리턴, 없다면 생성해서 Dictionary에 추가해준다.
public class ObjectPoolEntity<T> where T : Component
{
private readonly GameObject prefab;
private readonly int initialSize;
private readonly int maxSize;
private bool collectionCheck;
private ObjectPool<T> objectPool;
public T Get() => objectPool.Get();
}
실제 생성이 되는 ObjectPool 클래스이다.
SO의 데이터를 바탕으로 생성되고 SO와 관련된 참조는 없어 SO에 강한 의존성을 가지지 않는다.

풀링할 프리펩과 풀의 정보를 가진 SO에셋을 생성한다.
ObjectPoolEntity의 T형식을 다르게 지정해 줌으로써, 구현만 한다면 다른 컴포넌트들도 참조를 리턴할 수 있다.

풀을 사용할 객체에 변수를 선언해주고 인스펙터에서 SO에셋을 끌어 가져온다.

SO가 리턴한 GetPool()에 접근해서 오브젝트 풀링 기능을 사용할 수 있다.
아니 순찌,,,,,나 진짜 감격 그 자체가 되어버렸어,,,,!!!!
얼마나 많이 성장한거야!!! 이렇게 잘 할 수 있으면서 왜 그동안,,,
어쨌든 오늘 TIL 작성하느라 수고 많았엉 오늘 휼륭하다. 200점!!