Skip to content

Commit d14da99

Browse files
authored
[VirtualInput] Add cursor interpolation (#253)
- Moved Camera- and Cursor-Interpolation to the new VirtualInterpolationHandler - [InfoHud] Fixed Green and White keystrokes being the same during playback. Green should be one tick ahead - Fixed JUnit not behaving >:( - Fixes #251 - [Events] Changed event handler to not update the return value if it is null - [InfoHud] Re-enabled cursor display - Switch from the Triple class to it's own custom class - [PlaybackController] Add `playbackNext` keyboard, mouse and camera angle, to have fields that look ahead one tick - [PlaybackController] Rename keyboard mouse and cameraangle field to prepend `currentPlayback`
2 parents 9ea8cff + 8722ef8 commit d14da99

File tree

12 files changed

+431
-157
lines changed

12 files changed

+431
-157
lines changed

build.gradle

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,8 @@ dependencies {
5656
minecraft "com.mojang:minecraft:${project.minecraft_version}"
5757
mappings "net.legacyfabric:yarn:${project.minecraft_version}+build.mcp"
5858
modImplementation "net.fabricmc:fabric-loader:${project.loader_version}"
59-
testImplementation 'org.junit.jupiter:junit-jupiter:5.10.0'
59+
testImplementation 'org.junit.jupiter:junit-jupiter:5.13.3'
60+
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
6061
}
6162

6263
// task for downloading KillTheRng

src/main/java/com/minecrafttas/mctcommon/events/EventListenerRegistry.java

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -235,8 +235,7 @@ public static Object fireEvent(Class<? extends EventListenerRegistry.EventBase>
235235
// Iterate through all methods
236236
for (Method method : methodsInListener) {
237237

238-
// Check if the current method has the same name as the method we are looking
239-
// for
238+
// Check if the current method has the same name as the method we are looking for
240239
if (!checkName(method, methodToFind.getName())) {
241240
continue;
242241
}
@@ -252,7 +251,9 @@ public static Object fireEvent(Class<? extends EventListenerRegistry.EventBase>
252251
toThrow = null; // Reset toThrow as the correct method was found
253252
method.setAccessible(true);
254253
try {
255-
returnValue = method.invoke(eventListener, eventParams); // Call the method
254+
Object newReturnValue = method.invoke(eventListener, eventParams); // Call the method
255+
if (newReturnValue != null)
256+
returnValue = newReturnValue;
256257
} catch (IllegalAccessException | InvocationTargetException e) {
257258
throw new EventException(eventClass, e);
258259
} catch (IllegalArgumentException e) {

src/main/java/com/minecrafttas/tasmod/TASmodClient.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -198,6 +198,8 @@ private void registerEventListeners() {
198198
EventListenerRegistry.register(TASmodAPIRegistry.PLAYBACK_FILE_COMMAND);
199199
EventListenerRegistry.register(new LoggerMarkers());
200200
EventListenerRegistry.register(savestateHandlerClient);
201+
202+
EventListenerRegistry.register(virtual.interpolationHandler);
201203
}
202204

203205
@Override

src/main/java/com/minecrafttas/tasmod/events/EventClient.java

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import com.minecrafttas.mctcommon.events.EventListenerRegistry.EventBase;
44

55
import net.minecraft.client.Minecraft;
6+
import net.minecraft.client.gui.GuiScreen;
67

78
/**
89
* TASmod specific events fired on the client side
@@ -22,6 +23,17 @@ public static interface EventDrawHotbar extends EventBase {
2223
public void onDrawHotbar();
2324
}
2425

26+
/**
27+
* Fired when a screen in a gui is drawn
28+
*/
29+
@FunctionalInterface
30+
public static interface EventDrawScreen extends EventBase {
31+
/**
32+
* Fired when a screen in a gui is drawn
33+
*/
34+
public void onDrawScreen(GuiScreen screen, int xCoordinate, int yCoordinate);
35+
}
36+
2537
/**
2638
* Fired when drawing something on screen. Ignores F1
2739
*/

src/main/java/com/minecrafttas/tasmod/gui/InfoHud.java

Lines changed: 40 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -18,14 +18,18 @@
1818
import com.minecrafttas.tasmod.TASmod;
1919
import com.minecrafttas.tasmod.TASmodClient;
2020
import com.minecrafttas.tasmod.events.EventClient.EventDrawHotbar;
21+
import com.minecrafttas.tasmod.playback.PlaybackControllerClient;
2122
import com.minecrafttas.tasmod.playback.PlaybackControllerClient.TASstate;
2223
import com.minecrafttas.tasmod.playback.filecommands.builtin.DesyncMonitorFileCommandExtension;
24+
import com.minecrafttas.tasmod.virtual.VirtualInput;
25+
import com.minecrafttas.tasmod.virtual.VirtualInterpolationHandler.MouseInterpolation;
2326
import com.mojang.realmsclient.gui.ChatFormatting;
2427

2528
import net.minecraft.client.Minecraft;
2629
import net.minecraft.client.gui.GuiScreen;
2730
import net.minecraft.client.gui.ScaledResolution;
2831
import net.minecraft.util.math.MathHelper;
32+
import net.minecraft.util.text.TextFormatting;
2933

3034
/**
3135
* The info hud is a hud that is always being rendered ontop of the screen, it can show some stuff such as coordinates, etc.,
@@ -378,13 +382,25 @@ public boolean checkInit() {
378382
}
379383
}));
380384

381-
// title = "cursor";
382-
// y += 14;
383-
// if (configuration.getProperty(title + "_x", "err").equals("err")) setDefaults(title, y);
384-
// lists.add(new InfoLabel(title, Integer.parseInt(configuration.getProperty(title + "_x")), Integer.parseInt(configuration.getProperty(title + "_y")), Boolean.parseBoolean(configuration.getProperty(title + "_visible")), Boolean.parseBoolean(configuration.getProperty(title + "_rect")), () -> {
385-
// if (Minecraft.getMinecraft().currentScreen == this) return "Mouse Position";
386-
// return String.format("Mouse Cursor: " + TASmodClient.virtual.getNextMouse().getPath().get(0).cursorX + " " + TASmodClient.virtual.getNextMouse().getPath().get(0).cursorY);
387-
// })); TODO Remove?
385+
title = "cursor";
386+
y += 14;
387+
if (configuration.getProperty(title + "_x", "err").equals("err"))
388+
setDefaults(title, y);
389+
lists.add(new InfoLabel(title, Integer.parseInt(configuration.getProperty(title + "_x")), Integer.parseInt(configuration.getProperty(title + "_y")), Boolean.parseBoolean(configuration.getProperty(title
390+
+ "_visible")), Boolean.parseBoolean(configuration.getProperty(title + "_rect")), () -> {
391+
if (Minecraft.getMinecraft().currentScreen == this)
392+
return "Mouse Position";
393+
394+
MouseInterpolation mouseInterpolation = TASmodClient.virtual.interpolationHandler.getInterpolatedMouseCursor(0, false);
395+
Integer xCursor = mouseInterpolation.getX();
396+
Integer yCursor = mouseInterpolation.getY();
397+
398+
if (Minecraft.getMinecraft().currentScreen != null)
399+
return String.format("Mouse Cursor: %s %s", xCursor == null ? "null" : xCursor, yCursor == null ? "null" : yCursor);
400+
else
401+
return "Mouse Cursor: 0 0";
402+
403+
}));
388404

389405
// title = "trajectories";
390406
// y += 14;
@@ -537,29 +553,27 @@ private void drawRectWithText(String text, int x, int y, boolean rect) {
537553
}
538554

539555
private String keystrokes() {
556+
boolean isPlayingBack = TASmodClient.controller.isPlayingback();
557+
VirtualInput virtual = TASmodClient.virtual;
558+
PlaybackControllerClient controller = TASmodClient.controller;
540559

541-
String out1 = "" + ChatFormatting.WHITE;
542-
for (String mouse : TASmodClient.virtual.getCurrentMousePresses()) {
543-
out1 = out1.concat(mouse + " ");
544-
}
545-
if (Display.isActive() || TASmodClient.controller.isPlayingback()) {
546-
out1 = out1.concat("" + ChatFormatting.GREEN);
547-
for (String mouse : TASmodClient.virtual.getNextMousePresses()) {
548-
out1 = out1.concat(mouse + " ");
549-
}
550-
}
560+
String currentMousePresses = String.join(" ", virtual.getCurrentMousePresses());
551561

552-
String out2 = "" + ChatFormatting.WHITE;
553-
for (String key : TASmodClient.virtual.getCurrentKeyboardPresses()) {
554-
out2 = out2.concat(key + " ");
562+
String nextMousePresses = "";
563+
if (Display.isActive() || isPlayingBack) {
564+
List<String> mousePresses = isPlayingBack ? controller.getNextMousePresses() : virtual.getNextMousePresses();
565+
nextMousePresses = String.join(" ", mousePresses);
555566
}
556-
if (Display.isActive() || TASmodClient.controller.isPlayingback()) {
557-
out2 = out2.concat("" + ChatFormatting.GREEN);
558-
for (String key : TASmodClient.virtual.getNextKeyboardPresses()) {
559-
out2 = out2.concat(key + " ");
560-
}
567+
568+
String currentKeyboardPresses = String.join(" ", TASmodClient.virtual.getCurrentKeyboardPresses());
569+
570+
String nextKeyboardPresses = "";
571+
if (Display.isActive() || isPlayingBack) {
572+
List<String> keyboardPresses = isPlayingBack ? controller.getNextKeyboardPresses() : virtual.getNextKeyboardPresses();
573+
nextKeyboardPresses = String.join(" ", keyboardPresses);
561574
}
562-
return out1 + out2;
575+
576+
return String.format("%s%s %s%s %s%s %s%s", TextFormatting.WHITE, currentMousePresses, TextFormatting.GREEN, nextMousePresses, TextFormatting.WHITE, currentKeyboardPresses, TextFormatting.GREEN, nextKeyboardPresses);
563577
}
564578

565579
private Pair<Integer, Integer> getScreenOffset(int x, int y, InfoLabel label) {

src/main/java/com/minecrafttas/tasmod/mixin/playbackhooks/MixinEntityRenderer.java

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
package com.minecrafttas.tasmod.mixin.playbackhooks;
22

3-
import org.apache.commons.lang3.tuple.Triple;
43
import org.spongepowered.asm.mixin.Mixin;
54
import org.spongepowered.asm.mixin.Shadow;
65
import org.spongepowered.asm.mixin.injection.At;
@@ -11,11 +10,14 @@
1110

1211
import com.llamalad7.mixinextras.sugar.Share;
1312
import com.llamalad7.mixinextras.sugar.ref.LocalFloatRef;
13+
import com.llamalad7.mixinextras.sugar.ref.LocalIntRef;
1414
import com.minecrafttas.mctcommon.events.EventListenerRegistry;
1515
import com.minecrafttas.tasmod.TASmodClient;
1616
import com.minecrafttas.tasmod.events.EventClient.EventDrawHotbarAlways;
1717
import com.minecrafttas.tasmod.util.Ducks.SubtickDuck;
1818
import com.minecrafttas.tasmod.virtual.VirtualInput;
19+
import com.minecrafttas.tasmod.virtual.VirtualInterpolationHandler.CameraInterpolation;
20+
import com.minecrafttas.tasmod.virtual.VirtualInterpolationHandler.MouseInterpolation;
1921

2022
import net.minecraft.client.Minecraft;
2123
import net.minecraft.client.entity.EntityPlayerSP;
@@ -193,21 +195,31 @@ public void playback_updateOverlay(CallbackInfo ci) {
193195
EventListenerRegistry.fireEvent(EventDrawHotbarAlways.class);
194196
}
195197

198+
@Redirect(method = "updateCameraAndRender", at = @At(value = "INVOKE", target = "Lorg/lwjgl/input/Mouse;getX()I", remap = false))
199+
public int redirect_updateCameraAndRendererX(@Share(value = "interpolatedY") LocalIntRef shared) {
200+
MouseInterpolation interpolated = TASmodClient.virtual.interpolationHandler.getInterpolatedMouseCursor(Minecraft.getMinecraft().timer.renderPartialTicks, TASmodClient.controller.isPlayingback());
201+
shared.set(interpolated.getY());
202+
return interpolated.getX();
203+
}
204+
205+
@Redirect(method = "updateCameraAndRender", at = @At(value = "INVOKE", target = "Lorg/lwjgl/input/Mouse;getY()I", remap = false))
206+
public int redirect_updateCameraAndRendererY(@Share(value = "interpolatedY") LocalIntRef shared) {
207+
return shared.get();
208+
}
209+
196210
/**
197211
* Turns the camera via GLStateManager
198-
* @param pitch The pi
212+
* @param pitch The pitch
199213
* @param yaw The yaw
200-
* @see com.minecrafttas.tasmod.virtual.VirtualInput.VirtualCameraAngleInput#getInterpolatedState(float, float, float, boolean)
214+
* @see com.minecrafttas.tasmod.virtual.VirtualInterpolationHandler#getInterpolatedState(float, float, float, boolean)
201215
* @return The redirected yaw
202216
*/
203217
private float redirectCam(float pitch, float yaw) {
204-
Triple<Float, Float, Float> interpolated = TASmodClient.virtual.CAMERA_ANGLE.getInterpolatedState(Minecraft.getMinecraft().timer.renderPartialTicks, pitch, yaw, TASmodClient.controller.isPlayingback());
205-
float pitch2 = interpolated.getLeft();
206-
float yaw2 = interpolated.getMiddle();
218+
CameraInterpolation interpolated = TASmodClient.virtual.interpolationHandler.getInterpolatedState(Minecraft.getMinecraft().timer.renderPartialTicks, pitch, yaw, TASmodClient.controller.isPlayingback());
219+
float pitch2 = interpolated.getPitch();
220+
float yaw2 = interpolated.getYaw();
207221
// Update pitch
208222
GlStateManager.rotate(pitch2, 1.0f, 0.0f, 0.0f);
209-
// Update roll
210-
GlStateManager.rotate(interpolated.getRight(), 0.0f, 0.0f, 1.0f);
211223
// Update yaw
212224
return yaw2;
213225
}

src/main/java/com/minecrafttas/tasmod/mixin/playbackhooks/MixinGuiScreen.java

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,13 @@
33
import org.spongepowered.asm.mixin.Mixin;
44
import org.spongepowered.asm.mixin.Shadow;
55
import org.spongepowered.asm.mixin.injection.At;
6+
import org.spongepowered.asm.mixin.injection.Inject;
67
import org.spongepowered.asm.mixin.injection.Redirect;
8+
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
79

10+
import com.minecrafttas.mctcommon.events.EventListenerRegistry;
811
import com.minecrafttas.tasmod.TASmodClient;
12+
import com.minecrafttas.tasmod.events.EventClient.EventDrawScreen;
913
import com.minecrafttas.tasmod.util.Ducks.GuiScreenDuck;
1014
import com.minecrafttas.tasmod.virtual.VirtualInput;
1115
import com.minecrafttas.tasmod.virtual.event.VirtualKeyboardEvent;
@@ -103,6 +107,11 @@ private static boolean redirectIsAltKeyDown(int i) {
103107

104108
// =====================================================================================================================================
105109

110+
@Inject(method = "drawScreen", at = @At("HEAD"))
111+
private void injectDrawScreen(int i, int j, float f, CallbackInfo ci) {
112+
EventListenerRegistry.fireEvent(EventDrawScreen.class, (GuiScreen) (Object) this, i, j);
113+
}
114+
106115
@Shadow
107116
private int width;
108117

0 commit comments

Comments
 (0)