From fd38e9511895aa81a808d5d024197865d239a76c Mon Sep 17 00:00:00 2001 From: ccetl <109693935+ccetl@users.noreply.github.com> Date: Sat, 4 Jan 2025 17:02:11 +0100 Subject: [PATCH] feat(ElytraFly): fixes and options (#5178) - moved common code to the module - instant start now works as expected - instant stop now works as expected - added a not in fluid option that will stop the flight when you're in fluids - static now stops all your movement when you don't press any movement key - added an option to completely remove durability usage while elytra flying --- .../movement/elytrafly/ModuleElytraFly.kt | 97 ++++++++++++++++-- .../movement/elytrafly/modes/ElytraFlyMode.kt | 32 ++++++ .../elytrafly/modes/ElytraFlyModeStatic.kt | 50 ++++++++++ .../elytrafly/modes/ElytraFlyModeVanilla.kt | 39 ++++++++ .../movement/elytrafly/modes/ElytraStatic.kt | 98 ------------------- .../movement/elytrafly/modes/ElytraVanilla.kt | 87 ---------------- 6 files changed, 208 insertions(+), 195 deletions(-) create mode 100644 src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyMode.kt create mode 100644 src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeStatic.kt create mode 100644 src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeVanilla.kt delete mode 100644 src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraStatic.kt delete mode 100644 src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraVanilla.kt diff --git a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/ModuleElytraFly.kt b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/ModuleElytraFly.kt index 75efcb8ae40..5f82d02b8ec 100644 --- a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/ModuleElytraFly.kt +++ b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/ModuleElytraFly.kt @@ -19,32 +19,109 @@ package net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly import net.ccbluex.liquidbounce.config.types.ToggleableConfigurable +import net.ccbluex.liquidbounce.event.tickHandler import net.ccbluex.liquidbounce.features.module.Category import net.ccbluex.liquidbounce.features.module.ClientModule -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes.ElytraStatic -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes.ElytraVanilla +import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes.ElytraFlyModeStatic +import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes.ElytraFlyModeVanilla +import net.ccbluex.liquidbounce.utils.entity.set +import net.minecraft.entity.EquipmentSlot +import net.minecraft.entity.effect.StatusEffects +import net.minecraft.item.Items +import net.minecraft.network.packet.c2s.play.ClientCommandC2SPacket /** * ElytraFly module * - * Makes you fly faster on Elytra. + * Makes elytra flying easier to control. */ - object ModuleElytraFly : ClientModule("ElytraFly", Category.MOVEMENT) { - val instant by boolean("Instant", true) - val instantStop by boolean("InstantStop", false) + private val instantStart by boolean("InstantStart", false) + private val instantStop by boolean("InstantStop", true) + object Speed : ToggleableConfigurable(this, "Speed", true) { val vertical by float("Vertical", 0.5f, 0.1f..2f) - val horizontal by float("Horizontal", 1f, 0.1f..2f) + val horizontal by float("Horizontal", 1f, 0.1f..5f) } init { tree(Speed) } - internal val modes = choices("Mode", ElytraVanilla, arrayOf( - ElytraStatic, - ElytraVanilla + private val notInFluid by boolean("NotInFluid", false) + + /** + * Spams elytra starting so that we switch between falling and gliding all the time and so don't use any elytra + * durability. + */ + private val durabilityExploit by boolean("DurabilityExploit", false) + + internal val modes = choices("Mode", ElytraFlyModeStatic, arrayOf( + ElytraFlyModeStatic, + ElytraFlyModeVanilla )) + + private var needsToRestart = false + + override fun enable() { + needsToRestart = false + } + + override fun disable() { + needsToRestart = true + } + + // checks and start logic + @Suppress("unused") + private val tickHandler = tickHandler { + if (shouldNotOperate()) { + needsToRestart = false + return@tickHandler + } + + val stop = mc.options.sneakKey.isPressed && instantStop && player.isOnGround || notInFluid && player.isInFluid + if (stop && player.isGliding) { + player.stopGliding() + network.sendPacket(ClientCommandC2SPacket(player, ClientCommandC2SPacket.Mode.START_FALL_FLYING)) + needsToRestart = false + return@tickHandler + } + + if (player.isGliding) { + // we're already flying, yay + if (Speed.enabled) { + modes.activeChoice.onTick() + } + + if (durabilityExploit) { + network.sendPacket(ClientCommandC2SPacket(player, ClientCommandC2SPacket.Mode.START_FALL_FLYING)) + needsToRestart = true + } + } else if (player.input.playerInput.jump && player.velocity.y != 0.0 && instantStart || needsToRestart) { + // If the player has an elytra and wants to fly instead + + // Jump must be off due to abnormal speed boosts + player.input.set(jump = false) + player.startGliding() + network.sendPacket(ClientCommandC2SPacket(player, ClientCommandC2SPacket.Mode.START_FALL_FLYING)) + } + } + + fun shouldNotOperate(): Boolean { + if (player.vehicle != null) { + return true + } + + if (player.abilities.creativeMode || player.hasStatusEffect(StatusEffects.LEVITATION)) { + return true + } + + // Find the chest slot + val chestSlot = player.getEquippedStack(EquipmentSlot.CHEST) + + // If the player doesn't have an elytra in the chest slot or is in fluids + return chestSlot.item != Items.ELYTRA || chestSlot.willBreakNextUse() + } + } diff --git a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyMode.kt b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyMode.kt new file mode 100644 index 00000000000..bd2cdfac38b --- /dev/null +++ b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyMode.kt @@ -0,0 +1,32 @@ +/* + * This file is part of LiquidBounce (https://github.com/CCBlueX/LiquidBounce) + * + * Copyright (c) 2015 - 2025 CCBlueX + * + * LiquidBounce is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * LiquidBounce is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with LiquidBounce. If not, see . + */ +package net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes + +import net.ccbluex.liquidbounce.config.types.Choice +import net.ccbluex.liquidbounce.config.types.ChoiceConfigurable +import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly + +abstract class ElytraFlyMode(name: String) : Choice(name) { + + override val parent: ChoiceConfigurable + get() = ModuleElytraFly.modes + + open fun onTick() {} + +} diff --git a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeStatic.kt b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeStatic.kt new file mode 100644 index 00000000000..c01a18d233e --- /dev/null +++ b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeStatic.kt @@ -0,0 +1,50 @@ +/* + * This file is part of LiquidBounce (https://github.com/CCBlueX/LiquidBounce) + * + * Copyright (c) 2015 - 2025 CCBlueX + * + * LiquidBounce is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * LiquidBounce is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with LiquidBounce. If not, see . + */ +package net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes + +import net.ccbluex.liquidbounce.event.events.PlayerMoveEvent +import net.ccbluex.liquidbounce.event.handler +import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly +import net.ccbluex.liquidbounce.utils.entity.moving +import net.ccbluex.liquidbounce.utils.entity.strafe + +internal object ElytraFlyModeStatic : ElytraFlyMode("Static") { + + @Suppress("unused") + private val networkMovementTickHandler = handler { event -> + if (ModuleElytraFly.shouldNotOperate() || !player.isGliding) { + return@handler + } + + val speed = ModuleElytraFly.Speed.enabled + if (speed && player.moving) { + event.movement.strafe(speed = ModuleElytraFly.Speed.horizontal.toDouble()) + } else { + event.movement.x = 0.0 + event.movement.z = 0.0 + } + + event.movement.y = when { + mc.options.jumpKey.isPressed && speed -> ModuleElytraFly.Speed.vertical.toDouble() + mc.options.sneakKey.isPressed && speed -> -ModuleElytraFly.Speed.vertical.toDouble() + else -> 0.0 + } + } + +} diff --git a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeVanilla.kt b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeVanilla.kt new file mode 100644 index 00000000000..84942de0a6a --- /dev/null +++ b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraFlyModeVanilla.kt @@ -0,0 +1,39 @@ +/* + * This file is part of LiquidBounce (https://github.com/CCBlueX/LiquidBounce) + * + * Copyright (c) 2015 - 2025 CCBlueX + * + * LiquidBounce is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * LiquidBounce is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with LiquidBounce. If not, see . + */ +package net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes + +import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly +import net.ccbluex.liquidbounce.utils.entity.moving +import net.ccbluex.liquidbounce.utils.entity.strafe + +internal object ElytraFlyModeVanilla : ElytraFlyMode("Vanilla") { + + override fun onTick() { + if (player.moving) { + player.strafe(speed = ModuleElytraFly.Speed.horizontal.toDouble()) + } + + player.velocity.y = when { + mc.options.jumpKey.isPressed -> ModuleElytraFly.Speed.vertical.toDouble() + mc.options.sneakKey.isPressed -> -ModuleElytraFly.Speed.vertical.toDouble() + else -> return + } + } + +} diff --git a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraStatic.kt b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraStatic.kt deleted file mode 100644 index 77bde910ac8..00000000000 --- a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraStatic.kt +++ /dev/null @@ -1,98 +0,0 @@ -/* - * This file is part of LiquidBounce (https://github.com/CCBlueX/LiquidBounce) - * - * Copyright (c) 2015 - 2025 CCBlueX - * - * LiquidBounce is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * LiquidBounce is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with LiquidBounce. If not, see . - */ -package net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes - -import net.ccbluex.liquidbounce.config.types.Choice -import net.ccbluex.liquidbounce.config.types.ChoiceConfigurable -import net.ccbluex.liquidbounce.event.tickHandler -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly.instant -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly.instantStop -import net.ccbluex.liquidbounce.utils.entity.moving -import net.ccbluex.liquidbounce.utils.entity.set -import net.ccbluex.liquidbounce.utils.entity.strafe -import net.minecraft.entity.EquipmentSlot -import net.minecraft.item.Items - -internal object ElytraStatic : Choice("Static") { - override val parent: ChoiceConfigurable<*> - get() = ModuleElytraFly.modes - - val repeatable = tickHandler { - - if (player.vehicle != null) { - return@tickHandler - } - - // Find the chest slot - val chestSlot = player.getEquippedStack(EquipmentSlot.CHEST) - - if (player.abilities.creativeMode) { - return@tickHandler - } - - // If the player doesn't have an elytra in the chest slot - if (chestSlot.item != Items.ELYTRA) { - return@tickHandler - } - - if (mc.options.sneakKey.isPressed && instantStop) { - player.stopGliding() - return@tickHandler - } - fun isAnyMovementKeyPressed(): Boolean { - return mc.options.forwardKey.isPressed || mc.options.backKey.isPressed - || mc.options.leftKey.isPressed || mc.options.rightKey.isPressed - || mc.options.jumpKey.isPressed || mc.options.sneakKey.isPressed - } - - // If player is flying - if (player.isGliding && isAnyMovementKeyPressed()) { - if (ModuleElytraFly.Speed.enabled) { - if (player.moving) { - player.strafe(speed = ModuleElytraFly.Speed.horizontal.toDouble()) - } - player.velocity.y = when { - mc.options.jumpKey.isPressed -> ModuleElytraFly.Speed.vertical.toDouble() - mc.options.sneakKey.isPressed -> -ModuleElytraFly.Speed.vertical.toDouble() - else -> return@tickHandler - } - } - // If the player has an elytra and wants to fly instead - } else if (chestSlot.item == Items.ELYTRA && player.input.playerInput.jump) { - if (instant) { - // Jump must be off due to abnormal speed boosts - player.input.set( - jump = false - ) - } - } - - // If no movement key is pressed, set speed to zero - if (!mc.options.forwardKey.isPressed && !mc.options.backKey.isPressed - && !mc.options.leftKey.isPressed && !mc.options.rightKey.isPressed) { - player.strafe(speed = 0.0) - player.velocity.y = 0.0 - } - } - - - - -} diff --git a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraVanilla.kt b/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraVanilla.kt deleted file mode 100644 index 4645b79da1b..00000000000 --- a/src/main/kotlin/net/ccbluex/liquidbounce/features/module/modules/movement/elytrafly/modes/ElytraVanilla.kt +++ /dev/null @@ -1,87 +0,0 @@ -/* - * This file is part of LiquidBounce (https://github.com/CCBlueX/LiquidBounce) - * - * Copyright (c) 2015 - 2025 CCBlueX - * - * LiquidBounce is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * LiquidBounce is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with LiquidBounce. If not, see . - */ -package net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.modes - -import net.ccbluex.liquidbounce.config.types.Choice -import net.ccbluex.liquidbounce.config.types.ChoiceConfigurable -import net.ccbluex.liquidbounce.event.tickHandler -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly.instant -import net.ccbluex.liquidbounce.features.module.modules.movement.elytrafly.ModuleElytraFly.instantStop -import net.ccbluex.liquidbounce.utils.entity.moving -import net.ccbluex.liquidbounce.utils.entity.set -import net.ccbluex.liquidbounce.utils.entity.strafe -import net.minecraft.entity.EquipmentSlot -import net.minecraft.item.Items - -internal object ElytraVanilla : Choice("Vanilla") { - - - override val parent: ChoiceConfigurable - get() = ModuleElytraFly.modes - - - val repeatable = tickHandler { - - if (player.vehicle != null) { - return@tickHandler - } - - // Find the chest slot - val chestSlot = player.getEquippedStack(EquipmentSlot.CHEST) - - if (player.abilities.creativeMode) { - return@tickHandler - } - - // If the player doesn't have an elytra in the chest slot - if (chestSlot.item != Items.ELYTRA) { - return@tickHandler - } - - if (mc.options.sneakKey.isPressed && instantStop) { - player.stopGliding() - return@tickHandler - } - - // If player is flying - if (player.isGliding) { - if (ModuleElytraFly.Speed.enabled) { - if (player.moving) { - player.strafe(speed = ModuleElytraFly.Speed.horizontal.toDouble()) - } - player.velocity.y = when { - mc.options.jumpKey.isPressed -> ModuleElytraFly.Speed.vertical.toDouble() - mc.options.sneakKey.isPressed -> -ModuleElytraFly.Speed.vertical.toDouble() - else -> return@tickHandler - } - } - // If the player has an elytra and wants to fly instead - } else if (chestSlot.item == Items.ELYTRA && player.input.playerInput.jump) { - if (instant) { - // Jump must be off due to abnormal speed boosts - player.input.set( - jump = false - ) - } - } - } - - -}