From cccf629618453e9c2e4aff2acf5800c2e66c670d Mon Sep 17 00:00:00 2001 From: martinappleby Date: Wed, 5 Nov 2025 10:56:47 +0100 Subject: [PATCH] GUI: reload_parameters, reload_parameters button and update_data-collection_parameters is now "owned" by scan_settings_panel.py --- gui/src/aaregui/panels/scan_settings_panel.py | 95 ++++++++++++++++++- 1 file changed, 94 insertions(+), 1 deletion(-) diff --git a/gui/src/aaregui/panels/scan_settings_panel.py b/gui/src/aaregui/panels/scan_settings_panel.py index 9e7e2cc0..f6428642 100644 --- a/gui/src/aaregui/panels/scan_settings_panel.py +++ b/gui/src/aaregui/panels/scan_settings_panel.py @@ -1,5 +1,5 @@ from PySide6.QtCore import Slot, Signal -from PySide6.QtWidgets import QWidget, QGridLayout, QLabel, QFrame +from PySide6.QtWidgets import QWidget, QGridLayout, QLabel, QFrame, QPushButton from aaredaqlib.diffraction_geometry import DiffractionGeometry from aaredaqlib.models import DAQStatusModel @@ -22,6 +22,14 @@ class ScanSettingsPanel(QWidget): self._dtz = default_dtz self._high_res = diffraction.resolution_angstrom(self._dtz) + self._sample = None + self._params = None + self._last_sample_id = None + self._sample_space_group = None + self._sample_cell_parameters = None + self._sample_pdb_id = None + self._target_dose = None + self._layout = QGridLayout(self) self._layout.addWidget(QLabel("High resolution", parent=self), 0, 0) @@ -47,6 +55,12 @@ class ScanSettingsPanel(QWidget): self._layout.addWidget(self.transmission_enter, 2, 1, 1, 3) self.transmission_enter.newValue.connect(self.set_transmission) + self.reload_params_button = QPushButton("Reload DB params") + self.reload_params_button.setToolTip("Reload data collection parameters from database") + self.reload_params_button.clicked.connect(self.reload_parameters) + self.reload_params_button.setVisible(False) # Child classes should make it visible + + @Slot(DAQStatusModel) def update_daq_status(self, s: DAQStatusModel): self.dtz_enter.update_limits(s.bl.dtz_min, s.bl.dtz_max) @@ -54,6 +68,22 @@ class ScanSettingsPanel(QWidget): self.__diffraction.resolution_angstrom(s.bl.dtz_max)) self.__diffraction = s.diffraction + # Update sample and parameters + if s.sample is not None: + self._sample = s.sample + self._params = s.sample.aaredb_params if hasattr(s.sample, 'aaredb_params') else None + + # Enable reload button only if sample has parameters + self.reload_params_button.setEnabled(self._params is not None) + + # Check if this is a new sample - if so, update parameters + if self._last_sample_id != s.sample.db_id: + self.update_data_collection_parameters() + else: + self._sample = None + self._params = None + self.reload_params_button.setEnabled(False) + @Slot(float) def set_dtz(self, v: float): self._dtz = v @@ -73,3 +103,66 @@ class ScanSettingsPanel(QWidget): self._transmission = v self.transmission_enter.update_value(self._transmission) self.transmission_updated.emit(self._transmission) + + @Slot() + def reload_parameters(self): + """Manually reload data collection parameters from database. + This allows users to reset their changes back to database values.""" + # Temporarily clear the last sample ID to force reload + temp_id = self._last_sample_id + self._last_sample_id = None + self.update_data_collection_parameters() + self._last_sample_id = temp_id + + def update_data_collection_parameters(self): + """Update data collection parameters when a new sample is loaded. + Only updates fields if database parameters exist, otherwise keeps defaults. + This should only be called when a new sample is mounted. + + Child classes can override get_parameter_mappings() to specify which + parameters should be loaded.""" + + if self._sample is None: + return + + # Update the last sample ID to prevent repeated updates + self._last_sample_id = self._sample.db_id + + # If no parameters exist, we keep the current (default) values + if self._params is None: + return + + # Get parameter mappings from child class + param_mappings = self.get_parameter_mappings() + + # Update parameters based on mappings + for param_name, widget, converter in param_mappings: + value = getattr(self._params, param_name, None) + if value is not None: + widget.update_value(converter(value) if converter else value) + + # Handle transmission with conversion (common to all panels) + if (transmission := getattr(self._params, 'transmission', None)) is not None: + transmission_value = transmission / 100.0 if transmission > 1.0 else transmission + self._transmission = transmission_value + self.transmission_enter.update_value(transmission_value) + + # Handle target resolution (common to all panels) + if (target_res := getattr(self._params, 'targetresolution', None)) is not None: + self._high_res = target_res + self.high_res_enter.update_value(target_res) + + # Store metadata (common to all panels) + self._sample_space_group = getattr(self._params, 'spacegroupnumber', None) + self._sample_cell_parameters = getattr(self._params, 'cellparameters', None) + self._sample_pdb_id = getattr(self._params, 'pdbid', None) + self._target_dose = getattr(self._params, 'dose', None) + + def get_parameter_mappings(self): + """Return a list of (param_name, widget, converter) tuples. + Child classes should override this to specify their specific parameters. + + Returns: + List of tuples: (parameter_name, widget, converter_function or None) + """ + return []