diff --git a/core/src/main/java/co/aikar/commands/ACFUtil.java b/core/src/main/java/co/aikar/commands/ACFUtil.java index 97c3f6d5..3e6cc071 100644 --- a/core/src/main/java/co/aikar/commands/ACFUtil.java +++ b/core/src/main/java/co/aikar/commands/ACFUtil.java @@ -435,24 +435,22 @@ public final class ACFUtil { public static Number parseNumber(String num, boolean suffixes) { - double mod = 1; - if (suffixes) { - switch (num.charAt(num.length()-1)) { - case 'M': - case 'm': - mod = 1000000D; - num = num.substring(0, num.length()-1); - break; - case 'K': - case 'k': - mod = 1000D; - num = num.substring(0, num.length()-1); - } - } + ApplyModifierToNumber applyModifierToNumber = new ApplyModifierToNumber(num, suffixes).invoke(); + num = applyModifierToNumber.getNum(); + double mod = applyModifierToNumber.getMod(); return Double.parseDouble(num) * mod; } + public static BigDecimal parseBigNumber(String num, boolean suffixes) { + ApplyModifierToNumber applyModifierToNumber = new ApplyModifierToNumber(num, suffixes).invoke(); + num = applyModifierToNumber.getNum(); + double mod = applyModifierToNumber.getMod(); + + BigDecimal big = new BigDecimal(num); + return (mod == 1) ? big : big.multiply(new BigDecimal(mod)); + } + public static boolean hasIntersection(Collection list1, Collection list2) { for (T t : list1) { if (list2.contains(t)) { @@ -578,4 +576,40 @@ public final class ACFUtil { throw (T) t; } + private static class ApplyModifierToNumber { + private String num; + private boolean suffixes; + private double mod; + + public ApplyModifierToNumber(String num, boolean suffixes) { + this.num = num; + this.suffixes = suffixes; + } + + public String getNum() { + return num; + } + + public double getMod() { + return mod; + } + + public ApplyModifierToNumber invoke() { + mod = 1; + if (suffixes) { + switch (num.charAt(num.length()-1)) { + case 'M': + case 'm': + mod = 1000000D; + num = num.substring(0, num.length()-1); + break; + case 'K': + case 'k': + mod = 1000D; + num = num.substring(0, num.length()-1); + } + } + return this; + } + } } diff --git a/core/src/main/java/co/aikar/commands/CommandContexts.java b/core/src/main/java/co/aikar/commands/CommandContexts.java index 85b25241..7a0407ce 100644 --- a/core/src/main/java/co/aikar/commands/CommandContexts.java +++ b/core/src/main/java/co/aikar/commands/CommandContexts.java @@ -33,6 +33,8 @@ import co.aikar.commands.contexts.OptionalContextResolver; import com.google.common.collect.Maps; import org.jetbrains.annotations.NotNull; +import java.math.BigDecimal; +import java.math.BigInteger; import java.util.List; import java.util.Map; @@ -120,6 +122,20 @@ public class CommandContexts { + try { + return ACFUtil.parseBigNumber(c.popFirstArg(), c.hasFlag("suffixes")); + } catch (NumberFormatException e) { + throw new InvalidCommandArgument(MessageKeys.MUST_BE_A_NUMBER); + } + }); + registerContext(BigInteger.class, (c) -> { + try { + return ACFUtil.parseBigNumber(c.popFirstArg(), c.hasFlag("suffixes")).toBigIntegerExact(); + } catch (NumberFormatException e) { + throw new InvalidCommandArgument(MessageKeys.MUST_BE_A_NUMBER); + } + }); registerContext(Boolean.class, (c) -> ACFUtil.isTruthy(c.popFirstArg())); registerContext(boolean.class, (c) -> ACFUtil.isTruthy(c.popFirstArg())); registerContext(char.class, c -> { @@ -230,6 +246,7 @@ public class CommandContexts