From 00cb2b43a82232b6e26627323cd63c52fe7f8bb5 Mon Sep 17 00:00:00 2001 From: Jonas Herzig Date: Sat, 5 Sep 2020 16:08:21 +0200 Subject: [PATCH] Rewrite main menu button offset to be more compatible (closes #341) In particular, we now position it relative to the realms (fallback to multiplayer) button. This removes the need for special-casing ModMenu and fixes compatibility with Better Mod Button. --- .../java/com/replaymod/core/ReplayMod.java | 3 - .../core/handler/MainMenuHandler.java | 124 ------------------ .../com/replaymod/core/versions/MCVer.java | 8 -- .../replaymod/replay/handler/GuiHandler.java | 58 ++++++-- 4 files changed, 44 insertions(+), 149 deletions(-) delete mode 100644 src/main/java/com/replaymod/core/handler/MainMenuHandler.java diff --git a/src/main/java/com/replaymod/core/ReplayMod.java b/src/main/java/com/replaymod/core/ReplayMod.java index 85a656de..29a5dccc 100644 --- a/src/main/java/com/replaymod/core/ReplayMod.java +++ b/src/main/java/com/replaymod/core/ReplayMod.java @@ -5,7 +5,6 @@ import com.replaymod.compat.ReplayModCompat; import com.replaymod.core.gui.GuiBackgroundProcesses; import com.replaymod.core.gui.GuiReplaySettings; import com.replaymod.core.gui.RestoreReplayGui; -import com.replaymod.core.handler.MainMenuHandler; import com.replaymod.core.mixin.MinecraftAccessor; import com.replaymod.core.versions.MCVer; import com.replaymod.editor.ReplayModEditor; @@ -324,8 +323,6 @@ public class ReplayMod implements @Override public void initClient() { - new MainMenuHandler().register(); - //#if MC<=10710 //$$ FML_BUS.register(this); // For runLater(Runnable) //#endif diff --git a/src/main/java/com/replaymod/core/handler/MainMenuHandler.java b/src/main/java/com/replaymod/core/handler/MainMenuHandler.java deleted file mode 100644 index 905b2761..00000000 --- a/src/main/java/com/replaymod/core/handler/MainMenuHandler.java +++ /dev/null @@ -1,124 +0,0 @@ -package com.replaymod.core.handler; - -import com.replaymod.core.mixin.GuiMainMenuAccessor; -import de.johni0702.minecraft.gui.utils.EventRegistrations; -import net.minecraft.client.MinecraftClient; -import net.minecraft.client.gui.screen.TitleScreen; -import net.minecraft.client.gui.screen.Screen; -import org.lwjgl.opengl.GL11; - -import java.util.List; - -import static com.replaymod.core.versions.MCVer.*; - -//#if MC>=11400 && MC<11600 -//$$ import net.minecraft.realms.RealmsScreenProxy; -//#endif - -//#if FABRIC>=1 -import de.johni0702.minecraft.gui.versions.callbacks.InitScreenCallback; -//#else -//$$ import net.minecraftforge.client.event.GuiScreenEvent; -//$$ import net.minecraftforge.common.MinecraftForge; -//$$ import net.minecraftforge.eventbus.api.SubscribeEvent; -//#endif - -//#if MC>=11400 -import net.minecraft.client.gui.widget.AbstractButtonWidget; -import net.minecraft.client.resource.language.I18n; -//#else -//$$ import net.minecraft.client.gui.GuiButton; -//#endif - -/** - * Moves certain buttons on the main menu upwards so we can inject our own. - */ -public class MainMenuHandler extends EventRegistrations { - //#if FABRIC>=1 - { on(InitScreenCallback.EVENT, this::onInit); } - public void onInit(Screen guiScreen, List buttonList) { - //#else - //$$ @SubscribeEvent - //$$ public void onInit(GuiScreenEvent.InitGuiEvent.Post event) { - //$$ Screen guiScreen = getGui(event); - //$$ List buttonList = getButtonList(event); - //#endif - if (guiScreen instanceof TitleScreen) { - TitleScreen gui = (TitleScreen) guiScreen; - int realmsOffset = 0; - //#if MC>=11400 - final String BUTTON_REALMS = I18n.translate("menu.online"); - for (AbstractButtonWidget button : buttonList) { - //#else - //$$ for (GuiButton button : buttonList) { - //#endif - // Buttons that aren't in a rectangle directly above our space don't need moving - if (button.x + width(button) < gui.width / 2 - 100 - || button.x > gui.width / 2 + 100 - || button.y > gui.height / 4 + 10 + 4 * 24 + 20) continue; - // Move button up to make space for one rows of buttons - // and then move back down by 10 to compensate for the space to the exit button that was already there - int offset = -1 * 24 + 10; - button.y += offset; - - //#if MC>=11400 - //#if MC>=11400 - if (BUTTON_REALMS.equals(button.getMessage())) { - //#else - //$$ if (button.id == 14) { - //#endif - realmsOffset = offset; - } - //#endif - } - //#if MC>=11400 && MC<11600 - //$$ GuiMainMenuAccessor guiA = (GuiMainMenuAccessor) gui; - //$$ if (realmsOffset != 0 && guiA.getRealmsNotification() instanceof RealmsScreenProxy) { - //$$ guiA.setRealmsNotification(new RealmsNotificationProxy((RealmsScreenProxy) guiA.getRealmsNotification(), realmsOffset)); - //$$ } - //#endif - } - } - - //#if MC>=11400 && MC<11600 - //$$ private static class RealmsNotificationProxy extends Screen { - //$$ private final RealmsScreenProxy proxy; - //$$ private final int offset; - //$$ - //$$ private RealmsNotificationProxy(RealmsScreenProxy proxy, int offset) { - //#if MC>=11400 - //$$ super(null); - //#endif - //$$ this.proxy = proxy; - //$$ this.offset = offset; - //$$ } - //$$ - //$$ @Override - //$$ public void init(MinecraftClient mc, int width, int height) { - //$$ proxy.init(mc, width, height); - //$$ } - //$$ - //$$ @Override - //$$ public void tick() { - //$$ proxy.tick(); - //$$ } - //$$ - //$$ @Override - //$$ public void render(int mouseX, int mouseY, float partialTicks) { - //$$ GL11.glTranslated(0, offset, 0); - //$$ proxy.render(mouseX, mouseY - offset, partialTicks); - //$$ GL11.glTranslated(0, -offset, 0); - //$$ } - //$$ - //$$ @Override - //$$ public boolean mouseClicked(double mouseX, double mouseY, int mouseButton) { - //$$ return proxy.mouseClicked(mouseX, mouseY - offset, mouseButton); - //$$ } - //$$ - //$$ @Override - //$$ public void removed() { - //$$ proxy.removed(); - //$$ } - //$$ } - //#endif -} diff --git a/src/main/java/com/replaymod/core/versions/MCVer.java b/src/main/java/com/replaymod/core/versions/MCVer.java index ecc51887..2822a3d4 100644 --- a/src/main/java/com/replaymod/core/versions/MCVer.java +++ b/src/main/java/com/replaymod/core/versions/MCVer.java @@ -38,7 +38,6 @@ import java.util.ArrayList; //#if MC>=11400 import com.replaymod.core.mixin.AbstractButtonWidgetAccessor; import net.minecraft.SharedConstants; -import net.minecraft.client.gui.screen.TitleScreen; import net.minecraft.client.gui.widget.ButtonWidget; import net.minecraft.client.gui.widget.AbstractButtonWidget; @@ -598,13 +597,6 @@ public class MCVer { //#endif ) { GuiScreenAccessor acc = (GuiScreenAccessor) screen; - //#if MC>=11400 - if (screen instanceof TitleScreen && isModLoaded("modmenu")) { - // Since we bypass the usual addButton, we need to manually move our buttons down - // https://github.com/Prospector/ModMenu/blob/eea70ec37581a7229142cf21df795fdacc6a7b4c/src/main/java/io/github/prospector/modmenu/mixin/TitleScreenMixin.java#L42 - button.y += 12; - } - //#endif acc.getButtons().add(button); //#if MC>=11400 acc.getChildren().add(button); diff --git a/src/main/java/com/replaymod/replay/handler/GuiHandler.java b/src/main/java/com/replaymod/replay/handler/GuiHandler.java index 29e3c988..88eea893 100644 --- a/src/main/java/com/replaymod/replay/handler/GuiHandler.java +++ b/src/main/java/com/replaymod/replay/handler/GuiHandler.java @@ -8,11 +8,12 @@ import net.minecraft.client.gui.screen.TitleScreen; import net.minecraft.client.gui.screen.multiplayer.MultiplayerScreen; import net.minecraft.client.gui.screen.Screen; import net.minecraft.client.gui.widget.AbstractButtonWidget; -import net.minecraft.client.resource.language.I18n; //#if MC>=11600 import net.minecraft.text.Text; import net.minecraft.text.TranslatableText; +//#else +//$$ import net.minecraft.client.resource.language.I18n; //#endif //#if FABRIC>=1 @@ -29,6 +30,7 @@ import net.minecraft.client.gui.widget.ButtonWidget; import java.io.IOException; import java.util.ArrayList; import java.util.List; +import java.util.Optional; import java.util.function.Consumer; import static com.replaymod.core.versions.MCVer.*; @@ -152,40 +154,48 @@ public class GuiHandler extends EventRegistrations { } } if (achievements != null && stats != null) { - moveAllButtonsDirectlyBelowUpwards(buttonList, achievements.y, - achievements.x, stats.x + width(stats)); + moveAllButtonsInRect(buttonList, + achievements.x, stats.x + width(stats), + achievements.y, Integer.MAX_VALUE, + -24); } // In 1.13+ Forge, the Options button shares one row with the Open to LAN button //#if MC<11400 //$$ if (openToLan != null) { - //$$ moveAllButtonsDirectlyBelowUpwards(buttonList, openToLan.y, - //$$ openToLan.x, openToLan.x + openToLan.width); + //$$ moveAllButtonsInRect(buttonList, + //$$ openToLan.x, openToLan.x + openToLan.width, + //$$ openToLan.y, Integer.MAX_VALUE, + //$$ -24); //$$ } //#endif } } /** - * Moves all buttons that are within a rectangle below a certain y coordinate upwards by 24 units. + * Moves all buttons that in any way intersect a rectangle by a given amount on the y axis. * @param buttons List of buttons - * @param belowY The Y limit + * @param yStart Top y limit of the rectangle + * @param yEnd Bottom y limit of the rectangle * @param xStart Left x limit of the rectangle * @param xEnd Right x limit of the rectangle + * @param moveBy Signed distance to move the buttons */ - private void moveAllButtonsDirectlyBelowUpwards( + private void moveAllButtonsInRect( //#if MC>=11400 List buttons, //#else //$$ List buttons, //#endif - int belowY, int xStart, - int xEnd + int xEnd, + int yStart, + int yEnd, + int moveBy ) { buttons.stream() - .filter(button -> button.y >= belowY) .filter(button -> button.x <= xEnd && button.x + width(button) >= xStart) - .forEach(button -> button.y -= 24); + .filter(button -> button.y <= yEnd && button.y + height(button) >= yStart) + .forEach(button -> button.y += moveBy); } //#if FABRIC>=1 @@ -222,15 +232,35 @@ public class GuiHandler extends EventRegistrations { //$$ @SubscribeEvent //$$ public void injectIntoMainMenu(GuiScreenEvent.InitGuiEvent event) { //$$ Screen guiScreen = getGui(event); + //$$ List buttonList = getButtonList(event); //#endif if (!(guiScreen instanceof TitleScreen)) { return; } + + int x = guiScreen.width / 2 - 100; + // We want to position our button below the realms button + int y = findButton(buttonList, "menu.online", 14) + .map(Optional::of) + // or, if someone removed the realms button, we'll alternatively take the multiplayer one + .orElse(findButton(buttonList, "menu.multiplayer", 2)) + // if we found some button, put our button at its position (we'll move it out of the way shortly) + .map(it -> it.y) + // and if we can't even find that one, then just guess + .orElse(guiScreen.height / 4 + 10 + 4 * 24); + + // Move all buttons above or at our one upwards + moveAllButtonsInRect(buttonList, + x, x + 200, + Integer.MIN_VALUE, y, + -24); + + // Add our button InjectedButton button = new InjectedButton( guiScreen, BUTTON_REPLAY_VIEWER, - guiScreen.width / 2 - 100, - guiScreen.height / 4 + 10 + 4 * 24, + x, + y, 200, 20, "replaymod.gui.replayviewer",