Python frontend for Gmsh mesh generator providing intuitive abstractions for creating complex geometric models and generating high-quality meshes
—
Advanced mesh generation control features for precise mesh sizing, boundary layer generation, and structured meshing. These capabilities enable fine-grained control over mesh quality and structure for specialized engineering applications.
Control mesh element sizing through various field-based approaches, enabling adaptive mesh refinement and region-specific sizing.
def set_mesh_size_callback(fun, ignore_other_mesh_sizes=True):
"""
Set a callback function for dynamic mesh sizing based on position.
The callback function receives (dim, tag, x, y, z) parameters and
returns the desired element size at that location.
Parameters:
- fun: callable, sizing function with signature (dim, tag, x, y, z) -> float
- ignore_other_mesh_sizes: bool, ignore point-based mesh sizes
Returns:
None (sets sizing callback for geometry)
Example:
# Radial sizing based on distance from origin
geom.set_mesh_size_callback(
lambda dim, tag, x, y, z: 0.1 + 0.5 * (x**2 + y**2)**0.5
)
"""
def add_boundary_layer(*args, **kwargs):
"""
Create boundary layer size field for mesh refinement near surfaces.
Creates a BoundaryLayer size field that provides fine mesh control
near specified boundaries, essential for accurate boundary layer
resolution in fluid dynamics and heat transfer simulations.
Parameters (via BoundaryLayer constructor):
- lcmin: float, minimum element size in boundary layer
- lcmax: float, maximum element size away from boundary
- distmin: float, minimum distance for size transition
- distmax: float, maximum distance for size transition
- edges_list: list, edges for boundary layer (optional)
- faces_list: list, faces for boundary layer (optional)
- nodes_list: list, nodes for boundary layer (optional)
- num_points_per_curve: int, discretization points per curve
Returns:
BoundaryLayer: Size field object for background mesh configuration
"""
def set_background_mesh(fields, operator):
"""
Configure background mesh with multiple size fields.
Combines multiple size fields using specified operators to create
complex mesh sizing strategies with different priorities and regions.
Parameters:
- fields: list[SizeField], size field objects to combine
- operator: str, combination operator ("Min", "Max", "Mean", etc.)
Returns:
None (configures background mesh for geometry)
Example:
boundary_layer = geom.add_boundary_layer(...)
refinement_field = geom.add_distance_field(...)
geom.set_background_mesh([boundary_layer, refinement_field], "Min")
"""Generate structured meshes with explicit control over element count and distribution along curves, surfaces, and volumes.
def set_transfinite_curve(curve, num_nodes, mesh_type, coeff):
"""
Set transfinite meshing parameters for curve.
Creates structured mesh along curve with specified node count
and distribution. Essential for high-quality structured meshing.
Parameters:
- curve: Curve, target curve for transfinite meshing
- num_nodes: int, number of nodes along curve
- mesh_type: str, node distribution type ("Progression", "Bump", etc.)
- coeff: float, progression coefficient for non-uniform distribution
Returns:
None (configures curve for structured meshing)
"""
def set_transfinite_surface(surface, arrangement, corner_pts):
"""
Set transfinite meshing parameters for surface.
Creates structured quad mesh on surface using transfinite interpolation
between boundary curves. Requires compatible boundary discretization.
Parameters:
- surface: Surface, target surface for transfinite meshing
- arrangement: str, corner arrangement ("Left", "Right", "Alternate")
- corner_pts: list[Point], corner points defining surface orientation
Returns:
None (configures surface for structured meshing)
"""
def set_transfinite_volume(volume, corner_pts):
"""
Set transfinite meshing parameters for volume.
Creates structured hex mesh in volume using transfinite interpolation
between boundary surfaces. Requires compatible surface discretization.
Parameters:
- volume: Volume, target volume for transfinite meshing
- corner_pts: list[Point], corner points defining volume orientation
Returns:
None (configures volume for structured meshing)
"""
def set_recombined_surfaces(surfaces):
"""
Enable quad element generation for surfaces.
Combines triangular elements into quadrilateral elements where possible,
improving mesh quality for certain analysis types.
Parameters:
- surfaces: list[Surface], surfaces to recombine into quads
Returns:
None (enables recombination for specified surfaces)
"""Specialized classes for creating complex mesh sizing strategies with precise control over element size distribution.
class BoundaryLayer:
"""
Boundary layer size field for mesh refinement near surfaces.
Provides exponential size gradation from fine elements at boundaries
to coarser elements in the interior, essential for boundary layer
resolution in CFD and heat transfer applications.
"""
def __init__(self, lcmin, lcmax, distmin, distmax, edges_list=None,
faces_list=None, nodes_list=None, num_points_per_curve=None):
"""
Initialize boundary layer size field.
Parameters:
- lcmin: float, minimum element size at boundary
- lcmax: float, maximum element size away from boundary
- distmin: float, distance where size transition begins
- distmax: float, distance where maximum size is reached
- edges_list: list[Edge], edges for boundary layer application
- faces_list: list[Face], faces for boundary layer application
- nodes_list: list[Point], nodes for boundary layer application
- num_points_per_curve: int, discretization density per curve
"""
class SetBackgroundMesh:
"""
Background mesh configuration combining multiple size fields.
Enables complex mesh sizing strategies by combining different
size field types with mathematical operators.
"""
def __init__(self, fields, operator):
"""
Initialize background mesh configuration.
Parameters:
- fields: list[SizeField], size fields to combine
- operator: str, combination operator:
- "Min": Minimum size from all fields
- "Max": Maximum size from all fields
- "Mean": Average size from all fields
- "Intersection": Intersection-based combination
"""import pygmsh
with pygmsh.geo.Geometry() as geom:
# Create airfoil-like shape
airfoil = geom.add_polygon([
[0.0, 0.0], [0.5, 0.1], [1.0, 0.0],
[0.5, -0.1], [0.0, 0.0]
], mesh_size=0.1)
# Create boundary layer around airfoil
boundary_layer = geom.add_boundary_layer(
edges_list=airfoil.curves,
lcmin=0.001, # Very fine at surface
lcmax=0.1, # Coarser away from surface
distmin=0.0, # Start immediately at surface
distmax=0.05 # Transition distance
)
# Apply boundary layer as background mesh
geom.set_background_mesh([boundary_layer], "Min")
mesh = geom.generate_mesh(dim=2)import pygmsh
with pygmsh.geo.Geometry() as geom:
# Create structured rectangle
p1 = geom.add_point([0, 0, 0])
p2 = geom.add_point([1, 0, 0])
p3 = geom.add_point([1, 1, 0])
p4 = geom.add_point([0, 1, 0])
# Create curves with transfinite specification
l1 = geom.add_line(p1, p2)
l2 = geom.add_line(p2, p3)
l3 = geom.add_line(p3, p4)
l4 = geom.add_line(p4, p1)
# Set transfinite parameters for each curve
geom.set_transfinite_curve(l1, 11, "Progression", 1.0) # 11 nodes, uniform
geom.set_transfinite_curve(l2, 21, "Progression", 1.2) # 21 nodes, graded
geom.set_transfinite_curve(l3, 11, "Progression", 1.0) # Match opposite side
geom.set_transfinite_curve(l4, 21, "Progression", 1.2) # Match opposite side
# Create surface and set transfinite
curve_loop = geom.add_curve_loop([l1, l2, l3, l4])
surface = geom.add_plane_surface(curve_loop)
geom.set_transfinite_surface(surface, "Left", [p1, p2, p3, p4])
geom.set_recombined_surfaces([surface]) # Use quads instead of triangles
mesh = geom.generate_mesh(dim=2)import pygmsh
import numpy as np
with pygmsh.geo.Geometry() as geom:
# Create complex domain
outer = geom.add_circle([0, 0, 0], 2.0, make_surface=False)
inner = geom.add_circle([0, 0, 0], 0.5, make_surface=False)
# Domain with hole
domain = geom.add_plane_surface(geom.add_curve_loop([outer.curve_loop.curves[0]]))
hole = geom.add_plane_surface(geom.add_curve_loop([inner.curve_loop.curves[0]]))
final_surface = geom.boolean_difference(domain, hole)
# Set adaptive sizing based on distance from center and boundaries
def adaptive_sizing(dim, tag, x, y, z):
# Distance from center
r = np.sqrt(x**2 + y**2)
# Fine near inner boundary, coarser towards outer boundary
if r < 0.6:
return 0.02 # Very fine near hole
elif r < 1.0:
return 0.02 + 0.08 * (r - 0.6) / 0.4 # Gradual transition
else:
return 0.1 + 0.2 * (r - 1.0) # Coarser towards outside
geom.set_mesh_size_callback(adaptive_sizing)
mesh = geom.generate_mesh(dim=2)Install with Tessl CLI
npx tessl i tessl/pypi-pygmsh