Unity对象池笔记
游戏中常常需要对有些游戏对象进行反复的创建销毁,比如游戏中的子弹、敌人。反复的创建与销毁将浪费一定的系统资源。
引入对象池技术,可以将暂时不需要用到的游戏对象放在对象池(缓冲区),当需要使用到时再从对象池中提取。分为步骤:
- 建立单例模式的对象池类
- 建立从对象池里获取的方法
- 建立对象回收的方法
using System.Collections; using System.Collections.Generic; using UnityEngine; public class ObjectPool { #region 单例 private static ObjectPool instance; private ObjectPool()//给自己创建实例,并实例pool和prefabs { pool = new Dictionary<string, List<GameObject>>(); prefabs = new Dictionary<string, GameObject>(); } public static ObjectPool GetInstance() { if (instance == null) { instance = new ObjectPool(); } return instance; } #endregion /// <summary> /// 对象池 /// </summary> private Dictionary<string, List<GameObject>> pool; /// <summary> /// 预设体 /// </summary> private Dictionary<string, GameObject> prefabs; /// <summary> /// 从对象池中获取对象 /// </summary> /// <param name="objName"></param> /// <returns></returns> public GameObject GetObj(string objName) { //结果对象 GameObject result = null; //判断是否有该名字的对象池 if (pool.ContainsKey(objName)) { //对象池里有对象 if (pool[objName].Count > 0) { //获取结果 result = pool[objName][0]; //激活对象 result.SetActive(true); //从池中移除该对象 pool[objName].Remove(result); //返回结果 return result; } } //如果没有该名字的对象池或者该名字对象池没有对象 GameObject prefab = null; //如果已经加载过该预设体 if (prefabs.ContainsKey(objName)) { prefab = prefabs[objName]; } else //如果没有加载过该预设体 { //加载预设体 prefab = Resources.Load<GameObject>("Prefabs/" + objName); //更新字典 prefabs.Add(objName, prefab); } //生成 result = UnityEngine.Object.Instantiate(prefab); //改名(去除 Clone) result.name = objName; //返回 return result; } /// <summary> /// 回收对象到对象池 /// </summary> /// <param name="obj"></param> public void RecycleObj(GameObject obj) { //设置为非激活 obj.SetActive(false); //判断是否有该对象的对象池 if (pool.ContainsKey(obj.name)) { //放置到该对象池 pool[obj.name].Add(obj); } else { //创建该类型的池子,并将对象放入 pool.Add(obj.name, new List<GameObject>() { obj }); } } } 使用方法: ObjectPool PM = ObjectPool.GetInstance(); <br> //加载预设体 <br> // obj = Resources.Load<GameObject>("Prefabs/" + Cube); <br> PM.GetObj("Cube");