Getting the edge closest to the 3D cursor

I have these variables:
Active object: obj
edges list: list_edges
vertices list: list_vert
2d cursor position: mcursor
3d cursor position: raycast_hit
index of the the face under cursor: face_index (I can search only between the face’s edges)

It has to be in Object Mode. not in Edit Mode.

Using KDTree Utilities (mathutils.kdtree), I can get the closest vertices. But I don’t want the vertices, I want the edges.

I’m trying to understand how the Addon “Enhanced_3D_Cursor” can do this. But there are many lines of code and I don’t understand all.

Someone who experienced this know how to solve this problem?

I even thought about installing Rtree

hi

I did this script in order to select the closest edges to cursor… this work in Edit Mode but I hope you can modify this in order to work in object mode… that because I don’t understand input parameters… (my code is in spanish… sorry for that)

import bpyimport bmesh
import mathutils
import math


obj = bpy.context.object
me = obj.data
bm = bmesh.from_edit_mesh(me)


edges =  bm.edges
v1= bpy.context.scene.cursor_location #cursor_location


v2 = edges[0].verts[0]
print("start")
print("cursor_location: ", v1)


distancia1 = round(math.sqrt(math.fabs((((((v1[0])-(v2.co.x))**2))+((((v1[1])-(v2.co.y))**2))+((((v1[2])-(v2.co.z))**2))))),2)






vertice_cercano = None


print("first_distance: ", distancia1)


for edge in edges:
    for vertice in edge.verts:
        v2 = vertice
        distancia2 = round(math.sqrt(math.fabs((((((v1[0])-(v2.co.x))**2))+((((v1[1])-(v2.co.y))**2))+((((v1[2])-(v2.co.z))**2))))),2)


        print("intermediate distance: ", distancia2)
        if distancia2 <= distancia1:
            distancia1 = distancia2
            vertice_cercano = vertice




print("last_distance: ", distancia1)    
vertice_cercano.select = True


edges_conn = vertice_cercano.link_edges
#for edge in edges_conn:
    #edge.select = True


########ahora debo verificar la distancia mas cercana entre los vertices de los edges conectados



distancias = []
vertice_cercano_2 = None




for edge in edges_conn:
    for vertice in edge.verts:
        if vertice.co == vertice_cercano.co:
            print("Vertice mas cercano: ", vertice.index)
        else:
            v2 = vertice
            distancia4 = round(math.sqrt(math.fabs((((((v1[0])-(v2.co.x))**2))+((((v1[1])-(v2.co.y))**2))+((((v1[2])-(v2.co.z))**2))))),2)
            distancias.append(distancia4)
            
            
sorted(distancias)      


print("distancias: ", distancias)


distancia3 = distancias[0]      




print("first_distance_2_vertice_cercano: ", distancia3)


for edge in edges_conn:
    for vertice in edge.verts:
        if vertice.co == vertice_cercano.co:
            print("Vertice mas cercano: ", vertice.index)
        else:
            v2 = vertice
            distancia4 = round(math.sqrt(math.fabs((((((v1[0])-(v2.co.x))**2))+((((v1[1])-(v2.co.y))**2))+((((v1[2])-(v2.co.z))**2))))),2)


            print("intermediate distance 2 vertice cercano: ", distancia4)
            if distancia4 == distancia3:
                    distancia4= distancia3
                    segundo_vertice = vertice
                    segundo_vertice.select=True
                    
                    
            




print("last_distance_2_vertice_cercano: ", distancia3)    
    


    
bmesh.update_edit_mesh(me, True)



1 Like

Woow! I understand how it works :). I would like to avoid using the sqrt function, but I think it’s okay if I use the few edges of a face.
But I decided to work in the edit mode. So, the nearest edge can be obtained simply by “bpy.ops.view3d.select(extend = False, location = (mouse_coords))”.

Anyway, muchas gracias @YHOYO. This script will be useful in the future. :smiley:

hi… you can’t avoid the sqrt function because that function help you in order to obtain the distances… this is a basic math funtion :smiley: that I transcript to blender

It is okay too in mesh with many edges… for example…15.828:


I don’t understand your code: “bpy.ops.view3d.select(extend = False, location = (mouse_coords))”… do you have some example?

best regards

Diego

This site has an example of how to use this operator. The solution was given by CoDEmanX .

It is possible to know if the edge is close without using sqrt.
For example (to edges 2d):
edge = [vert0, vert1]
mouse_cursor = (mcursor[0], mcursor[1])


try:
    tg = (vert1[1]-vert0[1])/(vert1[0]-vert0[0])
    arctg = 1/tg
except:
    tg = 0
     arctg = 0

near_y = tg*(vert1[0]-mcursor[0])-(vert1[1]-mcursor[1])
near_x = arctg*(vert1[1]-mcursor[1])-(vert1[0]-mcursor[0])
if abs(near_x) < 25 or abs(near_y) < 25:
     return edge'


2.8 version?

I think is the same code because is bmesh. please check and tell me