feat(ui_builders_shared): implement class ScanSlicerUiSharedMixin

This commit is contained in:
dev 2026-02-26 12:20:34 +00:00
parent 736a1626aa
commit 59be2277b7

View file

@ -89,3 +89,155 @@ class ScrollbarWheelOnlyScrollArea(QScrollArea):
return return
super().wheelEvent(event) super().wheelEvent(event)
# ScanSlicerUiSharedMixin: class definition for ScanSlicer behavior.
class ScanSlicerUiSharedMixin:
# _build_section_title: function definition for ScanSlicer behavior.
def _build_section_title(self, text):
label = QLabel(text)
title_font = QFont(label.font())
title_font.setPixelSize(self.SECTION_TITLE_FONT_PX)
title_font.setBold(True)
label.setFont(title_font)
label.setStyleSheet(
f"padding-top: {self.SECTION_TITLE_VPAD}px; "
f"padding-bottom: {self.SECTION_TITLE_VPAD}px;"
)
return label
# _add_vertical_spacer: function definition for ScanSlicer behavior.
def _add_vertical_spacer(self, target_layout, row_index):
target_layout.addItem(
QSpacerItem(
0,
self.VERTICAL_SPACER_HEIGHT,
QSizePolicy.Policy.Minimum,
QSizePolicy.Policy.Fixed,
),
row_index,
0,
1,
2,
)
# _new_group_layout: function definition for ScanSlicer behavior.
def _new_group_layout(self):
group = QGroupBox()
group_layout = QGridLayout(group)
group_layout.setContentsMargins(
self.PANEL_CONTENT_MARGIN,
self.PANEL_CONTENT_MARGIN,
self.PANEL_CONTENT_MARGIN,
self.PANEL_CONTENT_MARGIN,
)
return group, group_layout
# _add_full_width_widget: function definition for ScanSlicer behavior.
def _add_full_width_widget(self, target_layout, row_index, widget):
target_layout.addWidget(widget, row_index, 0, 1, 2)
return row_index + 1
# _add_spacer_row: function definition for ScanSlicer behavior.
def _add_spacer_row(self, target_layout, row_index):
self._add_vertical_spacer(target_layout, row_index)
return row_index + 1
# _add_label_row: function definition for ScanSlicer behavior.
def _add_label_row(self, target_layout, row_index, text):
return self._add_full_width_widget(target_layout, row_index, QLabel(text))
# _create_panel_button: function definition for ScanSlicer behavior.
def _create_panel_button(self, text, callback, tooltip=None):
button = QPushButton(text)
if tooltip:
button.setToolTip(tooltip)
button.clicked.connect(callback)
return button
# _build_parameter_block: function definition for ScanSlicer behavior.
def _build_parameter_block(self, parent, name, parameter):
param_block = QWidget(parent)
param_block_layout = QVBoxLayout(param_block)
param_block_layout.setContentsMargins(0, 0, 0, self.VERTICAL_SPACER_HEIGHT)
param_block_layout.setSpacing(3)
param_label = QLabel(parameter.label)
param_label.setWordWrap(True)
param_block_layout.addWidget(param_label)
if parameter.label_secondary:
param_secondary_label = QLabel(parameter.label_secondary)
param_secondary_label.setWordWrap(True)
secondary_font = QFont(param_secondary_label.font())
secondary_info = QFontInfo(secondary_font)
if secondary_info.pixelSize() > 0:
secondary_font.setPixelSize(max(1, secondary_info.pixelSize() - 2))
elif secondary_info.pointSizeF() > 0:
secondary_font.setPointSizeF(max(1.0, secondary_info.pointSizeF() - 1.0))
else:
secondary_font.setPointSize(9)
param_secondary_label.setFont(secondary_font)
param_secondary_label.setStyleSheet("color: gray;")
param_block_layout.addWidget(param_secondary_label)
if name in self.CHOICE_PARAM_OPTIONS:
control = QComboBox(param_block)
for option_label, option_value in self.CHOICE_PARAM_OPTIONS[name]:
control.addItem(option_label, option_value)
choice_index = control.findData(parameter.get())
if choice_index >= 0:
control.setCurrentIndex(choice_index)
# on_param_choice_changed: function definition for ScanSlicer behavior.
def on_param_choice_changed(index, p=parameter, combo=control, param_name=name):
value = combo.itemData(index)
p.set(value)
if param_name in ("bw_method", "detect_pipeline", "morph_op"):
self.update_parameter_visibility()
if not self.updating_param_controls:
self.set_preset_dropdown_custom()
control.currentIndexChanged.connect(on_param_choice_changed)
param_block_layout.addWidget(control)
else:
slider_row = QWidget(param_block)
slider_row_layout = QHBoxLayout(slider_row)
slider_row_layout.setContentsMargins(0, 0, 0, 0)
slider_row_layout.setSpacing(6)
control = QSlider(Qt.Orientation.Horizontal)
control.setRange(parameter.min, parameter.max)
control.setSingleStep(max(1, parameter.step))
control.setPageStep(max(1, parameter.step))
control.setTickInterval(max(1, parameter.step))
control.setValue(parameter.get())
value_label = QLabel(str(parameter.get()))
value_label.setAlignment(Qt.AlignRight | Qt.AlignVCenter)
value_label.setMinimumWidth(40)
# on_param_slider_changed: function definition for ScanSlicer behavior.
def on_param_slider_changed(value, p=parameter, slider=control, label=value_label, param_name=name):
step = max(1, p.step)
snapped = p.min + round((value - p.min) / step) * step
snapped = min(p.max, max(p.min, snapped))
if snapped != value:
slider.blockSignals(True)
slider.setValue(snapped)
slider.blockSignals(False)
value = snapped
p.set(value)
label.setText(str(p.get()))
if param_name in ("bw_method", "detect_pipeline", "morph_op"):
self.update_parameter_visibility()
if not self.updating_param_controls:
self.set_preset_dropdown_custom()
control.valueChanged.connect(on_param_slider_changed)
slider_row_layout.addWidget(control, 1)
slider_row_layout.addWidget(value_label, 0)
param_block_layout.addWidget(slider_row)
self.param_controls[name] = control
self.param_blocks[name] = param_block
return param_block