Solved [1.10] Crafting with swords

Discussion in 'Plugin Development' started by Blackwing_Forged, Sep 27, 2016.

Thread Status:
Not open for further replies.
  1. I want to have crafting recipes be able to craft with all the types of swords, i have it so players can get a book with the lore "Sparky I" and if they craft that with any sword it sets the lore on the sword as "Sparky I". I have tried this, its probably wrong, if i could get some help that'd be great and id appreciate it, thanks.

    Code:
    public void registerCrafting()
        {
          
            ItemStack enchBook = new ItemStack(Material.BOOK);
          
            ItemMeta im1 = enchBook.getItemMeta();
            ArrayList<String> lore = (ArrayList<String>) im1.getLore();
            String lore2 = lore.toString();
            String lore3 = ChatColor.stripColor(lore2);
          
            ShapelessRecipe novice = null;
          
            List<ItemStack> swords = new ArrayList<ItemStack>();
            swords.add(new ItemStack(Material.WOOD_SWORD));
            swords.add(new ItemStack(Material.STONE_SWORD));
            swords.add(new ItemStack(Material.GOLD_SWORD));
            swords.add(new ItemStack(Material.IRON_SWORD));
            swords.add(new ItemStack(Material.DIAMOND_SWORD));
          
           
          
          
            ItemMeta im = ((ItemStack) swords).getItemMeta();
            for(ItemStack is : swords)
            {
                swords.add (is);
                novice = new ShapelessRecipe(is);
              
                novice.addIngredient(1, enchBook.getType());
                novice.addIngredient(1, is.getType());
              
                if(lore3.contains("Sparky I"))
                {
                    ArrayList<String> sparky1 = new ArrayList<String>();
                    sparky1.add(ChatColor.AQUA + "Sparky I");
                    im.setLore(sparky1);
                    Bukkit.getServer().addRecipe(novice);
                }
            }
        }
     
  2. Offline

    Zombie_Striker

    @Blackwing_Forged
    What is the issue? You never state what currently happens.

    Lore is not accounted for in recipies. You would need to do PrepareItemCraftevent and check the lore there. If the lore is correct, give the new item. If not, remove the "result" or cancel the event.
     
  3. Oh, sorry, nothing happens, when i put the book with a sword it doesn't show an output, so what things would i take out and put into the PrepareItemCraftEvent, the for statement?
     
  4. Offline

    Zombie_Striker

    @Blackwing_Forged
    Here is what you should do:
    1. In the onEnable, add the new recipe. Remember: The only thing that will be stored will be the material types and locations (if it is a shaped recipe)
    2. Create the PrepatreItemCraftEvent.
    3. Inside that event, check if the 'result' is equal to the 'result' from the recipe above.
    4. If so, check if the sword does not the lore. If it does not have the lore, set the result to null.
     
  5. Alright, before you said any of that, here's the new stuff, what happens now is when i put the book in with the sword, it gives me the sword back which is great, but it doesn't set the lore,

    Code:
    public void registerCrafting()
        {
            ItemStack enchBook = new ItemStack(Material.BOOK);
           
            ShapelessRecipe novice = null;
           
           
            swords.add(new ItemStack(Material.WOOD_SWORD));
            swords.add(new ItemStack(Material.STONE_SWORD));
            swords.add(new ItemStack(Material.GOLD_SWORD));
            swords.add(new ItemStack(Material.IRON_SWORD));
            swords.add(new ItemStack(Material.DIAMOND_SWORD));
           
          
            for(ItemStack is : swords)
            {
                //swords.add (is);
                novice = new ShapelessRecipe(is);
                novice.addIngredient(1, enchBook.getType());
                novice.addIngredient(1, is.getType());
               
                Bukkit.getServer().addRecipe(novice);
                /*if(lore3.contains("Sparky I"))
                {
                    ArrayList<String> sparky1 = new ArrayList<String>();
                    sparky1.add(ChatColor.AQUA + "Sparky I");
                    im.setLore(sparky1);
                }*/
            }
        }

    Code:
    @EventHandler
        public void testCraft(PrepareItemCraftEvent e)
        {
            ItemStack[] inv = e.getInventory().getMatrix();
            
            for(ItemStack is : inv)
            {
                ItemMeta im1 = is.getItemMeta();
                ArrayList<String> lore = (ArrayList<String>) im1.getLore();
                String lore2 = lore.toString();
                String lore3 = ChatColor.stripColor(lore2);
               
                if(is.getType() == Material.BOOK && lore3.contains("Sparky I"))
                {
                    ArrayList<ItemStack> sword = (ArrayList<ItemStack>) EnchantmentsMain.swords;
                   
                    for(ItemStack is1 : sword)
                    {
                        ItemMeta im = is1.getItemMeta();
                        ArrayList<String> sparky1 = new ArrayList<String>();
                        sparky1.add(ChatColor.AQUA + "Sparky I");
                        im.setLore(sparky1);
                        e.getInventory().setResult(is1);
                    }
                   
                }
            }
        }
     
  6. Offline

    Zombie_Striker

    This is your issue. What you are doing is saying the result should be the same as the sword "is". You have to add the lore to "is's" item meta for this line.
     
  7. @Zombie_Striker
    Thanks for that, it sets the lore as sparky on the sword now, but the issue is i can use any book for the recipe, i tried this but it still crafts the sword with any book. Also if the sword already had a custom name and item meta i want to keep that same item meta but just add the lore.


    Code:
    public void registerCrafting()
        {
            swords.add(new ItemStack(Material.WOOD_SWORD));
            swords.add(new ItemStack(Material.STONE_SWORD));
            swords.add(new ItemStack(Material.GOLD_SWORD));
            swords.add(new ItemStack(Material.IRON_SWORD));
            swords.add(new ItemStack(Material.DIAMOND_SWORD));
         
            for(ItemStack is : swords)
            {
                ItemMeta im = is.getItemMeta();
                ArrayList<String> sparky1 = new ArrayList<String>();
                sparky1.add(ChatColor.AQUA + "Sparky I");
                im.setLore(sparky1);
                is.setItemMeta(im);
             
                ShapelessRecipe novice = new ShapelessRecipe(is);
                novice.addIngredient(1, Material.BOOK);
                novice.addIngredient(1, is.getType());
                Bukkit.addRecipe(novice);
            }
        }

    Code:
    @EventHandler
        public void testCraft(PrepareItemCraftEvent e)
        {
            ArrayList<ItemStack> sword = EnchantmentsMain.swords;
            ItemStack[] inv = e.getInventory().getMatrix();
         
            if(e.getRecipe().getResult().equals(sword))
            {
                for(ItemStack is : inv)
                {
                    ItemMeta im1 = is.getItemMeta();
                    String name = im1.getDisplayName();
                    String lore3 = ChatColor.stripColor(name);
                     
                    if(!lore3.contains("Sparky I"))
                    {
                        e.getInventory().setResult(new ItemStack(Material.AIR));
                    }
                }
                 
            }
        }
     
    Last edited: Sep 29, 2016
  8. Offline

    Zombie_Striker

    This will almost never be true. Instead, use "isSimilar" instead of ".equals" and add a lore/displayname check.

    "is" can be null. Null check before you get the item meta.

    1. You are calling the display name lore. Are you sure this is what you want?
    2. Do not use ".contains" on a string in this case. Either the displayname is equal to "sparky I" or it is not. Contains loops through the whole string and sees if the displayname contains the substring. Since you only want to check if the name is "sparky I" , use equals.
     
  9. yeah i called it lore because i was originally going to check for lore but im actually checking display name but never changed the variable name. And on isSimilar my "sword" variable is and ArrayList of an ItemStack so that gives it an error since it only requires an itemstack.

    Change of plan, im making it so you put the book onto the sword in the inventory, i thought this would work but it doesn't :/ The message on the sword part doesn't even work
    Code:
    @EventHandler(priority = EventPriority.HIGHEST)
        public void testInv(InventoryClickEvent e)
        {
            if(!(e.getWhoClicked() instanceof Player))
                return;
          
            Player p = (Player)e.getWhoClicked();
            ItemStack item = e.getCurrentItem();
            ItemStack cursor = e.getCursor();
            ItemMeta metaCursor = cursor.getItemMeta();
            ItemMeta metaItem = item.getItemMeta();
          
            if(item != null)
            {
                if(item.equals(Material.WOOD_SWORD))
                {
                    p.sendMessage("Clicked sword");
                    if(cursor.equals(Material.BOOK))
                    {
                        p.sendMessage("Clicked book");
                        String name = ChatColor.stripColor(metaCursor.getDisplayName());
                        if(name.equals("Sparky I"))
                        {
                            ArrayList<String> lore = new ArrayList<String>();
                            lore.add(ChatColor.AQUA + "Sparky I");
                            metaItem.setLore(lore);
                            item.setItemMeta(metaItem);
                            p.sendMessage("Changed lore");
                        }
                    }
                }
            }
          
        }
    EDIT by Moderator: merged posts, please use the edit button instead of double posting.
     
    Last edited: Sep 30, 2016
Thread Status:
Not open for further replies.

Share This Page