Home > front end >  CS0120 Error appears in function despite a parameter being used
CS0120 Error appears in function despite a parameter being used

Time:08-09

This is my first time here on Stack Overflow, so I might be bad at phrasing my question, and my code is not very good either. I have been stumped on this for 2 days and I currently don't have any workarounds, please help.

So I'm making an inventory system with ScriptableObjects. Below is the ScriptableObject code for the save data of a player. Within it contains the Inventory and Wormhole class. Within the Inventory class contains the InventoryMain list, some special inventory slots and a function to add items that if an existing slot is found with the same item being added then it will just increase the value for that slot instead of making a new InventorySlot. The Wormhole class is an extension to the player's inventory, so it's similar to the Inventory class but without the special slots. The InventorySlot class is also defined at the bottom of the script.

PlayerSaveData.cs

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

[CreateAssetMenu(fileName = "New Inventory", menuName = "Inventory System/Inventory")]
public class PlayerSaveData : ScriptableObject
{
    [System.Serializable]
    public class Inventory
    {
        public List<InventorySlot> inventoryMain = new();
        public InventorySlot inventoryHead;
        public InventorySlot inventoryNeck;
        public InventorySlot inventoryBody;
        public InventorySlot inventoryOffhand;
        public InventorySlot inventoryLegs;
        public int inventoryMainLimit = 30;
        public void AddItem(ItemObject _item, int _amount)
        {
            bool hasItem = false;
            for (int i = 0; i < inventoryMain.Count; i  )
            {
                if (inventoryMain[i].item == _item)
                {
                    inventoryMain[i].AddAmount(_amount);
                    hasItem = true;
                    break;
                }
            }
            if (!hasItem)
            {
                if (inventoryMain.Count! < inventoryMainLimit)
                {
                    Debug.Log("Space found in Player inventory");
                    inventoryMain.Add(new InventorySlot(_item, _amount));
                }
                else
                {
                    Debug.Log("Player inventory full, checking wormhole");
                }
            }
        }
    }
    [System.Serializable]
    public class Wormhole
    {
        public List<InventorySlot> inventoryMain = new();
        public int inventoryMainLimit;
        public void AddItem(ItemObject _item, int _amount)
        {
            bool hasItem = false;
            for (int i = 0; i < inventoryMain.Count; i  )
            {
                if (inventoryMain[i].item == _item)
                {
                    inventoryMain[i].AddAmount(_amount);
                    hasItem = true;
                    break;
                }
            }
            if (!hasItem)
            {
                if (inventoryMain.Count! < inventoryMainLimit)
                {
                    Debug.Log("Space found in Wormhole inventory.")
                    inventoryMain.Add(new InventorySlot(_item, _amount));
                }
                else
                {
                    Debug.Log("Wormhole inventory full, ignoring item.");
                }
            }
        }
    }
}
[System.Serializable]
public class InventorySlot
{
    public ItemObject item;
    public int amount;
    public InventorySlot(ItemObject _item, int _amount)
    {
        item = _item;
        amount = _amount;
    }
    public void AddAmount(int value)
    {
        amount  = value;
    }
}

..and I'm trying to grab its information with CraftingRecipes.cs. (The script for searching Wormhole inventory is not even completed yet, but I can fix that after fixing this.)

CraftingRecipes.cs

using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;

[CreateAssetMenu(fileName = "New Recipe", menuName = "Inventory System/Recipe")]
public class CraftingRecipes : ScriptableObject
{
    public PlayerSaveData currentInventory;
    public List<InventorySlot> Materials;
    public List<InventorySlot> Products;

    public bool CanCraft(PlayerSaveData playerSaveData)
    {
        List<InventorySlot> playerContainer = playerSaveData.Inventory.inventoryMain.Concat(playerSaveData.Inventory.inventoryMain).ToList();
        bool[] check = (bool[])Enumerable.Repeat(false, Materials.Count);
        for (int a = 0; a < Materials.Count; a  )
        {
            for (int b = 0; b < playerContainer.Count; b  )
            {
                if (Materials[a].item == playerContainer[b].item && Materials[a].amount! > playerContainer[b].amount)
                {
                    check[a] = true;
                }
            }
        }
        for (int i = 0; i < check.Length; i  )
        {
            if (check[i] == false)
            {
                return false;
            }
        }

        return true;
    }

    public void Craft()
    {
        if (CanCraft(currentInventory))
        {
            for (int a = 0; a < Materials.Count; a  )
            {
                for (int b = 0; b < currentInventory.Inventory.inventoryMain.Count; b  )
                {
                    if (Materials[a].item == currentInventory.Inventory.InventoryMain[b].item && Materials[a].amount! > currentInventory.Container[b].amount)
                    {
                        currentInventory.Inventory.inventoryMain[b].amount -= Materials[a].amount;
                        break;
                    }
                }
            }
        }
    }
}

Unfortunately...

error CS0120

...keeps appearing in the first line of the CanCraft() function, which just concatenates the player's inventory and wormhole to a third list to check if the player has sufficient materials for the recipe. (I need more reputation to embed images, but this is my first time doing anything here) Worse, in the Craft() function even CS0117 appears.

CS0117 description

Error describes that PlayerSaveData.Inventory doesn't contain a definition of inventoryMain, even though it clearly does.

These scripts were made with separate tutorials, I've tried my best to make them compatible with each other, and I've ran out of workarounds. I've tried making the CanCraft() function take in both child objects of PlayerSaveData (PlayerSaveData.Inventory and PlayerSaveData.Wormhole), but that would mean I had to call the function with those parameters to begin with, which would just make the Craft() function have the error instead of the CanCraft() function. Please help, and sorry if my question is unreadable or unclear.

CodePudding user response:

So you have;

public class PlayerSaveData : ScriptableObject
{
    public class Inventory
    {
        public List<InventorySlot> inventoryMain = new();
        // etc
    }
}

Inventory is a class, not a property of PlayerSaveData. So PlayerSaveData.Inventory.[anything] can only be an attempt to reference a static field or property of the Inventory class. Which is probably not what you want.

Did you intend to write something like;

public class PlayerSaveData : ScriptableObject
{
    public Inventory Inventory { get; set; }
}
public class Inventory
{
    public List<InventorySlot> inventoryMain = new();
    // etc
}

So that each instance of PlayerSaveData has a related Inventory instance.

CodePudding user response:

For both errors, you need to create Inventory type property in PlayerSaveData class:

public class PlayerSaveData : ScriptableObject
{
    public Inventory Inventory { get; set; }
    // rest of the above code
  • Related