[1.13.2] When crafting the required items increases.

Discussion in 'Spigot Plugin Development' started by drhampust, Feb 14, 2019.

  1. My problem is that when I craft items using item stacks for the recipe the needed items increases beyond stack limit even. I'm using a "PrepareItemCraftEvent" to check if the recipe contains the required item, (Name, Lore).
    My current code is:
    Code (Text):
    /**
    *
    */
    package com.HampusToft;

    import java.util.HashMap;

    import org.bukkit.event.EventHandler;
    import org.bukkit.event.Listener;
    import org.bukkit.event.inventory.PrepareItemCraftEvent;
    import org.bukkit.event.player.PlayerJoinEvent;
    import org.bukkit.inventory.CraftingInventory;
    import org.bukkit.inventory.ItemStack;
    public class ItemstackCrafting implements Listener {

        private int i = 0;
     
        @SuppressWarnings("serial")
        @EventHandler
        public void onPlayerCraftItem(PrepareItemCraftEvent e){
            if(e.getInventory().getMatrix().length < 9){
                return;
            }
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier1(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(0, CoustomItems.rareEmeraldTier2());
                }});
         
            checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier2(), 1), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                for(int n = 0; n < 9; n++) {
                    put(n, CoustomItems.rareEmeraldTier1());
                }
            }});
            i = 0;
            while (i < 9) {
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier2(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(i, CoustomItems.rareEmeraldTier3());
                    i++;
                }});
            }
            checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier3(), 1), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                for(int n = 0; n < 9; n++) {
                    put(n, CoustomItems.rareEmeraldTier2());
                }
            }});
            i = 0;
            while (i < 9) {
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier3(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(i, CoustomItems.rareEmeraldTier4());
                    i++;
                }});
            }
            checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier4(), 1), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                for(int n = 0; n < 9; n++) {
                    put(n, CoustomItems.rareEmeraldTier3());
                }
            }});
            i = 0;
            while (i < 9) {
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier4(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(i, CoustomItems.rareEmeraldTier5());
                    i++;
                }});
            }
            checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier5(), 1), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                for(int n = 0; n < 9; n++) {
                    put(n, CoustomItems.rareEmeraldTier4());
                }
            }});
            i = 0;
            while (i < 9) {
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier5(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(i, CoustomItems.rareEmeraldBlockTier5());
                    i++;
                }});
            }
            checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldBlockTier5(), 1), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                for(int n = 0; n < 9; n++) {
                    put(n, CoustomItems.rareEmeraldTier5());
                }
            }});
        }
     
        public void checkCraft(ItemStack result, CraftingInventory inv, HashMap<Integer, ItemStack> ingredients){
            ItemStack[] matrix = inv.getMatrix();
            for(int n = 0; n < 9; n++){
                if(ingredients.containsKey(n)){
                    if(matrix[n] == null
                             || !matrix[n].getItemMeta().getDisplayName().equals(ingredients.get(n).getItemMeta().getDisplayName())
                             || !matrix[n].getItemMeta().getLore().equals(ingredients.get(n).getItemMeta().getLore())){
                        return;
                    }
                } else {
                    if(matrix[n] != null){
                        return;
                    }
                }
            }
            inv.setResult(result);
        }
    }
     
    note My only problem is within the:

    Code (Text):

            i = 0;
            while (i < 9) {
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier2(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(i, CoustomItems.rareEmeraldTier3());
                    i++;
                }});
            }
    and it's is supose to be a shapless recipe to make a block put in any of the 9 slots to be able to be converted to 9 of the eariler Tier Emerald.
    I can add the custom items class but it only contains methods to create the custom ItemStacks and to change the amount that the ItemStack contains.
    if you dont understand my examples I have provided 1 picture and 1 gif showing the problem first hand
    [​IMG] [​IMG]
    Edit: Picture didnt seem to work so i added the Gyazo link.
    Picture
    https://gyazo.com/83bc55ac2efaccb1fbc524e90cc88887

    Gif
    https://gyazo.com/517bf73805e40dbe0acf75bc0927d6c6
     
  2. I have noticed the pattern of items in the crafting grid. and it follows the expression (n-1)*2 where n is the number of items in the crafting grid at craft
    so 3 items would become (3-1)*2 = 4 items this also explains why 2 items in the stack remain 2 (2-1)*2 = 1*2 = 2 items left.
    this expression only works when simply left clicking 1 craft at a time. if you shift-click you won't get the same amount. 7 items that each Should produce 9 items. when shift-clicked you will receive a total of 261 Items and not the 63 that was expected.
     
  3. md_5

    Administrator Developer

    Use the recipes API, not the event.

    See Server.addRecipe
     
  4. but it can't use item stacks, right? Because the items need to match both name and lore to my items. otherwise, normal emeralds would work to craft my recipes. or does the ItemMeta have some function that I totally missed?
     
  5. It has been added recently Recipe.ExactChoice. Only 1.13.
     
  6. It says:
    and:
    And that is what I want, I want a shapeless recipe using item containing Name and lore (it's a recipe that transforms a compressed version back down like an iron block to ingots). or is it okay to use deprecated methods?
     
  7. well I would not use a draft api because very likely it has no functions yet. However it should not take too long until the class is ready to use.

    A better work around would be to use the current recipe api and then listen for the craft event to swap the items or if you have special ingredients listen for the prepareitemcraftevent
     
  8. so I'm already using the PrepareItemcraftEvent. and I know many use shapedRecipe and then cancel the event if the required item does not have the required meta (name and lore). this, however, feels really funky seeing as i have 4-5 recipes both using 9 emeralds whit name and lore in crafting and the result is an emerald whit name and lore (different ofc). my code in the original post checks if it contains an Item whit correct lore and name in the specified slot using a hashmap. it works when crafting the higher tier (9 emerald tier 1 to 1 emerald tier 2) but code to do the reverse (1 emerald tier 2 to 9 emerald tier 1) dose some unexpected behaviour (ingredients increases whit each craft except for when you have 1 or 2 ingredients).


    Code (Text):


    import java.util.HashMap;

    import org.bukkit.event.EventHandler;
    import org.bukkit.event.Listener;
    import org.bukkit.event.inventory.PrepareItemCraftEvent;
    import org.bukkit.event.player.PlayerJoinEvent;
    import org.bukkit.inventory.CraftingInventory;
    import org.bukkit.inventory.ItemStack;
    public class ItemstackCrafting implements Listener {

        private int i = 0;

        @SuppressWarnings("serial")
        @EventHandler
        public void onPlayerCraftItem(PrepareItemCraftEvent e){
            if(e.getInventory().getMatrix().length < 9){
                return;
            }
            i = 0;
            while (i < 9) {
                checkCraft(CoustomItems.changeAmount(CoustomItems.rareEmeraldTier5(), 9), e.getInventory(), new HashMap<Integer, ItemStack>(){{
                    put(i, CoustomItems.rareEmeraldBlockTier5());
                    i++;
                }});
            }

        public void checkCraft(ItemStack result, CraftingInventory inv, HashMap<Integer, ItemStack> ingredients){
            ItemStack[] matrix = inv.getMatrix();
            for(int n = 0; n < 9; n++){
                if(ingredients.containsKey(n)){
                    if(matrix[n] == null
                             || !matrix[n].getItemMeta().getDisplayName().equals(ingredients.get(n).getItemMeta().getDisplayName())
                             || !matrix[n].getItemMeta().getLore().equals(ingredients.get(n).getItemMeta().getLore())){
                        return;
                    }
                } else {
                    if(matrix[n] != null){
                        return;
                    }
                }
            }
            inv.setResult(result);
        }
    }
     
    Edit 1: Rephrased myself to hopefully clarify something i thought migth be confusing.
     
    #8 drhampust, Feb 14, 2019
    Last edited: Feb 14, 2019
  9. md_5

    Administrator Developer

    The problem is you are not clearing / subtracting from the craft inventory after a successful craft.
     

Share This Page