728x90
Unity에서 총알을 쏘는 스크립트를 작성하면
1. 총알이 필요할 때 총알 공장에 요청한다.
2. 총알 공장에서 총알을 만든다.
3. 총알을 발사하고 총알을 삭제한다.
위와같은 방식으로 진행한다.
위의 방식으로 총알을 만들고 삭제하면 메모리 공간에 OverFlow나 메모리 단편화(파편화)문제로 Garbage Collector가 돌아가서 CPU를 낭비하게 된다는 단점이 발생한다.
위의 문제를 해결하기 위해서 'Object Pool'을 활용할 수 있다.
1. 총알을 탄창에 미리 넣어두고
2. 필요할 때마다 총알을 꺼내쓴다.
3. 다 쓴 총알은 삭제하지 않고 비활성화한다.
여기서 탄창은 Pool
객체를 Pool로 만들어 둔 것을 Object Pool
네트워크 연결에 관련된 풀을 미리 잡아 둔 것을 Connection Pool이라고한다.
본격적으로 코드를 작성해보자!
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PlayerFire : MonoBehaviour
{
public GameObject bulletFactory; // 총알 공장
public int poolSize = 10; // 탄창에 담을 수 있는 총알의 개수(미리 만들어 둘 총알 게임오브젝트 개수)
GameObject[] bulletObjectPool; // 탄창
// Start is called before the first frame update
void Start()
{
// 탄창에 총알을 담는다.
bulletObjectPool = new GameObject[poolSize]; // 10크기의 탄창을 만듦
for (int i = 0; i < poolSize; i++)
{
GameObject go = Instantiate(bulletFactory);
bulletObjectPool[i] = go;
go.SetActive(false);
}
}
// Update is called once per frame
void Update()
{
}
}
1. 총알 발사 버튼이 눌리면
2. object pool에서 비활성화 된 bullet을 발사하고싶다.
void Update()
{
if(Input.GetKeyUp(KeyCode.Alpha1))
{
for(int i = 0;i < poolSize;i++)
{
GameObject go = bulletObjectPool[i];
if(go.activeSelf == false)
{
go.SetActive (true);
go.transform.position = transform.position;
break;
}
}
}
}
1. 만약 부딪힌 물체가 bullet이라면
2. 부딪힌 물체를 비활성화
3. 그렇지 않으면 제거
private void OnCollisionEnter(Collision collision)
{
if(collision.gameObject.name.Contains("Bullet"))
{
collision.gameObject.SetActive(false);
}
else
{
Destroy(collision.gameObject);
}
}