pyirena 0.3.3__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- pyirena-0.3.3/CHANGELOG.md +317 -0
- pyirena-0.3.3/LICENSE +21 -0
- pyirena-0.3.3/MANIFEST.in +18 -0
- pyirena-0.3.3/PKG-INFO +247 -0
- pyirena-0.3.3/README.md +201 -0
- pyirena-0.3.3/pyirena/__init__.py +62 -0
- pyirena-0.3.3/pyirena/batch.py +1874 -0
- pyirena-0.3.3/pyirena/core/__init__.py +16 -0
- pyirena-0.3.3/pyirena/core/data_merge.py +766 -0
- pyirena-0.3.3/pyirena/core/distributions.py +609 -0
- pyirena-0.3.3/pyirena/core/form_factors.py +644 -0
- pyirena-0.3.3/pyirena/core/modeling.py +1110 -0
- pyirena-0.3.3/pyirena/core/scattering_contrast.py +679 -0
- pyirena-0.3.3/pyirena/core/simple_fits.py +983 -0
- pyirena-0.3.3/pyirena/core/sizes.py +1207 -0
- pyirena-0.3.3/pyirena/core/unified.py +636 -0
- pyirena-0.3.3/pyirena/core/waxs_peakfit.py +1044 -0
- pyirena-0.3.3/pyirena/examples/__init__.py +10 -0
- pyirena-0.3.3/pyirena/examples/basic_demo.py +386 -0
- pyirena-0.3.3/pyirena/gui/__init__.py +26 -0
- pyirena-0.3.3/pyirena/gui/contrast_panel.py +1572 -0
- pyirena-0.3.3/pyirena/gui/data_merge_panel.py +1594 -0
- pyirena-0.3.3/pyirena/gui/data_selector.py +4136 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/__init__.py +32 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/collect_window.py +234 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/export.py +355 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/file_tree.py +398 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/graph_window.py +581 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/hdf5_browser.py +417 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/main_window.py +569 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/multi_collect_window.py +201 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/plot_controls.py +951 -0
- pyirena-0.3.3/pyirena/gui/hdf5viewer/pyirena_readers.py +579 -0
- pyirena-0.3.3/pyirena/gui/launch.py +27 -0
- pyirena-0.3.3/pyirena/gui/modeling_panel.py +2570 -0
- pyirena-0.3.3/pyirena/gui/sas_plot.py +660 -0
- pyirena-0.3.3/pyirena/gui/simple_fits_panel.py +1439 -0
- pyirena-0.3.3/pyirena/gui/sizes_panel.py +2583 -0
- pyirena-0.3.3/pyirena/gui/unified_fit.py +3701 -0
- pyirena-0.3.3/pyirena/gui/unified_fit_matplotlib_old.py +973 -0
- pyirena-0.3.3/pyirena/gui/waxs_peakfit_panel.py +2183 -0
- pyirena-0.3.3/pyirena/io/__init__.py +19 -0
- pyirena-0.3.3/pyirena/io/contrast_io.py +373 -0
- pyirena-0.3.3/pyirena/io/hdf5.py +873 -0
- pyirena-0.3.3/pyirena/io/nxcansas_data_merge.py +242 -0
- pyirena-0.3.3/pyirena/io/nxcansas_modeling.py +309 -0
- pyirena-0.3.3/pyirena/io/nxcansas_simple_fits.py +281 -0
- pyirena-0.3.3/pyirena/io/nxcansas_sizes.py +291 -0
- pyirena-0.3.3/pyirena/io/nxcansas_unified.py +391 -0
- pyirena-0.3.3/pyirena/io/nxcansas_waxs_peakfit.py +334 -0
- pyirena-0.3.3/pyirena/io/results.py +347 -0
- pyirena-0.3.3/pyirena/plotting/__init__.py +28 -0
- pyirena-0.3.3/pyirena/plotting/plot_saxs.py +398 -0
- pyirena-0.3.3/pyirena/plotting/unified_plots.py +397 -0
- pyirena-0.3.3/pyirena/py.typed +1 -0
- pyirena-0.3.3/pyirena/state/__init__.py +9 -0
- pyirena-0.3.3/pyirena/state/state_manager.py +654 -0
- pyirena-0.3.3/pyirena/tests/__init__.py +6 -0
- pyirena-0.3.3/pyirena/tests/test_sizes.py +384 -0
- pyirena-0.3.3/pyirena/tests/test_unified.py +172 -0
- pyirena-0.3.3/pyirena.egg-info/PKG-INFO +247 -0
- pyirena-0.3.3/pyirena.egg-info/SOURCES.txt +68 -0
- pyirena-0.3.3/pyirena.egg-info/dependency_links.txt +1 -0
- pyirena-0.3.3/pyirena.egg-info/entry_points.txt +6 -0
- pyirena-0.3.3/pyirena.egg-info/requires.txt +20 -0
- pyirena-0.3.3/pyirena.egg-info/top_level.txt +1 -0
- pyirena-0.3.3/pyproject.toml +90 -0
- pyirena-0.3.3/requirements.txt +12 -0
- pyirena-0.3.3/setup.cfg +4 -0
- pyirena-0.3.3/setup.py +11 -0
|
@@ -0,0 +1,317 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
## Released as first beta
|
|
9
|
+
|
|
10
|
+
## [0.3.2] - 2026-04-05 — First public beta
|
|
11
|
+
|
|
12
|
+
First beta release published to PyPI. Install with `pip install pyirena[gui]`.
|
|
13
|
+
|
|
14
|
+
### Added
|
|
15
|
+
|
|
16
|
+
#### Cylinder form factors for Modeling tool
|
|
17
|
+
Two new form factor entries for disk-like and rod-like particles:
|
|
18
|
+
|
|
19
|
+
- **Cylinder (Aspect Ratio)** (`cylinder_ar`): half-length L = AR·R, where R is the
|
|
20
|
+
radius from the distribution. Disk-like for AR < 1, rod-like for AR > 1.
|
|
21
|
+
- **Cylinder (Length)** (`cylinder_length`): fixed total height H [Å], independent of
|
|
22
|
+
radius. Volume scales as R² (not R³).
|
|
23
|
+
- Derived quantities (Rg, specific surface) use cylinder geometry.
|
|
24
|
+
- Orientationally-averaged form factor via 50-point Gauss-Legendre quadrature.
|
|
25
|
+
|
|
26
|
+
#### Core-shell form factors for Modeling tool
|
|
27
|
+
Five core-shell form factor variants with three polydispersity modes, following the
|
|
28
|
+
Igor Pro implementation:
|
|
29
|
+
|
|
30
|
+
- **Core-Shell Sphere** — by core R, by shell thickness, or by total R.
|
|
31
|
+
- **Core-Shell Spheroid** — by core R or by total R (with shared aspect ratio).
|
|
32
|
+
- SLD parameters (sld_core, sld_shell, sld_solvent in 10⁻⁶ Å⁻²) replace the scalar
|
|
33
|
+
contrast parameter, which is automatically locked to 1.0 and hidden in the GUI.
|
|
34
|
+
- SLD-contrast-weighted Rg; specific surface based on outer radius (Porod law).
|
|
35
|
+
- Volume convention: `scale` and `volume_fraction` are based on total particle volume
|
|
36
|
+
(core + shell together), not core-only. Documented in code and user guide.
|
|
37
|
+
|
|
38
|
+
#### Modeling GUI — standard buttons
|
|
39
|
+
Added standard buttons matching other tools (Simple Fits, Unified Fit, Sizes):
|
|
40
|
+
|
|
41
|
+
- **Results to graph** (#81c784 green) — annotate I(Q) plot with fitted parameter values.
|
|
42
|
+
- **Save State** (#3498db blue) — save current parameters to state file.
|
|
43
|
+
- **Import Parameters** (lightgreen) — import from pyIrena JSON config file.
|
|
44
|
+
- **Reset to Defaults** (#e67e22 orange) — reset all populations to default values.
|
|
45
|
+
- **Store in File** / **Export Parameters** renamed and recoloured to match standard.
|
|
46
|
+
- Auto-save state on window close (`closeEvent`).
|
|
47
|
+
|
|
48
|
+
### Fixed
|
|
49
|
+
|
|
50
|
+
- **Modeling "Open..." button**: loading a new file now clears all previous data, model
|
|
51
|
+
curves, distributions, residuals, and annotations from the graph. Previously old items
|
|
52
|
+
persisted because `graph_model()` and `_on_fit_complete()` bypassed the data tracking.
|
|
53
|
+
- **Modeling `load_file()`**: replaced nonexistent `load_nxcansas` import with the correct
|
|
54
|
+
`readGenericNXcanSAS` function from `pyirena.io.hdf5`.
|
|
55
|
+
- **Core-shell G-matrix units**: corrected from `F²×1e-16` to `F²/V_total×1e-4`. The old
|
|
56
|
+
formula double-counted the SLD unit conversion and missed the division by particle
|
|
57
|
+
volume, causing intensities ~10⁶ times too low.
|
|
58
|
+
|
|
59
|
+
## [0.2.1] - 2026-03-20
|
|
60
|
+
|
|
61
|
+
### Added
|
|
62
|
+
|
|
63
|
+
#### Modeling tool — parametric size-distribution fitting
|
|
64
|
+
New analysis tool for forward-modelling small-angle scattering data using
|
|
65
|
+
parametric size distributions, Unified Fit levels, and diffraction peaks.
|
|
66
|
+
|
|
67
|
+
- **5 distribution functions**: Gaussian, LogNormal (3-parameter shifted), LSW,
|
|
68
|
+
Schulz-Zimm (Gamma), Ardell — Igor-style CDF-inversion radius grid.
|
|
69
|
+
- **3 population types** combinable in up to 5 simultaneous populations:
|
|
70
|
+
- `SizeDistPopulation`: distribution × form factor (sphere, spheroid) × optional
|
|
71
|
+
structure factor (interferences / hard-sphere Percus-Yevick).
|
|
72
|
+
- `UnifiedLevelPopulation`: Beaucage Unified level G·exp(−q²Rg²/3) + B·Q*⁻ᴾ
|
|
73
|
+
with optional Born-Green correlations.
|
|
74
|
+
- `DiffractionPeakPopulation`: Gaussian, Lorentzian, or pseudo-Voigt peak at Q₀.
|
|
75
|
+
- **Engine** (`pyirena/core/modeling.py`): `ModelingEngine` with G-matrix caching,
|
|
76
|
+
`scipy.optimize.least_squares` (TRF) or Nelder-Mead fitting, and MC uncertainty.
|
|
77
|
+
- **HDF5 I/O** (`pyirena/io/nxcansas_modeling.py`): save/load for all population types.
|
|
78
|
+
- **GUI panel** (`pyirena/gui/modeling_panel.py`): multi-tab population editor,
|
|
79
|
+
I(Q) log-log plot with per-population overlays, distribution preview, Export/Import
|
|
80
|
+
Parameters, and MC uncertainty estimation.
|
|
81
|
+
- **Batch API** (`pyirena/batch.py`): `fit_modeling()` headless fitting function;
|
|
82
|
+
registered in `fit_pyirena()` under the `modeling` config key.
|
|
83
|
+
- **Data Selector** integration: Modeling (GUI/script) buttons at row 4.
|
|
84
|
+
|
|
85
|
+
#### Data Merge tool — SAXS/WAXS merging
|
|
86
|
+
New tool for merging two SAS datasets (e.g. SAXS + WAXS) onto a common Q scale.
|
|
87
|
+
|
|
88
|
+
- **Engine** (`pyirena/core/data_merge.py`): Nelder-Mead optimisation of scale factor,
|
|
89
|
+
flat background (DS1), and optional Q-shift; log-log linear interpolation in the
|
|
90
|
+
overlap region.
|
|
91
|
+
- **HDF5 I/O** (`pyirena/io/nxcansas_data_merge.py`): copies DS1 NXcanSAS file and
|
|
92
|
+
replaces Q/I/Idev/Qdev with merged data; appends `entry/data_merge_results`.
|
|
93
|
+
- **GUI panel** (`pyirena/gui/data_merge_panel.py`): dual dataset loader, SAXS/WAXS
|
|
94
|
+
plot mode toggle, cursor-driven overlap range, optimisation controls, and batch mode.
|
|
95
|
+
- **Batch API**: `merge_data()` headless merge function.
|
|
96
|
+
- **CLI entry point**: `pyirena-datamerge` console script.
|
|
97
|
+
|
|
98
|
+
#### Scattering Contrast Calculator
|
|
99
|
+
New tool for computing X-ray and neutron scattering length densities and contrast.
|
|
100
|
+
|
|
101
|
+
- Compound-level SLD calculation from chemical formula, density, and X-ray energy.
|
|
102
|
+
- Supports neutron SLDs with isotope substitution.
|
|
103
|
+
- Phase-pair contrast (ΔρX)² and (ΔρN)² tables.
|
|
104
|
+
- **GUI panel** (`pyirena/gui/contrast_panel.py`) with compound library, interactive
|
|
105
|
+
crosshair energy cursor, and JPEG export.
|
|
106
|
+
- **CLI entry point**: `pyirena-contrast` console script.
|
|
107
|
+
|
|
108
|
+
### Fixed
|
|
109
|
+
|
|
110
|
+
- **`fit_modeling` batch function**: previously only deserialized `SizeDistPopulation`
|
|
111
|
+
from config; now correctly rebuilds `UnifiedLevelPopulation` and
|
|
112
|
+
`DiffractionPeakPopulation` via `pop_type` dispatch.
|
|
113
|
+
- **`fit_pyirena`**: `modeling` config key was missing from `_TOOL_REGISTRY`; added
|
|
114
|
+
so `fit_pyirena()` automatically runs `fit_modeling()` when a `modeling` section is
|
|
115
|
+
present in the config file.
|
|
116
|
+
- **`pyirena/__init__.py`**: `__version__` was not updated from 0.1.1; now kept in
|
|
117
|
+
sync with `pyproject.toml`.
|
|
118
|
+
|
|
119
|
+
## [0.1.2] - 2026-02-22
|
|
120
|
+
|
|
121
|
+
### Added
|
|
122
|
+
|
|
123
|
+
#### Simple Fits tool — 13 single-model analytical fits
|
|
124
|
+
New analysis tool ported from Igor Pro `IR3_SimpleFits.ipf` and
|
|
125
|
+
`IR3_SystemSpecificModels.ipf`. Provides direct analytical model fitting with
|
|
126
|
+
linearization plots, Monte Carlo uncertainty estimation, and full HDF5 I/O.
|
|
127
|
+
|
|
128
|
+
**Core (`pyirena/core/simple_fits.py`)**
|
|
129
|
+
- `SimpleFitModel` dataclass: holds model name, parameters, limits, and complex-background
|
|
130
|
+
flag; provides `fit(q, I, dI)`, `to_dict()`, `from_dict()`.
|
|
131
|
+
- `MODEL_REGISTRY` dict mapping every model name to its parameter definitions, formula
|
|
132
|
+
function, linearization type, and complex-background flag.
|
|
133
|
+
- 13 supported models (parameter names in parentheses):
|
|
134
|
+
|
|
135
|
+
| Model | Parameters | Linearization |
|
|
136
|
+
|-------|-----------|---------------|
|
|
137
|
+
| Guinier | I0, Rg | ln(I) vs Q² |
|
|
138
|
+
| Guinier Rod | I0, Rc | ln(QI) vs Q² |
|
|
139
|
+
| Guinier Sheet | I0, Rg | ln(Q²I) vs Q² |
|
|
140
|
+
| Porod | Kp, Background | IQ⁴ vs Q⁴ |
|
|
141
|
+
| Power Law | P, Exponent, Background | — |
|
|
142
|
+
| Sphere | Scale, R | — |
|
|
143
|
+
| Spheroid | Scale, R, Beta | — |
|
|
144
|
+
| Debye-Bueche | Prefactor, Eta, CorrLength | — |
|
|
145
|
+
| Treubner-Strey | Prefactor, A, C1, C2 | — |
|
|
146
|
+
| Benedetti-Ciccariello | SolidSLD, VoidSLD, LayerSLD, Sp, t | — |
|
|
147
|
+
| Hermans | B, s, d1, d2, sigma1, sigma2 | — |
|
|
148
|
+
| Hybrid Hermans | Hermans params + G2, Rg2, G3, Rg3, B3, P3 | — |
|
|
149
|
+
| Unified Born Green | G1, Rg1, B1, P1, G2, Rg2, B2, P2, eta, ksi | — |
|
|
150
|
+
|
|
151
|
+
- Optional complex background `BG_A·Q⁻ⁿ + BG_flat` on all models except Porod and
|
|
152
|
+
Power Law (which have an explicit flat Background parameter).
|
|
153
|
+
- Sphere uses Gauss-Legendre quadrature orientational average for efficiency.
|
|
154
|
+
- Treubner-Strey derives correlation length ξ and repeat distance d from fit params.
|
|
155
|
+
- Guinier Sheet derives layer thickness from Rg.
|
|
156
|
+
- `fit()` uses `scipy.optimize.curve_fit`; returns chi², reduced chi², DOF,
|
|
157
|
+
`params_std` (from covariance diagonal), `residuals`, and model-specific `derived`.
|
|
158
|
+
|
|
159
|
+
**HDF5 I/O (`pyirena/io/nxcansas_simple_fits.py`)**
|
|
160
|
+
- `save_simple_fit_results(filepath, result, model_obj, intensity_data, intensity_error)`:
|
|
161
|
+
writes/overwrites `entry/simple_fit_results` NXprocess group.
|
|
162
|
+
- `load_simple_fit_results(filepath)`: loads all fit scalars, arrays, params, params_std,
|
|
163
|
+
and derived quantities.
|
|
164
|
+
- `print_simple_fit_results(result)`: formatted console summary.
|
|
165
|
+
|
|
166
|
+
**GUI panel (`pyirena/gui/simple_fits_panel.py`)**
|
|
167
|
+
- Three-panel layout: I(Q) log-log + model overlay (with cursor-selectable Q range),
|
|
168
|
+
normalised residuals, linearization plot (Guinier/Porod families only).
|
|
169
|
+
- Cursor-driven Q range selection linked to the I(Q) plot.
|
|
170
|
+
- Per-parameter widgets: value, lower/upper limits, "Fit?" checkbox; "No Limits" toggle.
|
|
171
|
+
- Complex background checkbox: adds BG_A, BG_n, BG_flat sub-parameters.
|
|
172
|
+
- **Fit** button: runs `SimpleFitModel.fit()`, displays results with ± uncertainties.
|
|
173
|
+
- **Calculate Uncertainty** button: Monte Carlo loop (configurable N runs); updates ± labels.
|
|
174
|
+
- **Store in File** button: saves results to HDF5.
|
|
175
|
+
- **Export / Import Parameters** buttons: read/write `simple_fits` section in a shared
|
|
176
|
+
`pyirena_config.json` (interoperable with Unified Fit and Sizes config files).
|
|
177
|
+
- Linearization panel shows transformed data + linear fit + intercept annotation for
|
|
178
|
+
Guinier/Porod models; shows "No linearization available" for other models.
|
|
179
|
+
- Highlighted Q-range band on linearization scatter plot.
|
|
180
|
+
- State fully persisted via `StateManager`; stale parameters removed on model change.
|
|
181
|
+
|
|
182
|
+
**Batch API (`pyirena/batch.py`)**
|
|
183
|
+
- `fit_simple(data_file, config, with_uncertainty, n_mc_runs, q_min, q_max)`: headless
|
|
184
|
+
fitting from a `SimpleFitModel` or plain dict config; saves results to HDF5.
|
|
185
|
+
- `fit_simple_from_config(data_file, config_file, save_to_nexus, ...)`: wrapper that
|
|
186
|
+
reads the `simple_fits` section of a `pyirena_config.json` (normalises GUI state-dict
|
|
187
|
+
keys, extracts q_min/q_max) and calls `fit_simple()`.
|
|
188
|
+
- `fit_pyirena()` now dispatches `simple_fits` config sections to `fit_simple_from_config()`.
|
|
189
|
+
- `fit_simple` exported from `pyirena.__init__`.
|
|
190
|
+
|
|
191
|
+
**Data Selector integration (`pyirena/gui/data_selector.py`)**
|
|
192
|
+
- **"Simple Fits"** checkbox added alongside Data / Unified Fit / Size Dist. checkboxes.
|
|
193
|
+
- *Create Graph*: opens `SimpleFitResultsWindow` (I(Q) + model + residuals, matching
|
|
194
|
+
colour scheme to the dataset; model line uses `color.darker(280)` for clear contrast).
|
|
195
|
+
- *Create Report*: loads `simple_fit_results` from HDF5; adds "## Simple Fits" section
|
|
196
|
+
with model name, chi², reduced chi², DOF, Q range, all parameters ± std, derived quantities.
|
|
197
|
+
- *Tabulate Results*: adds `SF_model`, `SF_chi2`, `SF_reduced_chi2`, `SF_dof`,
|
|
198
|
+
`SF_q_min`, `SF_q_max`, `SF_use_complex_bg`, `SF_<param>`, `SF_<param>_std`, and
|
|
199
|
+
`SF_derived_<name>` columns (dynamic — adapts to the parameters of the fitted model).
|
|
200
|
+
- **"Simple Fits (script)"** batch button now correctly calls `fit_simple_from_config()`
|
|
201
|
+
and saves results to the HDF5 file (was falling through to fit_sizes with no save).
|
|
202
|
+
|
|
203
|
+
#### Public API
|
|
204
|
+
- **`load_result(filepath, analysis)`** (`pyirena/io/results.py`) — importable directly
|
|
205
|
+
as `from pyirena import load_result`. Pass a file path and an analysis name
|
|
206
|
+
(`'unified_fit'`, `'size_distribution'`, or `'simple_fits'`) to retrieve a fully
|
|
207
|
+
documented result dict. Returns a safe empty structure (`found=False`) if results
|
|
208
|
+
are absent — no exception raised.
|
|
209
|
+
- `SUPPORTED_ANALYSES` tuple exported from `pyirena`.
|
|
210
|
+
|
|
211
|
+
#### Plot improvements (all panels)
|
|
212
|
+
- **Phantom-point fix** (I(Q) graph, Unified Fit, Size Distribution): error bar tops
|
|
213
|
+
clipped at `min(I·1000, P99(I)·1000)` — prevents cosmic rays or WAXS peaks at
|
|
214
|
+
extreme intensities from driving the y-axis to 10³⁸.
|
|
215
|
+
- **ViewBox hard limits**: y-axis locked to ±3 decades beyond the 99th-percentile data
|
|
216
|
+
range; x-axis locked to the nearest full decade beyond the data Q range ±1 extra
|
|
217
|
+
decade. Prevents accidental zoom-out to empty space.
|
|
218
|
+
- **x-axis zoom constraint**: applied to Simple Fits, Size Distribution, and Unified Fit
|
|
219
|
+
panels. Example: data 0.003–0.8 Å⁻¹ → zoom limits 0.0001–10 Å⁻¹.
|
|
220
|
+
|
|
221
|
+
### Fixed
|
|
222
|
+
- **Data Selector sort order**: the saved "Sort" pulldown state is now applied to the
|
|
223
|
+
file list immediately on startup (was restored to the combo but the list remained
|
|
224
|
+
alphabetical until the user manually changed the setting).
|
|
225
|
+
- **Report generation** (Size Distribution): section now reads scalar parameters from
|
|
226
|
+
the flat dict returned by `load_sizes_results()` (no longer looks for a non-existent
|
|
227
|
+
nested `'params'` key). Previously all parameters showed as `nan`/`unknown`.
|
|
228
|
+
- **Report generation** (Size Distribution): now includes all stored parameters:
|
|
229
|
+
contrast, aspect ratio, log spacing, background, error scale, power law B/P, Q range,
|
|
230
|
+
n_iterations, plus method-specific sub-tables for MaxEnt, Regularization, TNNLS, and
|
|
231
|
+
Monte Carlo.
|
|
232
|
+
|
|
233
|
+
## [0.1.1] - 2026-02-19
|
|
234
|
+
|
|
235
|
+
### Added
|
|
236
|
+
|
|
237
|
+
#### Size Distribution — Complex Background Model
|
|
238
|
+
- `SizesDistribution.compute_complex_background(q)`: evaluates `B·q⁻ᴾ + background`
|
|
239
|
+
for arbitrary q arrays.
|
|
240
|
+
- `SizesDistribution.fit_power_law(q, I, q_min, q_max, fit_B, fit_P)`: fits the
|
|
241
|
+
power-law amplitude B and/or exponent P to a user-selected Q range using
|
|
242
|
+
`scipy.optimize.curve_fit`.
|
|
243
|
+
- `SizesDistribution.fit_background_term(q, I, q_min, q_max)`: estimates the flat
|
|
244
|
+
background by averaging `I − B·q⁻ᴾ` in a selected Q range.
|
|
245
|
+
- New class attributes `power_law_B` and `power_law_P`; `fit()` now subtracts the
|
|
246
|
+
full complex background before inverting, and returns `n_data` in the result dict.
|
|
247
|
+
|
|
248
|
+
#### Size Distribution GUI (`sizes_panel.py`)
|
|
249
|
+
- **Background tab**: new panel tab with "Power-Law Term B·q⁻ᴾ" and "Flat Background"
|
|
250
|
+
groups; each has its own Q-range fields, "Set Q from cursors" button, and individual
|
|
251
|
+
fit buttons ("Fit P/B", "Fit Background").
|
|
252
|
+
- **"Fit Sizes" / "Fit All"** buttons: "Fit All" runs power-law fit → background fit
|
|
253
|
+
→ size distribution fit sequentially in one click.
|
|
254
|
+
- **Corrected-data overlay**: I(Q) − complex background shown as blue triangles on the
|
|
255
|
+
main graph, limited to the cursor Q range; complex background shown as a dashed grey
|
|
256
|
+
line.
|
|
257
|
+
- **"Calculate Uncertainty (MC)"** button: runs 10 Monte-Carlo fits on
|
|
258
|
+
Gaussian-perturbed data; reports per-bin mean/std of the distribution as error bars,
|
|
259
|
+
and propagates Rg, Vf, and peak-r uncertainties with ± notation in the Results box.
|
|
260
|
+
- **"Export Parameters" / "Import Parameters"** buttons: save and load all Sizes
|
|
261
|
+
parameters to/from a `pyirena_config.json` file sharing the same `_pyirena_config`
|
|
262
|
+
envelope used by Unified Fit (files are interoperable between tools).
|
|
263
|
+
- **Layout improvements**:
|
|
264
|
+
- Q min and Q max shown on one row in the Q Range group.
|
|
265
|
+
- Number-of-bins spinbox and "Logarithmic spacing" checkbox share one row.
|
|
266
|
+
- MaxEnt, Regularization, and TNNLS sub-controls each condensed to a single row.
|
|
267
|
+
- Results box condensed to two rows (χ²/Vf and Rg/Peak r).
|
|
268
|
+
- **Finer mouse-wheel steps** for Error scale: `ScrubbableLineEdit` now accepts a
|
|
269
|
+
`step_factor` parameter (default 0.1); Error scale uses 0.02 for precise control.
|
|
270
|
+
- **Fit curve** rendered with `width=4` pen and plotted on top of all other items.
|
|
271
|
+
- **Error scale live preview**: changing the Error scale field immediately redraws the
|
|
272
|
+
error bars without requiring a new fit.
|
|
273
|
+
|
|
274
|
+
#### Batch API (`batch.py`)
|
|
275
|
+
- `fit_sizes(data_file, config_file, save_to_nexus=True)`: headless size-distribution
|
|
276
|
+
fitting function analogous to `fit_unified()`. Reads a `'sizes'` group from a
|
|
277
|
+
pyIrena config JSON, applies the saved cursor Q range, runs the fit, optionally saves
|
|
278
|
+
results to NXcanSAS HDF5, and returns a structured result dict.
|
|
279
|
+
- `fit_pyirena()` now automatically dispatches to `fit_sizes()` when a config file
|
|
280
|
+
contains a `'sizes'` group.
|
|
281
|
+
- `fit_sizes` added to the public API (`pyirena.__init__`).
|
|
282
|
+
|
|
283
|
+
#### Data Selector (`data_selector.py`)
|
|
284
|
+
- **"Size Dist." checkbox** added next to the existing "Data" and "Unified Fit"
|
|
285
|
+
checkboxes.
|
|
286
|
+
- *Create Graph*: if checked, opens the Size Distribution panel with the selected
|
|
287
|
+
file's data.
|
|
288
|
+
- *Create Report*: if checked, loads stored size-distribution results from HDF5 and
|
|
289
|
+
includes a "## Size Distribution" section (chi², Vf, Rg, peak r, method, shape,
|
|
290
|
+
residuals stats) in the Markdown report.
|
|
291
|
+
|
|
292
|
+
#### State management (`state_manager.py`)
|
|
293
|
+
- `DEFAULT_STATE["sizes"]` extended with `power_law_B`, `power_law_P`,
|
|
294
|
+
`power_law_q_min`, `power_law_q_max`, `background_q_min`, `background_q_max`.
|
|
295
|
+
- Schema migration from version 1 → 2 resets `n_bins` (50 → 200), `log_spacing`
|
|
296
|
+
(False → True), and initialises `error_scale` on old saved states.
|
|
297
|
+
|
|
298
|
+
### Changed
|
|
299
|
+
- `SizesDistribution.fit()` now subtracts the complex background `B·q⁻ᴾ + background`
|
|
300
|
+
(previously only the flat background was removed).
|
|
301
|
+
- Default `n_bins` changed from 50 to 200 and `log_spacing` from False to True
|
|
302
|
+
(better resolution for typical SAXS size distributions); old saved states are
|
|
303
|
+
migrated automatically via `schema_version`.
|
|
304
|
+
- Sizes panel minimum width increased to 420 px to accommodate the wider layout.
|
|
305
|
+
|
|
306
|
+
## [0.1.0] - 2024-02-13
|
|
307
|
+
|
|
308
|
+
### Added
|
|
309
|
+
- Initial release of pyIrena
|
|
310
|
+
- Unified Fit model for small-angle scattering analysis
|
|
311
|
+
- Support for multi-level hierarchical structures
|
|
312
|
+
- Mass fractal mode
|
|
313
|
+
- Correlation function (Born-Green approximation)
|
|
314
|
+
- Parameter linking capabilities
|
|
315
|
+
- NXcanSAS HDF5 file support
|
|
316
|
+
- Basic plotting and analysis utilities
|
|
317
|
+
- Comprehensive documentation and examples
|
pyirena-0.3.3/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2024 Jan Ilavsky
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
# Include documentation files
|
|
2
|
+
include README.md
|
|
3
|
+
include LICENSE
|
|
4
|
+
include CHANGELOG.md
|
|
5
|
+
include requirements.txt
|
|
6
|
+
|
|
7
|
+
# Include examples
|
|
8
|
+
recursive-include pyirena/examples *.py *.ipynb *.md
|
|
9
|
+
|
|
10
|
+
# Include tests
|
|
11
|
+
recursive-include pyirena/tests *.py
|
|
12
|
+
|
|
13
|
+
# Exclude unnecessary files
|
|
14
|
+
global-exclude *.pyc
|
|
15
|
+
global-exclude *.pyo
|
|
16
|
+
global-exclude __pycache__
|
|
17
|
+
global-exclude .DS_Store
|
|
18
|
+
global-exclude *.ipf
|
pyirena-0.3.3/PKG-INFO
ADDED
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: pyirena
|
|
3
|
+
Version: 0.3.3
|
|
4
|
+
Summary: Python tools for small-angle scattering data analysis.
|
|
5
|
+
Author-email: Jan Ilavsky <ilavsky@anl.gov>
|
|
6
|
+
Maintainer-email: Jan Ilavsky <ilavsky@anl.gov>
|
|
7
|
+
License: MIT
|
|
8
|
+
Project-URL: Homepage, https://github.com/jilavsky/pyirena
|
|
9
|
+
Project-URL: Documentation, https://github.com/jilavsky/pyirena/tree/main/docs
|
|
10
|
+
Project-URL: Repository, https://github.com/jilavsky/pyirena
|
|
11
|
+
Project-URL: Changelog, https://github.com/jilavsky/pyirena/blob/main/CHANGELOG.md
|
|
12
|
+
Project-URL: Bug Tracker, https://github.com/jilavsky/pyirena/issues
|
|
13
|
+
Keywords: SAXS,SANS,USAXS,small-angle scattering,unified fit,Beaucage,X-ray scattering,neutron scattering,SAS,size distribution,core-shell,form factor
|
|
14
|
+
Classifier: Development Status :: 4 - Beta
|
|
15
|
+
Classifier: Intended Audience :: Science/Research
|
|
16
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
17
|
+
Classifier: Programming Language :: Python :: 3
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
23
|
+
Classifier: Topic :: Scientific/Engineering :: Physics
|
|
24
|
+
Classifier: Topic :: Scientific/Engineering :: Chemistry
|
|
25
|
+
Requires-Python: >=3.9
|
|
26
|
+
Description-Content-Type: text/markdown
|
|
27
|
+
License-File: LICENSE
|
|
28
|
+
Requires-Dist: numpy>=1.22.0
|
|
29
|
+
Requires-Dist: scipy>=1.8.0
|
|
30
|
+
Requires-Dist: h5py>=3.0.0
|
|
31
|
+
Provides-Extra: gui
|
|
32
|
+
Requires-Dist: matplotlib>=3.5.0; extra == "gui"
|
|
33
|
+
Requires-Dist: PySide6>=6.4.0; extra == "gui"
|
|
34
|
+
Requires-Dist: pyqtgraph>=0.13.0; extra == "gui"
|
|
35
|
+
Requires-Dist: xraydb>=4.5; extra == "gui"
|
|
36
|
+
Requires-Dist: periodictable>=1.7; extra == "gui"
|
|
37
|
+
Provides-Extra: dev
|
|
38
|
+
Requires-Dist: pytest>=7.0; extra == "dev"
|
|
39
|
+
Requires-Dist: pytest-cov; extra == "dev"
|
|
40
|
+
Requires-Dist: build; extra == "dev"
|
|
41
|
+
Requires-Dist: twine; extra == "dev"
|
|
42
|
+
Provides-Extra: all
|
|
43
|
+
Requires-Dist: pyirena[gui]; extra == "all"
|
|
44
|
+
Requires-Dist: pyirena[dev]; extra == "all"
|
|
45
|
+
Dynamic: license-file
|
|
46
|
+
|
|
47
|
+
# pyIrena
|
|
48
|
+
|
|
49
|
+
> Coded by Claude from SAXS_IgorCode Irena. Planned, defined, debugged and validated by Jan Ilavsky.
|
|
50
|
+
|
|
51
|
+
Python tools for small-angle scattering (SAS) data analysis. A port of the Igor Pro
|
|
52
|
+
[Irena](https://usaxs.xray.aps.anl.gov/software/irena) package. Includes interactive
|
|
53
|
+
GUI tools for fitting, modeling, data merging, and visualization of SAXS/SANS/USAXS data.
|
|
54
|
+
|
|
55
|
+
**Current release: v0.3.2 (first public beta)**
|
|
56
|
+
|
|
57
|
+
[](https://pypi.org/project/pyirena/)
|
|
58
|
+
[](https://www.python.org/downloads/)
|
|
59
|
+
[](https://opensource.org/licenses/MIT)
|
|
60
|
+
|
|
61
|
+
---
|
|
62
|
+
|
|
63
|
+
## Installation
|
|
64
|
+
|
|
65
|
+
**From PyPI (recommended):**
|
|
66
|
+
|
|
67
|
+
```bash
|
|
68
|
+
pip install pyirena[gui]
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
This installs pyirena with all GUI dependencies (PySide6, pyqtgraph, etc.). For the
|
|
72
|
+
core library only (no GUI), use `pip install pyirena`.
|
|
73
|
+
|
|
74
|
+
**From source (for development):**
|
|
75
|
+
|
|
76
|
+
```bash
|
|
77
|
+
git clone https://github.com/jilavsky/pyirena.git
|
|
78
|
+
cd pyirena
|
|
79
|
+
pip install -e ".[gui]"
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
**With conda:**
|
|
83
|
+
|
|
84
|
+
```bash
|
|
85
|
+
git clone https://github.com/jilavsky/pyirena.git
|
|
86
|
+
cd pyirena
|
|
87
|
+
conda env create -f environment.yml
|
|
88
|
+
conda activate pyirena
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
See [docs/installation.md](docs/installation.md) for full details, troubleshooting, and platform notes.
|
|
92
|
+
|
|
93
|
+
---
|
|
94
|
+
|
|
95
|
+
## Running the GUI
|
|
96
|
+
|
|
97
|
+
```bash
|
|
98
|
+
pyirena-gui
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
This launches the Data Selector, the main entry point for all analysis tools.
|
|
102
|
+
See [docs/gui_quickstart.md](docs/gui_quickstart.md) for a walkthrough.
|
|
103
|
+
|
|
104
|
+
Individual tools can also be launched directly:
|
|
105
|
+
|
|
106
|
+
| Command | Tool |
|
|
107
|
+
|---------|------|
|
|
108
|
+
| `pyirena-gui` | Data Selector (main entry point) |
|
|
109
|
+
| `pyirena-viewer` | HDF5 Viewer / Data Extractor |
|
|
110
|
+
| `pyirena-modeling` | Modeling tool (standalone) |
|
|
111
|
+
| `pyirena-datamerge` | Data Merge tool (standalone) |
|
|
112
|
+
| `pyirena-contrast` | Scattering Contrast Calculator |
|
|
113
|
+
|
|
114
|
+
---
|
|
115
|
+
|
|
116
|
+
## Analysis Tools
|
|
117
|
+
|
|
118
|
+
### Modeling
|
|
119
|
+
Parametric forward-modeling of SAS data. Combine up to 10 populations, each of which
|
|
120
|
+
can be a Size Distribution, Unified Fit Level, or Diffraction Peak. Fits the combined
|
|
121
|
+
model to experimental data using least-squares optimization.
|
|
122
|
+
|
|
123
|
+
- **5 distribution functions**: Gaussian, LogNormal, LSW, Schulz-Zimm, Ardell
|
|
124
|
+
- **9 form factors**: Sphere, Spheroid, Cylinder (aspect ratio / fixed length),
|
|
125
|
+
Core-Shell Sphere and Spheroid (by core R / shell t / total R)
|
|
126
|
+
- **2 structure factors**: Born-Green interferences, Hard Sphere (Percus-Yevick)
|
|
127
|
+
- Monte Carlo uncertainty estimation
|
|
128
|
+
- [Modeling GUI guide](docs/modeling_gui.md)
|
|
129
|
+
|
|
130
|
+
### Unified Fit
|
|
131
|
+
Beaucage hierarchical model (1995, 1996) with 1-5 structural levels, each combining
|
|
132
|
+
Guinier and power-law contributions. Optional Born-Green correlation function.
|
|
133
|
+
|
|
134
|
+
- [Unified Fit GUI guide](docs/unified_fit_gui.md)
|
|
135
|
+
- [Unified Fit features & parameters](docs/unified_fit_features.md)
|
|
136
|
+
|
|
137
|
+
### Size Distribution
|
|
138
|
+
Indirect Fourier transform to recover particle size distributions from SAS data.
|
|
139
|
+
Four inversion methods: MaxEnt, Regularization, TNNLS, and Monte Carlo.
|
|
140
|
+
|
|
141
|
+
- [Size Distribution methods](docs/sizes_methods.md)
|
|
142
|
+
|
|
143
|
+
### Simple Fits
|
|
144
|
+
13 direct analytical models: Guinier, Guinier-Porod, Porod, Sphere, Spheroid,
|
|
145
|
+
Debye-Bueche, Treubner-Strey, Power Law, and more. Each with linearization plots
|
|
146
|
+
and Monte Carlo uncertainty estimation.
|
|
147
|
+
|
|
148
|
+
- [Simple Fits GUI guide](docs/simple_fits_gui.md)
|
|
149
|
+
|
|
150
|
+
### WAXS Peak Fit
|
|
151
|
+
Fit diffraction peaks (Gaussian, Lorentzian, Pseudo-Voigt, Log-Normal) on linear
|
|
152
|
+
I vs Q scale. Auto-detect peaks via Savitzky-Golay + `scipy.signal.find_peaks`.
|
|
153
|
+
Simultaneous background fitting (constant, linear, cubic, or 5th-order polynomial).
|
|
154
|
+
|
|
155
|
+
- [WAXS Peak Fit GUI guide](docs/waxs_peakfit_gui.md)
|
|
156
|
+
|
|
157
|
+
### Data Merge
|
|
158
|
+
Merge two SAS datasets (e.g., SAXS + WAXS) onto a common Q scale. Optimizes scale
|
|
159
|
+
factor, flat background, and optional Q-shift using Nelder-Mead.
|
|
160
|
+
|
|
161
|
+
- [Data Merge GUI guide](docs/data_merge_gui.md)
|
|
162
|
+
|
|
163
|
+
### HDF5 Viewer / Data Extractor
|
|
164
|
+
Browse NXcanSAS HDF5 files, inspect raw data and analysis results, extract and plot
|
|
165
|
+
datasets. Supports all pyIrena result types (Unified Fit, Sizes, Simple Fits, WAXS
|
|
166
|
+
Peaks, Modeling).
|
|
167
|
+
|
|
168
|
+
- [HDF5 Viewer guide](docs/hdf5_viewer_gui.md)
|
|
169
|
+
|
|
170
|
+
### Scattering Contrast Calculator
|
|
171
|
+
Look up X-ray and neutron scattering length densities for materials by chemical
|
|
172
|
+
formula. Computes contrast (Delta-rho-squared) between two materials.
|
|
173
|
+
|
|
174
|
+
- [Contrast Calculator guide](docs/scattering_contrast_gui.md)
|
|
175
|
+
|
|
176
|
+
### Data Selector
|
|
177
|
+
Central GUI panel for managing data files and launching analysis tools. Load HDF5
|
|
178
|
+
files, select datasets, tabulate results across files, and generate reports.
|
|
179
|
+
|
|
180
|
+
---
|
|
181
|
+
|
|
182
|
+
## Batch Scripting API
|
|
183
|
+
|
|
184
|
+
All analysis tools can be run headlessly from Python scripts or JSON configuration files:
|
|
185
|
+
|
|
186
|
+
```python
|
|
187
|
+
from pyirena.batch import fit_pyirena
|
|
188
|
+
|
|
189
|
+
results = fit_pyirena(
|
|
190
|
+
data_file='sample.h5',
|
|
191
|
+
config_file='pyirena_config.json',
|
|
192
|
+
)
|
|
193
|
+
```
|
|
194
|
+
|
|
195
|
+
Individual functions: `fit_unified`, `fit_sizes`, `fit_simple`, `fit_waxs`,
|
|
196
|
+
`fit_modeling`, `merge_data`.
|
|
197
|
+
|
|
198
|
+
See [docs/batch_api.md](docs/batch_api.md) for the full scripting guide.
|
|
199
|
+
|
|
200
|
+
---
|
|
201
|
+
|
|
202
|
+
## NXcanSAS I/O
|
|
203
|
+
|
|
204
|
+
All data and results are stored in HDF5 files using the
|
|
205
|
+
[NXcanSAS](https://www.nexusformat.org/NXcanSAS.html) format. Fit results are saved
|
|
206
|
+
alongside raw data, making files self-contained and shareable.
|
|
207
|
+
|
|
208
|
+
- [NXcanSAS format details](docs/NXcanSAS_UnifiedFit_Format.md)
|
|
209
|
+
|
|
210
|
+
---
|
|
211
|
+
|
|
212
|
+
## Documentation
|
|
213
|
+
|
|
214
|
+
| Topic | File |
|
|
215
|
+
|-------|------|
|
|
216
|
+
| Installation | [docs/installation.md](docs/installation.md) |
|
|
217
|
+
| Quick start (GUI) | [docs/gui_quickstart.md](docs/gui_quickstart.md) |
|
|
218
|
+
| Modeling GUI guide | [docs/modeling_gui.md](docs/modeling_gui.md) |
|
|
219
|
+
| Unified Fit GUI guide | [docs/unified_fit_gui.md](docs/unified_fit_gui.md) |
|
|
220
|
+
| Unified Fit features & parameters | [docs/unified_fit_features.md](docs/unified_fit_features.md) |
|
|
221
|
+
| Size Distribution methods | [docs/sizes_methods.md](docs/sizes_methods.md) |
|
|
222
|
+
| Simple Fits GUI guide | [docs/simple_fits_gui.md](docs/simple_fits_gui.md) |
|
|
223
|
+
| WAXS Peak Fit GUI guide | [docs/waxs_peakfit_gui.md](docs/waxs_peakfit_gui.md) |
|
|
224
|
+
| Data Merge GUI guide | [docs/data_merge_gui.md](docs/data_merge_gui.md) |
|
|
225
|
+
| HDF5 Viewer guide | [docs/hdf5_viewer_gui.md](docs/hdf5_viewer_gui.md) |
|
|
226
|
+
| Contrast Calculator guide | [docs/scattering_contrast_gui.md](docs/scattering_contrast_gui.md) |
|
|
227
|
+
| NXcanSAS file format | [docs/NXcanSAS_UnifiedFit_Format.md](docs/NXcanSAS_UnifiedFit_Format.md) |
|
|
228
|
+
| Batch fitting API | [docs/batch_api.md](docs/batch_api.md) |
|
|
229
|
+
| Usage guide (scripting) | [docs/usage_guide.md](docs/usage_guide.md) |
|
|
230
|
+
| Developer: adding form factors | [docs/developer_adding_form_factors.md](docs/developer_adding_form_factors.md) |
|
|
231
|
+
| Developer: adding structure factors | [docs/developer_adding_structure_factors.md](docs/developer_adding_structure_factors.md) |
|
|
232
|
+
| Testing | [docs/testing.md](docs/testing.md) |
|
|
233
|
+
| Distribution / packaging | [docs/distribution.md](docs/distribution.md) |
|
|
234
|
+
| Contributing | [CONTRIBUTING.md](CONTRIBUTING.md) |
|
|
235
|
+
| Changelog | [CHANGELOG.md](CHANGELOG.md) |
|
|
236
|
+
|
|
237
|
+
---
|
|
238
|
+
|
|
239
|
+
## License
|
|
240
|
+
|
|
241
|
+
MIT -- see [LICENSE](LICENSE).
|
|
242
|
+
|
|
243
|
+
## Contact
|
|
244
|
+
|
|
245
|
+
- **Author**: Jan Ilavsky -- ilavsky@aps.anl.gov
|
|
246
|
+
- **Affiliation**: X-ray Science Division, Argonne National Laboratory
|
|
247
|
+
- **Issues**: https://github.com/jilavsky/pyirena/issues
|