Search code examples
pythoniosswiftnumpyopen3d

How to use boolean mask arrays with NumPy using PythonKit in Swift


I have the following Python code:

print("Cluster connected triangles")

with o3d.utility.VerbosityContextManager(
        o3d.utility.VerbosityLevel.Debug) as cm:
    triangle_clusters, cluster_n_triangles, cluster_area = (
        mesh.cluster_connected_triangles())
triangle_clusters = np.asarray(triangle_clusters)
cluster_n_triangles = np.asarray(cluster_n_triangles)
cluster_area = np.asarray(cluster_area)

print("Get mesh with small clusters removed")

mesh_1 = copy.deepcopy(mesh)
largest_cluster_idx = cluster_n_triangles.argmax()
triangles_to_remove = triangle_clusters != largest_cluster_idx
mesh_1.remove_triangles_by_mask(triangles_to_remove)

which i am trying to adapt in Swift (PythonKit)

let np = Python.import("numpy")

let clusters = mesh.cluster_connected_triangles()
let triangle_clusters = np.asarray(clusters[0])
let cluster_n_triangles = np.asarray(clusters[1])
let cluster_area = np.asarray(clusters[2])
let largest_cluster_idx = cluster_n_triangles.argmax()
let triangles_to_remove = (triangle_clusters != largest_cluster_idx).  // ERROR: Ambiguous use of operator '!='
let largestCluster = mesh.remove_triangles_by_mask(triangles_to_remove)

can someone please help me convert this Python line : triangles_to_remove = triangle_clusters != largest_cluster_idx in Swift/PythonKit

in other words: what is the PythonKit/Swift syntax for creating boolean mask arrays?


Solution

  • The answer is to wrap the code in PythonObject:

    print("Clustering...")
    
    let clusters = mesh.cluster_connected_triangles()
    let triangle_clusters = np.asarray(clusters[0])
    let cluster_n_triangles = np.asarray(clusters[1])
    let cluster_area = np.asarray(clusters[2])
    let largest_cluster_idx = cluster_n_triangles.argmax()
    
    print("\(mesh) : with \(cluster_n_triangles.count) clusters.")
    print("Largest cluster : \(cluster_n_triangles[largest_cluster_idx]) triangles.")
    
    //THIS!
    let triangles_to_remove = PythonObject(triangle_clusters != largest_cluster_idx)
    
    mesh.remove_triangles_by_mask(triangles_to_remove)
    mesh.remove_unreferenced_vertices()
    
    print("Cluster Result: \(mesh)")