Skip to content

Commit

Permalink
Merge branch 'motor_info_h5' of https://github.com/mspito/pymca into …
Browse files Browse the repository at this point in the history
…motor_info
  • Loading branch information
vasole committed Nov 27, 2024
2 parents bd73434 + bc2f0d2 commit b3992e9
Show file tree
Hide file tree
Showing 4 changed files with 156 additions and 3 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ docs/_build/
# cython generated files
src/PyMca5/PyMcaGraph/ctools/_ctools/cython/*.c
src/PyMca5/PyMcaPhysics/xas/_xas/cython/*.c
src/PyMca5/PyMcaMath/mva/_cython_kmeans/*.c

# PyCharm meta data
.idea/
Expand Down
49 changes: 49 additions & 0 deletions src/PyMca5/PyMcaCore/NexusTools.py
Original file line number Diff line number Diff line change
Expand Up @@ -510,6 +510,55 @@ def getPositionersGroup(h5file, path):
positioners = group
return positioners

def getStartingPositionersGroup(h5file, path):
"""
Retrieve the start positioners group associated to a path
retrieving them from the same entry.
It assumes they are either in:
- NXentry/NXinstrument/positioners_start or
- NXentry/NXinstrument/positioners or
- NXentry/measurement/pre_scan_snapshot
"""
entry_path = getEntryName(path, h5file=h5file)
instrument = getNXClassGroups(h5file, entry_path, ["NXinstrument", b"NXinstrument"], single=True)
positioners = None
if len(instrument):
instrument = instrument[0]
for key in instrument.keys():
if key in ["positioners_start", b"positioners_start"]:
positioners = instrument[key]
if not isGroup(positioners):
positioners = None
if positioners is None:
positioners = getPositionersGroup(h5file, path)
return positioners

def getStartingPositionerValues(h5file, path):
"""
Retrieve the start positioners names, values and units associated to a path
retrieving them from the same entry.
It assumes they are either in:
- NXentry/NXinstrument/positioners_start or
- NXentry/NXinstrument/positioners or
- NXentry/measurement/pre_scan_snapshot
"""
nxpositioners = getStartingPositionersGroup(h5file, path)
positions = list()
if nxpositioners is None:
return positions
for name, dset in nxpositioners.items():
if not isinstance(dset, h5py.Dataset):
continue
idx = (0,) * dset.ndim
positions.append((name, dset[idx], dset.attrs.get("units", "")))
return positions

def getMeasurementGroup(h5file, path):
"""
Retrieve the measurement group associated to a path
Expand Down
101 changes: 101 additions & 0 deletions src/PyMca5/PyMcaGui/io/hdf5/NexusInfo.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
import h5py

from PyMca5.PyMcaGui import PyMcaQt as qt
from PyMca5.PyMcaCore.NexusTools import getStartingPositionerValues

from . import HDF5Info


class NexusMotorInfoWidget(qt.QWidget):
def __init__(self, parent):
super().__init__(parent)

self.mainLayout = qt.QVBoxLayout(self)
self.mainLayout.setContentsMargins(0, 0, 0, 0)
self.mainLayout.setSpacing(2)

self.label = qt.QLabel(self)
self.label.setText("Number of motors: 0")

column_names = ["Name", "Value", "Units"]
self._column_names = column_names

self.table = qt.QTableWidget(self)
self.table.setColumnCount(len(column_names))
for i in range(len(column_names)):
item = self.table.horizontalHeaderItem(i)
if item is None:
item = qt.QTableWidgetItem(column_names[i], qt.QTableWidgetItem.Type)
item.setText(column_names[i])
self.table.setHorizontalHeaderItem(i, item)
self.table.setSortingEnabled(True)

self.mainLayout.addWidget(self.label)
self.mainLayout.addWidget(self.table)

def setInfoDict(self, ddict):
if "motors" in ddict:
self._setInfoDict(ddict["motors"])
else:
self._setInfoDict(ddict)

def _setInfoDict(self, ddict):
nrows = len(ddict.get(self._column_names[0], []))
self.label.setText("Number of motors: %d" % nrows)
self.table.setRowCount(nrows)

if not nrows:
self.hide()
return

for row in range(nrows):
for col, label in enumerate(self._column_names):
text = str(ddict[label][row])
item = self.table.item(row, col)
if item is None:
item = qt.QTableWidgetItem(text, qt.QTableWidgetItem.Type)
item.setFlags(qt.Qt.ItemIsSelectable | qt.Qt.ItemIsEnabled)
self.table.setItem(row, col, item)
else:
item.setText(text)

for col in range(len(self._column_names)):
self.table.resizeColumnToContents(col)


class NexusInfoWidget(HDF5Info.HDF5InfoWidget):

def _build(self):
super()._build()
self.motorInfoWidget = NexusMotorInfoWidget(self)
self.addTab(self.motorInfoWidget, "Motors")

def setInfoDict(self, ddict):
super().setInfoDict(ddict)
self.motorInfoWidget.setInfoDict(ddict)


def getInfo(hdf5File, node):
"""
hdf5File is and HDF5 file-like insance
node is the posix path to the node
"""
info = HDF5Info.getInfo(hdf5File, node)
info["motors"] = get_motor_positions(hdf5File, node)
return info


def get_motor_positions(hdf5File, node):
node = hdf5File[node]

nxentry_name = node.name.split("/")[1]
if not nxentry_name:
return dict()

nxentry = hdf5File[nxentry_name]
if not isinstance(nxentry, h5py.Group):
return dict()

positions = getStartingPositionerValues(hdf5File, nxentry_name)
column_names = "Name", "Value", "Units"
return dict(zip(column_names, zip(*positions)))
8 changes: 5 additions & 3 deletions src/PyMca5/PyMcaGui/io/hdf5/QNexusWidget.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@
QString = str

from . import HDF5Widget
from . import HDF5Info
from . import NexusInfo
from . import HDF5CounterTable
from . import HDF5McaTable
from . import QNexusWidgetActions
Expand Down Expand Up @@ -123,7 +123,7 @@ def __init__(self, parent=None, mca=False, buttons=False):
self._autoCntList = []
self._autoAliasList = []
self._defaultModel = HDF5Widget.FileModel()
self.getInfo = HDF5Info.getInfo
self.getInfo = NexusInfo.getInfo
self._modelDict = {}
self._widgetDict = {}
self._lastWidgetId = None
Expand Down Expand Up @@ -507,8 +507,9 @@ def showInfoWidget(self, filename, name, dset=False):
phynxFile = self.data._sourceObjectList[fileIndex]
else:
phynxFile = HDF5Widget.h5open(filename)

info = self.getInfo(phynxFile, name)
widget = HDF5Info.HDF5InfoWidget()
widget = NexusInfo.NexusInfoWidget()
widget.notifyCloseEventToWidget(self)
title = os.path.basename(filename)
title += " %s" % name
Expand All @@ -531,6 +532,7 @@ def sourceObjectDestroyed(weakrefReference):
del self._widgetDict[wid]
widget._sourceObjectWeakReference = weakref.ref(phynxFile,
sourceObjectDestroyed)

widget.setInfoDict(info)
# todo: this first `if` block can be dropped when silx is a hard dependency
if dset and Hdf5NodeView is None:
Expand Down

0 comments on commit b3992e9

Please sign in to comment.