Skip to content

Commit

Permalink
added select near look in Graph Editor
Browse files Browse the repository at this point in the history
Co-authored-by: nea <nea@nea.moe>
  • Loading branch information
hannibal002 and nea committed Sep 18, 2024
1 parent 7ae9220 commit 997bf1b
Show file tree
Hide file tree
Showing 4 changed files with 105 additions and 0 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,11 @@ public class GraphConfig {
@ConfigEditorKeybind(defaultKey = -98) // Middle Mouse
public int selectKey = -98;

@Expose
@ConfigOption(name = "Select near look", desc = "Select the node closest to where you are looking.")
@ConfigEditorKeybind(defaultKey = Keyboard.KEY_NONE)
public int selectRaycastKey = Keyboard.KEY_NONE;

@Expose
@ConfigOption(name = "Connect Key", desc = "Connect the nearest node with the active node. If the nodes are already connected removes the connection.")
@ConfigEditorKeybind(defaultKey = Keyboard.KEY_C)
Expand Down
24 changes: 24 additions & 0 deletions src/main/java/at/hannibal2/skyhanni/test/GraphEditor.kt
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ import at.hannibal2.skyhanni.utils.LorenzUtils
import at.hannibal2.skyhanni.utils.LorenzVec
import at.hannibal2.skyhanni.utils.NumberUtil.addSeparators
import at.hannibal2.skyhanni.utils.OSUtils
import at.hannibal2.skyhanni.utils.RaycastUtils
import at.hannibal2.skyhanni.utils.RenderUtils.draw3DLine_nea
import at.hannibal2.skyhanni.utils.RenderUtils.drawDynamicText
import at.hannibal2.skyhanni.utils.RenderUtils.drawWaypointFilled
Expand Down Expand Up @@ -127,6 +128,7 @@ object GraphEditor {
if (!inEditMode && !inTextMode) {
add("§ePlace: §6${KeyboardManager.getKeyName(config.placeKey)}")
add("§eSelect: §6${KeyboardManager.getKeyName(config.selectKey)}")
add("§eSelect (Look): §6${KeyboardManager.getKeyName(config.selectRaycastKey)}")
add("§eConnect: §6${KeyboardManager.getKeyName(config.connectKey)}")
add("§eTest: §6${KeyboardManager.getKeyName(config.dijkstraKey)}")
add("§eVision: §6${KeyboardManager.getKeyName(config.throughBlocksKey)}")
Expand Down Expand Up @@ -346,6 +348,28 @@ object GraphEditor {
closedNode
}
}
if (config.selectRaycastKey.isKeyClicked()) {
val playerRay = RaycastUtils.createPlayerLookDirectionRay()
var minimumDistance = Double.MAX_VALUE
var minimumNode: GraphingNode? = null
for (node in nodes) {
val nodeCenterPosition = node.position.add(0.5, 0.5, 0.5)
val distance = RaycastUtils.findDistanceToRay(playerRay, nodeCenterPosition)
if (distance > minimumDistance) {
continue
}
if (minimumDistance > 1.0) {
minimumNode = node
minimumDistance = distance
continue
}
if (minimumNode == null || minimumNode.position.distanceSqToPlayer() > node.position.distanceSqToPlayer()) {
minimumNode = node
minimumDistance = distance
}
}
activeNode = minimumNode
}
if (activeNode != closedNode && config.connectKey.isKeyClicked()) {
val edge = getEdgeIndex(activeNode, closedNode)
if (edge == null) {
Expand Down
3 changes: 3 additions & 0 deletions src/main/java/at/hannibal2/skyhanni/utils/LorenzVec.kt
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import net.minecraft.util.BlockPos
import net.minecraft.util.Rotations
import net.minecraft.util.Vec3
import kotlin.math.abs
import kotlin.math.absoluteValue
import kotlin.math.acos
import kotlin.math.cos
import kotlin.math.max
Expand Down Expand Up @@ -126,6 +127,8 @@ data class LorenzVec(
fun lengthSquared(): Double = x * x + y * y + z * z
fun length(): Double = sqrt(this.lengthSquared())

fun isNormalized(tolerance: Double = 0.01) = (lengthSquared() - 1.0).absoluteValue < tolerance

fun isZero(): Boolean = x == 0.0 && y == 0.0 && z == 0.0

fun clone(): LorenzVec = LorenzVec(x, y, z)
Expand Down
73 changes: 73 additions & 0 deletions src/main/java/at/hannibal2/skyhanni/utils/RaycastUtils.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
package at.hannibal2.skyhanni.utils

import net.minecraft.client.Minecraft

object RaycastUtils {

data class Ray(
val origin: LorenzVec,
val direction: LorenzVec,
) {
init {
require(direction.isNormalized())
}
}

data class Plane(
val origin: LorenzVec,
val normal: LorenzVec,
) {
init {
require(normal.isNormalized())
}
}

fun createPlayerLookDirectionRay(): Ray {
return Ray(
LocationUtils.playerEyeLocation(),
Minecraft.getMinecraft().thePlayer.lookVec.toLorenzVec()
)
}

/**
* Create a plane that contains [point] and is orthogonal to [ray].
*/
fun createOrthogonalPlaneToRayAtPoint(
ray: Ray,
point: LorenzVec,
): Plane {
return Plane(point, ray.direction)
}

/**
* Intersect a plane (of any orientation) with a ray. The ray and plane may not be parallel to each other.
*/
fun intersectPlaneWithRay(plane: Plane, ray: Ray): LorenzVec {
// require(plane.normal.dotProduct(ray.direction).absoluteValue != 0.0)
val intersectionPointDistanceAlongRay =
(plane.normal.dotProduct(plane.origin) - plane.normal.dotProduct(ray.origin)) / plane.normal.dotProduct(ray.direction)
return ray.origin + ray.direction.scale(intersectionPointDistanceAlongRay)
}

/**
* Finds the distance between the given ray and the point. If the point is behind the ray origin (according to the ray's direction),
* returns [Double.MAX_VALUE] instead.
*/
fun findDistanceToRay(ray: Ray, point: LorenzVec): Double {
val plane = createOrthogonalPlaneToRayAtPoint(ray, point)
val intersectionPoint = intersectPlaneWithRay(plane, ray)
if ((intersectionPoint - ray.origin).dotProduct(ray.direction) < 0) return Double.MAX_VALUE
return intersectionPoint.distance(point)
}

inline fun <T> createDistanceToRayEstimator(ray: Ray, crossinline position: (T) -> LorenzVec): (T) -> Double {
return {
findDistanceToRay(ray, position(it))
}
}

fun <T : Any> List<T>.findClosestPointToRay(ray: Ray, positionExtractor: (T) -> LorenzVec): T? {
return minByOrNull(createDistanceToRayEstimator(ray, positionExtractor))
}

}

0 comments on commit 997bf1b

Please sign in to comment.