Unity Singleton
Unity3D/Script / 2014. 3. 24. 18:36
using UnityEngine;
public abstract class MonoSingleton<T> : MonoBehaviour where T : MonoSingleton<T>
{
protected static bool m_bDontDestroyOnLoad = true;
private static bool m_bApplicationQuit = false;
private static object InstanceLocker = new object();
private static T m_Instance = null;
public static T Instance
{
get
{
if (true == m_bApplicationQuit)
return null;
lock (InstanceLocker)
{
// Instance requiered for the first time, we look for it
if (null == m_Instance)
{
T instance = GameObject.FindObjectOfType(typeof(T)) as T;
// Object not found, we create a temporary one
if (instance == null)
{
instance = new GameObject(typeof(T).ToString()).AddComponent<T>();
// Problem during the creation, this should not happen
if (instance == null)
{
Debug.LogError("Problem during the creation of " + typeof(T).ToString());
}
}
if (instance != null)
{
Initialize(instance);
}
}
return m_Instance;
}
}
}
private static void Initialize(T instance)
{
if (m_Instance == null)
{
var startTime = System.DateTime.Now;
m_Instance = instance;
// 씬 전환 시, 삭제시킬 싱글톤은 부모 객체에 안붙이도록..
// 싱글톤 시작 시, m_bDontDestroyOnLoad 셋팅 필요.
if (true == m_bDontDestroyOnLoad)
{
GameObject goRoot = GameObject.Find("Singletons") as GameObject;
if (null == goRoot)
{
goRoot = new GameObject("Singletons");
// DontDestroyOnLoad() 등록은 하위 상속받는 쪽에서 하도록 하는 게 나을까?
DontDestroyOnLoad(goRoot);
}
m_Instance.transform.parent = goRoot.transform;
}
m_Instance.OnInitialize();
var period = System.DateTime.Now - startTime;
if (period.TotalSeconds > 1.0f)
{
var name = m_Instance.ToString();
Debug.LogWarning("Profile Warnning. Singletion {" + name + "} too long init time : "
+ period.TotalSeconds.ToString("F") + "Seconds");
}
}
else if (m_Instance != instance)
{
DestroyImmediate(instance.gameObject);
}
}
private static void Destroyed(T instance)
{
if (m_Instance == instance)
{
m_Instance.OnFinalize();
m_Instance = null;
}
}
public void CreateSingleton() { }
// [Warning] GameObject에 Component로 미리 등록된 상태에서는 OnInitialize() 호출 안됨.
public virtual void OnInitialize() { }
// [Warning] GameObject에 Component로 미리 등록된 상태에서는 OnFinalize() 호출 안됨.
public virtual void OnFinalize() { }
protected virtual void CheckDontDestroyOnLoad() { }
private void Awake()
{
Initialize(this as T);
}
void OnDestroy()
{
Destroyed(this as T);
}
private void OnApplicationQuit()
{
m_bApplicationQuit = true;
Destroyed(this as T);
}
}
반응형
'Unity3D > Script' 카테고리의 다른 글
| A simple cross fade shader for Unity (0) | 2014.04.22 |
|---|---|
| 어플을 내렸을때, 어플을 종료할때의 처리 (3) | 2014.04.04 |
| Platform Dependent Compilation (0) | 2014.03.11 |
| Generic Based Singleton for MonoBehaviours完全版(?) (0) | 2014.03.05 |
| Singleton (0) | 2014.03.05 |

