Pool dùng hàng đợi
Thuộc phần Kiến trúc trò chơi trong Unity trong hành trình Unity của Coddy. Bài học 47 trên 64.
Một pool cần chỗ để giữ các đối tượng dự phòng, và C# có bộ sưu tập phù hợp: Queue<T>. Enqueue thêm một phần tử vào cuối hàng đợi, Dequeue lấy phần tử ở đầu hàng đợi, còn Count cho biết có bao nhiêu phần tử đang chờ. Bể cá này tạo một bong bóng sau mỗi 0.3 giây, và mỗi bong bóng quay lại pool khi lên đến mặt nước:
using System.Collections.Generic;
using UnityEngine;
public class BubblePool : MonoBehaviour
{
public GameObject bubblePrefab;
private Queue<GameObject> pool = new Queue<GameObject>();
private float timer;
void Update()
{
timer += Time.deltaTime;
if (timer >= 0.3f)
{
timer = 0f;
Get(new Vector3(Random.Range(-2f, 2f), 0f, 0f));
}
}
public GameObject Get(Vector3 position)
{
GameObject bubble;
if (pool.Count > 0)
{
bubble = pool.Dequeue();
}
else
{
bubble = Instantiate(bubblePrefab);
bubble.GetComponent<Bubble>().pool = this;
}
bubble.transform.position = position;
bubble.SetActive(true);
return bubble;
}
public void Return(GameObject bubble)
{
bubble.SetActive(false);
pool.Enqueue(bubble);
}
}// Bubble.cs, trên prefab bong bóng
public BubblePool pool;
void Update()
{
transform.Translate(0f, 2f * Time.deltaTime, 0f);
if (transform.position.y > 5f) pool.Return(gameObject);
}Get kiểm tra Count trước, vì gọi Dequeue trên hàng đợi rỗng sẽ gây ra ngoại lệ InvalidOperationException. Sau đó, hàm mới gọi Instantiate, và chỉ bong bóng mới tạo cần được gán trường pool: bong bóng được dùng lại vẫn giữ trường này. Hàng đợi đưa ra trước bong bóng đã chờ lâu nhất, theo nguyên tắc vào trước, ra trước. Khi lên đến mặt nước, bong bóng gọi Return thay vì Destroy, rồi nằm lại trong cảnh ở trạng thái không hoạt động cho đến lần gọi Get tiếp theo.
Get đặt vị trí của bong bóng trước khi gọi SetActive(true), vì bật đối tượng sẽ chạy OnEnable ngay lập tức, và những gì diễn ra ở đó cần thấy vị trí mới, không phải vị trí lần trước bong bóng biến mất. Đây cũng là lúc đối tượng được dùng lại bắt đầu lại: Awake và Start chỉ chạy một lần khi bong bóng được tạo, còn OnEnable chạy mỗi lần gọi Get.
Thử thách
Trung bìnhĐưa các dấu chân vào pool thay vì hủy chúng.
- Trong
Trail, giữ các đối tượng dự phòng trong mộtQueue<GameObject>.Return(footprint)tắt đối tượng và đưa nó vào hàng đợi;Starttạoprewarmdấu chân rồi đưa chúng vào hàng đợi. Get(position)lấy một đối tượng dự phòng ra khỏi hàng đợi (hoặc tạo một đối tượng), đặt nó vào vị trí rồi bật lên.- Trong
Footprint, thay lệnh Destroy: đặt lại tuổi trongOnEnable; saulifegiây, gọitrail.Return(gameObject).
Nhấn Chơi rồi đi bộ: các dấu chân mờ dần sau 1.5 giây. Sau đó nhấn Kiểm tra.
Tự làm thử
using System.Collections.Generic;
using UnityEngine;
public class Trail : MonoBehaviour
{
public GameObject footprintPrefab;
public float step = 1f;
public int prewarm = 6;
private Vector3 lastDrop;
void Start()
{
lastDrop = transform.position;
// Cho sẵn các dấu chân vào vùng lưu trữ theo số lượng prewarm
}
void Update()
{
if (Vector3.Distance(transform.position, lastDrop) >= step)
{
lastDrop = transform.position;
Get(new Vector3(transform.position.x, 0.02f, transform.position.z));
}
}
public GameObject Get(Vector3 position)
{
GameObject footprint = Instantiate(footprintPrefab, position, Quaternion.identity);
footprint.GetComponent<Footprint>().trail = this;
return footprint;
}
public void Return(GameObject footprint)
{
// Các dấu chân dự phòng nằm trong vùng lưu trữ
}
}
Tất cả bài học trong Kiến trúc trò chơi trong Unity
1Thành phần, không phải hệ thống phân cấp
Thành phần nhỏTập lệnh kẻ địch cơ sởThành phần trừu tượngCác thành phần phối hợp với nhauÔn tập: tháp pháo mô-đunÔn tập: pháo nòng đôi4Dữ liệu tuần tự hóa
Lớp có thể tuần tự hóaDanh sách trong InspectorKiểu liệt kê trong InspectorÔn tập: Bảng vật phẩm rơiÔn tập: Quay vật phẩm2Giao diện trong Unity
IDamageableGiao diện và TryGetComponentGetComponentsÔn tập: phím tương tácÔn tập: đối tượng gần nhất trong tầm với5ScriptableObjects
Tài sản dữ liệuChỉ số vũ khíCài đặt dùng chungLưu gióSóng dưới dạng dữ liệuÔn tập: Cơ sở dữ liệu vật phẩmÔn tập: Mua hàng từ cửa hàng8Code có thể tái sử dụng
Phương thức mở rộngSingleton tổng quátCác hàm hỗ trợ tổng quátÔn tập: FindNearest3Sự kiện
Sự kiện C# trong UnityĐăng ký trong OnEnableCác trường UnityEventSự kiện điều khiển UIÔn tập: Cửa sổ bật lên thành tíchÔn tập: Bộ hẹn giờ cửa sổ bật lên6Lưu dữ liệu bằng JSON
JsonUtilityLưu trò chơiTải dữ liệu và giá trị mặc địnhÔn tập: các ô lưuChọn và xóa một ô lưu9Tái sử dụng đối tượng bằng pool
Vì sao cần pool đối tượngPool dùng hàng đợiObjectPool của UnityÔn tập: pool đạnTự luyện tập: Playground Unity