tomwer 1.4.19__py3-none-any.whl → 1.5.0rc0__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.
Files changed (84) hide show
  1. orangecontrib/tomwer/tutorials/simple_volume_local_reconstruction.ows +11 -8
  2. orangecontrib/tomwer/tutorials/simple_volume_to_slurm_reconstruction.ows +12 -9
  3. orangecontrib/tomwer/widgets/control/DataDiscoveryOW.py +1 -1
  4. orangecontrib/tomwer/widgets/control/NXTomomillMixIn.py +21 -10
  5. tomwer/app/reducedarkflat.py +2 -2
  6. tomwer/core/process/edit/imagekeyeditor.py +4 -6
  7. tomwer/core/process/edit/nxtomoeditor.py +58 -20
  8. tomwer/core/process/output.py +6 -5
  9. tomwer/core/process/reconstruction/axis/anglemode.py +2 -2
  10. tomwer/core/process/reconstruction/axis/axis.py +1 -0
  11. tomwer/core/process/reconstruction/darkref/darkrefs.py +2 -2
  12. tomwer/core/process/reconstruction/darkref/darkrefscopy.py +1 -1
  13. tomwer/core/process/reconstruction/darkref/params.py +1 -1
  14. tomwer/core/process/reconstruction/nabu/castvolume.py +4 -1
  15. tomwer/core/process/reconstruction/nabu/helical.py +3 -1
  16. tomwer/core/process/reconstruction/nabu/nabuscores.py +1 -1
  17. tomwer/core/process/reconstruction/nabu/nabuslices.py +4 -4
  18. tomwer/core/process/reconstruction/nabu/plane.py +2 -2
  19. tomwer/core/process/reconstruction/nabu/test/test_castvolume.py +2 -0
  20. tomwer/core/process/reconstruction/nabu/utils.py +15 -14
  21. tomwer/core/process/reconstruction/normalization/params.py +1 -1
  22. tomwer/core/process/reconstruction/output.py +2 -2
  23. tomwer/core/process/reconstruction/tests/test_axis.py +1 -1
  24. tomwer/core/process/stitching/metadataholder.py +5 -5
  25. tomwer/core/process/stitching/nabustitcher.py +1 -4
  26. tomwer/core/scan/edfscan.py +3 -3
  27. tomwer/core/scan/nxtomoscan.py +3 -3
  28. tomwer/core/scan/scanbase.py +2 -2
  29. tomwer/core/tomwer_object.py +1 -1
  30. tomwer/core/utils/nxtomoutils.py +2 -2
  31. tomwer/core/utils/spec.py +6 -3
  32. tomwer/gui/control/datadiscovery.py +1 -1
  33. tomwer/gui/control/reducedarkflatselector.py +4 -4
  34. tomwer/gui/edit/imagekeyeditor.py +7 -9
  35. tomwer/gui/edit/nxtomoeditor.py +420 -112
  36. tomwer/gui/edit/tests/test_nx_editor.py +154 -82
  37. tomwer/gui/reconstruction/axis/CalculationWidget.py +1 -1
  38. tomwer/gui/reconstruction/axis/EstimatedCORWidget.py +12 -8
  39. tomwer/gui/reconstruction/darkref/darkrefwidget.py +2 -2
  40. tomwer/gui/reconstruction/nabu/castvolume.py +16 -1
  41. tomwer/gui/reconstruction/nabu/nabuconfig/base.py +1 -1
  42. tomwer/gui/reconstruction/nabu/nabuconfig/nabuconfig.py +1 -1
  43. tomwer/gui/reconstruction/nabu/nabuconfig/phase.py +2 -2
  44. tomwer/gui/reconstruction/nabu/nabuconfig/preprocessing.py +2 -4
  45. tomwer/gui/reconstruction/nabu/nabuconfig/reconstruction.py +71 -49
  46. tomwer/gui/reconstruction/nabu/nabuflow.py +3 -13
  47. tomwer/gui/reconstruction/nabu/slices.py +6 -6
  48. tomwer/gui/reconstruction/nabu/test/test_cast_volume.py +19 -0
  49. tomwer/gui/reconstruction/normalization/intensity.py +2 -2
  50. tomwer/gui/reconstruction/saaxis/dimensionwidget.py +71 -67
  51. tomwer/gui/reconstruction/scores/scoreplot.py +15 -7
  52. tomwer/gui/reconstruction/tests/test_saaxis.py +18 -16
  53. tomwer/gui/stitching/SingleAxisStitchingWidget.py +8 -8
  54. tomwer/gui/stitching/StitchingOptionsWidget.py +1 -1
  55. tomwer/gui/stitching/alignment.py +8 -8
  56. tomwer/gui/stitching/config/axisparams.py +2 -2
  57. tomwer/gui/stitching/config/output.py +1 -1
  58. tomwer/gui/stitching/config/stitchingstrategies.py +4 -6
  59. tomwer/gui/stitching/config/tomoobjdetails.py +21 -13
  60. tomwer/gui/stitching/normalization.py +6 -6
  61. tomwer/gui/stitching/tests/test_ZStitchingWindow.py +8 -1
  62. tomwer/gui/stitching/tests/test_preview.py +10 -7
  63. tomwer/gui/stitching/tests/utils.py +27 -18
  64. tomwer/gui/stitching/z_stitching/fineestimation.py +7 -9
  65. tomwer/gui/stitching/z_stitching/tests/test_raw_estimation.py +18 -7
  66. tomwer/gui/stitching/z_stitching/tests/test_stitching_window.py +7 -2
  67. tomwer/gui/utils/buttons.py +53 -35
  68. tomwer/gui/utils/flow.py +1 -1
  69. tomwer/gui/utils/unitsystem.py +44 -33
  70. tomwer/gui/visualization/diffviewer/diffviewer.py +4 -4
  71. tomwer/gui/visualization/diffviewer/shiftwidget.py +4 -6
  72. tomwer/gui/visualization/test/test_nx_tomo_metadata_viewer.py +25 -13
  73. tomwer/model/dataset.py +0 -0
  74. tomwer/tasks/reconstruction/cleardarkflat.py +42 -0
  75. tomwer/tests/app/test_stitching.py +1 -1
  76. tomwer/tests/orangecontrib/tomwer/widgets/edit/tests/test_nxtomo_editor.py +32 -20
  77. tomwer/tests/orangecontrib/tomwer/widgets/reconstruction/tests/test_nabu_widget.py +1 -1
  78. tomwer/version.py +3 -3
  79. {tomwer-1.4.19.dist-info → tomwer-1.5.0rc0.dist-info}/METADATA +8 -8
  80. {tomwer-1.4.19.dist-info → tomwer-1.5.0rc0.dist-info}/RECORD +84 -82
  81. {tomwer-1.4.19.dist-info → tomwer-1.5.0rc0.dist-info}/WHEEL +1 -1
  82. {tomwer-1.4.19.dist-info → tomwer-1.5.0rc0.dist-info}/entry_points.txt +0 -0
  83. {tomwer-1.4.19.dist-info → tomwer-1.5.0rc0.dist-info}/licenses/LICENSE +0 -0
  84. {tomwer-1.4.19.dist-info → tomwer-1.5.0rc0.dist-info}/top_level.txt +0 -0
