Store object in NBT?

Discussion in 'Spigot Plugin Development' started by SirLich, Apr 21, 2017.

  1. I am making some tools for myself to make chest GUI's easier to write/create/handle.

    My first thought was to attach an NBTTag (I am using an API) to the item (all items are STONE_AXE). Then whenever a stone axe is clicked, run a method like this:
    Code (Text):

    String a = event.getItem.getNBTStringAction;
    If a == rules:
         //do actions relating to this button
    If a == example:
         //do actions relating to this button
    If a == levels:
         //do actions relating to this button
    If a == staff:
         //do actions relating to this button
    If a == main_menu:
         //do actions relating to this button
     
    I realized though that is a functional way of accomplishing this task. So I started out to make an object oriented version of it.

    MY QUESTION: Can I attach objects as an NBTTag, or if not how should I go about writing an intelligent easy-to-maintain chest gui?
     
  2. you can attach custom NBTags.
     
  3. I personally prefer two own written classes, which handles everything gui-related. One of them is the Gui Object and the other is like a "Main-GUI" Object which handles Inventoryclicks and executes the wanted functions.
    Per Gui i use a Map<Integer, String> where the int is the Inventory Slot and the String the assigned Function.
     
  4. I don't think this is relevant to what they need.
     
  5. I think it is.

    In general i see 3 types of handling GUIs:
    1. Set up special items by unique names & lore and check for those at inventory click
    2. Like @ExoBiTe said, set up a map by slots + Actions and check if the specific slot of a GUI inventory is clicked (new problem: how to make sure it really is the GUI inv... maybe unique inv titles...)
    3. Make it like @SirLich suggested by custom NBT tags
    My personal opinion:
    First option might be the badest choice, because checking items by their name + lore isn't really save. Even essentials could create those.
    The second solution is ways better, i mostly did it like this already. But it's quite tricky to check if the inv is your GUI, e.g. if each player needs his own GUI. Mostly comparing inv titles is the only way, and this isn't really save... Because you can modify inv titles ingame, too (e.g. of chests).

    All in all i prefer the third solution, because it's the safest and most structured. I already did a project with many GUIs and menu navigations using this method. But there are several things to consider and it's quite tricky until it runs well.
    Tricky parts of this method:
    • Each GUI item needs to contain a unique action key (which is e.g. a NBTTagString on the items tag)
    • You need to hook safely into NMS to be version-independent
    Big advantages of this method:
    • You don't need to check the inventories, only the items
    • GUI-items containing such a key doesn't differ to normal items (at least the client sees no difference), because those custom tags won't be displayed
      So you can even use a normal stone block item without any name or something... it safely will be recognized by the not-seeable custom action key
    • Custom NBTTagStrings on items were the most safe method to make a item unique, because most people doesn't even know about it and those, who know about them mostly don't use them
    One last Thing: Please include you plugin name into your NBTTagString KEY-NAME. So even if other plugins use custom item tags, you'll be safe. Example: {id:"minecraft:stone",Count:1b,Damage:0s,tag:{MyPluginName_GUI-Action:"#ExampleAction"}}

    If you need further support, i could post some code from my prior project if necessary.