How to restrict natural exp level up?

Discussion in 'Plugin Development' started by CrazyYoungBro, Jun 17, 2016.

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

    I Al Istannen

    @CrazyYoungBro
    Just replace your public static variable with a private static one. Then provide a getter for it. This pattern is called Singelton, look it up :)

    Proceed at your own risk. This code is inefficient and not properly documentated. (open)

    Code:
    package me.ialistannen.inventory_profiles.util;
    
    import org.bukkit.entity.Player;
    
    /**
    * Some function for Experience things
    */
    public class ExpUtil {
    
        /**
         * @param level The level
         * @return The total exp needed to get to the level
         */
        public static int getXpForLevel(int level) {
            int totalXp = 0;
            for(int i = 1; i <= level; i++) {   
                totalXp += getXpIncreaseAtLevel(i);
            }
           
            return totalXp;
        }
       
        /**
         * @param level The Level
         * @return The xp increase at the given level
         */
        public static int getXpIncreaseAtLevel(int level) {
            int xpPerLevel = 0;
            for(int i = 1; i <= level; i++) {
                if(i == 1) {
                    xpPerLevel += 7;
                }
                else if(i <= 16) {
                    xpPerLevel += 2;
                }
                else if(i <= 31) {
                    xpPerLevel += 5;
                }
                else {
                    xpPerLevel += 9;
                }
            }
           
            return xpPerLevel;       
        }
       
        /**
         * @param level The level the user is at
         * @param progress The Progress he has made
         * @return The Extra xp that is
         */
        public static int getExtraXp(int level, float progress) {
            return Math.round(getXpIncreaseAtLevel(level) * progress);
        }
       
        /**
         * @param level The Level of the player
         * @param progress The extra progress
         * @return The total Experience for the player
         */
        public static int getTotalXp(int level, float progress) {
            return getXpForLevel(level) + getExtraXp(level, progress);
        }
       
        /**
         * @param xp The Experience of the player
         * @return The level the player has.
         */
        public static int getLevel(int xp) {
            int level = 1;
            for(; xp >= getXpIncreaseAtLevel(level) ; level++) {
                xp -= getXpIncreaseAtLevel(level);
            }
            return level - 1;
        }
       
        /**
         * @param totalXp The Total xp (level + extra)
         * @param level The level the player is at
         * @return The Extra percentage the player is at
         */
        public static float getExtraXpForLevel(int totalXp, int level) {
            totalXp -= getXpForLevel(level);
            return (float) totalXp / getXpIncreaseAtLevel(level);
        }
       
        /**
         * Sets the Player's experience to the specified amount
         *
         * @param player The player to set the xp for
         * @param xp The xp to set it to
         */
        public static void setXp(Player player, int xp) {
            player.setLevel(getLevel(xp));
            player.setExp(getExtraXpForLevel(xp, getLevel(xp)));
        }
     
  2. Offline

    CrazyYoungBro

    I am somewhat understanding it but not completely. I understand what code you have written but how to implement it in my listener class.
    I got the singleton stuff but the problem is my instance is of my main class and is in my listener class. Therefore, how to use singleton now?
     
    Last edited: Jun 20, 2016
  3. Offline

    I Al Istannen

    @CrazyYoungBro
    If you have the getInstance, just use it instead of the "Mainclass.main" you currently have. Just use "MainClass.getInstance()" instead.

    The player will level up automatically.
    To check how far they have come, either directly check the player#getXp() which will return a float between 0 and (nearly) 1.

    The other way, which shows the progress in absolute numbers, would be using the class I posted and using "getExtraXp(player level, player#getXp()" to get how much their partly filled xp bar is and then use "getXpIncreaseAtLevel(player level)" to get the xp they need for levelling up.

    Don't really know what you mean with this:
    If you just want to give him the next level, set his level (Player#setLevel()).
     
  4. Offline

    CrazyYoungBro

    Thanks.
    I meant on how to check if the player has enough exp to level up. So that he cannot just do /level CrazyYoungBro 100 without having enough exp to level up.
     
  5. Offline

    I Al Istannen

    @CrazyYoungBro
    Well, that depends on how you manage their xp.
    I think you or I have a major misunderstanding here.

    If you use the Bukkit methods and reset the xpGainEvent, the player will NEVER be able to level up. You would need to save the xp they gained, before resetting them in the xpGainEvent. Then use the class I posted and the "getLevel" and "getExtra" to get the level and percentage they should be.
     
  6. Offline

    CrazyYoungBro

    Ok Thanks. But can you give the exact name of the xpGainEvent? Also, how to cancel the ExpBottleEvent?
     
    Last edited: Jun 21, 2016
  7. Offline

    I Al Istannen

Thread Status:
Not open for further replies.

Share This Page