Beispiel #1
0
def mesh_to_image(meshes: list,
                  reference_image: itk.Image = None) -> itk.Image:
    # Allow single mesh as input
    if type(meshes) != list:
        meshes = [meshes]

    mesh_type = type(meshes[0])
    pixel_type, dimension = itk.template(mesh_type)[1]
    image_type = itk.Image[pixel_type, dimension]

    mesh_to_image_filter_type = itk.TriangleMeshToBinaryImageFilter[mesh_type,
                                                                    image_type]
    images = list()

    if not reference_image:
        # Set bounds to largest region encompassing all meshes
        # Bounds format: [x_min x_max y_min y_max z_min z_max]
        bounds = meshes[0].GetBoundingBox().GetBounds()
        for mesh in meshes[1:]:
            mesh_bounds = mesh.GetBoundingBox().GetBounds()
            for dim in range(0, dimension):
                bounds[dim * 2] = min(bounds[dim * 2], mesh_bounds[dim * 2])
                bounds[(dim * 2) + 1] = max(bounds[(dim * 2) + 1],
                                            mesh_bounds[(dim * 2) + 1])

        # Calculate spacing, origin, and size with 5 pixel buffer around mesh
        spacing = ((bounds[1] - bounds[0]) / 90, (bounds[3] - bounds[2]) / 90,
                   (bounds[5] - bounds[4]) / 90)
        origin = (bounds[0] - 5 * spacing[0], bounds[2] - 5 * spacing[1],
                  bounds[4] - 5 * spacing[2])
        size = (100, 100, 100)
        direction = itk.Matrix[itk.D, dimension, dimension].GetIdentity()
    else:
        # Use given parameters
        origin = reference_image.GetOrigin()
        spacing = reference_image.GetSpacing()
        size = reference_image.GetLargestPossibleRegion().GetSize()
        direction = reference_image.GetDirection()

    # Generate image for each mesh
    for mesh in meshes:
        mesh_to_image_filter = mesh_to_image_filter_type.New(
            Input=mesh,
            Origin=origin,
            Spacing=spacing,
            Size=size,
            Direction=direction)
        mesh_to_image_filter.Update()

        distance = itk.signed_maurer_distance_map_image_filter(
            mesh_to_image_filter.GetOutput())
        images.append(distance)

    return images[0] if len(images) == 1 else images
Beispiel #2
0
    def _get_meta_dict(self, img: Image) -> Dict:
        """
        Get all the meta data of the image and convert to dict type.

        Args:
            img: a ITK image object loaded from a image file.

        """
        img_meta_dict = img.GetMetaDataDictionary()
        meta_dict = dict()
        for key in img_meta_dict.GetKeys():
            # ignore deprecated, legacy members that cause issues
            if key.startswith("ITK_original_"):
                continue
            meta_dict[key] = img_meta_dict[key]
        meta_dict["origin"] = np.asarray(img.GetOrigin())
        meta_dict["spacing"] = np.asarray(img.GetSpacing())
        meta_dict["direction"] = itk.array_from_matrix(img.GetDirection())
        return meta_dict
Beispiel #3
0
    def _get_affine(self, img: Image) -> np.ndarray:
        """
        Get or construct the affine matrix of the image, it can be used to correct
        spacing, orientation or execute spatial transforms.
        Construct Affine matrix based on direction, spacing, origin information.
        Refer to: https://github.com/RSIP-Vision/medio

        Args:
            img: a ITK image object loaded from a image file.

        """
        direction = itk.array_from_matrix(img.GetDirection())
        spacing = np.asarray(img.GetSpacing())
        origin = np.asarray(img.GetOrigin())

        direction = np.asarray(direction)
        affine = np.eye(direction.shape[0] + 1)
        affine[(slice(-1), slice(-1))] = direction @ np.diag(spacing)
        affine[(slice(-1), -1)] = origin
        return affine