@@ -10,7 +10,7 @@ from nabu.pipeline.config import generate_nabu_configfile, parse_nabu_config_fil
10
10
  from nabu.pipeline.fullfield.nabu_config import (
11
11
  nabu_config as nabu_fullfield_default_config,
12
12
  )
13
- from silx.utils.enum import Enum as _Enum
13
+ from enum import Enum
14
14
 
15
15
  from tomoscan.identifier import VolumeIdentifier
16
16
  import tomwer.version
@@ -240,13 +240,13 @@ def get_multi_cor_recons_volume_identifiers(
240
240
  return res
241
241
 
242
242
 
243
- class _NabuMode(_Enum):
243
+ class _NabuMode(Enum):
244
244
  FULL_FIELD = "standard acquisition"
245
245
  HALF_ACQ = "half acquisition"
246
246
  # HELICAL = "helical acquisition"
247
247
 
248
248
 
249
- class _NabuStages(_Enum):
249
+ class _NabuStages(Enum):
250
250
  INI = "initialization"
251
251
  PRE = "pre-processing"
252
252
  PHASE = "phase"
@@ -267,7 +267,7 @@ class _NabuStages(_Enum):
267
267
  @staticmethod
268
268
  def getProcessEnum(stage):
269
269
  """Return the process Enum associated to the stage"""
270
- stage = _NabuStages.from_value(stage)
270
+ stage = _NabuStages(stage)
271
271
  if stage is _NabuStages.INI:
272
272
  raise NotImplementedError()
273
273
  elif stage is _NabuStages.PRE:
@@ -281,7 +281,7 @@ class _NabuStages(_Enum):
281
281
  raise NotImplementedError()
282
282
 
283
283
 
284
- class _NabuPreprocessing(_Enum):
284
+ class _NabuPreprocessing(Enum):
285
285
  """Define all the preprocessing action possible and the order they
286
286
  are applied on"""
287
287
 
@@ -296,7 +296,7 @@ class _NabuPreprocessing(_Enum):
296
296
  )
