1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
|
package at.hannibal2.skyhanni.utils
import at.hannibal2.skyhanni.utils.LorenzUtils.round
import net.minecraft.entity.Entity
import net.minecraft.network.play.server.S2APacketParticles
import net.minecraft.util.AxisAlignedBB
import net.minecraft.util.BlockPos
import net.minecraft.util.Rotations
import net.minecraft.util.Vec3
import kotlin.math.*
data class LorenzVec(
val x: Double,
val y: Double,
val z: Double,
) {
constructor(x: Int, y: Int, z: Int) : this(x.toDouble(), y.toDouble(), z.toDouble())
constructor(x: Float, y: Float, z: Float) : this(x.toDouble(), y.toDouble(), z.toDouble())
fun toBlocPos(): BlockPos = BlockPos(x, y, z)
fun toVec3(): Vec3 = Vec3(x, y, z)
fun distanceIgnoreY(other: LorenzVec): Double = distanceIgnoreYSq(other).pow(0.5)
fun distance(other: LorenzVec): Double = distanceSq(other).pow(0.5)
fun distanceSq(x: Double, y: Double, z: Double): Double = distanceSq(LorenzVec(x, y, z))
fun distance(x: Double, y: Double, z: Double): Double = distance(LorenzVec(x, y, z))
fun distanceSq(other: LorenzVec): Double {
val dx = (other.x - x)
val dy = (other.y - y)
val dz = (other.z - z)
return (dx * dx + dy * dy + dz * dz)
}
fun distanceIgnoreYSq(other: LorenzVec): Double {
val dx = (other.x - x)
val dz = (other.z - z)
return (dx * dx + dz * dz)
}
fun add(x: Double, y: Double, z: Double): LorenzVec = LorenzVec(this.x + x, this.y + y, this.z + z)
fun add(x: Int, y: Int, z: Int): LorenzVec = LorenzVec(this.x + x, this.y + y, this.z + z)
override fun toString(): String {
return "LorenzVec{" +
"x=" + x +
", y=" + y +
", z=" + z +
'}'
}
fun multiply(d: Double): LorenzVec = LorenzVec(x multiplyZeroSave d, y multiplyZeroSave d, z multiplyZeroSave d)
fun multiply(d: Int): LorenzVec =
LorenzVec(x multiplyZeroSave d.toDouble(), y multiplyZeroSave d.toDouble(), z multiplyZeroSave d.toDouble())
fun add(other: LorenzVec) = LorenzVec(x + other.x, y + other.y, z + other.z)
fun subtract(other: LorenzVec) = LorenzVec(x - other.x, y - other.y, z - other.z)
fun normalize() = length().let { LorenzVec(x / it, y / it, z / it) }
fun printWithAccuracy(accuracy: Int): String {
val x = (round(x * accuracy) / accuracy)
val y = (round(y * accuracy) / accuracy)
val z = (round(z * accuracy) / accuracy)
return LorenzVec(x, y, z).toCleanString()
}
private fun toCleanString(): String {
return "$x $y $z"
}
fun length(): Double {
return sqrt(x * x + y * y + z * z)
}
fun isZero(): Boolean = x == 0.0 && y == 0.0 && z == 0.0
fun clone(): LorenzVec = LorenzVec(x, y, z)
fun toDoubleArray(): Array<Double> {
return arrayOf(x, y, z)
}
fun equalsIgnoreY(other: LorenzVec) = x == other.x && z == other.z
fun equals(other: LorenzVec) = x == other.x && y == other.y && z == other.z
fun round(decimals: Int) = LorenzVec(x.round(decimals), y.round(decimals), z.round(decimals))
fun roundLocationToBlock(): LorenzVec {
val x = (x - .499999).round(0)
val y = (y - .499999).round(0)
val z = (z - .499999).round(0)
return LorenzVec(x, y, z)
}
fun slope(other: LorenzVec, factor: Double) = add(other.subtract(this).scale(factor))
fun roundLocation(): LorenzVec {
val x = if (this.x < 0) x.toInt().toDouble() - 1 else x.toInt().toDouble()
val y = y.toInt().toDouble() - 1
val z = if (this.z < 0) z.toInt().toDouble() - 1 else z.toInt().toDouble()
return LorenzVec(x, y, z)
}
fun boundingToOffset(offX: Double, offY: Double, offZ: Double) = AxisAlignedBB(x, y, z, x + offX, y + offY, z + offZ)
fun scale(scalar: Double): LorenzVec {
return LorenzVec(scalar * x, scalar * y, scalar * z)
}
companion object {
fun getFromYawPitch(yaw: Double, pitch: Double): LorenzVec {
val yaw: Double = (yaw + 90) * Math.PI / 180
val pitch: Double = (pitch + 90) * Math.PI / 180
val x = sin(pitch) * cos(yaw)
val y = sin(pitch) * sin(yaw)
val z = cos(pitch)
return LorenzVec(x, z, y)
}
// only for migration purposes
fun decodeFromString(string: String): LorenzVec {
val (x, y, z) = string.split(":").map { it.toDouble() }
return LorenzVec(x, y, z)
}
fun getBlockBelowPlayer() = LocationUtils.playerLocation().roundLocationToBlock().add(0.0, -1.0, 0.0)
}
}
private infix fun Double.multiplyZeroSave(other: Double): Double {
val result = this * other
return if (result == -0.0) 0.0 else result
}
fun BlockPos.toLorenzVec(): LorenzVec = LorenzVec(x, y, z)
fun Entity.getLorenzVec(): LorenzVec = LorenzVec(posX, posY, posZ)
fun Vec3.toLorenzVec(): LorenzVec = LorenzVec(xCoord, yCoord, zCoord)
fun Rotations.toLorenzVec(): LorenzVec = LorenzVec(x, y, z)
fun S2APacketParticles.toLorenzVec() = LorenzVec(xCoordinate, yCoordinate, zCoordinate)
fun Array<Double>.toLorenzVec(): LorenzVec {
return LorenzVec(this[0], this[1], this[2])
}
|