Пример #1
0
def iou_pymesh(mesh_src, mesh_pred, dim=FLAGS.dim):
    try:
        mesh1 = pymesh.load_mesh(mesh_src)
        grid1 = pymesh.VoxelGrid(2. / dim)
        grid1.insert_mesh(mesh1)
        grid1.create_grid()

        ind1 = ((grid1.mesh.vertices + 1.1) / 2.4 * dim).astype(np.int)
        v1 = np.zeros([dim, dim, dim])
        v1[ind1[:, 0], ind1[:, 1], ind1[:, 2]] = 1

        mesh2 = pymesh.load_mesh(mesh_pred)
        grid2 = pymesh.VoxelGrid(2. / dim)
        grid2.insert_mesh(mesh2)
        grid2.create_grid()

        ind2 = ((grid2.mesh.vertices + 1.1) / 2.4 * dim).astype(np.int)
        v2 = np.zeros([dim, dim, dim])
        v2[ind2[:, 0], ind2[:, 1], ind2[:, 2]] = 1

        intersection = np.sum(np.logical_and(v1, v2))
        union = np.sum(np.logical_or(v1, v2))
        return [float(intersection) / union, mesh_pred]
    except:
        print("error mesh {} / {}".format(mesh_src, mesh_pred))
Пример #2
0
def iou_pymesh(mesh1, mesh2, dim=110):
    # mesh1 = (vertices1, triangles1)
    # mesh2 = (vertices2, triangles2)

    mesh1 = pymesh.form_mesh(mesh1[0], mesh1[1])
    grid1 = pymesh.VoxelGrid(2. / dim)
    grid1.insert_mesh(mesh1)
    grid1.create_grid()

    ind1 = ((grid1.mesh.vertices + 1.1) / 2.4 * dim).astype(np.int)
    v1 = np.zeros([dim, dim, dim])
    v1[ind1[:, 0], ind1[:, 1], ind1[:, 2]] = 1

    mesh2 = pymesh.form_mesh(mesh2[0], mesh2[1])
    grid2 = pymesh.VoxelGrid(2. / dim)
    grid2.insert_mesh(mesh2)
    grid2.create_grid()

    ind2 = ((grid2.mesh.vertices + 1.1) / 2.4 * dim).astype(np.int)
    v2 = np.zeros([dim, dim, dim])
    v2[ind2[:, 0], ind2[:, 1], ind2[:, 2]] = 1

    intersection = np.sum(np.logical_and(v1, v2))
    union = np.sum(np.logical_or(v1, v2))
    return float(intersection) / union
def main():
    args = parse_args()
    mesh = pymesh.load_mesh(args.input_mesh)
    grid = pymesh.VoxelGrid(args.cell_size, mesh.dim)
    grid.insert_mesh(mesh)
    out_mesh = grid.mesh
    pymesh.save_mesh(args.output_mesh, out_mesh)
Пример #4
0
def voxelize_mesh():
    mesh = load_mesh("models/cube.obj")
    grid = pymesh.VoxelGrid(0.05, mesh.dim)
    grid.insert_mesh(mesh)
    grid.create_grid()
    out_mesh = grid.mesh
    centers = np.mean(out_mesh.vertices[out_mesh.elements], axis=1)
    np.save("models/voxels.npy", centers)
    visualize_cloud(centers)
Пример #5
0
def main():
    args = parse_args()
    mesh = pymesh.load_mesh(args.input_mesh)
    grid = pymesh.VoxelGrid(args.cell_size, mesh.dim)
    grid.insert_mesh(mesh)
    grid.create_grid()
    grid.dilate(args.dilate)
    grid.erode(args.erode)
    out_mesh = grid.mesh
    pymesh.save_mesh(args.output_mesh, out_mesh)
