Mesh Classes#
Base Classes#
Define the base Mesh class on which the other classes are based.
- class sphedron.mesh.base.Mesh(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]])[source]#
Flexible base class for spherical meshes.
Provides core functionality for node/face storage, node masking, and cached property computation.
Use
from_base()to start from a class-defined base graph, orfrom_graph()to start from provided nodes/faces. Both optionally rotate and refine before constructing the Mesh.Subclasses must implement
base()andrefine().- Parameters:
nodes – Cartesian coordinates of mesh nodes, shape
(N, 3).faces – Face definitions as indices into nodes, shape
(F, K)where K is 3 for triangles or 4 for rectangles.
Attributes
- property edges#
Get the edges of the mesh
- property edges_symmetric: ndarray[tuple[Any, ...], dtype[int64]]#
Get the edges of the undirected mesh
- property edges_unique#
Get directed edges of the graph, from lower to higher index nodes
- property faces: ndarray[tuple[Any, ...], dtype[int64]]#
Get faces of the mesh, can be rectangles or triangles or more
- property faces_partial: ndarray[tuple[Any, ...], dtype[_ScalarT]]#
Get faces of the mesh including those with partially masked nodes
- property nodes#
Returns the nodes of mesh in cartesian coordinates
- property nodes_latlong#
Returns the nodes of mesh in latitude/longitude format (degree)
- property num_edges#
Number of edges
- property num_faces: int#
Number of faces
- property num_nodes#
Number of nodes
- property triangles#
Return triangles of the mesh, useful for trimesh construction
Methods
from_base([refine_factor, rotate, ...])Create an instance starting from the class base graph.
from_graph(nodes, faces[, refine_factor, ...])Create mesh from nodes and faces and optionally rotate/refine.
refine(nodes, faces, factor[, use_angle])Refine the mesh.
base()Return the base (nodes, faces) geometry.
reset()Reset the node mask so all nodes are visible again.
mask_nodes(nodes_mask)Mask the nodes associated with nodes_mask[i] == True.
faces2triangles(faces)Convert face to their corresponding triangles
triangle2face_index(triangle_idx)Convert triangle index to face index
face2triangle_index(face_idx)Convert face index to triangle index
return Trimesh instance from the current nodes and faces
query_edges_from_faces(receiver_mesh)Get edges connecting nodes of the nearest face to receiver nodes.
query_edges_from_radius(receiver_mesh, radius)Get edges connecting nearest neighboring nodes to receiver nodes.
query_edges_from_neighbors(receiver_mesh, ...)Return edges connecting nearest neighboring nodes to receiver nodes.
- classmethod from_base(refine_factor: int = 1, rotate: bool = True, refine_by_angle: bool = False)[source]#
Create an instance starting from the class base graph.
- Pipeline:
base -> optional rotate -> optional refine -> construct
- Parameters:
refine_factor – The factor by which to refine the mesh.
rotate – Whether to rotate base nodes using rotation_axis/angle.
refine_by_angle – Whether to refine by angle (strategy-specific).
- Returns:
An instance of the class created from the generated nodes and faces.
- classmethod from_graph(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]], refine_factor: int = 1, refine_by_angle: bool = False, rotate: bool = False)[source]#
Create mesh from nodes and faces and optionally rotate/refine.
- Pipeline:
provided graph -> optional rotate -> optional refine -> construct
- Parameters:
nodes (numpy.ndarray[M, ...]) – Coordinates of the nodes.
faces (numpy.ndarray[N, K]) – Faces defined by indices into nodes.
refine_factor (int) – Factor by which to refine the mesh. Higher values yield a more finely subdivided mesh.
refine_by_angle (bool) – If True, refinement considers edge angles.
rotate (bool) – If True, rotate the provided nodes using the class rotation parameters before refinement.
- Returns:
A new instance containing the (optionally) refined graph.
- Return type:
Example
>>> from sphedron.mesh import Icosphere >>> base_nodes, base_faces = Icosphere.base() >>> refined = Icosphere.from_graph( ... base_nodes, base_faces, refine_factor=2 ... ) >>> print(refined.num_nodes, refined.num_faces)
- static refine(nodes, faces, factor, use_angle=False, **kwargs) Tuple[ndarray[tuple[Any, ...], dtype[_ScalarT]], ndarray[tuple[Any, ...], dtype[_ScalarT]]][source]#
Refine the mesh. Subclasses must override this method.
- static base() Tuple[ndarray[tuple[Any, ...], dtype[_ScalarT]], ndarray[tuple[Any, ...], dtype[_ScalarT]]][source]#
Return the base (nodes, faces) geometry. Subclasses must override.
- mask_nodes(nodes_mask: ndarray[tuple[Any, ...], dtype[bool]])[source]#
Mask the nodes associated with nodes_mask[i] == True.
This method expects a boolean mask of size (num_nodes,). It will mask the specified nodes but will not unmask any nodes that have previously been masked.
- Parameters:
nodes_mask – A boolean array indicating which nodes to mask. The array should have a size equal to the number of nodes in the graph.
- query_edges_from_faces(receiver_mesh: Mesh) ndarray[tuple[Any, ...], dtype[_ScalarT]][source]#
Get edges connecting nodes of the nearest face to receiver nodes.
This method retrieves the edges that connect the nodes of the nearest face in the current mesh to the nodes in the provided receiver mesh.
- Parameters:
receiver_mesh – The mesh object that contains the receiver nodes.
- Returns:
An NDArray containing the edges that connect the nodes of the nearest face to the receiver nodes, shape (N,2)
- query_edges_from_radius(receiver_mesh: Mesh, radius: float) ndarray[tuple[Any, ...], dtype[_ScalarT]][source]#
Get edges connecting nearest neighboring nodes to receiver nodes.
- Parameters:
receiver_mesh – The mesh object to query edges from.
radius – The radius within which to find neighboring nodes.
- Returns:
- Array of edges connecting nearest neighboring nodes to receiver
nodes, shaped (N,2)
- query_edges_from_neighbors(receiver_mesh, n_neighbors)[source]#
Return edges connecting nearest neighboring nodes to receiver nodes.
- Parameters:
receiver_mesh – The mesh object to receive edges from.
n_neighbors – The number of nearest neighbors to consider.
- Returns:
- Array of edges connecting nearest neighboring nodes to receiver
nodes, shaped (N,2)
- class sphedron.mesh.base.NodesOnlyMesh(nodes_latlong)[source]#
Bases:
MeshA mesh defined only by a set of nodes, with no real face connectivity.
This class does not support the refinement creation pattern (
from_base/from_graph). Use it when you only need node positions on the sphere.- Parameters:
nodes_latlong – Array of
(latitude, longitude)pairs in degrees, shape(N, 2).
- class sphedron.mesh.base.TriangularMesh(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]])[source]#
Bases:
MeshBase class for meshes with triangular faces.
Provides triangle-based refinement via
sphedron.refine.refine_triangles().Methods
refine(nodes, faces, factor[, use_angle])Refine a triangular mesh by subdividing each face.
faces2triangles(faces)Triangles are the faces themselves for triangular meshes.
triangle2face_index(triangle_idx)Triangle-to-face index (identity for triangular).
face2triangle_index(face_idx)Face-to-triangle index (identity for triangular).
- static refine(nodes, faces, factor, use_angle=False, **kwargs)[source]#
Refine a triangular mesh by subdividing each face.
- Parameters:
nodes – Node coordinates, shape (N, 3).
faces – Triangular face indices, shape (F, 3).
factor – Subdivision factor per edge.
use_angle – Use angle-based (geodesic) interpolation.
- Returns:
Tuple of (refined_nodes, refined_faces).
- class sphedron.mesh.base.RectangularMesh(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]])[source]#
Bases:
MeshBase class for meshes with rectangular (quad) faces.
Provides rectangle-based refinement via
sphedron.refine.refine_rectrangles().Methods
refine(nodes, faces, factor[, use_angle])Refine a rectangular mesh by subdividing each face.
faces2triangles(faces)Split each rectangle into two triangles.
triangle2face_index(triangle_idx)Convert triangle index to face index.
face2triangle_index(face_idx)Convert face index to its first triangle index.
- static refine(nodes, faces, factor, use_angle=False, **kwargs)[source]#
Refine a rectangular mesh by subdividing each face.
- Parameters:
nodes – Node coordinates, shape (N, 3).
faces – Rectangular face indices, shape (F, 4).
factor – Subdivision factor per edge.
use_angle – Use angle-based (geodesic) interpolation.
- Returns:
Tuple of (refined_nodes, refined_faces).
- faces2triangles(faces: ndarray[tuple[Any, ...], dtype[_ScalarT]]) ndarray[tuple[Any, ...], dtype[_ScalarT]][source]#
Split each rectangle into two triangles.
Refinable Meshes#
Refinable mesh classes: icosphere, octasphere, cubesphere, uniform.
- class sphedron.mesh.refinables.Icosphere(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]])[source]#
Bases:
TriangularMeshA triangular mesh generated from a refined icosahedron. Rotation angle is chosen to match Graphcast paper.
- class sphedron.mesh.refinables.Octasphere(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]])[source]#
Bases:
TriangularMeshA triangular mesh generated from a refined octahedron.
- class sphedron.mesh.refinables.Cubesphere(nodes: ndarray[tuple[Any, ...], dtype[_ScalarT]], faces: ndarray[tuple[Any, ...], dtype[_ScalarT]])[source]#
Bases:
RectangularMeshRepresents an cubesphere mesh, square-based.
- rotation_angle#
The angle used for rotating the icosphere.
- rotation_axis#
The axis around which the icosphere is rotated.
- static base() Tuple[ndarray[tuple[Any, ...], dtype[_ScalarT]], ndarray[tuple[Any, ...], dtype[_ScalarT]]][source]#
Create the base cube geometry.
- Returns:
Tuple (nodes, faces) of shapes (8, 3) and (6, 4).
The cube layout:
(-1,-1,1) 4------------5 (-1,1,1) /| /| / | / | / | / | (1,-1,1) 0---|--------1 (1,1,1) (-1,-1,-1) 7--------|---6 (-1,1,-1) | / | / | / | / |/ |/ (1,-1,-1) 3------------2 (1,1,-1)
- class sphedron.mesh.refinables.UniformMesh(resolution=1.0, uniform_lats: ndarray[tuple[Any, ...], dtype[_ScalarT]] | None = None, uniform_longs: ndarray[tuple[Any, ...], dtype[_ScalarT]] | None = None)[source]#
Bases:
RectangularMeshA rectangular mesh of uniformly distributed latitude and longitude.
The lat/lon grid is connected with quad faces where each cell connects four neighboring grid points. Longitude wraps around so the last column connects back to the first.
- Parameters:
resolution – Grid spacing in degrees (default 1.0). Ignored if uniform_lats and uniform_longs are provided.
uniform_lats – Custom latitude values in degrees. Must be provided together with uniform_longs.
uniform_longs – Custom longitude values in degrees. Must be provided together with uniform_lats.
Methods
reshape(values)Reshape flat node values back to the (lat, lon) grid layout.
Nested Meshes#
Hierarchical nested mesh structures at multiple refinement levels.
- class sphedron.mesh.nested.NestedMeshes(factors: List[int], refine_by_angle: bool = False, rotate: bool = True)[source]#
A manager for a hierarchy of meshes at increasing refinement levels.
Composes multiple
Meshobjects. Individual levels are accessible via indexing (nested[i]), and convenience properties aggregate nodes, edges, and faces across the hierarchy.- Parameters:
factors – List of refinement factors. Each entry refines the previous level by that factor. The cumulative product gives the effective depth at each level.
refine_by_angle – Use angle-based (geodesic) interpolation during refinement.
rotate – Rotate the base mesh using the class rotation parameters.
Attributes
- property nodes#
Nodes of the finest (most refined) mesh.
- property nodes_latlong#
Nodes of the finest mesh in latitude/longitude format (degrees).
- property num_edges#
Total number of edges across all refinement levels.
- property num_faces#
Total number of faces across all refinement levels.
- property num_nodes#
Number of nodes in the finest mesh.
- property edges: ndarray[tuple[Any, ...], dtype[int64]]#
All edges from every refinement level, concatenated.
- property faces: ndarray[tuple[Any, ...], dtype[int64]]#
All faces from every refinement level, concatenated.
Methods
__getitem__(level)Get the mesh at a specific refinement level.
__len__()Return the number of refinement levels.
reset()Resets the node masks on all meshes in the hierarchy.
mask_nodes(nodes_mask)Apply a mask to nodes, propagating to all refinement levels.
Build a Trimesh from the finest mesh.
query_edges_from_faces(receiver_mesh)Delegate face-based edge query to the finest mesh.
query_edges_from_radius(receiver_mesh, radius)Delegate radius-based edge query to the finest mesh.
query_edges_from_neighbors(receiver_mesh, ...)Delegate neighbor-based edge query to the finest mesh.
- mask_nodes(nodes_mask: ndarray[tuple[Any, ...], dtype[bool]])[source]#
Apply a mask to nodes, propagating to all refinement levels.
Applies the mask to the finest mesh and propagates the masking effect to coarser meshes where applicable.
- query_edges_from_faces(receiver_mesh) ndarray[tuple[Any, ...], dtype[_ScalarT]][source]#
Delegate face-based edge query to the finest mesh.
- class sphedron.mesh.nested.NestedIcospheres(factors: List[int], refine_by_angle: bool = False, rotate: bool = True)[source]#
Bases:
NestedMeshesNested icospheres, refined version of the previous.
- class sphedron.mesh.nested.NestedOctaspheres(factors: List[int], refine_by_angle: bool = False, rotate: bool = True)[source]#
Bases:
NestedMeshesNested octaspheres, where self.mesh[i+1] is a refined self.meshes[i].
- class sphedron.mesh.nested.NestedCubespheres(factors: List[int], refine_by_angle: bool = False, rotate: bool = True)[source]#
Bases:
NestedMeshesNested cubespheres, where self.mesh[i+1] is a refined self.meshes[i].