diff options
author | Roman / Linnea Gräf <roman.graef@gmail.com> | 2023-03-04 02:54:50 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2023-03-04 12:54:50 +1100 |
commit | 5dd063fbba6bde64806a7620541dc2d9bdf42871 (patch) | |
tree | 01aee1a743a32a0b2546513c59a43559ce3085fe | |
parent | db86c98e0c72b18663ef26cd46cef7d53c1d6414 (diff) | |
download | NotEnoughUpdates-5dd063fbba6bde64806a7620541dc2d9bdf42871.tar.gz NotEnoughUpdates-5dd063fbba6bde64806a7620541dc2d9bdf42871.tar.bz2 NotEnoughUpdates-5dd063fbba6bde64806a7620541dc2d9bdf42871.zip |
Replace all commands in NEU with a brigadier implementation (#599)
60 files changed, 2591 insertions, 3015 deletions
diff --git a/build.gradle.kts b/build.gradle.kts index e41aa513..aec078d3 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -135,19 +135,21 @@ dependencies { kotlinDependencies(kotlin("stdlib")) compileOnly(ksp(project(":annotations"))!!) - compileOnly("org.projectlombok:lombok:1.18.24") + compileOnly("org.projectlombok:lombok:1.18.24") annotationProcessor("org.projectlombok:lombok:1.18.24") "oneconfigAnnotationProcessor"("org.projectlombok:lombok:1.18.24") + shadowImplementation("com.mojang:brigadier:1.0.18") + shadowImplementation("org.spongepowered:mixin:0.7.11-SNAPSHOT") { isTransitive = false // Dependencies of mixin are already bundled by minecraft } - annotationProcessor("org.spongepowered:mixin:0.8.4-SNAPSHOT") + annotationProcessor("net.fabricmc:sponge-mixin:0.11.4+mixin.0.8.5") @Suppress("VulnerableLibrariesLocal") shadowApi("info.bliki.wiki:bliki-core:3.1.0") testImplementation("org.junit.jupiter:junit-jupiter:5.9.2") - testAnnotationProcessor("org.spongepowered:mixin:0.8.4-SNAPSHOT") + testAnnotationProcessor("net.fabricmc:sponge-mixin:0.11.4+mixin.0.8.5") // modImplementation("io.github.notenoughupdates:MoulConfig:0.0.1") devEnv("me.djtheredstoner:DevAuth-forge-legacy:1.1.0") @@ -233,6 +235,7 @@ tasks.shadowJar { from(kotlinDependencyCollectionJar) dependsOn(kotlinDependencyCollectionJar) fun relocate(name: String) = relocate(name, "io.github.moulberry.notenoughupdates.deps.$name") + relocate("com.mojang.brigadier") } tasks.assemble.get().dependsOn(remapJar) diff --git a/src/main/java/io/github/moulberry/notenoughupdates/NotEnoughUpdates.java b/src/main/java/io/github/moulberry/notenoughupdates/NotEnoughUpdates.java index 25d1002a..7f0136ee 100644 --- a/src/main/java/io/github/moulberry/notenoughupdates/NotEnoughUpdates.java +++ b/src/main/java/io/github/moulberry/notenoughupdates/NotEnoughUpdates.java @@ -25,7 +25,6 @@ import com.google.gson.GsonBuilder; import com.google.gson.JsonObject; import io.github.moulberry.notenoughupdates.autosubscribe.AutoLoad; import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe; -import io.github.moulberry.notenoughupdates.commands.Commands; import io.github.moulberry.notenoughupdates.core.BackgroundBlur; import io.github.moulberry.notenoughupdates.cosmetics.ShaderManager; import io.github.moulberry.notenoughupdates.listener.ChatListener; @@ -52,6 +51,7 @@ import io.github.moulberry.notenoughupdates.overlays.OverlayManager; import io.github.moulberry.notenoughupdates.profileviewer.ProfileViewer; import io.github.moulberry.notenoughupdates.recipes.RecipeGenerator; import io.github.moulberry.notenoughupdates.util.Utils; +import io.github.moulberry.notenoughupdates.util.brigadier.BrigadierRoot; import net.minecraft.client.Minecraft; import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.gui.GuiScreen; @@ -158,7 +158,6 @@ public class NotEnoughUpdates { public Navigation navigation = new Navigation(this); public GuiScreen openGui = null; public long lastOpenedGui = 0; - public Commands commands; public boolean packDevEnabled = false; public Color[][] colourMap = null; public AutoUpdater autoUpdater = new AutoUpdater(this); @@ -281,7 +280,7 @@ public class NotEnoughUpdates { manager.registerReloadListener(new CustomBlockSounds.ReloaderListener()); } - this.commands = new Commands(); + BrigadierRoot.INSTANCE.updateHooks(); BackgroundBlur.registerListener(); diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/Commands.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/Commands.java deleted file mode 100644 index 91365cd1..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/Commands.java +++ /dev/null @@ -1,107 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.dev.DevTestCommand; -import io.github.moulberry.notenoughupdates.commands.dev.DiagCommand; -import io.github.moulberry.notenoughupdates.commands.dev.DungeonWinTestCommand; -import io.github.moulberry.notenoughupdates.commands.dev.EnableStorageCommand; -import io.github.moulberry.notenoughupdates.commands.dev.NullzeeSphereCommand; -import io.github.moulberry.notenoughupdates.commands.dev.PackDevCommand; -import io.github.moulberry.notenoughupdates.commands.dev.ReloadRepoCommand; -import io.github.moulberry.notenoughupdates.commands.dev.ResetRepoCommand; -import io.github.moulberry.notenoughupdates.commands.dev.StatsCommand; -import io.github.moulberry.notenoughupdates.commands.dungeon.DhCommand; -import io.github.moulberry.notenoughupdates.commands.dungeon.DnCommand; -import io.github.moulberry.notenoughupdates.commands.dungeon.JoinDungeonCommand; -import io.github.moulberry.notenoughupdates.commands.dungeon.MapCommand; -import io.github.moulberry.notenoughupdates.commands.help.FeaturesCommand; -import io.github.moulberry.notenoughupdates.commands.help.HelpCommand; -import io.github.moulberry.notenoughupdates.commands.help.LinksCommand; -import io.github.moulberry.notenoughupdates.commands.help.SettingsCommand; -import io.github.moulberry.notenoughupdates.commands.help.StorageViewerWhyCommand; -import io.github.moulberry.notenoughupdates.commands.misc.AhCommand; -import io.github.moulberry.notenoughupdates.commands.misc.CalculatorCommand; -import io.github.moulberry.notenoughupdates.commands.misc.CalendarCommand; -import io.github.moulberry.notenoughupdates.commands.misc.CosmeticsCommand; -import io.github.moulberry.notenoughupdates.commands.misc.CustomizeCommand; -import io.github.moulberry.notenoughupdates.commands.misc.PronounsCommand; -import io.github.moulberry.notenoughupdates.commands.misc.UpdateCommand; -import io.github.moulberry.notenoughupdates.commands.profile.CataCommand; -import io.github.moulberry.notenoughupdates.commands.profile.PeekCommand; -import io.github.moulberry.notenoughupdates.commands.profile.PvCommand; -import io.github.moulberry.notenoughupdates.commands.profile.ViewProfileCommand; -import io.github.moulberry.notenoughupdates.miscfeatures.FairySouls; -import io.github.moulberry.notenoughupdates.miscgui.GuiEnchantColour; -import io.github.moulberry.notenoughupdates.miscgui.GuiInvButtonEditor; -import io.github.moulberry.notenoughupdates.miscgui.NEUOverlayPlacements; -import net.minecraftforge.client.ClientCommandHandler; -import net.minecraftforge.fml.common.Loader; - -public class Commands { - public Commands() { - - // Help Commands - ClientCommandHandler.instance.registerCommand(new LinksCommand()); - ClientCommandHandler.instance.registerCommand(new HelpCommand()); - ClientCommandHandler.instance.registerCommand(new StorageViewerWhyCommand()); - ClientCommandHandler.instance.registerCommand(new FeaturesCommand()); - ClientCommandHandler.instance.registerCommand(new SettingsCommand()); - - // Dev Commands - ClientCommandHandler.instance.registerCommand(new PackDevCommand()); - ClientCommandHandler.instance.registerCommand(new DungeonWinTestCommand()); - ClientCommandHandler.instance.registerCommand(new StatsCommand()); - ClientCommandHandler.instance.registerCommand(new DevTestCommand()); - ClientCommandHandler.instance.registerCommand(new NullzeeSphereCommand()); - ClientCommandHandler.instance.registerCommand(new DiagCommand()); - ClientCommandHandler.instance.registerCommand(new ReloadRepoCommand()); - ClientCommandHandler.instance.registerCommand(new ResetRepoCommand()); - ClientCommandHandler.instance.registerCommand(new EnableStorageCommand()); - - // Profile Commands - ClientCommandHandler.instance.registerCommand(new PeekCommand()); - ClientCommandHandler.instance.registerCommand(new ViewProfileCommand()); - ClientCommandHandler.instance.registerCommand(new PvCommand()); - if (!Loader.isModLoaded("skyblockextras")) ClientCommandHandler.instance.registerCommand(new CataCommand()); - - // Dungeon Commands - ClientCommandHandler.instance.registerCommand(new MapCommand()); - ClientCommandHandler.instance.registerCommand(new JoinDungeonCommand()); - ClientCommandHandler.instance.registerCommand(new DnCommand()); - ClientCommandHandler.instance.registerCommand(new DhCommand()); - - // Misc Commands - ClientCommandHandler.instance.registerCommand(new CosmeticsCommand()); - ClientCommandHandler.instance.registerCommand(new CustomizeCommand()); - ClientCommandHandler.instance.registerCommand(new ScreenCommand("neubuttons", GuiInvButtonEditor::new)); - ClientCommandHandler.instance.registerCommand(new ScreenCommand("neuec", GuiEnchantColour::new)); - ClientCommandHandler.instance.registerCommand(new ScreenCommand("neuoverlay", NEUOverlayPlacements::new)); - ClientCommandHandler.instance.registerCommand(new AhCommand()); - ClientCommandHandler.instance.registerCommand(new CalculatorCommand()); - ClientCommandHandler.instance.registerCommand(new CalendarCommand()); - ClientCommandHandler.instance.registerCommand(new UpdateCommand(NotEnoughUpdates.INSTANCE)); - ClientCommandHandler.instance.registerCommand(new PronounsCommand()); - - // Fairy Soul Commands - ClientCommandHandler.instance.registerCommand(new FairySouls.FairySoulsCommand()); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/EntityViewerCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/EntityViewerCommand.java deleted file mode 100644 index e3738661..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/EntityViewerCommand.java +++ /dev/null @@ -1,100 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands; - -import com.google.common.collect.Lists; -import io.github.moulberry.notenoughupdates.miscfeatures.entityviewer.EntityViewer; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.entity.EntityLivingBase; -import net.minecraft.event.ClickEvent; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.ChatStyle; -import net.minecraft.util.EnumChatFormatting; -import net.minecraft.util.ResourceLocation; -import net.minecraftforge.common.MinecraftForge; -import net.minecraftforge.fml.common.eventhandler.SubscribeEvent; -import net.minecraftforge.fml.common.gameevent.TickEvent; - -import java.util.Arrays; -import java.util.List; -import java.util.Queue; -import java.util.concurrent.ConcurrentLinkedDeque; - -public class EntityViewerCommand extends ClientCommandBase { - public EntityViewerCommand() { - super("neushowentity"); - MinecraftForge.EVENT_BUS.register(this); - } - - @Override - public List<String> getCommandAliases() { - return Lists.newArrayList("neuentityviewer"); - } - - @Override - public String getCommandUsage(ICommandSender sender) { - return EnumChatFormatting.RED + "Use /neushowentity list"; - } - - public void showUsage(ICommandSender sender) { - sender.addChatMessage(new ChatComponentText(getCommandUsage(sender))); - } - - private final Queue<EntityViewer> queuedGUIS = new ConcurrentLinkedDeque<>(); - - @SubscribeEvent - public void onTick(TickEvent event) { - if (Minecraft.getMinecraft().currentScreen == null) { - EntityViewer poll = queuedGUIS.poll(); - if (poll == null) return; - Minecraft.getMinecraft().displayGuiScreen(poll); - } - } - - @Override - public void processCommand(ICommandSender sender, String[] strings) throws CommandException { - if (strings.length == 0) { - showUsage(sender); - return; - } - if (strings[0].equals("list")) { - for (String label : EntityViewer.validEntities.keySet()) { - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.BLUE + " " + label) - .setChatStyle(new ChatStyle().setChatClickEvent( - new ClickEvent(ClickEvent.Action.SUGGEST_COMMAND, "/neuentityviewer " + label)))); - } - return; - } - EntityLivingBase entityLivingBase; - if (strings[0].startsWith("@")) { - ResourceLocation resourceLocation = new ResourceLocation(strings[0].substring(1)); - entityLivingBase = EntityViewer.constructEntity(resourceLocation); - } else { - entityLivingBase = EntityViewer.constructEntity(strings[0], Arrays.copyOfRange(strings, 1, strings.length)); - } - if (entityLivingBase == null) { - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Could not create that entity")); - return; - } - queuedGUIS.add(new EntityViewer(strings[0], entityLivingBase)); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/ScreenCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/ScreenCommand.java deleted file mode 100644 index 1b90e5df..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/ScreenCommand.java +++ /dev/null @@ -1,45 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; - -public class ScreenCommand extends ClientCommandBase { - - private final ScreenOpener opener; - - protected ScreenCommand(String name, ScreenOpener opener) { - super(name); - this.opener = opener; - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - NotEnoughUpdates.INSTANCE.openGui = opener.open(); - } - - @FunctionalInterface - public interface ScreenOpener { - GuiScreen open(); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DevTestCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DevTestCommand.java deleted file mode 100644 index 1a1400ab..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DevTestCommand.java +++ /dev/null @@ -1,292 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import com.google.gson.JsonArray; -import com.google.gson.JsonElement; -import com.google.gson.JsonObject; -import io.github.moulberry.notenoughupdates.BuildFlags; -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.core.config.GuiPositionEditor; -import io.github.moulberry.notenoughupdates.core.util.MiscUtils; -import io.github.moulberry.notenoughupdates.miscfeatures.FishingHelper; -import io.github.moulberry.notenoughupdates.miscfeatures.customblockzones.CustomBiomes; -import io.github.moulberry.notenoughupdates.miscfeatures.customblockzones.LocationChangeEvent; -import io.github.moulberry.notenoughupdates.miscfeatures.customblockzones.SpecialBlockZone; -import io.github.moulberry.notenoughupdates.miscgui.GuiPriceGraph; -import io.github.moulberry.notenoughupdates.miscgui.minionhelper.MinionHelperManager; -import io.github.moulberry.notenoughupdates.util.ApiCache; -import io.github.moulberry.notenoughupdates.util.PronounDB; -import io.github.moulberry.notenoughupdates.util.SBInfo; -import io.github.moulberry.notenoughupdates.util.TabListUtils; -import io.github.moulberry.notenoughupdates.util.Utils; -import io.github.moulberry.notenoughupdates.util.hypixelapi.ProfileCollectionInfo; -import lombok.var; -import net.minecraft.client.Minecraft; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.launchwrapper.Launch; -import net.minecraft.util.BlockPos; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; -import net.minecraft.util.EnumParticleTypes; -import net.minecraftforge.common.MinecraftForge; - -import java.util.Arrays; -import java.util.List; -import java.util.stream.Collectors; - -public class DevTestCommand extends ClientCommandBase { - - private static final List<String> DEV_TESTERS = - Arrays.asList( - "d0e05de7-6067-454d-beae-c6d19d886191", // moulberry - "66502b40-6ac1-4d33-950d-3df110297aab", // lucycoconut - "a5761ff3-c710-4cab-b4f4-3e7f017a8dbf", // ironm00n - "5d5c548a-790c-4fc8-bd8f-d25b04857f44", // ariyio - "53924f1a-87e6-4709-8e53-f1c7d13dc239", // throwpo - "d3cb85e2-3075-48a1-b213-a9bfb62360c1", // lrg89 - "0b4d470f-f2fb-4874-9334-1eaef8ba4804", // dediamondpro - "ebb28704-ed85-43a6-9e24-2fe9883df9c2", // lulonaut - "698e199d-6bd1-4b10-ab0c-52fedd1460dc", // craftyoldminer - "8a9f1841-48e9-48ed-b14f-76a124e6c9df", // eisengolem - "a7d6b3f1-8425-48e5-8acc-9a38ab9b86f7", // whalker - "0ce87d5a-fa5f-4619-ae78-872d9c5e07fe", // ascynx - "a049a538-4dd8-43f8-87d5-03f09d48b4dc", // egirlefe - "7a9dc802-d401-4d7d-93c0-8dd1bc98c70d", // efefury - "bb855349-dfd8-4125-a750-5fc2cf543ad5" // hannibal2 - ); - - private static final String[] DEV_FAIL_STRINGS = { - "No.", - "I said no.", - "You aren't allowed to use this.", - "Are you sure you want to use this? Type 'Yes' in chat.", - "Are you sure you want to use this? Type 'Yes' in chat.", - "Lmao you thought", - "Ok please stop", - "What do you want from me?", - "This command almost certainly does nothing useful for you", - "Ok, this is the last message, after this it will repeat", - "No.", - "I said no.", - "Dammit. I thought that would work. Uhh...", - "\u00a7dFrom \u00a7c[ADMIN] Minikloon\u00a77: If you use that command again, I'll have to ban you", - "", - "Ok, this is actually the last message, use the command again and you'll crash I promise" - }; - private int devFailIndex = 0; - - public static int testValue = 0; - - public DevTestCommand() { - super("neudevtest"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (!DEV_TESTERS.contains(Minecraft.getMinecraft().thePlayer.getUniqueID().toString()) - && !(boolean) Launch.blackboard.get("fml.deobfuscatedEnvironment")) { - if (devFailIndex >= DEV_FAIL_STRINGS.length) { - throw new Error("L") { - @Override - public void printStackTrace() { - throw new Error("L"); - } - }; - } - if (devFailIndex == DEV_FAIL_STRINGS.length - 2) { - devFailIndex++; - - ChatComponentText component = new ChatComponentText("\u00a7cYou are permanently banned from this server!"); - component.appendText("\n"); - component.appendText("\n\u00a77Reason: \u00a7rI told you not to run the command - Moulberry"); - component.appendText("\n\u00a77Find out more: \u00a7b\u00a7nhttps://www.hypixel.net/appeal"); - component.appendText("\n"); - component.appendText("\n\u00a77Ban ID: \u00a7r#49871982"); - component.appendText("\n\u00a77Sharing your Ban ID may affect the processing of your appeal!"); - Minecraft.getMinecraft().getNetHandler().getNetworkManager().closeChannel(component); - return; - } - Utils.addChatMessage(EnumChatFormatting.RED + DEV_FAIL_STRINGS[devFailIndex++]); - return; - } - if (args.length == 1 && args[0].equalsIgnoreCase("dumpapihistogram")) { - synchronized (ApiCache.INSTANCE) { - Utils.addChatMessage("§e[NEU] API Request Histogram"); - Utils.addChatMessage("§e[NEU] §bClass Name§e: §aCached§e/§cNonCached§e/§dTotal"); - ApiCache.INSTANCE.getHistogramTotalRequests().forEach((className, totalRequests) -> { - var nonCachedRequests = ApiCache.INSTANCE.getHistogramNonCachedRequests().getOrDefault(className, 0); - var cachedRequests = totalRequests - nonCachedRequests; - Utils.addChatMessage( - String.format( - "§e[NEU] §b%s §a%d§e/§c%d§e/§d%d", - className, - cachedRequests, - nonCachedRequests, - totalRequests - )); - }); - } - } - if (args.length == 1 && args[0].equalsIgnoreCase("testprofile")) { - NotEnoughUpdates.INSTANCE.manager.apiUtils.newHypixelApiRequest("skyblock/profiles") - .queryArgument( - "uuid", - "" + Minecraft.getMinecraft().thePlayer.getUniqueID() - ) - .requestJson() - .thenApply(jsonObject -> { - JsonArray profiles = jsonObject.get("profiles").getAsJsonArray(); - JsonObject cp = null; - for (JsonElement profile : profiles) { - JsonObject asJsonObject = profile.getAsJsonObject(); - if ((asJsonObject.has("selected") && - asJsonObject.get("selected").getAsBoolean()) || cp == null) { - cp = asJsonObject; - } - } - return cp; - }) - .thenCompose(obj -> ProfileCollectionInfo.getCollectionData( - obj, - Minecraft.getMinecraft().thePlayer.getUniqueID().toString() - )) - .thenAccept(it -> - Utils.addChatMessage("Response: " + it)); - } - if (args.length >= 1 && args[0].equalsIgnoreCase("profileinfo")) { - String currentProfile = SBInfo.getInstance().currentProfile; - SBInfo.Gamemode gamemode = SBInfo.getInstance().getGamemodeForProfile(currentProfile); - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.GOLD + - "You are on Profile " + - currentProfile + - " with the mode " + - gamemode)); - } - if (args.length >= 1 && args[0].equalsIgnoreCase("buildflags")) { - Minecraft.getMinecraft().thePlayer.addChatMessage(new ChatComponentText( - "BuildFlags: \n" + - BuildFlags.getAllFlags().entrySet().stream() - .map(it -> " + " + it.getKey() + " - " + it.getValue()) - .collect(Collectors.joining("\n")))); - return; - } - if (args.length >= 1 && args[0].equalsIgnoreCase("exteditor")) { - if (args.length > 1) { - NotEnoughUpdates.INSTANCE.config.hidden.externalEditor = String.join( - " ", - Arrays.copyOfRange(args, 1, args.length) - ); - } - Utils.addChatMessage( - "§e[NEU] §fYour external editor is: §Z" + NotEnoughUpdates.INSTANCE.config.hidden.externalEditor); - return; - } - if (args.length >= 1 && args[0].equalsIgnoreCase("pricetest")) { - if (args.length == 1) { - NotEnoughUpdates.INSTANCE.manager.auctionManager.updateBazaar(); - } else { - NotEnoughUpdates.INSTANCE.openGui = new GuiPriceGraph(args[1]); - } - } - if (args.length == 1 && args[0].equalsIgnoreCase("zone")) { - BlockPos target = Minecraft.getMinecraft().objectMouseOver.getBlockPos(); - if (target == null) target = Minecraft.getMinecraft().thePlayer.getPosition(); - SpecialBlockZone zone = CustomBiomes.INSTANCE.getSpecialZone(target); - Arrays.asList( - new ChatComponentText("Showing Zone Info for: " + target), - new ChatComponentText("Zone: " + (zone != null ? zone.name() : "null")), - new ChatComponentText("Location: " + SBInfo.getInstance().getLocation()), - new ChatComponentText("Biome: " + CustomBiomes.INSTANCE.getCustomBiome(target)) - ).forEach(Minecraft.getMinecraft().thePlayer::addChatMessage); - MinecraftForge.EVENT_BUS.post(new LocationChangeEvent(SBInfo.getInstance().getLocation(), SBInfo - .getInstance() - .getLocation())); - } - if (args.length == 1 && args[0].equalsIgnoreCase("positiontest")) { - NotEnoughUpdates.INSTANCE.openGui = new GuiPositionEditor(); - return; - } - - if (args.length == 2 && args[0].equalsIgnoreCase("pt")) { - FishingHelper.type = EnumParticleTypes.valueOf(args[1]); - return; - } - if (args.length == 1 && args[0].equalsIgnoreCase("dev")) { - NotEnoughUpdates.INSTANCE.config.hidden.dev = !NotEnoughUpdates.INSTANCE.config.hidden.dev; - Utils.addChatMessage( - "§e[NEU] Dev mode " + (NotEnoughUpdates.INSTANCE.config.hidden.dev ? "§aenabled" : "§cdisabled")); - return; - } - if (args.length == 1 && args[0].equalsIgnoreCase("saveconfig")) { - NotEnoughUpdates.INSTANCE.saveConfig(); - return; - } - if (args.length == 1 && args[0].equalsIgnoreCase("searchmode")) { - NotEnoughUpdates.INSTANCE.config.hidden.firstTimeSearchFocus = true; - Utils.addChatMessage(EnumChatFormatting.AQUA + "I would never search"); - return; - } - if (args.length == 1 && args[0].equalsIgnoreCase("bluehair")) { - PronounDB.test(); - return; - } - if (args.length == 2 && args[0].equalsIgnoreCase("openGui")) { - try { - NotEnoughUpdates.INSTANCE.openGui = (GuiScreen) Class.forName(args[1]).newInstance(); - Utils.addChatMessage("Opening gui: " + NotEnoughUpdates.INSTANCE.openGui); - } catch (InstantiationException | IllegalAccessException | ClassNotFoundException | ClassCastException e) { - e.printStackTrace(); - Utils.addChatMessage("Failed to open this GUI."); - } - } - if (args.length == 1 && args[0].equalsIgnoreCase("center")) { - double x = Math.floor(Minecraft.getMinecraft().thePlayer.posX) + 0.5f; - double z = Math.floor(Minecraft.getMinecraft().thePlayer.posZ) + 0.5f; - Minecraft.getMinecraft().thePlayer.setPosition(x, Minecraft.getMinecraft().thePlayer.posY, z); - } - if (args.length >= 1 && args[0].equalsIgnoreCase("minion")) { - MinionHelperManager.getInstance().handleCommand(args); - } - if (args.length == 1 && args[0].equalsIgnoreCase("copytablist")) { - StringBuilder builder = new StringBuilder(); - for (String name : TabListUtils.getTabList()) { - builder.append(name).append("\n"); - } - MiscUtils.copyToClipboard(builder.toString()); - Utils.addChatMessage("§e[NEU] Copied tablist to clipboard!"); - } - if (args.length >= 1 && args[0].equalsIgnoreCase("useragent")) { - String newUserAgent = args.length == 1 ? null : String.join(" ", Arrays.copyOfRange(args, 1, args.length)); - Utils.addChatMessage("§e[NEU] Changed user agent override to: " + newUserAgent); - NotEnoughUpdates.INSTANCE.config.hidden.customUserAgent = newUserAgent; - } - if (args.length == 2 && args[0].equalsIgnoreCase("value")) { - try { - testValue = Integer.parseInt(args[1]); - } catch (NumberFormatException e) { - Utils.addChatMessage("NumberFormatException!"); - } - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DiagCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DiagCommand.java deleted file mode 100644 index fb546efb..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DiagCommand.java +++ /dev/null @@ -1,134 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.miscfeatures.CrystalMetalDetectorSolver; -import io.github.moulberry.notenoughupdates.miscfeatures.CrystalWishingCompassSolver; -import io.github.moulberry.notenoughupdates.options.customtypes.NEUDebugFlag; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; - -public class DiagCommand extends ClientCommandBase { - public DiagCommand() { - super("neudiag"); - } - - private static final String USAGE_TEXT = EnumChatFormatting.WHITE + - "Usage: /neudiag <metal | wishing | debug>\n\n" + - "/neudiag metal Metal Detector Solver diagnostics\n" + - " <no sub-command> Show current solution diags\n" + - " center=<off | on> Disable / enable using center\n" + - "/neudiag wishing Wishing Compass Solver diagnostics\n" + - "/neudiag debug\n" + - " <no sub-command> Show all enabled flags\n" + - " <list> Show all flags\n"+ - " <enable | disable> <flag> Enable/disable flag\n"; - - private void showUsage(ICommandSender sender) { - sender.addChatMessage(new ChatComponentText(USAGE_TEXT)); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (args.length == 0) { - showUsage(sender); - return; - } - - String command = args[0].toLowerCase(); - switch (command) { - case "metal": - if (args.length == 1) { - CrystalMetalDetectorSolver.logDiagnosticData(true); - return; - } - - String subCommand = args[1].toLowerCase(); - if (subCommand.equals("center=off")) { - CrystalMetalDetectorSolver.setDebugDoNotUseCenter(true); - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.YELLOW + - "Center coordinates-based solutions disabled")); - } else if (subCommand.equals("center=on")) { - CrystalMetalDetectorSolver.setDebugDoNotUseCenter(false); - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.YELLOW + - "Center coordinates-based solutions enabled")); - } else { - showUsage(sender); - return; - } - - break; - case "wishing": - CrystalWishingCompassSolver.getInstance().logDiagnosticData(true); - break; - case "debug": - if (args.length > 1) { - boolean enablingFlag = true; - String action = args[1]; - switch (action) { - case "list": - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.YELLOW + "Here are all flags:\n" + NEUDebugFlag.getFlagList())); - return; - case "disable": - enablingFlag = false; - // falls through - case "enable": - if (args.length != 3) { - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + - "You must specify a flag:\n" + - NEUDebugFlag.getFlagList())); - return; - } - - String flagName = args[2].toUpperCase(); - try { - NEUDebugFlag debugFlag = NEUDebugFlag.valueOf(flagName); - if (enablingFlag) { - NotEnoughUpdates.INSTANCE.config.hidden.debugFlags.add(debugFlag); - } else { - NotEnoughUpdates.INSTANCE.config.hidden.debugFlags.remove(debugFlag); - } - } catch (IllegalArgumentException e) { - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + - flagName + " is invalid. Valid flags are:\n" + - NEUDebugFlag.getFlagList())); - return; - } - break; - default: - showUsage(sender); - return; - } - } - - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.YELLOW + "Effective debug flags: \n" + - NEUDebugFlag.getEnabledFlags())); - break; - default: - showUsage(sender); - return; - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DungeonWinTestCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DungeonWinTestCommand.java deleted file mode 100644 index be25e697..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/DungeonWinTestCommand.java +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.dungeons.DungeonWin; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ResourceLocation; - -public class DungeonWinTestCommand extends ClientCommandBase { - - public DungeonWinTestCommand() { - super("neudungeonwintest"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (args.length > 0) { - DungeonWin.TEAM_SCORE = new ResourceLocation("notenoughupdates:dungeon_win/" + args[0].toLowerCase() + ".png"); - } - - DungeonWin.displayWin(); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/EnableStorageCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/EnableStorageCommand.java deleted file mode 100644 index 3415b030..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/EnableStorageCommand.java +++ /dev/null @@ -1,39 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; - -public class EnableStorageCommand extends ClientCommandBase { - - public EnableStorageCommand() { - super("neuenablestorage"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - NotEnoughUpdates.INSTANCE.config.storageGUI.enableStorageGUI3 = true; - NotEnoughUpdates.INSTANCE.saveConfig(); - } - -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/NullzeeSphereCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/NullzeeSphereCommand.java deleted file mode 100644 index 3a9ce90f..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/NullzeeSphereCommand.java +++ /dev/null @@ -1,61 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.miscfeatures.NullzeeSphere; -import net.minecraft.client.entity.EntityPlayerSP; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.BlockPos; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; - -public class NullzeeSphereCommand extends ClientCommandBase { - - public NullzeeSphereCommand() { - super("neuzeesphere"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (args.length != 1) { - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.RED + "Usage: /neuzeesphere [on/off] or /neuzeesphere (radius) or /neuzeesphere setCenter")); - return; - } - if (args[0].equalsIgnoreCase("on")) { - NullzeeSphere.enabled = true; - } else if (args[0].equalsIgnoreCase("off")) { - NullzeeSphere.enabled = false; - } else if (args[0].equalsIgnoreCase("setCenter")) { - EntityPlayerSP p = ((EntityPlayerSP) sender); - NullzeeSphere.centerPos = new BlockPos(p.posX, p.posY, p.posZ); - NullzeeSphere.overlayVBO = null; - } else { - try { - NullzeeSphere.size = Float.parseFloat(args[0]); - NullzeeSphere.overlayVBO = null; - } catch (Exception e) { - sender.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Can't parse radius: " + args[0])); - } - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/PackDevCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/PackDevCommand.java deleted file mode 100644 index 1d30a15f..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/PackDevCommand.java +++ /dev/null @@ -1,304 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.core.util.MiscUtils; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.client.entity.AbstractClientPlayer; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.entity.Entity; -import net.minecraft.entity.EntityLiving; -import net.minecraft.entity.EntityLivingBase; -import net.minecraft.entity.item.EntityArmorStand; -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.item.ItemStack; -import net.minecraft.nbt.NBTBase; -import net.minecraft.nbt.NBTTagCompound; -import net.minecraft.util.BlockPos; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; - -import java.util.HashMap; -import java.util.List; -import java.util.function.Supplier; - -public class PackDevCommand extends ClientCommandBase { - static Minecraft mc = Minecraft.getMinecraft(); - - public PackDevCommand() { - super("neupackdev"); - } - - private static final HashMap<String, Command<?, ?>> commands = new HashMap<String, Command<?, ?>>() {{ - put( - "getnpc", - new Command<>( - "NPC", - () -> mc.theWorld.playerEntities, - true, - AbstractClientPlayer.class - ) - ); - put( - "getnpcs", - new Command<>( - "NPC", - () -> mc.theWorld.playerEntities, - false, - AbstractClientPlayer.class - ) - ); - put( - "getmob", - new Command<>( - "mob", - () -> mc.theWorld.loadedEntityList, - true, - EntityLiving.class - ) - ); - put( - "getmobs", - new Command<>( - "mob", - () -> mc.theWorld.loadedEntityList, - false, - EntityLiving.class - ) - ); - put( - "getarmorstand", - new Command<>( - "armor stand", - () -> mc.theWorld.loadedEntityList, - true, - EntityArmorStand.class - ) - ); - put( - "getarmorstands", - new Command<>( - "armor stand", - () -> mc.theWorld.loadedEntityList, - false, - EntityArmorStand.class - ) - ); - }}; - - @Override - public List<String> addTabCompletionOptions(ICommandSender sender, String[] args, BlockPos pos) { - return args.length == 1 ? getListOfStringsMatchingLastWord(args, commands.keySet()) : null; - } - - public static void togglePackDeveloperMode(ICommandSender sender) { - NotEnoughUpdates.INSTANCE.packDevEnabled = !NotEnoughUpdates.INSTANCE.packDevEnabled; - if (NotEnoughUpdates.INSTANCE.packDevEnabled) { - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.GREEN + "Enabled pack developer mode.")); - } else { - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.RED + "Disabled pack developer mode.")); - } - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (args.length == 0) { - togglePackDeveloperMode(sender); - return; - } - - double dist = 5.0; - if (args.length >= 2) { - try { - dist = Double.parseDouble(args[1]); - } catch (NumberFormatException e) { - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.RED + "Invalid distance! Must be a number, defaulting to a radius of 5.")); - } - } - - StringBuilder output; - String subCommand = args[0].toLowerCase(); - if (commands.containsKey(subCommand)) { - Command<?, ?> command = commands.get(subCommand); - output = command.getData(dist); - } else if (subCommand.equals("getall")) { - output = getAll(dist); - } else if (subCommand.equals("getallclose")) { - output = getAllClose(dist); - } else { - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.RED + "Invalid sub-command.")); - return; - } - - if (output.length() != 0) { - MiscUtils.copyToClipboard(output.toString()); - } - } - - private static StringBuilder getAllClose(Double dist) { - StringBuilder sb = new StringBuilder(); - sb.append(commands.get("getmob").getData(dist)); - sb.append(commands.get("getarmorstand").getData(dist)); - sb.append(commands.get("getnpc").getData(dist)); - return sb; - } - - private static StringBuilder getAll(Double dist) { - StringBuilder sb = new StringBuilder(); - sb.append(commands.get("getmobs").getData(dist)); - sb.append(commands.get("getarmorstands").getData(dist)); - sb.append(commands.get("getnpcs").getData(dist)); - return sb; - } - - public static <T extends EntityLivingBase> StringBuilder livingBaseDataBuilder(T entity, Class<T> clazz) { - StringBuilder entityData = new StringBuilder(); - if (EntityPlayer.class.isAssignableFrom(entity.getClass())) { - EntityPlayer entityPlayer = (EntityPlayer) entity; - - // NPC Information - String skinResourcePath = ((AbstractClientPlayer) entityPlayer).getLocationSkin().getResourcePath(); - entityData - .append("Player Id: ") - .append(entityPlayer.getUniqueID() != null ? entityPlayer.getUniqueID().toString() : "null") - .append(entityPlayer.getCustomNameTag() != null ? entityPlayer.getCustomNameTag() : "null") - .append("\nEntity Texture Id: ") - .append(skinResourcePath != null ? skinResourcePath.replace("skins/", "") : "null"); - } - - if (!clazz.isAssignableFrom(entity.getClass())) { - return entityData; - } - - //Entity Information - entityData - .append("Entity Id: ") - .append(entity.getEntityId()) - .append("\nMob: ") - .append(entity.getName() != null ? entity.getName() : "null") - .append("\nCustom Name: ") - .append(entity.getCustomNameTag() != null ? entity.getCustomNameTag() : "null"); - - //Held Item - if (entity.getHeldItem() != null) { - entityData - .append("\nItem: ") - .append(entity.getHeldItem()) - .append("\nItem Display Name: ") - .append(entity.getHeldItem().getDisplayName() != null - ? entity.getHeldItem().getDisplayName() - : "null") - .append("\nItem Tag Compound: "); - NBTTagCompound heldItemTagCompound = entity.getHeldItem().getTagCompound(); - if (heldItemTagCompound != null) { - String heldItemString = heldItemTagCompound.toString(); - NBTBase extraAttrTag = heldItemTagCompound.getTag("ExtraAttributes"); - entityData - .append(heldItemString != null ? heldItemString : "null") - .append("\nItem Tag Compound Extra Attributes: ") - .append(extraAttrTag != null ? extraAttrTag : "null"); - } else { - entityData.append("null"); - } - - } else { - entityData.append("\nItem: null"); - } - - entityData.append(armorDataBuilder(entity)).append("\n\n"); - - return entityData; - } - - private static final String[] armorPieceTypes = {"Boots", "Leggings", "Chestplate", "Helmet"}; - - public static <T extends EntityLivingBase> StringBuilder armorDataBuilder(T entity) { - StringBuilder armorData = new StringBuilder(); - for (int i = 0; i < 4; i++) { - ItemStack currentArmor = entity.getCurrentArmor(0); - armorData.append(String.format("\n%s: ", armorPieceTypes[i])); - if (currentArmor == null) { - armorData.append("null"); - } else { - armorData.append(currentArmor.getTagCompound() != null ? currentArmor.getTagCompound().toString() : "null"); - } - } - return armorData; - } - - static class Command<T extends EntityLivingBase, U extends Entity> { - String typeFriendlyName; - Supplier<List<U>> entitySupplier; - Class<T> clazz; - boolean single; - - Command( - String typeFriendlyName, - Supplier<List<U>> entitySupplier, - boolean single, - Class<T> clazz - ) { - this.typeFriendlyName = typeFriendlyName; - this.entitySupplier = entitySupplier; - this.single = single; - this.clazz = clazz; - } - - @SuppressWarnings("unchecked") - public StringBuilder getData(double dist) { - StringBuilder result = new StringBuilder(); - double distSq = dist * dist; - T closest = null; - for (Entity entity : entitySupplier.get()) { - if (!clazz.isAssignableFrom(entity.getClass()) || entity == mc.thePlayer) { - continue; - } - T entityT = (T) entity; - double entityDistanceSq = entity.getDistanceSq(mc.thePlayer.posX, mc.thePlayer.posY, mc.thePlayer.posZ); - if (entityDistanceSq < distSq) { - if (single) { - distSq = entityDistanceSq; - closest = entityT; - } else { - result.append(livingBaseDataBuilder(entityT, clazz)); - } - } - } - - if ((single && closest == null) || (!single && result.length() == 0)) { - Utils.addChatMessage(EnumChatFormatting.RED + "No " + typeFriendlyName + "s found within " + dist + " blocks."); - } else { - Utils.addChatMessage( - EnumChatFormatting.GREEN + "Copied " + typeFriendlyName + " data to clipboard"); - return single ? livingBaseDataBuilder(closest, clazz) : result; - } - - return result; - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/ReloadRepoCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/ReloadRepoCommand.java deleted file mode 100644 index 0bf57594..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/ReloadRepoCommand.java +++ /dev/null @@ -1,39 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ChatComponentText; - -public class ReloadRepoCommand extends ClientCommandBase { - - public ReloadRepoCommand() { - super("neureloadrepo"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - NotEnoughUpdates.INSTANCE.manager.reloadRepository(); - sender.addChatMessage(new ChatComponentText("§e[NEU] Reloaded repository.")); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/ResetRepoCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/ResetRepoCommand.java deleted file mode 100644 index 3f693898..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/ResetRepoCommand.java +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ChatComponentText; - -public class ResetRepoCommand extends ClientCommandBase { - - public ResetRepoCommand() { - super("neuresetrepo"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - NotEnoughUpdates.INSTANCE.manager - .userFacingRepositoryReload() - .thenAccept(strings -> - strings.forEach(line -> - sender.addChatMessage(new ChatComponentText("§e[NEU] " + line)))); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/StatsCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/StatsCommand.java deleted file mode 100644 index ea417977..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dev/StatsCommand.java +++ /dev/null @@ -1,200 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dev; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.DiscordMarkdownBuilder; -import io.github.moulberry.notenoughupdates.util.HastebinUploader; -import io.github.moulberry.notenoughupdates.util.SBInfo; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.client.renderer.OpenGlHelper; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.BlockPos; -import net.minecraft.util.EnumChatFormatting; -import net.minecraftforge.common.ForgeVersion; -import net.minecraftforge.fml.client.FMLClientHandler; -import net.minecraftforge.fml.common.Loader; -import org.lwjgl.opengl.Display; -import org.lwjgl.opengl.GL11; - -import javax.management.JMX; -import javax.management.MBeanServer; -import javax.management.ObjectName; -import java.awt.*; -import java.awt.datatransfer.StringSelection; -import java.lang.management.ManagementFactory; -import java.util.List; -import java.util.Locale; -import java.util.concurrent.ExecutorService; -import java.util.concurrent.Executors; - -public class StatsCommand extends ClientCommandBase { - private final ExecutorService threadPool = Executors.newFixedThreadPool(1); - - public StatsCommand() { - super("neustats"); - } - - private static final int activeModCount = Loader.instance().getActiveModList().size(); - - @Override - public void processCommand(ICommandSender sender, String[] args) { - if (args.length > 0) { - switch (args[0].toLowerCase(Locale.ROOT)) { - case "modlist": - if (activeModCount > 15) { - clipboardAndSendMessage(createModList(new DiscordMarkdownBuilder()).toString()); - } else { - clipboardAndSendMessage(createStats()); - } - break; - case "dump": - modPrefixedMessage(EnumChatFormatting.GREEN + - "This will upload a dump of the java classes your game has loaded how big they are and how many there are. This can take a few seconds as it is uploading to HasteBin."); - threadPool.submit(() -> { - try { - final MBeanServer server = ManagementFactory.getPlatformMBeanServer(); - final ObjectName objectName = ObjectName.getInstance("com.sun.management:type=DiagnosticCommand"); - final DiagnosticCommandMXBean proxy = JMX.newMXBeanProxy( - server, - objectName, - DiagnosticCommandMXBean.class - ); - clipboardAndSendMessage(HastebinUploader.upload( - proxy.gcClassHistogram(new String[0]).replace("[", "[]"), - HastebinUploader.Mode.NORMAL - )); - } catch (Exception e) { - clipboardAndSendMessage(null); - } - }); - break; - } - } else { - clipboardAndSendMessage(createStats()); - } - - } - - @Override - public List<String> addTabCompletionOptions(ICommandSender sender, String[] args, BlockPos pos) { - return args.length == 1 ? getListOfStringsMatchingLastWord(args, "modlist", "dump") : null; - } - - public interface DiagnosticCommandMXBean { - String gcClassHistogram(String[] array); - } - - private static void clipboardAndSendMessage(String data) { - if (data == null) { - modPrefixedMessage(EnumChatFormatting.DARK_RED + "Error occurred trying to perform command."); - return; - } - try { - StringSelection clipboard = new StringSelection(data); - Toolkit.getDefaultToolkit().getSystemClipboard().setContents(clipboard, clipboard); - modPrefixedMessage(EnumChatFormatting.GREEN + "Dev info copied to clipboard."); - } catch (Exception ignored) { - modPrefixedMessage(EnumChatFormatting.DARK_RED + "Could not copy to clipboard."); - } - } - - private static void modPrefixedMessage(String message) { - Utils.addChatMessage( - EnumChatFormatting.GOLD + "[" + EnumChatFormatting.RED + "NotEnoughUpdates" + EnumChatFormatting.GOLD + "]: " + message); - } - - private static String createStats() { - DiscordMarkdownBuilder builder = new DiscordMarkdownBuilder(); - long maxMemory = Runtime.getRuntime().maxMemory(); - long totalMemory = Runtime.getRuntime().totalMemory(); - long freeMemory = Runtime.getRuntime().freeMemory(); - long currentMemory = totalMemory - freeMemory; - - builder.category("System Stats"); - builder.append("OS", System.getProperty("os.name")); - builder.append("CPU", OpenGlHelper.getCpu()); - builder.append( - "Display", - String.format("%dx%d (%s)", Display.getWidth(), Display.getHeight(), GL11.glGetString(GL11.GL_VENDOR)) - ); - builder.append("GPU", GL11.glGetString(GL11.GL_RENDERER)); - builder.append("GPU Driver", GL11.glGetString(GL11.GL_VERSION)); - if (getMemorySize() > 0) builder.append("Maximum Memory", (getMemorySize() / 1024L / 1024L) + "MB"); - builder.append("Shaders", ("" + OpenGlHelper.isFramebufferEnabled()).toUpperCase()); - builder.category("Java Stats"); - builder.append( - "Java", - String.format("%s %dbit", System.getProperty("java.version"), Minecraft.getMinecraft().isJava64bit() ? 64 : 32) - ); - builder.append( - "Memory", - String.format( - "% 2d%% %03d/%03dMB", - currentMemory * 100L / maxMemory, - currentMemory / 1024L / 1024L, - maxMemory / 1024L / 1024L - ) - ); - builder.append( - "Memory Allocated", - String.format("% 2d%% %03dMB", totalMemory * 100L / maxMemory, totalMemory / 1024L / 1024L) - ); - builder.category("Game Stats"); - builder.append("FPS", String.valueOf(Minecraft.getDebugFPS())); - builder.append("Loaded Mods", String.valueOf(activeModCount)); - builder.append("Forge", ForgeVersion.getVersion()); - builder.append("Optifine", FMLClientHandler.instance().hasOptifine() ? "TRUE" : "FALSE"); - builder.category("Neu Settings"); - builder.append("API Key", NotEnoughUpdates.INSTANCE.config.apiData.apiKey.isEmpty() ? "FALSE" : "TRUE"); - builder.append("On SkyBlock", NotEnoughUpdates.INSTANCE.hasSkyblockScoreboard() ? "TRUE" : "FALSE"); - builder.append( - "Mod Version", - Loader.instance().getIndexedModList().get(NotEnoughUpdates.MODID).getDisplayVersion() - ); - builder.append("SB Profile", SBInfo.getInstance().currentProfile); - builder.append("Has Advanced Tab", SBInfo.getInstance().hasNewTab ? "TRUE" : "FALSE"); - builder.category("Repo Stats"); - builder.append("Last Commit", NotEnoughUpdates.INSTANCE.manager.latestRepoCommit); - builder.append("Loaded Items", String.valueOf(NotEnoughUpdates.INSTANCE.manager.getItemInformation().size())); - if (activeModCount <= 15) createModList(builder); - - return builder.toString(); - } - - private static DiscordMarkdownBuilder createModList(DiscordMarkdownBuilder builder) { - builder.category("Mods Loaded"); - Loader.instance().getActiveModList().forEach(mod -> builder.append(mod.getName(), mod.getSource().getName())); - return builder; - } - - private static long getMemorySize() { - try { - return ((com.sun.management.OperatingSystemMXBean) ManagementFactory.getOperatingSystemMXBean()).getTotalPhysicalMemorySize(); - } catch (Exception e) { - try { - return ((com.sun.management.UnixOperatingSystemMXBean) ManagementFactory.getOperatingSystemMXBean()).getTotalPhysicalMemorySize(); - } catch (Exception ignored) {/*IGNORE*/} - } - return -1; - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/DnCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/DnCommand.java deleted file mode 100644 index 3b697905..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/DnCommand.java +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dungeon; - -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.EnumChatFormatting; - -public class DnCommand extends ClientCommandBase { - - public DnCommand() { - super("dn"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - Minecraft.getMinecraft().thePlayer.sendChatMessage("/warp dungeon_hub"); - Utils.addChatMessage(EnumChatFormatting.AQUA + "Warping to:" + EnumChatFormatting.YELLOW + " Deez Nuts lmao"); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/JoinDungeonCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/JoinDungeonCommand.java deleted file mode 100644 index 58bfbef2..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/JoinDungeonCommand.java +++ /dev/null @@ -1,57 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dungeon; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.EnumChatFormatting; -import org.apache.commons.lang3.StringUtils; - -public class JoinDungeonCommand extends ClientCommandBase { - - public JoinDungeonCommand() { - super("join"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (!NotEnoughUpdates.INSTANCE.hasSkyblockScoreboard()) { - Minecraft.getMinecraft().thePlayer.sendChatMessage("/join " + StringUtils.join(args, " ")); - } else { - if (args.length != 1) { - Utils.addChatMessage(EnumChatFormatting.RED + "Example Usage: /join f7, /join m6 or /join 7"); - } else { - String cataPrefix = "catacombs"; - if (args[0].toLowerCase().startsWith("m")) { - cataPrefix = "master_catacombs"; - } - String cmd = "/joindungeon " + cataPrefix + " " + args[0].charAt(args[0].length() - 1); - Utils.addChatMessage(EnumChatFormatting.YELLOW + "Running command: " + cmd); - Utils.addChatMessage(EnumChatFormatting.YELLOW + - "The dungeon should start soon. If it doesn't, make sure you have a party of 5 people"); - Minecraft.getMinecraft().thePlayer.sendChatMessage(cmd); - } - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/MapCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/MapCommand.java deleted file mode 100644 index d52ed196..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/MapCommand.java +++ /dev/null @@ -1,131 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.dungeon; - -import com.google.gson.JsonElement; -import com.google.gson.JsonObject; -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.dungeons.GuiDungeonMapEditor; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.block.material.MapColor; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.item.ItemMap; -import net.minecraft.item.ItemStack; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; -import net.minecraft.world.storage.MapData; - -import java.awt.*; -import java.io.File; -import java.util.Map; - -public class MapCommand extends ClientCommandBase { - - public MapCommand() { - super("neumap"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - - if (!NotEnoughUpdates.INSTANCE.config.hidden.dev) { - NotEnoughUpdates.INSTANCE.openGui = new GuiDungeonMapEditor(null); - return; - } - - if (args.length == 1 && args[0].equals("reset")) { - NotEnoughUpdates.INSTANCE.colourMap = null; - return; - } - - if (args.length != 2) { - NotEnoughUpdates.INSTANCE.openGui = new GuiDungeonMapEditor(null); - return; - } - - if (args[0].equals("save")) { - ItemStack stack = Minecraft.getMinecraft().thePlayer.getHeldItem(); - if (stack != null && stack.getItem() instanceof ItemMap) { - ItemMap map = (ItemMap) stack.getItem(); - MapData mapData = map.getMapData(stack, Minecraft.getMinecraft().theWorld); - - if (mapData == null) return; - - JsonObject json = new JsonObject(); - for (int i = 0; i < 16384; ++i) { - int x = i % 128; - int y = i / 128; - - int j = mapData.colors[i] & 255; - - Color c; - if (j / 4 == 0) { - c = new Color((i + i / 128 & 1) * 8 + 16 << 24, true); - } else { - c = new Color(MapColor.mapColorArray[j / 4].getMapColor(j & 3), true); - } - - json.addProperty(x + ":" + y, c.getRGB()); - } - - try { - new File(NotEnoughUpdates.INSTANCE.manager.configLocation, "maps").mkdirs(); - NotEnoughUpdates.INSTANCE.manager.writeJson( - json, - new File(NotEnoughUpdates.INSTANCE.manager.configLocation, "maps/" + args[1] + ".json") - ); - } catch (Exception e) { - e.printStackTrace(); - } - - Utils.addChatMessage(EnumChatFormatting.GREEN + "Saved to file."); - } - - return; - } - - if (args[0].equals("load")) { - JsonObject json = NotEnoughUpdates.INSTANCE.manager.getJsonFromFile(new File( - NotEnoughUpdates.INSTANCE.manager.configLocation, - "maps/" + args[1] + ".json" - )); - - NotEnoughUpdates.INSTANCE.colourMap = new Color[128][128]; - for (int x = 0; x < 128; x++) { - for (int y = 0; y < 128; y++) { - NotEnoughUpdates.INSTANCE.colourMap[x][y] = new Color(0, 0, 0, 0); - } - } - for (Map.Entry<String, JsonElement> entry : json.entrySet()) { - int x = Integer.parseInt(entry.getKey().split(":")[0]); - int y = Integer.parseInt(entry.getKey().split(":")[1]); - - NotEnoughUpdates.INSTANCE.colourMap[x][y] = new Color(entry.getValue().getAsInt(), true); - } - - return; - } - - NotEnoughUpdates.INSTANCE.openGui = new GuiDungeonMapEditor(null); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/FeaturesCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/help/FeaturesCommand.java deleted file mode 100644 index bbabc172..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/FeaturesCommand.java +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.help; - -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Constants; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.event.ClickEvent; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; - -public class FeaturesCommand extends ClientCommandBase { - public FeaturesCommand() { - super("neufeatures"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - Utils.addChatMessage(""); - if (Constants.MISC == null || !Constants.MISC.has("featureslist")) { - Utils.showOutdatedRepoNotification(); - return; - } - String url = Constants.MISC.get("featureslist").getAsString(); - - if (Utils.openUrl(url)) { - Utils.addChatMessage( - EnumChatFormatting.DARK_PURPLE + "" + EnumChatFormatting.BOLD + "NEU" + EnumChatFormatting.RESET + - EnumChatFormatting.GOLD + "> Opening Feature List in browser."); - } else { - ChatComponentText clickTextFeatures = new ChatComponentText( - EnumChatFormatting.DARK_PURPLE + "" + EnumChatFormatting.BOLD + "NEU" + EnumChatFormatting.RESET + - EnumChatFormatting.GOLD + "> Click here to open the Feature List in your browser."); - clickTextFeatures.setChatStyle(Utils.createClickStyle(ClickEvent.Action.OPEN_URL, url)); - Minecraft.getMinecraft().thePlayer.addChatMessage(clickTextFeatures); - - } - Utils.addChatMessage(""); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/HelpCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/help/HelpCommand.java deleted file mode 100644 index 3a47509d..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/HelpCommand.java +++ /dev/null @@ -1,94 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.help; - -import com.google.common.collect.Lists; -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.command.ICommandSender; - -import java.util.ArrayList; - -public class HelpCommand extends ClientCommandBase { - - public HelpCommand() { - super("neuhelp"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) { - ArrayList<String> neuHelpMessages = Lists.newArrayList( - "\u00a75\u00a7lNotEnoughUpdates commands", - "\u00a76/neu \u00a77- Opens the main NEU GUI.", - "\u00a76/pv \u00a7b?{name} \u00a72\u2D35 \u00a7r\u00a77- Opens the profile viewer", - "\u00a76/neusouls {on/off/clear/unclear} \u00a7r\u00a77- Shows waypoints to fairy souls.", - "\u00a76/neubuttons \u00a7r\u00a77- Opens a GUI which allows you to customize inventory buttons.", - "\u00a76/neuec \u00a7r\u00a77- Opens the enchant colour GUI.", - "\u00a76/join {floor} \u00a7r\u00a77- Short Command to join a Dungeon. \u00a7lNeed a Party of 5 People\u00a7r\u00a77 {4/f7/m5}.", - "\u00a76/neucosmetics \u00a7r\u00a77- Opens the cosmetic GUI.", - "\u00a76/neurename \u00a7r\u00a77- Opens the NEU Item Customizer.", - "\u00a76/cata \u00a7b?{name} \u00a72\u2D35 \u00a7r\u00a77- Opens the profile viewer's Catacombs page.", - "\u00a76/neulinks \u00a7r\u00a77- Shows links to NEU/Moulberry.", - "\u00a76/neuoverlay \u00a7r\u00a77- Opens GUI Editor for quickcommands and searchbar.", - "\u00a76/neuah \u00a7r\u00a77- Opens NEU's custom auction house GUI.", - "\u00a76/neucalendar \u00a7r\u00a77- Opens NEU's custom calendar GUI.", - "\u00a76/neucalc \u00a7r\u00a77- Run calculations.", - "", - "\u00a76\u00a7lOld commands:", - "\u00a76/peek \u00a7b?{user} \u00a72\u2D35 \u00a7r\u00a77- Shows quick stats for a user.", - "", - "\u00a76\u00a7lDebug commands:", - "\u00a76/neustats \u00a7r\u00a77- Copies helpful info to the clipboard.", - "\u00a76/neustats modlist \u00a7r\u00a77- Copies mod list info to clipboard.", - "\u00a76/neuresetrepo \u00a7r\u00a77- Deletes all repo files.", - "\u00a76/neureloadrepo \u00a7r\u00a77- Debug command with repo.", - "", - "\u00a76\u00a7lDev commands:", - "\u00a76/neupackdev \u00a7r\u00a77- pack creator command - getnpc, getmob(s), getarmorstand(s), getall. Optional radius argument for all." - ); - for (String neuHelpMessage : neuHelpMessages) { - Utils.addChatMessage(neuHelpMessage); - } - if (NotEnoughUpdates.INSTANCE.config.hidden.dev) { - ArrayList<String> neuDevHelpMessages = Lists.newArrayList( - "\u00a76/neudevtest \u00a7r\u00a77- dev test command", - "\u00a76/neuzeephere \u00a7r\u00a77- sphere", - "\u00a76/neudungeonwintest \u00a7r\u00a77- displays the dungeon win screen" - ); - - for (String neuDevHelpMessage : neuDevHelpMessages) { - Utils.addChatMessage(neuDevHelpMessage); - } - } - String[] helpInfo = { - "", - "\u00a77Commands marked with a \u00a72\"\u2D35\"\u00a77 require an api key. You can set your api key via \"/api new\" or by manually putting it in the api field in \"/neu\"", - "", - "\u00a77Arguments marked with a \u00a7b\"?\"\u00a77 are optional.", - "", - "\u00a76\u00a7lScroll up to see everything" - }; - - for (String message : helpInfo) { - Utils.addChatMessage(message); - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/LinksCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/help/LinksCommand.java deleted file mode 100644 index 793e652e..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/LinksCommand.java +++ /dev/null @@ -1,52 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.help; - -import com.google.gson.JsonObject; -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; - -import java.io.File; - -public class LinksCommand extends ClientCommandBase { - - public LinksCommand() { - super("neulinks"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - File repo = NotEnoughUpdates.INSTANCE.manager.repoLocation; - if (repo.exists()) { - File updateJson = new File(repo, "update.json"); - try { - JsonObject update = NotEnoughUpdates.INSTANCE.manager.getJsonFromFile(updateJson); - - Utils.addChatMessage(""); - NotEnoughUpdates.INSTANCE.displayLinks(update,0 ); - Utils.addChatMessage(""); - } catch (Exception ignored) { - } - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/SettingsCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/help/SettingsCommand.java deleted file mode 100644 index 1855a2b5..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/SettingsCommand.java +++ /dev/null @@ -1,53 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.help; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.core.GuiScreenElementWrapper; -import io.github.moulberry.notenoughupdates.options.NEUConfigEditor; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import org.apache.commons.lang3.StringUtils; - -import java.util.Arrays; -import java.util.List; - -public class SettingsCommand extends ClientCommandBase { - - public SettingsCommand() { - super("neu"); - } - - @Override - public List<String> getCommandAliases() { - return Arrays.asList("neusettings", "neuconfig"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (args.length > 0) { - NotEnoughUpdates.INSTANCE.openGui = - new GuiScreenElementWrapper(new NEUConfigEditor(NotEnoughUpdates.INSTANCE.config, StringUtils.join(args, " "))); - } else { - NotEnoughUpdates.INSTANCE.openGui = new GuiScreenElementWrapper(new NEUConfigEditor(NotEnoughUpdates.INSTANCE.config)); - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/StorageViewerWhyCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/help/StorageViewerWhyCommand.java deleted file mode 100644 index 820c6f2a..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/help/StorageViewerWhyCommand.java +++ /dev/null @@ -1,45 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.help; - -import com.google.common.collect.Lists; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.NotificationHandler; -import net.minecraft.command.ICommandSender; - -public class StorageViewerWhyCommand extends ClientCommandBase { - - public StorageViewerWhyCommand() { - super("neustwhy"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) { - NotificationHandler.displayNotification(Lists.newArrayList( - "\u00a7eStorage Viewer", - "\u00a77Currently, the storage viewer requires you to click twice", - "\u00a77in order to switch between pages. This is because Hypixel", - "\u00a77has not yet added a shortcut command to go to any enderchest/", - "\u00a77storage page.", - "\u00a77While it is possible to send the second click", - "\u00a77automatically, doing so violates Hypixel's new mod rules." - ), true); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/AhCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/AhCommand.java deleted file mode 100644 index 1ca398ef..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/AhCommand.java +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.auction.CustomAHGui; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.EnumChatFormatting; -import org.apache.commons.lang3.StringUtils; - -public class AhCommand extends ClientCommandBase { - - public AhCommand() { - super("neuah"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (!NotEnoughUpdates.INSTANCE.hasSkyblockScoreboard()) { - Utils.addChatMessage(EnumChatFormatting.RED + "You must be on SkyBlock to use this feature."); - } else if (NotEnoughUpdates.INSTANCE.config.apiData.apiKey == null || - NotEnoughUpdates.INSTANCE.config.apiData.apiKey.trim().isEmpty()) { - Utils.addChatMessage( - EnumChatFormatting.RED + "Can't open NEU AH: an api key is not set. Run /api new and put the result in settings."); - } else { - NotEnoughUpdates.INSTANCE.openGui = new CustomAHGui(); - NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.lastOpen = System.currentTimeMillis(); - NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.clearSearch(); - NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.updateSearch(); - - if (args.length > 0) { - NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.setSearch(StringUtils.join(args, " ")); - } else { - if (NotEnoughUpdates.INSTANCE.config.neuAuctionHouse.saveLastSearch) { - NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.setSearch(null); - } - } - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CalculatorCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CalculatorCommand.java deleted file mode 100644 index b01f106b..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CalculatorCommand.java +++ /dev/null @@ -1,75 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.Calculator; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; - -import java.math.BigDecimal; -import java.text.DecimalFormat; -import java.util.Arrays; -import java.util.List; -import java.util.Objects; - -public class CalculatorCommand extends ClientCommandBase { - public CalculatorCommand() { - super("neucalc"); - } - - @Override - public List<String> getCommandAliases() { - return Arrays.asList("neucalculator"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if ((args.length == 1 && Objects.equals(args[0], "help")) || args.length == 0) { - sender.addChatMessage(new ChatComponentText( - "\n§e[NEU] §5It's a calculator.\n" + - "§eFor Example §b/neucalc 3m*7k§e.\n" + - "§eYou can also use suffixes (k, m, b, t, s)§e.\n" + - "§eThe \"s\" suffix acts as 64.\n" + - "§eTurn on Sign Calculator in /neu misc to also support this in sign popups and the neu search bar.\n")); - return; - } - String source = String.join(" ", args); - try { - BigDecimal calculate = Calculator.calculate(source); - DecimalFormat formatter = new DecimalFormat("#,##0.##"); - String format = formatter.format(calculate); - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.YELLOW + "[NEU] " + EnumChatFormatting.WHITE + source + " " + EnumChatFormatting.YELLOW + - "= " + EnumChatFormatting.GREEN + format - )); - } catch (Calculator.CalculatorException e) { - sender.addChatMessage(new ChatComponentText( - EnumChatFormatting.YELLOW + "[NEU] " + EnumChatFormatting.RED + "Error during calculation: " + - e.getMessage() + "\n" + - EnumChatFormatting.WHITE + source.substring(0, e.getOffset()) + EnumChatFormatting.DARK_RED + - source.substring(e.getOffset(), e.getLength() + e.getOffset()) + EnumChatFormatting.GRAY + - source.substring(e.getLength() + e.getOffset()) - )); - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CalendarCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CalendarCommand.java deleted file mode 100644 index 58c13474..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CalendarCommand.java +++ /dev/null @@ -1,41 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.miscgui.CalendarOverlay; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; - -public class CalendarCommand extends ClientCommandBase { - - public CalendarCommand() { - super("neucalendar"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - Minecraft.getMinecraft().thePlayer.closeScreen(); - CalendarOverlay.setEnabled(true); - NotEnoughUpdates.INSTANCE.sendChatMessage("/calendar"); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CosmeticsCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CosmeticsCommand.java deleted file mode 100644 index bbab316e..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CosmeticsCommand.java +++ /dev/null @@ -1,47 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.cosmetics.GuiCosmetics; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.renderer.OpenGlHelper; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.EnumChatFormatting; - -public class CosmeticsCommand extends ClientCommandBase { - - public CosmeticsCommand() { - super("neucosmetics"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (!OpenGlHelper.isFramebufferEnabled() && NotEnoughUpdates.INSTANCE.config.notifications.doFastRenderNotif) { - Utils.addChatMessage(EnumChatFormatting.RED + - "NEU Cosmetics do not work with OptiFine Fast Render. Go to ESC > Options > Video Settings > Performance > Fast Render to disable it."); - - } - - NotEnoughUpdates.INSTANCE.openGui = new GuiCosmetics(); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CustomizeCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CustomizeCommand.java deleted file mode 100644 index 28c2893d..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/CustomizeCommand.java +++ /dev/null @@ -1,63 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.miscgui.GuiItemCustomize; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.item.ItemStack; -import net.minecraft.util.ChatComponentText; - -import java.util.Collections; -import java.util.List; - -public class CustomizeCommand extends ClientCommandBase { - - public CustomizeCommand() { - super("neucustomize"); - } - - @Override - public List<String> getCommandAliases() { - return Collections.singletonList("neurename"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - ItemStack held = Minecraft.getMinecraft().thePlayer.getHeldItem(); - - if (held == null) { - sender.addChatMessage(new ChatComponentText("\u00a7cYou can't customize your hand...")); - return; - } - - String heldUUID = NotEnoughUpdates.INSTANCE.manager.getUUIDForItem(held); - - if (heldUUID == null) { - sender.addChatMessage(new ChatComponentText("\u00a7cHeld item does not have a UUID, so it cannot be customized")); - return; - } - - NotEnoughUpdates.INSTANCE.openGui = new GuiItemCustomize(held, heldUUID); - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/PronounsCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/PronounsCommand.java deleted file mode 100644 index cf0d0c56..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/PronounsCommand.java +++ /dev/null @@ -1,94 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.util.MinecraftExecutor; -import io.github.moulberry.notenoughupdates.util.PronounDB; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.client.gui.GuiNewChat; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ChatComponentText; - -import java.util.Optional; -import java.util.Random; -import java.util.UUID; -import java.util.concurrent.CompletableFuture; - -public class PronounsCommand extends ClientCommandBase { - public PronounsCommand() { - super("neupronouns"); - } - - @Override - public String getCommandUsage(ICommandSender sender) { - return "/neupronouns <username> [platform]"; - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - switch (args.length) { - case 1: - fetchPronouns("minecraft", args[0]); - break; - case 2: - fetchPronouns(args[1], args[0]); - break; - default: - sender.addChatMessage(new ChatComponentText("§4" + getCommandUsage(sender))); - } - } - - private void fetchPronouns(String platform, String user) { - GuiNewChat nc = Minecraft.getMinecraft().ingameGUI.getChatGUI(); - int id = new Random().nextInt(); - nc.printChatMessageWithOptionalDeletion(new ChatComponentText("§e[NEU] Fetching Pronouns..."), id); - - CompletableFuture<Optional<PronounDB.PronounChoice>> pronouns; - if ("minecraft".equals(platform)) { - CompletableFuture<UUID> c = new CompletableFuture<>(); - NotEnoughUpdates.profileViewer.getPlayerUUID(user, uuidString -> { - if (uuidString == null) { - c.completeExceptionally(new NullPointerException()); - } else { - c.complete(Utils.parseDashlessUUID(uuidString)); - } - }); - pronouns = c.thenCompose(PronounDB::getPronounsFor); - } else { - pronouns = PronounDB.getPronounsFor(platform, user); - } - pronouns.handleAsync((pronounChoice, throwable) -> { - if (throwable != null || !pronounChoice.isPresent()) { - nc.printChatMessageWithOptionalDeletion(new ChatComponentText("§e[NEU] §4Failed to fetch pronouns."), id); - return null; - } - PronounDB.PronounChoice betterPronounChoice = pronounChoice.get(); - nc.printChatMessageWithOptionalDeletion(new ChatComponentText( - "§e[NEU] Pronouns for §b" + user + " §eon §b" + platform + "§e:"), id); - betterPronounChoice.render().forEach(it -> nc.printChatMessage(new ChatComponentText("§e[NEU] §a" + it))); - return null; - }, MinecraftExecutor.OnThread); - - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/UpdateCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/UpdateCommand.java deleted file mode 100644 index 1aeebda5..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/misc/UpdateCommand.java +++ /dev/null @@ -1,76 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.misc; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.util.ChatComponentText; - -import java.util.Arrays; -import java.util.List; -import java.util.Objects; - -public class UpdateCommand extends ClientCommandBase { - NotEnoughUpdates neu; - - public UpdateCommand(NotEnoughUpdates neu) { - super("neuupdate"); - this.neu = neu; - } - - @Override - public List<String> getCommandAliases() { - return Arrays.asList("neuupdates", "enoughupdates"); - } - - public void displayHelp(ICommandSender sender) { - sender.addChatMessage(new ChatComponentText( - "" + - "§e[NEU] §b/neuupdate help - View help.\n" + - "§e[NEU] §b/neuupdate check - Check for updates.\n" + - "" - )); - - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if ((args.length == 1 && Objects.equals(args[0], "help")) || args.length == 0) { - displayHelp(sender); - return; - } - switch (args[0].toLowerCase().intern()) { - case "check": - neu.autoUpdater.displayUpdateMessageIfOutOfDate(); - break; - case "scheduledownload": - neu.autoUpdater.scheduleDownload(); - break; - case "updatemodes": - sender.addChatMessage(new ChatComponentText("§e[NEU] §bTo ensure we do not accidentally corrupt your mod folder, we can only offer support for auto-updates on system with certain capabilities for file deletions (specifically unix systems). You can still manually update your files")); - break; - default: - displayHelp(sender); - - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/PeekCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/PeekCommand.java deleted file mode 100644 index 23852ab6..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/PeekCommand.java +++ /dev/null @@ -1,343 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.profile; - -import com.google.gson.JsonObject; -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.profileviewer.PlayerStats; -import io.github.moulberry.notenoughupdates.profileviewer.ProfileViewer; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.util.BlockPos; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; -import org.apache.commons.lang3.text.WordUtils; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Map; -import java.util.Random; -import java.util.concurrent.CountDownLatch; -import java.util.concurrent.Executors; -import java.util.concurrent.ScheduledExecutorService; -import java.util.concurrent.ScheduledFuture; -import java.util.concurrent.TimeUnit; - -public class PeekCommand extends ClientCommandBase { - - private ScheduledExecutorService peekCommandExecutorService = null; - private ScheduledFuture<?> peekScheduledFuture = null; - - public PeekCommand() { - super("peek"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - String name; - if (args.length == 0) { - name = Minecraft.getMinecraft().thePlayer.getName(); - } else { - name = args[0]; - } - int id = new Random().nextInt(Integer.MAX_VALUE / 2) + Integer.MAX_VALUE / 2; - - Minecraft.getMinecraft().ingameGUI.getChatGUI().printChatMessageWithOptionalDeletion(new ChatComponentText( - EnumChatFormatting.YELLOW + "[PEEK] Getting player information..."), id); - NotEnoughUpdates.profileViewer.getProfileByName(name, profile -> { - if (profile == null) { - Minecraft.getMinecraft().ingameGUI.getChatGUI().printChatMessageWithOptionalDeletion(new ChatComponentText( - EnumChatFormatting.RED + "[PEEK] Unknown player or the Hypixel API is down."), id); - } else { - profile.resetCache(); - - if (peekCommandExecutorService == null || peekCommandExecutorService.isTerminated()) { - peekCommandExecutorService = Executors.newSingleThreadScheduledExecutor(); - } - - if (peekScheduledFuture != null && !peekScheduledFuture.isDone()) { - Utils.addChatMessage( - EnumChatFormatting.RED + "[PEEK] New peek command was run, cancelling old one."); - peekScheduledFuture.cancel(true); - } - - Minecraft.getMinecraft().ingameGUI.getChatGUI().printChatMessageWithOptionalDeletion(new ChatComponentText( - EnumChatFormatting.YELLOW + "[PEEK] Getting the player's SkyBlock profile(s)..."), id); - - long startTime = System.currentTimeMillis(); - peekScheduledFuture = peekCommandExecutorService.schedule(new Runnable() { - public void run() { - if (System.currentTimeMillis() - startTime > 10 * 1000) { - Minecraft.getMinecraft().ingameGUI - .getChatGUI() - .printChatMessageWithOptionalDeletion(new ChatComponentText( - EnumChatFormatting.RED + "[PEEK] Getting profile info took too long, aborting."), id); - return; - } - - String g = EnumChatFormatting.GRAY.toString(); - - JsonObject profileInfo = profile.getProfileInformation(null); - if (profileInfo != null) { - float overallScore = 0; - - boolean isMe = name.equalsIgnoreCase("moulberry"); - - PlayerStats.Stats stats = profile.getStats(null); - if (stats == null) { - peekScheduledFuture = peekCommandExecutorService.schedule(this, 200, TimeUnit.MILLISECONDS); - return; - } - Map<String, ProfileViewer.Level> skyblockInfo = profile.getSkyblockInfo(null); - - if (NotEnoughUpdates.INSTANCE.config.profileViewer.useSoopyNetworth) { - Minecraft.getMinecraft().ingameGUI.getChatGUI().printChatMessageWithOptionalDeletion(new ChatComponentText( - EnumChatFormatting.YELLOW + "[PEEK] Getting the player's Skyblock networth..."), id); - - CountDownLatch countDownLatch = new CountDownLatch(1); - - profile.getSoopyNetworth(null, () -> countDownLatch.countDown()); - - try { //Wait for async network request - countDownLatch.await(10, TimeUnit.SECONDS); - } catch (InterruptedException e) {} - - //Now it's waited for network request the data should be cached (accessed in nw section) - } - - Minecraft.getMinecraft().ingameGUI - .getChatGUI() - .printChatMessageWithOptionalDeletion(new ChatComponentText(EnumChatFormatting.GREEN + " " + - EnumChatFormatting.STRIKETHROUGH + "-=-" + EnumChatFormatting.RESET + EnumChatFormatting.GREEN + - " " + - Utils.getElementAsString(profile.getHypixelProfile().get("displayname"), name) + "'s Info " + - EnumChatFormatting.STRIKETHROUGH + "-=-"), id); - - if (skyblockInfo == null) { - Utils.addChatMessage(EnumChatFormatting.YELLOW + "Skills API disabled!"); - } else { - float totalSkillLVL = 0; - float totalSkillCount = 0; - - List<String> skills = Arrays.asList("taming", "mining", "foraging", "enchanting", "farming", "combat", "fishing", "alchemy", "carpentry"); - for (String skillName : skills) { - totalSkillLVL += skyblockInfo.get(skillName).level; - totalSkillCount++; - } - - float combat = skyblockInfo.get("combat").level; - float zombie = skyblockInfo.get("zombie").level; - float spider = skyblockInfo.get("spider").level; - float wolf = skyblockInfo.get("wolf").level; - float enderman = skyblockInfo.get("enderman").level; - float blaze = skyblockInfo.get("blaze").level; - - float avgSkillLVL = totalSkillLVL / totalSkillCount; - - if (isMe) { - avgSkillLVL = 6; - combat = 4; - zombie = 2; - spider = 1; - wolf = 2; - enderman = 0; - blaze = 0; - } - - EnumChatFormatting combatPrefix = combat > 20 - ? (combat > 35 ? EnumChatFormatting.GREEN : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting zombiePrefix = zombie > 3 - ? (zombie > 6 ? EnumChatFormatting.GREEN : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting spiderPrefix = spider > 3 - ? (spider > 6 ? EnumChatFormatting.GREEN : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting wolfPrefix = - wolf > 3 ? (wolf > 6 ? EnumChatFormatting.GREEN : EnumChatFormatting.YELLOW) : EnumChatFormatting.RED; - EnumChatFormatting endermanPrefix = enderman > 3 - ? (enderman > 6 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting blazePrefix = blaze > 3 - ? (blaze > 6 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting avgPrefix = avgSkillLVL > 20 - ? (avgSkillLVL > 35 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - - overallScore += zombie * zombie / 81f; - overallScore += spider * spider / 81f; - overallScore += wolf * wolf / 81f; - overallScore += enderman * enderman / 81f; - overallScore += blaze * blaze / 81f; - overallScore += avgSkillLVL / 20f; - - int cata = (int) skyblockInfo.get("catacombs").level; - EnumChatFormatting cataPrefix = cata > 15 - ? (cata > 25 ? EnumChatFormatting.GREEN : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - - overallScore += cata * cata / 2000f; - - Utils.addChatMessage(g + "Combat: " + combatPrefix + (int) Math.floor(combat) + - (cata > 0 ? g + " - Cata: " + cataPrefix + cata : "") + - g + " - AVG: " + avgPrefix + (int) Math.floor(avgSkillLVL)); - Utils.addChatMessage(g + "Slayer: " + zombiePrefix + (int) Math.floor(zombie) + g + "-" + - spiderPrefix + (int) Math.floor(spider) + g + "-" + - wolfPrefix + (int) Math.floor(wolf) + g + "-" + - endermanPrefix + (int) Math.floor(enderman) + g + "-" + - blazePrefix + (int) Math.floor(blaze)); - } - if (stats == null) { - Utils.addChatMessage(EnumChatFormatting.YELLOW + "Skills, collection and/or inventory apis disabled!"); - } else { - int health = (int) stats.get("health"); - int defence = (int) stats.get("defence"); - int strength = (int) stats.get("strength"); - int intelligence = (int) stats.get("intelligence"); - - EnumChatFormatting healthPrefix = health > 800 - ? (health > 1600 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting defencePrefix = defence > 200 - ? (defence > 600 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting strengthPrefix = strength > 100 - ? (strength > 300 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - EnumChatFormatting intelligencePrefix = intelligence > 300 - ? (intelligence > 900 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) - : EnumChatFormatting.RED; - - Utils.addChatMessage( g + "Stats : " + healthPrefix + health + EnumChatFormatting.RED + "\u2764 " + - defencePrefix + defence + EnumChatFormatting.GREEN + "\u2748 " + - strengthPrefix + strength + EnumChatFormatting.RED + "\u2741 " + - intelligencePrefix + intelligence + EnumChatFormatting.AQUA + "\u270e "); - } - float bankBalance = Utils.getElementAsFloat(Utils.getElement(profileInfo, "banking.balance"), -1); - float purseBalance = Utils.getElementAsFloat(Utils.getElement(profileInfo, "coin_purse"), 0); - - long networth; - if (NotEnoughUpdates.INSTANCE.config.profileViewer.useSoopyNetworth) { - ProfileViewer.Profile.SoopyNetworthData nwData = profile.getSoopyNetworth(null, () -> {}); - if (nwData == null) { - networth = -2l; - } else { - networth = nwData.getTotal(); - } - } else { - networth = profile.getNetWorth(null); - } - - float money = Math.max(bankBalance + purseBalance, networth); - EnumChatFormatting moneyPrefix = money > 50 * 1000 * 1000 ? - (money > 200 * 1000 * 1000 - ? EnumChatFormatting.GREEN - : EnumChatFormatting.YELLOW) : EnumChatFormatting.RED; - Utils.addChatMessage( g + "Purse: " + moneyPrefix + Utils.shortNumberFormat(purseBalance, 0) + g + " - Bank: " + - (bankBalance == -1 ? EnumChatFormatting.YELLOW + "N/A" : moneyPrefix + - (isMe ? "4.8b" : Utils.shortNumberFormat(bankBalance, 0))) + - (networth > 0 ? g + " - Net: " + moneyPrefix + Utils.shortNumberFormat(networth, 0) : "")); - - overallScore += Math.min(2, money / (100f * 1000 * 1000)); - - String activePet = Utils.getElementAsString( - Utils.getElement(profile.getPetsInfo(null), "active_pet.type"), - "None Active" - ); - String activePetTier = Utils.getElementAsString(Utils.getElement( - profile.getPetsInfo(null), - "active_pet.tier" - ), "UNKNOWN"); - - String col = NotEnoughUpdates.petRarityToColourMap.get(activePetTier); - if (col == null) col = EnumChatFormatting.LIGHT_PURPLE.toString(); - - Utils.addChatMessage(g + "Pet : " + col + WordUtils.capitalizeFully(activePet.replace("_", " "))); - - String overall = "Skywars Main"; - if (isMe) { - overall = Utils.chromaString("Literally the best player to exist"); // ego much - } else if (overallScore < 5 && (bankBalance + purseBalance) > 500 * 1000 * 1000) { - overall = EnumChatFormatting.GOLD + "Bill Gates"; - } else if (overallScore > 9) { - overall = Utils.chromaString("Didn't even think this score was possible"); - } else if (overallScore > 8) { - overall = Utils.chromaString("Mentally unstable"); - } else if (overallScore > 7) { - overall = EnumChatFormatting.GOLD + "Why though 0.0"; - } else if (overallScore > 5.5) { - overall = EnumChatFormatting.GOLD + "Bro stop playing"; - } else if (overallScore > 4) { - overall = EnumChatFormatting.GREEN + "Kinda sweaty"; - } else if (overallScore > 3) { - overall = EnumChatFormatting.YELLOW + "Alright I guess"; - } else if (overallScore > 2) { - overall = EnumChatFormatting.YELLOW + "Ender Non"; - } else if (overallScore > 1) { - overall = EnumChatFormatting.RED + "Played SkyBlock"; - } - - Utils.addChatMessage(g + "Overall score: " + overall + g + " (" + Math.round(overallScore * 10) / 10f + ")"); - - peekCommandExecutorService.shutdownNow(); - } else { - peekScheduledFuture = peekCommandExecutorService.schedule(this, 200, TimeUnit.MILLISECONDS); - } - } - }, 200, TimeUnit.MILLISECONDS); - } - }); - } - - @Override - public List<String> addTabCompletionOptions(ICommandSender sender, String[] args, BlockPos pos) { - if (args.length != 1) return null; - - String lastArg = args[args.length - 1]; - List<String> playerMatches = new ArrayList<>(); - for (EntityPlayer player : Minecraft.getMinecraft().theWorld.playerEntities) { - String playerName = player.getName(); - if (playerName.toLowerCase().startsWith(lastArg.toLowerCase())) { - playerMatches.add(playerName); - } - } - return playerMatches; - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/PvCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/PvCommand.java deleted file mode 100644 index 2d5c05f4..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/PvCommand.java +++ /dev/null @@ -1,41 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.profile; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import net.minecraft.client.Minecraft; -import net.minecraft.command.ICommandSender; -import org.apache.commons.lang3.StringUtils; - -public class PvCommand extends ViewProfileCommand { - - public PvCommand() { - super("pv"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) { - if (!NotEnoughUpdates.INSTANCE.isOnSkyblock()) { - Minecraft.getMinecraft().thePlayer.sendChatMessage("/pv " + StringUtils.join(args, " ")); - } else { - super.processCommand(sender, args); - } - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/ViewProfileCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/ViewProfileCommand.java deleted file mode 100644 index 26468e39..00000000 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/ViewProfileCommand.java +++ /dev/null @@ -1,102 +0,0 @@ -/* - * Copyright (C) 2022 NotEnoughUpdates contributors - * - * This file is part of NotEnoughUpdates. - * - * NotEnoughUpdates is free software: you can redistribute it - * and/or modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation, either - * version 3 of the License, or (at your option) any later version. - * - * NotEnoughUpdates is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. - */ - -package io.github.moulberry.notenoughupdates.commands.profile; - -import io.github.moulberry.notenoughupdates.NotEnoughUpdates; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import io.github.moulberry.notenoughupdates.profileviewer.GuiProfileViewer; -import io.github.moulberry.notenoughupdates.util.Utils; -import net.minecraft.client.Minecraft; -import net.minecraft.client.renderer.OpenGlHelper; -import net.minecraft.command.ICommandSender; -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.util.BlockPos; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.EnumChatFormatting; - -import java.util.ArrayList; -import java.util.List; -import java.util.function.Consumer; - -public class ViewProfileCommand extends ClientCommandBase { - - public static final Consumer<String[]> RUNNABLE = (args) -> { - if (!OpenGlHelper.isFramebufferEnabled()) { - Utils.addChatMessage(EnumChatFormatting.RED + - "Some parts of the profile viewer do not work with OptiFine Fast Render. Go to ESC > Options > Video Settings > Performance > Fast Render to disable it."); - - } - if (NotEnoughUpdates.INSTANCE.config.apiData.apiKey == null || - NotEnoughUpdates.INSTANCE.config.apiData.apiKey.trim().isEmpty()) { - Utils.addChatMessage(EnumChatFormatting.RED + - "Can't view profile, an API key is not set. Run /api new and put the result in settings."); - } else if (args.length == 0) { - NotEnoughUpdates.profileViewer.getProfileByName(Minecraft.getMinecraft().thePlayer.getName(), profile -> { - if (profile == null) { - Utils.addChatMessage(EnumChatFormatting.RED + - "Invalid player name/API key. Maybe the API is down? Try /api new."); - } else { - profile.resetCache(); - NotEnoughUpdates.INSTANCE.openGui = new GuiProfileViewer(profile); - } - }); - } else if (args.length > 1) { - Utils.addChatMessage(EnumChatFormatting.RED + - "Too many arguments. Usage: /neuprofile [name]"); - } else { - NotEnoughUpdates.profileViewer.getProfileByName(args[0], profile -> { - if (profile == null) { - Utils.addChatMessage(EnumChatFormatting.RED + "Invalid player name/api key. Maybe the API is down? Try /api new."); - } else { - profile.resetCache(); - NotEnoughUpdates.INSTANCE.openGui = new GuiProfileViewer(profile); - } - }); - } - }; - - public ViewProfileCommand() { - this("neuprofile"); - } - - public ViewProfileCommand(String name) { - super(name); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) { - RUNNABLE.accept(args); - } - - @Override - public List<String> addTabCompletionOptions(ICommandSender sender, String[] args, BlockPos pos) { - if (args.length != 1) return null; - - String lastArg = args[args.length - 1]; - List<String> playerMatches = new ArrayList<>(); - for (EntityPlayer player : Minecraft.getMinecraft().theWorld.playerEntities) { - String playerName = player.getName(); - if (playerName.toLowerCase().startsWith(lastArg.toLowerCase())) { - playerMatches.add(playerName); - } - } - return playerMatches; - } -} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/listener/RenderListener.java b/src/main/java/io/github/moulberry/notenoughupdates/listener/RenderListener.java index 5ccd6767..65724c65 100644 --- a/src/main/java/io/github/moulberry/notenoughupdates/listener/RenderListener.java +++ b/src/main/java/io/github/moulberry/notenoughupdates/listener/RenderListener.java @@ -26,7 +26,6 @@ import io.github.moulberry.notenoughupdates.NEUApi; import io.github.moulberry.notenoughupdates.NEUOverlay; import io.github.moulberry.notenoughupdates.NotEnoughUpdates; import io.github.moulberry.notenoughupdates.auction.CustomAHGui; -import io.github.moulberry.notenoughupdates.commands.profile.ViewProfileCommand; import io.github.moulberry.notenoughupdates.core.GuiScreenElementWrapper; import io.github.moulberry.notenoughupdates.dungeons.DungeonWin; import io.github.moulberry.notenoughupdates.miscfeatures.AbiphoneWarning; @@ -1062,7 +1061,14 @@ public class RenderListener { if (tag.hasKey("SkullOwner") && tag.getCompoundTag("SkullOwner").hasKey("Name")) { String username = tag.getCompoundTag("SkullOwner").getString("Name"); Utils.playPressSound(); - ViewProfileCommand.RUNNABLE.accept(new String[]{username}); + NotEnoughUpdates.profileViewer.getProfileByName(username, profile -> { + if (profile == null) { + Utils.addChatMessage("${RED}Invalid player name/API key. Maybe the API is down? Try /api new."); + } else { + profile.resetCache(); + NotEnoughUpdates.INSTANCE.openGui = new GuiProfileViewer(profile); + } + }); } } } diff --git a/src/main/java/io/github/moulberry/notenoughupdates/miscfeatures/FairySouls.java b/src/main/java/io/github/moulberry/notenoughupdates/miscfeatures/FairySouls.java index 5a611178..97aa25d4 100644 --- a/src/main/java/io/github/moulberry/notenoughupdates/miscfeatures/FairySouls.java +++ b/src/main/java/io/github/moulberry/notenoughupdates/miscfeatures/FairySouls.java @@ -26,7 +26,6 @@ import com.google.gson.JsonObject; import com.google.gson.JsonSyntaxException; import io.github.moulberry.notenoughupdates.NotEnoughUpdates; import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe; -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; import io.github.moulberry.notenoughupdates.core.util.StringUtils; import io.github.moulberry.notenoughupdates.core.util.render.RenderUtils; import io.github.moulberry.notenoughupdates.util.Constants; @@ -34,8 +33,6 @@ import io.github.moulberry.notenoughupdates.util.SBInfo; import io.github.moulberry.notenoughupdates.util.Utils; import lombok.var; import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; import net.minecraft.util.BlockPos; import net.minecraft.util.EnumChatFormatting; import net.minecraftforge.client.event.ClientChatReceivedEvent; @@ -56,7 +53,6 @@ import java.io.OutputStreamWriter; import java.lang.reflect.Type; import java.nio.charset.StandardCharsets; import java.util.ArrayList; -import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.List; @@ -87,6 +83,14 @@ public class FairySouls { return instance; } + public boolean isTrackSouls() { + return trackSouls; + } + + public boolean isShowSouls() { + return showSouls; + } + @SubscribeEvent public void onWorldLoad(WorldEvent.Load event) { currentLocation = null; @@ -379,25 +383,6 @@ public class FairySouls { Utils.addChatMessage(s); } - private static void printHelp() { - print(""); - print(EnumChatFormatting.DARK_PURPLE.toString() + EnumChatFormatting.BOLD + " NEU Fairy Soul Waypoint Guide"); - print(EnumChatFormatting.LIGHT_PURPLE + "Shows waypoints for every fairy soul in your world"); - print(EnumChatFormatting.LIGHT_PURPLE + "Clicking a fairy soul automatically removes it from the list"); - if (!NotEnoughUpdates.INSTANCE.config.hidden.dev) { - print(EnumChatFormatting.DARK_RED + "" + EnumChatFormatting.OBFUSCATED + "Ab" + EnumChatFormatting.RESET + - EnumChatFormatting.DARK_RED + "!" + EnumChatFormatting.RESET + EnumChatFormatting.RED + - " This feature cannot and will not work in Dungeons. " + EnumChatFormatting.DARK_RED + "!" + - EnumChatFormatting.OBFUSCATED + "Ab"); - } - print(EnumChatFormatting.GOLD.toString() + EnumChatFormatting.BOLD + " Commands:"); - print(EnumChatFormatting.YELLOW + "/neusouls help - Display this message"); - print(EnumChatFormatting.YELLOW + "/neusouls on/off - Enable/disable showing waypoint markers"); - print(EnumChatFormatting.YELLOW + - "/neusouls clear/unclear - Marks every waypoint in your current world as completed/uncompleted"); - print(""); - } - @SubscribeEvent(priority = EventPriority.HIGHEST, receiveCanceled = true) public void onChatReceived(ClientChatReceivedEvent event) { if (!trackSouls || event.type == 2) return; @@ -407,53 +392,4 @@ public class FairySouls { markClosestSoulFound(); } } - - public static class FairySoulsCommand extends ClientCommandBase { - public FairySoulsCommand() { - super("neusouls"); - } - - @Override - public List<String> getCommandAliases() { - return Collections.singletonList("fairysouls"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - if (args.length != 1) { - printHelp(); - return; - } - - String subcommand = args[0].toLowerCase(); - switch (subcommand) { - case "help": - printHelp(); - break; - case "on": - case "enable": - if (!FairySouls.instance.trackSouls) { - print( - EnumChatFormatting.RED + "Fairy soul tracking is off, enable it using /neu before using this command"); - return; - } - print(EnumChatFormatting.DARK_PURPLE + "Enabled fairy soul waypoints"); - FairySouls.getInstance().setShowFairySouls(true); - break; - case "off": - case "disable": - FairySouls.getInstance().setShowFairySouls(false); - print(EnumChatFormatting.DARK_PURPLE + "Disabled fairy soul waypoints"); - break; - case "clear": - FairySouls.getInstance().markAllAsFound(); - break; - case "unclear": - FairySouls.getInstance().markAllAsMissing(); - break; - default: - print(EnumChatFormatting.RED + "Unknown subcommand: " + subcommand); - } - } - } } diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/CataCommand.java b/src/main/java/io/github/moulberry/notenoughupdates/mixins/AccessorCommandHandler.java index afc47418..73d31196 100644 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/profile/CataCommand.java +++ b/src/main/java/io/github/moulberry/notenoughupdates/mixins/AccessorCommandHandler.java @@ -1,5 +1,5 @@ /* - * Copyright (C) 2022 NotEnoughUpdates contributors + * Copyright (C) 2023 NotEnoughUpdates contributors * * This file is part of NotEnoughUpdates. * @@ -17,20 +17,17 @@ * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. */ -package io.github.moulberry.notenoughupdates.commands.profile; +package io.github.moulberry.notenoughupdates.mixins; -import io.github.moulberry.notenoughupdates.profileviewer.GuiProfileViewer; -import net.minecraft.command.ICommandSender; +import net.minecraft.command.CommandHandler; +import net.minecraft.command.ICommand; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.gen.Accessor; -public class CataCommand extends ViewProfileCommand { +import java.util.Set; - public CataCommand() { - super("cata"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) { - GuiProfileViewer.currentPage = GuiProfileViewer.ProfileViewerPage.DUNGEON; - super.processCommand(sender, args); - } +@Mixin(CommandHandler.class) +public interface AccessorCommandHandler { + @Accessor("commandSet") + Set<ICommand> neuGetClientCommands(); } diff --git a/src/main/java/io/github/moulberry/notenoughupdates/util/brigadier/NEUBrigadierHook.kt b/src/main/java/io/github/moulberry/notenoughupdates/util/brigadier/NEUBrigadierHook.kt new file mode 100644 index 00000000..668c412a --- /dev/null +++ b/src/main/java/io/github/moulberry/notenoughupdates/util/brigadier/NEUBrigadierHook.kt @@ -0,0 +1,109 @@ +/* + * Copyright (C) 2023 Linnea Gräf + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.util.brigadier + +import com.mojang.brigadier.ParseResults +import com.mojang.brigadier.exceptions.CommandSyntaxException +import com.mojang.brigadier.suggestion.Suggestions +import com.mojang.brigadier.tree.CommandNode +import net.minecraft.command.CommandBase +import net.minecraft.command.ICommandSender +import net.minecraft.util.BlockPos +import net.minecraft.util.ChatComponentText +import net.minecraft.util.EnumChatFormatting.RED +import net.minecraft.util.EnumChatFormatting.YELLOW +import java.util.concurrent.CompletableFuture +import java.util.function.Predicate + +/** + * Hook for converting brigadier commands to normal legacy Minecraft commands (string array style). + */ +class NEUBrigadierHook( + val brigadierRoot: BrigadierRoot, + val commandNode: CommandNode<DefaultSource>, + val aliases: List<String> +) : CommandBase() { + /** + * Runs before the command gets executed. Return false to prevent execution. + */ + var beforeCommand: Predicate<ParseResults<DefaultSource>>? = null + + override fun getCommandName(): String { + return commandNode.name + } + + override fun getCommandAliases(): List<String> { + return aliases + } + + data class Usage( + val path: String, + val help: String?, + ) + + + override fun getCommandUsage(sender: ICommandSender): String { + return brigadierRoot.getAllUsages("/$commandName", commandNode, mutableSetOf()).joinToString("\n") { "${it.path} - ${it.help ?: "Missing help"}"} + } + + private fun getText(args: Array<out String>) = "${commandNode.name} ${args.joinToString(" ")}" + + override fun processCommand(sender: ICommandSender, args: Array<out String>) { + val results = brigadierRoot.parseText.apply(sender to getText(args).trim()) + if (beforeCommand?.test(results) == false) + return + try { + brigadierRoot.dispatcher.execute(results) + } catch (syntax: CommandSyntaxException) { + brigadierRoot.getAllUsages("/$commandName", commandNode, mutableSetOf()).forEach { + sender.addChatMessage(ChatComponentText("${YELLOW}[NEU] ${it.path} - ${it.help}")) + } + } + } + + // We love async tab completion (may end up requiring pressing tab multiple times, but uhhhhh .get() bad) + private var lastCompletionText: String? = null + private var lastCompletion: CompletableFuture<Suggestions>? = null + override fun addTabCompletionOptions( + sender: ICommandSender, + args: Array<out String>, + pos: BlockPos + ): List<String> { + val originalText = getText(args) + var lc: CompletableFuture<Suggestions>? = null + if (lastCompletionText == originalText) { + lc = lastCompletion + } + if (lc == null) { + lastCompletion?.cancel(true) + val results = brigadierRoot.parseText.apply(sender to originalText) + lc = brigadierRoot.dispatcher.getCompletionSuggestions(results) + } + lastCompletion = lc + lastCompletionText = originalText + val suggestions = lastCompletion?.getNow(null) ?: return emptyList() + return suggestions.list.map { it.text } + } + + override fun canCommandSenderUseCommand(sender: ICommandSender): Boolean { + return true // Permissions are checked by brigadier instead (or by the beforeCommand hook) + } + +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/DevTestCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/DevTestCommand.kt new file mode 100644 index 00000000..805ff114 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/DevTestCommand.kt @@ -0,0 +1,256 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.dev + +import com.mojang.brigadier.arguments.StringArgumentType +import io.github.moulberry.notenoughupdates.BuildFlags +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.core.config.GuiPositionEditor +import io.github.moulberry.notenoughupdates.core.util.MiscUtils +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.miscfeatures.FishingHelper +import io.github.moulberry.notenoughupdates.miscfeatures.customblockzones.CustomBiomes +import io.github.moulberry.notenoughupdates.miscfeatures.customblockzones.LocationChangeEvent +import io.github.moulberry.notenoughupdates.miscgui.GuiPriceGraph +import io.github.moulberry.notenoughupdates.miscgui.minionhelper.MinionHelperManager +import io.github.moulberry.notenoughupdates.util.PronounDB +import io.github.moulberry.notenoughupdates.util.SBInfo +import io.github.moulberry.notenoughupdates.util.TabListUtils +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.client.Minecraft +import net.minecraft.client.gui.GuiScreen +import net.minecraft.command.ICommandSender +import net.minecraft.entity.player.EntityPlayer +import net.minecraft.launchwrapper.Launch +import net.minecraft.util.ChatComponentText +import net.minecraft.util.EnumChatFormatting.* +import net.minecraft.util.EnumParticleTypes +import net.minecraftforge.common.MinecraftForge +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import java.util.function.Predicate +import kotlin.math.floor + +@NEUAutoSubscribe +class DevTestCommand { + companion object { + val DEV_TESTERS: List<String> = mutableListOf( + "d0e05de7-6067-454d-beae-c6d19d886191", // moulberry + "66502b40-6ac1-4d33-950d-3df110297aab", // lucycoconut + "a5761ff3-c710-4cab-b4f4-3e7f017a8dbf", // ironm00n + "5d5c548a-790c-4fc8-bd8f-d25b04857f44", // ariyio + "53924f1a-87e6-4709-8e53-f1c7d13dc239", // throwpo + "d3cb85e2-3075-48a1-b213-a9bfb62360c1", // lrg89 + "0b4d470f-f2fb-4874-9334-1eaef8ba4804", // dediamondpro + "ebb28704-ed85-43a6-9e24-2fe9883df9c2", // lulonaut + "698e199d-6bd1-4b10-ab0c-52fedd1460dc", // craftyoldminer + "8a9f1841-48e9-48ed-b14f-76a124e6c9df", // eisengolem + "a7d6b3f1-8425-48e5-8acc-9a38ab9b86f7", // whalker + "0ce87d5a-fa5f-4619-ae78-872d9c5e07fe", // ascynx + "a049a538-4dd8-43f8-87d5-03f09d48b4dc", // egirlefe + "7a9dc802-d401-4d7d-93c0-8dd1bc98c70d", // efefury + "bb855349-dfd8-4125-a750-5fc2cf543ad5" // hannibal2 + ) + val SPECIAL_KICK = "SPECIAL_KICK" + + val DEV_FAIL_STRINGS = arrayOf( + "No.", + "I said no.", + "You aren't allowed to use this.", + "Are you sure you want to use this? Type 'Yes' in chat.", + "Are you sure you want to use this? Type 'Yes' in chat.", + "Lmao you thought", + "Ok please stop", + "What do you want from me?", + "This command almost certainly does nothing useful for you", + "Ok, this is the last message, after this it will repeat", + "No.", + "I said no.", + "Dammit. I thought that would work. Uhh...", + "\u00a7dFrom \u00a7c[ADMIN] Minikloon\u00a77: If you use that command again, I'll have to ban you", + SPECIAL_KICK, + "Ok, this is actually the last message, use the command again and you'll crash I promise" + ) + + fun isDeveloper(commandSender: ICommandSender): Boolean { + return DEV_TESTERS.contains((commandSender as? EntityPlayer)?.uniqueID?.toString()) + || Launch.blackboard.get("fml.deobfuscatedEnvironment") as Boolean + + } + } + + var devFailIndex = 0 + fun canPlayerExecute(commandSender: ICommandSender): Boolean { + return isDeveloper(commandSender) + } + + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + val hook = event.command("neudevtest") { + requires { + canPlayerExecute(it) + } + thenLiteralExecute("profileinfo") { + val currentProfile = SBInfo.getInstance().currentProfile + val gamemode = SBInfo.getInstance().getGamemodeForProfile(currentProfile) + reply("${GOLD}You are on Profile $currentProfile with the mode $gamemode") + }.withHelp("Display information about your current profile") + thenLiteralExecute("buildflags") { + reply("BuildFlags: \n" + + BuildFlags.getAllFlags().entries + .joinToString(("\n")) { (key, value) -> " + $key - $value" }) + }.withHelp("List the flags with which NEU was built") + thenLiteral("exteditor") { + thenArgument("editor", StringArgumentType.string()) { newEditor -> + thenExecute { + NotEnoughUpdates.INSTANCE.config.hidden.externalEditor = this[newEditor] + reply("You changed your external editor to: §Z${this[newEditor]}") + } + }.withHelp("Change the editor used to edit repo files") + thenExecute { + reply("Your external editor is: §Z${NotEnoughUpdates.INSTANCE.config.hidden.externalEditor}") + } + }.withHelp("See your current external editor for repo files") + thenLiteral("pricetest") { + thenArgument("item", StringArgumentType.string()) { item -> + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = GuiPriceGraph(this[item]) + } + }.withHelp("Display the price graph for an item by id") + thenExecute { + NotEnoughUpdates.INSTANCE.manager.auctionManager.updateBazaar() + } + }.withHelp("Update the price data from the bazaar") + thenLiteralExecute("zone") { + val target = Minecraft.getMinecraft().objectMouseOver.blockPos + ?: Minecraft.getMinecraft().thePlayer.position + val zone = CustomBiomes.INSTANCE.getSpecialZone(target) + listOf( + ChatComponentText("Showing Zone Info for: $target"), + ChatComponentText("Zone: " + (zone?.name ?: "null")), + ChatComponentText("Location: " + SBInfo.getInstance().getLocation()), + ChatComponentText("Biome: " + CustomBiomes.INSTANCE.getCustomBiome(target)) + ).forEach { component -> + reply(component) + } + MinecraftForge.EVENT_BUS.post( + LocationChangeEvent( + SBInfo.getInstance().getLocation(), SBInfo + .getInstance() + .getLocation() + ) + ) + }.withHelp("Display information about the special block zone at your cursor (Custom Texture Regions)") + thenLiteralExecute("positiontest") { + NotEnoughUpdates.INSTANCE.openGui = GuiPositionEditor() + }.withHelp("Open the gui position editor") + thenLiteral("pt") { + thenArgument("particle", EnumArgumentType.enum<EnumParticleTypes>()) { particle -> + thenExecute { + FishingHelper.type = this[particle] + reply("Fishing particles set to ${FishingHelper.type}") + } + } + } + thenLiteralExecute("dev") { + NotEnoughUpdates.INSTANCE.config.hidden.dev = !NotEnoughUpdates.INSTANCE.config.hidden.dev + reply("§e[NEU] Dev mode " + if (NotEnoughUpdates.INSTANCE.config.hidden.dev) "§aenabled" else "§cdisabled") + }.withHelp("Toggle developer mode") + thenLiteralExecute("saveconfig") { + NotEnoughUpdates.INSTANCE.saveConfig() + reply("Config saved") + }.withHelp("Force sync the config to disk") + thenLiteralExecute("searchmode") { + NotEnoughUpdates.INSTANCE.config.hidden.firstTimeSearchFocus = true + reply(AQUA.toString() + "I would never search") + }.withHelp("Reset your search data to redisplay the search tutorial") + thenLiteralExecute("bluehair") { + PronounDB.test() + }.withHelp("Test the pronoundb integration") + thenLiteral("opengui") { + thenArgumentExecute("class", StringArgumentType.string()) { className -> + try { + NotEnoughUpdates.INSTANCE.openGui = + Class.forName(this[className]).newInstance() as GuiScreen + reply("Opening gui: " + NotEnoughUpdates.INSTANCE.openGui) + } catch (e: Exception) { + e.printStackTrace() + reply("Failed to open this GUI.") + } + }.withHelp("Open a gui by class name") + } + thenLiteralExecute("center") { + val x = floor(Minecraft.getMinecraft().thePlayer.posX) + 0.5f + val z = floor(Minecraft.getMinecraft().thePlayer.posZ) + 0.5f + Minecraft.getMinecraft().thePlayer.setPosition(x, Minecraft.getMinecraft().thePlayer.posY, z) + reply("Literal hacks") + }.withHelp("Center yourself on the block you are currently standing (like using AOTE)") + thenLiteral("minion") { + thenArgumentExecute("args", RestArgumentType) { arg -> + MinionHelperManager.getInstance().handleCommand(arrayOf("minion") + this[arg].split(" ")) + }.withHelp("Minion related commands. Not yet integrated in brigadier") + } + thenLiteralExecute("copytablist") { + val tabList = TabListUtils.getTabList().joinToString("\n", postfix = "\n") + MiscUtils.copyToClipboard(tabList) + reply("Copied tablist to clipboard!") + }.withHelp("Copy the tab list") + thenLiteralExecute("useragent") { + thenArgumentExecute("newuseragent", RestArgumentType) { userAgent -> + reply("Setting your user agent to ${this[userAgent]}") + NotEnoughUpdates.INSTANCE.config.hidden.customUserAgent = this[userAgent] + }.withHelp("Set a custom user agent for all HTTP requests") + thenExecute { + reply("Resetting your user agent.") + NotEnoughUpdates.INSTANCE.config.hidden.customUserAgent = null + } + }.withHelp("Reset the custom user agent") + } + hook.beforeCommand = Predicate { + if (!canPlayerExecute(it.context.source)) { + if (devFailIndex !in DEV_FAIL_STRINGS.indices) { + throw object : Error("L") { + @Override + fun printStackTrace() { + throw Error("L") + } + } + } + val text = DEV_FAIL_STRINGS[devFailIndex++] + if (text == SPECIAL_KICK) { + val component = ChatComponentText("\u00a7cYou are permanently banned from this server!") + component.appendText("\n") + component.appendText("\n\u00a77Reason: \u00a7rI told you not to run the command - Moulberry") + component.appendText("\n\u00a77Find out more: \u00a7b\u00a7nhttps://www.hypixel.net/appeal") + component.appendText("\n") + component.appendText("\n\u00a77Ban ID: \u00a7r#49871982") + component.appendText("\n\u00a77Sharing your Ban ID may affect the processing of your appeal!") + Minecraft.getMinecraft().netHandler.networkManager.closeChannel(component) + } else { + it.context.source.addChatMessage(ChatComponentText("$RED$text")) + } + false + } else { + true + } + } + } + +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/DiagCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/DiagCommand.kt new file mode 100644 index 00000000..3e5e7b9b --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/DiagCommand.kt @@ -0,0 +1,78 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.dev + +import com.mojang.brigadier.arguments.BoolArgumentType.bool +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.miscfeatures.CrystalMetalDetectorSolver +import io.github.moulberry.notenoughupdates.miscfeatures.CrystalWishingCompassSolver +import io.github.moulberry.notenoughupdates.options.customtypes.NEUDebugFlag +import io.github.moulberry.notenoughupdates.util.brigadier.* +import io.github.moulberry.notenoughupdates.util.brigadier.EnumArgumentType.Companion.enum +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +// Why is this not merged into /neudevtest +@NEUAutoSubscribe +class DiagCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neudiag") { + thenLiteral("metal") { + thenLiteral("center") { + thenArgumentExecute("usecenter", bool()) { useCenter -> + CrystalMetalDetectorSolver.setDebugDoNotUseCenter(this[useCenter]) + reply("Center coordinates-based solutions ${if (this[useCenter]) "enabled" else "disabled"}") + }.withHelp("Toggle coordinate based solutions") + } + thenExecute { + CrystalMetalDetectorSolver.logDiagnosticData(true) + reply("Enabled metal detector diagnostic logging.") + } + }.withHelp("Enable metal detector diagnostics") + thenLiteralExecute("wishing") { + CrystalWishingCompassSolver.getInstance().logDiagnosticData(true) + reply("Enabled wishing compass diagnostic logging") + }.withHelp("Enable wishing compass diagnostic logging") + thenLiteral("debug") { + thenLiteralExecute("list") { + reply("Here are all flags:\n${NEUDebugFlag.getFlagList()}") + }.withHelp("List all debug diagnostic logging flags") + thenLiteral("setflag") { + thenArgument("flag", enum<NEUDebugFlag>()) { flag -> + thenArgumentExecute("enable", bool()) { enable -> + val debugFlags = NotEnoughUpdates.INSTANCE.config.hidden.debugFlags + if (this[enable]) { + debugFlags.add(this[flag]) + } else { + debugFlags.remove(this[flag]) + } + reply("${if(this[enable]) "Enabled" else "Disabled"} the flag ${this[flag]}.") + }.withHelp("Enable or disable a diagnostic logging stream") + } + } + thenExecute { + reply("Effective debug flags: \n${NEUDebugFlag.getEnabledFlags()}") + } + }.withHelp("Log diagnostic data.") + } + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/NEUStatsCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/NEUStatsCommand.kt new file mode 100644 index 00000000..7035aaa3 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/NEUStatsCommand.kt @@ -0,0 +1,209 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.dev + +import com.mojang.brigadier.context.CommandContext +import com.sun.management.OperatingSystemMXBean +import com.sun.management.UnixOperatingSystemMXBean +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.DiscordMarkdownBuilder +import io.github.moulberry.notenoughupdates.util.HastebinUploader +import io.github.moulberry.notenoughupdates.util.SBInfo +import io.github.moulberry.notenoughupdates.util.brigadier.reply +import io.github.moulberry.notenoughupdates.util.brigadier.thenExecute +import io.github.moulberry.notenoughupdates.util.brigadier.thenLiteralExecute +import io.github.moulberry.notenoughupdates.util.brigadier.withHelp +import net.minecraft.client.Minecraft +import net.minecraft.client.renderer.OpenGlHelper +import net.minecraft.command.ICommandSender +import net.minecraft.util.EnumChatFormatting.DARK_RED +import net.minecraft.util.EnumChatFormatting.GREEN +import net.minecraftforge.common.ForgeVersion +import net.minecraftforge.fml.client.FMLClientHandler +import net.minecraftforge.fml.common.Loader +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import org.lwjgl.opengl.Display +import org.lwjgl.opengl.GL11 +import java.awt.Toolkit +import java.awt.datatransfer.StringSelection +import java.lang.management.ManagementFactory +import java.util.concurrent.CompletableFuture +import javax.management.JMX +import javax.management.ObjectName + +@NEUAutoSubscribe +class NEUStatsCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("stats", "neustats") { + thenLiteralExecute("modlist") { + clipboardAndSendMessage( + DiscordMarkdownBuilder() + .also(::appendModList) + .toString() + ) + }.withHelp("Copy the mod list to your clipboard") + thenLiteralExecute("full") { + clipboardAndSendMessage( + DiscordMarkdownBuilder() + .also(::appendStats) + .also(::appendModList) + .toString() + ) + }.withHelp("Copy the full list of all NEU stats and your mod list to your clipboard") + thenLiteralExecute("dump") { + reply("${GREEN}This will upload a dump of the java classes your game has loaded how big they are and how many there are. This can take a few seconds as it is uploading to HasteBin.") + uploadDataUsageDump().thenAccept { + clipboardAndSendMessage(it) + } + }.withHelp("Dump all loaded classes and their memory usage and copy that to your clipboard.") + thenExecute { + clipboardAndSendMessage( + DiscordMarkdownBuilder() + .also(::appendStats) + .also { + if (Loader.instance().activeModList.size <= 15) appendModList(it) + } + .toString() + ) + } + }.withHelp("Copy a list of NEU relevant stats to your clipboard for debugging purposes") + } + interface DiagnosticCommandMXBean { + fun gcClassHistogram(array: Array<String>): String + } + + private fun uploadDataUsageDump(): CompletableFuture<String?> { + return CompletableFuture.supplyAsync { + try { + val server = + ManagementFactory.getPlatformMBeanServer() + val objectName = + ObjectName.getInstance("com.sun.management:type=DiagnosticCommand") + val proxy = JMX.newMXBeanProxy( + server, + objectName, + DiagnosticCommandMXBean::class.java + ) + HastebinUploader.upload( + proxy.gcClassHistogram(emptyArray()).replace("[", "[]"), + HastebinUploader.Mode.NORMAL + ) + } catch (e: Exception) { + null + } + } + + } + + + private fun getMemorySize(): Long { + try { + return (ManagementFactory.getOperatingSystemMXBean() as OperatingSystemMXBean).totalPhysicalMemorySize + } catch (e: java.lang.Exception) { + try { + return (ManagementFactory.getOperatingSystemMXBean() as UnixOperatingSystemMXBean).totalPhysicalMemorySize + } catch (ignored: java.lang.Exception) { /*IGNORE*/ + } + } + return -1 + } + + val ONE_MB = 1024L * 1024L + private fun appendStats(builder: DiscordMarkdownBuilder) { + val maxMemory = Runtime.getRuntime().maxMemory() + val totalMemory = Runtime.getRuntime().totalMemory() + val freeMemory = Runtime.getRuntime().freeMemory() + val currentMemory = totalMemory - freeMemory + builder.category("System Stats") + builder.append("OS", System.getProperty("os.name")) + builder.append("CPU", OpenGlHelper.getCpu()) + builder.append( + "Display", + String.format("%dx%d (%s)", Display.getWidth(), Display.getHeight(), GL11.glGetString(GL11.GL_VENDOR)) + ) + builder.append("GPU", GL11.glGetString(GL11.GL_RENDERER)) + builder.append("GPU Driver", GL11.glGetString(GL11.GL_VERSION)) + if (getMemorySize() > 0) + builder.append( + "Maximum Memory", + "${getMemorySize() / ONE_MB}MB" + ) + builder.append("Shaders", ("" + OpenGlHelper.isFramebufferEnabled()).uppercase()) + builder.category("Java Stats") + builder.append( + "Java", + "${System.getProperty("java.version")} ${if (Minecraft.getMinecraft().isJava64bit) 64 else 32}bit", + ) + builder.append( + "Memory", String.format( + "% 2d%% %03d/%03dMB", + currentMemory * 100L / maxMemory, + currentMemory / ONE_MB, + maxMemory / ONE_MB + ) + ) + builder.append( + "Memory Allocated", + String.format("% 2d%% %03dMB", totalMemory * 100L / maxMemory, totalMemory / ONE_MB) + ) + builder.category("Game Stats") + builder.append("FPS", Minecraft.getDebugFPS().toString()) + builder.append("Loaded Mods", Loader.instance().activeModList.size) + builder.append("Forge", ForgeVersion.getVersion()) + builder.append("Optifine", if (FMLClientHandler.instance().hasOptifine()) "TRUE" else "FALSE") + builder.category("Neu Settings") + builder.append("API Key", if (NotEnoughUpdates.INSTANCE.config.apiData.apiKey.isEmpty()) "FALSE" else "TRUE") + builder.append("On SkyBlock", if (NotEnoughUpdates.INSTANCE.hasSkyblockScoreboard()) "TRUE" else "FALSE") + builder.append( + "Mod Version", + Loader.instance().indexedModList[NotEnoughUpdates.MODID]!!.displayVersion + ) + builder.append("SB Profile", SBInfo.getInstance().currentProfile) + builder.append("Has Advanced Tab", if (SBInfo.getInstance().hasNewTab) "TRUE" else "FALSE") + builder.category("Repo Stats") + builder.append("Last Commit", NotEnoughUpdates.INSTANCE.manager.latestRepoCommit) + builder.append("Loaded Items", NotEnoughUpdates.INSTANCE.manager.itemInformation.size.toString()) + } + + private fun appendModList(builder: DiscordMarkdownBuilder): DiscordMarkdownBuilder { + builder.category("Mods Loaded") + Loader.instance().activeModList.forEach { + builder.append(it.name, "${it.source} (${it.displayVersion})") + } + return builder + } + + fun CommandContext<ICommandSender>.clipboardAndSendMessage(data: String?) { + if (data == null) { + reply("${DARK_RED}Error occurred trying to perform command.") + return + } + try { + val clipboard = StringSelection(data) + Toolkit.getDefaultToolkit().systemClipboard.setContents(clipboard, null) + reply("${GREEN}Dev info copied to clipboard.") + } catch (ignored: Exception) { + reply("${DARK_RED}Could not copy to clipboard.") + } + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/PackDevCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/PackDevCommand.kt new file mode 100644 index 00000000..fceacfab --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/PackDevCommand.kt @@ -0,0 +1,165 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.dev + +import com.mojang.brigadier.arguments.DoubleArgumentType.doubleArg +import com.mojang.brigadier.builder.ArgumentBuilder +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.core.util.MiscUtils +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.client.Minecraft +import net.minecraft.client.entity.AbstractClientPlayer +import net.minecraft.command.ICommandSender +import net.minecraft.entity.Entity +import net.minecraft.entity.EntityLiving +import net.minecraft.entity.EntityLivingBase +import net.minecraft.entity.item.EntityArmorStand +import net.minecraft.entity.player.EntityPlayer +import net.minecraft.item.ItemStack +import net.minecraft.util.EnumChatFormatting +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class PackDevCommand { + + fun <T : EntityLivingBase, U : ArgumentBuilder<ICommandSender, U>> U.npcListCommand( + name: String, + singleCommand: String, + multipleCommand: String, + clazz: Class<T>, + provider: () -> List<Entity> + ) { + fun getEntities(distance: Double): List<T> { + val distanceSquared = distance * distance + val thePlayer = Minecraft.getMinecraft().thePlayer + return provider() + .asSequence() + .filterIsInstance(clazz) + .filter { it != thePlayer } + .filter { it.getDistanceSqToEntity(thePlayer) < distanceSquared } + .toList() + } + + thenLiteral(singleCommand) { + thenArgumentExecute("distance", doubleArg(0.0)) { dist -> + val dist = this[dist] + val entity = getEntities(dist).minByOrNull { it.getDistanceSqToEntity(Minecraft.getMinecraft().thePlayer) } + if (entity == null) { + reply("No $name found within $dist blocks") + return@thenArgumentExecute + } + MiscUtils.copyToClipboard(StringBuilder().appendEntityData(entity).toString().trim()) + reply("Copied data to clipboard") + }.withHelp("Find the nearest $name and copy data about them to your clipboard") + } + thenLiteral(multipleCommand) { + thenArgumentExecute("distance", doubleArg(0.0)) { dist -> + val dist = this[dist] + val entity = getEntities(dist) + val sb = StringBuilder() + reply("Found ${entity.size} ${name}s") + if (entity.isNotEmpty()) { + entity.forEach { + sb.appendEntityData(it) + } + MiscUtils.copyToClipboard(sb.toString().trim()) + + reply("Copied data to clipboard") + } + }.withHelp("Find all $name within range and copy data about them to your clipboard") + } + } + + fun StringBuilder.appendEntityData(entity: EntityLivingBase) { + if (entity is EntityPlayer) { + append("Player UUID: ") + appendLine(entity.uniqueID) + if (entity is AbstractClientPlayer) { + append("Entity Texture Id: ") + appendLine(entity.locationSkin.resourcePath?.replace("skins/", "")) + } + } + append("Custom Name Tag: ") + appendLine(entity.customNameTag ?: "null") + append("Mob: ") + appendLine(entity.name) + append("Entity Id: ") + appendLine(entity.entityId) + + appendItemData("Item", entity.heldItem) + + for ((slot, name) in listOf("Boots", "Leggings", "Chestplate", "Helmet").withIndex()) { + val armorPiece = entity.getCurrentArmor(slot) + appendItemData(name, armorPiece) + } + appendLine() + appendLine() + } + + fun StringBuilder.appendItemData(name: String, item: ItemStack?) { + append("$name: ") + if (item != null) { + appendLine(item) + append("$name Display Name") + appendLine(item.displayName) + append("$name Tag Compound: ") + val compound = item.tagCompound + if (compound == null) { + appendLine("null") + } else { + appendLine(compound) + append("$name Tag Compound Extra Attributes") + appendLine(compound.getTag("ExtraAttributes")) + } + } else { + appendLine("null") + } + + } + + + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neupackdev") { + npcListCommand("Player", "getplayer", "getplayers", AbstractClientPlayer::class.java) { + Minecraft.getMinecraft().theWorld.playerEntities + } + npcListCommand("NPC", "getnpc", "getnpcs", AbstractClientPlayer::class.java) { + Minecraft.getMinecraft().theWorld.playerEntities.filter { it.uniqueID?.version() != 4 } + } + npcListCommand("mob", "getmob", "getmobs", EntityLiving::class.java) { + Minecraft.getMinecraft().theWorld.loadedEntityList + } + npcListCommand("armor stand", "getarmorstand", "getarmorstands", EntityArmorStand::class.java) { + Minecraft.getMinecraft().theWorld.loadedEntityList + } + thenExecute { + NotEnoughUpdates.INSTANCE.packDevEnabled = !NotEnoughUpdates.INSTANCE.packDevEnabled + if (NotEnoughUpdates.INSTANCE.packDevEnabled) { + reply("${EnumChatFormatting.GREEN}Enabled pack developer mode.") + } else { + reply("${EnumChatFormatting.RED}Disabled pack developer mode.") + } + } + }.withHelp("Toggle pack developer mode") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/SimpleDevCommands.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/SimpleDevCommands.kt new file mode 100644 index 00000000..95a6500e --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/dev/SimpleDevCommands.kt @@ -0,0 +1,110 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.dev + +import com.mojang.brigadier.arguments.FloatArgumentType.floatArg +import com.mojang.brigadier.arguments.StringArgumentType.string +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.dungeons.DungeonWin +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.miscfeatures.NullzeeSphere +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.client.entity.EntityPlayerSP +import net.minecraft.event.ClickEvent +import net.minecraft.util.BlockPos +import net.minecraft.util.ChatComponentText +import net.minecraft.util.ResourceLocation +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import java.util.function.Consumer + +@NEUAutoSubscribe +class SimpleDevCommands { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neureloadrepo") { + thenExecute { + NotEnoughUpdates.INSTANCE.manager.reloadRepository() + reply("Reloaded repository.") + } + }.withHelp("Reload the NEU data repository from disk (not from network)") + event.command("neudungeonwintest") { + thenArgumentExecute("file", string()) { file -> + DungeonWin.TEAM_SCORE = ResourceLocation("notenoughupdates:dungeon_win/${this[file].lowercase()}.png") + reply("Changed the dungeon win display") + }.withHelp("Change the dungeon win test to load from a file") + thenExecute { + DungeonWin.displayWin() + } + }.withHelp("Display the dungeon win pop up") + event.command("neuenablestorage") { + thenLiteralExecute("disable") { + NotEnoughUpdates.INSTANCE.config.storageGUI.enableStorageGUI3 = true + NotEnoughUpdates.INSTANCE.saveConfig() + reply("Disabled the NEU storage overlay. Click here to enable again") { + chatStyle.chatClickEvent = ClickEvent( + ClickEvent.Action.SUGGEST_COMMAND, + "/neuenablestorage" + ) + } + }.withHelp("Disable the neu storage overlay") + thenExecute { + NotEnoughUpdates.INSTANCE.config.storageGUI.enableStorageGUI3 = true + NotEnoughUpdates.INSTANCE.saveConfig() + reply("Enabled the NEU storage overlay. Click here to disable again") { + chatStyle.chatClickEvent = ClickEvent( + ClickEvent.Action.SUGGEST_COMMAND, + "/neuenablestorage disable" + ) + } + } + }.withHelp("Enable the neu storage overlay") + event.command("neuzeesphere") { + thenLiteralExecute("on") { + NullzeeSphere.enabled = true + reply("Enabled nullzee sphere") + }.withHelp("Enable nullzee sphere") + thenLiteralExecute("off") { + NullzeeSphere.enabled = false + reply("Disabled nullzee sphere") + }.withHelp("Disable nullzee sphere") + thenLiteralExecute("setcenter") { + val p = source as EntityPlayerSP + NullzeeSphere.centerPos = BlockPos(p.posX, p.posY, p.posZ) + NullzeeSphere.overlayVBO = null + reply("Set center to ${NullzeeSphere.centerPos}") + }.withHelp("Set the center of the nullzee sphere") + thenArgumentExecute("radius", floatArg(0F)) { size -> + NullzeeSphere.size = this[size] + NullzeeSphere.overlayVBO = null + reply("Set size to ${this[size]}") + }.withHelp("Set the radius of the nullzee sphere") + } + event.command("neuresetrepo") { + thenExecute { + NotEnoughUpdates.INSTANCE.manager + .userFacingRepositoryReload() + .thenAccept { it + it.forEach(::reply) + } + } + }.withHelp("Reload the NEU data repository from network") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/FeaturesCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/FeaturesCommand.kt new file mode 100644 index 00000000..6cc4e255 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/FeaturesCommand.kt @@ -0,0 +1,65 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.help + +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.Constants +import io.github.moulberry.notenoughupdates.util.Utils +import io.github.moulberry.notenoughupdates.util.brigadier.reply +import io.github.moulberry.notenoughupdates.util.brigadier.thenExecute +import io.github.moulberry.notenoughupdates.util.brigadier.withHelp +import net.minecraft.event.ClickEvent +import net.minecraft.util.ChatComponentText +import net.minecraft.util.EnumChatFormatting +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class FeaturesCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neufeatures") { + thenExecute { + reply("") + val url = Constants.MISC?.get("featureslist")?.asString + if (url == null) { + Utils.showOutdatedRepoNotification() + return@thenExecute + } + + if (Utils.openUrl(url)) { + reply( + EnumChatFormatting.DARK_PURPLE.toString() + "" + EnumChatFormatting.BOLD + "NEU" + EnumChatFormatting.RESET + + EnumChatFormatting.GOLD + "> Opening Feature List in browser." + ) + } else { + val clickTextFeatures = ChatComponentText( + (EnumChatFormatting.DARK_PURPLE.toString() + "" + EnumChatFormatting.BOLD + "NEU" + EnumChatFormatting.RESET + + EnumChatFormatting.GOLD + "> Click here to open the Feature List in your browser.") + ) + clickTextFeatures.chatStyle = + Utils.createClickStyle(ClickEvent.Action.OPEN_URL, url) + reply(clickTextFeatures) + } + reply("") + } + }.withHelp("List all of NEUs features") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/HelpCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/HelpCommand.kt new file mode 100644 index 00000000..1b4f817e --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/HelpCommand.kt @@ -0,0 +1,95 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.help + +import com.mojang.brigadier.arguments.StringArgumentType.string +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class HelpCommand { + val neuHelpMessages = listOf( + "§5§lNotEnoughUpdates commands", + "§6/neu §7- Opens the main NEU GUI.", + "§6/pv §b?{name} §2ⴵ §r§7- Opens the profile viewer", + "§6/neusouls {on/off/clear/unclear} §r§7- Shows waypoints to fairy souls.", + "§6/neubuttons §r§7- Opens a GUI which allows you to customize inventory buttons.", + "§6/neuec §r§7- Opens the enchant colour GUI.", + "§6/join {floor} §r§7- Short Command to join a Dungeon. §lNeed a Party of 5 People§r§7 {4/f7/m5}.", + "§6/neucosmetics §r§7- Opens the cosmetic GUI.", + "§6/neurename §r§7- Opens the NEU Item Customizer.", + "§6/cata §b?{name} §2ⴵ §r§7- Opens the profile viewer's Catacombs page.", + "§6/neulinks §r§7- Shows links to NEU/Moulberry.", + "§6/neuoverlay §r§7- Opens GUI Editor for quickcommands and searchbar.", + "§6/neuah §r§7- Opens NEU's custom auction house GUI.", + "§6/neucalendar §r§7- Opens NEU's custom calendar GUI.", + "§6/neucalc §r§7- Run calculations.", + "", + "§6§lOld commands:", + "§6/peek §b?{user} §2ⴵ §r§7- Shows quick stats for a user.", + "", + "§6§lDebug commands:", + "§6/neustats §r§7- Copies helpful info to the clipboard.", + "§6/neustats modlist §r§7- Copies mod list info to clipboard.", + "§6/neuresetrepo §r§7- Deletes all repo files.", + "§6/neureloadrepo §r§7- Debug command with repo.", + "", + "§6§lDev commands:", + "§6/neupackdev §r§7- pack creator command - getnpc, getmob(s), getarmorstand(s), getall. Optional radius argument for all." + ) + val neuDevHelpMessages = listOf( + "§6/neudevtest §r§7- dev test command", + "§6/neuzeephere §r§7- sphere", + "§6/neudungeonwintest §r§7- displays the dungeon win screen" + ) + val helpInfo = listOf( + "", + "§7Commands marked with a §2\"ⴵ\"§7 require an api key. You can set your api key via \"/api new\" or by manually putting it in the api field in \"/neu\"", + "", + "§7Arguments marked with a §b\"?\"§7 are optional.", + "", + "§6§lScroll up to see everything" + ) + + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neuhelp") { + thenArgumentExecute("command", string()) { commandName -> + val commandNode = event.dispatcher.root.getChild(this[commandName]) + if (commandNode == null) { + reply("Could not find NEU command with name ${this[commandName]}") + return@thenArgumentExecute + } + reply(event.brigadierRoot.getAllUsages("/${this[commandName]}", commandNode).joinToString("\n"){ + "${it.path} - ${it.help}" + }) + }.withHelp("Display help for a specific NEU command") + thenExecute { + neuHelpMessages.forEach(::reply) + if (NotEnoughUpdates.INSTANCE.config.hidden.dev) + neuDevHelpMessages.forEach(::reply) + helpInfo.forEach(::reply) + } + }.withHelp("Display a list of all NEU commands") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/LinksCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/LinksCommand.kt new file mode 100644 index 00000000..957948ae --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/LinksCommand.kt @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.help + +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.Utils +import io.github.moulberry.notenoughupdates.util.brigadier.reply +import io.github.moulberry.notenoughupdates.util.brigadier.thenExecute +import io.github.moulberry.notenoughupdates.util.brigadier.withHelp +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class LinksCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neulinks") { + thenExecute { + val manager = NotEnoughUpdates.INSTANCE.manager + val updateJsonFile = manager.repoLocation.resolve("update.json") + if (!updateJsonFile.exists()) { + Utils.showOutdatedRepoNotification() + return@thenExecute + } + try { + val updateJson = manager.getJsonFromFile(updateJsonFile) + NotEnoughUpdates.INSTANCE.displayLinks(updateJson, 0) + } catch (_: Exception) { + Utils.showOutdatedRepoNotification() + } + } + }.withHelp("Display links for Moulberry and NEU") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/SettingsCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/SettingsCommand.kt new file mode 100644 index 00000000..fe58c807 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/SettingsCommand.kt @@ -0,0 +1,53 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.help + +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.core.GuiScreenElementWrapper +import io.github.moulberry.notenoughupdates.core.config.struct.ConfigProcessor +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.options.NEUConfigEditor +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class SettingsCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neu", "neusettings") { + thenArgument("search", RestArgumentType) { search -> + suggestsList(ConfigProcessor.create(NotEnoughUpdates.INSTANCE.config).keys.toList()) + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = GuiScreenElementWrapper( + NEUConfigEditor( + NotEnoughUpdates.INSTANCE.config, + this[search] + ) + ) + } + }.withHelp("Search the NEU settings") + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = + GuiScreenElementWrapper(NEUConfigEditor(NotEnoughUpdates.INSTANCE.config)) + } + }.withHelp("Open the NEU settings") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/StorageViewerWhyCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/StorageViewerWhyCommand.kt new file mode 100644 index 00000000..782eaf3d --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/help/StorageViewerWhyCommand.kt @@ -0,0 +1,48 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ +package io.github.moulberry.notenoughupdates.commands.help + +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.NotificationHandler +import io.github.moulberry.notenoughupdates.util.brigadier.thenExecute +import io.github.moulberry.notenoughupdates.util.brigadier.withHelp +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class StorageViewerWhyCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neustwhy") { + thenExecute { + NotificationHandler.displayNotification( + listOf( + "§eStorage Viewer", + "§7Currently, the storage viewer requires you to click twice", + "§7in order to switch between pages. This is because Hypixel", + "§7has not yet added a shortcut command to go to any enderchest/", + "§7storage page.", + "§7While it is possible to send the second click", + "§7automatically, doing so violates Hypixel's new mod rules." + ), true + ) + } + }.withHelp("Display information about why you have to click twice in the NEU storage overlay") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/AhCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/AhCommand.kt new file mode 100644 index 00000000..c7d80487 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/AhCommand.kt @@ -0,0 +1,67 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.auction.CustomAHGui +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.Utils +import io.github.moulberry.notenoughupdates.util.brigadier.RestArgumentType +import io.github.moulberry.notenoughupdates.util.brigadier.get +import io.github.moulberry.notenoughupdates.util.brigadier.reply +import io.github.moulberry.notenoughupdates.util.brigadier.thenArgumentExecute +import net.minecraft.util.EnumChatFormatting.RED +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import java.util.function.Predicate + +@NEUAutoSubscribe +class AhCommand { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + val hook = event.command("neuah") { + + thenArgumentExecute("search", RestArgumentType) { search -> + if (NotEnoughUpdates.INSTANCE.config.apiData.apiKey == null || + NotEnoughUpdates.INSTANCE.config.apiData.apiKey.isBlank() + ) { + reply("${RED}Can't open NEU AH: an api key is not set. Run /api new and put the result in settings.") + return@thenArgumentExecute + } + NotEnoughUpdates.INSTANCE.openGui = CustomAHGui() + NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.lastOpen = System.currentTimeMillis() + NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.clearSearch() + NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.updateSearch() + + val search = this[search] + + NotEnoughUpdates.INSTANCE.manager.auctionManager.customAH.setSearch( + if (search.isBlank() && NotEnoughUpdates.INSTANCE.config.neuAuctionHouse.saveLastSearch) + null else search + ) + } + } + hook.beforeCommand = Predicate { + if (!NotEnoughUpdates.INSTANCE.hasSkyblockScoreboard()) + Utils.addChatMessage("${RED}You must be on SkyBlock to use this feature.") + NotEnoughUpdates.INSTANCE.hasSkyblockScoreboard() + } + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/DungeonCommands.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/DungeonCommands.kt new file mode 100644 index 00000000..3b721df5 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/DungeonCommands.kt @@ -0,0 +1,144 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import com.google.gson.JsonObject +import com.mojang.brigadier.arguments.StringArgumentType.string +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.dungeons.GuiDungeonMapEditor +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.block.material.MapColor +import net.minecraft.client.Minecraft +import net.minecraft.item.ItemMap +import net.minecraft.util.EnumChatFormatting.GREEN +import net.minecraft.util.EnumChatFormatting.RED +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import java.awt.Color + +@NEUAutoSubscribe +class DungeonCommands { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("dh") { + thenExecute { + Minecraft.getMinecraft().thePlayer.sendChatMessage("/warp dungeon_hub") + } + }.withHelp("Warps to the dungeon hub") + event.command("dn") { + thenExecute { + Minecraft.getMinecraft().thePlayer.sendChatMessage("/warp dungeon_hub") + reply("Warping to...") + reply("Deez nuts lmao") + } + }.withHelp("Warps to the dungeon nuts") + event.command("join") { + thenArgument("floor", string()) { floor -> + suggestsList((1..7).flatMap { listOf("f$it", "m$it") }) + thenExecute { + val floor = this[floor] + val prefix = if (floor.startsWith("m")) "master_catacombs" else "catacombs" + val level = floor.lastOrNull()?.digitToIntOrNull() + val cmd = "/joindungeon $prefix ${floor.lastOrNull()}" + reply("Running command: $cmd") + Minecraft.getMinecraft().thePlayer.sendChatMessage(cmd) + } + }.withHelp("Join a dungeon floor with a party of 5") + } + event.command("neumap") { + thenLiteral("reset") { + thenExecute { + NotEnoughUpdates.INSTANCE.colourMap = null + reply("Reset color map") + } + requiresDev() + }.withHelp("Reset the colour map") + thenLiteral("save") { + thenArgument("filename", string()) { fileName -> + requiresDev() + thenExecute { + val stack = Minecraft.getMinecraft().thePlayer.heldItem + if (stack == null || stack.item !is ItemMap) { + reply("Please hold a map item") + return@thenExecute + } + val map = stack.item as ItemMap + val mapData = map.getMapData(stack, Minecraft.getMinecraft().theWorld) + if (mapData == null) { + reply("Could not grab map data (empty map)") + return@thenExecute + } + val json = JsonObject() + for (i in 0 until (128 * 128)) { + val x = i % 128 + val y = i / 128 + val j = mapData.colors[i].toInt() and 255 + val c = if (j / 4 == 0) { + Color((i + i / 128 and 1) * 8 + 16 shl 24, true) + } else { + Color(MapColor.mapColorArray[j / 4].getMapColor(j and 3), true) + } + json.addProperty("$x:$y", c.rgb) + } + try { + NotEnoughUpdates.INSTANCE.manager.configLocation.resolve("maps").mkdirs() + NotEnoughUpdates.INSTANCE.manager.writeJson( + json, + NotEnoughUpdates.INSTANCE.manager.configLocation.resolve("maps/${this[fileName]}.json") + ) + reply("${GREEN}Saved to file.") + } catch (e: Exception) { + e.printStackTrace() + reply("${RED}Failed to save.") + } + } + }.withHelp("Save a colour map from an item") + } + thenLiteral("load") { + thenArgument("filename", string()) { fileName -> + requiresDev() + thenExecute { + val json = NotEnoughUpdates.INSTANCE.manager.getJsonFromFile( + NotEnoughUpdates.INSTANCE.manager.configLocation.resolve( + "maps/${this[fileName]}.json" + ) + ) + NotEnoughUpdates.INSTANCE.colourMap = (0 until 128).map { x -> + (0 until 128).map { y -> + val key = "$x:$y" + json[key]?.asInt?.let { Color(it, true) } ?: Color(0, 0, 0, 0) + }.toTypedArray() + }.toTypedArray() + for (x in 0..127) { + for (y in 0..127) { + NotEnoughUpdates.INSTANCE.colourMap[x][y] = Color(0, 0, 0, 0) + } + } + reply("Loaded colour map from file") + } + }.withHelp("Load a colour map from a file") + } + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = GuiDungeonMapEditor(null) + } + }.withHelp("Open the dungeon map editor") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/FairySoulsCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/FairySoulsCommand.kt new file mode 100644 index 00000000..1d766646 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/FairySoulsCommand.kt @@ -0,0 +1,62 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.miscfeatures.FairySouls +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.util.EnumChatFormatting.DARK_PURPLE +import net.minecraft.util.EnumChatFormatting.RED +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class FairySoulsCommand { + + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neusouls", "fairysouls") { + val enable = thenLiteralExecute("enable") { + if (!FairySouls.getInstance().isTrackSouls) { + reply("${RED}Fairy soul tracking is off, enable it using /neu before using this command") + return@thenLiteralExecute + } + reply("${DARK_PURPLE}Enabled fairy soul waypoints") + FairySouls.getInstance().setShowFairySouls(true) + }.withHelp("Show fairy soul waypoints") + thenLiteral("on") { redirect(enable) } + val disable = thenLiteralExecute("disable") { + FairySouls.getInstance().setShowFairySouls(false) + reply("${DARK_PURPLE}Disabled fairy soul waypoints") + }.withHelp("Hide fairy soul waypoints") + thenLiteral("off") { redirect(disable) } + val clear = thenLiteralExecute("clear") { + FairySouls.getInstance().markAllAsFound() + // Reply handled by mark all as found + }.withHelp("Mark all fairy souls in your current world as found") + thenLiteral("markfound") { redirect(clear) } + val unclear = thenLiteralExecute("unclear") { + FairySouls.getInstance().markAllAsMissing() + // Reply handled by mark all as missing + }.withHelp("Mark all fairy souls in your current world as not found") + thenLiteral("marknotfound") { redirect(unclear) } + } + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/MiscCommands.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/MiscCommands.kt new file mode 100644 index 00000000..c86eb4fe --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/MiscCommands.kt @@ -0,0 +1,169 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import com.mojang.brigadier.arguments.StringArgumentType.string +import io.github.moulberry.notenoughupdates.NEUManager +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.cosmetics.GuiCosmetics +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.miscgui.CalendarOverlay +import io.github.moulberry.notenoughupdates.miscgui.GuiItemCustomize +import io.github.moulberry.notenoughupdates.util.Calculator +import io.github.moulberry.notenoughupdates.util.Calculator.CalculatorException +import io.github.moulberry.notenoughupdates.util.MinecraftExecutor +import io.github.moulberry.notenoughupdates.util.PronounDB +import io.github.moulberry.notenoughupdates.util.Utils +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.client.Minecraft +import net.minecraft.client.renderer.OpenGlHelper +import net.minecraft.util.ChatComponentText +import net.minecraft.util.EnumChatFormatting.* +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import java.text.DecimalFormat +import java.util.* +import java.util.concurrent.CompletableFuture + +@NEUAutoSubscribe +class MiscCommands { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neucalc", "neucalculator") { + thenArgumentExecute("calculation", RestArgumentType) { calculation -> + val calculation = this[calculation] + try { + val calculate = Calculator.calculate(calculation) + val formatter = DecimalFormat("#,##0.##") + val formatted = formatter.format(calculate) + reply("$WHITE$calculation $YELLOW= $GREEN$formatted") + } catch (e: CalculatorException) { + reply( + "${RED}Error during calculation: ${e.message}\n${WHITE}${calculation.substring(0, e.offset)}" + + "${DARK_RED}${calculation.substring(e.offset, e.length + e.offset)}${GRAY}" + + calculation.substring(e.length + e.offset) + ) + } + }.withHelp("Calculate an expression") + thenExecute { + reply( + "§5It's a calculator.\n" + + "§eFor Example §b/neucalc 3m*7k§e.\n" + + "§eYou can also use suffixes (k, m, b, t, s)§e.\n" + + "§eThe \"s\" suffix acts as 64.\n" + + "§eTurn on Sign Calculator in /neu misc to also support this in sign popups and the neu search bar." + ) + } + }.withHelp("Display help for NEUs calculator") + event.command("neucalendar") { + thenExecute { + Minecraft.getMinecraft().thePlayer.closeScreen() + CalendarOverlay.setEnabled(true) + NotEnoughUpdates.INSTANCE.sendChatMessage("/calendar") + } + }.withHelp("Display NEUs custom calendar overlay") + event.command("neucosmetics") { + thenExecute { + if (!OpenGlHelper.isFramebufferEnabled() && NotEnoughUpdates.INSTANCE.config.notifications.doFastRenderNotif) { + reply( + "${RED}NEU Cosmetics do not work with OptiFine Fast Render. Go to ESC > Options > Video Settings > Performance > Fast Render to disable it." + ) + } + NotEnoughUpdates.INSTANCE.openGui = GuiCosmetics() + } + }.withHelp("Equip NEU cosmetics") + event.command("neucustomize", "neurename") { + thenExecute { + val held = Minecraft.getMinecraft().thePlayer.heldItem + if (held == null) { + reply("${RED}You can't customize your hand...") + return@thenExecute + } + val heldUUID = NEUManager.getUUIDForItem(held) + if (heldUUID == null) { + reply("${RED}This item does not have an UUID, so it cannot be customized.") + return@thenExecute + } + + NotEnoughUpdates.INSTANCE.openGui = GuiItemCustomize(held, heldUUID) + } + }.withHelp("Customize your items") + event.command("neupronouns", "neuliberals") { + thenArgument("user", string()) {user-> + suggestsList { Minecraft.getMinecraft().theWorld.playerEntities.map { it.name } } + thenArgumentExecute("platform", string()) { platform -> + fetchPronouns(this[platform], this[user]) + }.withHelp("Look up someones pronouns using their username on a platform") + thenExecute { + fetchPronouns("minecraft", this[user]) + } + }.withHelp("Look up someones pronouns using their minecraft username") + } + event.command("neuupdate", "neuupdates", "enoughupdates") { + thenLiteralExecute("check") { + NotEnoughUpdates.INSTANCE.autoUpdater.displayUpdateMessageIfOutOfDate() + }.withHelp("Check for updates") + thenLiteralExecute("scheduledownload") { + NotEnoughUpdates.INSTANCE.autoUpdater.scheduleDownload() + }.withHelp("Queue a new version of NEU to be downloaded") + thenLiteralExecute("updatemodes") { + reply("§bTo ensure we do not accidentally corrupt your mod folder, we can only offer support for auto-updates on system with certain capabilities for file deletions (specifically unix systems). You can still manually update your files") + }.withHelp("Display an explanation why you cannot auto update") + } + } + + fun fetchPronouns(platform: String, user: String) { + val nc = Minecraft.getMinecraft().ingameGUI.chatGUI + val id = Random().nextInt() + nc.printChatMessageWithOptionalDeletion(ChatComponentText("§e[NEU] Fetching Pronouns..."), id) + + val pronouns = if ("minecraft" == platform) { + val c = CompletableFuture<UUID>() + NotEnoughUpdates.profileViewer.getPlayerUUID(user) { uuidString -> + if (uuidString == null) { + c.completeExceptionally(NullPointerException()) + } else { + c.complete(Utils.parseDashlessUUID(uuidString)) + } + } + c.thenCompose { minecraftPlayer -> + PronounDB.getPronounsFor(minecraftPlayer) + } + } else { + PronounDB.getPronounsFor(platform, user) + } + pronouns.handleAsync({ pronounChoice, throwable -> + if (throwable != null || !pronounChoice.isPresent) { + nc.printChatMessageWithOptionalDeletion(ChatComponentText("§e[NEU] §4Failed to fetch pronouns."), id) + return@handleAsync null + } + val betterPronounChoice = pronounChoice.get() + nc.printChatMessageWithOptionalDeletion( + ChatComponentText("§e[NEU] Pronouns for §b$user §eon §b$platform§e:"), id + ) + betterPronounChoice.render().forEach { + nc.printChatMessage(ChatComponentText("§e[NEU] §a$it")) + } + null + }, MinecraftExecutor.OffThread) + + } + +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/PeekCommand.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/PeekCommand.kt new file mode 100644 index 00000000..61fa6029 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/PeekCommand.kt @@ -0,0 +1,318 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import com.mojang.brigadier.arguments.StringArgumentType.string +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.profileviewer.ProfileViewer +import io.github.moulberry.notenoughupdates.util.Utils +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.client.Minecraft +import net.minecraft.util.ChatComponentText +import net.minecraft.util.EnumChatFormatting.* +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import org.apache.commons.lang3.text.WordUtils +import java.util.* +import java.util.concurrent.* + +@NEUAutoSubscribe +class PeekCommand { + + var future: Future<*>? = null + val executor = Executors.newScheduledThreadPool(1) + + fun executePeek(name: String) { + val chatGui = Minecraft.getMinecraft().ingameGUI.chatGUI + val id = Random().nextInt(Int.MAX_VALUE / 2) + Int.MAX_VALUE / 2 + fun deleteReply(text: String) { + chatGui.printChatMessageWithOptionalDeletion(ChatComponentText(text), id) + } + + deleteReply("$YELLOW[PEEK] Getting player information...") + + + NotEnoughUpdates.profileViewer.getProfileByName( + name + ) { profile: ProfileViewer.Profile? -> + if (profile == null) { + deleteReply("$RED[PEEK] Unknown player or the Hypixel API is down.") + } else { + profile.resetCache() + if (future?.isDone != true) { + Utils.addChatMessage( + "$RED[PEEK] New peek command was run, cancelling old one." + ) + future?.cancel(true) + } + deleteReply("$YELLOW[PEEK] Getting the player's SkyBlock profile(s)...") + val startTime = System.currentTimeMillis() + future = ForkJoinPool.commonPool().submit(object : Runnable { + override fun run() { + if (System.currentTimeMillis() - startTime > 10 * 1000) { + deleteReply("$RED[PEEK] Getting profile info took too long, aborting.") + return + } + val g = GRAY.toString() + val profileInfo = profile.getProfileInformation(null) + if (profileInfo == null) { + future = executor.schedule(this, 200, TimeUnit.MILLISECONDS) + return + } + var overallScore = 0f + val isMe = name.equals("moulberry", ignoreCase = true) + val stats = profile.getStats(null) + if (stats == null) { + future = executor.schedule(this, 200, TimeUnit.MILLISECONDS) + return + } + val skyblockInfo = profile.getSkyblockInfo(null) + if (NotEnoughUpdates.INSTANCE.config.profileViewer.useSoopyNetworth) { + deleteReply("$YELLOW[PEEK] Getting the player's Skyblock networth...") + val countDownLatch = CountDownLatch(1) + profile.getSoopyNetworth(null, Runnable { countDownLatch.countDown() }) + try { //Wait for async network request + countDownLatch.await(10, TimeUnit.SECONDS) + } catch (e: InterruptedException) { + } + + //Now it's waited for network request the data should be cached (accessed in nw section) + } + deleteReply( + "$GREEN $STRIKETHROUGH-=-$RESET$GREEN ${ + Utils.getElementAsString( + profile.hypixelProfile!!["displayname"], + name + ) + }'s Info $STRIKETHROUGH-=-" + ) + if (skyblockInfo == null) { + Utils.addChatMessage(YELLOW.toString() + "Skills API disabled!") + } else { + var totalSkillLVL = 0f + var totalSkillCount = 0f + val skills: List<String> = + mutableListOf( + "taming", + "mining", + "foraging", + "enchanting", + "farming", + "combat", + "fishing", + "alchemy", + "carpentry" + ) + for (skillName in skills) { + totalSkillLVL += skyblockInfo[skillName]!!.level + totalSkillCount++ + } + var combat = skyblockInfo["combat"]!!.level + var zombie = skyblockInfo["zombie"]!!.level + var spider = skyblockInfo["spider"]!!.level + var wolf = skyblockInfo["wolf"]!!.level + var enderman = skyblockInfo["enderman"]!!.level + var blaze = skyblockInfo["blaze"]!!.level + var avgSkillLVL = totalSkillLVL / totalSkillCount + if (isMe) { + avgSkillLVL = 6f + combat = 4f + zombie = 2f + spider = 1f + wolf = 2f + enderman = 0f + blaze = 0f + } + val combatPrefix = + if (combat > 20) (if (combat > 35) GREEN else YELLOW) else RED + val zombiePrefix = + if (zombie > 3) (if (zombie > 6) GREEN else YELLOW) else RED + val spiderPrefix = + if (spider > 3) (if (spider > 6) GREEN else YELLOW) else RED + val wolfPrefix = + if (wolf > 3) (if (wolf > 6) GREEN else YELLOW) else RED + val endermanPrefix = + if (enderman > 3) (if (enderman > 6) GREEN else YELLOW) else RED + val blazePrefix = + if (blaze > 3) (if (blaze > 6) GREEN else YELLOW) else RED + val avgPrefix = + if (avgSkillLVL > 20) (if (avgSkillLVL > 35) GREEN else YELLOW) else RED + overallScore += zombie * zombie / 81f + overallScore += spider * spider / 81f + overallScore += wolf * wolf / 81f + overallScore += enderman * enderman / 81f + overallScore += blaze * blaze / 81f + overallScore += avgSkillLVL / 20f + val cata = skyblockInfo["catacombs"]!!.level.toInt() + val cataPrefix = + if (cata > 15) (if (cata > 25) GREEN else YELLOW) else RED + overallScore += cata * cata / 2000f + Utils.addChatMessage( + g + "Combat: " + combatPrefix + Math.floor(combat.toDouble()) + .toInt() + + (if (cata > 0) "$g - Cata: $cataPrefix$cata" else "") + + g + " - AVG: " + avgPrefix + Math.floor(avgSkillLVL.toDouble()) + .toInt() + ) + Utils.addChatMessage( + g + "Slayer: " + zombiePrefix + Math.floor(zombie.toDouble()) + .toInt() + g + "-" + + spiderPrefix + Math.floor(spider.toDouble()) + .toInt() + g + "-" + + wolfPrefix + Math.floor(wolf.toDouble()).toInt() + g + "-" + + endermanPrefix + Math.floor(enderman.toDouble()) + .toInt() + g + "-" + + blazePrefix + Math.floor(blaze.toDouble()).toInt() + ) + } + val health = stats["health"].toInt() + val defence = stats["defence"].toInt() + val strength = stats["strength"].toInt() + val intelligence = stats["intelligence"].toInt() + val healthPrefix = + if (health > 800) (if (health > 1600) GREEN else YELLOW) else RED + val defencePrefix = + if (defence > 200) (if (defence > 600) GREEN else YELLOW) else RED + val strengthPrefix = + if (strength > 100) (if (strength > 300) GREEN else YELLOW) else RED + val intelligencePrefix = + if (intelligence > 300) (if (intelligence > 900) GREEN else YELLOW) else RED + Utils.addChatMessage( + g + "Stats : " + healthPrefix + health + RED + "\u2764 " + + defencePrefix + defence + GREEN + "\u2748 " + + strengthPrefix + strength + RED + "\u2741 " + + intelligencePrefix + intelligence + AQUA + "\u270e " + ) + val bankBalance = + Utils.getElementAsFloat( + Utils.getElement( + profileInfo, + "banking.balance" + ), -1f + ) + val purseBalance = + Utils.getElementAsFloat( + Utils.getElement( + profileInfo, + "coin_purse" + ), 0f + ) + val networth = if (NotEnoughUpdates.INSTANCE.config.profileViewer.useSoopyNetworth) { + val nwData = + profile.getSoopyNetworth(null, Runnable {}) + nwData?.total ?: -2L + } else { + profile.getNetWorth(null) + } + val money = + Math.max(bankBalance + purseBalance, networth.toFloat()) + val moneyPrefix = + if (money > 50 * 1000 * 1000) (if (money > 200 * 1000 * 1000) GREEN else YELLOW) else RED + Utils.addChatMessage( + g + "Purse: " + moneyPrefix + Utils.shortNumberFormat( + purseBalance.toDouble(), + 0 + ) + g + " - Bank: " + + (if (bankBalance == -1f) YELLOW.toString() + "N/A" else moneyPrefix.toString() + + if (isMe) "4.8b" else Utils.shortNumberFormat( + bankBalance.toDouble(), + 0 + )) + + if (networth > 0) "$g - Net: $moneyPrefix" + Utils.shortNumberFormat( + networth.toDouble(), + 0 + ) else "" + ) + overallScore += Math.min(2f, money / (100f * 1000 * 1000)) + val activePet = + Utils.getElementAsString( + Utils.getElement( + profile.getPetsInfo( + null + ), "active_pet.type" + ), + "None Active" + ) + val activePetTier = + Utils.getElementAsString( + Utils.getElement( + profile.getPetsInfo(null), + "active_pet.tier" + ), "UNKNOWN" + ) + var col = NotEnoughUpdates.petRarityToColourMap[activePetTier] + if (col == null) col = LIGHT_PURPLE.toString() + Utils.addChatMessage( + g + "Pet : " + col + WordUtils.capitalizeFully( + activePet.replace("_", " ") + ) + ) + var overall = "Skywars Main" + if (isMe) { + overall = + Utils.chromaString("Literally the best player to exist") // ego much + } else if (overallScore < 5 && bankBalance + purseBalance > 500 * 1000 * 1000) { + overall = GOLD.toString() + "Bill Gates" + } else if (overallScore > 9) { + overall = + Utils.chromaString("Didn't even think this score was possible") + } else if (overallScore > 8) { + overall = + Utils.chromaString("Mentally unstable") + } else if (overallScore > 7) { + overall = GOLD.toString() + "Why though 0.0" + } else if (overallScore > 5.5) { + overall = GOLD.toString() + "Bro stop playing" + } else if (overallScore > 4) { + overall = GREEN.toString() + "Kinda sweaty" + } else if (overallScore > 3) { + overall = YELLOW.toString() + "Alright I guess" + } else if (overallScore > 2) { + overall = YELLOW.toString() + "Ender Non" + } else if (overallScore > 1) { + overall = RED.toString() + "Played SkyBlock" + } + Utils.addChatMessage( + g + "Overall score: " + overall + g + " (" + Math.round( + overallScore * 10 + ) / 10f + ")" + ) + } + }) + } + } + } + + @SubscribeEvent + fun onCommand(event: RegisterBrigadierCommandEvent) { + event.command("peek") { + thenArgument("player", string()) { player -> + suggestsList { Minecraft.getMinecraft().theWorld.playerEntities.map { it.name } } + thenExecute { + executePeek(this[player]) + } + }.withHelp("Quickly glance at other peoples stats") + thenExecute { + executePeek(Minecraft.getMinecraft().thePlayer.name) + } + }.withHelp("Quickly glance at your own stats") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/ProfileViewerCommands.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/ProfileViewerCommands.kt new file mode 100644 index 00000000..8a2763f7 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/ProfileViewerCommands.kt @@ -0,0 +1,87 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import com.mojang.brigadier.arguments.StringArgumentType.string +import com.mojang.brigadier.context.CommandContext +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.profileviewer.GuiProfileViewer +import io.github.moulberry.notenoughupdates.util.brigadier.* +import net.minecraft.client.Minecraft +import net.minecraft.client.renderer.OpenGlHelper +import net.minecraft.command.ICommandSender +import net.minecraft.util.EnumChatFormatting.RED +import net.minecraftforge.fml.common.Loader +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class ProfileViewerCommands { + companion object { + fun CommandContext<ICommandSender>.openPv(name: String) { + if (!OpenGlHelper.isFramebufferEnabled()) { + reply("${RED}Some parts of the profile viewer do not work with OptiFine Fast Render. Go to ESC > Options > Video Settings > Performance > Fast Render to disable it.") + } + + if (NotEnoughUpdates.INSTANCE.config.apiData.apiKey.isNullOrBlank()) { + reply("${RED}Can't view profile, an API key is not set. Run /api new and put the result in settings.") + return + } + + NotEnoughUpdates.profileViewer.getProfileByName(name) { profile -> + if (profile == null) { + reply("${RED}Invalid player name/API key. Maybe the API is down? Try /api new.") + } else { + profile.resetCache() + NotEnoughUpdates.INSTANCE.openGui = GuiProfileViewer(profile) + } + } + } + } + + + @SubscribeEvent + fun onCommand(event: RegisterBrigadierCommandEvent) { + fun pvCommand(name: String, before: () -> Unit) { + event.command(name) { + thenExecute { + before() + openPv(Minecraft.getMinecraft().thePlayer.name) + } + thenArgument("player", string()) { player -> + suggestsList { Minecraft.getMinecraft().theWorld.playerEntities.map { it.name } } + thenExecute { + before() + openPv(this[player]) + } + }.withHelp("Open the profile viewer for a player") + }.withHelp("Open the profile viewer for yourself") + } + pvCommand("pv") {} + pvCommand("neuprofile") {} + if (!Loader.isModLoaded("skyblockextras")) + pvCommand("cata") { + GuiProfileViewer.currentPage = GuiProfileViewer.ProfileViewerPage.DUNGEON + } + + + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/ScreenOpenCommands.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/ScreenOpenCommands.kt new file mode 100644 index 00000000..7a9b8d0e --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/commands/misc/ScreenOpenCommands.kt @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.commands.misc + +import io.github.moulberry.notenoughupdates.NotEnoughUpdates +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.miscgui.GuiEnchantColour +import io.github.moulberry.notenoughupdates.miscgui.GuiInvButtonEditor +import io.github.moulberry.notenoughupdates.miscgui.NEUOverlayPlacements +import io.github.moulberry.notenoughupdates.util.brigadier.thenExecute +import io.github.moulberry.notenoughupdates.util.brigadier.withHelp +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent + +@NEUAutoSubscribe +class ScreenOpenCommands { + @SubscribeEvent + fun onCommands(event: RegisterBrigadierCommandEvent) { + event.command("neubuttons") { + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = GuiInvButtonEditor() + } + }.withHelp("Open the NEU inventory button editor") + event.command("neuec") { + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = GuiEnchantColour() + } + }.withHelp("Open the NEU custom enchant colour editor") + event.command("neuoverlay") { + thenExecute { + NotEnoughUpdates.INSTANCE.openGui = NEUOverlayPlacements() + } + }.withHelp("Open the NEU gui overlay editor") + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/events/RegisterBrigadierCommandEvent.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/events/RegisterBrigadierCommandEvent.kt new file mode 100644 index 00000000..d3e0b69a --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/events/RegisterBrigadierCommandEvent.kt @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2023 Linnea Gräf + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.events + +import com.mojang.brigadier.builder.LiteralArgumentBuilder +import io.github.moulberry.notenoughupdates.util.brigadier.BrigadierRoot +import io.github.moulberry.notenoughupdates.util.brigadier.NEUBrigadierHook +import io.github.moulberry.notenoughupdates.util.brigadier.literal +import net.minecraft.command.ICommandSender +import java.util.function.Consumer + +data class RegisterBrigadierCommandEvent(val brigadierRoot: BrigadierRoot) : NEUEvent() { + val dispatcher = brigadierRoot.dispatcher + val hooks = mutableListOf<NEUBrigadierHook>() + fun command(name: String, block: Consumer<LiteralArgumentBuilder<ICommandSender>>): NEUBrigadierHook { + return command(name) { + block.accept(this) + } + } + + fun command( + name: String, + vararg aliases: String, + block: LiteralArgumentBuilder<ICommandSender>.() -> Unit + ): NEUBrigadierHook { + val node = dispatcher.register(literal(name, block)) + for (alias in aliases) { + dispatcher.register(literal(alias) { redirect(node) }) + } + val hook = NEUBrigadierHook(brigadierRoot, node, aliases.toList()) + hooks.add(hook) + return hook + } + +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/BrigadierRoot.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/BrigadierRoot.kt new file mode 100644 index 00000000..66008044 --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/BrigadierRoot.kt @@ -0,0 +1,103 @@ +/* + * Copyright (C) 2023 Linnea Gräf + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.util.brigadier + +import com.mojang.brigadier.CommandDispatcher +import com.mojang.brigadier.ParseResults +import com.mojang.brigadier.tree.ArgumentCommandNode +import com.mojang.brigadier.tree.CommandNode +import io.github.moulberry.notenoughupdates.autosubscribe.NEUAutoSubscribe +import io.github.moulberry.notenoughupdates.events.RegisterBrigadierCommandEvent +import io.github.moulberry.notenoughupdates.util.LRUCache +import net.minecraft.command.ICommandSender +import net.minecraftforge.client.ClientCommandHandler +import java.lang.RuntimeException +import java.util.* + +@NEUAutoSubscribe +object BrigadierRoot { + private val help: MutableMap<CommandNode<DefaultSource>, String> = IdentityHashMap() + var dispatcher = CommandDispatcher<DefaultSource>() + private set + val parseText = + LRUCache.memoize<Pair<ICommandSender, String>, ParseResults<DefaultSource>>({ (sender, text) -> + dispatcher.parse(text, sender) + }, 1) + + fun getHelpForNode(node: CommandNode<DefaultSource>): String? { + return help[node] + } + + fun setHelpForNode(node: CommandNode<DefaultSource>, helpText: String) { + if (node.command == null) { + RuntimeException("Warning: Setting help on node that cannot be executed. Will be ignored").printStackTrace() + } + help[node] = helpText + } + + + fun getAllUsages( + path: String, + node: CommandNode<ICommandSender>, + visited: MutableSet<CommandNode<ICommandSender>> = mutableSetOf() + ): Sequence<NEUBrigadierHook.Usage> = sequence { + if (node in visited) return@sequence + visited.add(node) + val redirect = node.redirect + if (redirect != null) { + yieldAll(getAllUsages(path, node.redirect, visited)) + visited.remove(node) + return@sequence + } + if (node.command != null) + yield(NEUBrigadierHook.Usage(path, getHelpForNode(node))) + node.children.forEach { + val nodeName = when (it) { + is ArgumentCommandNode<*, *> -> "<${it.name}>" + else -> it.name + } + yieldAll(getAllUsages("$path $nodeName", it, visited)) + } + visited.remove(node) + } + + + fun updateHooks() = registerHooks(ClientCommandHandler.instance) + + fun registerHooks(handler: ClientCommandHandler) { + val iterator = handler.commands.entries.iterator() + while (iterator.hasNext()) { + if (iterator.next().value is NEUBrigadierHook) + iterator.remove() + } + dispatcher = CommandDispatcher() + help.clear() + parseText.clearCache() + val event = RegisterBrigadierCommandEvent(this) + event.post() + event.hooks.forEach { + if (handler.commands.containsKey(it.commandName)) { + println("Could not register command ${it.commandName}") + } else { + handler.registerCommand(it) + } + } + } +} diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/EnumArgumentType.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/EnumArgumentType.kt new file mode 100644 index 00000000..14b6ed6e --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/EnumArgumentType.kt @@ -0,0 +1,64 @@ +/* + * Copyright (C) 2023 NotEnoughUpdates contributors + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.util.brigadier + +import com.mojang.brigadier.LiteralMessage +import com.mojang.brigadier.StringReader +import com.mojang.brigadier.arguments.ArgumentType +import com.mojang.brigadier.context.CommandContext +import com.mojang.brigadier.exceptions.SimpleCommandExceptionType +import com.mojang.brigadier.suggestion.Suggestions +import com.mojang.brigadier.suggestion.SuggestionsBuilder +import java.util.concurrent.CompletableFuture + +class EnumArgumentType<T : Enum<T>>( + val values: List<T> +) : ArgumentType<T> { + companion object { + @JvmStatic + fun <T : Enum<T>> enum(values: Array<T>) = EnumArgumentType(values.toList()) + + inline fun <reified T : Enum<T>> enum() = enum(enumValues<T>()) + } + + override fun getExamples(): Collection<String> { + return values.map { it.name } + } + + override fun <S : Any?> listSuggestions( + context: CommandContext<S>, + builder: SuggestionsBuilder + ): CompletableFuture<Suggestions> { + + examples + .filter {builder.remaining.isBlank() || it.startsWith(builder.remaining, ignoreCase = true) } + .forEach { builder.suggest(it) } + return builder.buildFuture() + } + + private val invalidEnum = + SimpleCommandExceptionType(LiteralMessage("Expected one of: ${values.joinToString(", ")}")) + + override fun parse(reader: StringReader): T { + val enumName = reader.readString() + return values.find { enumName == it.name } + ?: throw invalidEnum.createWithContext(reader) + } +} diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/DhCommand.java b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/RestArgumentType.kt index 222862f9..adfdae6a 100644 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/dungeon/DhCommand.java +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/RestArgumentType.kt @@ -1,5 +1,5 @@ /* - * Copyright (C) 2022 NotEnoughUpdates contributors + * Copyright (C) 2023 NotEnoughUpdates contributors * * This file is part of NotEnoughUpdates. * @@ -17,21 +17,15 @@ * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. */ -package io.github.moulberry.notenoughupdates.commands.dungeon; +package io.github.moulberry.notenoughupdates.util.brigadier -import io.github.moulberry.notenoughupdates.commands.ClientCommandBase; -import net.minecraft.client.Minecraft; -import net.minecraft.command.CommandException; -import net.minecraft.command.ICommandSender; +import com.mojang.brigadier.StringReader +import com.mojang.brigadier.arguments.ArgumentType -public class DhCommand extends ClientCommandBase { - - public DhCommand() { - super("dh"); - } - - @Override - public void processCommand(ICommandSender sender, String[] args) throws CommandException { - Minecraft.getMinecraft().thePlayer.sendChatMessage("/warp dungeon_hub"); - } +object RestArgumentType : ArgumentType<String> { + override fun parse(reader: StringReader): String { + val remaining = reader.remaining + reader.cursor += remaining.length + return remaining + } } diff --git a/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/dsl.kt b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/dsl.kt new file mode 100644 index 00000000..17203a4b --- /dev/null +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/brigadier/dsl.kt @@ -0,0 +1,179 @@ +/* + * Copyright (C) 2023 Linnea Gräf + * + * This file is part of NotEnoughUpdates. + * + * NotEnoughUpdates is free software: you can redistribute it + * and/or modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation, either + * version 3 of the License, or (at your option) any later version. + * + * NotEnoughUpdates is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. + */ + +package io.github.moulberry.notenoughupdates.util.brigadier + +import com.mojang.brigadier.arguments.ArgumentType +import com.mojang.brigadier.builder.ArgumentBuilder +import com.mojang.brigadier.builder.LiteralArgumentBuilder +import com.mojang.brigadier.builder.RequiredArgumentBuilder +import com.mojang.brigadier.context.CommandContext +import com.mojang.brigadier.tree.ArgumentCommandNode +import com.mojang.brigadier.tree.CommandNode +import com.mojang.brigadier.tree.LiteralCommandNode +import io.github.moulberry.notenoughupdates.commands.dev.DevTestCommand +import io.github.moulberry.notenoughupdates.util.iterate +import net.minecraft.command.ICommandSender +import net.minecraft.util.ChatComponentText +import net.minecraft.util.IChatComponent +import java.lang.reflect.ParameterizedType +import java.lang.reflect.Type +import java.lang.reflect.TypeVariable + + +typealias DefaultSource = ICommandSender + + + +private fun normalizeGeneric(argument: Type): Class<*> { + return if (argument is Class<*>) { + argument + } else if (argument is TypeVariable<*>) { + normalizeGeneric(argument.bounds[0]) + } else if (argument is ParameterizedType) { + normalizeGeneric(argument.rawType) + } else { + Any::class.java + } +} + +data class TypeSafeArg<T : Any>(val name: String, val argument: ArgumentType<T>) { + val argClass by lazy { + argument.javaClass + .iterate<Class<in ArgumentType<T>>> { + it.superclass + } + .flatMap { + it.genericInterfaces.toList() + } + .filterIsInstance<ParameterizedType>() + .find { it.rawType == ArgumentType::class.java }!! + .let { + normalizeGeneric(it.actualTypeArguments[0]) + } + } + + @JvmName("getWithThis") + fun <S> CommandContext<S>.get(): T = + get(this) + + + fun <S> get(ctx: CommandContext<S>): T { + return ctx.getArgument(name, argClass) as T + } +} + +fun <T : ICommandSender, C : CommandContext<T>> C.reply(component: IChatComponent) { + source.addChatMessage(ChatComponentText("§e[NEU] ").appendSibling(component)) +} + +fun <T : ICommandSender, C : CommandContext<T>> C.reply(text: String, block: ChatComponentText.() -> Unit = {}) { + source.addChatMessage(ChatComponentText(text.split("\n").joinToString("\n") { "§e[NEU] $it" }).also(block)) +} + +operator fun <T : Any, C : CommandContext<*>> C.get(arg: TypeSafeArg<T>): T { + return arg.get(this) +} + + +fun <T : Any> argument( + name: String, + argument: ArgumentType<T>, + block: RequiredArgumentBuilder<DefaultSource, T>.(TypeSafeArg<T>) -> Unit +): RequiredArgumentBuilder<DefaultSource, T> = + RequiredArgumentBuilder.argument<DefaultSource, T>(name, argument).also { block(it, TypeSafeArg(name, argument)) } + +fun <T : ArgumentBuilder<DefaultSource, T>, AT : Any> T.thenArgument( + name: String, + argument: ArgumentType<AT>, + block: RequiredArgumentBuilder<DefaultSource, AT>.(TypeSafeArg<AT>) -> Unit +): ArgumentCommandNode<DefaultSource, AT> = argument(name, argument, block).build().also(::then) + +fun <T : ArgumentBuilder<DefaultSource, T>, AT : Any> T.thenArgumentExecute( + name: String, + argument: ArgumentType<AT>, + block: CommandContext<DefaultSource>.(TypeSafeArg<AT>) -> Unit +): ArgumentCommandNode<DefaultSource, AT> = thenArgument(name, argument) { + thenExecute { + block(it) + } +} + +fun literal( + name: String, + block: LiteralArgumentBuilder<DefaultSource>.() -> Unit = {} +): LiteralArgumentBuilder<DefaultSource> = + LiteralArgumentBuilder.literal<DefaultSource>(name).also(block) + +fun <T : ArgumentBuilder<DefaultSource, T>> T.thenLiteral( + name: String, + block: LiteralArgumentBuilder<DefaultSource>.() -> Unit +): LiteralCommandNode<DefaultSource> = + then(literal(name), block) as LiteralCommandNode<DefaultSource> + + +fun <T : ArgumentBuilder<DefaultSource, T>> T.thenLiteralExecute( + name: String, + block: CommandContext<DefaultSource>.() -> Unit +): LiteralCommandNode<DefaultSource> = + thenLiteral(name) { + thenExecute(block) + } + +fun <T : ArgumentBuilder<DefaultSource, T>, U : ArgumentBuilder<DefaultSource, U>> T.then( + node: U, + block: U.() -> Unit +): CommandNode<DefaultSource> = + node.also(block).build().also(::then) + +fun <T : ArgumentBuilder<DefaultSource, T>> T.thenExecute(block: CommandContext<DefaultSource>.() -> Unit): T = + executes { + block(it) + 1 + } + +fun <T : ArgumentBuilder<DefaultSource, T>> T.requiresDev(): T { + requires { DevTestCommand.isDeveloper(it) } + return this +} + +fun NEUBrigadierHook.withHelp(helpText: String): NEUBrigadierHook { + commandNode.withHelp(helpText) + return this +} + +fun <T : CommandNode<DefaultSource>> T.withHelp(helpText: String): T { + BrigadierRoot.setHelpForNode(this, helpText) + return this +} + +fun <A : Any, T : RequiredArgumentBuilder<DefaultSource, A>> T.suggestsList(list: List<String>) { + suggestsList { list } +} + +fun <A : Any, T : RequiredArgumentBuilder<DefaultSource, A>> T.suggestsList(list: () -> List<String>) { + suggests { context, builder -> + list().filter { it.startsWith(builder.remaining, ignoreCase = true) } + .forEach { builder.suggest(it) } + builder.buildFuture() + } +} + + + diff --git a/src/main/java/io/github/moulberry/notenoughupdates/commands/ClientCommandBase.java b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/iterate.kt index e0ae7a1a..bcfe11aa 100644 --- a/src/main/java/io/github/moulberry/notenoughupdates/commands/ClientCommandBase.java +++ b/src/main/kotlin/io/github/moulberry/notenoughupdates/util/iterate.kt @@ -1,5 +1,5 @@ /* - * Copyright (C) 2022 NotEnoughUpdates contributors + * Copyright (C) 2023 NotEnoughUpdates contributors * * This file is part of NotEnoughUpdates. * @@ -17,30 +17,12 @@ * along with NotEnoughUpdates. If not, see <https://www.gnu.org/licenses/>. */ -package io.github.moulberry.notenoughupdates.commands; +package io.github.moulberry.notenoughupdates.util -import net.minecraft.command.CommandBase; -import net.minecraft.command.ICommandSender; - -public abstract class ClientCommandBase extends CommandBase { - private final String name; - - protected ClientCommandBase(String name) { - this.name = name; - } - - @Override - public String getCommandName() { - return name; - } - - @Override - public String getCommandUsage(ICommandSender sender) { - return "/" + name; - } - - @Override - public boolean canCommandSenderUseCommand(ICommandSender sender) { - return true; - } +fun <T : Any> T.iterate(evolve: (T) -> T?): Sequence<T> = sequence { + var pointer: T? = this@iterate + while (pointer != null) { + yield(pointer) + pointer = evolve(pointer) + } } diff --git a/src/main/resources/mixins.notenoughupdates.json b/src/main/resources/mixins.notenoughupdates.json index 8877aed8..8a8b10bc 100644 --- a/src/main/resources/mixins.notenoughupdates.json +++ b/src/main/resources/mixins.notenoughupdates.json @@ -5,6 +5,7 @@ "plugin": "io.github.moulberry.notenoughupdates.envcheck.NEUMixinConfigPlugin", "compatibilityLevel": "JAVA_8", "mixins": [ + "AccessorCommandHandler", "AccessorEntityAgeable", "AccessorEntityArmorStand", "AccessorGuiPlayerTabOverlay", |