using System;
using System.Collections.Generic;
using UnityEngine;
namespace Framework {
/// <summary>
/// 对象池
/// </summary>
public sealed class ObjectPool {
private const string LOG_NULL = "Construct callback is null ";
/// <summary>
/// 构造步长
/// </summary>
public ushort constructStep = 1;
/// <summary>
/// 对象构造回调
/// </summary>
private Func<object> m_OnConstruct;
/// <summary>
/// 销毁回调
/// </summary>
private Action<object> m_OnDestroy;
/// <summary>
/// 启用回调
/// </summary>
private Action<object> m_OnEnabled;
/// <summary>
/// 关闭回调
/// </summary>
private Action<object> m_OnDisabled;
/// <summary>
/// 启用链表
/// </summary>
private List<object> m_EnabledList = new List<object> ();
/// <summary>
/// 关闭池
/// </summary>
private Queue<object> m_DisabledPool = new Queue<object> ();
/// <summary>
/// 构造函数
/// </summary>
/// <param name="onContruct">对象构造回调</param>
/// <param name="onDestroy">对象销毁回调</param>
/// <param name="onEnabled"></param>
/// <param name="onDisabled"></param>
public ObjectPool (Func<object> onContruct, Action<object> onDestroy = null, Action<object> onEnabled = null, Action<object> onDisabled = null) {
if (onContruct == null) {
Debug.LogError (LOG_NULL);
}
}
/// <summary>
/// 添加对象
/// </summary>
/// <returns></returns>
private object Add () {
for (int i = 0; i < constructStep - 1; ++i) {
object obj = m_OnConstruct.Invoke ();
m_DisabledPool.Enqueue (obj);
}
return m_OnConstruct.Invoke ();
}
/// <summary>
/// 获取对象
/// </summary>
/// <returns>返回对象</returns>
public object Get () {
object obj = m_DisabledPool.Count > 0 ? m_DisabledPool.Dequeue () : Add ();
m_EnabledList.Add (obj);
if (m_OnEnabled != null) {
m_OnEnabled.Invoke (obj);
}
return obj;
}
/// <summary>
/// 获取所有对象
/// </summary>
/// <returns></returns>
public object[] GetAll () {
return m_EnabledList.ToArray ();
}
/// <summary>
/// 回收对象
/// </summary>
/// <param name="obj"></param>
public void Remove (object obj) {
if (!m_EnabledList.Contains (obj)) {
return;
}
m_EnabledList.Remove (obj);
m_DisabledPool.Enqueue (obj);
if (m_OnDisabled != null) {
m_OnDisabled.Invoke (obj);
}
}
/// <summary>
/// 清理对象
/// </summary>
/// <param name="destroy">是否销毁</param>
public void Clear (bool destroy = true) {
if (destroy) {
if (m_OnDestroy != null) {
foreach (var obj in m_EnabledList) {
m_OnDestroy.Invoke (obj);
}
while (m_DisabledPool.Count > 0) {
m_OnDestroy.Invoke (m_DisabledPool.Dequeue ());
}
}
m_EnabledList.Clear ();
m_DisabledPool.Clear ();
} else {
foreach (var obj in m_EnabledList) {
m_DisabledPool.Enqueue (obj);
if (m_OnDisabled != null) {
m_OnDisabled.Invoke (obj);
}
}
m_EnabledList.Clear ();
}
}
}
}