Пример #1
0
def save_meshio(filename, mesh, file_format=None, **kwargs):
    """Save mesh to file using meshio.

    Parameters
    ----------
    filename : str
        Filename to save the mesh to.

    mesh : pyvista.DataSet
        Any PyVista mesh/spatial data type.

    file_format : str, optional
        File type for meshio to save.  For example ``'.bdf'``.  This
        is normally inferred from the extension but this can be
        overridden.

    **kwargs : dict, optional
        Additional keyword arguments.  See
        ``meshio.write_points_cells`` for more details.

    Examples
    --------
    Save a pyvista sphere to a Abaqus data file.

    >>> import pyvista
    >>> sphere = pyvista.Sphere()
    >>> pyvista.save_meshio('mymesh.inp', sphere)  # doctest:+SKIP

    """
    import meshio
    from meshio.vtk._vtk import vtk_to_meshio_type

    # Make sure relative paths will work
    filename = os.path.abspath(os.path.expanduser(str(filename)))

    # Cast to pyvista.UnstructuredGrid
    if not isinstance(mesh, pyvista.UnstructuredGrid):
        mesh = mesh.cast_to_unstructured_grid()

    # Copy useful arrays to avoid repeated calls to properties
    vtk_offset = mesh.offset
    vtk_cells = mesh.cells
    vtk_cell_type = mesh.celltypes

    # Check that meshio supports all cell types in input mesh
    pixel_voxel = {8, 11}       # Handle pixels and voxels
    for cell_type in np.unique(vtk_cell_type):
        if cell_type not in vtk_to_meshio_type.keys() and cell_type not in pixel_voxel:
            raise TypeError(f"meshio does not support VTK type {cell_type}.")

    # Get cells
    cells = []
    c = 0
    for offset, cell_type in zip(vtk_offset, vtk_cell_type):
        numnodes = vtk_cells[offset+c]
        if _vtk.VTK9:  # must offset by cell count
            cell = vtk_cells[offset+1+c:offset+1+c+numnodes]
            c += 1
        else:
            cell = vtk_cells[offset+1:offset+1+numnodes]
        cell = (
            cell if cell_type not in pixel_voxel
            else cell[[0, 1, 3, 2]] if cell_type == 8
            else cell[[0, 1, 3, 2, 4, 5, 7, 6]]
        )
        cell_type = cell_type if cell_type not in pixel_voxel else cell_type+1
        cell_type = (
            vtk_to_meshio_type[cell_type] if cell_type != 7
            else f"polygon{numnodes}"
        )

        if len(cells) > 0 and cells[-1][0] == cell_type:
            cells[-1][1].append(cell)
        else:
            cells.append((cell_type, [cell]))

    for k, c in enumerate(cells):
        cells[k] = (c[0], np.array(c[1]))

    # Get point data
    point_data = {k.replace(" ", "_"): v for k, v in mesh.point_data.items()}

    # Get cell data
    vtk_cell_data = mesh.cell_data
    n_cells = np.cumsum([len(c[1]) for c in cells[:-1]])
    cell_data = (
        {k.replace(" ", "_"): np.split(v, n_cells) for k, v in vtk_cell_data.items()}
        if vtk_cell_data
        else {}
    )

    # Save using meshio
    meshio.write_points_cells(
        filename=filename,
        points=np.array(mesh.points),
        cells=cells,
        point_data=point_data,
        cell_data=cell_data,
        file_format=file_format,
        **kwargs
    )
