From 4ba01d78b432fe1a90465d7b7ff8375ccb5351d2 Mon Sep 17 00:00:00 2001 From: wyzula-jan Date: Wed, 22 Oct 2025 13:59:44 +0200 Subject: [PATCH] wip changed to custom 2d positioner box --- .../bec_widgets/widgets/xray_eye/x_ray_eye.py | 106 +++++++++++++----- 1 file changed, 78 insertions(+), 28 deletions(-) diff --git a/csaxs_bec/bec_widgets/widgets/xray_eye/x_ray_eye.py b/csaxs_bec/bec_widgets/widgets/xray_eye/x_ray_eye.py index f2cf7c1..f02957a 100644 --- a/csaxs_bec/bec_widgets/widgets/xray_eye/x_ray_eye.py +++ b/csaxs_bec/bec_widgets/widgets/xray_eye/x_ray_eye.py @@ -1,11 +1,13 @@ from __future__ import annotations +from PySide6.QtWidgets import QToolButton, QSpinBox from qtpy.QtCore import Qt, QTimer from qtpy.QtWidgets import QDoubleSpinBox from qtpy.QtWidgets import QPushButton from qtpy.QtWidgets import QWidget, QVBoxLayout, QHBoxLayout, QGridLayout, QLabel, QLineEdit, QSizePolicy, QFrame from bec_lib import bec_logger +from bec_qthemes import material_icon from bec_widgets import BECWidget, SafeSlot, SafeProperty from bec_widgets.widgets.control.device_control.positioner_box import PositionerBox2D from bec_widgets.widgets.plots.image.image import Image @@ -20,7 +22,70 @@ logger = bec_logger.logger DEVICE_HORIZONTAL = "samx" DEVICE_VERTICAL = "samy" CAMERA = ("cam_flomni_overview","preview") -PIXEL_CALIBRATION = 0.1 / 113 # .2 with binning #TODO needed here or not? + +class XRayEye2DControl(QWidget): + def __init__(self, parent=None,step_size:int=100): + super().__init__(parent=parent) + self._step_size = step_size + self.root_layout = QGridLayout(self) + + # Up + self.move_up_button = QToolButton(parent=self) + self.move_up_button.setIcon(material_icon('keyboard_double_arrow_up')) + self.root_layout.addWidget(self.move_up_button,0,2) + # Up tweak button + self.move_up_tweak_button = QToolButton(parent=self) + self.move_up_tweak_button.setIcon(material_icon('keyboard_arrow_up')) + self.root_layout.addWidget(self.move_up_tweak_button,1,2) + + # Left + self.move_left_button = QToolButton(parent=self) + self.move_left_button.setIcon(material_icon('keyboard_double_arrow_left')) + self.root_layout.addWidget(self.move_left_button,2,0) + # Left tweak button + self.move_left_tweak_button = QToolButton(parent=self) + self.move_left_tweak_button.setIcon(material_icon('keyboard_arrow_left')) + self.root_layout.addWidget(self.move_left_tweak_button,2,1) + + # Right + self.move_right_button = QToolButton(parent=self) + self.move_right_button.setIcon(material_icon('keyboard_double_arrow_right')) + self.root_layout.addWidget(self.move_right_button,2,4) + # Right tweak button + self.move_right_tweak_button = QToolButton(parent=self) + self.move_right_tweak_button.setIcon(material_icon('keyboard_arrow_right')) + self.root_layout.addWidget(self.move_right_tweak_button,2,3) + + # Down + self.move_down_button = QToolButton(parent=self) + self.move_down_button.setIcon(material_icon('keyboard_double_arrow_down')) + self.root_layout.addWidget(self.move_down_button,4,2) + # Down tweak button + self.move_down_tweak_button = QToolButton(parent=self) + self.move_down_tweak_button.setIcon(material_icon('keyboard_arrow_down')) + self.root_layout.addWidget(self.move_down_tweak_button,3,2) + + @SafeProperty(int) + def step_size(self)->int: + return self._step_size + + @step_size.setter + def step_size(self,step_size:int): + self._step_size = step_size + + @SafeSlot(bool) + def enable_controls_hor(self,enable:bool): + self.move_left_button.setEnabled(enable) + self.move_left_tweak_button.setEnabled(enable) + self.move_right_button.setEnabled(enable) + self.move_right_tweak_button.setEnabled(enable) + + @SafeSlot(bool) + def enable_controls_ver(self,enable:bool): + self.move_up_button.setEnabled(enable) + self.move_up_tweak_button.setEnabled(enable) + self.move_down_button.setEnabled(enable) + self.move_down_tweak_button.setEnabled(enable) class XRayEye(BECWidget, QWidget): @@ -71,13 +136,7 @@ class XRayEye(BECWidget, QWidget): self.control_panel_layout.addWidget(self._create_separator()) # 2D Positioner (fixed size) - self.motor_control_2d = PositionerBox2D(parent=self, device_hor=DEVICE_HORIZONTAL, device_ver=DEVICE_VERTICAL) - self.motor_control_2d.hide_device_boxes = True - self.motor_control_2d.adjustSize() - m_hint = self.motor_control_2d.sizeHint() - self.motor_control_2d.setFixedWidth(m_hint.width()) - self.motor_control_2d.setMaximumHeight(m_hint.height()) - self.motor_control_2d.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed) + self.motor_control_2d = XRayEye2DControl(parent=self) self.control_panel_layout.addWidget(self.motor_control_2d, 0, Qt.AlignTop | Qt.AlignRight) # separator @@ -85,25 +144,17 @@ class XRayEye(BECWidget, QWidget): # Step size label step_size_form = QGridLayout() - #Horizontal - self.step_size_horizontal = QDoubleSpinBox(parent=self) - self.step_size_horizontal.setDecimals(4) - self.step_size_horizontal.setRange(0.0001, 100000) - self.step_size_horizontal.setSingleStep(0.1) - self.step_size_horizontal.setValue(1.0) - #Vertical - self.step_size_vertical = QDoubleSpinBox(parent=self) - self.step_size_vertical.setDecimals(4) - self.step_size_vertical.setRange(0.0001, 100000) - self.step_size_vertical.setSingleStep(0.1) - self.step_size_vertical.setValue(1.0) + #General Step size + self.step_size = QSpinBox(parent=self) + self.step_size.setRange(10, 100) + self.step_size.setSingleStep(10) + self.step_size.setValue(100) # Submit button self.submit_button = QPushButton("Submit", parent=self) # Add to layout form step_size_form.addWidget(QLabel("Horizontal", parent=self),0,0) - step_size_form.addWidget(self.step_size_horizontal,0,1) + step_size_form.addWidget(self.step_size, 0, 1) step_size_form.addWidget(QLabel("Vertical", parent=self),1,0) - step_size_form.addWidget(self.step_size_vertical,1,1) step_size_form.addWidget(self.submit_button,2,0,1,2) # Add form to control panel @@ -137,13 +188,11 @@ class XRayEye(BECWidget, QWidget): def _make_connections(self): # Fetch initial state self.on_live_view_enabled(True) - self.step_size_horizontal.setValue(self.motor_control_2d.step_size_hor) - self.step_size_vertical.setValue(self.motor_control_2d.step_size_ver) + self.step_size.setValue(self.motor_control_2d.step_size) # Make connections self.live_preview_toggle.enabled.connect(self.on_live_view_enabled) - self.step_size_horizontal.valueChanged.connect(lambda x: self.motor_control_2d.setProperty("step_size_hor",x)) - self.step_size_vertical.valueChanged.connect(lambda x: self.motor_control_2d.setProperty("step_size_ver",x)) + self.step_size.valueChanged.connect(lambda x: self.motor_control_2d.setProperty("step_size",x)) self.submit_button.clicked.connect(self.submit) def _create_separator(self): @@ -174,6 +223,7 @@ class XRayEye(BECWidget, QWidget): ################################################################################ @SafeProperty(bool) def enable_live_view(self): + """Get or set the live view enabled state.""" return self.live_preview_toggle.checked @enable_live_view.setter @@ -240,8 +290,8 @@ class XRayEye(BECWidget, QWidget): @SafeSlot(bool,bool) def on_motors_enable(self,x_enable:bool,y_enable:bool): - self.motor_control_2d.enable_controls_hor = x_enable - self.motor_control_2d.enable_controls_ver = y_enable + self.motor_control_2d.enable_controls_hor(x_enable) + self.motor_control_2d.enable_controls_ver(y_enable) @SafeSlot(str) def set_message(self, msg: str):