PoolManager.cs 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
  1. using System.Collections;
  2. using System.Collections.Generic;
  3. using UnityEngine;
  4. using UnityEngine.Events;
  5. public class PoolManager : MonoBehaviour
  6. {
  7. public static PoolManager instance;
  8. public Dictionary<GameObject, List<GameObject>> pools;
  9. public Dictionary<GameObject, List<GameObject>> activeObjs;
  10. void Awake()
  11. {
  12. if (instance)
  13. {
  14. Destroy(gameObject);
  15. return;
  16. }
  17. instance = this;
  18. pools = new Dictionary<GameObject, List<GameObject>>();
  19. activeObjs = new Dictionary<GameObject, List<GameObject>>();
  20. }
  21. public static GameObject Instantiate(GameObject prefab, Vector3 pos = default, Quaternion rotation = default, Transform parent = null)
  22. {
  23. GameObject go;
  24. if (instance.pools.ContainsKey(prefab) && instance.pools[prefab].Count > 0)
  25. {
  26. go = instance.pools[prefab][0];
  27. go.transform.parent = parent;
  28. go.transform.position = pos;
  29. go.transform.rotation = rotation;
  30. instance.pools[prefab].RemoveAt(0);
  31. }
  32. else
  33. {
  34. go = Object.Instantiate(prefab, pos, rotation, parent);
  35. PoolItem poolItem = go.AddComponent<PoolItem>();
  36. poolItem.prefab = prefab;
  37. }
  38. go.SetActive(true);
  39. if (!instance.activeObjs.ContainsKey(prefab))
  40. {
  41. instance.activeObjs.Add(prefab, new List<GameObject>());
  42. }
  43. instance.activeObjs[prefab].Add(go);
  44. return go;
  45. }
  46. public static void Preloading(GameObject prefab,int num)
  47. {
  48. instance.activeObjs.Add(prefab, new List<GameObject>());
  49. for (int i = 0; i < num; i++)
  50. {
  51. GameObject go = Object.Instantiate(prefab);
  52. PoolItem poolItem = go.AddComponent<PoolItem>();
  53. poolItem.prefab = prefab;
  54. go.SetActive(false);
  55. instance.activeObjs[prefab].Add(go);
  56. }
  57. }
  58. public static void InstantiateAsync(string name, Vector3 pos = default, Quaternion rotation = default, Transform parent = null, UnityAction<GameObject> callback = null)
  59. {
  60. if (instance == null)
  61. {
  62. Debug.LogError("PoolManager instance not initialized!");
  63. callback(null);
  64. return;
  65. }
  66. instance.StartCoroutine(instance.ReallyLoadGameObjectAsync(name,pos,rotation,parent, callback));
  67. }
  68. private IEnumerator ReallyLoadGameObjectAsync(string name, Vector3 pos = default, Quaternion rotation = default, Transform parent = null, UnityAction<GameObject> callback = null)
  69. {
  70. ResourceRequest r = Resources.LoadAsync<GameObject>(name);
  71. yield return r;
  72. if (r.asset == null)
  73. {
  74. Debug.LogError($"Failed to load GameObject: {name}");
  75. callback(null);
  76. yield break;
  77. }
  78. GameObject prefab = r.asset as GameObject;
  79. if (instance.pools.ContainsKey(prefab) && instance.pools[prefab].Count > 0)
  80. {
  81. GameObject go = instance.pools[prefab][0];
  82. go.transform.parent = parent;
  83. go.transform.position = pos;
  84. go.transform.rotation = rotation;
  85. go.SetActive(true);
  86. instance.pools[prefab].RemoveAt(0);
  87. if (!instance.activeObjs.ContainsKey(prefab))
  88. instance.activeObjs.Add(prefab, new List<GameObject>());
  89. instance.activeObjs[prefab].Add(go);
  90. callback(go);
  91. }
  92. else
  93. {
  94. GameObject go = Object.Instantiate(prefab);
  95. go.transform.parent = parent;
  96. go.transform.position = pos;
  97. go.transform.rotation = rotation;
  98. PoolItem poolItem = go.AddComponent<PoolItem>();
  99. poolItem.prefab = prefab;
  100. if (!instance.activeObjs.ContainsKey(prefab))
  101. instance.activeObjs.Add(prefab, new List<GameObject>());
  102. instance.activeObjs[prefab].Add(go);
  103. callback(go);
  104. }
  105. }
  106. public void Recycle(PoolItem poolItem)
  107. {
  108. if (!pools.ContainsKey(poolItem.prefab))
  109. {
  110. pools.Add(poolItem.prefab, new List<GameObject>());
  111. }
  112. pools[poolItem.prefab].Add(poolItem.gameObject);
  113. activeObjs[poolItem.prefab].Remove(poolItem.gameObject);
  114. }
  115. public void DestroyItem(PoolItem poolItem)
  116. {
  117. if (!pools.ContainsKey(poolItem.prefab))
  118. {
  119. return;
  120. }
  121. pools[poolItem.prefab].Remove(poolItem.gameObject);
  122. activeObjs[poolItem.prefab].Remove(poolItem.gameObject);
  123. }
  124. }