From fbbdab73c6442893c95668194c85360e12bcc9b2 Mon Sep 17 00:00:00 2001 From: James Seibel Date: Fri, 12 Jul 2024 17:24:45 -0500 Subject: [PATCH] Attempt to fix lag spikes when right clicking blocks --- .../fabric/FabricClientProxy.java | 69 ++++++++++++------- .../neoforge/NeoforgeClientProxy.java | 43 ++++++++---- 2 files changed, 76 insertions(+), 36 deletions(-) diff --git a/fabric/src/main/java/com/seibel/distanthorizons/fabric/FabricClientProxy.java b/fabric/src/main/java/com/seibel/distanthorizons/fabric/FabricClientProxy.java index 4dba8bc4f..5e9845cee 100644 --- a/fabric/src/main/java/com/seibel/distanthorizons/fabric/FabricClientProxy.java +++ b/fabric/src/main/java/com/seibel/distanthorizons/fabric/FabricClientProxy.java @@ -32,6 +32,7 @@ import com.seibel.distanthorizons.core.api.internal.SharedApi; import com.seibel.distanthorizons.core.dependencyInjection.ModAccessorInjector; import com.seibel.distanthorizons.core.dependencyInjection.SingletonInjector; import com.seibel.distanthorizons.core.logging.DhLoggerBuilder; +import com.seibel.distanthorizons.core.util.threading.ThreadPoolUtil; import com.seibel.distanthorizons.core.wrapperInterfaces.minecraft.IMinecraftClientWrapper; import com.seibel.distanthorizons.core.wrapperInterfaces.modAccessor.ISodiumAccessor; import com.seibel.distanthorizons.core.wrapperInterfaces.world.IClientLevelWrapper; @@ -120,6 +121,7 @@ public class FabricClientProxy implements AbstractModInitializer.IEventProxy }); // (kinda) block break event + // Since fabric doesn't have a client-side break-block API event, this is the next best thing AttackBlockCallback.EVENT.register((player, level, interactionHand, blockPos, direction) -> { // if we have access to the server, use the chunk save event instead @@ -127,18 +129,27 @@ public class FabricClientProxy implements AbstractModInitializer.IEventProxy { if (SharedApi.isChunkAtBlockPosAlreadyUpdating(blockPos.getX(), blockPos.getZ())) { - // Since fabric doesn't have a client-side break-block API event, this is the next best thing - ChunkAccess chunk = level.getChunk(blockPos); - if (chunk != null) + // executor to prevent locking up the render/event thread + // if the getChunk() takes longer than expected + // (which can be caused by certain mods) + var executor = ThreadPoolUtil.getFileHandlerExecutor(); + if (executor != null) { - //LOGGER.trace("attack block at blockPos: " + blockPos); - - IClientLevelWrapper wrappedLevel = ClientLevelWrapper.getWrapper((ClientLevel) level); - SharedApi.INSTANCE.chunkBlockChangedEvent( - new ChunkWrapper(chunk, level, wrappedLevel), - wrappedLevel - ); - } + executor.execute(() -> + { + ChunkAccess chunk = level.getChunk(blockPos); + if (chunk != null) + { + //LOGGER.trace("attack block at blockPos: " + blockPos); + + IClientLevelWrapper wrappedLevel = ClientLevelWrapper.getWrapper((ClientLevel) level); + SharedApi.INSTANCE.chunkBlockChangedEvent( + new ChunkWrapper(chunk, level, wrappedLevel), + wrappedLevel + ); + } + }); + } } } @@ -147,27 +158,37 @@ public class FabricClientProxy implements AbstractModInitializer.IEventProxy }); // (kinda) block place event + // Since fabric doesn't have a client-side place-block API event, this is the next best thing UseBlockCallback.EVENT.register((player, level, hand, hitResult) -> { // if we have access to the server, use the chunk save event instead if (MC.clientConnectedToDedicatedServer()) { - if (SharedApi.isChunkAtBlockPosAlreadyUpdating(hitResult.getBlockPos().getX(), hitResult.getBlockPos().getZ())) + if (hitResult.getType() == HitResult.Type.BLOCK + && !hitResult.isInside()) { - // Since fabric doesn't have a client-side place-block API event, this is the next best thing - if (hitResult.getType() == HitResult.Type.BLOCK - && !hitResult.isInside()) + if (SharedApi.isChunkAtBlockPosAlreadyUpdating(hitResult.getBlockPos().getX(), hitResult.getBlockPos().getZ())) { - ChunkAccess chunk = level.getChunk(hitResult.getBlockPos()); - if (chunk != null) + // executor to prevent locking up the render/event thread + // if the getChunk() takes longer than expected + // (which can be caused by certain mods) + var executor = ThreadPoolUtil.getFileHandlerExecutor(); + if (executor != null) { - //LOGGER.trace("use block at blockPos: " + hitResult.getBlockPos()); - - IClientLevelWrapper wrappedLevel = ClientLevelWrapper.getWrapper((ClientLevel) level); - SharedApi.INSTANCE.chunkBlockChangedEvent( - new ChunkWrapper(chunk, level, wrappedLevel), - wrappedLevel - ); + executor.execute(() -> + { + ChunkAccess chunk = level.getChunk(hitResult.getBlockPos()); + if (chunk != null) + { + //LOGGER.trace("use block at blockPos: " + hitResult.getBlockPos()); + + IClientLevelWrapper wrappedLevel = ClientLevelWrapper.getWrapper((ClientLevel) level); + SharedApi.INSTANCE.chunkBlockChangedEvent( + new ChunkWrapper(chunk, level, wrappedLevel), + wrappedLevel + ); + } + }); } } } diff --git a/neoforge/src/main/java/com/seibel/distanthorizons/neoforge/NeoforgeClientProxy.java b/neoforge/src/main/java/com/seibel/distanthorizons/neoforge/NeoforgeClientProxy.java index de73b4031..e5dc92b42 100644 --- a/neoforge/src/main/java/com/seibel/distanthorizons/neoforge/NeoforgeClientProxy.java +++ b/neoforge/src/main/java/com/seibel/distanthorizons/neoforge/NeoforgeClientProxy.java @@ -29,6 +29,7 @@ import com.seibel.distanthorizons.core.api.internal.SharedApi; import com.seibel.distanthorizons.core.dependencyInjection.SingletonInjector; import com.seibel.distanthorizons.core.logging.DhLoggerBuilder; import com.seibel.distanthorizons.core.util.math.Mat4f; +import com.seibel.distanthorizons.core.util.threading.ThreadPoolUtil; import com.seibel.distanthorizons.core.wrapperInterfaces.chunk.IChunkWrapper; import com.seibel.distanthorizons.core.wrapperInterfaces.minecraft.IMinecraftClientWrapper; @@ -168,12 +169,21 @@ public class NeoforgeClientProxy implements AbstractModInitializer.IEventProxy return; } - //LOGGER.trace("interact or block place event at blockPos: " + event.getPos()); - - LevelAccessor level = event.getLevel(); - - ChunkAccess chunk = level.getChunk(event.getPos()); - this.onBlockChangeEvent(level, chunk); + // executor to prevent locking up the render/event thread + // if the getChunk() takes longer than expected + // (which can be caused by certain mods) + var executor = ThreadPoolUtil.getFileHandlerExecutor(); + if (executor != null) + { + executor.execute(() -> + { + //LOGGER.trace("interact or block place event at blockPos: " + event.getPos()); + + LevelAccessor level = event.getLevel(); + ChunkAccess chunk = level.getChunk(event.getPos()); + this.onBlockChangeEvent(level, chunk); + }); + } } @SubscribeEvent public void leftClickBlockEvent(PlayerInteractEvent.LeftClickBlock event) @@ -183,12 +193,21 @@ public class NeoforgeClientProxy implements AbstractModInitializer.IEventProxy return; } - //LOGGER.trace("break or block attack at blockPos: " + event.getPos()); - - LevelAccessor level = event.getLevel(); - - ChunkAccess chunk = level.getChunk(event.getPos()); - this.onBlockChangeEvent(level, chunk); + // executor to prevent locking up the render/event thread + // if the getChunk() takes longer than expected + // (which can be caused by certain mods) + var executor = ThreadPoolUtil.getFileHandlerExecutor(); + if (executor != null) + { + executor.execute(() -> + { + //LOGGER.trace("break or block attack at blockPos: " + event.getPos()); + + LevelAccessor level = event.getLevel(); + ChunkAccess chunk = level.getChunk(event.getPos()); + this.onBlockChangeEvent(level, chunk); + }); + } } private void onBlockChangeEvent(LevelAccessor level, ChunkAccess chunk) {