// Assets/_Project/Scripts/Gameplay/Draft/DraftPool.cs using System.Collections.Generic; using UnityEngine; namespace TD.Gameplay.Draft { /// /// Scene singleton holding every available this match. The /// array index is the option's DraftOptionId — the stable identifier used to /// replicate offers and picks over the network (mirrors the tower catalog pattern). /// /// /// Plain MonoBehaviour: identical on every peer (same assets), so there is nothing to /// sync. The server reads it to generate offers and apply picks; clients read it to /// render draft cards from the replicated option ids. /// public class DraftPool : MonoBehaviour { public static DraftPool Instance { get; private set; } [Tooltip("Every DraftOption asset that can be offered this match. Array index is " + "the DraftOptionId used over the network.")] [SerializeField] private DraftOption[] options; private void Awake() { if (Instance != null && Instance != this) { Debug.LogError("[DraftPool] Multiple instances detected. Only one per scene."); return; } Instance = this; } private void OnDestroy() { if (Instance == this) Instance = null; } /// Number of options in the pool. public int Count => options?.Length ?? 0; /// Returns the option at (its DraftOptionId), or null. public DraftOption Get(int id) => (options != null && id >= 0 && id < options.Length) ? options[id] : null; /// /// Server-only helper: collects the ids of every option currently valid to offer /// to (skips nulls and options whose /// returns false). Used by /// as the candidate set for the weighted draw. /// public void CollectValidIds(ulong clientId, List into) { into.Clear(); if (options == null) return; for (int i = 0; i < options.Length; i++) { if (options[i] == null) continue; if (options[i].IsValidFor(clientId)) into.Add(i); } } } }