297
297
 
298
298
 
299
- class _NabuPhase(_Enum):
299
+ class _NabuPhase(Enum):
300
300
  """Define all the phase action possible and the order they
301
301
  are applied on"""
302
302
 
@@ -309,7 +309,7 @@ class _NabuPhase(_Enum):
309
309
  return (_NabuPhase.PHASE, _NabuPhase.UNSHARP_MASK, _NabuPhase.LOGARITHM)
310
310
 
311
311
 
312
- class _NabuProcessing(_Enum):
312
+ class _NabuProcessing(Enum):
313
313
  """Define all the processing action possible"""
314
314
 
315
315
  RECONSTRUCTION = "reconstruction"
@@ -319,7 +319,7 @@ class _NabuProcessing(_Enum):
319
319
  return (_NabuProcessing.RECONSTRUCTION,)
320
320
 
321
321
 
322
- class _NabuPostProcessing(_Enum):
322
+ class _NabuPostProcessing(Enum):
323
323
  """Define all the post processing action available"""
324
324
 
325
325
  SAVE_DATA = "save"
@@ -329,11 +329,12 @@ class _NabuPostProcessing(_Enum):
329
329
  return (_NabuPostProcessing.SAVE_DATA,)
330
330
 
331
331
 
332
- class _NabuReconstructionMethods(_Enum):
332
+ class _NabuReconstructionMethods(Enum):
333
333
  FBP = "FBP"
334
+ MLEM = "MLEM"
334
335
 
335
336
 
336
- class _NabuPhaseMethod(_Enum):
337
+ class _NabuPhaseMethod(Enum):
337
338
  """
338
339
  Nabu phase method
339
340
  """
@@ -354,10 +355,10 @@ class _NabuPhaseMethod(_Enum):
354
355
  elif value.lower() == "ctf":
355
356
  return _NabuPhaseMethod.CTF
356
357
  else:
357
- return super().from_value(value=value)
358
+ return _NabuPhaseMethod(value=value)
358
359
 
359
360
 
360
- class _NabuFBPFilterType(_Enum):
361
+ class _NabuFBPFilterType(Enum):
361
362
  RAMLAK = "ramlak"
362
363
  SHEPP_LOGAN = "shepp-logan"
363
364
  COSINE = "cosine"
@@ -368,12 +369,12 @@ class _NabuFBPFilterType(_Enum):
368
369
  HILBERT = "hilbert"
369
370
 
370
371
 
371
- class _NabuPaddingType(_Enum):
372
+ class _NabuPaddingType(Enum):
372
373
  ZEROS = "zeros"
373
374
  EDGES = "edges"
374
375
 
375
376
 
376
- class RingCorrectionMethod(_Enum):
377
+ class RingCorrectionMethod(Enum):
377
378
  NONE = "None"
378
379
  MUNCH = "munch"
379
380
  VO = "vo"
@@ -86,7 +86,7 @@ class SinoNormalizationParams:
86
86
  def method(self, method: str | Method | None):
87
87
  if method is None:
88
88
  method = Method.NONE
