diff --git a/Forge/src/main/java/chylex/bettercontrols/BetterControlsMod.java b/Forge/src/main/java/chylex/bettercontrols/BetterControlsMod.java index fcc65ae..34c3b8d 100644 --- a/Forge/src/main/java/chylex/bettercontrols/BetterControlsMod.java +++ b/Forge/src/main/java/chylex/bettercontrols/BetterControlsMod.java @@ -4,20 +4,20 @@ import chylex.bettercontrols.gui.BetterControlsScreen; import net.minecraft.client.Minecraft; import net.minecraft.client.gui.screens.Screen; import net.minecraftforge.api.distmarker.Dist; +import net.minecraftforge.client.ConfigGuiHandler.ConfigGuiFactory; import net.minecraftforge.fml.DistExecutor; import net.minecraftforge.fml.IExtensionPoint.DisplayTest; import net.minecraftforge.fml.ModLoadingContext; import net.minecraftforge.fml.common.Mod; import net.minecraftforge.fml.loading.FMLPaths; -import net.minecraftforge.fmlclient.ConfigGuiHandler.ConfigGuiFactory; -import net.minecraftforge.fmllegacy.network.FMLNetworkConstants; +import net.minecraftforge.network.NetworkConstants; @Mod("bettercontrols") public final class BetterControlsMod { public BetterControlsMod() { BetterControlsCommon.setConfig(DistExecutor.safeCallWhenOn(Dist.CLIENT, () -> ClientLoader::loadConfig)); ModLoadingContext.get().registerExtensionPoint(ConfigGuiFactory.class, () -> new ConfigGuiFactory(ClientLoader::createScreen)); - ModLoadingContext.get().registerExtensionPoint(DisplayTest.class, () -> new DisplayTest(() -> FMLNetworkConstants.IGNORESERVERONLY, (a, b) -> true)); + ModLoadingContext.get().registerExtensionPoint(DisplayTest.class, () -> new DisplayTest(() -> NetworkConstants.IGNORESERVERONLY, (a, b) -> true)); } private static final class ClientLoader { diff --git a/build.gradle.kts b/build.gradle.kts index fae12c6..d28a5f6 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -74,12 +74,12 @@ allprojects { } extensions.getByType<JavaPluginExtension>().apply { - toolchain.languageVersion.set(JavaLanguageVersion.of(16)) + toolchain.languageVersion.set(JavaLanguageVersion.of(17)) } tasks.withType<JavaCompile> { options.encoding = "UTF-8" - options.release.set(16) + options.release.set(17) } } diff --git a/gradle.properties b/gradle.properties index c65a0e7..013a25a 100644 --- a/gradle.properties +++ b/gradle.properties @@ -3,15 +3,15 @@ modId=bettercontrols modName=Better Controls modDescription=Adds many powerful key bindings and options to control your movement.\\n\\nThe features complement vanilla mechanics without giving unfair advantages, so server use should be fine. modAuthor=chylex -modVersion=1.2.1 +modVersion=1.2.2 modLicense=MPL-2.0 modSourcesURL=https://github.com/chylex/Better-Controls modIssuesURL=https://github.com/chylex/Better-Controls/issues # Dependencies -minecraftVersion=1.17.1 -forgeVersion=37.0.75 -fabricVersion=0.11.7 +minecraftVersion=1.18 +forgeVersion=38.0.8 +fabricVersion=0.12.8 mixinVersion=0.8.4 # Gradle diff --git a/src/main/java/chylex/bettercontrols/mixin/HookControlsListWidget.java b/src/main/java/chylex/bettercontrols/mixin/HookControlsListWidget.java index 1b06c7b..e766315 100644 --- a/src/main/java/chylex/bettercontrols/mixin/HookControlsListWidget.java +++ b/src/main/java/chylex/bettercontrols/mixin/HookControlsListWidget.java @@ -4,14 +4,14 @@ import net.minecraft.client.KeyMapping; import net.minecraft.client.Minecraft; import net.minecraft.client.Options; import net.minecraft.client.gui.components.ContainerObjectSelectionList; -import net.minecraft.client.gui.screens.controls.ControlList; -import net.minecraft.client.gui.screens.controls.ControlList.Entry; +import net.minecraft.client.gui.screens.controls.KeyBindsList; +import net.minecraft.client.gui.screens.controls.KeyBindsList.Entry; import org.apache.commons.lang3.ArrayUtils; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.Redirect; -@Mixin(ControlList.class) +@Mixin(KeyBindsList.class) public abstract class HookControlsListWidget extends ContainerObjectSelectionList<Entry> { public HookControlsListWidget(final Minecraft client, final int width, final int height, final int top, final int bottom, final int itemHeight) { super(client, width, height, top, bottom, itemHeight); diff --git a/src/main/java/chylex/bettercontrols/mixin/HookControlsScreen.java b/src/main/java/chylex/bettercontrols/mixin/HookControlsScreen.java index 0e17282..aaebeca 100644 --- a/src/main/java/chylex/bettercontrols/mixin/HookControlsScreen.java +++ b/src/main/java/chylex/bettercontrols/mixin/HookControlsScreen.java @@ -1,28 +1,61 @@ package chylex.bettercontrols.mixin; import chylex.bettercontrols.gui.BetterControlsScreen; -import net.minecraft.client.CycleOption; import net.minecraft.client.Minecraft; -import net.minecraft.client.Option; import net.minecraft.client.Options; import net.minecraft.client.gui.components.AbstractWidget; import net.minecraft.client.gui.components.Button; +import net.minecraft.client.gui.components.events.GuiEventListener; +import net.minecraft.client.gui.screens.OptionsSubScreen; import net.minecraft.client.gui.screens.Screen; import net.minecraft.client.gui.screens.controls.ControlsScreen; +import net.minecraft.network.chat.Component; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.injection.At; -import org.spongepowered.asm.mixin.injection.Redirect; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; @Mixin(ControlsScreen.class) -public abstract class HookControlsScreen { - @Redirect(method = "init", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/CycleOption;createButton(Lnet/minecraft/client/Options;III)Lnet/minecraft/client/gui/components/AbstractWidget;")) - private AbstractWidget replaceAutoJumpButton(final CycleOption<?> option, final Options options, final int x, final int y, final int width) { - if (option == Option.AUTO_JUMP && !Screen.hasAltDown()) { - @SuppressWarnings("ConstantConditions") - final ControlsScreen screen = (ControlsScreen)(Object)this; - return new Button(x, y, width, 20, BetterControlsScreen.TITLE.plainCopy().append("..."), btn -> Minecraft.getInstance().setScreen(new BetterControlsScreen(screen))); +public abstract class HookControlsScreen extends OptionsSubScreen { + public HookControlsScreen(final Screen parentScreen, final Options options, final Component title) { + super(parentScreen, options, title); + } + + @Inject(method = "init", at = @At("RETURN")) + public void afterInit(final CallbackInfo ci) { + @SuppressWarnings("ConstantConditions") + final ControlsScreen screen = (ControlsScreen)(Object)this; + final int center = width / 2; + + int leftBottomY = 0; + int rightBottomY = 0; + + for (final GuiEventListener child : children()) { + if (!(child instanceof AbstractWidget widget)) { + continue; + } + + final int bottomY = widget.y + widget.getHeight(); + + if (widget.x + widget.getWidth() < center) { + leftBottomY = Math.max(leftBottomY, bottomY); + } + if (widget.x >= center) { + rightBottomY = Math.max(rightBottomY, bottomY); + } } - return option.createButton(options, x, y, width); + final int x, y; + + if (leftBottomY < rightBottomY) { + x = center - 155; + y = leftBottomY + 4; + } + else { + x = center + 5; + y = rightBottomY + 4; + } + + addRenderableWidget(new Button(x, y, 150, 20, BetterControlsScreen.TITLE.plainCopy().append("..."), btn -> Minecraft.getInstance().setScreen(new BetterControlsScreen(screen)))); } } diff --git a/src/main/resources/bettercontrols.mixins.json b/src/main/resources/bettercontrols.mixins.json index 0d64674..c0ec713 100644 --- a/src/main/resources/bettercontrols.mixins.json +++ b/src/main/resources/bettercontrols.mixins.json @@ -3,7 +3,7 @@ "minVersion": "0.8", "package": "chylex.bettercontrols.mixin", "refmap": "bettercontrols.refmap.json", - "compatibilityLevel": "JAVA_16", + "compatibilityLevel": "JAVA_17", "client": [ "AccessCameraFields", "AccessClientPlayerFields",