[Easy] [No-API] Setting Up Custom Tab-Completion

Discussion in 'Resources' started by TheHandfish, Aug 5, 2014.

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

    TheHandfish

    Hello,

    Awhile ago I was looking for a way to use auto-tab-complete for one of my plugins. This is the function that allows a user who presses "tab" in the space of an argument to cycle through various argument options. This is a useful feature, because for example, someone who wants to quickly /kick a player needs only do "/kick (tab)" and then see the player's name, and auto-complete it. If you remember only a part of the player's name, you can write the part you remember and then press tab, and it will complete the name.

    Today I'm going to show you how to use the tab auto-complete-function for your plugin. NOTE: I will not be posting straight-out code snippets. Rather, I'll be using pictures. This is so that you actually write the thing out, not just copy my code. :p I want you to learn it, and it's all very easy so it shouldn't be necessary for me to post the code. Here is a list of what you'll need to know before you start the tutorial:

    Required & suggested knowledge:

    Basics of Java & Bukkit
    • How to make a command
    • Accessing variables from other classes you've made

    Let's jump right in, shall we? To begin with, I'll need you to have made a command or have one in mind. I myself am going to be using three separate classes:

    • Our pre-made Command class
    • Our pre-made Main class
    • A TabCompleter-implementing class

    Step 1: Making our TabCompleter Class

    Let's start our TabCompleter-implementing class. Make a new class in whichever package you choose named "[Command]TabCompleter." For example, I named mine: "ConstructTabCompleter"

    A new class will be created. You'll want the first line (excluding the imports & package declarations at the very top), the one that would normally say "public class ConstructTabCompleter" to look like this:

    [​IMG]

    By implementing Bukkit's TabCompleter, we are enabling the option to create our own custom tab completions.

    Depending on your IDE, it may ask you to "implement all abstract methods." You can go ahead and do that, or write it out yourself by doing what I am doing.

    Step 2: Writing up the onTabComplete method

    Within the class you've just created, make the next line be "@Override." This is a sign for the our IDE's compiler. It lets it know that you're overriding the method of a parent class, in this case, TabCompleter's class. Next we need to make the onTabComplete() method we'll be using beneath our @Override annotation.

    The inTabComplete() method is pretty much build like the onCommand() method, just with a different method name and return value. Since you've written a command class beforehand, you'll know what it should look like. Here is what I wrote:

    [​IMG]

    Change the parameter names as you'd like. I just wrote them this way for clarity. Any java coder should know, however, that it doesn't really matter what the variable names you use are as long as they don't use any funny characters or spaces.

    Right now, if you press tab, nothing different would happen than before you wrote this. This is because I am returning "null." But what we want to do is, in certain cases, return a List<String> for the command. Now, this part is pretty much up to you. You can set it so in certain cases, with certain arguments, it will return a list. The only difficult part for you would be getting a list to return. Since I can't read your minds, I'll show you an example of what I did for my code.

    [​IMG]
    [​IMG]

    A lot of these methods are accessed from other classes, but I'll tell you the basics.

    1. I check if: a) The command is "construct", b) the first argument is "build" c) there are two arguments, but the second one is empty, and d) the sender is a player (although I only needed to do this because of one of my personal methods).

    2. I access, from a config, a list of strings.

    3. I make a new list, and loop through the Config list to see if the player is allowed to build this site. If it is allowed to be used, it is added to the list (newList).

    4. Finally, I return newList.

    Step 3: Finishing up & setting the command's completer

    One last step. Because right now, the whole thing would not work. Why? Well, for the same reason why you need to set a command executor for a command, you must set a tab completer for a command, too.

    Go to your Main class (or stay in it if you were silly enough to stuff this entire thing in your Main class) and add this line:

    [​IMG]

    Of course, you must change "Construct" and "ConstructTabCompleter" to whatever your command and class names are. After this you are done! Go and try it out:

    [​IMG]

    Thank you for reading my tutorial. Please let me know if there is something that needs improvement (as it is my first here on Bukkit.org), and tell me if you found it helpful. :) Thanks!

    ~ TheHandfish
     
    ProCZ, zThana, Ross Gosling and 9 others like this.
  2. Offline

    Phasesaber

    Great tutorial.
    What IDE are you using?
     
  3. Offline

    Stealth2800

    Very informative and well written, good job!
     
  4. Offline

    TheHandfish

    Thank you both. And I am using NetBeans. :)
     
  5. Offline

    mazentheamazin

    * That's actually a requirement to make plugins.
     
    ZodiacTheories likes this.
  6. Offline

    AdamQpzm

    Unless you're going to politely ask them to leave, or threaten them, not sure why you'd use /msg :p

    Also, as a side note, since you never do anything with the player, there's no real need to check if it's a player or assign it to a variable.
     
  7. Offline

    TheHandfish

    Oops lol. At first I was using /msg as an example, then I realized not all servers may use that, so I tried a more universal example and forgot to update everything.

    Actually, I use the player in getAllowedBuildSite();

    Not really. You could technically make the whole thing inside one class. It's unorganized and hard to navigate, but it does work technically. Maybe I should state that you access them from your own classes.
     
  8. Offline

    mazentheamazin

    TheHandfish
    Let me clarify, one should have basic knowledge of Java before making plugins; I consider it a requirement. This includes the ability to access methods from other classes using instances or static where appropriate.
     
    AdamQpzm likes this.
  9. Offline

    TheHandfish

    ^ Fair enough. Revised.
     
  10. Offline

    AdamQpzm

  11. Offline

    KingFaris11

    Thank you for this! I'm actually implementing this in my mini-game plugin since I have a LOT of subcommands for one command - and the Owner of the server'll get confused, this'll help him a lot!

    One thing though...
    Code:
    List<String> empty = new ArrayList<>();
    list = empty;
    
    [​IMG]

    Just use:
    Code:
    if (list == null) list = new ArrayList<String>();
    
     
  12. Offline

    RenditionsRule

    "ono phail" -OneOfHand'sPlugins 2k14
     
    TheHandfish likes this.
  13. Offline

    TheHandfish

    Glad you examined the artistic source (kidding) of my old plugin, WhymCraft. Metalmikey002. :p
     
  14. Offline

    unon1100

    Remember: If you ever want to, you can still spawn things and such with <tab>. Trolls are fun.

    Moderator: /kick someha<tab> *spawns 50 creepers at moderator's location*
     
    Stealth2800 and TheHandfish like this.
  15. Offline

    RenditionsRule

    TheHandfish Dayum handeh. I'm using this in one of my plugins.
     
    TheHandfish likes this.
Thread Status:
Not open for further replies.

Share This Page