Exemple #1
0
def separate_surfaces(v, f, fl):
    """
    :param v vertices
    :param f faces
    :param fl face labels
    perturb the surfaces according to the face labels
    :return v_dict, f_dict
    """
    v_dict = {}
    f_dict_temp = {}
    f_dict = {}
    count_dict = {}
    for fidx, lb in enumerate(fl):
        if lb not in f_dict_temp:
            f_dict_temp[lb] = np.zeros_like(f)
            f_dict_temp[lb][0, :] = f[fidx, :].copy()
            count_dict[lb] = 1
        else:
            f_dict_temp[lb][count_dict[lb], :] = f[fidx, :].copy()
            count_dict[lb] += 1
    for lb in f_dict_temp:
        f_dict_temp[lb] = f_dict_temp[lb][0:count_dict[lb], :]
        v_dict[lb], f_dict[lb], _, _ = igl.remove_unreferenced(
            v, f_dict_temp[lb])
    return v_dict, f_dict
Exemple #2
0
 def test_remove_unreferenced(self):
     nv, nf, i, j = igl.remove_unreferenced(self.v1, self.f1)
     self.assertEqual(nv.shape[1], self.v1.shape[1])
     self.assertEqual(nf.shape[1], self.f1.shape[1])
     self.assertEqual(i.shape[0], self.v1.shape[0])
     self.assertEqual(nv.dtype, self.v1.dtype)
     self.assertTrue(nf.dtype == i.dtype == j.dtype == self.f1.dtype)
Exemple #3
0
def extract_patches(V, F, FL):
    '''
    return patch_dict {label_i: (V_i, F_i, I_i, J_i)}
    '''
    label_num = FL.max() + 1
    patch_idx_dict = {}
    for fidx, fl in enumerate(FL):
        if fl not in patch_idx_dict:
            patch_idx_dict[fl] = [fidx]
        else:
            patch_idx_dict[fl].append(fidx)
    patch_dict = {}
    for key in patch_idx_dict:
        F_key = F[patch_idx_dict[key]]
        V_key, F_key, I_key, J_key = igl.remove_unreferenced(V, F_key)
        patch_dict[key] = (V_key, F_key, I_key, J_key)
    return patch_dict
def main():

    parser = argparse.ArgumentParser()

    parser.add_argument('model_weights_path',
                        type=str,
                        help='path to the model checkpoint')
    parser.add_argument('input_path', type=str, help='path to the input')

    parser.add_argument('--disable_cuda',
                        action='store_true',
                        help='disable cuda')

    parser.add_argument('--sample_cloud',
                        type=int,
                        help='run on sampled points')

    parser.add_argument('--n_rounds',
                        type=int,
                        default=5,
                        help='number of rounds')
    parser.add_argument('--prob_thresh',
                        type=float,
                        default=.9,
                        help='threshold for final surface')

    parser.add_argument(
        '--output',
        type=str,
        help='path to save the resulting high prob mesh to. also disables viz')
    parser.add_argument('--output_trim_unused',
                        action='store_true',
                        help='trim unused vertices when outputting')

    # Parse arguments
    args = parser.parse_args()
    set_args_defaults(args)

    viz = not args.output
    args.polyscope = False

    # Initialize polyscope
    if viz:
        polyscope.init()

    # === Load the input

    if args.input_path.endswith(".npz"):
        record = np.load(args.input_path)
        verts = torch.tensor(record['vert_pos'],
                             dtype=args.dtype,
                             device=args.device)
        surf_samples = torch.tensor(record['surf_pos'],
                                    dtype=args.dtype,
                                    device=args.device)

        samples = verts.clone()
        faces = torch.zeros((0, 3), dtype=torch.int64, device=args.device)

        polyscope.register_point_cloud("surf samples", toNP(surf_samples))

    if args.input_path.endswith(".xyz"):
        raw_pts = np.loadtxt(args.input_path)
        verts = torch.tensor(raw_pts, dtype=args.dtype, device=args.device)

        samples = verts.clone()
        faces = torch.zeros((0, 3), dtype=torch.int64, device=args.device)

        polyscope.register_point_cloud("surf samples", toNP(verts))

    else:
        print("reading mesh")
        verts, faces = utils.read_mesh(args.input_path)
        print("  {} verts   {} faces".format(verts.shape[0], faces.shape[0]))
        verts = torch.tensor(verts, dtype=args.dtype, device=args.device)
        faces = torch.tensor(faces, dtype=torch.long, device=args.device)

        # verts = verts[::10,:]

        if args.sample_cloud:
            samples = mesh_utils.sample_points_on_surface(
                verts, faces, args.sample_cloud)
        else:
            samples = verts.clone()

    # === Load the model

    print("loading model weights")
    model = PointTriNet_Mesher()
    model.load_state_dict(torch.load(args.model_weights_path))

    model.eval()

    with torch.no_grad():

        # Sample lots of faces from the vertices
        print("predicting")
        candidate_triangles, candidate_probs = model.predict_mesh(
            samples.unsqueeze(0), n_rounds=args.n_rounds)
        candidate_triangles = candidate_triangles.squeeze(0)
        candidate_probs = candidate_probs.squeeze(0)
        print("done predicting")

        # Visualize
        high_prob = args.prob_thresh
        high_faces = candidate_triangles[candidate_probs > high_prob]
        closed_faces = mesh_utils.fill_holes_greedy(high_faces)

        if viz:
            polyscope.register_point_cloud("input points", toNP(samples))

            spmesh = polyscope.register_surface_mesh("all faces",
                                                     toNP(samples),
                                                     toNP(candidate_triangles),
                                                     enabled=False)
            spmesh.add_scalar_quantity("probs",
                                       toNP(candidate_probs),
                                       defined_on='faces')

            spmesh = polyscope.register_surface_mesh(
                "high prob mesh " + str(high_prob), toNP(samples),
                toNP(high_faces))
            spmesh.add_scalar_quantity(
                "probs",
                toNP(candidate_probs[candidate_probs > high_prob]),
                defined_on='faces')

            spmesh = polyscope.register_surface_mesh("hole-closed mesh " +
                                                     str(high_prob),
                                                     toNP(samples),
                                                     toNP(closed_faces),
                                                     enabled=False)

            polyscope.show()

        # Save output
        if args.output:

            high_prob = args.prob_thresh
            out_verts = toNP(samples)
            out_faces = toNP(high_faces)
            out_faces_closed = toNP(closed_faces)

            if args.output_trim_unused:
                out_verts, out_faces, _, _ = igl.remove_unreferenced(
                    out_verts, out_faces)

            igl.write_triangle_mesh(args.output + "_mesh.ply", out_verts,
                                    out_faces)
            write_ply_points(args.output + "_samples.ply", toNP(samples))

            igl.write_triangle_mesh(args.output + "_pred_mesh.ply", out_verts,
                                    out_faces)
            igl.write_triangle_mesh(args.output + "_pred_mesh_closed.ply",
                                    out_verts, out_faces_closed)
            write_ply_points(args.output + "_samples.ply", toNP(samples))