def process_obj(obj_file, dir_in, dir_out, grid_size, max_faces, make_convex=False, fit_cylinder=False, quality='low'):
    mesh_path = join(dir_in, obj_file)
    print('---------------------------------------------------------------------------')
    print('Processing: ' + obj_file)
    print('---------------------------------------------------------------------------')
    # load the mesh
    print('Loading mesh...')
    mesh = pymesh.load_mesh(mesh_path)
    print('Mesh verts: ' + str(mesh.vertices.shape))
    print('Mesh faces: ' + str(mesh.faces.shape))
    # filter out those that have too many faces
    if (mesh.faces.shape[0] > max_faces):
        print('Over max faces...continuing to next shape!')
        return
    # cleanup
    surf_mesh = mesh
    if make_convex:
        # first tet to get just outer surface
        print('Tetrahedralizing mesh...')
        tetgen = pymesh.tetgen()
        tetgen.points = mesh.vertices; # Input points
        tetgen.triangles = np.empty(0)
        tetgen.verbosity = 0
        tetgen.run(); # Execute tetgen
        surf_mesh = tetgen.mesh
    elif fit_cylinder:
        # same top and bottom radius
        # want to center around origin
        # first find radius (max of all x and z)
        # print (mesh.bbox)
        # print(mesh.bbox[0][0])
        cyl_rad = max([abs(mesh.bbox[0][0]), abs(mesh.bbox[1][0]), abs(mesh.bbox[0][2]), abs(mesh.bbox[1][2])])
        # find height max y - min y
        cyl_half_height = (mesh.bbox[1][1] - mesh.bbox[0][1]) / 2.0
        surf_mesh = pymesh.generate_cylinder(np.array([0, -cyl_half_height, 0]), np.array([0, cyl_half_height, 0]), cyl_rad, cyl_rad)
    # print('Tet verts: ' + str(tet_mesh.vertices.shape))
    # print('Tet faces: ' + str(tet_mesh.faces.shape))
    # remesh to improve vertex distribution for moment calculation
    # print('Remeshing...')
    # surf_mesh = tet_mesh #fix_mesh(tet_mesh, quality)
    print('Surface verts: ' + str(surf_mesh.vertices.shape))
    print('Surface faces: ' + str(surf_mesh.faces.shape))
    # voxelize to find volume
    print('Voxelizing...')
    grid = pymesh.VoxelGrid(grid_size, surf_mesh.dim)
    grid.insert_mesh(surf_mesh)
    grid.create_grid()
    vox_mesh = grid.mesh

    # save sim information
    # the number of voxels will be used for the volume (mass)
    num_voxels = vox_mesh.voxels.shape[0]
    vol = num_voxels * grid_size*grid_size*grid_size

    # move mesh to true COM based on voxelization (centroid of the center of all voxels)
    centroid = np.array([0., 0., 0.])
    for i in range(0, num_voxels):
        # find average position of all vertices defining voxel
        vox_pos = np.mean(vox_mesh.vertices[vox_mesh.voxels[i], :], axis=0)
        centroid += vox_pos
    centroid /= num_voxels

    print('Centroid: (%f, %f, %f)' % (centroid[0], centroid[1], centroid[2]))
    centroid_vox_mesh = pymesh.form_mesh(vox_mesh.vertices - np.reshape(centroid, (1, -1)), vox_mesh.faces, vox_mesh.voxels)
    centroid_surf_mesh = pymesh.form_mesh(surf_mesh.vertices - np.reshape(centroid, (1, -1)), surf_mesh.faces)

    # also calculate moment of inertia around principal axes for a DENSITY of 1 (mass = volume)
    inertia = np.array([0., 0., 0.])
    point_mass = vol / float(num_voxels)
    print('Point mass: %f' % (point_mass))
    for i in range(0, num_voxels):
        # find average position of all vertices defining voxel
        vox_pos = np.mean(centroid_vox_mesh.vertices[centroid_vox_mesh.voxels[i], :], axis=0)
        x2 = vox_pos[0]*vox_pos[0]
        y2 = vox_pos[1]*vox_pos[1]
        z2 = vox_pos[2]*vox_pos[2]
        # inertia += np.array([point_mass*(y2+z2),point_mass*(x2+z2),point_mass*(x2+y2)])
        inertia += np.array([x2*point_mass,y2*point_mass,z2*point_mass])

    print('Num voxels: ' + str(num_voxels))
    print('Volume: ' + str(vol))
    print('Moment of inertia: (%f, %f, %f)' % (inertia[0], inertia[1], inertia[2]))
    json_dict = {'num_vox' : num_voxels, 'vol' : vol, 'inertia' : inertia.tolist()}
    json_out_path = join(dir_out, obj_file.replace('.obj', '.json'))
    with open(json_out_path, 'w') as outfile:
        json_str = json.dump(json_dict, outfile)

    
    # save surface mesh
    mesh_out_path = join(dir_out, obj_file)
    pymesh.save_mesh(mesh_out_path, centroid_surf_mesh)

    # sample point cloud on surface mesh
    print('Sampling point cloud...')
    points_out_path = join(dir_out, obj_file.replace('.obj', '.pts'))
    subprocess.check_output(['./MeshSample', '-n1024', '-s3', mesh_out_path, points_out_path])