Skip to content

Instantly share code, notes, and snippets.

@Mindgamesnl
Last active August 18, 2023 14:52
Show Gist options
  • Save Mindgamesnl/b8d3540742fbddbe921a4fa587fa5daf to your computer and use it in GitHub Desktop.
Save Mindgamesnl/b8d3540742fbddbe921a4fa587fa5daf to your computer and use it in GitHub Desktop.
Inventory holders, a quicky

Inventory holders can be used to register own types, handlers and data to a opened GUI for a player.

To start, we need to create our menu class that implemetns InventoryHolder and any other functions we may want. For this example, we are gonna fill the inventory and open it for player, then save the player for later ussage with our handler.

The menu

It will look something like this

import org.bukkit.Bukkit;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import org.bukkit.inventory.Inventory;
import org.bukkit.inventory.InventoryHolder;
import org.bukkit.inventory.ItemStack;

public class MyMenu implements InventoryHolder {

    private Inventory inventory = Bukkit.createInventory(this, 6 * 9, "My menu");
    private Player target;

    public MyMenu(Player player) {
        //set the player, for later used
        this.target = player;
        //fill it with one stone
        inventory.setItem(4, new ItemStack(Material.STONE, 1));
        //open the menu
        player.openInventory(inventory);
    }

    public Boolean trigger(ItemStack itemStack) {
        //check if the clicked item is stone
        if (itemStack.getType() == Material.STONE) {
            target.sendMessage("No, you may not steal my fancy stone. It is my only friend.");
            //cancel the event
            return true;
        }
        //dont cancel the event
        return false;
    }

    @Override
    public Inventory getInventory() {
        return this.inventory;
    }
}

The handler

Then, to handle it We use the bukkit event like normal, but this time we check if it is an instance of our menu, and cast/call it if this is the case.

import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.inventory.InventoryClickEvent;

public class MyListener implements Listener {

    @EventHandler
    public void onInventoryClick(InventoryClickEvent event) {
        //filter out bad events
        if (event.getInventory() == null
            || event.getCurrentItem() == null) return;

        //check if the inventory is an instance of our menu
        if (event.getInventory().getHolder() instanceof MyMenu) {
            //call teh function and hold its state
            Boolean cancel = ((MyMenu) event.getInventory().getHolder()).trigger(event.getCurrentItem());
            //set the event cancelled based on the return state
            event.setCancelled(cancel);
        }
    }

}

Opening the menu

To open the menu and register the handler, all we have to do is

new MyMenu(Bukkit.getPlayer("Mindgamesnl");

And that's all, we now have

  • a menu that builds itself
  • a menu that is linked to a player
  • one lister that handles our menu like a callback function
  • a simpler and cleaner inventory system
  • a stone block in our gui, that the player cannot interact of based on our handler

That's all folks

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment