using UnityEngine; using System.Collections.Generic; public class Shelf : MonoBehaviour { public ShelfData shelfData; public ShelfData.ShelfType shelfType => shelfData.shelfType; [HideInInspector] public Transform[] stackPoints; public List stockedItems = new List(); public bool useManualLevelHeights = false; // Toggle in Inspector void Awake() { GenerateStaticStackPoints(); } // Generates a static grid of stack points based on rows and columns public void GenerateStaticStackPoints() { if (shelfData == null) { Debug.LogError("ShelfData not assigned!"); return; } // --- Preserve stacked items --- List itemsToPreserve = new List(); foreach (Transform child in transform) { if (child.name.StartsWith("StackPoint_")) { // Save and unparent any items parented to this stack point List toUnparent = new List(); foreach (Transform item in child) { itemsToPreserve.Add(item); toUnparent.Add(item); } foreach (var item in toUnparent) item.parent = this.transform; // Temporarily unparent to shelf root } } // Remove old stack points var toRemove = new List(); foreach (Transform child in transform) if (child.name.StartsWith("StackPoint_")) toRemove.Add(child); foreach (var child in toRemove) DestroyImmediate(child.gameObject); // ...rest of your code... int totalPoints = shelfData.rows * shelfData.columns * shelfData.levels; stackPoints = new Transform[totalPoints]; int idx = 0; for (int l = 0; l < shelfData.levels; l++) { float y = useManualLevelHeights && shelfData.manualLevelHeights != null && l < shelfData.manualLevelHeights.Length ? shelfData.manualLevelHeights[l] : (shelfData.shelfSize.y / shelfData.levels) * (l + 0.5f); for (int r = 0; r < shelfData.rows; r++) { for (int c = 0; c < shelfData.columns; c++) { float x = (-shelfData.shelfSize.x / 2) + (shelfData.shelfSize.x / shelfData.columns) * (c + 0.5f); float z = (shelfData.shelfSize.z / 2) - (shelfData.shelfSize.z / shelfData.rows) * (r + 0.5f); Vector3 localOffset = new Vector3(x, y, z) + shelfData.stackOriginOffset; GameObject point = new GameObject($"StackPoint_{l}_{r}_{c}"); point.transform.parent = this.transform; point.transform.localPosition = localOffset; stackPoints[idx++] = point.transform; } } } // --- Re-parent preserved items to the closest new stack point --- foreach (var item in itemsToPreserve) { // Find the nearest stack point to the item's position Transform nearest = null; float minDist = float.MaxValue; foreach (var sp in stackPoints) { float dist = Vector3.Distance(sp.position, item.position); if (dist < minDist) { minDist = dist; nearest = sp; } } if (nearest != null) item.parent = nearest; else item.parent = this.transform; // fallback } } public void AddStockedItem(string itemName) { if (!stockedItems.Contains(itemName)) stockedItems.Add(itemName); } public void RemoveStockedItem(string itemName) { stockedItems.Remove(itemName); } public Transform GetNextAvailableStackPoint() { foreach (var point in stackPoints) { if (point.childCount == 0) return point; } return null; } public Transform GetNearestStackPoint(Vector3 hitPosition, out bool isOccupied) { Transform nearest = null; float minDist = float.MaxValue; isOccupied = false; foreach (var point in stackPoints) { float dist = Vector3.Distance(point.position, hitPosition); if (dist < minDist) { minDist = dist; nearest = point; } } if (nearest != null) isOccupied = nearest.childCount > 0; return nearest; } // Draws the grid in the editor for configuration void OnDrawGizmos() { if (shelfData == null) return; Gizmos.color = Color.cyan; Gizmos.DrawWireCube(transform.position + Vector3.up * shelfData.shelfSize.y * 0.5f, shelfData.shelfSize); for (int l = 0; l < shelfData.levels; l++) { float y = useManualLevelHeights && shelfData.manualLevelHeights != null && l < shelfData.manualLevelHeights.Length ? shelfData.manualLevelHeights[l] : (shelfData.shelfSize.y / shelfData.levels) * (l + 0.5f); for (int r = 0; r < shelfData.rows; r++) { for (int c = 0; c < shelfData.columns; c++) { float x = (-shelfData.shelfSize.x / 2) + (shelfData.shelfSize.x / shelfData.columns) * (c + 0.5f); // Z: match runtime! float z = (shelfData.shelfSize.z / 2) - (shelfData.shelfSize.z / shelfData.rows) * (r + 0.5f); Vector3 localOffset = new Vector3(x, y, z) + shelfData.stackOriginOffset; Vector3 worldPos = transform.TransformPoint(localOffset); Gizmos.color = Color.yellow; Gizmos.DrawWireCube(worldPos, Vector3.one * 0.04f); Gizmos.color = Color.red; Gizmos.DrawSphere(worldPos, 0.02f); } } } } }