I/O for many mesh formats
—
Core classes for representing mesh geometry, topology, and associated data with methods for manipulation and data conversion.
Primary class representing an unstructured mesh with points, cells, and associated data arrays.
class Mesh:
"""
Central mesh representation with points, cells, and associated data.
Constructor:
Mesh(points, cells, point_data=None, cell_data=None, field_data=None,
point_sets=None, cell_sets=None, gmsh_periodic=None, info=None)
Parameters:
- points: ArrayLike - Array of vertex coordinates with shape (n_points, dim)
Typically 2D or 3D coordinates as numpy array
- cells: Dict[str, ArrayLike] | List[Tuple[str, ArrayLike] | CellBlock]
Cell connectivity data. Can be:
* Dictionary: {"triangle": triangles, "quad": quads}
* List of tuples: [("triangle", triangles), ("quad", quads)]
* List of CellBlock objects
- point_data: Dict[str, ArrayLike] | None - Point-associated data arrays
Keys are data names, values are arrays with shape (n_points,) or (n_points, n_components)
- cell_data: Dict[str, List[ArrayLike]] | None - Cell-associated data arrays
Keys are data names, values are lists of arrays (one per cell block)
- field_data: Dict[str, Any] | None - Global field data and metadata
- point_sets: Dict[str, ArrayLike] | None - Named collections of point indices
Used for boundary conditions, material definitions
- cell_sets: Dict[str, List[ArrayLike]] | None - Named collections of cell indices
Keys are set names, values are lists of arrays (one per cell block)
- gmsh_periodic: Any | None - GMSH-specific periodic boundary data
- info: Any | None - Additional mesh information and metadata
Attributes:
- points: np.ndarray - Vertex coordinates array
- cells: List[CellBlock] - List of cell blocks
- point_data: Dict[str, np.ndarray] - Point-associated data
- cell_data: Dict[str, List[np.ndarray]] - Cell-associated data
- field_data: Dict[str, Any] - Field data
- point_sets: Dict[str, np.ndarray] - Point sets
- cell_sets: Dict[str, List[np.ndarray]] - Cell sets
- gmsh_periodic: Any - GMSH periodic data
- info: Any - Additional information
"""
def write(self, path_or_buf, file_format=None, **kwargs):
"""
Write mesh to file or buffer.
Parameters:
- path_or_buf: str | Path | Buffer - Output destination
- file_format: str | None - Optional format specification
- **kwargs: dict - Format-specific options
Examples:
>>> mesh.write("output.vtk")
>>> mesh.write("mesh.stl", binary=True)
"""
def copy(self):
"""
Create deep copy of mesh object.
Returns:
- Mesh - Independent copy of the mesh
Examples:
>>> mesh_copy = mesh.copy()
>>> mesh_copy.points[0] = [999, 999, 999] # Won't affect original
"""
def get_cells_type(self, cell_type):
"""
Get all cells of specified type concatenated into single array.
Parameters:
- cell_type: str - Cell type identifier (e.g., "triangle", "quad", "tetra")
Returns:
- np.ndarray - Concatenated connectivity array for all cells of given type
Shape: (n_cells_of_type, nodes_per_cell)
Returns empty array if no cells of that type exist
Examples:
>>> triangles = mesh.get_cells_type("triangle")
>>> print(f"Triangle connectivity shape: {triangles.shape}")
"""
def get_cell_data(self, name, cell_type):
"""
Get cell data for specific cell type.
Parameters:
- name: str - Name of cell data array
- cell_type: str - Cell type to extract data for
Returns:
- np.ndarray - Concatenated data array for specified cell type
Examples:
>>> material_ids = mesh.get_cell_data("material", "tetra")
>>> temperatures = mesh.get_cell_data("temperature", "triangle")
"""
@property
def cells_dict(self):
"""
Dictionary view of cells organized by type.
Returns:
- Dict[str, np.ndarray] - Cell connectivity arrays keyed by cell type
All cells of same type are concatenated into single array
Examples:
>>> for cell_type, connectivity in mesh.cells_dict.items():
... print(f"{cell_type}: {connectivity.shape}")
"""
@property
def cell_data_dict(self):
"""
Dictionary view of cell data organized by name and type.
Returns:
- Dict[str, Dict[str, np.ndarray]] - Nested dictionary structure
Outer key: data name, Inner key: cell type, Value: data array
Examples:
>>> materials = mesh.cell_data_dict["material"]["tetra"]
>>> tri_temps = mesh.cell_data_dict["temperature"]["triangle"]
"""
@property
def cell_sets_dict(self):
"""
Dictionary view of cell sets organized by set name and cell type.
Returns:
- Dict[str, Dict[str, np.ndarray]] - Nested dictionary structure
Outer key: set name, Inner key: cell type, Value: indices array
Examples:
>>> boundary_tris = mesh.cell_sets_dict["boundary"]["triangle"]
>>> material_tets = mesh.cell_sets_dict["steel"]["tetra"]
"""
def cell_sets_to_data(self, data_name=None):
"""
Convert cell sets to integer cell data arrays.
Converts named cell sets into integer data where each cell gets
an integer ID corresponding to its set membership.
Parameters:
- data_name: str | None - Name for resulting cell data
If None, uses joined names of all cell sets
Side Effects:
- Adds integer array(s) to cell_data
- Clears cell_sets dictionary
Examples:
>>> mesh.cell_sets_to_data("regions")
>>> # Creates mesh.cell_data["regions"] with integer IDs
"""
def point_sets_to_data(self, join_char="-"):
"""
Convert point sets to integer point data array.
Parameters:
- join_char: str - Character used to join set names for data name
Side Effects:
- Adds integer array to point_data
- Clears point_sets dictionary
Examples:
>>> mesh.point_sets_to_data()
>>> # Creates point data with name like "boundary-inlet-outlet"
"""
def cell_data_to_sets(self, key):
"""
Convert integer cell data to cell sets.
Parameters:
- key: str - Name of integer cell data to convert
Side Effects:
- Creates cell sets based on unique integer values
- Removes the cell data array
Raises:
- RuntimeError - If cell data is not integer type
Examples:
>>> mesh.cell_data_to_sets("material_ids")
>>> # Creates cell sets like "material-1", "material-2", etc.
"""
def point_data_to_sets(self, key):
"""
Convert integer point data to point sets.
Parameters:
- key: str - Name of integer point data to convert
Side Effects:
- Creates point sets based on unique integer values
- Removes the point data array
Raises:
- RuntimeError - If point data is not integer type
Examples:
>>> mesh.point_data_to_sets("boundary_ids")
>>> # Creates point sets like "boundary-1", "boundary-2", etc.
"""
@classmethod
def read(cls, path_or_buf, file_format=None):
"""
Read mesh from file (deprecated).
Note: This method is deprecated. Use meshio.read() instead.
Parameters:
- path_or_buf: str | Path | Buffer - Input source
- file_format: str | None - Optional format specification
Returns:
- Mesh - Loaded mesh object
"""Container class representing a block of cells of the same topological type.
class CellBlock:
"""
Represents a block of cells of the same type with connectivity data.
Constructor:
CellBlock(cell_type, data, tags=None)
Parameters:
- cell_type: str - Cell type identifier
Examples: "triangle", "quad", "tetra", "hexahedron", "line", "vertex"
Also supports higher-order elements: "triangle6", "tetra10", etc.
- data: List | np.ndarray - Cell connectivity data
For regular cells: 2D array with shape (n_cells, nodes_per_cell)
For polyhedron: list of variable-length sublists
- tags: List[str] | None - Optional list of string tags for the cell block
Attributes:
- type: str - Cell type string identifier
- data: np.ndarray | List - Connectivity data array or list
- dim: int - Topological dimension (0=vertex, 1=line, 2=surface, 3=volume)
- tags: List[str] - List of associated tags
"""
def __len__(self):
"""
Get number of cells in the block.
Returns:
- int - Number of cells
Examples:
>>> num_triangles = len(triangle_block)
"""
def __repr__(self):
"""
String representation showing cell block information.
Returns:
- str - Descriptive string with type, count, and tags
Examples:
>>> print(cell_block)
<meshio CellBlock, type: triangle, num cells: 1000, tags: ['boundary']>
"""Dictionary mapping cell type names to their topological dimensions.
topological_dimension: Dict[str, int]
"""
Dictionary mapping cell type names to topological dimensions.
Keys include:
- 0D elements: "vertex"
- 1D elements: "line", "line3", "line4", ..., "line11"
- 2D elements: "triangle", "triangle6", "triangle10", "quad", "quad8", "polygon"
- 3D elements: "tetra", "tetra10", "hexahedron", "hexahedron20", "wedge", "pyramid"
- VTK Lagrange elements: "VTK_LAGRANGE_CURVE", "VTK_LAGRANGE_TRIANGLE", etc.
Examples:
>>> from meshio import topological_dimension
>>> print(topological_dimension["triangle"]) # 2
>>> print(topological_dimension["tetra"]) # 3
>>> print(topological_dimension["line"]) # 1
"""import meshio
import numpy as np
# Simple triangle mesh
points = np.array([
[0.0, 0.0, 0.0],
[1.0, 0.0, 0.0],
[0.0, 1.0, 0.0],
[1.0, 1.0, 0.0]
])
cells = [
("triangle", [[0, 1, 2], [1, 3, 2]])
]
mesh = meshio.Mesh(points, cells)
# With associated data
point_data = {
"temperature": np.array([20.0, 25.0, 22.0, 27.0]),
"velocity": np.random.rand(4, 3)
}
cell_data = {
"material": [np.array([1, 2])], # One value per triangle
"density": [np.array([2.5, 3.1])]
}
mesh_with_data = meshio.Mesh(
points, cells,
point_data=point_data,
cell_data=cell_data
)# Mixed element mesh
points = np.random.rand(20, 3)
cells = [
("triangle", [[0, 1, 2], [1, 3, 2]]),
("quad", [[4, 5, 6, 7], [8, 9, 10, 11]]),
("tetra", [[12, 13, 14, 15]])
]
mesh = meshio.Mesh(points, cells)
# Access cells by type
triangles = mesh.get_cells_type("triangle")
quads = mesh.get_cells_type("quad")
tetras = mesh.get_cells_type("tetra")
print(f"Triangles shape: {triangles.shape}") # (2, 3)
print(f"Quads shape: {quads.shape}") # (2, 4)
print(f"Tetras shape: {tetras.shape}") # (1, 4)
# Dictionary access
cells_dict = mesh.cells_dict
for cell_type, connectivity in cells_dict.items():
print(f"{cell_type}: {len(connectivity)} cells")# Define material regions and boundary conditions
cell_sets = {
"material_steel": [np.array([0, 2, 4]), np.array([])], # Triangle indices, no quads
"material_aluminum": [np.array([1, 3]), np.array([0, 1])] # Both triangles and quads
}
point_sets = {
"boundary": np.array([0, 1, 2, 3]),
"inlet": np.array([0, 1]),
"outlet": np.array([2, 3])
}
mesh = meshio.Mesh(
points, cells,
cell_sets=cell_sets,
point_sets=point_sets
)
# Convert sets to integer data
mesh.cell_sets_to_data("regions")
mesh.point_sets_to_data()
print("Cell data:", list(mesh.cell_data.keys()))
print("Point data:", list(mesh.point_data.keys()))# Create mesh with integer cell data
cell_data = {
"material_id": [np.array([1, 1, 2, 2]), np.array([3, 3])] # Per cell type
}
mesh = meshio.Mesh(points, cells, cell_data=cell_data)
# Convert back to sets
mesh.cell_data_to_sets("material_id")
print("Cell sets:", list(mesh.cell_sets.keys()))
# Get data for specific cell type
if mesh.cell_data:
steel_temps = mesh.get_cell_data("temperature", "triangle")# Create CellBlock objects directly
triangle_block = meshio.CellBlock(
"triangle",
[[0, 1, 2], [1, 3, 2]],
tags=["boundary", "surface"]
)
quad_block = meshio.CellBlock(
"quad",
[[4, 5, 6, 7], [8, 9, 10, 11]],
tags=["volume"]
)
mesh = meshio.Mesh(points, [triangle_block, quad_block])
# Access CellBlock properties
for cell_block in mesh.cells:
print(f"Type: {cell_block.type}")
print(f"Count: {len(cell_block)}")
print(f"Dimension: {cell_block.dim}")
print(f"Tags: {cell_block.tags}")# Add global field data
field_data = {
"simulation_time": 1.5,
"solver_version": "2.1.0",
"units": {"length": "meters", "time": "seconds"},
"constants": np.array([9.81, 1.0e-6]) # gravity, viscosity
}
mesh = meshio.Mesh(
points, cells,
field_data=field_data,
info={"created_by": "simulation_script.py", "date": "2024-01-01"}
)# Print mesh summary
print(mesh)
# Output:
# <meshio mesh object>
# Number of points: 20
# Number of cells:
# triangle: 2
# quad: 2
# tetra: 1
# Point data: temperature, velocity
# Cell data: material, density
# Field data: simulation_time, solver_version, units, constants
# Detailed inspection
print(f"Points shape: {mesh.points.shape}")
print(f"Number of cell blocks: {len(mesh.cells)}")
for i, cell_block in enumerate(mesh.cells):
print(f"Block {i}: {cell_block}")Meshio automatically validates data consistency during mesh construction:
try:
# This will raise ValueError - mismatched point data length
bad_mesh = meshio.Mesh(
points=np.random.rand(10, 3), # 10 points
cells=[("triangle", [[0, 1, 2]])],
point_data={"temp": np.array([1, 2, 3])} # Only 3 values
)
except ValueError as e:
print(f"Validation error: {e}")
try:
# This will raise ValueError - mismatched cell data
bad_mesh = meshio.Mesh(
points=points,
cells=[("triangle", [[0, 1, 2]])], # 1 cell
cell_data={"material": [np.array([1, 2])]} # 2 values
)
except ValueError as e:
print(f"Validation error: {e}")Install with Tessl CLI
npx tessl i tessl/pypi-meshio