Search code examples
pythonmayamelpymel

Find closest point on mesh in specific axis (maya)


Let's say I have one locator above a polyPlane. What I want to do is a lookup or trace from the locator in negative or positive y until it hits the polyPlane and return the position of the closest point/vertex/uv/

I imagine this have been done one million times but the only examples I have found works by locating the closest point based on all axis which in my case is close to useless.

I would appreciate any help I could get!

Edit: Added image of the difference between the first suggested solution and what I want to achieve

enter image description here


Solution

  • What we can do is use OpenMaya (Maya's API) to loop over the faceVerts gathered in an array, check to see which is shortest distance from the locator position compared to the current facevert, if it is shorter than the last shortest distance, save it as the closestVertex variable.

    import maya.OpenMaya as OpenMaya
    from pymel.core import *
    
    geo = PyNode('pSphere1')
    pos = PyNode('locator1').getRotatePivot(space='world')
    
    nodeDagPath = OpenMaya.MObject()
    try:
        selectionList = OpenMaya.MSelectionList()
        selectionList.add(geo.name())
        nodeDagPath = OpenMaya.MDagPath()
        selectionList.getDagPath(0, nodeDagPath)
    except:
        warning('OpenMaya.MDagPath() failed on %s' % geo.name())
    
    mfnMesh = OpenMaya.MFnMesh(nodeDagPath)
    
    pointA = OpenMaya.MPoint(pos.x, pos.y, pos.z)
    pointB = OpenMaya.MPoint()
    space = OpenMaya.MSpace.kWorld
    
    util = OpenMaya.MScriptUtil()
    util.createFromInt(0)
    idPointer = util.asIntPtr()
    
    mfnMesh.getClosestPoint(pointA, pointB, space, idPointer)  
    idx = OpenMaya.MScriptUtil(idPointer).asInt()
    
    faceVerts = [geo.vtx[i] for i in geo.f[idx].getVertices()]
    closestVertex = None
    minLength = None
    for v in faceVerts:
        thisLength = (pos - v.getPosition(space='world')).length()
        if minLength is None or thisLength < minLength:
            minLength = thisLength
            closestVertex = v
    select(closestVertex)
    

    This could probably be done with python without the API, but if you've got maya, you've got access to the API :)

    I hope this helps