1.14.4 Checking inventory giving error when it doesn't contain the item

Discussion in 'Spigot Plugin Development' started by Sean0402, Jan 29, 2020.

  1. Hey, I have an issue with checking the players inventory, it works fine if they have 1 of the items, but errors when they don't have any of the items in their inventory specified in this code;
    Code (Java):
    int count = 0;
                    if (inventoryChecker) {
                        for (ItemStack items : ((Player) e.getRightClicked()).getInventory().getContents()) {
                            if (items != null && items.getType() == Material.DIAMOND_HORSE_ARMOR || items.getType() == Material.GOLDEN_HORSE_ARMOR) {
                                count += items.getAmount();
                                e.getPlayer().sendMessage("Items: " + items);
                                e.getPlayer().sendMessage("Count: " + count);
                                e.getPlayer().sendMessage("Horse armour: " + items.getType().equals(Material.DIAMOND_HORSE_ARMOR));
                            }
                        }
                    }
    Error line;
    Code (Java):
                            if (items.isSimilar(new ItemStack(Material.DIAMOND_HORSE_ARMOR)) || items.isSimilar(new ItemStack(Material.GOLDEN_HORSE_ARMOR))) {
     
     
    #1 Sean0402, Jan 29, 2020
    Last edited: Jan 30, 2020
  2. FrostedSnowman

    Resource Staff

    Provide a null check for items.
     
  3. I had one. That doesn't solve the issue. The above code is something I was testing and assuming it'd work.
     
  4. Why aren't you comparing the materials instead of checking if the item is similar to a new itemstack of the right type. That checks the amount, lore, and name as well (unless that's what you want)
     
  5. Code (Java):
    if (items != null && items.getType() == Material.DIAMOND_HORSE_ARMOR || items.getType() == Material.GOLDEN_HORSE_ARMOR) {
    I can do it like this, but that wont solve the issue and i dont get why
     
  6. Been working with some other languages recently and found out that some of them have a interesting 'syntax' in terms of AND&OR checks. Kinda forgot if it's different in Java but might wanna give the following pseudo code a try.

    Code (Text):
    if(item not null && (item is gold horse armor || diamond horse armor) ) {
        //basically putting your OR check in parentheses
    }
    Again, don't remember if it makes a difference in Java and I have no way to test it right now.
     
  7. Do something like this
    Code (Text):
    if(item != null) {
        if (item.getType().equals(Material.DIAMOND_HORSE_ARMOR) || item.getType().equals(Material.GOLDEN_HORSE_ARMOR)) {
            //player has the items
        }
    }
     
    • Like Like x 1
  8. That seems to not do anything for some reason. Wont print at all
     
  9. Okay, so let me explain why your test didn't work:
    When we are talking about logic, we also need to talk about precedence. It's the same as in mathematics; you first have to multiply before you can accumulate (a * b + c == (a * b) + c)
    The same goes for Logic; AND has higher precedence than OR (basically what @Fluxcus pointed out). So you code:
    Code (Text):
    if (item != null && itemType == diamondHorseArmor || itemType == goldHorseArmor)
    is equivalent to
    Code (Text):
    if ( (item != null && itemType == diamondHorseArmor) || itemType == goldHorseArmor)
    However, you want this:
    Code (Text):
    if ( item != null && ( itemType == diamondHorseArmor || itemType == goldHorseArmor) )
    Therefore the latter code (checking in a first if-condition if the item is not null and then checking in a second if the item is an armor also works, if i doesn't for you then you have made some other misstake.)

    Now all of that is not necessary since Inventory already comes with some nice convenient methods that have all of your needs covered:
    Code (Java):
    final Map<Integer,? extends ItemStack> allDiamondArmors = player.getInventory().all(Material.DIAMOND_HORSE_ARMOR);
    final Map<Integer,? extends ItemStack> allGoldArmors = player.getInventory().all(Material.GOLDEN_HORSE_ARMOR);
     
    The map returns the ItemStacks and the index that they are in the inventory.