I'm in the process of implementing an inventory system in my game.
The script which is most important to this question is InventorySlotManager.
public class InventorySlotManager : MonoBehaviour
{
ItemData itemData;
const int numSlots = 20;
Item[] itemsInInventory = new Item[numSlots];
[SerializeField] GameObject[] slots = new GameObject[numSlots];
[SerializeField] GameObject itemImagePrefab;
int[] stackSize = new int[numSlots];
void Awake()
{
itemData = GameObject.Find("Item Manager").GetComponent<ItemData>();
}
void Start()
{
AddItem(itemData.coin);
AddItem(itemData.silverRing);
AddItem(itemData.coin);
}
void Update()
{
if (Input.GetKey(KeyCode.Alpha1))
{
AddItem(itemData.coin);
}
if (Input.GetKey(KeyCode.Alpha2))
{
AddItem(itemData.silverRing);
}
}
void AddItem(Item item)
{
int indexOfDuplicateItem = System.Array.IndexOf(itemsInInventory, item);
if (indexOfDuplicateItem > -1)
{
Text quantityTextOfDuplicateItem = slots[indexOfDuplicateItem].transform.Find("Item Image(Clone)").gameObject.GetComponentInChildren<Text>();
quantityTextOfDuplicateItem.text = (++stackSize[indexOfDuplicateItem]).ToString();
}
else
{
for (int i = 0; i < numSlots; i++)
{
if (itemsInInventory[i] == null)
{
itemsInInventory[i] = item;
GameObject itemImage = Instantiate(itemImagePrefab, slots[i].transform);
itemImage.GetComponent<Image>().sprite = item.itemSprite;
Text quantityTextOfNewItem = slots[i].GetComponentInChildren<Text>();
stackSize[i] = item.itemQuantity;
quantityTextOfNewItem.text = stackSize[i].ToString();
return;
}
}
}
}
}
This does what you'd expect. (The bit in Update is just there temporarily for testing.) When an item gets added, the function checks to see if one already exists in the items array. If not, then the for loop is executed and the item is added to the items array, an item image game object is instantiated in the corresponding index of the slots array, etc. So far so good, everything behaves properly until I start dragging items around in my DragHandler script.
So I press play, my inventory has two kinds of objects in it (coin, and silver ring). They each display their correct quantities (stack sizes) as I keep adding items. Then, I move the coin from slot 0 to slot 5 and attempt to add more coins to the inventory. It stops working because the line Text quantityTextOfDuplicateItem = slots[indexOfDuplicateItem].transform.Find("Item Image(Clone)").gameObject.GetComponentInChildren<Text>();
returns null at that point.
What is the best way to fix this such that this reference won't become null if I move the item to a different slot after it gets added to my inventory? I think I either have to map the items array to the slots array or store all of these values, e.g., items, slots, quantitytext, in one array. Is this correct?