Grids¶
In order to solve a problem using the boundary element method, we must first define the grid (or mesh) on which the problem will be discretised. In Bempp, the grid will be a triangulation of a 2D surface in 3D space. Bempp currently only supports grids consisting of flat surface triangles.
This section looks at how grids can be created and used in Bempp. Full documentation of the functionality of Bempp grids can be found on Read the Docs.
Overview¶
A Bempp grid can be created using a built-in grid, by importing a gmsh file, or by providing the grid data.
We first import Bempp and NumPy.
import bempp.api
import numpy as np
Built-in grids¶
Various shapes are included in the bempp.api.shapes
module, and discretisations with
different numbers of elements can be created using these.
In order for the these built-in grids to work, Gmsh must be
installed and the command gmsh
must be available in the path.
The command regular_sphere
creates a sphere by refining a
base octahedron. The number of elements in the sphere is given by
\(8 \times 4^n\), where \(n\) is the refinement level.
The following command creates a triangulation of a sphere with refinement level 3:
grid = bempp.api.shapes.regular_sphere(3)
The command sphere
creates a sphere with a chosen element size.
The following command creates a sphere with element diameter \(h=0.1\):
grid = bempp.api.shapes.sphere(h=0.1)
The command cube
creates a cube with a chosen element size.
The following command creates a cube with element diameter \(h=0.3\):
grid = bempp.api.shapes.cube(h=0.3)
Full automatically-generated documentation of Bempp’s available built-in grids can be found here.
Importing a grid¶
Grids can be importedusing Bempp’s import_grid
command.
For example, the following command will load a grid from the Gmsh file my_grid.msh
.
grid = bempp.api.import_grid('my_grid.msh')
Bempp uses the file ending to recognise a number of grid formats. Importing grids is handled by the meshio library.
This works through the external meshio
library.
A list of all files types that can be imported can be found in the meshio documentation.
Frequently used formats with Bempp are .msh
(Gmsh),
.vtk
(Legacy VTK), and .vtu
(VTK Xml Format).
Creating a grid from element data¶
Bempp grids can be generated from arrays containing vertex coordinates and connectivity information. For example, to create a grid consisting of two triangles with vertices \(\\{(0, 0, 0), (1, 0, 0), (0, 1, 0)\\}\) and \(\\{(1, 0, 0), (1, 1, 0), (0, 1, 0)\\}\) we use the following commands:
vertices = np.array(
[[0, 1, 0, 1], [0, 0, 1, 1], [0, 0, 0, 0]],
dtype=np.float64)
elements = np.array(
[[0, 1], [1, 3], [2, 2]], dtype=np.uint32)
grid = bempp.api.Grid(vertices, elements)
Note that the three arrays in the vertices
array are the \(x\)-coordinates,
then the \(y\)-coordinates, then the \(z\)-coordinates.
Similarly, the three arrays in the elements
array are the first points of each triangle,
then the second points, then the third points.
In general, the vertices
and elements
arrays should have shapes \(3\times M\) and \(3\times N\)
(respectively) for a grid with \(M\) vertices and \(N\) elements.
The array vertices
contains the 3D coordinates of all vertices. The array
elements
contains the connectivity information. In this case the first
triangle consists of the vertices 0, 1, 2, and the second triangle consists
of the vertices 1, 3, 2.
Optionally, we can specify a list domain_indices
that gives different groups of elements the same id. This can be used
for example to generate different types of boundary data on different parts
of the grid, or to specify function spaces only on parts of the grid. In this
example, both triangles automatically have the identifier 0 since nothing
else was specified. This is equivalent to running:
grid = bempp.api.Grid(vertices, elements, domain_indices=[0, 0])
Using Grids¶
Once you have created a Bempp grid, you may want to use information about your grid. This page show how commonly used information can be obtained from a Bempp grid.
Querying grid information¶
The number of elements, edges and vertices in a grid are given by:
grid.number_of_elements
grid.number_of_edges
grid.number_of_vertices
To query the maximum and minimum element diameter use the following attributes:
grid.maximum_element_diameter
grid.minimum_element_diameter
The vertex indices of the element 5 can be obtained using:
grid.elements[:, 5]
Note that the numbering of element starts at 0, so element 5 is the grid’s sixth element.
The vertex coordinates of element 5 can be found using:
grid.vertices[:, grid.elements[:, 5]]
The area of the element 5 is:
grid.volumes[5]
The edge indices associated with element 5 are:
grid.element_edges[5]
The vertex indices of the edges of element 5 can be obtained using:
grid.edges[:, grid.element_edges[:, 5]]
This returns a 2×3 array of the vertex coordinates associated with the three edges of the element. Edges in Bempp are ordered in the following way:
Edge |
First vertex |
Second vertex |
---|---|---|
0 |
0 |
1 |
1 |
0 |
2 |
2 |
1 |
2 |
Full automatically-generated documentation of the Bempp Grid
class can be found
here.
Plotting and exporting grids¶
To export a grid, we can use the export
command:
bempp.api.export('grid.msh', grid=grid)
This commands export the object grid
as Gmsh file with the
name grid.msh
.
In order to plot a grid, we can simply use the command:
grid.plot()
By default, this will plot using Gmsh (or plotly if you are inside a Jupyter notebook). The following command can be used to change the plotting backend.
bempp.api.PLOT_BACKEND = "gmsh"
bempp.api.PLOT_BACKEND = "paraview"
This requires Gmsh or Paraview to be available in the system path.