API reference¶
Top-level¶
pyfieldml: a pure-Python implementation of FieldML 0.5.
BasisNotFoundError ¶
Bases: FieldMLError
Raised when a referenced basis function is not registered.
Document ¶
An in-memory FieldML document.
Holds a single primary Region (the first one in the document) plus
the original DOM tree for round-trip writing.
source_version
property
¶
source_version: str
FieldML version declared on the root element (@version).
explore ¶
explore() -> Any
Open an interactive Jupyter widget to browse the evaluator graph.
Requires the [viz] extra: pip install pyfieldml[viz].
field ¶
field(name: str) -> Field
Return a Field wrapper for the evaluator named name.
Phase-2: requires the graph convention produced by add_lagrange_mesh.
from_file
classmethod
¶
from_file(path: PathLike) -> Document
Read a FieldML document from an on-disk file.
from_meshio
classmethod
¶
from_meshio(
mesh: Mesh, *, name: str = "imported"
) -> Document
Convert a meshio.Mesh to a Document. Requires pyfieldml[meshio].
from_region
classmethod
¶
from_region(region: Region) -> Document
Build a Document from a programmatically-constructed Region.
from_string
classmethod
¶
from_string(content: str | bytes) -> Document
Read a FieldML document from an in-memory string/bytes.
External data-resource hrefs (HDF5, plain-text) are resolved relative to the current working directory since no source path is available.
to_meshio ¶
to_meshio() -> meshio.Mesh
Convert this Document to a meshio.Mesh. Requires pyfieldml[meshio].
write ¶
write(path: PathLike) -> None
Phase-1 write path: re-serializes the DOM tree we parsed from.
EvaluationError ¶
Bases: FieldMLError
Raised when the evaluation engine cannot produce a result.
FieldMLError ¶
Bases: Exception
Base class for every error raised by pyfieldml.
FieldMLParseError ¶
FieldMLValidationError ¶
Region ¶
A named namespace for FieldML types, evaluators, and imports.
Objects are stored in insertion order. Names must be unique across all object kinds within a region.
UnboundArgumentError ¶
Bases: FieldMLError
Raised when an ArgumentEvaluator is evaluated without a binding.
UnresolvedImportError ¶
Bases: FieldMLError
Raised when a FieldML <Import> cannot be located.
read ¶
read(path: PathLike) -> Document
Read a FieldML document from path. Convenience for Document.from_file.
validate ¶
validate(path: PathLike) -> None
Parse and XSD-validate path. Raises FieldMLError on any failure.
Document and Field¶
An in-memory FieldML document.
Holds a single primary Region (the first one in the document) plus
the original DOM tree for round-trip writing.
source_version
property
¶
source_version: str
FieldML version declared on the root element (@version).
explore ¶
explore() -> Any
Open an interactive Jupyter widget to browse the evaluator graph.
Requires the [viz] extra: pip install pyfieldml[viz].
field ¶
field(name: str) -> Field
Return a Field wrapper for the evaluator named name.
Phase-2: requires the graph convention produced by add_lagrange_mesh.
from_file
classmethod
¶
from_file(path: PathLike) -> Document
Read a FieldML document from an on-disk file.
from_meshio
classmethod
¶
from_meshio(
mesh: Mesh, *, name: str = "imported"
) -> Document
Convert a meshio.Mesh to a Document. Requires pyfieldml[meshio].
from_region
classmethod
¶
from_region(region: Region) -> Document
Build a Document from a programmatically-constructed Region.
from_string
classmethod
¶
from_string(content: str | bytes) -> Document
Read a FieldML document from an in-memory string/bytes.
External data-resource hrefs (HDF5, plain-text) are resolved relative to the current working directory since no source path is available.
to_meshio ¶
to_meshio() -> meshio.Mesh
Convert this Document to a meshio.Mesh. Requires pyfieldml[meshio].
write ¶
write(path: PathLike) -> None
Phase-1 write path: re-serializes the DOM tree we parsed from.
Ergonomic wrapper for evaluating a FieldML evaluator graph.
supports Lagrange-only meshes where the region contains:
- A ParameterEvaluator named
coord_namewith node coordinates. - A ParameterEvaluator named
coord_name + ".connectivity"holding 1-indexed element->node connectivity. - An ExternalEvaluator whose name begins with
library.basis.naming the Lagrange basis (produced byadd_lagrange_mesh).
Phase 3: also supports cubic-Hermite line meshes where the region additionally
contains:
- coord_name + ".derivatives" - per-node derivative DOFs (same shape as
nodes).
- coord_name + ".scales" - per-element per-end derivative scale factors,
shape (n_elems, 2).
evaluate ¶
evaluate(
*, element: int | ndarray, xi: ArrayLike
) -> np.ndarray
Evaluate the field at parametric coordinate(s) within element(s).
jacobian ¶
jacobian(*, element: int, xi: ArrayLike) -> np.ndarray
Return the d(field)/d(xi) Jacobian at the given element and xi.
For a D-valued field on an R-dim reference element, returns shape (D, R).
plot ¶
plot(doc: Any = None, **kwargs: Any) -> Any
Render this Field via PyVista. Requires a Document + pyfieldml[viz].
sample ¶
sample(points: ArrayLike) -> np.ndarray
Sample the field at physical points. Points outside the mesh return NaN.
Errors¶
Error hierarchy for pyfieldml. All library errors subclass FieldMLError.
BasisNotFoundError ¶
Bases: FieldMLError
Raised when a referenced basis function is not registered.
EvaluationError ¶
Bases: FieldMLError
Raised when the evaluation engine cannot produce a result.
FieldMLError ¶
Bases: Exception
Base class for every error raised by pyfieldml.
FieldMLParseError ¶
FieldMLValidationError ¶
UnboundArgumentError ¶
Bases: FieldMLError
Raised when an ArgumentEvaluator is evaluated without a binding.
UnresolvedImportError ¶
Bases: FieldMLError
Raised when a FieldML <Import> cannot be located.
Model layer¶
Region — a namespace container for FieldML objects.
Region ¶
A named namespace for FieldML types, evaluators, and imports.
Objects are stored in insertion order. Names must be unique across all object kinds within a region.
FieldML type classes: Ensemble, Continuous, Mesh, Boolean.
BooleanType
dataclass
¶
Boolean type — a two-valued domain.
ContinuousType
dataclass
¶
A continuous (real-valued) type, scalar or with named components.
EnsembleType
dataclass
¶
A finite ordered set of positive integers (element IDs, node IDs, etc.).
MeshType
dataclass
¶
A mesh type — an ensemble of elements paired with a continuous chart (xi).
Evaluator hierarchy for the FieldML semantic model.
AggregateEvaluator
dataclass
¶
Bases: Evaluator
Assemble a value from per-component sub-evaluators.
components is typed Sequence[Evaluator] so that callers can pass a
list of subclasses (list[ConstantEvaluator] etc.) without tripping
list's invariance.
ArgumentEvaluator
dataclass
¶
ConstantEvaluator
dataclass
¶
Evaluator
dataclass
¶
Base class for all FieldML evaluators. Instantiated only via subclasses.
ExternalEvaluator
dataclass
¶
ParameterEvaluator
dataclass
¶
PiecewiseEvaluator
dataclass
¶
Resolution of
Imports can target: - The bundled FieldML standard library (by its canonical URL). - A local file, resolved relative to the importing document's directory.
ImportResolver ¶
Resolves <Import> targets to Region objects.
Builders¶
Mesh builders — one call produces a complete Lagrange mesh graph.
add_hermite_mesh ¶
add_hermite_mesh(
region: Region,
*,
name: str,
nodes: ndarray,
elements: ndarray,
derivatives: ndarray,
scales: ndarray | None = None,
topology: str = "line",
coord_name: str = "coordinates",
) -> tuple[MeshType, ParameterEvaluator]
Add a cubic-Hermite mesh to region.
Supports three topologies
line: 2 DOF kinds/node (value, d/dxi1); 4 DOFs/elem.quad(bicubic): 4 DOF kinds/node (value, d/dxi1, d/dxi2, d2/dxi1dxi2); 16 DOFs/elem.hex(tricubic): 8 DOF kinds/node (value, d/dxi1, d/dxi2, d/dxi3, d2/dxi1dxi2, d2/dxi1dxi3, d2/dxi2dxi3, d3/dxi1dxi2dxi3); 64 DOFs/elem.
DOF convention (CMISS-style per-corner ordering):
Quad per-corner basis DOF order: (value, d/dxi1, d/dxi2, d2/dxi1dxi2).
User-supplied ``derivatives[n]`` has shape ``(3, D)`` with slot order
(d/dxi1, d/dxi2, d2/dxi1dxi2) — matching the basis order minus the value.
Hex per-corner basis DOF order (f_u + 2*f_v + 4*f_w, f in {0,1}):
0: value, 1: d/dxi1, 2: d/dxi2, 3: d2/dxi1dxi2,
4: d/dxi3, 5: d2/dxi1dxi3, 6: d2/dxi2dxi3, 7: d3/dxi1dxi2dxi3.
User-supplied ``derivatives[n]`` has shape ``(7, D)`` with slot order
(d/dxi1, d/dxi2, d/dxi3, d2/dxi1dxi2, d2/dxi1dxi3, d2/dxi2dxi3,
d3/dxi1dxi2dxi3). The evaluator reorders to basis DOF layout at assembly.
Produces
- MeshType(name) with elements + xi chart
- ParameterEvaluator(coord_name) for node coordinates, shape (N_nodes, D)
- ParameterEvaluator(coord_name + '.derivatives'), shape (N_nodes, n_deriv_slots * D) flattened (n_deriv_slots=1 for line, 3 for quad, 7 for hex)
- ParameterEvaluator(coord_name + '.connectivity'), (n_elems, n_per_elem), 1-indexed
- ParameterEvaluator(coord_name + '.scales'), (n_elems, n_dofs_per_elem) for quad/hex (all-ones default); (n_elems, 2) for line (legacy layout)
- ExternalEvaluator naming the basis
For line, scales retain the legacy (n_elems, 2) layout (one scalar per node per element, applied to derivative slots only) for backward compatibility.
add_lagrange_mesh ¶
add_lagrange_mesh(
region: Region,
*,
name: str,
nodes: ndarray,
elements: ndarray,
topology: str,
order: int,
coord_name: str = "coordinates",
) -> tuple[MeshType, ParameterEvaluator]
Add a complete Lagrange mesh to region.
Produces types (ContinuousType for coord value type, two EnsembleTypes, ContinuousType for xi chart, MeshType), a ParameterEvaluator for node coords, a ParameterEvaluator for element→node connectivity (1-indexed), and an ExternalEvaluator naming the Lagrange basis.
Biomechanics-flavored high-level builders over add_lagrange_mesh.
add_fiber_field ¶
add_fiber_field(
region: Region,
*,
mesh_name: str,
vectors: ndarray,
name: str = "fiber_direction",
) -> ParameterEvaluator
Vector field conventionally representing muscle/myocyte fiber directions.
add_landmark_set ¶
add_landmark_set(
region: Region,
*,
name: str,
points: ndarray,
labels: list[str] | None = None,
) -> ParameterEvaluator
Add a named set of anatomical landmarks: (N, 3) points + optional labels.
Labels are stored on the Region as auxiliary metadata (_landmark_labels)
until Phase-6 extends the XML writer to emit them as a FieldML extension.
add_material_field ¶
add_material_field(
region: Region,
*,
mesh_name: str,
values_per_element: ndarray,
name: str = "material",
) -> ParameterEvaluator
Per-element scalar field (e.g. Young's modulus, density).
add_scalar_field ¶
add_scalar_field(
region: Region,
*,
name: str,
mesh_name: str,
values: ndarray,
) -> ParameterEvaluator
Add a per-node scalar field.
values has shape (n_nodes,). mesh_name is the MeshType name
(currently used only to disambiguate; no validation in Phase 5).
add_vector_field ¶
add_vector_field(
region: Region,
*,
name: str,
mesh_name: str,
values: ndarray,
) -> ParameterEvaluator
Add a per-node vector field, shape (n_nodes, D).
Evaluation engine¶
Walk a FieldML evaluator graph and produce numeric values.
evaluate_evaluator ¶
evaluate_evaluator(
ev: Evaluator, ctx: EvaluationContext
) -> Any
Dispatch on evaluator subtype. Returns the numeric value of ev under ctx.
Evaluation-time scope: binding tables, element/xi, free-variable map.
EvaluationContext
dataclass
¶
Scope carried through a single evaluation call.
Basis registry¶
Runtime registry for basis functions.
basis ¶
basis(
name: str, *, topology: str, order: int
) -> Callable[[type[T]], type[T]]
Class decorator: register a basis-function implementation under name.
Linear and quadratic Lagrange basis functions on the standard topologies.
Reference element conventions:
- line: xi in [0, 1]
- tri: unit triangle, vertices (0,0) (1,0) (0,1)
- quad: unit square [0,1]^2, CCW
- tet: unit tet, vertices (0,0,0) (1,0,0) (0,1,0) (0,0,1)
- hex: unit cube [0,1]^3; CMISS node order = lexicographic in (xi1, xi2, xi3)
- wedge: tri x line, i.e. triangle at xi3=0 and triangle at xi3=1
LinearLagrangeHex ¶
LinearLagrangeLine ¶
LinearLagrangeQuad ¶
LinearLagrangeTet ¶
LinearLagrangeTriangle ¶
LinearLagrangeWedge ¶
QuadraticLagrangeHex ¶
Triquadratic Lagrange basis on the unit cube [0,1]^3 (27 nodes).
Nodes arranged 3x3x3 in lexicographic order in (xi1, xi2, xi3): k = i + 3j + 9l where i, j, l in {0, 1, 2}.
QuadraticLagrangeLine ¶
QuadraticLagrangeQuad ¶
Biquadratic Lagrange basis on the unit square [0,1]^2 (9 nodes).
Nodes arranged 3x3 in lexicographic order (xi1 inner, xi2 outer): k = i + 3*j where i, j in {0, 1, 2} correspond to positions {0, 0.5, 1}.
QuadraticLagrangeTet ¶
Quadratic Lagrange basis on the unit tetrahedron (10 nodes).
Node order
0-3: vertices (0,0,0), (1,0,0), (0,1,0), (0,0,1) 4: mid(v0, v1) = (0.5, 0, 0 ) 5: mid(v1, v2) = (0.5, 0.5, 0 ) 6: mid(v0, v2) = (0, 0.5, 0 ) 7: mid(v0, v3) = (0, 0, 0.5) 8: mid(v1, v3) = (0.5, 0, 0.5) 9: mid(v2, v3) = (0, 0.5, 0.5)
QuadraticLagrangeTriangle ¶
Quadratic Lagrange basis on the unit triangle (6 nodes).
shape_derivatives ¶
shape_derivatives(xi: ndarray) -> np.ndarray
Return shape-function derivatives with shape (..., 6, 2).
shape_functions ¶
shape_functions(xi: ndarray) -> np.ndarray
Return shape functions with shape (..., 6).
Node order
0: vertex (0, 0) 1: vertex (1, 0) 2: vertex (0, 1) 3: edge midpoint (0.5, 0) -- between v0 and v1 4: edge midpoint (0.5, 0.5) -- between v1 and v2 5: edge midpoint (0, 0.5) -- between v2 and v0
QuadraticLagrangeWedge ¶
Quadratic Lagrange basis on the wedge/prism (quadratic tri x quadratic line).
Flattening: line outer, tri inner, so node k = l*6 + t where l in {0,1,2} indexes the line nodes at w in {0, 0.5, 1} and t in {0..5} indexes the quadratic triangle nodes (3 vertices + 3 edge midpoints).
Data backends¶
DOM layer¶
DOM layer: XML ↔ lxml tree, versioning, XSD validation, serialization.
ParsedDocument
dataclass
¶
A parsed-but-uninterpreted FieldML document.
Attributes¶
tree
The underlying lxml ElementTree.
version
The FieldML version declared on the root element (@version).
source_file
Absolute path as a string, or None when parsed from a bytes/string source.
parse_file ¶
parse_file(path: PathLike) -> ParsedDocument
Parse a FieldML document from an on-disk file.
parse_string ¶
parse_string(content: str | bytes) -> ParsedDocument
Parse a FieldML document from an in-memory string/bytes.
validate_tree ¶
validate_tree(tree: _ElementTree) -> None
Validate an lxml ElementTree against the bundled FieldML 0.5 XSD.
Raises¶
FieldMLValidationError
If the document fails schema validation. .issues holds one entry
per schema error, each including source line number when available.
write_file ¶
write_file(tree: _ElementTree, path: PathLike) -> None
Serialize tree to path as UTF-8 XML with a trailing newline.
write_string ¶
write_string(tree: _ElementTree) -> bytes
Serialize tree to UTF-8 bytes (with XML declaration).
Interop bridges¶
meshio interop - two-way conversion between FieldML documents and meshio.Mesh.
Lossy in both directions: meshio has no evaluator graphs, and FieldML's arbitrary-basis machinery doesn't map cleanly to meshio's fixed cell types. For v0.4: only Lagrange meshes produced by add_lagrange_mesh are supported.
PyVista interop - convert FieldML documents to VTK UnstructuredGrid.
Only Lagrange meshes produced by add_lagrange_mesh are supported. For
Hermite meshes, sample the reconstructed geometry at node positions and
export a linear-Lagrange representation (loses basis fidelity, preserves
node positions).
plot_doc ¶
plot_doc(doc: Any, **kwargs: Any) -> Any
Render a Document via PyVista. Returns whatever pyvista.plot returns.
plot_field ¶
plot_field(field: Any, doc: Any, **kwargs: Any) -> Any
Shape-aware field plot - scalar/vector dispatch.
doc is passed so we can build the full grid (Field doesn't carry a
Document reference in Phase 2+).
to_pyvista ¶
to_pyvista(doc: Any) -> pyvista.UnstructuredGrid
Convert a pyfieldml.Document to a PyVista UnstructuredGrid.
Write FieldML documents as XDMF3 + HDF5 for ParaView / VisIt consumption.
One-way export. Supports Lagrange meshes produced by add_lagrange_mesh.
Emits:
-
write_xdmf ¶
write_xdmf(doc: Any, path: Any) -> None
Write doc as an XDMF3 descriptor + HDF5 sidecar at path.
scikit-fem bridge — convert a FieldML Lagrange mesh to skfem.Mesh + Basis.
to_scikit_fem ¶
to_scikit_fem(
doc: Any, *, mesh_name: str | None = None
) -> tuple[Any, Any]
Return (skfem.Mesh, skfem.Basis) for the named (or first) mesh.
Phase-4: Lagrange linear meshes only. Raises NotImplementedError for unsupported topology+order combinations.
OpenSim-adjacent export — produce OpenSim-compatible assets from a Document.
Not a full .osim round-trip. Exports mesh geometry (.vtp), landmark sets (CSV), and fiber vector fields as short line glyphs (.vtp polylines) for hand-assembly into OpenSim models.
export_fiber_lines ¶
export_fiber_lines(
doc: Any,
*,
mesh: str | None = None,
field: str,
out_path: Any,
length_scale: float = 0.01,
) -> Path
Export a vector field as short line glyphs (.vtp polylines).
For each mesh node, emit a line segment from the node position along the
local fiber direction. Length = length_scale * bbox_diagonal.
export_geometry ¶
export_geometry(
doc: Any,
out_dir: Any,
*,
filename: str = "geometry.vtp",
) -> Path
Write the document's primary mesh as a VTK PolyData (.vtp) file.
Requires pyfieldml[opensim] (which installs meshio).
export_muscle_attachments ¶
export_muscle_attachments(
doc: Any,
out_path: Any,
*,
landmark_name: str | None = None,
) -> Path
Write a landmark set as CSV: label, x, y, z.
Looks up a ParameterEvaluator whose name contains "landmark" or
"attachment" — or uses landmark_name if provided.
Visualization¶
Jupyter widget: interactive browser of a FieldML document's evaluator graph.
explore ¶
explore(doc: Any) -> Any
Return an ipywidgets layout displaying the evaluator graph.
Three panes
- Left: SelectMultiple of evaluator names.
- Center: ipycytoscape graph with edges from ReferenceEvaluators to their sources.
- Right: HTML detail for the currently-selected node.
Raises ImportError if [viz] extra isn't installed.
Validation¶
Semantic linter over a loaded Document.
Reports issues the XSD cannot catch: - Orphan evaluators (defined but never referenced). - Inverted elements (negative Jacobian at centroid). - Future: unbound arguments, cyclic references, etc.
Semantic diff between two FieldML documents.
Not an XML diff — compares the evaluator-graph structure and parameter array values. Useful for answering "did the mesh change?" or "did the material field differ between these two models?".
Diff
dataclass
¶
Collection of differences between two Documents.
DiffEntry
dataclass
¶
One difference between two Documents.
Attributes¶
kind
Short identifier, e.g. "missing_types", "parameter_values_differ".
message
Human-readable description.
name
Offending object name (if any).
diff_documents ¶
diff_documents(a: Any, b: Any) -> Diff
Return a :class:Diff describing how a differs from b.
Datasets¶
Model zoo - curated FieldML assets for tutorials and research.
Public API
datasets.list() -> list of available dataset names datasets.info(name) -> metadata dict for a dataset datasets.download(name) -> explicit pre-fetch datasets.cache_dir() -> path to the on-disk cache root datasets.load(name) -> pyfieldml.Document datasets.load_unit_cube() -> shortcut for the bundled unit_cube datasets.load_femur() -> anatomical-synthetic femur datasets.load_rectus_femoris() -> synthetic spindle muscle datasets.load_bunny_stanford() -> Stanford Bunny (public domain) datasets.load_femur_bodyparts3d() -> BodyParts3D femur (CC-BY-SA 2.1 JP)
info ¶
info(name: str) -> dict[str, str]
Return metadata (name, license, citation, origin) for name.
load_bunny_stanford ¶
load_bunny_stanford() -> Document
Return the bundled Stanford Bunny Document (public domain triangle mesh).
load_femur ¶
load_femur() -> Document
Return the bundled anatomical-synthetic femur Document.
Produced by a CSG envelope (shaft + femoral head + neck + trochanters + distal condyles) with a BMD-proxy Young's modulus field.
load_femur_bodyparts3d ¶
load_femur_bodyparts3d() -> Document
Return the bundled BodyParts3D femur Document (CC-BY-SA 2.1 JP triangle mesh).
load_rectus_femoris ¶
load_rectus_femoris() -> Document
Return the bundled synthetic rectus_femoris Document (spindle + fiber field).
load_unit_cube ¶
load_unit_cube() -> Document
Return the bundled unit_cube Document (shortcut for load('unit_cube')).