mirror of
https://github.com/mcMMO-Dev/mcMMO.git
synced 2024-11-26 07:06:45 +01:00
Standard level scaling now mirrors RetroMode in a true 1:10 parity
This commit is contained in:
parent
33dd34931c
commit
50e4e971d9
@ -1,3 +1,11 @@
|
|||||||
|
Version 2.1.64
|
||||||
|
(API) method to get XP in FormulaManager has been renamed to getXPtoNextLevel(...), this shouldn't break anything as plugins should be using our Experience API methods instead of this
|
||||||
|
(API) Added method getLevel(Player player, PrimarySkillType primarySkillType) to ExperienceAPI.java
|
||||||
|
Corrected how Standard mode (1-100 scaling) XP to next level was calculated, it is now a true 1:10 ratio with Retro (1-1000) scale, which is how it was intended to be to begin with
|
||||||
|
|
||||||
|
NOTE: The net result of this change is it will take a bit longer to level with Standard, but it should not be a drastic change. You might not even notice it.
|
||||||
|
Standard is meant to take the same amount of time to level from levels 1-100 as it takes Retro to do 1-1000, this change corrects from errors in the code that made Standard actually take less XP than Retro despite intending for it to be a cosmetic difference in progression.
|
||||||
|
|
||||||
Version 2.1.63
|
Version 2.1.63
|
||||||
Fixed Armor Impact not scaling by skill rank
|
Fixed Armor Impact not scaling by skill rank
|
||||||
Significantly Buffed the amount of durability damage incurred by a successful Armor Impact
|
Significantly Buffed the amount of durability damage incurred by a successful Armor Impact
|
||||||
|
4
pom.xml
4
pom.xml
@ -2,7 +2,7 @@
|
|||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<groupId>com.gmail.nossr50.mcMMO</groupId>
|
<groupId>com.gmail.nossr50.mcMMO</groupId>
|
||||||
<artifactId>mcMMO</artifactId>
|
<artifactId>mcMMO</artifactId>
|
||||||
<version>2.1.63</version>
|
<version>2.1.64-SNAPSHOT</version>
|
||||||
<name>mcMMO</name>
|
<name>mcMMO</name>
|
||||||
<url>https://github.com/mcMMO-Dev/mcMMO</url>
|
<url>https://github.com/mcMMO-Dev/mcMMO</url>
|
||||||
<scm>
|
<scm>
|
||||||
@ -167,7 +167,7 @@
|
|||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.spigotmc</groupId>
|
<groupId>org.spigotmc</groupId>
|
||||||
<artifactId>spigot-api</artifactId>
|
<artifactId>spigot-api</artifactId>
|
||||||
<version>1.14.1-R0.1-SNAPSHOT</version>
|
<version>1.14.2-R0.1-SNAPSHOT</version>
|
||||||
<scope>provided</scope>
|
<scope>provided</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
|
@ -649,11 +649,28 @@ public final class ExperienceAPI {
|
|||||||
* @return the level of a given skill
|
* @return the level of a given skill
|
||||||
*
|
*
|
||||||
* @throws InvalidSkillException if the given skill is not valid
|
* @throws InvalidSkillException if the given skill is not valid
|
||||||
|
* @deprecated Use getLevel(Player player, PrimarySkillType skillType) instead
|
||||||
*/
|
*/
|
||||||
|
@Deprecated
|
||||||
public static int getLevel(Player player, String skillType) {
|
public static int getLevel(Player player, String skillType) {
|
||||||
return getPlayer(player).getSkillLevel(getSkillType(skillType));
|
return getPlayer(player).getSkillLevel(getSkillType(skillType));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the level a player has in a specific skill.
|
||||||
|
* </br>
|
||||||
|
* This function is designed for API usage.
|
||||||
|
*
|
||||||
|
* @param player The player to get the level for
|
||||||
|
* @param skillType The skill to get the level for
|
||||||
|
* @return the level of a given skill
|
||||||
|
*
|
||||||
|
* @throws InvalidSkillException if the given skill is not valid
|
||||||
|
*/
|
||||||
|
public static int getLevel(Player player, PrimarySkillType skillType) {
|
||||||
|
return getPlayer(player).getSkillLevel(skillType);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the level an offline player has in a specific skill.
|
* Get the level an offline player has in a specific skill.
|
||||||
* </br>
|
* </br>
|
||||||
@ -995,7 +1012,7 @@ public final class ExperienceAPI {
|
|||||||
* @throws InvalidFormulaTypeException if the given formulaType is not valid
|
* @throws InvalidFormulaTypeException if the given formulaType is not valid
|
||||||
*/
|
*/
|
||||||
public static int getXpNeededToLevel(int level) {
|
public static int getXpNeededToLevel(int level) {
|
||||||
return mcMMO.getFormulaManager().getCachedXpToLevel(level, ExperienceConfig.getInstance().getFormulaType());
|
return mcMMO.getFormulaManager().getXPtoNextLevel(level, ExperienceConfig.getInstance().getFormulaType());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -1009,7 +1026,7 @@ public final class ExperienceAPI {
|
|||||||
* @throws InvalidFormulaTypeException if the given formulaType is not valid
|
* @throws InvalidFormulaTypeException if the given formulaType is not valid
|
||||||
*/
|
*/
|
||||||
public static int getXpNeededToLevel(int level, String formulaType) {
|
public static int getXpNeededToLevel(int level, String formulaType) {
|
||||||
return mcMMO.getFormulaManager().getCachedXpToLevel(level, getFormulaType(formulaType));
|
return mcMMO.getFormulaManager().getXPtoNextLevel(level, getFormulaType(formulaType));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -203,7 +203,7 @@ public class Party {
|
|||||||
|
|
||||||
public int getXpToLevel() {
|
public int getXpToLevel() {
|
||||||
FormulaType formulaType = ExperienceConfig.getInstance().getFormulaType();
|
FormulaType formulaType = ExperienceConfig.getInstance().getFormulaType();
|
||||||
return (mcMMO.getFormulaManager().getCachedXpToLevel(level, formulaType)) * (getOnlineMembers().size() + Config.getInstance().getPartyXpCurveMultiplier());
|
return (mcMMO.getFormulaManager().getXPtoNextLevel(level, formulaType)) * (getOnlineMembers().size() + Config.getInstance().getPartyXpCurveMultiplier());
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getXpToLevelPercentage() {
|
public String getXpToLevelPercentage() {
|
||||||
|
@ -397,7 +397,7 @@ public class PlayerProfile {
|
|||||||
int level = (ExperienceConfig.getInstance().getCumulativeCurveEnabled()) ? UserManager.getPlayer(playerName).getPowerLevel() : skills.get(primarySkillType);
|
int level = (ExperienceConfig.getInstance().getCumulativeCurveEnabled()) ? UserManager.getPlayer(playerName).getPowerLevel() : skills.get(primarySkillType);
|
||||||
FormulaType formulaType = ExperienceConfig.getInstance().getFormulaType();
|
FormulaType formulaType = ExperienceConfig.getInstance().getFormulaType();
|
||||||
|
|
||||||
return mcMMO.getFormulaManager().getCachedXpToLevel(level, formulaType);
|
return mcMMO.getFormulaManager().getXPtoNextLevel(level, formulaType);
|
||||||
}
|
}
|
||||||
|
|
||||||
private int getChildSkillLevel(PrimarySkillType primarySkillType) {
|
private int getChildSkillLevel(PrimarySkillType primarySkillType) {
|
||||||
|
@ -66,7 +66,7 @@ public enum PrimarySkillType {
|
|||||||
ImmutableList.of(SubSkillType.WOODCUTTING_LEAF_BLOWER, SubSkillType.WOODCUTTING_TREE_FELLER, SubSkillType.WOODCUTTING_HARVEST_LUMBER));
|
ImmutableList.of(SubSkillType.WOODCUTTING_LEAF_BLOWER, SubSkillType.WOODCUTTING_TREE_FELLER, SubSkillType.WOODCUTTING_HARVEST_LUMBER));
|
||||||
|
|
||||||
private Class<? extends SkillManager> managerClass;
|
private Class<? extends SkillManager> managerClass;
|
||||||
private Color runescapeColor;
|
private Color skillColor;
|
||||||
private SuperAbilityType ability;
|
private SuperAbilityType ability;
|
||||||
private ToolType tool;
|
private ToolType tool;
|
||||||
private List<SubSkillType> subSkillTypes;
|
private List<SubSkillType> subSkillTypes;
|
||||||
@ -110,13 +110,13 @@ public enum PrimarySkillType {
|
|||||||
NON_CHILD_SKILLS = ImmutableList.copyOf(nonChildSkills);
|
NON_CHILD_SKILLS = ImmutableList.copyOf(nonChildSkills);
|
||||||
}
|
}
|
||||||
|
|
||||||
private PrimarySkillType(Class<? extends SkillManager> managerClass, Color runescapeColor, List<SubSkillType> subSkillTypes) {
|
private PrimarySkillType(Class<? extends SkillManager> managerClass, Color skillColor, List<SubSkillType> subSkillTypes) {
|
||||||
this(managerClass, runescapeColor, null, null, subSkillTypes);
|
this(managerClass, skillColor, null, null, subSkillTypes);
|
||||||
}
|
}
|
||||||
|
|
||||||
private PrimarySkillType(Class<? extends SkillManager> managerClass, Color runescapeColor, SuperAbilityType ability, ToolType tool, List<SubSkillType> subSkillTypes) {
|
private PrimarySkillType(Class<? extends SkillManager> managerClass, Color skillColor, SuperAbilityType ability, ToolType tool, List<SubSkillType> subSkillTypes) {
|
||||||
this.managerClass = managerClass;
|
this.managerClass = managerClass;
|
||||||
this.runescapeColor = runescapeColor;
|
this.skillColor = skillColor;
|
||||||
this.ability = ability;
|
this.ability = ability;
|
||||||
this.tool = tool;
|
this.tool = tool;
|
||||||
this.subSkillTypes = subSkillTypes;
|
this.subSkillTypes = subSkillTypes;
|
||||||
@ -243,7 +243,7 @@ public enum PrimarySkillType {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* public void celebrateLevelUp(Player player) {
|
/* public void celebrateLevelUp(Player player) {
|
||||||
ParticleEffectUtils.fireworkParticleShower(player, runescapeColor);
|
ParticleEffectUtils.fireworkParticleShower(player, skillColor);
|
||||||
}*/
|
}*/
|
||||||
|
|
||||||
public boolean shouldProcess(Entity target) {
|
public boolean shouldProcess(Entity target) {
|
||||||
|
@ -15,8 +15,10 @@ public class FormulaManager {
|
|||||||
private static File formulaFile = new File(mcMMO.getFlatFileDirectory() + "formula.yml");
|
private static File formulaFile = new File(mcMMO.getFlatFileDirectory() + "formula.yml");
|
||||||
|
|
||||||
// Experience needed to reach a level, cached values to improve conversion speed
|
// Experience needed to reach a level, cached values to improve conversion speed
|
||||||
private final Map<Integer, Integer> experienceNeededLinear = new HashMap<Integer, Integer>();
|
private Map<Integer, Integer> experienceNeededRetroLinear;
|
||||||
private final Map<Integer, Integer> experienceNeededExponential = new HashMap<Integer, Integer>();
|
private Map<Integer, Integer> experienceNeededStandardLinear;
|
||||||
|
private Map<Integer, Integer> experienceNeededRetroExponential;
|
||||||
|
private Map<Integer, Integer> experienceNeededStandardExponential;
|
||||||
|
|
||||||
private FormulaType previousFormula;
|
private FormulaType previousFormula;
|
||||||
|
|
||||||
@ -26,9 +28,20 @@ public class FormulaManager {
|
|||||||
public FormulaManager() {
|
public FormulaManager() {
|
||||||
/* Setting for Classic Mode (Scales a lot of stuff up by * 10) */
|
/* Setting for Classic Mode (Scales a lot of stuff up by * 10) */
|
||||||
retroModeEnabled = Config.getInstance().getIsRetroMode();
|
retroModeEnabled = Config.getInstance().getIsRetroMode();
|
||||||
|
initExperienceNeededMaps();
|
||||||
loadFormula();
|
loadFormula();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initialize maps used for XP to next level
|
||||||
|
*/
|
||||||
|
private void initExperienceNeededMaps() {
|
||||||
|
experienceNeededRetroLinear = new HashMap<>();
|
||||||
|
experienceNeededRetroExponential = new HashMap<>();
|
||||||
|
experienceNeededStandardLinear = new HashMap<>();
|
||||||
|
experienceNeededStandardExponential = new HashMap<>();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the formula type that was used before converting
|
* Get the formula type that was used before converting
|
||||||
*
|
*
|
||||||
@ -60,7 +73,7 @@ public class FormulaManager {
|
|||||||
int totalXP = 0;
|
int totalXP = 0;
|
||||||
|
|
||||||
for (int level = 0; level < skillLevel; level++) {
|
for (int level = 0; level < skillLevel; level++) {
|
||||||
totalXP += getCachedXpToLevel(level, previousFormula);
|
totalXP += getXPtoNextLevel(level, previousFormula);
|
||||||
}
|
}
|
||||||
|
|
||||||
totalXP += skillXPLevel;
|
totalXP += skillXPLevel;
|
||||||
@ -83,7 +96,7 @@ public class FormulaManager {
|
|||||||
int maxLevel = Config.getInstance().getLevelCap(primarySkillType);
|
int maxLevel = Config.getInstance().getLevelCap(primarySkillType);
|
||||||
|
|
||||||
while (experience > 0 && newLevel < maxLevel) {
|
while (experience > 0 && newLevel < maxLevel) {
|
||||||
int experienceToNextLevel = getCachedXpToLevel(newLevel, formulaType);
|
int experienceToNextLevel = getXPtoNextLevel(newLevel, formulaType);
|
||||||
|
|
||||||
if (experience - experienceToNextLevel < 0) {
|
if (experience - experienceToNextLevel < 0) {
|
||||||
remainder = experience;
|
remainder = experience;
|
||||||
@ -106,42 +119,97 @@ public class FormulaManager {
|
|||||||
* @param formulaType The {@link FormulaType} used
|
* @param formulaType The {@link FormulaType} used
|
||||||
* @return amount of experience needed to reach next level
|
* @return amount of experience needed to reach next level
|
||||||
*/
|
*/
|
||||||
public int getCachedXpToLevel(int level, FormulaType formulaType) {
|
public int getXPtoNextLevel(int level, FormulaType formulaType) {
|
||||||
int experience;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Retro mode XP requirements are the default requirements
|
* Retro mode XP requirements are the default requirements
|
||||||
* Standard mode XP requirements are multiplied by a factor of 10
|
* Standard mode XP requirements are multiplied by a factor of 10
|
||||||
*/
|
*/
|
||||||
int xpNeededMultiplier = retroModeEnabled ? 1 : 10;
|
|
||||||
|
|
||||||
|
//TODO: When the heck is Unknown used?
|
||||||
if (formulaType == FormulaType.UNKNOWN) {
|
if (formulaType == FormulaType.UNKNOWN) {
|
||||||
formulaType = FormulaType.LINEAR;
|
formulaType = FormulaType.LINEAR;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return processXPToNextLevel(level, formulaType);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the value of XP needed for the next level based on the level Scaling, the level, and the formula type
|
||||||
|
* @param level target level
|
||||||
|
* @param formulaType target formulaType
|
||||||
|
*/
|
||||||
|
private int processXPToNextLevel(int level, FormulaType formulaType) {
|
||||||
|
if(mcMMO.isRetroModeEnabled())
|
||||||
|
{
|
||||||
|
return processXPRetroToNextLevel(level, formulaType);
|
||||||
|
} else {
|
||||||
|
return processStandardXPToNextLevel(level, formulaType);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calculate the XP needed for the next level for the linear formula for Standard scaling (1-100)
|
||||||
|
* @param level target level
|
||||||
|
* @return raw xp needed to reach the next level
|
||||||
|
*/
|
||||||
|
private int processStandardXPToNextLevel(int level, FormulaType formulaType) {
|
||||||
|
Map<Integer, Integer> experienceMapRef = formulaType == FormulaType.LINEAR ? experienceNeededStandardLinear : experienceNeededStandardExponential;
|
||||||
|
|
||||||
|
if(!experienceMapRef.containsKey(level)) {
|
||||||
|
int experienceSum = 0;
|
||||||
|
int retroIndex = (level * 10) + 1;
|
||||||
|
|
||||||
|
//Sum the range of levels in Retro that this Standard level would represent
|
||||||
|
for(int x = retroIndex; x < (retroIndex + 10); x++) {
|
||||||
|
//calculateXPNeeded doesn't cache results so we use that instead of invoking the Retro XP methods to avoid memory bloat
|
||||||
|
experienceSum += calculateXPNeeded(x, formulaType);
|
||||||
|
}
|
||||||
|
|
||||||
|
experienceMapRef.put(level, experienceSum);
|
||||||
|
}
|
||||||
|
|
||||||
|
return experienceMapRef.get(level);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calculates the XP to next level for Retro Mode scaling
|
||||||
|
* Results are cached to reduce needless operations
|
||||||
|
* @param level target level
|
||||||
|
* @param formulaType target formula type
|
||||||
|
* @return raw xp needed to reach the next level based on formula type
|
||||||
|
*/
|
||||||
|
private int processXPRetroToNextLevel(int level, FormulaType formulaType) {
|
||||||
|
Map<Integer, Integer> experienceMapRef = formulaType == FormulaType.LINEAR ? experienceNeededRetroLinear : experienceNeededRetroExponential;
|
||||||
|
|
||||||
|
if (!experienceMapRef.containsKey(level)) {
|
||||||
|
int experience = calculateXPNeeded(level, FormulaType.LINEAR);
|
||||||
|
experienceMapRef.put(level, experience);
|
||||||
|
}
|
||||||
|
|
||||||
|
return experienceMapRef.get(level);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Does the actual math to get the XP needed for a level in RetroMode scaling
|
||||||
|
* Standard uses a sum of RetroMode XP needed levels for its own thing, so it uses this too
|
||||||
|
* @param level target level
|
||||||
|
* @param formulaType target formulatype
|
||||||
|
* @return the raw XP needed for the next level based on formula type
|
||||||
|
*/
|
||||||
|
private int calculateXPNeeded(int level, FormulaType formulaType) {
|
||||||
int base = ExperienceConfig.getInstance().getBase(formulaType);
|
int base = ExperienceConfig.getInstance().getBase(formulaType);
|
||||||
double multiplier = ExperienceConfig.getInstance().getMultiplier(formulaType);
|
double multiplier = ExperienceConfig.getInstance().getMultiplier(formulaType);
|
||||||
double exponent = ExperienceConfig.getInstance().getExponent(formulaType);
|
|
||||||
|
|
||||||
switch (formulaType) {
|
switch(formulaType) {
|
||||||
case LINEAR:
|
case LINEAR:
|
||||||
if (!experienceNeededLinear.containsKey(level)) {
|
return (int) Math.floor(base + level * multiplier);
|
||||||
experience = (int) Math.floor( xpNeededMultiplier * (base + level * multiplier));
|
|
||||||
experienceNeededLinear.put(level, experience);
|
|
||||||
}
|
|
||||||
|
|
||||||
return experienceNeededLinear.get(level);
|
|
||||||
|
|
||||||
case EXPONENTIAL:
|
case EXPONENTIAL:
|
||||||
if (!experienceNeededExponential.containsKey(level)) {
|
double exponent = ExperienceConfig.getInstance().getExponent(formulaType);
|
||||||
experience = (int) Math.floor( xpNeededMultiplier * (multiplier * Math.pow(level, exponent) + base));
|
return (int) Math.floor(multiplier * Math.pow(level, exponent) + base);
|
||||||
experienceNeededExponential.put(level, experience);
|
|
||||||
}
|
|
||||||
|
|
||||||
return experienceNeededExponential.get(level);
|
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return 0;
|
//TODO: Should never be called
|
||||||
|
mcMMO.p.getLogger().severe("Invalid formula specified for calculation, defaulting to Linear");
|
||||||
|
return calculateXPNeeded(level, FormulaType.LINEAR);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user