Skip to content

Commit b336acf

Browse files
authored
Improve TargetStrafe module. The previous implementation wasn't working (#323)
1 parent 12edc91 commit b336acf

4 files changed

Lines changed: 108 additions & 52 deletions

File tree

src/main/java/com/lambda/mixin/entity/ClientPlayerEntityMixin.java

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -90,9 +90,12 @@ private void onOpenEditSignScreen(SignBlockEntity sign, boolean front, CallbackI
9090

9191
@WrapOperation(method = "move", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/AbstractClientPlayerEntity;move(Lnet/minecraft/entity/MovementType;Lnet/minecraft/util/math/Vec3d;)V"))
9292
private void wrapMove(ClientPlayerEntity instance, MovementType movementType, Vec3d vec3d, Operation<Void> original) {
93-
EventFlow.post(new MovementEvent.Player.Pre(movementType, vec3d));
93+
MovementEvent.Player.Pre preEvent = new MovementEvent.Player.Pre(movementType, vec3d);
94+
EventFlow.post(preEvent);
95+
vec3d = preEvent.getMovement();
9496
original.call(instance, movementType, vec3d);
95-
EventFlow.post(new MovementEvent.Player.Post(movementType, vec3d));
97+
MovementEvent.Player.Post postEvent = new MovementEvent.Player.Post(movementType, vec3d);
98+
EventFlow.post(postEvent);
9699
}
97100

98101
@WrapOperation(method = "tickMovement", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/input/Input;tick()V"))

src/main/java/com/lambda/mixin/input/KeyBindingMixin.java

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,6 @@ boolean modifyIsPressed(boolean original) {
3636

3737
if (Sprint.INSTANCE.isEnabled()) return true;
3838
if (Speed.INSTANCE.isEnabled() && Speed.getMode() == Speed.Mode.GrimStrafe) return true;
39-
if (TargetStrafe.INSTANCE.isEnabled() && TargetStrafe.isActive()) return true;
4039
return original;
4140
}
4241
}

src/main/kotlin/com/lambda/event/events/MovementEvent.kt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,18 +37,18 @@ sealed class MovementEvent {
3737
/**
3838
* Event triggered before player movement.
3939
*
40-
* @property movementType The type of movement.
40+
* @property movement Type The type of movement.
4141
* @property movement The movement vector.
4242
*/
4343
data class Pre(
4444
override val movementType: MovementType,
45-
override val movement: Vec3d,
45+
override var movement: Vec3d,
4646
) : Player(), ICancellable by Cancellable()
4747

4848
/**
4949
* Event triggered after player movement.
5050
*
51-
* @property movementType The type of movement.
51+
* @property movement Type The type of movement.
5252
* @property movement The movement vector.
5353
*/
5454
data class Post(

src/main/kotlin/com/lambda/module/modules/movement/TargetStrafe.kt

Lines changed: 100 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -17,80 +17,134 @@
1717

1818
package com.lambda.module.modules.movement
1919

20-
import com.lambda.event.events.RotationEvent
20+
import com.lambda.config.ConfigEditor.forEachSetting
21+
import com.lambda.config.ConfigEditor.hideAllExcept
22+
import com.lambda.config.blocks.WorldLineSettings
23+
import com.lambda.config.withEdits
24+
import com.lambda.context.SafeContext
25+
import com.lambda.event.events.MovementEvent
2126
import com.lambda.event.events.TickEvent
2227
import com.lambda.event.listener.SafeListener.Companion.listen
28+
import com.lambda.graphics.mc.renderer.ImmediateRenderer.Companion.immediateRenderer
2329
import com.lambda.interaction.managers.rotating.Rotation.Companion.rotationTo
2430
import com.lambda.module.Module
2531
import com.lambda.module.modules.combat.KillAura
2632
import com.lambda.module.tag.ModuleTag
27-
import com.lambda.util.math.distSq
28-
import com.lambda.util.player.MovementUtils.update
29-
import kotlin.math.pow
33+
import net.minecraft.entity.effect.StatusEffects
34+
import net.minecraft.util.math.Vec3d
35+
import java.awt.Color
36+
import kotlin.math.cos
37+
import kotlin.math.sin
38+
import kotlin.math.sqrt
3039

3140
object TargetStrafe : Module(
3241
name = "TargetStrafe",
33-
description = "Automatically strafes around entities",
42+
description = "Strafes around a target in a circle. The default settings work great for old NCP.",
3443
tag = ModuleTag.MOVEMENT,
3544
) {
36-
private val targetDistance by setting("Strafe Distance", 1.0, 0.0..5.0, 0.1)
37-
private val jitterCompensation by setting("Jitter Compensation", 0.0, 0.0..1.0, 0.1)
38-
private val stabilize by setting("Stabilize", StabilizationMode.Normal)
39-
40-
enum class StabilizationMode {
41-
None,
42-
Weak,
43-
Normal,
44-
Strong
45-
}
45+
private val autoJump by setting("AutoJump", true)
46+
private val distanceSetting by setting("PreferredDistance", 1f, 0f..6f, 0.1f)
47+
private val maxDistance by setting("MaxDistance", 10f, 1f..32f, 0.5f)
48+
private val turnAmount by setting("TurnAmount", 5f, 1f..90f, 0.5f)
49+
private val hSpeed by setting("HSpeed", 0.2873f, 0.001f..10.0f, 0.0001f)
50+
51+
private val needsAura by setting("NeedsAura", true)
52+
private val antiStuck by setting("AntiStuck", true)
53+
54+
private val renderCircle by setting("RenderCircle", true)
55+
private val renderCircleColor by setting("RenderCircleColor", Color(255, 255, 255, 100)) { renderCircle }
56+
private val renderThickness by configBlock(WorldLineSettings(this))
57+
.withEdits {
58+
hideAllExcept(
59+
::distanceScaling,
60+
::worldWidthSetting,
61+
::screenWidthSetting
62+
)
63+
forEachSetting {
64+
visibility { old -> { old() && renderCircle } }
65+
}
66+
}
67+
68+
private var direction = 1
4669

47-
private var forwardDirection = 1.0
48-
private var strafeDirection = 1.0
70+
private var currentDistance = 0.0
71+
private var currentTargetVec: Vec3d? = null
4972

50-
@JvmStatic
51-
val isActive get() = isEnabled && KillAura.isEnabled && KillAura.target != null
73+
private var strafing = false
5274

5375
init {
5476
listen<TickEvent.Post> {
55-
if (player.horizontalCollision) strafeDirection *= -1
77+
if (strafing && autoJump && player.isOnGround) {
78+
player.jump()
79+
}
80+
}
81+
82+
listen<MovementEvent.Player.Pre> { event ->
83+
if (player.horizontalCollision && antiStuck) {
84+
switchDirection()
85+
}
86+
if (canStrafe()) {
87+
val rotations = KillAura.target?.let { it1 -> player.eyePos?.rotationTo(it1.pos) } ?: return@listen
88+
KillAura.target?.let { it1 -> doStrafeAtSpeed(event, rotations.yawF, it1.pos) }
89+
currentTargetVec = KillAura.target?.pos
5690

57-
if (KillAura.target == null) {
58-
forwardDirection = 1.0
59-
strafeDirection = 1.0
91+
strafing = true
92+
} else {
93+
strafing = false
6094
}
6195
}
6296

63-
listen<RotationEvent.StrafeInput> { event ->
64-
KillAura.target?.let { target ->
65-
event.strafeYaw = player.eyePos.rotationTo(target.boundingBox.center).yaw
97+
immediateRenderer("TargetStrafe immediate renderer") {
98+
if (strafing && renderCircle) {
99+
circleLine(
100+
currentTargetVec ?: return@immediateRenderer,
101+
distanceSetting.toDouble(),
102+
renderCircleColor,
103+
renderThickness.width,
104+
segments = 64
105+
)
106+
}
107+
}
108+
}
66109

67-
val distSq = player.pos distSq target.pos
68-
val keepRange = 0.5 * jitterCompensation
110+
private fun SafeContext.doStrafeAtSpeed(event: MovementEvent.Player.Pre, rotation: Float, target: Vec3d): Boolean {
111+
var playerSpeed = hSpeed
112+
var rotationYaw = rotation + (90f * direction)
69113

70-
forwardDirection = when {
71-
distSq > (targetDistance + keepRange).pow(2) -> 1.0
72-
distSq < (targetDistance - keepRange).pow(2) -> -1.0
73-
else -> forwardDirection
74-
}
75114

76-
// Premium code, do not touch it bites
77-
var shouldStabilize = when (stabilize) {
78-
StabilizationMode.None -> false
79-
StabilizationMode.Weak -> player.age % 4 == 0 // 1/4
80-
StabilizationMode.Normal -> player.age % 2 == 0 // 2/4
81-
StabilizationMode.Strong -> player.age % 4 != 0 // 3/4
82-
}
115+
val disX = player.pos.x - target.x
116+
val disZ = player.pos.z - target.z
83117

84-
shouldStabilize = shouldStabilize && distSq > (targetDistance + 0.5).pow(2)
118+
val distance = sqrt(disX * disX + disZ * disZ)
85119

86-
val strafe = if (shouldStabilize) 0.0 else strafeDirection
87-
event.input.update(forwardDirection, strafe, jump = true)
120+
if (distance < maxDistance) {
121+
if (distance > distanceSetting) {
122+
rotationYaw -= turnAmount * direction
123+
} else if (distance < distanceSetting) {
124+
rotationYaw += turnAmount * direction
88125
}
126+
} else {
127+
rotationYaw = rotation
89128
}
90129

91-
onEnable {
92-
forwardDirection = 1.0
93-
strafeDirection = 1.0
130+
currentDistance = distance
131+
132+
// speed
133+
val speed = player.getStatusEffect(StatusEffects.SPEED)
134+
if (speed != null) {
135+
136+
playerSpeed *= 1.0f + 0.2f * (speed.amplifier + 1)
94137
}
138+
139+
event.movement = Vec3d(playerSpeed * cos(Math.toRadians((rotationYaw + 90.0f).toDouble())), event.movement.y, playerSpeed * sin(Math.toRadians((rotationYaw + 90.0f).toDouble())))
140+
return false
141+
}
142+
143+
private fun canStrafe(): Boolean {
144+
return (KillAura.isEnabled || !needsAura) && KillAura.target != null
145+
}
146+
147+
private fun switchDirection() {
148+
direction = -direction
95149
}
96150
}

0 commit comments

Comments
 (0)