1
0
forked from Clones/Controlify

virtual mouse + singleplayer screen compat + 22w05a

This commit is contained in:
isXander
2023-02-02 21:36:44 +00:00
parent 57fcd0c0dc
commit 09628defc4
34 changed files with 697 additions and 111 deletions

View File

@ -11,6 +11,6 @@ import org.spongepowered.asm.mixin.injection.At;
public class AbstractSelectionListMixin {
@ModifyExpressionValue(method = "setFocused", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/InputType;isKeyboard()Z"))
private boolean shouldEnsureEntryVisible(boolean keyboard) {
return keyboard || Controlify.getInstance().getCurrentInputMode() == InputMode.CONTROLLER;
return keyboard || Controlify.instance().currentInputMode() == InputMode.CONTROLLER;
}
}

View File

@ -2,7 +2,7 @@ package dev.isxander.controlify.mixins.compat.screen.vanilla;
import dev.isxander.controlify.compatibility.screen.component.ComponentProcessor;
import dev.isxander.controlify.compatibility.screen.component.ComponentProcessorProvider;
import dev.isxander.controlify.compatibility.screen.component.SliderComponentProcessor;
import dev.isxander.controlify.compatibility.vanilla.SliderComponentProcessor;
import net.minecraft.client.gui.components.AbstractSliderButton;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;

View File

@ -14,4 +14,7 @@ public interface ScreenAccessor {
@Invoker
void invokeChangeFocus(ComponentPath path);
@Invoker
void invokeClearFocus();
}

View File

@ -12,10 +12,10 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
@Mixin(Screen.class)
public class ScreenMixin implements ScreenProcessorProvider {
@Unique
private final ScreenProcessor controlify$processor = new ScreenProcessor((Screen) (Object) this);
private final ScreenProcessor<Screen> controlify$processor = new ScreenProcessor<>((Screen) (Object) this);
@Override
public ScreenProcessor screenProcessor() {
public ScreenProcessor<Screen> screenProcessor() {
return controlify$processor;
}

View File

@ -0,0 +1,16 @@
package dev.isxander.controlify.mixins.compat.screen.vanilla;
import net.minecraft.client.gui.components.Button;
import net.minecraft.client.gui.screens.worldselection.SelectWorldScreen;
import net.minecraft.client.gui.screens.worldselection.WorldSelectionList;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.gen.Accessor;
@Mixin(SelectWorldScreen.class)
public interface SelectWorldScreenAccessor {
@Accessor
Button getSelectButton();
@Accessor
WorldSelectionList getList();
}

View File

@ -0,0 +1,17 @@
package dev.isxander.controlify.mixins.compat.screen.vanilla;
import dev.isxander.controlify.compatibility.screen.ScreenProcessor;
import dev.isxander.controlify.compatibility.screen.ScreenProcessorProvider;
import dev.isxander.controlify.compatibility.vanilla.SelectWorldScreenProcessor;
import net.minecraft.client.gui.screens.worldselection.SelectWorldScreen;
import org.spongepowered.asm.mixin.Mixin;
@Mixin(SelectWorldScreen.class)
public class SelectWorldScreenMixin implements ScreenProcessorProvider {
private final SelectWorldScreenProcessor controlify$processor = new SelectWorldScreenProcessor((SelectWorldScreen) (Object) this);
@Override
public ScreenProcessor<?> screenProcessor() {
return controlify$processor;
}
}

View File

@ -0,0 +1,17 @@
package dev.isxander.controlify.mixins.compat.screen.vanilla;
import dev.isxander.controlify.compatibility.screen.component.ComponentProcessor;
import dev.isxander.controlify.compatibility.screen.component.ComponentProcessorProvider;
import dev.isxander.controlify.compatibility.vanilla.WorldListEntryComponentProcessor;
import net.minecraft.client.gui.screens.worldselection.WorldSelectionList;
import org.spongepowered.asm.mixin.Mixin;
@Mixin(WorldSelectionList.WorldListEntry.class)
public class WorldSelectionListEntryMixin implements ComponentProcessorProvider {
private final WorldListEntryComponentProcessor controlify$processor = new WorldListEntryComponentProcessor();
@Override
public ComponentProcessor componentProcessor() {
return controlify$processor;
}
}

View File

@ -1,16 +1,10 @@
package dev.isxander.controlify.mixins.core;
import com.llamalad7.mixinextras.injector.ModifyExpressionValue;
import com.llamalad7.mixinextras.injector.wrapoperation.Operation;
import com.llamalad7.mixinextras.injector.wrapoperation.WrapOperation;
import dev.isxander.controlify.Controlify;
import dev.isxander.controlify.InputMode;
import dev.isxander.controlify.ingame.ControllerPlayerMovement;
import net.minecraft.client.Minecraft;
import net.minecraft.client.Options;
import net.minecraft.client.multiplayer.ClientPacketListener;
import net.minecraft.client.player.Input;
import net.minecraft.client.player.KeyboardInput;
import net.minecraft.network.protocol.game.ClientboundLoginPacket;
import org.objectweb.asm.Opcodes;
import org.spongepowered.asm.mixin.Final;
@ -29,7 +23,7 @@ public class ClientPacketListenerMixin {
@Inject(method = "handleLogin", at = @At(value = "FIELD", target = "Lnet/minecraft/client/player/LocalPlayer;input:Lnet/minecraft/client/player/Input;", opcode = Opcodes.ASTORE, shift = At.Shift.AFTER))
private void useControllerInput(ClientboundLoginPacket packet, CallbackInfo ci) {
if (Controlify.getInstance().getCurrentInputMode() == InputMode.CONTROLLER && minecraft.player != null)
minecraft.player.input = new ControllerPlayerMovement(Controlify.getInstance().getCurrentController());
if (Controlify.instance().currentInputMode() == InputMode.CONTROLLER && minecraft.player != null)
minecraft.player.input = new ControllerPlayerMovement(Controlify.instance().currentController());
}
}

View File

@ -3,15 +3,22 @@ package dev.isxander.controlify.mixins.core;
import dev.isxander.controlify.Controlify;
import dev.isxander.controlify.InputMode;
import net.minecraft.client.KeyboardHandler;
import net.minecraft.client.Minecraft;
import org.spongepowered.asm.mixin.Final;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
@Mixin(KeyboardHandler.class)
public class KeyboardHandlerMixin {
@Inject(method = "keyPress", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/Minecraft;setLastInputType(Lnet/minecraft/client/InputType;)V"))
private void onKeyboardInput(long window, int key, int scancode, int action, int modifiers, CallbackInfo ci) {
Controlify.getInstance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
@Shadow @Final private Minecraft minecraft;
// m_unngxkoe is lambda for GLFW keypress hook - do it outside of the `keyPress` method due to fake inputs
@Inject(method = "m_unngxkoe", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/KeyboardHandler;keyPress(JIIII)V"))
private void onKeyboardInput(long window, int i, int j, int k, int m, CallbackInfo ci) {
if (window == minecraft.getWindow().getWindow())
Controlify.instance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
}
}

View File

@ -11,11 +11,11 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
public class MinecraftMixin {
@Inject(method = "<init>", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/KeyboardHandler;setup(J)V", shift = At.Shift.AFTER))
private void onInputInitialized(CallbackInfo ci) {
Controlify.getInstance().onInitializeInput();
Controlify.instance().onInitializeInput();
}
@Inject(method = "runTick", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/MouseHandler;turnPlayer()V"))
private void doPlayerLook(boolean tick, CallbackInfo ci) {
Controlify.getInstance().getInGameInputHandler().processPlayerLook();
Controlify.instance().inGameInputHandler().processPlayerLook();
}
}

View File

@ -2,26 +2,37 @@ package dev.isxander.controlify.mixins.core;
import dev.isxander.controlify.Controlify;
import dev.isxander.controlify.InputMode;
import net.minecraft.client.Minecraft;
import net.minecraft.client.MouseHandler;
import org.spongepowered.asm.mixin.Final;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
@Mixin(MouseHandler.class)
public class MouseHandlerMixin {
@Inject(method = "onPress", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/Minecraft;setLastInputType(Lnet/minecraft/client/InputType;)V"))
@Shadow @Final private Minecraft minecraft;
// m_sljgmtqm is lambda for GLFW mouse click hook - do it outside of the `onPress` method due to fake inputs
@Inject(method = "m_sljgmtqm", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/MouseHandler;onPress(JIII)V"))
private void onMouseClickInput(long window, int button, int action, int modifiers, CallbackInfo ci) {
Controlify.getInstance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
if (window == minecraft.getWindow().getWindow())
Controlify.instance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
}
@Inject(method = "onMove", at = @At("RETURN"))
// m_swhlgdws is lambda for GLFW mouse move hook - do it outside of the `onMove` method due to fake inputs
@Inject(method = "m_swhlgdws", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/MouseHandler;onMove(JDD)V"))
private void onMouseMoveInput(long window, double x, double y, CallbackInfo ci) {
Controlify.getInstance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
if (window == minecraft.getWindow().getWindow())
Controlify.instance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
}
@Inject(method = "onScroll", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/Minecraft;getOverlay()Lnet/minecraft/client/gui/screens/Overlay;"))
// m_qoshpwkl is lambda for GLFW mouse scroll hook - do it outside of the `onScroll` method due to fake inputs
@Inject(method = "m_qoshpwkl", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/MouseHandler;onScroll(JDD)V"))
private void onMouseScrollInput(long window, double scrollDeltaX, double scrollDeltaY, CallbackInfo ci) {
Controlify.getInstance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
if (window == minecraft.getWindow().getWindow())
Controlify.instance().setCurrentInputMode(InputMode.KEYBOARD_MOUSE);
}
}

View File

@ -0,0 +1,18 @@
package dev.isxander.controlify.mixins.feature.virtualmouse;
import com.llamalad7.mixinextras.sugar.Local;
import com.mojang.blaze3d.vertex.PoseStack;
import dev.isxander.controlify.Controlify;
import net.minecraft.client.renderer.GameRenderer;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
@Mixin(GameRenderer.class)
public class GameRendererMixin {
@Inject(method = "render", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/gui/screens/Screen;renderWithTooltip(Lcom/mojang/blaze3d/vertex/PoseStack;IIF)V", shift = At.Shift.AFTER))
private void onPostRenderScreen(float tickDelta, long startTime, boolean tick, CallbackInfo ci, @Local(ordinal = 1) PoseStack poseStack) {
Controlify.instance().virtualMouseHandler().renderVirtualMouse(poseStack);
}
}

View File

@ -0,0 +1,11 @@
package dev.isxander.controlify.mixins.feature.virtualmouse;
import net.minecraft.client.KeyboardHandler;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.gen.Invoker;
@Mixin(KeyboardHandler.class)
public interface KeyboardHandlerAccessor {
@Invoker
void invokeKeyPress(long window, int key, int scancode, int action, int modifiers);
}

View File

@ -0,0 +1,22 @@
package dev.isxander.controlify.mixins.feature.virtualmouse;
import dev.isxander.controlify.Controlify;
import net.minecraft.client.Minecraft;
import net.minecraft.client.gui.screens.Screen;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
@Mixin(Minecraft.class)
public class MinecraftMixin {
@Inject(method = "setScreen", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/Minecraft;updateTitle()V"))
private void onScreenChanged(Screen screen, CallbackInfo ci) {
Controlify.instance().virtualMouseHandler().onScreenChanged();
}
@Inject(method = "runTick", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/MouseHandler;turnPlayer()V"))
private void onUpdateMouse(boolean tick, CallbackInfo ci) {
Controlify.instance().virtualMouseHandler().updateMouse();
}
}

View File

@ -0,0 +1,17 @@
package dev.isxander.controlify.mixins.feature.virtualmouse;
import net.minecraft.client.MouseHandler;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.gen.Invoker;
@Mixin(MouseHandler.class)
public interface MouseHandlerAccessor {
@Invoker
void invokeOnMove(long window, double x, double y);
@Invoker
void invokeOnPress(long window, int button, int action, int modifiers);
@Invoker
void invokeOnScroll(long window, double scrollDeltaX, double scrollDeltaY);
}