Creating a custom creative InventoryView

Discussion in 'Plugin Development' started by chrisXgames, Jul 6, 2014.

Thread Status:
Not open for further replies.
  1. Offline

    chrisXgames

    I am making a technology plugin in which I need players to choose items. I was going to do this using a Creative Inventory.

    How could I create a Custom Creative InventoryView which uses a filled Creative Inventory view for the top and a small inventory on the bottom. I don't want the bottom Inventory to be the players Inventory. Here is what I have so far:

    Code:java
    1. public class SelectorInventoryView extends InventoryView{
    2.  
    3. private Inventory top, bottom;
    4. private Player player;
    5.  
    6. public SelectorInventoryView(Player player){
    7. this.player = player;
    8. this.top = Bukkit.createInventory(player, InventoryType.CREATIVE);
    9. this.bottom = Bukkit.createInventory(player, 9);
    10. this.bottom.setMaxStackSize(1);
    11. }
    12.  
    13. @Override
    14. public Inventory getBottomInventory() {
    15. return bottom;
    16. }
    17.  
    18. @Override
    19. public HumanEntity getPlayer() {
    20. return player;
    21. }
    22.  
    23. @Override
    24. public Inventory getTopInventory() {
    25. return top;
    26. }
    27.  
    28. @Override
    29. public InventoryType getType() {
    30. return InventoryType.CREATIVE;
    31. }
    32.  
    33. }


    Any help would be appreciated :)
     
  2. Offline

    xTigerRebornx

  3. Offline

    chrisXgames

  4. Offline

    xTigerRebornx

    chrisXgames Could implement a "Page" system, where you have ItemStacks to go forward and back a page, then utilize this to spread the items across multiple chest inventories.
     
  5. Offline

    chrisXgames

    That is great advice. Is it possible to get all Items and all valid MaterialData for that Item?
     
  6. Offline

    xTigerRebornx

  7. Offline

    chrisXgames

  8. Offline

    xTigerRebornx

    chrisXgames Deprecated doesn't mean broken. Though, you could create new instances of the MaterialData class (and its subclasases) using the getData() method and calling newInstance() on it (or create a method to pair the class with a new MaterialData object). Though, that 2nd thing is all getNewData() does, except with the deprecated data value.
     
  9. Offline

    chrisXgames


    Now I get a lengthy error.

    [14:03:20] [Server thread/ERROR]: null
    org.bukkit.command.CommandException: Unhandled exception executing command 'tech' in plugin TechCraft v0.1
    at org.bukkit.command.PluginCommand.execute(PluginCommand.java:46) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at org.bukkit.command.SimpleCommandMap.dispatch(SimpleCommandMap.java:180) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at org.bukkit.craftbukkit.v1_7_R3.CraftServer.dispatchCommand(CraftServer.java:701) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.PlayerConnection.handleCommand(PlayerConnection.java:956) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.PlayerConnection.a(PlayerConnection.java:817) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.PacketPlayInChat.a(PacketPlayInChat.java:28) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.PacketPlayInChat.handle(PacketPlayInChat.java:47) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.NetworkManager.a(NetworkManager.java:157) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.ServerConnection.c(SourceFile:134) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.MinecraftServer.v(MinecraftServer.java:667) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.DedicatedServer.v(DedicatedServer.java:260) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.MinecraftServer.u(MinecraftServer.java:558) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.MinecraftServer.run(MinecraftServer.java:469) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.ThreadServerApplication.run(SourceFile:628) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    Caused by: java.lang.ArrayIndexOutOfBoundsException: 27
    at org.bukkit.craftbukkit.v1_7_R3.inventory.CraftInventoryCustom$MinecraftInventory.getItem(CraftInventoryCustom.java:70) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.Slot.getItem(Slot.java:43) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.Container.a(Container.java:66) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.Container.addSlotListener(Container.java:57) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at org.bukkit.craftbukkit.v1_7_R3.entity.CraftHumanEntity.openInventory(CraftHumanEntity.java:319) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at us.chrisix.techcraft.core.selector.Selector.open(Selector.java:21) ~[?:?]
    at us.chrisix.techcraft.TechCraft.onCommand(TechCraft.java:45) ~[?:?]
    at org.bukkit.command.PluginCommand.execute(PluginCommand.java:44) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    ... 13 more
    [14:03:20] [Server thread/ERROR]: Encountered an unexpected exception
    net.minecraft.server.v1_7_R3.ReportedException: Ticking entity
    at net.minecraft.server.v1_7_R3.MinecraftServer.v(MinecraftServer.java:653) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.DedicatedServer.v(DedicatedServer.java:260) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.MinecraftServer.u(MinecraftServer.java:558) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.MinecraftServer.run(MinecraftServer.java:469) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.ThreadServerApplication.run(SourceFile:628) [craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    Caused by: java.lang.ArrayIndexOutOfBoundsException: 27
    at org.bukkit.craftbukkit.v1_7_R3.inventory.CraftInventoryCustom$MinecraftInventory.getItem(CraftInventoryCustom.java:70) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.Slot.getItem(Slot.java:43) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.Container.b(Container.java:74) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.EntityPlayer.h(EntityPlayer.java:175) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.World.entityJoinedWorld(World.java:1421) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.World.playerJoinedWorld(World.java:1402) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.World.tickEntities(World.java:1290) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.WorldServer.tickEntities(WorldServer.java:481) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    at net.minecraft.server.v1_7_R3.MinecraftServer.v(MinecraftServer.java:649) ~[craftbukkit.jar:git-Bukkit-1.7.9-R0.1-10-g8688bd4-b3092jnks]
    ...

    The line of code us.chrisix.techcraft.core.selector.Selector.open(Selector.java:21) is when the player opens my custom inventory view.

    Custom Inventory View
    Code:java
    1. public class SelectorInventoryView extends InventoryView{
    2.  
    3. private Selector selector;
    4. private int tab;
    5. private Inventory inventory;
    6.  
    7. public SelectorInventoryView(Selector selector, int tab){
    8. this.selector = selector;
    9. this.tab = tab;
    10. this.inventory = selector.getTabs()[tab].toInventory(selector.getPlayer());
    11. }
    12.  
    13. public SelectorInventoryView next(){
    14. if(tab + 1 == selector.getTabs().length){
    15. return null;
    16. }
    17. else{
    18. return new SelectorInventoryView(selector, tab + 1);
    19. }
    20. }
    21.  
    22. @Override
    23. public Inventory getBottomInventory() {
    24. return selector.getSelected();
    25. }
    26.  
    27. @Override
    28. public HumanEntity getPlayer() {
    29. return selector.getPlayer();
    30. }
    31.  
    32. @Override
    33. public Inventory getTopInventory() {
    34. return inventory;
    35. }
    36.  
    37. @Override
    38. public InventoryType getType() {
    39. return InventoryType.CHEST;
    40. }
    41.  
    42. }


    Selector Class
    Code:java
    1. public class Selector {
    2.  
    3. private Player player;
    4. private Tab[] tabs;
    5. private Inventory selected;
    6.  
    7. public Selector(Player player, Tab[] tabs){
    8. this.player = player;
    9. this.tabs = tabs;
    10. this.selected = Bukkit.createInventory(player, 27);
    11. }
    12.  
    13. public void open(){
    14. SelectorInventoryView view = new SelectorInventoryView(this, 0);
    15. player.openInventory(view);
    16. }
    17.  
    18. // Getters
    19. public Player getPlayer(){ return player; }
    20. public Tab[] getTabs(){ return tabs; }
    21. public Inventory getSelected(){ return selected; }
    22.  
    23. }
     
  10. Offline

    xTigerRebornx

  11. Offline

    chrisXgames


    I've created InventoryViews in the past for some of my other plugins. So I thought it would be simple to just create my own inventory view to show the tab items on top, and the selected items on the bottom. But what really happens is that the player inventory is on the bottom and throws the error. I looked at what needs to be part of the InventoryView before and I can't find that I'm doing anything wrong.

    What other way would there be to achieve what I want to happen?

    onCommand Code.
    Code:java
    1. public boolean onCommand(CommandSender sender, Command command, String label, String args[]){
    2. if(sender instanceof Player && command.getName().equalsIgnoreCase("tech")){
    3. Player player = (Player) sender;
    4. if(args[0].equalsIgnoreCase("seltest")){
    5. Selector select = new Selector(player, new Tab[]{
    6. new Tab("test", new ItemStack[]{
    7. new ItemStack(Material.WOOD)
    8. } )
    9. } );
    10.  
    11. select.open();
    12. }
    13. }
    14. return false;
    15. }
     
  12. Offline

    xTigerRebornx

    chrisXgames Ah, I see what you are trying to do. Give me a few min., Ill do some testing to see how to accomplish this.
    May I see this method?:
    Code:
    selector.getTabs()[tab].toInventory(selector.getPlayer());
     
  13. Offline

    chrisXgames


    Here is my Tab class.

    Code:java
    1. public class Tab {
    2.  
    3. private String name;
    4. private ItemStack[] context;
    5.  
    6. public Tab(String name, ItemStack[] context){
    7. this.name = name;
    8. this.context = context;
    9. }
    10.  
    11. public Inventory toInventory(){
    12. Inventory inv = Bukkit.createInventory(null, 54);
    13. for(int i = 0; i < context.length && i < 54; i++){
    14. inv.setItem(i, context);
    15. }
    16.  
    17. return inv;
    18. }
    19.  
    20. public String getName(){ return name; }
    21.  
    22. public ItemStack[] getContext(){
    23. return context;
    24. }
    25.  
    26. }


    Thanks for helping me out with this :)
     
  14. Offline

    xTigerRebornx

    chrisXgames The InventoryViews you've made in the past, did those work properly? If so, may you show some of them? From the testing i've done, it seems to "break" the connection of the Player, kicking them, but assuming they are still online on the server (as the warning on InventoryView suggested) From what I've gathered, the InventoryView's getType() may be causing the problem. It may be that the client (or server) doesn't know how to handle the InventoryView. Further testing, I was able to open a "proper" inventory view (Chest up top, Player inventory at bottom), it threw many errors with clicks and was generally buggy. It may just be that there isn't much support for custom InventoryViews in Bukkit.
     
  15. Offline

    chrisXgames

    My other InventoryViews had the proper way, Chest on Top and Player on the bottom. They didn't work with Shift-Clicks very well. But the rest worked fine. So yes there might not be support for a such a view that I am looking for.

    Did you have another idea on how I could go through tabs and select Items?
     
  16. Offline

    xTigerRebornx

    chrisXgames Use just a regular Inventory (54 size), structured something like:

    Code:
    <------->
    xxxxxxxxx
    xxxxxxxxx
    xxxxxxxxx
    xxxxxxxxx
    ---------
    Where < is Back a page (if at page one, either isn't there, sends to last page, or whatever you want), > is Next page (similar to what happens at page one, except with the last page either leading to first or just not being there), - being a filler item to represent a blank slot (could be air, or something like black stained glass, piston head, etc), and x being your ItemStack's.
    Could mess around with this style, and create something you'd like.

    As for InventoryViews, they seem buggy when you try and create your own custom views. Drag clicks break, Internal server errors, etc.
     
  17. Offline

    chrisXgames

    How could I implement that? I was thinking that using Commands was too complicated. And I believe there is no way to create custom buttons.
     
  18. Offline

    xTigerRebornx

    chrisXgames Simply use Bukkit#createInventory() to make the 54-slot inventory, and have each of the "buttons" be an ItemStack of specific type and metadata, such as making the "Back" Red Stained Glass with the name "&cBack", then use listeners for the various events fired involving Inventories.
     
  19. Offline

    chrisXgames

    Ohh, I was just going to have them go through each tab. But that way works better :) Thank you for all your help.
     
Thread Status:
Not open for further replies.

Share This Page