Skip to content

Commit e498551

Browse files
authored
Merge pull request #25 from Brain-Modulation-Lab/enh/group-flexible
enh: program choice improved and disabled electrode checkbox redefined
2 parents ae16201 + d5c5c1e commit e498551

12 files changed

Lines changed: 117 additions & 6 deletions

src/clinical_dbs_annotator/__main__.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
import logging
99
import sys
1010

11+
import PySide6.QtSvg # noqa: F401 - required to enable SVG rendering in QSS
1112
from PySide6.QtWidgets import QApplication
1213

1314
from .logging_config import setup_logging

src/clinical_dbs_annotator/utils/theme_manager.py

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,13 +94,26 @@ def load_stylesheet(self, theme: Theme) -> str:
9494
Raises:
9595
FileNotFoundError: If stylesheet file doesn't exist
9696
"""
97+
import re
98+
9799
path = self.get_theme_stylesheet_path(theme)
98100

99101
if not os.path.exists(path):
100102
raise FileNotFoundError(f"Theme stylesheet not found: {path}")
101103

102104
with open(path, encoding="utf-8") as f:
103-
return f.read()
105+
content = f.read()
106+
107+
base_dir = os.path.dirname(path)
108+
109+
def _resolve(match):
110+
url = match.group(1).strip().strip("\"'")
111+
if not os.path.isabs(url):
112+
abs_url = os.path.normpath(os.path.join(base_dir, url))
113+
return f"url({abs_url.replace(os.sep, '/')})"
114+
return match.group(0)
115+
116+
return re.sub(r"url\(([^)]+)\)", _resolve, content)
104117

105118
def apply_theme(self, theme: Theme, app: QApplication = None) -> None:
106119
"""

src/clinical_dbs_annotator/views/step1_view.py

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -247,6 +247,12 @@ def _create_settings_group(self) -> QGroupBox:
247247
group_row = QGroupBox("Program")
248248
group_row_layout = QHBoxLayout()
249249
self.group_combo = QComboBox()
250+
self.group_combo.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Fixed)
251+
# Prevent focus rectangle on dropdown
252+
self.group_combo.view().window().setAttribute(
253+
Qt.WA_TranslucentBackground, False
254+
)
255+
self.group_combo.view().setStyleSheet("QAbstractItemView { outline: none; }")
250256
# Load program names from config
251257
program_config = get_program_config_manager()
252258
programs = program_config.get_all_programs()
@@ -258,10 +264,12 @@ def _create_settings_group(self) -> QGroupBox:
258264
edit_programs_btn = QPushButton()
259265
edit_programs_btn.setIcon(self._create_settings_icon())
260266
edit_programs_btn.setToolTip("Edit program names")
261-
edit_programs_btn.setFixedSize(24, 24)
267+
edit_programs_btn.setObjectName("programSettingsButton")
262268
edit_programs_btn.clicked.connect(self._edit_program_names)
263269
group_row_layout.addWidget(edit_programs_btn)
264270

271+
group_row_layout.addStretch()
272+
265273
group_row.setLayout(group_row_layout)
266274

267275
freq_limits = STIMULATION_LIMITS["frequency"]

src/clinical_dbs_annotator/views/step3_view.py

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -230,6 +230,12 @@ def _create_stimulation_params_group(self) -> QWidget:
230230
group_row = QGroupBox("Program")
231231
group_row_layout = QHBoxLayout()
232232
self.group_combo = QComboBox()
233+
self.group_combo.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Fixed)
234+
# Prevent focus rectangle on dropdown
235+
self.group_combo.view().window().setAttribute(
236+
Qt.WA_TranslucentBackground, False
237+
)
238+
self.group_combo.view().setStyleSheet("QAbstractItemView { outline: none; }")
233239
# Load program names from config
234240
program_config = get_program_config_manager()
235241
programs = program_config.get_all_programs()
@@ -241,10 +247,12 @@ def _create_stimulation_params_group(self) -> QWidget:
241247
edit_programs_btn = QPushButton()
242248
edit_programs_btn.setIcon(self._create_settings_icon())
243249
edit_programs_btn.setToolTip("Edit program names")
244-
edit_programs_btn.setFixedSize(24, 24)
250+
edit_programs_btn.setObjectName("programSettingsButton")
245251
edit_programs_btn.clicked.connect(self._edit_program_names)
246252
group_row_layout.addWidget(edit_programs_btn)
247253

254+
group_row_layout.addStretch()
255+
248256
group_row.setLayout(group_row_layout)
249257

250258
freq_limits = STIMULATION_LIMITS["frequency"]

src/logs/program_names.json

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"custom_programs": [
3+
"Sleep settings"
4+
]
5+
}

styles/checkbox_check_dark.svg

Lines changed: 3 additions & 0 deletions
Loading

styles/checkbox_check_light.svg

Lines changed: 3 additions & 0 deletions
Loading

styles/dark_theme.qss

Lines changed: 36 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ QComboBox {
6464
padding: 6px 10px;
6565
font-size: 12px;
6666
font-weight: 500;
67+
min-width: 120px;
6768
}
6869

