mirror of
https://github.com/CCBlueX/LiquidBounce.git
synced 2025-09-06 09:46:38 +00:00
fix(AutoShoot): linear prediction (#6762)
This commit is contained in:
@@ -211,20 +211,23 @@ object ModuleAutoShoot : ClientModule("AutoShoot", Category.COMBAT) {
|
||||
}
|
||||
|
||||
private fun findRotation(target: LivingEntity, gravityType: GravityType): Rotation? {
|
||||
val eyes = player.eyePos
|
||||
// todo: calculate time until projectile reaches target
|
||||
val pointOnHitbox = pointTracker.findPoint(eyes, target, 1)
|
||||
|
||||
return when (gravityType) {
|
||||
GravityType.AUTO -> {
|
||||
// Should not happen, we convert [gravityType] to LINEAR or PROJECTILE before.
|
||||
return null
|
||||
}
|
||||
GravityType.LINEAR -> Rotation.lookingAt(pointOnHitbox.pos, eyes)
|
||||
GravityType.LINEAR -> {
|
||||
// On linear we likely don't need to care about gravity,
|
||||
// but instead aim exactly at the hitbox of the target.
|
||||
val eyes = player.eyePos
|
||||
val point = pointTracker.findPoint(eyes, target, 1)
|
||||
Rotation.lookingAt(point.pos, eyes)
|
||||
}
|
||||
// Determines the required yaw and pitch angles to hit a target with a projectile,
|
||||
// considering gravity's effect on the projectile's motion.
|
||||
GravityType.PROJECTILE -> {
|
||||
SituationalProjectileAngleCalculator.calculateAngleForEntity(TrajectoryInfo.GENERIC, target)
|
||||
SituationalProjectileAngleCalculator.calculateAngleForEntity(TrajectoryInfo.GENERIC,
|
||||
target)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -209,7 +209,7 @@ object ModuleKillAura : ClientModule("KillAura", Category.COMBAT) {
|
||||
}
|
||||
|
||||
val rotation = (if (rotations.rotationTiming == ON_TICK) {
|
||||
findRotation(target, range.toDouble(), 0)?.rotation
|
||||
findRotation(target, range.toDouble())?.rotation
|
||||
} else {
|
||||
null
|
||||
} ?: RotationManager.currentRotation ?: player.rotation).normalize()
|
||||
@@ -325,15 +325,11 @@ object ModuleKillAura : ClientModule("KillAura", Category.COMBAT) {
|
||||
val squaredMaxRange = maximumRange.pow(2)
|
||||
val squaredNormalRange = range.pow(2)
|
||||
|
||||
// Calculate ticks until next click
|
||||
val ticksUntilClick = clickScheduler.ticksUntilClick
|
||||
debugParameter("Ticks Until Click") { ticksUntilClick }
|
||||
|
||||
// Find suitable target
|
||||
val target = targetTracker.targets()
|
||||
.filter { entity -> entity.squaredBoxedDistanceTo(player) <= squaredMaxRange }
|
||||
.sortedBy { entity -> if (entity.squaredBoxedDistanceTo(player) <= squaredNormalRange) 0 else 1 }
|
||||
.firstOrNull { entity -> processTarget(entity, maximumRange, ticksUntilClick) }
|
||||
.firstOrNull { entity -> processTarget(entity, maximumRange) }
|
||||
|
||||
if (target != null) {
|
||||
targetTracker.target = target
|
||||
@@ -356,10 +352,9 @@ object ModuleKillAura : ClientModule("KillAura", Category.COMBAT) {
|
||||
@Suppress("ReturnCount")
|
||||
private fun processTarget(
|
||||
entity: LivingEntity,
|
||||
range: Float,
|
||||
ticks: Int
|
||||
range: Float
|
||||
): Boolean {
|
||||
val (rotation, _) = findRotation(entity, range.toDouble(), ticks) ?: return false
|
||||
val (rotation, _) = findRotation(entity, range.toDouble()) ?: return false
|
||||
val ticks = rotations.calculateTicks(rotation)
|
||||
debugParameter("Rotation Ticks") { ticks }
|
||||
|
||||
@@ -405,9 +400,9 @@ object ModuleKillAura : ClientModule("KillAura", Category.COMBAT) {
|
||||
*
|
||||
* @return The best spot to attack the entity
|
||||
*/
|
||||
private fun findRotation(entity: LivingEntity, range: Double, ticks: Int): RotationWithVector? {
|
||||
private fun findRotation(entity: LivingEntity, range: Double): RotationWithVector? {
|
||||
val eyes = player.eyePos
|
||||
val point = pointTracker.findPoint(eyes, entity, ticks)
|
||||
val point = pointTracker.findPoint(eyes, entity)
|
||||
|
||||
val pointPos = point.pos
|
||||
|
||||
|
@@ -45,8 +45,6 @@ class PointTracker(val parent: EventListener) : Configurable("AimPoint"), EventL
|
||||
private val predicateBoxParts by multiEnumChoice<ExemptBoxPart>("ExemptBoxParts")
|
||||
private val predicateBestHitVector = tree(ExemptBestHitVector(this))
|
||||
|
||||
private val prediction by boolean("Prediction", false)
|
||||
|
||||
/**
|
||||
* This introduces a layer of randomness to the point tracker. A gaussian distribution is being used to
|
||||
* calculate the offset.
|
||||
@@ -71,14 +69,10 @@ class PointTracker(val parent: EventListener) : Configurable("AimPoint"), EventL
|
||||
*
|
||||
* @param entity The entity we want to track.
|
||||
*/
|
||||
fun findPoint(eyes: Vec3d, entity: LivingEntity, ticks: Int): PointInsideBox {
|
||||
fun findPoint(eyes: Vec3d, entity: LivingEntity, ticks: Int = 0): PointInsideBox {
|
||||
// Predict target position
|
||||
val targetPos = if (prediction) {
|
||||
PositionExtrapolation.getBestForEntity(entity)
|
||||
.getPositionInTicks(ticks.toDouble())
|
||||
} else {
|
||||
entity.pos
|
||||
}
|
||||
val targetPos = PositionExtrapolation.getBestForEntity(entity)
|
||||
.getPositionInTicks(ticks.toDouble())
|
||||
|
||||
// Project points onto box
|
||||
val box = entity.getBoundingBoxAt(targetPos)
|
||||
|
@@ -6,6 +6,7 @@ import net.ccbluex.liquidbounce.utils.math.times
|
||||
import net.minecraft.entity.LivingEntity
|
||||
import net.minecraft.entity.player.PlayerEntity
|
||||
import net.minecraft.util.math.Vec3d
|
||||
import kotlin.math.max
|
||||
import kotlin.math.round
|
||||
|
||||
/**
|
||||
@@ -50,7 +51,7 @@ class PlayerSimulationExtrapolation(private val simulation: SimulatedPlayerCache
|
||||
constructor(player: PlayerEntity) : this(PlayerSimulationCache.getSimulationForOtherPlayers(player))
|
||||
|
||||
override fun getPositionInTicks(ticks: Double): Vec3d {
|
||||
val ticks = round(ticks.coerceAtMost(30.0)).toInt()
|
||||
val ticks = max(0, round(ticks.coerceAtMost(30.0)).toInt())
|
||||
if (ticks == 0) {
|
||||
return this.simulation.simulatedPlayer.pos
|
||||
}
|
||||
|
Reference in New Issue
Block a user