diff --git a/src/main/java/carpet/CarpetSettings.java b/src/main/java/carpet/CarpetSettings.java index b9fd1f54..43ac7c1d 100644 --- a/src/main/java/carpet/CarpetSettings.java +++ b/src/main/java/carpet/CarpetSettings.java @@ -580,4 +580,10 @@ public class CarpetSettings category = CLIENT ) public static boolean fogOff = false; + + @Rule( + desc = "Creative No Clip", + category = {CREATIVE, CLIENT} + ) + public static boolean creativeNoClip = false; } diff --git a/src/main/java/carpet/mixins/PistonBlockEntity_creativeNoClipMixin.java b/src/main/java/carpet/mixins/PistonBlockEntity_creativeNoClipMixin.java new file mode 100644 index 00000000..9e81659f --- /dev/null +++ b/src/main/java/carpet/mixins/PistonBlockEntity_creativeNoClipMixin.java @@ -0,0 +1,29 @@ +package carpet.mixins; + +import carpet.CarpetSettings; +import net.minecraft.block.entity.PistonBlockEntity; +import net.minecraft.entity.Entity; +import net.minecraft.entity.player.PlayerEntity; +import net.minecraft.util.math.Direction; +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.Redirect; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; + +@Mixin(PistonBlockEntity.class) +public class PistonBlockEntity_creativeNoClipMixin +{ + @Inject(method = "method_23672", at = @At("HEAD"), cancellable = true) + private static void dontPushSpectators(Direction direction, Entity entity, double d, Direction direction2, CallbackInfo ci) + { + if (CarpetSettings.creativeNoClip && entity instanceof PlayerEntity && (((PlayerEntity) entity).isCreative()) && ((PlayerEntity) entity).abilities.flying) ci.cancel(); + } + + @Redirect(method = "pushEntities", at = @At(value = "INVOKE", target = "Lnet/minecraft/entity/Entity;setVelocity(DDD)V")) + private void ignoreAccel(Entity entity, double x, double y, double z) + { + if (CarpetSettings.creativeNoClip && entity instanceof PlayerEntity && (((PlayerEntity) entity).isCreative()) && ((PlayerEntity) entity).abilities.flying) return; + entity.setVelocity(x,y,z); + } +} diff --git a/src/main/java/carpet/mixins/PlayerEntity_creativeNoClipMixin.java b/src/main/java/carpet/mixins/PlayerEntity_creativeNoClipMixin.java new file mode 100644 index 00000000..ea50dab4 --- /dev/null +++ b/src/main/java/carpet/mixins/PlayerEntity_creativeNoClipMixin.java @@ -0,0 +1,56 @@ +package carpet.mixins; + +import carpet.CarpetSettings; +import net.minecraft.entity.EntityType; +import net.minecraft.entity.LivingEntity; +import net.minecraft.entity.MovementType; +import net.minecraft.entity.player.PlayerAbilities; +import net.minecraft.entity.player.PlayerEntity; +import net.minecraft.util.math.Vec3d; +import net.minecraft.world.World; +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.Redirect; + +@Mixin(PlayerEntity.class) +public abstract class PlayerEntity_creativeNoClipMixin extends LivingEntity +{ + @Shadow public abstract boolean isCreative(); + + @Shadow @Final public PlayerAbilities abilities; + + protected PlayerEntity_creativeNoClipMixin(EntityType type, World world) + { + super(type, world); + } + + @Redirect(method = "tick", at = @At( + value = "INVOKE", + target = "Lnet/minecraft/entity/player/PlayerEntity;isSpectator()Z") + ) + private boolean canClipTroughWorld(PlayerEntity playerEntity) + { + return playerEntity.isSpectator() || (CarpetSettings.creativeNoClip && playerEntity.isCreative() && playerEntity.abilities.flying); + + } + + @Redirect(method = "tickMovement", at = @At( + value = "INVOKE", + target = "Lnet/minecraft/entity/player/PlayerEntity;isSpectator()Z") + ) + private boolean collidesWithEntities(PlayerEntity playerEntity) + { + return playerEntity.isSpectator() || (CarpetSettings.creativeNoClip && playerEntity.isCreative() && playerEntity.abilities.flying); + } + + @Redirect(method = "updateSize", at = @At( + value = "INVOKE", + target = "Lnet/minecraft/entity/player/PlayerEntity;isSpectator()Z") + ) + private boolean spectatorsDontPose(PlayerEntity playerEntity) + { + return playerEntity.isSpectator() || (CarpetSettings.creativeNoClip && playerEntity.isCreative() && playerEntity.abilities.flying); + } +} diff --git a/src/main/java/carpet/mixins/WorldRenderer_creativeNoClipMixin.java b/src/main/java/carpet/mixins/WorldRenderer_creativeNoClipMixin.java new file mode 100644 index 00000000..4e8a8109 --- /dev/null +++ b/src/main/java/carpet/mixins/WorldRenderer_creativeNoClipMixin.java @@ -0,0 +1,19 @@ +package carpet.mixins; + +import carpet.CarpetSettings; +import net.minecraft.client.network.ClientPlayerEntity; +import net.minecraft.client.render.WorldRenderer; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Redirect; + +@Mixin(WorldRenderer.class) +public class WorldRenderer_creativeNoClipMixin +{ + @Redirect(method = "render", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/ClientPlayerEntity;isSpectator()Z")) + private boolean canSeeWorld(ClientPlayerEntity clientPlayerEntity) + { + return clientPlayerEntity.isSpectator() || (CarpetSettings.creativeNoClip && clientPlayerEntity.isCreative()); + } + +} diff --git a/src/main/resources/carpet.mixins.json b/src/main/resources/carpet.mixins.json index ead13568..ce36d841 100644 --- a/src/main/resources/carpet.mixins.json +++ b/src/main/resources/carpet.mixins.json @@ -156,7 +156,10 @@ "PistonBlockEntity_movableTEMixin", "World_movableTEMixin", "WorldChunk_movableTEMixin", - "PistonHandler_movableTEMixin" + "PistonHandler_movableTEMixin", + "PlayerEntity_creativeNoClipMixin", + "PistonBlockEntity_creativeNoClipMixin" + ], "client": [ "RenderTickCounter_tickSpeedMixin", @@ -169,7 +172,9 @@ "PistonBlockEntityRenderer_movableTEMixin", "ClientPlayNetworkHandler_smoothClientAnimationsMixin", "ClientPlayerEntity_clientCommandMixin", - "WorldRenderer_fogOffMixin" + "WorldRenderer_fogOffMixin", + "WorldRenderer_creativeNoClipMixin" + ], "server": [ "MinecraftDedicatedServerMixin"