6970
QComboBox:hover {
@@ -101,12 +102,12 @@ QComboBox QAbstractItemView {
101102
selection-color: white;
102103
padding: 4px;
103104
font-size: 12px;
105+
show-decoration-selected: 0;
104106
}
105107

106108
QComboBox QAbstractItemView::item {
107109
background-color: #334155;
108110
padding: 8px 12px;
109-
border-bottom: 1px solid #475569;
110111
min-height: 20px;
111112
}
112113

@@ -117,6 +118,7 @@ QComboBox QAbstractItemView::item:hover {
117118
QComboBox QAbstractItemView::item:selected {
118119
background-color: #f59e0b;
119120
color: white;
121+
border-radius: 4px;
120122
}
121123

122124

@@ -301,6 +303,19 @@ QGroupBox::title {
301303
background-color: #1e293b;
302304
}
303305

306+
QGroupBox::indicator:unchecked {
307+
border: 1px solid #64748b;
308+
border-radius: 2px;
309+
margin-top: 2px;
310+
}
311+
312+
QGroupBox::indicator:checked {
313+
border: 1px solid #64748b;
314+
border-radius: 2px;
315+
margin-top: 2px;
316+
image: url(checkbox_check_dark.svg);
317+
}
318+
304319
/* Horizontal Lines */
305320
QFrame[frameShape="4"] {
306321
background: #334155;
@@ -374,6 +389,26 @@ QPushButton#theme_toggle:pressed {
374389
background-color: #1e293b;
375390
}
376391

392+
/* Program Settings Button - Square with same height as dropdown */
393+
QPushButton#programSettingsButton {
394+
background-color: #334155;
395+
border: 1px solid #475569;
396+
border-radius: 4px;
397+
width: 34px;
398+
height: 34px;
399+
padding: 0;
400+
icon-size: 16px;
401+
}
402+
403+
QPushButton#programSettingsButton:hover {
404+
background-color: #475569;
405+
border-color: #f59e0b;
406+
}
407+
408+
QPushButton#programSettingsButton:pressed {
409+
background-color: #1e293b;
410+
}
411+
377412
/* Tooltips */
378413
QToolTip {
379414
background-color: #334155;

styles/light_theme.qss

Lines changed: 32 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ QComboBox {
6464
padding: 6px 10px;
6565
font-size: 12px;
6666
font-weight: 500;
67+
min-width: 120px;
6768
}
6869

6970
QComboBox:hover {
@@ -91,11 +92,11 @@ QComboBox QAbstractItemView {
9192
selection-color: white;
9293
padding: 4px;
9394
font-size: 12px;
95+
show-decoration-selected: 0;
9496
}
9597

9698
QComboBox QAbstractItemView::item {
9799
padding: 8px 12px;
98-
border-bottom: 1px solid #e2e8f0;
99100
min-height: 20px;
100101
}
101102

@@ -106,6 +107,7 @@ QComboBox QAbstractItemView::item:hover {
106107
QComboBox QAbstractItemView::item:selected {
107108
background-color: #b45309;
108109
color: white;
110+
border-radius: 4px;
109111
}
110112

111113
/* MultiSelectComboBox - Enhanced styling */
@@ -152,6 +154,7 @@ MultiSelectComboBox QAbstractItemView {
152154
selection-color: white;
153155
padding: 4px;
154156
font-size: 12px;
157+
show-decoration-selected: 0;
155158
}
156159

157160
MultiSelectComboBox QAbstractItemView::item {
@@ -167,6 +170,7 @@ MultiSelectComboBox QAbstractItemView::item:hover {
167170
MultiSelectComboBox QAbstractItemView::item:selected {
168171
background-color: #b45309;
169172
color: white;
173+
border-radius: 4px;
170174
}
171175

172176
/* Buttons - Modern Flat Design */
@@ -318,6 +322,13 @@ QGroupBox::indicator:unchecked {
318322
margin-top: 2px;
319323
}
320324

325+
QGroupBox::indicator:checked {
326+
border: 1px solid #475569;
327+
border-radius: 2px;
328+
margin-top: 2px;
329+
image: url(checkbox_check_light.svg);
330+
}
331+
321332
/* Horizontal Lines */
322333
QFrame[frameShape="4"] {
323334
background: #cbd5e1;
@@ -382,6 +393,26 @@ QPushButton#theme_toggle {
382393
font-size: 14px;
383394
}
384395

396+
/* Program Settings Button - Square with same height as dropdown */
397+
QPushButton#programSettingsButton {
398+
background-color: #ffffff;
399+
border: 1px solid #cbd5e1;
400+
border-radius: 4px;
401+
width: 34px;
402+
height: 34px;
403+
padding: 0;
404+
icon-size: 16px;
405+
}
406+
407+
QPushButton#programSettingsButton:hover {
408+
background-color: #f1f5f9;
409+
border-color: #b45309;
410+
}
411+
412+
QPushButton#programSettingsButton:pressed {
413+
background-color: #e2e8f0;
414+
}
415+
385416
QPushButton#theme_toggle:hover {
386417
background-color: #f1f5f9;
387418
border-color: #94a3b8;

tests/integration/test_export_integration.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@
1111
from pathlib import Path
1212
from unittest.mock import patch
1313

14+
import pandas as pd
15+
1416
# Add src directory to path
1517
sys.path.insert(0, str(Path(__file__).parent.parent.parent / "src"))
1618

0 commit comments

Comments
 (0)