Пример #2
0
def save_meshio(filename, mesh, file_format=None, **kwargs):
    """Save mesh to file using meshio.

    Parameters
    ----------
    mesh : pyvista.Common
        Any PyVista mesh/spatial data type.
    file_format : str
        File type for meshio to save.

    """
    import meshio
    from meshio.vtk._vtk import vtk_to_meshio_type

    # Make sure relative paths will work
    filename = os.path.abspath(os.path.expanduser(str(filename)))

    # Cast to pyvista.UnstructuredGrid
    if not isinstance(mesh, pyvista.UnstructuredGrid):
        mesh = mesh.cast_to_unstructured_grid()

    # Copy useful arrays to avoid repeated calls to properties
    vtk_offset = mesh.offset
    vtk_cells = mesh.cells
    vtk_cell_type = mesh.celltypes

    # Check that meshio supports all cell types in input mesh
    pixel_voxel = {8, 11}  # Handle pixels and voxels
    for cell_type in np.unique(vtk_cell_type):
        if cell_type not in vtk_to_meshio_type.keys(
        ) and cell_type not in pixel_voxel:
            raise TypeError(
                "meshio does not support VTK type {}.".format(cell_type))

    # Get cells
    cells = []
    c = 0
    for offset, cell_type in zip(vtk_offset, vtk_cell_type):
        numnodes = vtk_cells[offset + c]
        if VTK9:  # must offset by cell count
            cell = vtk_cells[offset + 1 + c:offset + 1 + c + numnodes]
            c += 1
        else:
            cell = vtk_cells[offset + 1:offset + 1 + numnodes]
        cell = (cell if cell_type not in pixel_voxel else cell[[0, 1, 3, 2]]
                if cell_type == 8 else cell[[0, 1, 3, 2, 4, 5, 7, 6]])
        cell_type = cell_type if cell_type not in pixel_voxel else cell_type + 1
        cell_type = (vtk_to_meshio_type[cell_type]
                     if cell_type != 7 else "polygon{}".format(numnodes))

        if len(cells) > 0 and cells[-1][0] == cell_type:
            cells[-1][1].append(cell)
        else:
            cells.append((cell_type, [cell]))

    for k, c in enumerate(cells):
        cells[k] = (c[0], np.array(c[1]))

    # Get point data
    point_data = {k.replace(" ", "_"): v for k, v in mesh.point_arrays.items()}

    # Get cell data
    vtk_cell_data = mesh.cell_arrays
    n_cells = np.cumsum([len(c[1]) for c in cells[:-1]])
    cell_data = ({
        k.replace(" ", "_"): np.split(v, n_cells)
        for k, v in vtk_cell_data.items()
    } if vtk_cell_data else {})

    # Save using meshio
    meshio.write_points_cells(filename=filename,
                              points=np.array(mesh.points),
                              cells=cells,
                              point_data=point_data,
                              cell_data=cell_data,
                              file_format=file_format,
                              **kwargs)
Пример #3
0
def save_meshio(filename, mesh, file_format=None, **kwargs):
    """Save mesh to file using meshio.

    Parameters
    ----------
    mesh : pyvista.Common
        Any PyVista mesh/spatial data type.
    file_format : str
        File type for meshio to save.

    """
    import meshio
    from meshio.vtk._vtk import vtk_to_meshio_type

    # Make sure relative paths will work
    filename = os.path.abspath(os.path.expanduser(str(filename)))

    # Cast to pyvista.UnstructuredGrid
    if not isinstance(mesh, pyvista.UnstructuredGrid):
        mesh = mesh.cast_to_unstructured_grid()

    # Copy useful arrays to avoid repeated calls to properties
    vtk_offset = mesh.offset
    vtk_cells = mesh.cells
    vtk_cell_type = mesh.celltypes

    # Check that meshio supports all cell types in input mesh
    pixel_voxel = {8, 11}  # Handle pixels and voxels
    for cell_type in np.unique(vtk_cell_type):
        assert cell_type in vtk_to_meshio_type.keys(
        ) or cell_type in pixel_voxel, (
            "meshio does not support VTK type {}.".format(cell_type))

    # Get cells
    cells = {}
    mapper = {}  # For cell data
    for i, (offset, cell_type) in enumerate(zip(vtk_offset, vtk_cell_type)):
        numnodes = vtk_cells[offset]
        cell = vtk_cells[offset + 1:offset + 1 + numnodes]
        cell = (cell if cell_type not in pixel_voxel else cell[[0, 1, 3, 2]]
                if cell_type == 8 else cell[[0, 1, 3, 2, 4, 5, 7, 6]])
        cell_type = cell_type if cell_type not in pixel_voxel else cell_type + 1
        cell_type = (vtk_to_meshio_type[cell_type]
                     if cell_type != 7 else "polygon{}".format(numnodes))
        if cell_type not in cells.keys():
            cells[cell_type] = [cell]
            mapper[cell_type] = [i]
        else:
            cells[cell_type].append(cell)
            mapper[cell_type].append(i)
    cells = {k: np.vstack(v) for k, v in cells.items()}

    # Get point data
    point_data = {k.replace(" ", "_"): v for k, v in mesh.point_arrays.items()}

    # Get cell data
    vtk_cell_data = mesh.cell_arrays
    cell_data = {
        k: {kk.replace(" ", "_"): vv[v]
            for kk, vv in vtk_cell_data.items()}
        for k, v in mapper.items()
    } if vtk_cell_data else {}

    # Save using meshio
    meshio.write_points_cells(filename=filename,
                              points=np.array(mesh.points),
                              cells=cells,
                              point_data=point_data,
                              cell_data=cell_data,
                              file_format=file_format,
                              **kwargs)