89
- self._method = Method.from_value(method)
89
+ self._method = Method(method)
90
90
 
91
91
  @property
92
92
  def source(self):
@@ -1,7 +1,7 @@
1
1
  from __future__ import annotations
2
2
  import os
3
3
  import logging
4
- from silx.utils.enum import Enum as _Enum
4
+ from enum import Enum as _Enum
5
5
  from tomwer.io.utils.raw_and_processed_data import (
6
6
  to_processed_data_path,
7
7
  )
@@ -30,7 +30,7 @@ class NabuOutputFileFormat(_Enum):
30
30
  def from_value(cls, value):
31
31
  if isinstance(value, str):
32
32
  value = value.lstrip(".")
33
- return super().from_value(value)
33
+ return NabuOutputFileFormat(value)
34
34
 
35
35
 
36
36
  def get_file_format(file_str):
@@ -40,7 +40,7 @@ def test_read_x_rotation_axis_pixel_position(nxtomo_scan_360): # noqa F811
40
40
  with h5py.File(nxtomo_scan_360.master_file, mode="a") as h5f:
41
41
  h5f[x_rotation_axis_pixel_position_path] = 12.5
42
42
 
43
- nxtomo_scan_360.clear_caches()
43
+ nxtomo_scan_360.clear_cache()
44
44
  task.run()
45
45
  assert nxtomo_scan_360.axis_params.absolute_cor_value == 22.5
46
46
  assert nxtomo_scan_360.axis_params.relative_cor_value == 12.5
@@ -41,19 +41,19 @@ class StitchingMetadata:
41
41
  if value is not None and not isinstance(
42
42
  value, (float, numpy.float32, numpy.float64)
43
43
  ):
44
- raise TypeError
44
+ raise TypeError(f"Invalid type for value. Got {type(value)}")
45
45
  self._pixel_or_voxel_size[axis] = value
46
46
 
47
47
  def setPxPos(self, value, axis):
48
48
  if value is not None and not isinstance(value, (int, numpy.int32)):
49
- raise TypeError
49
+ raise TypeError(f"Invalid type for value. Got {type(value)}")
50
50
  self._pos_as_px[axis] = value
51
51
 
52
52
  def setMetricPos(self, value, axis):
53
53
  if value is not None and not isinstance(
54
54
  value, (int, numpy.float32, numpy.float64, float)
55
55
  ):
56
- raise TypeError
56
+ raise TypeError(f"Invalid type for value. Got {type(value)}")
57
57
  self._pos_as_m[axis] = value
58
58
 
59
59
  def get_raw_position_m(self, axis):
@@ -111,9 +111,9 @@ class StitchingMetadata:
111
111
  return self._pixel_or_voxel_size[axis]
112
112
  elif isinstance(self.tomo_obj, TomoScanBase):
113
113
  if axis == 0:
114
- return self.tomo_obj.y_pixel_size
114
+ return self.tomo_obj.sample_y_pixel_size
115
115
  elif axis in (1, 2):
116
- return self.tomo_obj.x_pixel_size
116
+ return self.tomo_obj.sample_x_pixel_size
117
117
  else:
118
118
  raise TypeError(f"axis is expected to be in (0, 1, 2). {axis} provided")
119
119
  elif isinstance(self.tomo_obj, VolumeBase):
@@ -162,12 +162,9 @@ class StitchingPostProcAggregation(_StitchingPostProcAggregation):
162
162
 
163
163
  def __init__(self, *args, **kwargs) -> None:
164
164
  super().__init__(*args, **kwargs)
165
- print("creates StitchingPostProcAggregation")
166
165
 
167
166
  if isinstance(self.stitching_config, dict):
168
- stitching_type = StitchingType.from_value(
169
- self.stitching_config["stitching"]["type"]
170
- )
167
+ stitching_type = StitchingType(self.stitching_config["stitching"]["type"])
171
168
  if stitching_type is StitchingType.Z_PREPROC:
172
169
  self._stitching_config = PreProcessedZStitchingConfiguration.from_dict(
173
170
  self.stitching_config
@@ -127,9 +127,9 @@ class EDFTomoScan(_tsEDFTomoScan, TomwerScanBase):
127
127
  )
