Adding L-shaped domains for SeismicMesh
3.0.5. The 3D L-shaped domain indeed has some trouble with the pockets between SDFs so that remains to be improved but it's a valid mesh with a bounded minimum dihedral angle.
Note: min() and max() of two SDFs do not always produce a valid SDF. The result is actually not a distance field, but just a lower bound to the real distance to the resulting surface. Here I use the union to approximate the domain which results in errors "deep" in the interior of the geometry but this okay for meshing in these examples...
import numpy as np
import meshio
from SeismicMesh import Rectangle, generate_mesh, geometry
hmin = 0.05
bbox = (0.0, 1.0, 0.0, 1.0)
bbox0 = (0.0, 1.0, 0.0, 0.5)
rect0 = Rectangle(bbox0)
bbox1 = (0.0, 0.5, 0.0, 1.0)
rect1 = Rectangle(bbox1)
corners = geometry.corners
def union(x):
return np.minimum.reduce([rect0.eval(x), rect1.eval(x)])
pfix = np.vstack((corners(bbox0), corners(bbox1)))
points, cells = generate_mesh(
bbox=bbox,
domain=union,
edge_length=hmin,
pfix=pfix,
verbose=2,
)
meshio.write_points_cells(
"L_shape_2d.vtk",
points,
[("triangle", cells)],
)
from SeismicMesh import Cube, generate_mesh, sliver_removal, geometry
hmin = 0.05
bbox = (0.0, 1.0, 0.0, 1.0, 0.0, 1.0)
tol = hmin/10
bbox0 = (0.0, 1.0, 0.0, 1.0, 0.0, 0.50 + tol)
cube0 = Cube(bbox0)
bbox1 = (0.0, 1.0, 0.5, 1.0, 0.50 - tol, 1.0)
cube1 = Cube(bbox1)
bbox2 = (0.5 - tol, 1.0, 0.0, 1.0, 0.50 - tol, 1.0)
cube2 = Cube(bbox2)
corners = geometry.corners
def union(x):
return np.minimum.reduce([cube0.eval(x), cube1.eval(x), cube2.eval(x)])
pfix = np.vstack((corners(bbox0), corners(bbox1), corners(bbox2)))
points, cells = generate_mesh(
bbox=bbox,
domain=union,
edge_length=hmin,
pfix=pfix,
verbose=2,
)
points, cells = sliver_removal(
points=points,
bbox=bbox,
domain=union,
edge_length=hmin,
verbose=2,
)
meshio.write_points_cells(
"L_shape.vtk",
points,
[("tetra", cells)],
)