diff --git a/src/client/java/com/straice/smoothdoors/SmoothDoubleDoorsClient.java b/src/client/java/com/straice/smoothdoors/SmoothDoubleDoorsClient.java index adb50f0..0277d87 100644 --- a/src/client/java/com/straice/smoothdoors/SmoothDoubleDoorsClient.java +++ b/src/client/java/com/straice/smoothdoors/SmoothDoubleDoorsClient.java @@ -3,8 +3,8 @@ package com.straice.smoothdoors; import net.fabricmc.api.ClientModInitializer; public class SmoothDoubleDoorsClient implements ClientModInitializer { - @Override - public void onInitializeClient() { - // This entrypoint is suitable for setting up client-specific logic, such as rendering. - } -} \ No newline at end of file + @Override + public void onInitializeClient() { + // No-op: hooks handled by mixins/events + } +} diff --git a/src/client/java/com/straice/smoothdoors/client/anim/SddAnimator.java b/src/client/java/com/straice/smoothdoors/client/anim/SddAnimator.java index c2d49c2..d22147f 100644 --- a/src/client/java/com/straice/smoothdoors/client/anim/SddAnimator.java +++ b/src/client/java/com/straice/smoothdoors/client/anim/SddAnimator.java @@ -2,339 +2,270 @@ package com.straice.smoothdoors.client.anim; import com.straice.smoothdoors.config.SddConfig; import com.straice.smoothdoors.config.SddConfigManager; -import net.minecraft.block.Block; -import net.minecraft.block.BlockState; -import net.minecraft.block.DoorBlock; -import net.minecraft.block.FenceGateBlock; -import net.minecraft.block.TrapdoorBlock; +import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap; +import net.minecraft.block.*; import net.minecraft.block.enums.BlockHalf; import net.minecraft.block.enums.DoorHinge; -import net.minecraft.block.enums.DoubleBlockHalf; import net.minecraft.client.MinecraftClient; import net.minecraft.client.render.OverlayTexture; import net.minecraft.client.render.VertexConsumerProvider; import net.minecraft.client.render.WorldRenderer; -import net.minecraft.client.render.block.BlockRenderManager; import net.minecraft.client.util.math.MatrixStack; -import net.minecraft.state.property.Properties; -import net.minecraft.util.math.BlockPos; -import net.minecraft.util.math.Direction; +import net.minecraft.util.math.*; import net.minecraft.util.math.RotationAxis; -import net.minecraft.util.math.Vec3d; - -import java.util.Iterator; -import java.util.Map; -import java.util.concurrent.ConcurrentHashMap; +import net.minecraft.world.BlockRenderView; public final class SddAnimator { - public enum Kind { - DOOR, - TRAPDOOR, - FENCE_GATE - } + private static final MinecraftClient MC = MinecraftClient.getInstance(); - private static final Map ANIMS = new ConcurrentHashMap<>(); - private static long lastNs = -1L; + // Duración base (segundos) a speed=1.0x + private static final float BASE_DURATION_S = 0.35f; + + private static final Long2ObjectOpenHashMap ANIMS = new Long2ObjectOpenHashMap<>(); private SddAnimator() {} - private static final class Anim { - final BlockPos pos; - final Kind kind; - final boolean toOpen; - float time; // seconds - final BlockState baseClosed; // state renderizado (cerrado) al que aplicamos la rotación + // === API que te piden los mixins === - Anim(BlockPos pos, Kind kind, boolean toOpen, BlockState baseClosed) { - this.pos = pos; - this.kind = kind; - this.toOpen = toOpen; - this.baseClosed = baseClosed; - this.time = 0f; - } + /** Se usa en BlockRenderManagerMixin para ocultar el bloque vanilla mientras animamos. */ + public static boolean shouldHideInChunk(BlockPos pos, BlockState state) { + return ANIMS.containsKey(pos.asLong()); } - // ========= API (llamada desde mixins) ========= - + /** Se usa para arrancar/parar animaciones cuando cambia un bloque. */ public static void onBlockUpdate(BlockPos pos, BlockState oldState, BlockState newState) { - Kind kNew = kindOf(newState); - if (kNew == null) { - ANIMS.remove(pos); + Kind kind = kindOf(oldState, newState); + if (kind == null) { + ANIMS.remove(pos.asLong()); return; } - if (!newState.contains(Properties.OPEN)) return; - boolean oldOpen = oldState.contains(Properties.OPEN) && oldState.get(Properties.OPEN); - boolean newOpen = newState.get(Properties.OPEN); + boolean oldOpen = isOpen(oldState); + boolean newOpen = isOpen(newState); if (oldOpen == newOpen) return; - MinecraftClient client = MinecraftClient.getInstance(); - if (client.world == null) return; - - // Door: animar lower+upper - if (kNew == Kind.DOOR && newState.getBlock() instanceof DoorBlock && newState.contains(Properties.DOUBLE_BLOCK_HALF)) { - DoubleBlockHalf half = newState.get(Properties.DOUBLE_BLOCK_HALF); - BlockPos basePos = (half == DoubleBlockHalf.UPPER) ? pos.down() : pos; - - BlockState lower = client.world.getBlockState(basePos); - BlockState upper = client.world.getBlockState(basePos.up()); - - BlockState lowerClosed = (lower.getBlock() instanceof DoorBlock && lower.contains(Properties.OPEN)) - ? lower.with(Properties.OPEN, false) - : newState.with(Properties.OPEN, false).with(Properties.DOUBLE_BLOCK_HALF, DoubleBlockHalf.LOWER); - - BlockState upperClosed = (upper.getBlock() instanceof DoorBlock && upper.contains(Properties.OPEN)) - ? upper.with(Properties.OPEN, false) - : newState.with(Properties.OPEN, false).with(Properties.DOUBLE_BLOCK_HALF, DoubleBlockHalf.UPPER); - - startAnim(basePos, Kind.DOOR, newOpen, lowerClosed); - startAnim(basePos.up(), Kind.DOOR, newOpen, upperClosed); + SddConfig cfg = SddConfigManager.get(); + if (!isAnimationEnabled(cfg, kind)) { + ANIMS.remove(pos.asLong()); return; } - // Trapdoor / Fence gate - startAnim(pos, kNew, newOpen, newState.with(Properties.OPEN, false)); + float speed = speedFor(cfg, kind); + if (speed <= 0.001f) speed = 1.0f; + + // Renderizamos SIEMPRE el modelo "cerrado" y nosotros aplicamos la rotación. + BlockState base = forceClosedModel(newState, kind); + + Anim anim = new Anim(pos.toImmutable(), base, kind, oldOpen, newOpen, speed); + ANIMS.put(pos.asLong(), anim); } - /** - * Si devuelve true, el mixin que renderiza chunks debe "ocultar" el bloque real para que - * sólo se vea el animado. - */ - public static boolean shouldHideInChunk(BlockPos pos, BlockState state) { - Anim a = ANIMS.get(pos); - if (a == null) return false; - if (kindOf(state) != a.kind) return false; + /** Render con tickDelta explícito. */ + public static void renderAll(Vec3d camPos, float tickDelta) { + if (ANIMS.isEmpty() || MC.world == null) return; - SddConfig cfg = SddConfigManager.get(); - return isEnabled(cfg, a.kind); - } + tick(tickDelta); - /** - * Llamar cada frame desde WorldRendererMixin, pasando camera.getPos(). - */ - public static void renderAll(Vec3d camPos) { - MinecraftClient client = MinecraftClient.getInstance(); - if (client.world == null) { - ANIMS.clear(); - lastNs = -1L; - return; - } + VertexConsumerProvider.Immediate consumers = MC.getBufferBuilders().getEntityVertexConsumers(); + MatrixStack matrices = new MatrixStack(); - float dt = frameDtSeconds(); - if (ANIMS.isEmpty()) return; - - SddConfig cfg = SddConfigManager.get(); - BlockRenderManager brm = client.getBlockRenderManager(); - VertexConsumerProvider.Immediate consumers = client.getBufferBuilders().getEntityVertexConsumers(); - - Iterator> it = ANIMS.entrySet().iterator(); - while (it.hasNext()) { - Anim a = it.next().getValue(); - - if (!isEnabled(cfg, a.kind)) { - it.remove(); - continue; - } - - float speed = getSpeed(cfg, a.kind); - - float baseDuration = switch (a.kind) { - case DOOR -> 0.18f; - case TRAPDOOR -> 0.16f; - case FENCE_GATE -> 0.16f; - }; - float dur = baseDuration / Math.max(0.05f, speed); - - a.time += dt; - float t = (dur <= 0f) ? 1f : (a.time / dur); - if (t > 1f) t = 1f; - - float eased = smoothStep(t); - float open01 = a.toOpen ? eased : (1f - eased); - - renderOne(client, brm, consumers, camPos, a, open01); - - if (t >= 1f) it.remove(); + for (Anim a : ANIMS.values()) { + renderOne(a, camPos, matrices, consumers); } consumers.draw(); + cleanupFinished(); } - // ========= Render ========= + /** Overload por compat si algún sitio llama sin tickDelta. */ + public static void renderAll(Vec3d camPos) { + float tickDelta = 0.0f; + if (MC != null) { + // En 1.21.x normalmente es esto: + tickDelta = MC.getRenderTickCounter().getTickProgress(true); + } + renderAll(camPos, tickDelta); + } - private static void renderOne(MinecraftClient client, - BlockRenderManager brm, - VertexConsumerProvider.Immediate consumers, - Vec3d camPos, - Anim a, - float open01) { + // === Interno === - BlockState worldState = client.world.getBlockState(a.pos); - if (kindOf(worldState) != a.kind) return; + private static void tick(float tickDelta) { + float dt = (1.0f / 20.0f) * MathHelper.clamp(tickDelta, 0.0f, 1.0f); - MatrixStack matrices = new MatrixStack(); + for (Anim a : ANIMS.values()) { + float duration = BASE_DURATION_S / a.speed; + if (duration < 0.05f) duration = 0.05f; - // CLAVE: coordenadas relativas a cámara + float step = dt / duration; + a.t = MathHelper.clamp(a.t + step, 0.0f, 1.0f); + } + } + + private static void cleanupFinished() { + ANIMS.long2ObjectEntrySet().removeIf(e -> e.getValue().t >= 1.0f); + } + + private static void renderOne(Anim anim, Vec3d camPos, MatrixStack matrices, VertexConsumerProvider consumers) { + if (MC.world == null) return; + + BlockPos pos = anim.pos; + BlockState state = anim.baseState; + + matrices.push(); matrices.translate( - a.pos.getX() - camPos.x, - a.pos.getY() - camPos.y, - a.pos.getZ() - camPos.z + pos.getX() - camPos.x, + pos.getY() - camPos.y, + pos.getZ() - camPos.z ); - int light = WorldRenderer.getLightmapCoordinates(client.world, a.pos); + float eased = easeInOut(anim.t); + float angleDeg = lerpAngleDeg(anim.fromOpen, anim.toOpen, eased, anim.kind, state); + applyTransform(anim.kind, state, angleDeg, matrices); - switch (a.kind) { - case DOOR -> applyDoorTransform(matrices, worldState, open01); - case TRAPDOOR -> applyTrapdoorTransform(matrices, worldState, open01); - case FENCE_GATE -> applyFenceGateTransform(matrices, worldState, open01); - } + int light = WorldRenderer.getLightmapCoordinates((BlockRenderView) MC.world, pos); + MC.getBlockRenderManager().renderBlockAsEntity(state, matrices, consumers, light, OverlayTexture.DEFAULT_UV); - brm.renderBlockAsEntity(a.baseClosed, matrices, consumers, light, OverlayTexture.DEFAULT_UV); + matrices.pop(); } - // ========= Transforms ========= - - private static void applyDoorTransform(MatrixStack m, BlockState worldState, float open01) { - if (!(worldState.getBlock() instanceof DoorBlock)) return; - - Direction facing = worldState.get(Properties.HORIZONTAL_FACING); - DoorHinge hinge = worldState.get(Properties.DOOR_HINGE); - - float pivotX = 0.5f; - float pivotZ = 0.5f; - - switch (facing) { - case NORTH -> pivotX = (hinge == DoorHinge.LEFT) ? 0.0f : 1.0f; - case SOUTH -> pivotX = (hinge == DoorHinge.LEFT) ? 1.0f : 0.0f; - case EAST -> pivotZ = (hinge == DoorHinge.LEFT) ? 0.0f : 1.0f; - case WEST -> pivotZ = (hinge == DoorHinge.LEFT) ? 1.0f : 0.0f; - default -> {} - } - - float sign; - switch (facing) { - case NORTH -> sign = (hinge == DoorHinge.RIGHT) ? -1f : 1f; - case SOUTH -> sign = (hinge == DoorHinge.RIGHT) ? 1f : -1f; - case EAST -> sign = (hinge == DoorHinge.RIGHT) ? 1f : -1f; - case WEST -> sign = (hinge == DoorHinge.RIGHT) ? -1f : 1f; - default -> sign = 1f; - } - - float yawDeg = open01 * 90.0f * sign; - - m.translate(pivotX, 0.0f, pivotZ); - m.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(yawDeg)); - m.translate(-pivotX, 0.0f, -pivotZ); + private static float lerpAngleDeg(boolean fromOpen, boolean toOpen, float t, Kind kind, BlockState state) { + float a = angleFor(kind, state, fromOpen); + float b = angleFor(kind, state, toOpen); + return MathHelper.lerp(t, a, b); } - private static void applyTrapdoorTransform(MatrixStack m, BlockState worldState, float open01) { - if (!(worldState.getBlock() instanceof TrapdoorBlock)) return; + private static float angleFor(Kind kind, BlockState state, boolean open) { + if (!open) return 0.0f; - Direction facing = worldState.get(Properties.HORIZONTAL_FACING); - BlockHalf half = worldState.get(Properties.BLOCK_HALF); + switch (kind) { + case DOOR -> { + DoorHinge hinge = state.get(DoorBlock.HINGE); + return (hinge == DoorHinge.RIGHT) ? -90.0f : 90.0f; + } + case TRAPDOOR -> { + BlockHalf half = state.get(TrapdoorBlock.HALF); + return (half == BlockHalf.TOP) ? -90.0f : 90.0f; + } + case FENCE_GATE -> { + return 90.0f; + } + } + return 0.0f; + } - float sign = (half == BlockHalf.TOP) ? -1f : 1f; - float angle = open01 * 90.0f * sign; - - float pivotX = 0.5f; - float pivotY = 0.5f; - float pivotZ = 0.5f; - - switch (facing) { - case NORTH -> { - pivotZ = 0.0f; - m.translate(pivotX, pivotY, pivotZ); - m.multiply(RotationAxis.POSITIVE_X.rotationDegrees(angle)); - m.translate(-pivotX, -pivotY, -pivotZ); - } - case SOUTH -> { - pivotZ = 1.0f; - m.translate(pivotX, pivotY, pivotZ); - m.multiply(RotationAxis.NEGATIVE_X.rotationDegrees(angle)); - m.translate(-pivotX, -pivotY, -pivotZ); - } - case WEST -> { - pivotX = 0.0f; - m.translate(pivotX, pivotY, pivotZ); - m.multiply(RotationAxis.NEGATIVE_Z.rotationDegrees(angle)); - m.translate(-pivotX, -pivotY, -pivotZ); - } - case EAST -> { - pivotX = 1.0f; - m.translate(pivotX, pivotY, pivotZ); - m.multiply(RotationAxis.POSITIVE_Z.rotationDegrees(angle)); - m.translate(-pivotX, -pivotY, -pivotZ); - } - default -> {} + private static void applyTransform(Kind kind, BlockState state, float angleDeg, MatrixStack matrices) { + switch (kind) { + case DOOR -> transformDoor(state, angleDeg, matrices); + case TRAPDOOR -> transformTrapdoor(state, angleDeg, matrices); + case FENCE_GATE -> transformFenceGate(state, angleDeg, matrices); } } - private static void applyFenceGateTransform(MatrixStack m, BlockState worldState, float open01) { - if (!(worldState.getBlock() instanceof FenceGateBlock)) return; + private static void transformDoor(BlockState state, float angleDeg, MatrixStack matrices) { + Direction facing = state.get(DoorBlock.FACING); + DoorHinge hinge = state.get(DoorBlock.HINGE); - Direction facing = worldState.get(Properties.HORIZONTAL_FACING); + Direction hingeSide = (hinge == DoorHinge.RIGHT) ? facing.rotateYClockwise() : facing.rotateYCounterclockwise(); + float pivotX = hingeSide.getOffsetX() == 1 ? 1.0f : (hingeSide.getOffsetX() == -1 ? 0.0f : 0.5f); + float pivotZ = hingeSide.getOffsetZ() == 1 ? 1.0f : (hingeSide.getOffsetZ() == -1 ? 0.0f : 0.5f); - float sign; - switch (facing) { - case NORTH, WEST -> sign = 1f; - case SOUTH, EAST -> sign = -1f; - default -> sign = 1f; - } - - float yawDeg = open01 * 90.0f * sign; - - m.translate(0.5f, 0.0f, 0.5f); - m.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(yawDeg)); - m.translate(-0.5f, 0.0f, -0.5f); + matrices.translate(pivotX, 0.0f, pivotZ); + matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(angleDeg)); + matrices.translate(-pivotX, 0.0f, -pivotZ); } - // ========= Helpers ========= + private static void transformTrapdoor(BlockState state, float angleDeg, MatrixStack matrices) { + Direction facing = state.get(TrapdoorBlock.FACING); - private static Kind kindOf(BlockState s) { + float pivotX = facing.getOffsetX() == 1 ? 1.0f : (facing.getOffsetX() == -1 ? 0.0f : 0.5f); + float pivotZ = facing.getOffsetZ() == 1 ? 1.0f : (facing.getOffsetZ() == -1 ? 0.0f : 0.5f); + + matrices.translate(pivotX, 0.5f, pivotZ); + if (facing == Direction.NORTH || facing == Direction.SOUTH) { + matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(angleDeg)); + } else { + matrices.multiply(RotationAxis.POSITIVE_Z.rotationDegrees(-angleDeg)); + } + matrices.translate(-pivotX, -0.5f, -pivotZ); + } + + private static void transformFenceGate(BlockState state, float angleDeg, MatrixStack matrices) { + matrices.translate(0.5f, 0.0f, 0.5f); + matrices.multiply(RotationAxis.POSITIVE_Y.rotationDegrees(angleDeg)); + matrices.translate(-0.5f, 0.0f, -0.5f); + } + + private static BlockState forceClosedModel(BlockState s, Kind kind) { + return switch (kind) { + case DOOR -> s.with(DoorBlock.OPEN, false); + case TRAPDOOR -> s.with(TrapdoorBlock.OPEN, false); + case FENCE_GATE -> s.with(FenceGateBlock.OPEN, false); + }; + } + + private static boolean isOpen(BlockState s) { Block b = s.getBlock(); + if (b instanceof DoorBlock) return s.get(DoorBlock.OPEN); + if (b instanceof TrapdoorBlock) return s.get(TrapdoorBlock.OPEN); + if (b instanceof FenceGateBlock) return s.get(FenceGateBlock.OPEN); + return false; + } + + private static Kind kindOf(BlockState oldState, BlockState newState) { + Block b = newState.getBlock(); if (b instanceof DoorBlock) return Kind.DOOR; if (b instanceof TrapdoorBlock) return Kind.TRAPDOOR; if (b instanceof FenceGateBlock) return Kind.FENCE_GATE; + + b = oldState.getBlock(); + if (b instanceof DoorBlock) return Kind.DOOR; + if (b instanceof TrapdoorBlock) return Kind.TRAPDOOR; + if (b instanceof FenceGateBlock) return Kind.FENCE_GATE; + return null; } - private static void startAnim(BlockPos pos, Kind kind, boolean toOpen, BlockState baseClosed) { - ANIMS.put(pos.toImmutable(), new Anim(pos.toImmutable(), kind, toOpen, baseClosed)); - } - - private static boolean isEnabled(SddConfig cfg, Kind kind) { + private static boolean isAnimationEnabled(SddConfig cfg, Kind kind) { return switch (kind) { case DOOR -> cfg.animateDoors; case TRAPDOOR -> cfg.animateTrapdoors; - case FENCE_GATE -> cfg.animateFenceGates; + case FENCE_GATE -> cfg.animateFenceGates; // debe existir en tu config }; } - private static float getSpeed(SddConfig cfg, Kind kind) { + private static float speedFor(SddConfig cfg, Kind kind) { return switch (kind) { case DOOR -> cfg.doorSpeed; case TRAPDOOR -> cfg.trapdoorSpeed; - case FENCE_GATE -> cfg.fenceGateSpeed; + case FENCE_GATE -> cfg.fenceGateSpeed; // debe existir en tu config }; } - private static float smoothStep(float t) { - return t * t * (3f - 2f * t); + private static float easeInOut(float t) { + return t * t * (3.0f - 2.0f * t); } - private static float frameDtSeconds() { - long now = System.nanoTime(); - if (lastNs < 0L) { - lastNs = now; - return 0f; - } - long d = now - lastNs; - lastNs = now; + public enum Kind { DOOR, TRAPDOOR, FENCE_GATE } - double sec = d / 1_000_000_000.0; - if (sec < 0) sec = 0; - if (sec > 0.1) sec = 0.1; - return (float) sec; + private static final class Anim { + final BlockPos pos; + final BlockState baseState; + final Kind kind; + final boolean fromOpen; + final boolean toOpen; + final float speed; + + float t; // 0..1 + + Anim(BlockPos pos, BlockState baseState, Kind kind, boolean fromOpen, boolean toOpen, float speed) { + this.pos = pos; + this.baseState = baseState; + this.kind = kind; + this.fromOpen = fromOpen; + this.toOpen = toOpen; + this.speed = speed; + this.t = 0.0f; + } } } diff --git a/src/client/java/com/straice/smoothdoors/mixin/client/BlockRenderManagerMixin.java b/src/client/java/com/straice/smoothdoors/mixin/client/BlockRenderManagerMixin.java index 18d6a82..e1b26b5 100644 --- a/src/client/java/com/straice/smoothdoors/mixin/client/BlockRenderManagerMixin.java +++ b/src/client/java/com/straice/smoothdoors/mixin/client/BlockRenderManagerMixin.java @@ -18,18 +18,14 @@ import java.util.List; public class BlockRenderManagerMixin { @Inject( - method = "renderBlock", + method = "renderBlock(Lnet/minecraft/block/BlockState;Lnet/minecraft/util/math/BlockPos;Lnet/minecraft/world/BlockRenderView;Lnet/minecraft/client/util/math/MatrixStack;Lnet/minecraft/client/render/VertexConsumer;ZLjava/util/List;)V", at = @At("HEAD"), cancellable = true ) - private void sdd$renderBlock(BlockState state, - BlockPos pos, - BlockRenderView world, - MatrixStack matrices, - VertexConsumer vertexConsumer, - boolean cull, - List list, - CallbackInfo ci) { + private void sdd$renderBlock(BlockState state, BlockPos pos, BlockRenderView world, + MatrixStack matrices, VertexConsumer vertexConsumer, + boolean cull, List parts, + CallbackInfo ci) { if (SddAnimator.shouldHideInChunk(pos, state)) { ci.cancel(); } diff --git a/src/client/java/com/straice/smoothdoors/mixin/client/ClientWorldMixin.java b/src/client/java/com/straice/smoothdoors/mixin/client/WorldMixin.java similarity index 54% rename from src/client/java/com/straice/smoothdoors/mixin/client/ClientWorldMixin.java rename to src/client/java/com/straice/smoothdoors/mixin/client/WorldMixin.java index caf677a..018b420 100644 --- a/src/client/java/com/straice/smoothdoors/mixin/client/ClientWorldMixin.java +++ b/src/client/java/com/straice/smoothdoors/mixin/client/WorldMixin.java @@ -2,18 +2,21 @@ package com.straice.smoothdoors.mixin.client; import com.straice.smoothdoors.client.anim.SddAnimator; import net.minecraft.block.BlockState; -import net.minecraft.client.world.ClientWorld; import net.minecraft.util.math.BlockPos; +import net.minecraft.world.World; 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(ClientWorld.class) -public class ClientWorldMixin { +@Mixin(World.class) +public class WorldMixin { - @Inject(method = "updateListeners", at = @At("TAIL")) - private void sdd$updateListeners(BlockPos pos, BlockState oldState, BlockState newState, int flags, CallbackInfo ci) { + @Inject( + method = "scheduleBlockRerenderIfNeeded(Lnet/minecraft/util/math/BlockPos;Lnet/minecraft/block/BlockState;Lnet/minecraft/block/BlockState;)V", + at = @At("HEAD") + ) + private void sdd$onRerender(BlockPos pos, BlockState oldState, BlockState newState, CallbackInfo ci) { SddAnimator.onBlockUpdate(pos, oldState, newState); } } diff --git a/src/client/java/com/straice/smoothdoors/mixin/client/WorldRendererMixin.java b/src/client/java/com/straice/smoothdoors/mixin/client/WorldRendererMixin.java deleted file mode 100644 index 51c30c4..0000000 --- a/src/client/java/com/straice/smoothdoors/mixin/client/WorldRendererMixin.java +++ /dev/null @@ -1,41 +0,0 @@ -package com.straice.smoothdoors.mixin.client; - -import com.mojang.blaze3d.buffers.GpuBufferSlice; -import com.straice.smoothdoors.client.anim.SddAnimator; -import net.minecraft.client.render.Camera; -import net.minecraft.client.render.RenderTickCounter; -import net.minecraft.client.render.WorldRenderer; -import net.minecraft.client.util.ObjectAllocator; -import org.joml.Matrix4f; -import org.joml.Vector4f; -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(WorldRenderer.class) -public class WorldRendererMixin { - - @Inject( - method = "render(Lnet/minecraft/client/util/ObjectAllocator;" + - "Lnet/minecraft/client/render/RenderTickCounter;" + - "ZLnet/minecraft/client/render/Camera;" + - "Lorg/joml/Matrix4f;Lorg/joml/Matrix4f;" + - "Lcom/mojang/blaze3d/buffers/GpuBufferSlice;" + - "Lorg/joml/Vector4f;Z)V", - at = @At("TAIL") - ) - private void sdd$renderTail(ObjectAllocator allocator, - RenderTickCounter tickCounter, - boolean renderBlockOutline, - Camera camera, - Matrix4f positionMatrix, - Matrix4f projectionMatrix, - GpuBufferSlice slice, - Vector4f fogColor, - boolean bl, - CallbackInfo ci) { - - SddAnimator.renderAll(camera.getPos()); - } -} diff --git a/src/client/resources/smooth-double-doors.client.mixins.json b/src/client/resources/smooth-double-doors.client.mixins.json index 97f37d5..ece13b1 100644 --- a/src/client/resources/smooth-double-doors.client.mixins.json +++ b/src/client/resources/smooth-double-doors.client.mixins.json @@ -4,8 +4,7 @@ "compatibilityLevel": "JAVA_21", "client": [ "client.ClientWorldMixin", - "client.BlockRenderManagerMixin", - "client.WorldRendererMixin" + "client.BlockRenderManagerMixin" ], "injectors": { "defaultRequire": 1