128
128
  return EDFTomoScan(scan=identifier.folder)
129
129
 
130
- def clear_caches(self):
131
- _tsEDFTomoScan.clear_caches(self)
132
- TomwerScanBase.clear_caches(self)
130
+ def clear_cache(self):
131
+ _tsEDFTomoScan.clear_cache(self)
132
+ TomwerScanBase.clear_cache(self)
133
133
 
134
134
  @staticmethod
135
135
  def directory_contains_scan(directory, src_pattern, dest_pattern):
@@ -178,9 +178,9 @@ class NXtomoScan(_tsNXtomoScan, TomwerScanBase):
178
178
  else:
179
179
  return os.path.exists(master_file + ".h5")
180
180
 
181
- def clear_caches(self):
182
- _tsNXtomoScan.clear_caches(self)
183
- TomwerScanBase.clear_caches(self)
181
+ def clear_cache(self):
182
+ _tsNXtomoScan.clear_cache(self)
183
+ TomwerScanBase.clear_cache(self)
184
184
 
185
185
  def is_abort(self, src_pattern, dest_pattern):
186
186
  """
@@ -92,10 +92,10 @@ class TomwerScanBase(TomwerObject):
92
92
  """
93
93
  raise NotImplementedError("Base class")
94
94
 
95
- def clear_caches(self):
95
+ def clear_cache(self):
96
96
  self._cache_proj_urls = None
97
97
  self._notify_ffc_rsc_missing = True
98
- super().clear_caches()
98
+ super().clear_cache()
99
99
 
100
100
  def _flat_field_correction(
101
101
  self,
@@ -19,7 +19,7 @@ class TomwerObject(Dataset):
19
19
  """util function to clear some heavy object from the cache"""
20
20
  raise NotImplementedError()
21
21
 
22
- def clear_caches(self):
22
+ def clear_cache(self):
23
23
  pass
24
24
 
25
25
  @property
@@ -11,12 +11,12 @@ def get_n_series(image_key_values: tuple | list, image_key_type: ImageKey) -> in
11
11
 
12
12
  :param image_key_values: list or tuple of image_keys to consider. Can be integers or tomoscan.esrf.scan.hdf5scan.ImageKey
13
13
  """
14
- image_key_type = ImageKey.from_value(image_key_type)
14
+ image_key_type = ImageKey(image_key_type)
15
15
  if image_key_type is ImageKey.INVALID:
16
16
  raise ValueError(
17
17
  "we can't count Invalid image keys series because those are ignored from tomoscan"
18
18
  )
19
- image_key_values = [ImageKey.from_value(img_key) for img_key in image_key_values]
19
+ image_key_values = [ImageKey(img_key) for img_key in image_key_values]
20
20
 
21
21
  # remove invalid frames
22
22
  image_key_values = numpy.array(
tomwer/core/utils/spec.py CHANGED
@@ -3,14 +3,17 @@ from __future__ import annotations
3
3
  import fileinput
4
4
  import logging
5
5
  import os
6
+ import pint
7
+
8
+ import fabio
6
9
 
7
- import fabio.edfimage
8
10
  from lxml import etree
9
- from pyunitsystem.metricsystem import MetricSystem
10
11
 
11
12
 
12
13
  _logger = logging.getLogger(__name__)
13
14
 
15
+ _ureg = pint.get_application_registry()
16
+
14
17
 
15
18
  def _getInformation(scan, refFile, information, _type, aliases=None):
16
19
  """
@@ -258,6 +261,6 @@ def getPixelSize(scan) -> float | None:
258
261
  value = float(ddict["IMAGE_PIXEL_SIZE_1".lower()])
259
262
  # for now pixel size are stored in microns. We want to return them in meter
260
263
  if value is not None:
261
- return value * MetricSystem.MICROMETER.value
264
+ return (value * _ureg.micrometer).to_base_units().magnitude
262
265
  else:
263
266
  return None
@@ -44,7 +44,7 @@ class ScanDiscoveryConfigWidget(qt.QGroupBox):
44
44
  raise NotImplementedError
45
45
 
46
46
  def setScanType(self, mode: ScanType):
47
- mode = ScanType.from_value(mode)
47
+ mode = ScanType(mode)
48
48
  if mode is ScanType.SPEC:
49
49
  self._specQRB.setChecked(True)
50
50
  elif mode is ScanType.BLISS:
@@ -287,11 +287,11 @@ class ReduceDarkFlatSelectorTableWidget(qt.QWidget):
287
287
  h5file=url.file_path(),
288
288
  path=url.data_path(),
289
289
  )
