From e685b8b11db49e89f710d2f30bc2f4a2c92864e3 Mon Sep 17 00:00:00 2001 From: Ross Date: Mon, 22 Sep 2025 10:58:05 +0100 Subject: [PATCH] Refactor stack panel functionality to remove top bar and implement toggle for right-side panel visibility --- dicom-viewer/src/App.tsx | 192 ++++++++------------------------------- 1 file changed, 40 insertions(+), 152 deletions(-) diff --git a/dicom-viewer/src/App.tsx b/dicom-viewer/src/App.tsx index 4711987..2e38491 100644 --- a/dicom-viewer/src/App.tsx +++ b/dicom-viewer/src/App.tsx @@ -173,13 +173,13 @@ function App({ container_id, imageStacks, autoCacheStack, annotationJson, viewer const [presetsOpen, setPresetsOpen] = useState(false); const [settingsOpen, setSettingsOpen] = useState(false); - // Control visibility of the global top stack bar (hidden by default) - const [topBarVisible, setTopBarVisible] = useState(false); + // Settings open state + // (top bar removed; stack browser moved to right-side panel) // Right-side stack panel pinned state (false = auto-hide, true = pinned open) const [stackPanelPinned, setStackPanelPinned] = useState(false); - // Local hover state for temporary reveal when not pinned - const [stackPanelHover, setStackPanelHover] = useState(false); + // Local open state toggled by small button (replaces hover-to-open) + const [stackPanelOpen, setStackPanelOpen] = useState(false); const [fullscreenHoverIdx, setFullscreenHoverIdx] = useState(null); const [openDropdownIdx, setOpenDropdownIdx] = useState(null); @@ -2990,144 +2990,10 @@ function App({ container_id, imageStacks, autoCacheStack, annotationJson, viewer )} - {/* Top bar stack browser (hidden by default) */} -
- - - {topBarVisible && ( -
- {/* Group stacks by studyId or studyInstanceUID or 'Unspecified' */} - {(() => { - const groups: Record = {}; - availableStacks.forEach((stackObj, idx) => { - const studyKey = stackObj.studyId || stackObj.studyInstanceUID || 'Unspecified'; - if (!groups[studyKey]) groups[studyKey] = []; - groups[studyKey].push({ idx, stack: stackObj }); - }); - return Object.keys(groups).map(studyKey => ( -
- - {studyKey === 'Unspecified' ? 'Unspecified study' : `Study: ${studyKey}`} - - {groups[studyKey].map(({ idx, stack }) => { - const imageIds = Array.isArray(stack.imageIds) ? stack.imageIds : []; - const label = stack.name || (stack.caseId ? `Case: ${stack.caseId}` : `Stack ${idx + 1}`); - const count = imageIds.length; - const invalid = !Array.isArray(imageIds) || count === 0; - // Highlight if this stack is selected in any viewport - const isSelected = selectedStackIdx.includes(idx); - return ( -
{ - if (invalid) return; - e.dataTransfer.setData('text/stack-idx', String(idx)); - e.dataTransfer.effectAllowed = 'copy'; - }} - style={{ - display: 'flex', - flexDirection: 'row', - alignItems: 'center', - justifyContent: 'space-between', - minWidth: 90, - maxWidth: 220, - padding: '7px 14px', - margin: '0 2px', - background: isSelected ? '#1976d2' : '#333', - color: isSelected ? '#fff' : '#eee', - border: isSelected ? '2px solid #90caf9' : 'none', - borderRadius: '4px', - fontWeight: isSelected ? 'bold' : 'normal', - fontSize: 15, - cursor: invalid ? 'not-allowed' : 'grab', - opacity: invalid ? 0.5 : 1, - transition: 'background 0.2s, border 0.2s', - boxShadow: isSelected ? '0 2px 8px #1976d2aa' : undefined, - }} - title={invalid ? 'Invalid stack descriptor' : `${label} — ${count} image${count === 1 ? '' : 's'}`} - > - {label} - {count} img{count === 1 ? '' : 's'} -
- ); - })} -
- )); - })()} -
- )} -
- {/* Persistent floating button to reveal the stack bar */} - + {/* top stack bar removed; use right-side panel instead */} {/* Right-side stack panel (pinnable, shows on hover when not pinned) */} -
setStackPanelHover(true)} - onMouseLeave={() => setStackPanelHover(false)} - style={{ - position: "absolute", - right: 0, - top: 12, - height: 'calc(100% - 24px)', - width: 320, - zIndex: 2100, - display: 'flex', - alignItems: 'stretch', - pointerEvents: 'auto', - }} - > +
{/* Panel container: translateX to hide when not pinned and not hovered */}
- {/* Visible handle when panel is hidden to allow hover */} - {!stackPanelPinned && ( -
-
-
- )}
+ {/* Floating right-edge toggle — always visible so users can open the panel */} + {! (stackPanelPinned || stackPanelOpen) && ( + + )} +
{/* Side menu toggle button */}