From 111120ec66b601adeaf6d2488c6eec313ee9da13 Mon Sep 17 00:00:00 2001 From: btwonion Date: Sun, 6 Oct 2024 21:41:07 +0200 Subject: [PATCH] add option to modify detection range for collisions --- README.md | 5 +- changelog.md | 2 +- gradle.properties | 2 +- .../java/dev/nyon/bbm/asm/EntityMixin.java | 47 +++++++++++++++++++ .../nyon/bbm/BetterBoatMovementEntrypoint.kt | 8 ++-- src/main/kotlin/dev/nyon/bbm/config/Config.kt | 38 +++++++++++---- .../dev/nyon/bbm/config/ConfigScreen.kt | 12 ++++- src/main/resources/assets/bbm/lang/en_us.json | 4 +- src/main/resources/bbm.mixins.json | 5 +- 9 files changed, 102 insertions(+), 21 deletions(-) create mode 100644 src/main/java/dev/nyon/bbm/asm/EntityMixin.java diff --git a/README.md b/README.md index 0904178..7c4be44 100644 --- a/README.md +++ b/README.md @@ -15,7 +15,7 @@ ```json5 { - "version": 3, // just ignore that, only for migrations + "version": 4, // just ignore that, only for migrations "config": { "stepHeight": 0.35, // The amount of blocks you are going to be boosted when triggering a boost "playerEjectTicks": 200.0, // The ticks the game waits before kicking you out of a boat after the player lost control @@ -23,7 +23,8 @@ "boostOnBlocks": false, // Toggles, whether a boat, which is on a block should be boosted upwards when running against an elevation "boostOnIce": true, // Toggles, whether a boat, which is on an ice block should be boosted upwards when running against an elevation "boostOnWater": true, // Toggles, whether a boat, which is on water should be boosted upwards when floating against an elevation - "onlyForPlayers": true // Toggles, whether a boat should only be boosted when carrying a player + "onlyForPlayers": true, // Toggles, whether a boat should only be boosted when carrying a player, + "extraCollisionDetectionRange": 0.0 // Changes the detection range of a collision. Increasing this will boost a boat x blocks before actually touching the block it approaches. You may encounter weird behaviour when changing this value to big numbers. } } ``` diff --git a/changelog.md b/changelog.md index 17c84c7..65deed5 100644 --- a/changelog.md +++ b/changelog.md @@ -1 +1 @@ -- update version range to also accept snapshots and higher versions without an update \ No newline at end of file +- add option to change the detection range of collisions \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index ae56deb..f5d3e78 100644 --- a/gradle.properties +++ b/gradle.properties @@ -12,6 +12,6 @@ mod.id=bbm mod.name=BetterBoatMovement mod.description=Increases boat step height to move up water and blocks mod.beta=0 -mod.major-version=2.2.3 +mod.major-version=2.2.4 mod.mixins=bbm.mixins.json mod.supported-loaders=fabric,quilt,neoforge,forge \ No newline at end of file diff --git a/src/main/java/dev/nyon/bbm/asm/EntityMixin.java b/src/main/java/dev/nyon/bbm/asm/EntityMixin.java new file mode 100644 index 0000000..e9ce0c0 --- /dev/null +++ b/src/main/java/dev/nyon/bbm/asm/EntityMixin.java @@ -0,0 +1,47 @@ +package dev.nyon.bbm.asm; + +import dev.nyon.bbm.config.Config; +import dev.nyon.bbm.config.ConfigKt; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.entity.vehicle.Boat; +import net.minecraft.world.level.Level; +import net.minecraft.world.phys.AABB; +import net.minecraft.world.phys.Vec3; +import net.minecraft.world.phys.shapes.VoxelShape; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.ModifyArg; + +import java.util.List; + +@Mixin(Entity.class) +public class EntityMixin { + @ModifyArg( + method = "collide", + at = @At( + value = "INVOKE", + target = "Lnet/minecraft/world/entity/Entity;collideBoundingBox(Lnet/minecraft/world/entity/Entity;Lnet/minecraft/world/phys/Vec3;Lnet/minecraft/world/phys/AABB;Lnet/minecraft/world/level/Level;Ljava/util/List;)Lnet/minecraft/world/phys/Vec3;" + ), + index = 2 + ) + private AABB changeCollisionRange( + Entity entity, + Vec3 movement, + AABB box, + Level world, + List shapes + ) { + if (!(entity instanceof Boat boat)) return box; + Config config = ConfigKt.getActiveConfig(); + if (config == null) return box; + + if (boat.getPassengers() + .stream() + .filter(passenger -> passenger instanceof Player) + .toList() + .isEmpty() && config.getOnlyForPlayers()) return box; + + return box.inflate(config.getExtraCollisionDetectionRange(), 0, config.getExtraCollisionDetectionRange()); + } +} diff --git a/src/main/kotlin/dev/nyon/bbm/BetterBoatMovementEntrypoint.kt b/src/main/kotlin/dev/nyon/bbm/BetterBoatMovementEntrypoint.kt index d190d88..ea1371a 100644 --- a/src/main/kotlin/dev/nyon/bbm/BetterBoatMovementEntrypoint.kt +++ b/src/main/kotlin/dev/nyon/bbm/BetterBoatMovementEntrypoint.kt @@ -83,7 +83,7 @@ object BetterBoatMovementEntrypoint { /^? if >=1.20.5 {^/ MOD_BUS.addListener { event -> - val registrar = event.registrar("3") + val registrar = event.registrar("4") registrar.playToClient(Config.packetType, Config.codec, DirectionalPayloadHandler( { config, _ -> serverConfig = config @@ -92,7 +92,7 @@ object BetterBoatMovementEntrypoint { } /^?} else {^/ /^MOD_BUS.addListener { event -> - val registrar = event.registrar("3") + val registrar = event.registrar("4") registrar.play(Config.identifier, FriendlyByteBuf.Reader{ buf -> Config(buf) }) { handler -> handler.client { config, _ -> serverConfig = config }.server { _, _ -> } } @@ -145,7 +145,7 @@ object BetterBoatMovementEntrypoint { init { instantiateConfig(FMLLoader.getGamePath().resolve("config/better-boat-movement.json")) - val channel = NetworkRegistry.newSimpleChannel(resourceLocation("better-boat-movement:channel"), { "3" }, { true }, { true }) + val channel = NetworkRegistry.newSimpleChannel(resourceLocation("better-boat-movement:channel"), { "4" }, { true }, { true }) channel.registerMessage( 0, Config::class.java, @@ -190,7 +190,7 @@ object BetterBoatMovementEntrypoint { private fun instantiateConfig(path: Path) { config( path, - 3, + 4, Config() ) { element, version -> migrate(element, version) } config = loadConfig() diff --git a/src/main/kotlin/dev/nyon/bbm/config/Config.kt b/src/main/kotlin/dev/nyon/bbm/config/Config.kt index e8ef924..c0f694f 100644 --- a/src/main/kotlin/dev/nyon/bbm/config/Config.kt +++ b/src/main/kotlin/dev/nyon/bbm/config/Config.kt @@ -19,7 +19,8 @@ data class Config( var boostOnBlocks: Boolean = true, var boostOnIce: Boolean = true, var boostOnWater: Boolean = true, - var onlyForPlayers: Boolean = true + var onlyForPlayers: Boolean = true, + var extraCollisionDetectionRange: Double = 0.0 ) : CustomPacketPayload { companion object { @Transient @@ -37,7 +38,8 @@ data class Config( buf.readBoolean(), buf.readBoolean(), buf.readBoolean(), - buf.readBoolean() + buf.readBoolean(), + buf.readDouble() ) } @@ -52,6 +54,7 @@ data class Config( buf.writeBoolean(config.boostOnIce) buf.writeBoolean(config.boostOnWater) buf.writeBoolean(config.onlyForPlayers) + buf.writeDouble(config.extraCollisionDetectionRange) } } } @@ -72,7 +75,8 @@ data class Config( var boostOnBlocks: Boolean = true, var boostOnIce: Boolean = true, var boostOnWater: Boolean = true, - var onlyForPlayers: Boolean = true + var onlyForPlayers: Boolean = true, + var extraCollisionDetectionRange: Double = 0.0 ) : FabricPacket { companion object { @Transient @@ -86,7 +90,8 @@ data class Config( buffer.readBoolean(), buffer.readBoolean(), buffer.readBoolean(), - buffer.readBoolean() + buffer.readBoolean(), + buffer.readDouble() ) } } @@ -99,6 +104,7 @@ data class Config( buf.writeBoolean(boostOnIce) buf.writeBoolean(boostOnWater) buf.writeBoolean(onlyForPlayers) + buf.writeDouble(config.extraCollisionDetectionRange) } override fun getType(): PacketType<*> { @@ -117,7 +123,8 @@ data class Config( var boostOnBlocks: Boolean = true, var boostOnIce: Boolean = true, var boostOnWater: Boolean = true, - var onlyForPlayers: Boolean = true + var onlyForPlayers: Boolean = true, + var extraCollisionDetectionRange: Double = 0.0 ) : CustomPacketPayload { companion object { @Transient @@ -131,7 +138,8 @@ data class Config( buf.readBoolean(), buf.readBoolean(), buf.readBoolean(), - buf.readBoolean() + buf.readBoolean(), + buf.readDouble() ) override fun write(buf: FriendlyByteBuf) { @@ -142,6 +150,7 @@ data class Config( buf.writeBoolean(config.boostOnIce) buf.writeBoolean(config.boostOnWater) buf.writeBoolean(config.onlyForPlayers) + buf.writeDouble(config.extraCollisionDetectionRange) } override fun id(): ResourceLocation { @@ -156,7 +165,8 @@ data class Config( var boostOnBlocks: Boolean = true, var boostOnIce: Boolean = true, var boostOnWater: Boolean = true, - var onlyForPlayers: Boolean = true + var onlyForPlayers: Boolean = true, + var extraCollisionDetectionRange: Double = 0.0 ) { constructor(buf: FriendlyByteBuf) : this( buf.readFloat(), @@ -165,7 +175,8 @@ data class Config( buf.readBoolean(), buf.readBoolean(), buf.readBoolean(), - buf.readBoolean() + buf.readBoolean(), + buf.readDouble() ) fun write(buf: FriendlyByteBuf) { @@ -176,6 +187,7 @@ data class Config( buf.writeBoolean(config.boostOnIce) buf.writeBoolean(config.boostOnWater) buf.writeBoolean(config.onlyForPlayers) + buf.writeDouble(config.extraCollisionDetectionRange) } } @@ -203,6 +215,16 @@ fun migrate(tree: JsonElement, version: Int?): Config? { boostUnderwater = jsonObject["boostUnderwater"]?.jsonPrimitive?.booleanOrNull ?: return null, onlyForPlayers = jsonObject["onlyForPlayers"]?.jsonPrimitive?.booleanOrNull ?: return null ) + 3 -> Config( + jsonObject["stepHeight"]?.jsonPrimitive?.floatOrNull ?: return null, + jsonObject["playerEjectTicks"]?.jsonPrimitive?.floatOrNull ?: return null, + jsonObject["boostUnderwater"]?.jsonPrimitive?.booleanOrNull ?: return null, + jsonObject["boostOnBlocks"]?.jsonPrimitive?.booleanOrNull ?: return null, + jsonObject["boostOnIce"]?.jsonPrimitive?.booleanOrNull ?: return null, + jsonObject["boostOnWater"]?.jsonPrimitive?.booleanOrNull ?: return null, + jsonObject["onlyForPlayers"]?.jsonPrimitive?.booleanOrNull ?: return null, + jsonObject["extraCollisionDetectionRange"]?.jsonPrimitive?.doubleOrNull ?: return null + ) else -> null } } diff --git a/src/main/kotlin/dev/nyon/bbm/config/ConfigScreen.kt b/src/main/kotlin/dev/nyon/bbm/config/ConfigScreen.kt index 89509f7..1acfebe 100644 --- a/src/main/kotlin/dev/nyon/bbm/config/ConfigScreen.kt +++ b/src/main/kotlin/dev/nyon/bbm/config/ConfigScreen.kt @@ -7,7 +7,7 @@ import net.minecraft.client.gui.screens.Screen fun generateYaclScreen(parent: Screen?): Screen = YetAnotherConfigLib("bbm") { val general by categories.registering { val stepHeight by rootOptions.registering { - binding(1f, { config.stepHeight }, { config.stepHeight = it}) + binding(1f, { config.stepHeight }, { config.stepHeight = it }) controller = numberField(0f) descriptionBuilder { addDefaultText(1) @@ -15,7 +15,7 @@ fun generateYaclScreen(parent: Screen?): Screen = YetAnotherConfigLib("bbm") { } val playerEjectTicks by rootOptions.registering { - binding(0.2f, { config.playerEjectTicks }, { config.playerEjectTicks = it}) + binding(0.2f, { config.playerEjectTicks }, { config.playerEjectTicks = it }) controller = numberField(0f, 10000f) descriptionBuilder { addDefaultText(1) @@ -61,6 +61,14 @@ fun generateYaclScreen(parent: Screen?): Screen = YetAnotherConfigLib("bbm") { addDefaultText(1) } } + + val extraCollisionDetectionRange by rootOptions.registering { + binding(0.0, { config.extraCollisionDetectionRange }, { config.extraCollisionDetectionRange = it }) + controller = numberField(0.0) + descriptionBuilder { + addDefaultText(1) + } + } } save { saveConfig(config) } diff --git a/src/main/resources/assets/bbm/lang/en_us.json b/src/main/resources/assets/bbm/lang/en_us.json index 7705603..d3eb078 100644 --- a/src/main/resources/assets/bbm/lang/en_us.json +++ b/src/main/resources/assets/bbm/lang/en_us.json @@ -14,5 +14,7 @@ "yacl3.config.bbm.category.general.root.option.boostOnWater": "Boost on water", "yacl3.config.bbm.category.general.root.option.boostOnWater.description": "Toggles, whether a boat, which is on water should be boosted upwards when floating against an elevation.", "yacl3.config.bbm.category.general.root.option.onlyForPlayers": "Only for players", - "yacl3.config.bbm.category.general.root.option.onlyForPlayers.description": "Toggles, whether a boat should only be boosted when carrying a player." + "yacl3.config.bbm.category.general.root.option.onlyForPlayers.description": "Toggles, whether a boat should only be boosted when carrying a player.", + "yacl3.config.bbm.category.general.root.option.extraCollisionDetectionRange": "Extra collision detection range", + "yacl3.config.bbm.category.general.root.option.extraCollisionDetectionRange.description": "Changes the detection range of a collision. Increasing this will boost a boat x blocks before actually touching the block it approaches.\n*You may encounter weird behaviour when changing this value to big numbers.*" } diff --git a/src/main/resources/bbm.mixins.json b/src/main/resources/bbm.mixins.json index f4072c6..97d8b7d 100644 --- a/src/main/resources/bbm.mixins.json +++ b/src/main/resources/bbm.mixins.json @@ -4,12 +4,13 @@ "package": "dev.nyon.bbm.asm", "compatibilityLevel": "JAVA_17", "mixins": [ - "BoatMixin" + "BoatMixin", + "EntityMixin" ], "client": [ "MinecraftMixin" ], "injectors": { "defaultRequire": 1 - } + } }