Unity对象池封装
1、应用场景:
对一些游戏场景:需要多次创建和销毁的对象【如枪战游戏里的子弹、RPG游戏里的剧情小怪...】
2、为什么要使用对象池:
可以减少GC的次数,提高游戏性能
3、对象池原理:
a、需要生成对象时,先判断容器里是否存在可用的该类型对象,存在则直接取,不存在就实例化
b、将需要销毁的对象保存而不删除【设置不可见,保存在容器中】
4、具体实现:【将对象池比作为衣柜,衣柜里有好多抽屉,不同抽屉放置不同类型的衣服】
C#
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PoolObj : SingletonBase<PoolObj> {
public Dictionary<string, List<GameObject>> poolDict = new Dictionary<string, List<GameObject>>();
public GameObject GetObj(string name)
{
GameObject obj = null;
//如果衣橱里有该类型抽屉 并且 该抽屉 有可用的衣服
if (poolDict.ContainsKey(name) && poolDict[name].Count > 0)
{
//取出目标衣服,在抽屉里移除衣服
obj = poolDict[name][0];
poolDict[name].RemoveAt(0);
}
else
{
//创建衣服
obj = GameObject.Instantiate(Resources.Load<GameObject>(name));
obj.name = name;//将对象名字设置为 预制体 名字
}
obj.SetActive(true);
return obj;
}
public void PushObj(string name,GameObject obj)
{
obj.SetActive(false);
//如果衣柜里有该类型抽屉
if (poolDict.ContainsKey(name))
{
//直接在相应抽屉里添加衣服
poolDict[name].Add(obj);
}
else
{
//衣柜里没有该抽屉 则 创建抽屉
poolDict.Add(name, new List<GameObject>() { obj});
}
}
}
预制体上挂上延迟销毁的代码:
C#
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class delayPush : MonoBehaviour {
void OnEnable()
{
Invoke("Push", 1);//延迟1秒放入对象池
}
void Push()//调用对象池 放入管理方法
{
PoolObj.GetInstance().PushObj(this.gameObject.name,this.gameObject);
}
}
测试代码:
C#
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class GameStart : MonoBehaviour {
void Update()
{
if (Input.GetMouseButtonDown(0))
{
PoolObj.GetInstance().GetObj("Pool/Cube");//预制体路径
}
if (Input.GetMouseButtonDown(1))
{
PoolObj.GetInstance().GetObj("Pool/Cube2");
}
}
}
效果:
评论