diff --git a/src/main/java/de/florianmichael/viafabricplus/base/screen/VFPScreen.java b/src/main/java/de/florianmichael/viafabricplus/base/screen/VFPScreen.java index e73e9c72..ad25f10b 100644 --- a/src/main/java/de/florianmichael/viafabricplus/base/screen/VFPScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/base/screen/VFPScreen.java @@ -21,13 +21,16 @@ import com.mojang.blaze3d.systems.RenderSystem; import de.florianmichael.viafabricplus.ViaFabricPlus; import net.minecraft.client.MinecraftClient; import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.screen.ConfirmLinkScreen; import net.minecraft.client.gui.screen.NoticeScreen; import net.minecraft.client.gui.screen.Screen; import net.minecraft.client.gui.widget.ButtonWidget; +import net.minecraft.client.gui.widget.PressableTextWidget; import net.minecraft.client.sound.PositionedSoundInstance; import net.minecraft.client.util.math.MatrixStack; import net.minecraft.sound.SoundEvents; import net.minecraft.text.Text; +import org.jetbrains.annotations.Nullable; import java.awt.*; @@ -37,14 +40,55 @@ import java.awt.*; */ public class VFPScreen extends Screen { + private static final String MOD_URL = "https://github.com/ViaVersion/ViaFabricPlus"; + private final boolean backButton; public Screen prevScreen; - public VFPScreen(String title, boolean backButton) { + private Text subtitle; + private ButtonWidget.PressAction subtitlePressAction; + + private PressableTextWidget subtitleWidget; + + public VFPScreen(final String title, final boolean backButton) { super(Text.of(title)); this.backButton = backButton; } + /*** + * Sets the subtitle and the subtitle press action to the default values + * The default value of the subtitle is the url to the GitHub repository of VFP + * The default value of the subtitle press action is to open the url in a confirmation screen + * + */ + public void setupDefaultSubtitle() { + this.setupSubtitle(Text.of(MOD_URL), ConfirmLinkScreen.opening(MOD_URL, this, true)); + } + + /*** + * Sets the subtitle and the subtitle press action + * + * @param subtitle The subtitle which should be rendered + */ + public void setupSubtitle(@Nullable final Text subtitle) { + this.setupSubtitle(subtitle, null); + } + + /*** + * Sets the subtitle and the subtitle press action + * + * @param subtitle The subtitle which should be rendered + * @param subtitlePressAction The press action which should be executed when the subtitle is clicked + */ + public void setupSubtitle(@Nullable final Text subtitle, @Nullable final ButtonWidget.PressAction subtitlePressAction) { + this.subtitle = subtitle; + this.subtitlePressAction = subtitlePressAction; + if (subtitleWidget != null && subtitlePressAction == null) { + remove(subtitleWidget); + subtitleWidget = null; + } + } + /** * Intended method to open a VFP screen * @@ -61,6 +105,19 @@ public class VFPScreen extends Screen { if (backButton) { this.addDrawableChild(ButtonWidget.builder(Text.literal("<-"), button -> this.close()).position(5, 5).size(20, 20).build()); } + + if (this.subtitle != null && this.subtitlePressAction != null) { + final int subtitleWidth = textRenderer.getWidth(subtitle); + this.addDrawableChild(subtitleWidget = new PressableTextWidget( + width / 2 - (subtitleWidth / 2), + (textRenderer.fontHeight + 2) * 2 + 3, + subtitleWidth, + textRenderer.fontHeight + 2, + subtitle, + subtitlePressAction, + textRenderer + )); + } } @Override @@ -68,17 +125,12 @@ public class VFPScreen extends Screen { MinecraftClient.getInstance().setScreen(prevScreen); } - public void renderTitle(final DrawContext context) { - renderTitle(context, Text.of("https://github.com/ViaVersion/ViaFabricPlus")); - } - /** - * Renders the ViaFabricPlus title with a specific subtitle + * Renders the ViaFabricPlus title * * @param context The current draw context - * @param subTitle The subtitle which should be rendered */ - public void renderTitle(final DrawContext context, final Text subTitle) { + public void renderTitle(final DrawContext context) { final MatrixStack matrices = context.getMatrices(); matrices.push(); @@ -86,7 +138,18 @@ public class VFPScreen extends Screen { context.drawCenteredTextWithShadow(textRenderer, "ViaFabricPlus", width / 4, 3, Color.ORANGE.getRGB()); matrices.pop(); - context.drawCenteredTextWithShadow(textRenderer, subTitle, width / 2, (textRenderer.fontHeight + 2) * 2 + 3, -1); + renderSubtitle(context); + } + + /** + * Renders the subtitle that doesn't have a press action + * + * @param context The current draw context + */ + public void renderSubtitle(final DrawContext context) { + if (subtitle != null && subtitlePressAction == null) { + context.drawCenteredTextWithShadow(textRenderer, subtitle, width / 2, (textRenderer.fontHeight + 2) * 2 + 3, -1); + } } /** diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/base/ForceVersionScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/base/ForceVersionScreen.java index 6bbb35df..8f73b3f4 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/base/ForceVersionScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/base/ForceVersionScreen.java @@ -17,7 +17,6 @@ */ package de.florianmichael.viafabricplus.screen.base; -import net.raphimc.vialoader.util.VersionEnum; import de.florianmichael.viafabricplus.base.screen.VFPScreen; import net.minecraft.client.MinecraftClient; import net.minecraft.client.font.TextRenderer; @@ -27,6 +26,7 @@ import net.minecraft.client.gui.widget.AlwaysSelectedEntryListWidget; import net.minecraft.text.MutableText; import net.minecraft.text.Text; import net.minecraft.util.Formatting; +import net.raphimc.vialoader.util.VersionEnum; import java.util.function.Consumer; @@ -38,6 +38,8 @@ public class ForceVersionScreen extends VFPScreen { this.prevScreen = prevScreen; this.selectionConsumer = selectionConsumer; + + this.setupSubtitle(Text.translatable("forceversion.viafabricplus.title")); } @Override @@ -52,7 +54,7 @@ public class ForceVersionScreen extends VFPScreen { this.renderBackground(context, mouseX, mouseY, delta); super.render(context, mouseX, mouseY, delta); - this.renderTitle(context, Text.translatable("forceversion.viafabricplus.title")); + this.renderTitle(context); } public class SlotList extends AlwaysSelectedEntryListWidget { diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/base/ProtocolSelectionScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/base/ProtocolSelectionScreen.java index 0b1de0eb..a9164279 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/base/ProtocolSelectionScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/base/ProtocolSelectionScreen.java @@ -18,13 +18,13 @@ package de.florianmichael.viafabricplus.screen.base; import de.florianmichael.classic4j.BetaCraftHandler; -import de.florianmichael.viafabricplus.definition.account.ClassiCubeAccountHandler; import de.florianmichael.viafabricplus.base.screen.VFPScreen; +import de.florianmichael.viafabricplus.definition.account.ClassiCubeAccountHandler; +import de.florianmichael.viafabricplus.protocolhack.ProtocolHack; +import de.florianmichael.viafabricplus.screen.settings.SettingsScreen; +import de.florianmichael.viafabricplus.screen.thirdparty.BetaCraftScreen; import de.florianmichael.viafabricplus.screen.thirdparty.classicube.ClassiCubeLoginScreen; import de.florianmichael.viafabricplus.screen.thirdparty.classicube.ClassiCubeServerListScreen; -import de.florianmichael.viafabricplus.screen.thirdparty.BetaCraftScreen; -import de.florianmichael.viafabricplus.screen.settings.SettingsScreen; -import de.florianmichael.viafabricplus.protocolhack.ProtocolHack; import net.minecraft.client.MinecraftClient; import net.minecraft.client.font.TextRenderer; import net.minecraft.client.gui.DrawContext; @@ -44,6 +44,7 @@ public class ProtocolSelectionScreen extends VFPScreen { protected ProtocolSelectionScreen() { super("Protocol selection", true); + this.setupDefaultSubtitle(); } @Override diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/settings/SettingsScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/settings/SettingsScreen.java index f94e78bf..f6e1032f 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/settings/SettingsScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/settings/SettingsScreen.java @@ -20,9 +20,9 @@ package de.florianmichael.viafabricplus.screen.settings; import de.florianmichael.viafabricplus.ViaFabricPlus; import de.florianmichael.viafabricplus.base.screen.MappedSlotEntry; import de.florianmichael.viafabricplus.base.screen.VFPScreen; -import de.florianmichael.viafabricplus.screen.settings.settingrenderer.meta.TitleRenderer; import de.florianmichael.viafabricplus.base.settings.base.AbstractSetting; import de.florianmichael.viafabricplus.base.settings.base.SettingGroup; +import de.florianmichael.viafabricplus.screen.settings.settingrenderer.meta.TitleRenderer; import net.minecraft.client.MinecraftClient; import net.minecraft.client.gui.DrawContext; import net.minecraft.client.gui.widget.AlwaysSelectedEntryListWidget; @@ -32,6 +32,7 @@ public class SettingsScreen extends VFPScreen { public SettingsScreen() { super("Setting", true); + this.setupDefaultSubtitle(); } @Override diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/BetaCraftScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/BetaCraftScreen.java index 59a5ef16..43626ed8 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/BetaCraftScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/BetaCraftScreen.java @@ -26,6 +26,7 @@ import de.florianmichael.viafabricplus.screen.settings.settingrenderer.meta.Titl import net.minecraft.client.MinecraftClient; import net.minecraft.client.font.TextRenderer; import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.screen.ConfirmLinkScreen; import net.minecraft.client.gui.screen.ConnectScreen; import net.minecraft.client.gui.widget.AlwaysSelectedEntryListWidget; import net.minecraft.client.gui.widget.ButtonWidget; @@ -40,8 +41,15 @@ public class BetaCraftScreen extends VFPScreen { public static BCServerList SERVER_LIST; public final static BetaCraftScreen INSTANCE = new BetaCraftScreen(); + private static final String BETA_CRAFT_SERVER_LIST_URL = "https://betacraft.uk/serverlist/"; + protected BetaCraftScreen() { super("BetaCraft", true); + this.setupSubtitle(Text.of(BETA_CRAFT_SERVER_LIST_URL), ConfirmLinkScreen.opening( + BETA_CRAFT_SERVER_LIST_URL, + this, + true + )); } @Override diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeLoginScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeLoginScreen.java index fd61e0ff..d4f4e78f 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeLoginScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeLoginScreen.java @@ -21,10 +21,11 @@ import com.mojang.blaze3d.systems.RenderSystem; import de.florianmichael.classic4j.ClassiCubeHandler; import de.florianmichael.classic4j.api.LoginProcessHandler; import de.florianmichael.classic4j.model.classicube.account.CCAccount; -import de.florianmichael.viafabricplus.screen.base.ProtocolSelectionScreen; -import de.florianmichael.viafabricplus.definition.account.ClassiCubeAccountHandler; import de.florianmichael.viafabricplus.base.screen.VFPScreen; +import de.florianmichael.viafabricplus.definition.account.ClassiCubeAccountHandler; +import de.florianmichael.viafabricplus.screen.base.ProtocolSelectionScreen; import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.screen.ConfirmLinkScreen; import net.minecraft.client.gui.screen.Screen; import net.minecraft.client.gui.widget.ButtonWidget; import net.minecraft.client.gui.widget.TextFieldWidget; @@ -33,22 +34,24 @@ import net.minecraft.text.Text; public class ClassiCubeLoginScreen extends VFPScreen { public final static ClassiCubeLoginScreen INSTANCE = new ClassiCubeLoginScreen(); + private static final String CLASSI_CUBE_URL = "https://www.classicube.net/"; + public ClassiCubeLoginScreen() { super("ClassiCube Login", false); } @Override public void open(Screen prevScreen) { - status = Text.translatable("classicube.viafabricplus.account"); - + this.setupSubtitle( + Text.translatable("classicube.viafabricplus.account"), + ConfirmLinkScreen.opening(CLASSI_CUBE_URL, this, true) + ); super.open(prevScreen); } private TextFieldWidget nameField; private TextFieldWidget passwordField; - private Text status; - @Override protected void init() { super.init(); @@ -68,7 +71,7 @@ public class ClassiCubeLoginScreen extends VFPScreen { this.addDrawableChild(ButtonWidget.builder(Text.literal("Login"), button -> { ClassiCubeAccountHandler.INSTANCE.setAccount(new CCAccount(nameField.getText(), passwordField.getText())); - status = Text.translatable("classicube.viafabricplus.loading"); + this.setupSubtitle(Text.translatable("classicube.viafabricplus.loading")); ClassiCubeHandler.requestAuthentication(ClassiCubeAccountHandler.INSTANCE.getAccount(), null, new LoginProcessHandler() { @Override @@ -84,7 +87,7 @@ public class ClassiCubeLoginScreen extends VFPScreen { @Override public void handleException(Throwable throwable) { throwable.printStackTrace(); - status = Text.literal(throwable.getMessage()); + setupSubtitle(Text.literal(throwable.getMessage())); } }); }).position(width / 2 - 75, passwordField.getY() + (20 * 4) + 5).size(150, 20).build()); @@ -101,8 +104,9 @@ public class ClassiCubeLoginScreen extends VFPScreen { this.renderBackground(context, mouseX, mouseY, delta); context.drawCenteredTextWithShadow(this.textRenderer, this.title, this.width / 2, 70, 16777215); - context.drawCenteredTextWithShadow(this.textRenderer, this.status, this.width / 2, 1, 16777215); super.render(context, mouseX, mouseY, delta); + + this.renderSubtitle(context); } } diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeMFAScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeMFAScreen.java index 390cf135..2e1de2aa 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeMFAScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeMFAScreen.java @@ -22,9 +22,9 @@ import de.florianmichael.classic4j.ClassiCubeHandler; import de.florianmichael.classic4j.api.LoginProcessHandler; import de.florianmichael.classic4j.model.classicube.CCError; import de.florianmichael.classic4j.model.classicube.account.CCAccount; +import de.florianmichael.viafabricplus.base.screen.VFPScreen; import de.florianmichael.viafabricplus.definition.account.ClassiCubeAccountHandler; import de.florianmichael.viafabricplus.integration.Classic4JImpl; -import de.florianmichael.viafabricplus.base.screen.VFPScreen; import de.florianmichael.viafabricplus.screen.base.ProtocolSelectionScreen; import net.minecraft.client.gui.DrawContext; import net.minecraft.client.gui.screen.Screen; diff --git a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeServerListScreen.java b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeServerListScreen.java index dc5b6807..0d96855d 100644 --- a/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeServerListScreen.java +++ b/src/main/java/de/florianmichael/viafabricplus/screen/thirdparty/classicube/ClassiCubeServerListScreen.java @@ -22,16 +22,17 @@ import de.florianmichael.classic4j.ClassiCubeHandler; import de.florianmichael.classic4j.api.LoginProcessHandler; import de.florianmichael.classic4j.model.classicube.account.CCAccount; import de.florianmichael.classic4j.model.classicube.server.CCServerInfo; +import de.florianmichael.viafabricplus.base.screen.MappedSlotEntry; +import de.florianmichael.viafabricplus.base.screen.VFPScreen; +import de.florianmichael.viafabricplus.base.settings.groups.AuthenticationSettings; import de.florianmichael.viafabricplus.definition.account.ClassiCubeAccountHandler; import de.florianmichael.viafabricplus.injection.access.IServerInfo; import de.florianmichael.viafabricplus.protocolhack.provider.vialegacy.ViaFabricPlusClassicMPPassProvider; -import de.florianmichael.viafabricplus.base.screen.VFPScreen; import de.florianmichael.viafabricplus.screen.base.ProtocolSelectionScreen; -import de.florianmichael.viafabricplus.base.screen.MappedSlotEntry; -import de.florianmichael.viafabricplus.base.settings.groups.AuthenticationSettings; import net.minecraft.client.MinecraftClient; import net.minecraft.client.font.TextRenderer; import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.screen.ConfirmLinkScreen; import net.minecraft.client.gui.screen.ConnectScreen; import net.minecraft.client.gui.screen.Screen; import net.minecraft.client.gui.widget.AlwaysSelectedEntryListWidget; @@ -49,6 +50,8 @@ public class ClassiCubeServerListScreen extends VFPScreen { public final static List SERVER_LIST = new ArrayList<>(); public final static ClassiCubeServerListScreen INSTANCE = new ClassiCubeServerListScreen(); + private static final String CLASSI_CUBE_SERVER_LIST_URL = "https://www.classicube.net/server/list/"; + public static void open(final Screen prevScreen, final LoginProcessHandler loginProcessHandler) { ClassiCubeHandler.requestServerList(ClassiCubeAccountHandler.INSTANCE.getAccount(), ccServerList -> { ClassiCubeServerListScreen.SERVER_LIST.addAll(ccServerList.servers()); @@ -58,6 +61,14 @@ public class ClassiCubeServerListScreen extends VFPScreen { public ClassiCubeServerListScreen() { super("ClassiCube ServerList", true); + final CCAccount account = ClassiCubeAccountHandler.INSTANCE.getAccount(); + if (account != null) { + this.setupSubtitle(Text.of(CLASSI_CUBE_SERVER_LIST_URL), ConfirmLinkScreen.opening( + CLASSI_CUBE_SERVER_LIST_URL, + this, + true + )); + } } @Override @@ -82,11 +93,24 @@ public class ClassiCubeServerListScreen extends VFPScreen { public void render(DrawContext context, int mouseX, int mouseY, float delta) { this.renderBackground(context, mouseX, mouseY, delta); super.render(context, mouseX, mouseY, delta); - + this.renderTitle(context); final CCAccount account = ClassiCubeAccountHandler.INSTANCE.getAccount(); - if (account == null) return; - - this.renderTitle(context, Text.of("ClassiCube Profile: " + account.username())); + if (account != null) { + context.drawTextWithShadow( + textRenderer, + Text.of("ClassiCube Profile: "), + 32, + 6, + -1 + ); + context.drawTextWithShadow( + textRenderer, + Text.of(account.username()), + 32, + 16, + -1 + ); + } } public static class SlotList extends AlwaysSelectedEntryListWidget {