Create a custom player.class , implement Player

Discussion in 'Spigot Plugin Development' started by Kwizzy, Apr 21, 2016.

  1. Version : 1.9
    API : Spigot
    IDE: Intellij Idea
    Problem : I want to create a custom class of player for put my own method with the bukkit default methods.
    Research : https://bukkit.org/threads/implement-player.48984/ , https://bukkit.org/threads/extending-player.66702/
    Error :
    Caused by: java.lang.ClassCastException

    Code :
    I've a simple class who implement Player http://hastebin.com/foqazeqaqo.java .

    I've try to create the interface Player : http://hastebin.com/jolemoqopo.java (same error)



    [​IMG]


    I'ts possible to have a " custom" class of " Player " ?

    On bukkit.org he speak to re create a CraftPlayer ...

    If a gentleman can help me :D

    Thanks you
     
    • Friendly Friendly x 1
  2. You can, yes. I think so at least. You'll have to implement a lot of overiding methods. Then you can create your own.
     
  3. If you want s custom player class, I wouldn't implement Player. Instead just store the player variable in that class. Also, you can't cast a Player to a CustomPlayer so that's why there's not much of a point in implementing it. You can just do CustomPlayer#getPlayer()
     
    • Agree Agree x 3
  4. Yeah. Just create a new object, and store a Player variable inside that object, and manipulate it.
     
  5. What I did when I was making something like this is like the 2 fellas above me said.

    Pass a Player in your constructor, save it as an object and create a getter. I named mine getBukkitPlayer()
     
  6. No because i want the bukkit method too.
    I know what do you mean and it's really boring to do custom.getPlayer(p) because you need to check if it's not null and if you want to use bukkit method you need to use p and not custom.

    So i think there is a way to do that but idk how to do it.
     
  7. If you manage your custom classes properly you shoulnd't have to do anymore null checks than normal.
     
    • Like Like x 2
    • Agree Agree x 1
    • Funny Funny x 1
  8. It's not the best ever way i prefer.
     
  9. btw, great post, OP. Really nicely formatted and lots of information. Most users could learn a thing or two from you :)

    EDIT:
    Ah, alright. I can't help you then.
     
    • Agree Agree x 3
  10. Do a wrapper (as earlier posts suggested) instead of extending the Player class. Much easier to maintain.

    If you want the Bukkit methods. You can either make them and redirect them to your player instance or implement the Player class and handle all of the methods.

    EDIT: You shouldn't need to null check, unless you mess up really hard.
     
    • Like Like x 1
  11. Something like that : http://hastebin.com/urocevacus.avrasm ?
    (Old code)

    Thank's i'm come of a french forum so i've c/p the help post form ;)
     
  12. That's ok. THOUGH I highly recommend separating your lists of the player instance and your player wrapper.

    You should make a separate manager class for your CustomPlayer instances, example here:
    https://gist.github.com/Hexragon/20b566a044def425a7a49d2c10b9dd19
    You can see here that I create an instance every time the player logs on and removing the reference when they log off. When I create the custom instance, I immediately store the Player in a final constant. So as long as you do this, and you are able to get the CustomPlayer's instance, you have no need for a null check.

    Here's what a CustomPlayer instance would look like:
    https://gist.github.com/Hexragon/3cb56c7ee4562dddf721999937818a5d

     
    • Agree Agree x 1
  13. Firestar311

    Firestar311 Previously ThomasRW
    Supporter

    I have a custom plugin for my server. I have created a custom player that implements Player. And pass a player object in the constructor. And then have a global class variable in the class.
    Code (Text):
    public CustomPlayer(Player player) {
            this.player = player;
    }
    This allows me to also create anything else, like a file to store some data like homes, toggles etc... And then I just use my player object for all the methods from the Player Interface so for example unless I want to change how it works I just do this.
    Code (Text):
    @Override
        public void closeInventory() {
            player.closeInventory();
        }

        @Override
        public Inventory getEnderChest() {
            return player.getEnderChest();
        }
    This is more work, but also allows more control as well. You can't cast it but You can use it like this (From event)
    Code (Text):
    CustomPlayer cp = new CustomPlayer(e.getPlayer())
     
  14. Implement Player so you can pass the CustomPlayer instance as an argument when they require a Player.

    However, doing that will increase code size by a measurable amount, so you should make your wrapped Player public and use methods like this : customPlayerInstance.player.sendMessage("hi there");
     
    #15 Hexragon, Apr 21, 2016
    Last edited: Apr 21, 2016
  15. Have fun implementing probably more than 50 methods.
     
    • Agree Agree x 1
    • Funny Funny x 1
  16. Which is why I added the after note.

    Also back to the original point. @Kwizzy don't try to implement every method of Player as it's redundant and inefficient, implement ones that you really need (sendMessage), all others you should refer to the wrapped Player instance.
     
    • Like Like x 1
  17. I've found :

    Code (Text):
    public class WOLPlayer extends CraftPlayer implements Listener
    {
        public WOLPlayer(Player player) {
            super((CraftServer) player.getServer(), ((CraftPlayer) player).getHandle());
        }
    }
     
    I can use every methods of the Player and custom method !

    Have fun :D
     
    • Funny Funny x 1
  18. NO NO NO DO NOT EXTEND CRAFTPLAYER what have you done you evil thing

    It's NMS specific and will crash in an unelegant way in other server versions. Don't extend CraftPlayer as it is extremely bad practice.

    Please read the earlier suggestion I told you, (tldr make Player instance public, access player methods through customPlayer.player#methodhere)
     
    #19 Hexragon, Apr 21, 2016
    Last edited: Apr 21, 2016
    • Agree Agree x 1
  19. I'know what i'm doing, it's for me, i know the risk :)