290
- for target in REDUCER_TARGET.values():
291
- if target in reduced_info_dict:
292
- reduced_frames = reduced_info_dict[target]
290
+ for target in REDUCER_TARGET:
291
+ if target.value in reduced_info_dict:
292
+ reduced_frames = reduced_info_dict[target.value]
293
293
  reduced_frames["reduce_frames_name"] = (
294
- f"{target} from {url.data_path()}@{os.path.basename(url.file_path())}"
294
+ f"{target.value} from {url.data_path()}@{os.path.basename(url.file_path())}"
295
295
  )
296
296
  result.append(reduced_frames)
297
297
 
@@ -112,9 +112,7 @@ class ImageKeyWindow(qt.QMainWindow):
112
112
  def setModifications(self, modifications):
113
113
  self._mainWindow.clearModifcations()
114
114
  image_keys_set = set(modifications.values())
115
- image_keys_set = set(
116
- [_ImageKey.from_value(image_key) for image_key in image_keys_set]
117
- )
115
+ image_keys_set = set([_ImageKey(image_key) for image_key in image_keys_set])
118
116
  for image_key_type in image_keys_set:
119
117
  self._mainWindow.applyModifications(
120
118
  modifications=modifications, new_image_key=image_key_type
@@ -432,7 +430,7 @@ class _ImageKeyList(qt.QTableWidget):
432
430
  self.setItem(i_frame, 0, _item)
433
431
 
434
432
  # current image key
435
- current_image_key = _ImageKey.from_value(frame.image_key)
433
+ current_image_key = _ImageKey(frame.image_key)
436
434
  current_image_key = self._IMAGE_KEYS_INV[current_image_key]
437
435
  currentImgKeyItem = qt.QLabel(current_image_key, self)
438
436
  self.setCellWidget(i_frame, 1, currentImgKeyItem)
@@ -442,7 +440,7 @@ class _ImageKeyList(qt.QTableWidget):
442
440
  new_image_key = frames_new_keys[frame.index]
443
441
  else:
444
442
  new_image_key = frame.image_key
445
- new_image_key = _ImageKey.from_value(new_image_key)
443
+ new_image_key = _ImageKey(new_image_key)
446
444
  new_image_key = self._IMAGE_KEYS_INV[new_image_key]
447
445
  newImgKeyItem = _ImageKeyComboBox(parent=self, image_key=new_image_key)
448
446
  self._imageKeyComboboxes[index] = newImgKeyItem
@@ -694,16 +692,16 @@ class ImageKeyUpgraderList(qt.QTableWidget):
694
692
  self.setCellWidget(i_operation, 1, remove_button)
695
693
 
696
694
  def addOperation(self, from_image_key: _ImageKey, to_image_key: _ImageKey):
697
- from_image_key = _ImageKey.from_value(from_image_key)
698
- to_image_key = _ImageKey.from_value(to_image_key)
695
+ from_image_key = _ImageKey(from_image_key)
696
+ to_image_key = _ImageKey(to_image_key)
699
697
 
700
698
  self._operations[from_image_key] = to_image_key
701
699
  self._update()
702
700
  self.sigOperationsChanged.emit()
703
701
 
704
702
  def removeOperation(self, from_image_key: _ImageKey, to_image_key: _ImageKey):
705
- from_image_key = _ImageKey.from_value(from_image_key)
706
- to_image_key = _ImageKey.from_value(to_image_key)
703
+ from_image_key = _ImageKey(from_image_key)
704
+ to_image_key = _ImageKey(to_image_key)
707
705
  if (
708
706
  from_image_key not in self._operations
709
707
  or self._operations[from_image_key] != to_image_key