API reference¶
The symbols below are re-exported from the top-level ebsdsim package.
Simulation¶
Public API for EBSD master-pattern generation.
Ångström Cell / Atom in; conversion to nm SimCell happens once in
ebsdsim.crystal.build. Default dynamical solver is Galerkin (RKSM).
- class ebsdsim.api.Atom(element, x, y, z, occupancy=1.0, b_iso=None)[source]¶
Bases:
objectCrystallographic site in fractional coordinates (direct lattice).
- Parameters:
element (str) – Chemical symbol (e.g.
"Ni","Ga").x (float) – Fractional coordinates in the direct unit cell.
y (float) – Fractional coordinates in the direct unit cell.
z (float) – Fractional coordinates in the direct unit cell.
occupancy (float, optional) – Site occupancy in
[0, 1]. Default1.0.b_iso (float or None, optional) – Isotropic Debye–Waller factor in Ų. When
None, a room-temperature default is used during structure-factor evaluation.
- class ebsdsim.api.Cell(a, b, c, alpha=90.0, beta=90.0, gamma=90.0, space_group=1)[source]¶
Bases:
objectUnit-cell lattice parameters (Å and degrees).
- Parameters:
a (float) – Lattice lengths in ångströms.
b (float) – Lattice lengths in ångströms.
c (float) – Lattice lengths in ångströms.
alpha (float, optional) – Interaxial angles in degrees. Default
90.0each.beta (float, optional) – Interaxial angles in degrees. Default
90.0each.gamma (float, optional) – Interaxial angles in degrees. Default
90.0each.space_group (int or str, optional) – International Tables space-group number or Hermann–Mauguin symbol. Default
1(triclinicP1).
- class ebsdsim.api.Material(cell, atoms, name='')[source]¶
Bases:
objectCrystal specification for master-pattern simulation.
- Parameters:
- class ebsdsim.api.MasterPattern(pattern, integrated, n_k, n_sites, metadata=<factory>, bin_patterns=<factory>, bin_voltages_kv=<factory>, bin_weights=<factory>, kij=None, khat=None, pg_num=None, pg_symbol=None, data=<factory>, axes=<factory>)[source]¶
Bases:
objectRasterized master pattern and integration metadata.
patternis the north-hemisphere Lambert raster(side, side)withside = 1 + 2 * halfw, equal todata[energy_int, site_int, 0]. It holds raw dynamical intensities; uselambert_data()for display scaling.datais the dense Lambert tensor(E, S, H, side, side)of raw intensities.integratedandbin_patternsstore fundamental-sector values (flattened(n_k * n_sites,)). Bothlu_smithand Smith returnlen(bin_patterns) == len(bin_voltages_kv); the integrated total is a separate accumulator. Emptybin_patternsis the integrated-only edge case; voltages and weights remain energy-model metadata.kijandkhatgive fundamental-sector pixel indices and unit directions.save/lambert_dataare attached byebsdsim.apiso the engine layer does not importebsdsim.io.- Parameters:
- pattern: NDArray[float32]¶
- integrated: NDArray[float32]¶
- data: NDArray[float32]¶
- __init__(pattern, integrated, n_k, n_sites, metadata=<factory>, bin_patterns=<factory>, bin_voltages_kv=<factory>, bin_weights=<factory>, kij=None, khat=None, pg_num=None, pg_symbol=None, data=<factory>, axes=<factory>)¶
- lambert_data(*, normalize=None, robust_p_low=0.01, robust_p_high=0.99)¶
Expand raw FS intensities to Lambert
(E, S, H, side, side).- Parameters:
normalize ({"minmax", "robust"} or None, optional) – Display scaling mode.
Nonereturns raw intensities unchanged.robust_p_low (float, optional) – Percentile window used when
normalize="robust".robust_p_high (float, optional) – Percentile window used when
normalize="robust".self (MasterPattern)
- Returns:
data (ndarray of float32) – Lambert tensor; see
datafor axis semantics.axes (dict) – Index maps for energy, site, and hemisphere axes.
- Return type:
- save(path)¶
Write this master pattern (with intermediates) to a compressed
.npz.See
ebsdsim.save_master_pattern()for the on-disk format.- Parameters:
self (MasterPattern)
- Return type:
- ebsdsim.api.master_pattern(material, *, voltage_kv=20.0, halfw=500, dmin=0.05, energy_binwidth_keV=1.0, n_trajectories=1048576, sigma_deg=70.0, omega_deg=0.0, solver='galerkin', rank=8, exact_slow_cpu=False, verbosity=0, chunk_size=256, marginal_coverage=1.0, relative_image_stop=0.01, mc_backend='surrogate', bethe_c_strong=20.0, bethe_c_weak=40.0, bethe_c_cutoff=200.0, dbdiff_sg_cutoff=1.0, mc_auto_stop=True, mc_relative_tol=0.01, mc_min_trajectories=1048576, mc_max_trajectories=16777216)[source]¶
Generate an EBSD master pattern from a manual material specification.
Requires a WebGPU-capable GPU. Returns raw dynamical intensities; call
MasterPattern.lambert_data()for display scaling.- Parameters:
material (Material) – Crystal structure and composition.
voltage_kv (float) – Beam energy in kV (default
20).halfw (int) – Lambert half-width; side is
1 + 2 * halfw(default500).dmin (float) – Minimum interplanar spacing in nm (default
0.05).energy_binwidth_keV (float) – Monte Carlo energy-bin width in keV (default
1).n_trajectories (int) – MC trajectories per bin when
mc_auto_stop=False.sigma_deg (float) – Specimen tilt and azimuth (degrees).
omega_deg (float) – Specimen tilt and azimuth (degrees).
solver ({"galerkin", "smith", "lu_smith"}) – Dynamical backend (default
galerkin). The legacy name"smith_iterative"is still accepted as a deprecated alias for"smith".rank (int) – Krylov / Lyapunov rank (default
8for Galerkin;smithrequires16,lu_smithaccepts higher). Galerkin uses a fixed rank for every k-vector; there is no adaptive or per-k rank selection.exact_slow_cpu (bool) – Full-rank CPU Lyapunov instead of GPU Smith.
verbosity ({0, 1, 2}) – Progress reporting level.
chunk_size (int) – GPU batch size for the multi-beam solve.
marginal_coverage (float) – Fraction of the MC energy distribution to integrate.
relative_image_stop (float) – Early-stop threshold on relative image change.
mc_backend ({"surrogate", "gpu"}) – Energy model (default
surrogate).bethe_c_strong (float) – Bethe perturbation cutoffs.
bethe_c_weak (float) – Bethe perturbation cutoffs.
bethe_c_cutoff (float) – Bethe perturbation cutoffs.
dbdiff_sg_cutoff (float) – Structure-factor inclusion threshold.
mc_auto_stop (bool) – Adaptive Monte Carlo trajectory count.
mc_relative_tol (float) – MC convergence tolerance.
mc_min_trajectories (int) – Bounds on adaptive MC trajectory count.
mc_max_trajectories (int) – Bounds on adaptive MC trajectory count.
- Returns:
Lambert-rasterized result with per-bin intermediates and metadata.
- Return type:
See also
- ebsdsim.api.master_pattern_from_cif(path, **kwargs)[source]¶
Generate an EBSD master pattern from a CIF file or bundled preset.
pathmay be a filesystem path or a bundled preset name such as"GaN.cif"or"Ni.cif". The CIF is standardized to the International Tables setting on load (dual-origin groups use origin choice 2).Accepts the same keyword arguments as
master_pattern(). See Simulation parameters for the full parameter reference.- Parameters:
path (str or Path) – CIF file path or preset stem/name.
**kwargs – Forwarded to
master_pattern()/SimParams.
- Returns:
Lambert-rasterized result with per-bin intermediates and metadata.
- Return type:
- Raises:
FileNotFoundError – If
pathdoes not resolve to a file or bundled preset.ValueError – If the CIF is symmetry-inconsistent or the point group cannot be resolved.
Result container¶
MasterPattern is defined in the engine layer
and re-exported from ebsdsim.api.
On-disk format¶
I/O layer: compressed .npz export of master patterns.
The on-disk format stores the fundamental-sector intensities only (the
minimal, symmetry-reduced representation) and is always compressed. Per-energy
bin intensity slices are written when MasterPattern.bin_patterns is
non-empty (len(bin_patterns) == len(bin_voltages_kv) for both lu_smith
and Smith). Smith runs also keep a separate device-accumulated integrated
total; bin_voltages_kv / bin_weights remain the energy-model metadata.
The embedded point-group operators and fundamental-sector normals make the
file self-describing: it can be expanded back into full Lambert hemispheres
with NumPy alone (see ebsdsim.io.load).
Arrays written¶
fundamental_sectorfloat32(n_energy, n_site, n_k)The symmetry-reduced intensities for every direction, packed along an energy axis and a site axis (raw, un-normalized). The energy axis is
1 + n_binslong whenn_bins > 1(index 0 is the energy-integrated weighted sum, index1 + bis binb) and length 1 otherwise (integrated-only whenbin_patternsis empty, or a single stored bin). The site axis is1 + n_siteslong whenn_sites > 1(index 0 is the site mean, index1 + sis sites) and length 1 otherwise. The north/south hemisphere of each of then_kdirections is carried by the sign column offundamental_kij(the per-group N/S split is irregular, so hemisphere is not a separate array axis).fundamental_kijint32(n_k, 3)Lambert pixel indices
(i, j, sign)for each fundamental-sector direction (sign > 0north,sign < 0south).fundamental_khatfloat32(n_k, 3)Unit propagation directions for each fundamental-sector pixel.
pg_operatorsfloat64(n_ops, 3, 3)Proper/improper point-group rotation matrices.
fs_normalsfloat64(n_normals, 3)Inward normals bounding the fundamental sector.
bin_voltages_kv/bin_weightsfloat32(n_energy_bins,)Dynamical voltage (kV) and energy weight of each energy-model bin. When per-bin patterns are stored their count matches this length; an empty
bin_patternslist is the integrated-only edge case (no intensity slices).site_weightsfloat32(n_sites,)Normalized occupancy × multiplicity weights used for the site-integrated marginal (index 0 on the site axis). Per-site slices are raw intensities.
meta_jsonuint8(n_bytes,)UTF-8 JSON metadata blob (decode with
bytes(arr).decode("utf-8")).
- ebsdsim.io.save.cell_metadata(cell)[source]¶
Serialize a
SimCellto a JSON-friendly dict.Per-site isotropic Debye–Waller factors are recorded in both Ų and nm² because they are commonly estimated and materially affect the pattern.
- ebsdsim.io.save.save_master_pattern(mp, path)[source]¶
Write a master pattern (with intermediates) to a compressed
.npz.The file stores symmetry-reduced fundamental-sector intensities plus embedded point-group operators so it can be expanded offline with
ebsdsim.io.load.Per-bin intensity slices are written when
mp.bin_patternsis non-empty (same count contract aslu_smith/ Smith:len(bin_patterns) == len(bin_voltages_kv)). Emptybin_patternswith non-emptybin_voltages_kvremains a legal integrated-only edge case: voltages/weights are energy-model metadata, not a claim that one pattern exists per voltage.- Parameters:
mp (MasterPattern) – Result from
master_pattern()ormaster_pattern_from_cif().path (str or Path) – Output path;
.npzis appended if missing.
- Returns:
Resolved output path.
- Return type:
Path
Loader¶
I/O layer: load master-pattern .npz (raw FS + Lambert expand).
Lambert geometry and display scaling live in ebsdsim.lambert; this module
owns NPZ I/O and the expand-to-Lambert orchestration.
Quick start¶
>>> from ebsdsim.io.load import load_master_pattern, to_uint8, save_png_gray
>>> mp = load_master_pattern("GaN-master-pattern.npz") # raw Lambert data in mp.data
>>> disp, _ = mp.lambert_data(normalize="robust") # display scaling on demand
>>> nh = disp[0, 0, 0] # energy-integrated, site-integrated, north hemisphere
>>> save_png_gray(to_uint8(nh), "GaN_integrated_nh.png")
- class ebsdsim.io.load.LoadedMasterPattern(meta, integrated_fs, bin_fs, kij, khat, pg_operators, fs_normals, bin_voltages_kv, bin_weights, site_weights=None, data=<factory>, axes=<factory>, _maps=<factory>)[source]¶
Bases:
objectMaster pattern loaded from a
.npzfile.metaholds simulation metadata.integrated_fsandbin_fsare fundamental-sector intensities;datais the expanded Lambert tensor of raw values. Seeaxesfor index maps.n_bins == 0(emptybin_fs) means energy-integrated only: voltages and weights describe the energy model but no per-bin intensity slices were stored. Current solvers (lu_smithand Smith) store one pattern per voltage bin;bin_voltages_kv.sizemust not be treated asn_binsfor older integrated-only files.- Parameters:
integrated_fs (NDArray[float32])
bin_fs (NDArray[float32])
kij (NDArray[int32])
khat (NDArray[float32])
pg_operators (NDArray[float64])
fs_normals (NDArray[float64])
bin_voltages_kv (NDArray[float32])
bin_weights (NDArray[float32])
site_weights (NDArray[float32] | None)
data (NDArray[float32])
_maps (dict[bool, tuple[NDArray[float32], NDArray[float32], NDArray[uint8]]])
- integrated_fs: NDArray[float32]¶
- bin_fs: NDArray[float32]¶
- kij: NDArray[int32]¶
- khat: NDArray[float32]¶
- pg_operators: NDArray[float64]¶
- fs_normals: NDArray[float64]¶
- bin_voltages_kv: NDArray[float32]¶
- bin_weights: NDArray[float32]¶
- data: NDArray[float32]¶
- reduce_over_sites(values_fs)[source]¶
Collapse a
(n_k, n_sites)array to one value per direction.- Parameters:
values_fs (NDArray[floating])
- Return type:
NDArray[float32]
- lambert_data(*, normalize=None, robust_p_low=0.01, robust_p_high=0.99)[source]¶
Expand raw FS intensities to Lambert
(E, S, H, side, side).normalizeisNone(raw),"minmax", or"robust". Display scaling is applied on demand only;dataalways stays raw.
- reconstruct(values_fs=None, *, normalize=None, robust_p_low=0.01, robust_p_high=0.99, interp='bilinear')[source]¶
Expand fundamental-sector values into full
(side, side)hemispheres.Returns
(nh, sh). For centrosymmetric groupsshis a copy ofnh. Ifvalues_fsisNonethe integrated pattern is used.
- reconstruct_bin(bin_index, **kwargs)[source]¶
Expand a single per-energy-bin intermediate.
Raises
IndexErrorwhen no per-bin slices were stored (n_bins == 0, integrated-only).
- __init__(meta, integrated_fs, bin_fs, kij, khat, pg_operators, fs_normals, bin_voltages_kv, bin_weights, site_weights=None, data=<factory>, axes=<factory>, _maps=<factory>)¶
- Parameters:
integrated_fs (NDArray[float32])
bin_fs (NDArray[float32])
kij (NDArray[int32])
khat (NDArray[float32])
pg_operators (NDArray[float64])
fs_normals (NDArray[float64])
bin_voltages_kv (NDArray[float32])
bin_weights (NDArray[float32])
site_weights (NDArray[float32] | None)
data (NDArray[float32])
_maps (dict[bool, tuple[NDArray[float32], NDArray[float32], NDArray[uint8]]])
- Return type:
None
- ebsdsim.io.load.load_master_pattern(path)[source]¶
Load an ebsdsim master-pattern
.npz.- Parameters:
path (str or Path) – File written by
ebsdsim.save_master_pattern().- Returns:
Raw Lambert data in
LoadedMasterPattern.data; callLoadedMasterPattern.lambert_data()for display scaling.n_binsis the number of stored intensity slices (0 when the file is integrated-only); do not equate it withbin_voltages_kv.size.- Return type:
Notes
Folding geometry is taken from the stored
pg_operators/fs_normalsarrays (and the orientedmeta['pg_symbol']when present). The loader never recomputes operators from a barepg_num, which would be orientation-ambiguous for some crystal families.
- ebsdsim.io.load.build_master_pattern_data(*, integrated_fs, bin_fs, kij, pg_operators, fs_normals, hw, side, needs_southern_hemisphere, site_weights=None, normalize=None, robust_p_low=0.01, robust_p_high=0.99, interp='bilinear')[source]¶
Expand the fundamental sector into a dense
(E, S, H, side, side)tensor.Axes¶
E(energy):1 + n_binswhenn_bins > 1(index 0 is theenergy-integrated pattern, index
1 + bis binb); otherwise1(integrated-only whenn_bins == 0, or a single stored bin that shares index 0 whenn_bins == 1).S(site):1 + n_siteswhenn_sites > 1(index 0 is thesite-integrated pattern, index
1 + sis sites); otherwise1(the single site).H(hemisphere):2whenneeds_southern_hemisphereelse1(index 0 north, index 1 south).
The point-group pixel-source map is built once per hemisphere and shared across every energy/site channel, so the fundamental sector is expanded without redundant per-channel geometry work.
Returns
(data, axes)whereaxesdocuments the index layout.- Parameters:
integrated_fs (NDArray[floating])
bin_fs (NDArray[floating])
kij (NDArray[integer])
pg_operators (NDArray[floating])
fs_normals (NDArray[floating])
hw (int)
side (int)
needs_southern_hemisphere (bool)
site_weights (NDArray[floating] | None)
normalize (Literal['minmax', 'robust'] | None)
robust_p_low (float)
robust_p_high (float)
interp (Literal['nearest', 'bilinear'])
- Return type:
Display scaling¶
Lambert layer: display normalization (minmax / robust percentiles).
- ebsdsim.lambert.display.scale_fs_channel(vals, normalize, *, robust_p_low=0.01, robust_p_high=0.99)[source]¶
Scale one fundamental-sector channel to
[0, 1]for display.- Parameters:
normalize (Literal['minmax', 'robust'] | None) –
None— return raw values (no scaling)."minmax"— divide by per-channel min/max (lossless up to float precision)."robust"— IQR outlier gate, then percentile window (lossy by default usesrobust_p_low/robust_p_high).robust_p_low (float) – Percentiles in
[0, 1]used only whennormalize="robust".robust_p_high (float) – Percentiles in
[0, 1]used only whennormalize="robust".vals (NDArray[floating])
- Return type:
NDArray[float32]