From a65865f4175bf6ee0cce369cee44f7a812af112d Mon Sep 17 00:00:00 2001 From: Maarten van Heusden <50550545+mmvanheusden@users.noreply.github.com> Date: Mon, 26 May 2025 22:08:46 +0200 Subject: [PATCH 1/3] Initial LevitationTweaks implementation --- .../modules/movement/LevitationTweaks.kt | 158 ++++++++++++++++++ 1 file changed, 158 insertions(+) create mode 100644 common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt diff --git a/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt b/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt new file mode 100644 index 000000000..8b420a3b2 --- /dev/null +++ b/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt @@ -0,0 +1,158 @@ +/* + * Copyright 2025 Lambda + * + * This program 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. + * + * This program 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 this program. If not, see . + */ + +package com.lambda.module.modules.movement + +import com.lambda.context.SafeContext +import com.lambda.event.events.ClientEvent +import com.lambda.event.events.MovementEvent +import com.lambda.event.events.TickEvent +import com.lambda.event.listener.SafeListener.Companion.listen +import com.lambda.module.Module +import com.lambda.module.tag.ModuleTag +import com.lambda.util.Communication.info +import com.lambda.util.KeyboardUtils.isKeyPressed +import com.lambda.util.NamedEnum +import com.lambda.util.math.MathUtils.toInt +import com.lambda.util.player.MovementUtils.isInputting +import com.lambda.util.player.MovementUtils.motionY +import com.lambda.util.player.MovementUtils.setSpeed +import net.minecraft.entity.effect.StatusEffectInstance +import net.minecraft.entity.effect.StatusEffects.LEVITATION +import org.lwjgl.glfw.GLFW.GLFW_KEY_LEFT_CONTROL +import java.time.Duration +import java.time.LocalDateTime + +object LevitationTweaks : Module( + name = "LevitationTweaks", + description = "Abuse the levitation effect", + defaultTags = setOf(ModuleTag.MOVEMENT) +) { + private val mode by setting("Mode", Mode.UNCP) + + // REMOVE + private val restore by setting("Restore", true, description = "Restore levitation on module disable") { mode == Mode.REMOVE } + + // UNCP + private val constantUpFactor by setting( + "Idle Up Speed", unit = "%", description = "Permanent upwards motion", defaultValue = 2.0, range = 0.0..100.0 + ) { mode == Mode.UNCP} + private val control by setting("Control", true, ) { mode == Mode.UNCP} + private val strafeBoost by setting("Strafe Boost", true, ) { mode == Mode.UNCP && control } + private val strafeBoostSpeed by setting( + "Boost Speed", unit = "%", defaultValue = 100, range = 0..120 + ) { mode == Mode.UNCP && control && strafeBoost} + private val timer by setting( + "Timer", true + ) { mode == Mode.UNCP && control && strafeBoost} + private val timerBoost by setting("Timer Boost", 1.08, 1.0..1.2, 0.01) { mode == Mode.UNCP && control && timer} + + private val controlDownSpeed by setting( + "Control Down Speed", unit = "%", defaultValue = 100, range = 0..300 + ) { mode == Mode.UNCP && control} + private val controlUpSpeed by setting( + "Control Up Speed", unit = "%", defaultValue = 100, range = 0..140 + ) { mode == Mode.UNCP && control} + + + + private enum class Mode(override val displayName: String) : NamedEnum { + REMOVE("Remove"), UNCP("NCP New") + } + + private var capturedEffect: StatusEffectInstance? = null + private var wearOffTime: LocalDateTime? = null + private var canMove = false + + init { + // Checks if levitation is applied. + fun SafeContext.checkForLevitationEffect(): StatusEffectInstance? { + return player.activeStatusEffects.entries.firstOrNull { it.value.effectType == LEVITATION }?.value + } + + onDisable { + /* RESTORE EFFECT AFTER EARLY DISABLE */ + val now = LocalDateTime.now() + if (mode != Mode.UNCP && restore && capturedEffect != null && now.isBefore(wearOffTime)) { + // info("Reapplying effect: $capturedEffect") + val durationTicks = wearOffTime?.let { Duration.between(now, it).seconds.toInt() * 20 } ?: 0 + //TODO: refactor this ugly time difference calculation + val newEffect = StatusEffectInstance(LEVITATION, durationTicks, capturedEffect!!.amplifier) + info("Reapplied levitation for ${durationTicks / 20} seconds") + player.addStatusEffect(newEffect) + } + + canMove = false + capturedEffect = null // Reset on disable + } + + onEnable { + canMove = false + capturedEffect = null // Reset when enabled again + } + + + listen { + // Capture effect to apply magic on later + if (capturedEffect == null) { + capturedEffect = checkForLevitationEffect() + if (capturedEffect == null) return@listen // Still not available, wait for next tick + wearOffTime = LocalDateTime.now().plusSeconds(capturedEffect!!.duration.toLong() / 20) + } + + if (LocalDateTime.now().isAfter(wearOffTime)) { + info("Effect wore off.") + capturedEffect == null + disable() + } + + when (mode) { + Mode.REMOVE -> { + if (checkForLevitationEffect() != null) player.removeStatusEffect(LEVITATION) + } + Mode.UNCP -> { + if (checkForLevitationEffect() != null) canMove = true + } + } + } + + listen { event -> + info(event.toString()) + if (mode != Mode.UNCP || !canMove) return@listen + + player.motionY = when { + player.isSneaking && control -> { // BOOST DOWN +// TODO: find out how to initiate downwards movement without a flag +/* player.motionX *= 0.5 + player.motionZ *= 0.5*/ + -(0.4 * (controlDownSpeed / 100)) + } + player.input.jumping && control -> (0.12 * (controlUpSpeed / 100)) // BOOST UP + else -> 0.06 * (constantUpFactor / 100) // idle motion up + } + + if (isKeyPressed(GLFW_KEY_LEFT_CONTROL) && strafeBoost && control) {setSpeed(Speed.NCP_BASE_SPEED * isInputting.toInt() * (strafeBoostSpeed/100))} + } + + listen { + if (mode != Mode.UNCP) return@listen + if (!isKeyPressed(GLFW_KEY_LEFT_CONTROL) || !timer || !canMove || !strafeBoost) return@listen + it.speed = timerBoost + } + } + +} \ No newline at end of file From dfff0c98b1daebd4bf0651399aa73f1b7970e4bd Mon Sep 17 00:00:00 2001 From: Maarten van Heusden <50550545+mmvanheusden@users.noreply.github.com> Date: Tue, 27 May 2025 21:21:02 +0200 Subject: [PATCH 2/3] fix: comment out debug print --- .../com/lambda/module/modules/movement/LevitationTweaks.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt b/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt index 8b420a3b2..2b247622f 100644 --- a/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt +++ b/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt @@ -131,7 +131,7 @@ object LevitationTweaks : Module( } listen { event -> - info(event.toString()) +// info(event.toString()) if (mode != Mode.UNCP || !canMove) return@listen player.motionY = when { From cc534906eb109a6406db33fa6534edc3ef257951 Mon Sep 17 00:00:00 2001 From: Maarten van Heusden <50550545+mmvanheusden@users.noreply.github.com> Date: Fri, 30 May 2025 10:52:32 +0200 Subject: [PATCH 3/3] refactor: follow setting code style convention --- .../modules/movement/LevitationTweaks.kt | 29 +++++++------------ 1 file changed, 10 insertions(+), 19 deletions(-) diff --git a/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt b/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt index 2b247622f..d86af1d25 100644 --- a/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt +++ b/common/src/main/kotlin/com/lambda/module/modules/movement/LevitationTweaks.kt @@ -48,26 +48,17 @@ object LevitationTweaks : Module( private val restore by setting("Restore", true, description = "Restore levitation on module disable") { mode == Mode.REMOVE } // UNCP - private val constantUpFactor by setting( - "Idle Up Speed", unit = "%", description = "Permanent upwards motion", defaultValue = 2.0, range = 0.0..100.0 - ) { mode == Mode.UNCP} - private val control by setting("Control", true, ) { mode == Mode.UNCP} - private val strafeBoost by setting("Strafe Boost", true, ) { mode == Mode.UNCP && control } - private val strafeBoostSpeed by setting( - "Boost Speed", unit = "%", defaultValue = 100, range = 0..120 - ) { mode == Mode.UNCP && control && strafeBoost} - private val timer by setting( - "Timer", true - ) { mode == Mode.UNCP && control && strafeBoost} - private val timerBoost by setting("Timer Boost", 1.08, 1.0..1.2, 0.01) { mode == Mode.UNCP && control && timer} - - private val controlDownSpeed by setting( - "Control Down Speed", unit = "%", defaultValue = 100, range = 0..300 - ) { mode == Mode.UNCP && control} - private val controlUpSpeed by setting( - "Control Up Speed", unit = "%", defaultValue = 100, range = 0..140 - ) { mode == Mode.UNCP && control} + private val constantUpFactor by setting("Idle Up Speed", 2.0, 0.0..100.0, description = "Permanent upwards motion", unit = "%") { mode == Mode.UNCP } + private val control by setting("Control", true) { mode == Mode.UNCP } + private val controlDownSpeed by setting("Control Down Speed", 100, 0..300, unit = "%") { mode == Mode.UNCP && control } + private val controlUpSpeed by setting("Control Up Speed", 100, 0..140, unit = "%") { mode == Mode.UNCP && control } + + private val strafeBoost by setting("Strafe Boost", true) { mode == Mode.UNCP && control } + private val strafeBoostSpeed by setting("Boost Speed", 100, 0..120, unit = "%") { mode == Mode.UNCP && control && strafeBoost } + + private val timer by setting("Timer", true) { mode == Mode.UNCP && control && strafeBoost } + private val timerBoost by setting("Timer Boost", 1.08, 1.0..1.2, 0.01) { mode == Mode.UNCP && control && timer } private enum class Mode(override val displayName: String) : NamedEnum {