Files
test/Documentation/poolingManager.md
T
2026-05-04 16:16:58 +07:00

3.5 KiB

Pooling Manager Execution Flow

Purpose

The pooling system recycles Addressables-backed GameObject instances instead of repeatedly calling Instantiate and Destroy. Each Addressables key owns one runtime pool that tracks active objects, idle objects, and a memory-release timer.

PoolManager loads prefab assets through AddressableManager, so it uses the same Addressables initialization path and loaded-prefab cache as the rest of the project. Runtime instances are ordinary instantiated GameObjects owned by the pool.

Runtime Files

  • IPoolable.cs: prefab-side lifecycle interface.
  • ObjectPool.cs: owns instances and the loaded prefab reference for one Addressables key.
  • PoolManager.cs: singleton service used by gameplay, server packet handlers, UI code, and effects systems.

Spawn Flow

  1. Call PoolManager.Instance.SpawnAsync(...) or PoolManager.Instance.Spawn(...).
  2. PoolManager finds or creates an ObjectPool for the Addressables key.
  3. The pool updates its memoryReleaseTTL from the spawn parameter.
  4. If a memory release countdown is running, the pool cancels it.
  5. The pool reuses an idle object when available.
  6. If no idle object exists, the pool waits for AddressableManager initialization, loads the prefab with AddressableManager.LoadPrefabAsync(), then instantiates it.
  7. The instance is parented, positioned, rotated, activated, and all IPoolable.OnSpawn() hooks are called.
  8. If autoDespawnTime > 0, PoolManager starts a version-checked auto-despawn coroutine.
  9. The spawned GameObject is returned to the caller.

Despawn Flow

  1. Call PoolManager.Instance.Despawn(gameObject) or PoolManager.Instance.Despawn(addressableKey, gameObject).
  2. The target pool validates that the object is currently active.
  3. All IPoolable.OnDespawn() hooks are called.
  4. The object is deactivated, parented under the pool root, and pushed into the idle stack.
  5. When the active count reaches zero, the pool starts the memory release countdown.

Memory Release Flow

  1. The countdown waits for the latest memoryReleaseTTL value supplied by spawn calls for that key.
  2. A new spawn for the same key cancels the countdown and keeps the prefab plus idle instances available.
  3. If the countdown completes while active count is still zero, the pool:
    • unregisters itself from PoolManager;
    • destroys all pooled instances;
    • calls AddressableManager.ForceReleaseAsset(addressableKey) to release the cached prefab asset;
    • destroys the pool root object.

Auto Despawn Safety

Auto despawn stores the instance spawn version when the coroutine starts. If the object is manually despawned and reused before the timer completes, the version changes and the old coroutine will not despawn the new lifecycle.

Shutdown Flow

PoolManager subscribes to AddressableManager.OnDispose. When the Addressables manager is disposed, all pools release their instances and prefab assets before AddressableManager.ReleaseAllAssets() runs. PoolManager.OnDestroy() also releases all pools as a fallback.

Example

GameObject fx = await PoolManager.Instance.SpawnAsync(
    "effects/fireball.prefab",
    hitPosition,
    Quaternion.identity,
    memoryReleaseTTL: 15f,
    autoDespawnTime: 2f);

For coroutine-based callers:

PoolManager.Instance.Spawn(
    "effects/fireball.prefab",
    hitPosition,
    Quaternion.identity,
    memoryReleaseTTL: 15f,
    autoDespawnTime: 2f,
    onComplete: spawned => { /* use spawned */ });