ChessAnalysisPipeline 0.0.5__py3-none-any.whl → 0.0.6__py3-none-any.whl
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.
Potentially problematic release.
This version of ChessAnalysisPipeline might be problematic. Click here for more details.
- CHAP/TaskManager.py +214 -0
- CHAP/common/models/integration.py +392 -249
- CHAP/common/models/map.py +350 -198
- CHAP/common/processor.py +227 -189
- CHAP/common/reader.py +52 -39
- CHAP/common/utils/fit.py +1197 -991
- CHAP/common/utils/general.py +629 -372
- CHAP/common/utils/material.py +158 -121
- CHAP/common/utils/scanparsers.py +735 -339
- CHAP/common/writer.py +31 -25
- CHAP/edd/models.py +63 -49
- CHAP/edd/processor.py +130 -109
- CHAP/edd/reader.py +1 -1
- CHAP/edd/writer.py +1 -1
- CHAP/inference/processor.py +35 -28
- CHAP/inference/reader.py +1 -1
- CHAP/inference/writer.py +1 -1
- CHAP/pipeline.py +14 -28
- CHAP/processor.py +44 -75
- CHAP/reader.py +49 -40
- CHAP/runner.py +73 -32
- CHAP/saxswaxs/processor.py +1 -1
- CHAP/saxswaxs/reader.py +1 -1
- CHAP/saxswaxs/writer.py +1 -1
- CHAP/server.py +130 -0
- CHAP/sin2psi/processor.py +1 -1
- CHAP/sin2psi/reader.py +1 -1
- CHAP/sin2psi/writer.py +1 -1
- CHAP/tomo/__init__.py +1 -4
- CHAP/tomo/models.py +53 -31
- CHAP/tomo/processor.py +1326 -900
- CHAP/tomo/reader.py +4 -2
- CHAP/tomo/writer.py +4 -2
- CHAP/writer.py +47 -41
- {ChessAnalysisPipeline-0.0.5.dist-info → ChessAnalysisPipeline-0.0.6.dist-info}/METADATA +1 -1
- ChessAnalysisPipeline-0.0.6.dist-info/RECORD +52 -0
- ChessAnalysisPipeline-0.0.5.dist-info/RECORD +0 -50
- {ChessAnalysisPipeline-0.0.5.dist-info → ChessAnalysisPipeline-0.0.6.dist-info}/LICENSE +0 -0
- {ChessAnalysisPipeline-0.0.5.dist-info → ChessAnalysisPipeline-0.0.6.dist-info}/WHEEL +0 -0
- {ChessAnalysisPipeline-0.0.5.dist-info → ChessAnalysisPipeline-0.0.6.dist-info}/entry_points.txt +0 -0
- {ChessAnalysisPipeline-0.0.5.dist-info → ChessAnalysisPipeline-0.0.6.dist-info}/top_level.txt +0 -0
CHAP/common/utils/material.py
CHANGED
|
@@ -1,92 +1,103 @@
|
|
|
1
1
|
#!/usr/bin/env python3
|
|
2
|
-
|
|
3
2
|
# -*- coding: utf-8 -*-
|
|
3
|
+
#pylint: disable=
|
|
4
4
|
"""
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
5
|
+
File : general.py
|
|
6
|
+
Author : Rolf Verberg <rolfverberg AT gmail dot com>
|
|
7
|
+
Description: Module defining the Material class
|
|
8
8
|
"""
|
|
9
9
|
|
|
10
|
-
|
|
10
|
+
# System modules
|
|
11
|
+
from logging import getLogger
|
|
12
|
+
from os import path
|
|
11
13
|
|
|
12
|
-
|
|
14
|
+
# Third party modules
|
|
13
15
|
import numpy as np
|
|
14
16
|
try:
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
17
|
+
from xrayutilities import materials
|
|
18
|
+
from xrayutilities import simpack
|
|
19
|
+
HAVE_XU = True
|
|
20
|
+
except ImportError:
|
|
21
|
+
HAVE_XU = False
|
|
20
22
|
try:
|
|
21
23
|
from hexrd import material
|
|
22
|
-
|
|
23
|
-
except:
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
if have_hexrd:
|
|
24
|
+
HAVE_HEXRD = True
|
|
25
|
+
except ImportError:
|
|
26
|
+
HAVE_HEXRD = False
|
|
27
|
+
if HAVE_HEXRD:
|
|
27
28
|
try:
|
|
28
29
|
from hexrd.valunits import valWUnit
|
|
29
|
-
except:
|
|
30
|
-
|
|
31
|
-
|
|
30
|
+
except ImportError:
|
|
31
|
+
HAVE_HEXRD = False
|
|
32
|
+
|
|
33
|
+
POEDER_INTENSITY_CUTOFF = 1.e-8
|
|
34
|
+
|
|
35
|
+
logger = getLogger(__name__)
|
|
32
36
|
|
|
33
|
-
powder_intensity_cutoff = 1.e-8
|
|
34
37
|
|
|
35
38
|
class Material:
|
|
36
|
-
"""Base class for materials in an sin2psi or EDD analysis.
|
|
37
|
-
Right now it assumes a single material
|
|
38
|
-
extend its ability to do differently when test data is available
|
|
39
39
|
"""
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
40
|
+
Base class for materials in an sin2psi or EDD analysis. Right now
|
|
41
|
+
it assumes a single material, extend its ability to do differently
|
|
42
|
+
when test data is available
|
|
43
|
+
"""
|
|
44
|
+
def __init__(
|
|
45
|
+
self, material_name=None, material_file=None, sgnum=None,
|
|
46
|
+
lattice_parameters_angstroms=None, atoms=None, pos=None,
|
|
47
|
+
enrgy=None):
|
|
48
|
+
"""Initialize Material."""
|
|
43
49
|
self._enrgy = enrgy
|
|
44
50
|
self._materials = []
|
|
45
51
|
self._ds_min = []
|
|
46
52
|
self._ds_unique = None
|
|
47
53
|
self._hkls_unique = None
|
|
48
54
|
if material_name is not None:
|
|
49
|
-
self.add_material(
|
|
50
|
-
|
|
55
|
+
self.add_material(
|
|
56
|
+
material_name, material_file, sgnum,
|
|
57
|
+
lattice_parameters_angstroms, atoms, pos)
|
|
51
58
|
|
|
52
|
-
@property
|
|
53
|
-
#FIX passing arguments to a property isn't correct?
|
|
54
59
|
def lattice_parameters(self, index=0):
|
|
55
|
-
"""Convert from internal nm units to angstrom
|
|
56
|
-
"""
|
|
60
|
+
"""Convert from internal nm units to angstrom."""
|
|
57
61
|
matl = self._materials[index]
|
|
58
|
-
if isinstance(matl,
|
|
62
|
+
if isinstance(matl, materials.material.Crystal):
|
|
59
63
|
return [matl.a, matl.b, matl.c]
|
|
60
|
-
|
|
61
|
-
return [
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
64
|
+
if isinstance(matl, material.Material):
|
|
65
|
+
return [
|
|
66
|
+
lpars.getVal('angstrom')
|
|
67
|
+
for lpars in self._materials[index].latticeParameters[0:3]]
|
|
68
|
+
raise ValueError('Illegal material class type')
|
|
65
69
|
|
|
66
|
-
@property
|
|
67
70
|
def ds_unique(self, tth_tol=None, tth_max=None, round_sig=8):
|
|
71
|
+
"""Return the unique lattice spacings."""
|
|
68
72
|
if self._ds_unique is None:
|
|
69
|
-
self.
|
|
73
|
+
self.get_ds_unique(tth_tol, tth_max, round_sig)
|
|
70
74
|
return self._ds_unique
|
|
71
75
|
|
|
72
|
-
@property
|
|
73
76
|
def hkls_unique(self, tth_tol=None, tth_max=None, round_sig=8):
|
|
77
|
+
"""Return the unique HKLs."""
|
|
74
78
|
if self._hkls_unique is None:
|
|
75
|
-
self.
|
|
79
|
+
self.get_ds_unique(tth_tol, tth_max, round_sig)
|
|
76
80
|
return self._hkls_unique
|
|
77
81
|
|
|
78
|
-
def add_material(
|
|
79
|
-
|
|
82
|
+
def add_material(
|
|
83
|
+
self, material_name, material_file=None, sgnum=None,
|
|
84
|
+
lattice_parameters_angstroms=None, atoms=None, pos=None,
|
|
85
|
+
dmin_angstroms=0.6):
|
|
86
|
+
"""Add a material."""
|
|
80
87
|
# At this point only for a single material
|
|
81
|
-
# Unique energies works for more, but fitting with different
|
|
88
|
+
# Unique energies works for more, but fitting with different
|
|
89
|
+
# materials is not implemented
|
|
82
90
|
if len(self._materials) == 1:
|
|
83
|
-
|
|
91
|
+
raise ValueError('Multiple materials not implemented yet')
|
|
84
92
|
self._ds_min.append(dmin_angstroms)
|
|
85
|
-
self._materials.append(
|
|
93
|
+
self._materials.append(
|
|
94
|
+
Material.make_material(
|
|
95
|
+
material_name, material_file, sgnum,
|
|
86
96
|
lattice_parameters_angstroms, atoms, pos, dmin_angstroms))
|
|
87
97
|
|
|
88
|
-
def
|
|
89
|
-
"""
|
|
98
|
+
def get_ds_unique(self, tth_tol=None, tth_max=None, round_sig=8):
|
|
99
|
+
"""
|
|
100
|
+
Get the list of unique lattice spacings from material HKLs.
|
|
90
101
|
|
|
91
102
|
Parameters
|
|
92
103
|
----------
|
|
@@ -96,136 +107,162 @@ class Material:
|
|
|
96
107
|
|
|
97
108
|
Returns
|
|
98
109
|
-------
|
|
99
|
-
hkls
|
|
100
|
-
ds
|
|
110
|
+
hkls: list of hkl's corresponding to the unique lattice spacings
|
|
111
|
+
ds: list of the unique lattice spacings
|
|
101
112
|
"""
|
|
102
113
|
hkls = np.empty((0,3))
|
|
103
114
|
ds = np.empty((0))
|
|
104
|
-
|
|
105
|
-
for i,m in enumerate(self._materials):
|
|
115
|
+
ds_index = np.empty((0))
|
|
116
|
+
for i, m in enumerate(self._materials):
|
|
106
117
|
material_class_valid = False
|
|
107
|
-
if
|
|
108
|
-
if isinstance(m,
|
|
109
|
-
powder =
|
|
110
|
-
hklsi = [hkl for hkl in powder.data
|
|
111
|
-
|
|
112
|
-
|
|
118
|
+
if HAVE_XU:
|
|
119
|
+
if isinstance(m, materials.material.Crystal):
|
|
120
|
+
powder = simpack.PowderDiffraction(m, en=self._enrgy)
|
|
121
|
+
hklsi = [hkl for hkl in powder.data
|
|
122
|
+
if powder.data[hkl]['active']]
|
|
123
|
+
ds_i = [m.planeDistance(hkl) for hkl in powder.data
|
|
124
|
+
if powder.data[hkl]['active']]
|
|
125
|
+
mask = [d > self._ds_min[i] for d in ds_i]
|
|
113
126
|
hkls = np.vstack((hkls, np.array(hklsi)[mask,:]))
|
|
114
|
-
|
|
127
|
+
ds_i = np.array(ds_i)[mask]
|
|
115
128
|
material_class_valid = True
|
|
116
|
-
if
|
|
129
|
+
if HAVE_HEXRD:
|
|
117
130
|
if isinstance(m, material.Material):
|
|
118
|
-
|
|
131
|
+
plane_data = m.planeData
|
|
119
132
|
if tth_tol is not None:
|
|
120
|
-
|
|
133
|
+
plane_data.tThWidth = np.radians(tth_tol)
|
|
121
134
|
if tth_max is not None:
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
hkls = np.vstack((hkls,
|
|
125
|
-
|
|
135
|
+
plane_data.exclusions = None
|
|
136
|
+
plane_data.tThMax = np.radians(tth_max)
|
|
137
|
+
hkls = np.vstack((hkls, plane_data.hkls.T))
|
|
138
|
+
ds_i = plane_data.getPlaneSpacings()
|
|
126
139
|
material_class_valid = True
|
|
127
140
|
if not material_class_valid:
|
|
128
141
|
raise ValueError('Illegal material class type')
|
|
129
|
-
ds = np.hstack((ds,
|
|
130
|
-
|
|
142
|
+
ds = np.hstack((ds, ds_i))
|
|
143
|
+
ds_index = np.hstack((ds_index, i*np.ones(len(ds_i))))
|
|
131
144
|
|
|
132
145
|
# Sort lattice spacings in reverse order (use -)
|
|
133
|
-
ds_unique,
|
|
134
|
-
|
|
146
|
+
ds_unique, ds_index_unique, _ = np.unique(
|
|
147
|
+
-ds.round(round_sig), return_index=True, return_counts=True)
|
|
135
148
|
ds_unique = np.abs(ds_unique)
|
|
136
149
|
|
|
137
150
|
# Limit the list to unique lattice spacings
|
|
138
|
-
self._hkls_unique = hkls[
|
|
139
|
-
self._ds_unique = ds[
|
|
140
|
-
hkl_list = np.vstack(
|
|
141
|
-
|
|
142
|
-
|
|
151
|
+
self._hkls_unique = hkls[ds_index_unique,:].astype(int)
|
|
152
|
+
self._ds_unique = ds[ds_index_unique]
|
|
153
|
+
hkl_list = np.vstack(
|
|
154
|
+
(np.arange(self._ds_unique.shape[0]), ds_index[ds_index_unique],
|
|
155
|
+
self._hkls_unique.T, self._ds_unique)).T
|
|
156
|
+
logger.info("Unique d's:")
|
|
143
157
|
for hkl in hkl_list:
|
|
144
|
-
|
|
145
|
-
|
|
158
|
+
logger.info(
|
|
159
|
+
f'{hkl[0]:4.0f} {hkl[1]:.0f} {hkl[2]:.0f} {hkl[3]:.0f} '
|
|
160
|
+
f'{hkl[4]:.0f} {hkl[5]:.6f}')
|
|
146
161
|
|
|
147
162
|
return self._hkls_unique, self._ds_unique
|
|
148
163
|
|
|
149
164
|
@staticmethod
|
|
150
|
-
def make_material(
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
165
|
+
def make_material(
|
|
166
|
+
material_name, material_file=None, sgnum=None,
|
|
167
|
+
lattice_parameters_angstroms=None, atoms=None, pos=None,
|
|
168
|
+
dmin_angstroms=0.6):
|
|
169
|
+
"""
|
|
170
|
+
Use HeXRD to get material properties when a materials file is
|
|
171
|
+
provided. Use xrayutilities otherwise.
|
|
154
172
|
"""
|
|
155
173
|
if not isinstance(material_name, str):
|
|
156
|
-
raise ValueError(
|
|
174
|
+
raise ValueError(
|
|
175
|
+
f'Illegal material_name: {material_name} '
|
|
176
|
+
f'{type(material_name)}')
|
|
157
177
|
if lattice_parameters_angstroms is not None:
|
|
158
178
|
if material_file is not None:
|
|
159
|
-
|
|
160
|
-
|
|
179
|
+
logger.warning(
|
|
180
|
+
'Overwrite lattice_parameters of material_file with input '
|
|
181
|
+
f'values ({lattice_parameters_angstroms})')
|
|
161
182
|
if isinstance(lattice_parameters_angstroms, (int, float)):
|
|
162
183
|
lattice_parameters = [lattice_parameters_angstroms]
|
|
163
|
-
elif isinstance(
|
|
184
|
+
elif isinstance(
|
|
185
|
+
lattice_parameters_angstroms, (tuple, list, np.ndarray)):
|
|
164
186
|
lattice_parameters = list(lattice_parameters_angstroms)
|
|
165
187
|
else:
|
|
166
|
-
raise ValueError(
|
|
167
|
-
|
|
188
|
+
raise ValueError(
|
|
189
|
+
'Illegal lattice_parameters_angstroms: '
|
|
190
|
+
f'{lattice_parameters_angstroms} '
|
|
191
|
+
f'{type(lattice_parameters_angstroms)}')
|
|
168
192
|
if material_file is None:
|
|
169
193
|
if not isinstance(sgnum, int):
|
|
170
194
|
raise ValueError(f'Illegal sgnum: {sgnum} {type(sgnum)}')
|
|
171
|
-
if sgnum is None or lattice_parameters_angstroms is None
|
|
172
|
-
|
|
173
|
-
|
|
195
|
+
if (sgnum is None or lattice_parameters_angstroms is None
|
|
196
|
+
or pos is None):
|
|
197
|
+
raise ValueError(
|
|
198
|
+
'Valid inputs for sgnum, lattice_parameters_angstroms and '
|
|
199
|
+
'pos are required if materials file is not specified')
|
|
174
200
|
if isinstance(pos, str):
|
|
175
201
|
pos = [pos]
|
|
176
202
|
use_xu = True
|
|
177
|
-
if (np.array(pos).ndim == 1 and isinstance(pos[0], (int, float))
|
|
178
|
-
np.array(pos).size == 3):
|
|
179
|
-
if
|
|
203
|
+
if (np.array(pos).ndim == 1 and isinstance(pos[0], (int, float))
|
|
204
|
+
and np.array(pos).size == 3):
|
|
205
|
+
if HAVE_HEXRD:
|
|
180
206
|
pos = np.array([pos])
|
|
181
207
|
use_xu = False
|
|
182
|
-
elif (np.array(pos).ndim == 2 and np.array(pos).shape[0] > 0
|
|
183
|
-
np.array(pos).shape[1] == 3):
|
|
184
|
-
if
|
|
208
|
+
elif (np.array(pos).ndim == 2 and np.array(pos).shape[0] > 0
|
|
209
|
+
and np.array(pos).shape[1] == 3):
|
|
210
|
+
if HAVE_HEXRD:
|
|
185
211
|
pos = np.array(pos)
|
|
186
212
|
use_xu = False
|
|
187
|
-
elif not (np.array(pos).ndim == 1 and isinstance(pos[0], str)
|
|
188
|
-
|
|
189
|
-
raise ValueError(
|
|
213
|
+
elif not (np.array(pos).ndim == 1 and isinstance(pos[0], str)
|
|
214
|
+
and np.array(pos).size > 0 and HAVE_XU):
|
|
215
|
+
raise ValueError(
|
|
216
|
+
f'Illegal pos (HAVE_XU = {HAVE_XU}): {pos} {type(pos)}')
|
|
190
217
|
if use_xu:
|
|
191
218
|
if atoms is None:
|
|
192
219
|
atoms = [material_name]
|
|
193
|
-
matl =
|
|
194
|
-
|
|
220
|
+
matl = materials.Crystal(
|
|
221
|
+
material_name,
|
|
222
|
+
materials.SGLattice(sgnum, *lattice_parameters,
|
|
223
|
+
atoms=atoms, pos=list(np.array(pos))))
|
|
195
224
|
else:
|
|
196
225
|
matl = material.Material(material_name)
|
|
197
226
|
matl.sgnum = sgnum
|
|
198
227
|
matl.atominfo = np.vstack((pos.T, np.ones(pos.shape[0]))).T
|
|
199
228
|
matl.latticeParameters = lattice_parameters
|
|
200
|
-
matl.dmin = valWUnit(
|
|
229
|
+
matl.dmin = valWUnit(
|
|
230
|
+
'lp', 'length', dmin_angstroms, 'angstrom')
|
|
201
231
|
exclusions = matl.planeData.get_exclusions()
|
|
202
232
|
powder_intensity = matl.planeData.powder_intensity
|
|
203
|
-
exclusions = [
|
|
204
|
-
|
|
205
|
-
|
|
233
|
+
exclusions = [
|
|
234
|
+
exclusion or i >= len(powder_intensity)
|
|
235
|
+
or powder_intensity[i] < POEDER_INTENSITY_CUTOFF
|
|
236
|
+
for i, exclusion in enumerate(exclusions)]
|
|
206
237
|
matl.planeData.set_exclusions(exclusions)
|
|
207
|
-
|
|
208
|
-
|
|
238
|
+
logger.debug(
|
|
239
|
+
f'powder_intensity = {matl.planeData.powder_intensity}')
|
|
240
|
+
logger.debug(f'exclusions = {matl.planeData.exclusions}')
|
|
209
241
|
else:
|
|
210
|
-
if not
|
|
211
|
-
raise ValueError(
|
|
212
|
-
|
|
242
|
+
if not HAVE_HEXRD:
|
|
243
|
+
raise ValueError(
|
|
244
|
+
'Illegal inputs: must provide detailed material info when '
|
|
245
|
+
'hexrd package is unavailable')
|
|
213
246
|
if sgnum is not None:
|
|
214
|
-
|
|
215
|
-
|
|
247
|
+
logger.warning(
|
|
248
|
+
'Ignore sgnum input when material_file is specified')
|
|
249
|
+
if not (path.splitext(material_file)[1] in
|
|
250
|
+
('.h5', '.hdf5', '.xtal', '.cif')):
|
|
216
251
|
raise ValueError(f'Illegal material file {material_file}')
|
|
217
|
-
matl = material.Material(
|
|
218
|
-
|
|
252
|
+
matl = material.Material(
|
|
253
|
+
material_name, material_file,
|
|
254
|
+
dmin=valWUnit('lp', 'length', dmin_angstroms, 'angstrom'))
|
|
219
255
|
if lattice_parameters_angstroms is not None:
|
|
220
256
|
matl.latticeParameters = lattice_parameters
|
|
221
257
|
exclusions = matl.planeData.get_exclusions()
|
|
222
258
|
powder_intensity = matl.planeData.powder_intensity
|
|
223
|
-
exclusions = [
|
|
224
|
-
|
|
225
|
-
|
|
259
|
+
exclusions = [
|
|
260
|
+
exclusion or i >= len(powder_intensity)
|
|
261
|
+
or powder_intensity[i] < POEDER_INTENSITY_CUTOFF
|
|
262
|
+
for i, exclusion in enumerate(exclusions)]
|
|
226
263
|
matl.planeData.set_exclusions(exclusions)
|
|
227
|
-
|
|
228
|
-
|
|
264
|
+
logger.debug(
|
|
265
|
+
f'powder_intensity = {matl.planeData.powder_intensity}')
|
|
266
|
+
logger.debug(f'exclusions = {matl.planeData.exclusions}')
|
|
229
267
|
|
|
230
268
|
return matl
|
|
231
|
-
|