diff --git a/src/main/java/com/minecrafttas/tasmod/mixin/MixinTimer.java b/src/main/java/com/minecrafttas/tasmod/mixin/MixinTimer.java
index 518e3483..2885fb65 100644
--- a/src/main/java/com/minecrafttas/tasmod/mixin/MixinTimer.java
+++ b/src/main/java/com/minecrafttas/tasmod/mixin/MixinTimer.java
@@ -15,59 +15,122 @@
@Mixin(Timer.class)
/**
- * Rewrites updateTimer to make it possible to interpolate ticks.
+ *
Rewrites updateTimer, to add a tickratechanger and apply ticksync.
+ *
Dynamically speeds up or slows down the tickrate depending on the time between {@link TickSyncClient TickSync} packages.
* @author Pancake
*
*/
public class MixinTimer {
+ /**
+ *
How many ticks elapsed since the {@link Timer#updateTimer()} method was called.
+ *
Used in Minecraft#runGameLoop to call {@link Minecraft#runTick()} in the for loop
+ */
@Shadow
private int elapsedTicks;
- @Shadow
- private float renderPartialTicks;
+ /**
+ * How many "frames" elapsed since the {@link Timer#updateTimer()} method was called
+ */
@Shadow
private float elapsedPartialTicks;
+ /**
+ * Value between 0-1 of how many frames have elapsed inbetween ticks
+ */
@Shadow
- private long lastSyncSysClock;
+ private float renderPartialTicks;
+ /**
+ * The last time the {@link Timer#updateTimer()} method was called
+ */
@Shadow
- private float tickLength;
+ private long lastSyncSysClock;
+ // ==========================================================
+
+ /**
+ * System time the last time a tick has run and ticksync has triggered
+ */
@Unique
- private long millisLastTick;
- @Unique
- private long lastGameLoop;
+ private long timeSinceLastTick;
+ /**
+ * The tick length in the last tick
+ */
@Unique
- private float lastTickDuration;
+ private float lastTickLength;
+ /**
+ *
Overwrites {@link Timer#updateTimer()} in a way,
+ * so that the tickrate matches the tickrate of the server.
+ *
+ *
It does this by removing {@link Timer#tickLength} from the equasion.
+ * Takes the time between incoming packets from {@link TickSyncClient#onClientPacket(com.minecrafttas.mctcommon.networking.interfaces.PacketID, java.nio.ByteBuffer, String) TickSyncClient.onClientPacket()}
+ * and calculates the tickrate dynamically.
+ *
+ *
If no packet is present, it stops the client.
+ * This can happen when:
+ *
+ * - The packet did not reach it's destination
+ * - The tickrate on the server is 0
+ * - The server is lagging and unable to send packets
+ * - Another player is taking too long to send a packet
+ *
+ *
+ * @param ci
+ */
@Inject(method = "updateTimer", at = @At("HEAD"), cancellable = true)
public void inject_tick(CallbackInfo ci) {
- if (TASmodClient.client != null && !TASmodClient.client.isClosed()) {
- lastSyncSysClock = Minecraft.getSystemTime(); // update the tick tracker so that after returning to scheduling the client won't catch up all ticks (max 10)
- this.elapsedTicks = 0; // do not do any ticks
- long newGameLoop = Minecraft.getSystemTime();
+ /*
+ * Run overriden updateTimer method
+ *
+ * Only runs when there is a connection to the custom networking server and the player is in a world
+ */
+ if (TASmodClient.client != null && !TASmodClient.client.isClosed() && Minecraft.getMinecraft().world != null) {
+
+ long currentTime = Minecraft.getSystemTime(); // The current system time as of calling this method
+ /*
+ * The length of the tick in milliseconds.
+ * Set to 50 in vanilla, but in this instance,
+ * it is set to the duration of when Ticksync.shouldTick was true
+ */
+ float tickLength = lastTickLength;
+
+ this.elapsedTicks = 0; // Prevent the client from ticking
+
+ /*
+ * Ticksync block.
+ * Allows the client to run for 1 tick if TickSyncClient.shouldTick is true
+ */
if (TickSyncClient.shouldTick.compareAndSet(true, false)) {
- this.elapsedTicks++;
- this.lastTickDuration = newGameLoop - this.millisLastTick;
+
+ this.elapsedTicks++; // Allow the client to tick once
+ tickLength = currentTime - timeSinceLastTick; // Check the time between ticks
if (TASmodClient.tickratechanger.advanceTick) {
- lastTickDuration = TASmodClient.tickratechanger.millisecondsPerTick; // Keep the lastTick duration steady during tickadvance, since it grows larger the longer you wait in tickrate 0
+ tickLength = TASmodClient.tickratechanger.millisecondsPerTick; // Keep the lastTick duration steady during tickadvance, since it grows larger the longer you wait in tickrate 0
}
- this.millisLastTick = newGameLoop; // Update millisLastTick
- this.renderPartialTicks = 0; // Reset after the tick
+ timeSinceLastTick = currentTime;
+ this.renderPartialTicks = 0; // Reset render partial ticks after a new tick
}
- // Interpolating
- this.elapsedPartialTicks = (newGameLoop - this.lastGameLoop) / this.lastTickDuration;
- float newPartialTicks = this.renderPartialTicks;
- newPartialTicks += this.elapsedPartialTicks;
- newPartialTicks -= (int) this.renderPartialTicks;
- if (newPartialTicks > this.renderPartialTicks) {
- this.renderPartialTicks = newPartialTicks;
+
+ /*
+ * Vanilla calculation from updateTimer,
+ * with added interpolation calculation
+ */
+ this.elapsedPartialTicks = (currentTime - this.lastSyncSysClock) / tickLength; // Use the calculated tickLength instead of the vanill tickLength
+ float newRenderPartialTicks = this.renderPartialTicks;
+ newRenderPartialTicks += this.elapsedPartialTicks;
+ newRenderPartialTicks -= (int) this.renderPartialTicks;
+
+ if (newRenderPartialTicks > this.renderPartialTicks) { // Fixes stuttering when the renderPartialTicks stay the same during tickrate 0
+ this.renderPartialTicks = newRenderPartialTicks;
}
- this.lastGameLoop = newGameLoop;
+
+ this.lastSyncSysClock = currentTime; // Update vanilla variable
+ lastTickLength = tickLength; // Update last tick length
ci.cancel();
- } else {
- this.millisLastTick = Minecraft.getSystemTime();
- this.lastGameLoop = Minecraft.getSystemTime();
- TickSyncClient.shouldTick.set(true); // The client should always tick if it once thrown out of the vanilla scheduling part, to make the server tick, etc.
+ }
+ // Run vanilla updateTimer
+ else {
+ this.timeSinceLastTick = Minecraft.getSystemTime();
+ TickSyncClient.shouldTick.set(true); // Client should always tick, when in the main menu
}
}
}
diff --git a/src/main/java/com/minecrafttas/tasmod/playback/PlaybackControllerClient.java b/src/main/java/com/minecrafttas/tasmod/playback/PlaybackControllerClient.java
index 4b3e1714..4d372071 100644
--- a/src/main/java/com/minecrafttas/tasmod/playback/PlaybackControllerClient.java
+++ b/src/main/java/com/minecrafttas/tasmod/playback/PlaybackControllerClient.java
@@ -103,7 +103,7 @@ public class PlaybackControllerClient implements
EventVirtualInput.EventVirtualCameraAngleTick,
EventVirtualInput.EventVirtualMouseSubtick
- //@formatter:on
+//@formatter:on
{
private Logger logger = TASmod.LOGGER;
diff --git a/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncClient.java b/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncClient.java
index 2faddab1..8896e4b1 100644
--- a/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncClient.java
+++ b/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncClient.java
@@ -15,11 +15,10 @@
import net.minecraft.client.Minecraft;
/**
- * This class manages tick sync
- * German: https://1drv.ms/p/s!Av_ysXerhm5CphLvLvguvL5QYe1A?e=MHPldP
- * English: https://1drv.ms/p/s!Av_ysXerhm5Cpha7Qq2tiVebd4DY?e=pzxOva
- *
+ * Synchronizes the client tickrate with the server tickrate
+ *
* @author Pancake
+ * @see TickSyncServer
*/
public class TickSyncClient implements ClientPacketHandler, EventClientTickPost {
diff --git a/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncServer.java b/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncServer.java
index 18d3ec4d..27fc8df3 100644
--- a/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncServer.java
+++ b/src/main/java/com/minecrafttas/tasmod/ticksync/TickSyncServer.java
@@ -19,11 +19,10 @@
import net.minecraft.server.MinecraftServer;
/**
- * This class manages tick sync
- * German: https://1drv.ms/p/s!Av_ysXerhm5CphLvLvguvL5QYe1A?e=MHPldP
- * English: https://1drv.ms/p/s!Av_ysXerhm5Cpha7Qq2tiVebd4DY?e=pzxOva
- *
+ *
Synchronizes the server tickrate with all clients
+ *
* @author Pancake
+ * @see TickSyncClient
*/
public class TickSyncServer implements ServerPacketHandler, EventServerTickPost, EventClientCompleteAuthentication {