fix: OHIF-219 - Viewport Labels should be sequential (#1881)
This commit is contained in:
parent
066ba97bc9
commit
b28a70520e
@ -399,10 +399,7 @@ function OHIFCornerstoneSRViewport({
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const label =
|
const label = viewports.length > 1 ? _viewportLabels[viewportIndex] : '';
|
||||||
viewports.length > 1
|
|
||||||
? _viewportLabels[firstViewportIndexWithMatchingDisplaySetUid]
|
|
||||||
: '';
|
|
||||||
|
|
||||||
// TODO -> disabled double click for now: onDoubleClick={_onDoubleClick}
|
// TODO -> disabled double click for now: onDoubleClick={_onDoubleClick}
|
||||||
|
|
||||||
|
|||||||
@ -23,7 +23,7 @@ function PanelStudyBrowserTracking({
|
|||||||
// Tabs --> Studies --> DisplaySets --> Thumbnails
|
// Tabs --> Studies --> DisplaySets --> Thumbnails
|
||||||
const [{ StudyInstanceUIDs }, dispatchImageViewer] = useImageViewer();
|
const [{ StudyInstanceUIDs }, dispatchImageViewer] = useImageViewer();
|
||||||
const [
|
const [
|
||||||
{ activeViewportIndex, viewports },
|
{ activeViewportIndex, viewports, numCols, numRows },
|
||||||
viewportGridService,
|
viewportGridService,
|
||||||
] = useViewportGrid();
|
] = useViewportGrid();
|
||||||
const [
|
const [
|
||||||
@ -49,6 +49,8 @@ function PanelStudyBrowserTracking({
|
|||||||
const activeDisplaySetInstanceUID =
|
const activeDisplaySetInstanceUID =
|
||||||
viewports[activeViewportIndex]?.displaySetInstanceUID;
|
viewports[activeViewportIndex]?.displaySetInstanceUID;
|
||||||
|
|
||||||
|
const isSingleViewport = numCols === 1 && numRows === 1;
|
||||||
|
|
||||||
// TODO: Should this be somewhere else? Feels more like a mode "lifecycle" setup/destroy?
|
// TODO: Should this be somewhere else? Feels more like a mode "lifecycle" setup/destroy?
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const { unsubscribe } = MeasurementService.subscribe(
|
const { unsubscribe } = MeasurementService.subscribe(
|
||||||
@ -133,7 +135,8 @@ function PanelStudyBrowserTracking({
|
|||||||
currentDisplaySets,
|
currentDisplaySets,
|
||||||
thumbnailImageSrcMap,
|
thumbnailImageSrcMap,
|
||||||
trackedSeries,
|
trackedSeries,
|
||||||
viewports
|
viewports,
|
||||||
|
isSingleViewport
|
||||||
);
|
);
|
||||||
|
|
||||||
setDisplaySets(mappedDisplaySets);
|
setDisplaySets(mappedDisplaySets);
|
||||||
@ -189,7 +192,8 @@ function PanelStudyBrowserTracking({
|
|||||||
changedDisplaySets,
|
changedDisplaySets,
|
||||||
thumbnailImageSrcMap,
|
thumbnailImageSrcMap,
|
||||||
trackedSeries,
|
trackedSeries,
|
||||||
viewports
|
viewports,
|
||||||
|
isSingleViewport
|
||||||
);
|
);
|
||||||
|
|
||||||
setDisplaySets(mappedDisplaySets);
|
setDisplaySets(mappedDisplaySets);
|
||||||
@ -279,7 +283,7 @@ function PanelStudyBrowserTracking({
|
|||||||
];
|
];
|
||||||
setExpandedStudyInstanceUIDs(updatedExpandedStudyInstanceUIDs);
|
setExpandedStudyInstanceUIDs(updatedExpandedStudyInstanceUIDs);
|
||||||
}
|
}
|
||||||
}, [jumpToDisplaySet]);
|
}, [expandedStudyInstanceUIDs, jumpToDisplaySet, tabs]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<StudyBrowser
|
<StudyBrowser
|
||||||
@ -355,21 +359,22 @@ function _mapDisplaySets(
|
|||||||
displaySets,
|
displaySets,
|
||||||
thumbnailImageSrcMap,
|
thumbnailImageSrcMap,
|
||||||
trackedSeriesInstanceUIDs,
|
trackedSeriesInstanceUIDs,
|
||||||
viewports // TODO: make array of `displaySetInstanceUIDs`?
|
viewports, // TODO: make array of `displaySetInstanceUIDs`?
|
||||||
|
isSingleViewport
|
||||||
) {
|
) {
|
||||||
const thumbnailDisplaySets = [];
|
const thumbnailDisplaySets = [];
|
||||||
const thumbnailNoImageDisplaySets = [];
|
const thumbnailNoImageDisplaySets = [];
|
||||||
displaySets.forEach(ds => {
|
displaySets.forEach(ds => {
|
||||||
const imageSrc = thumbnailImageSrcMap[ds.displaySetInstanceUID];
|
const imageSrc = thumbnailImageSrcMap[ds.displaySetInstanceUID];
|
||||||
const componentType = _getComponentType(ds.Modality);
|
const componentType = _getComponentType(ds.Modality);
|
||||||
const firstViewportIndexWithMatchingDisplaySetUid = viewports.findIndex(
|
const viewportIdentificator = isSingleViewport
|
||||||
vp => vp.displaySetInstanceUID === ds.displaySetInstanceUID
|
? []
|
||||||
);
|
: viewports.reduce((acc, viewportData, index) => {
|
||||||
|
if (viewportData.displaySetInstanceUID === ds.displaySetInstanceUID) {
|
||||||
const viewportIdentificator =
|
acc.push(_viewportLabels[index]);
|
||||||
viewports.length > 1
|
}
|
||||||
? _viewportLabels[firstViewportIndexWithMatchingDisplaySetUid]
|
return acc;
|
||||||
: '';
|
}, []);
|
||||||
|
|
||||||
const array =
|
const array =
|
||||||
componentType === 'thumbnailTracked'
|
componentType === 'thumbnailTracked'
|
||||||
|
|||||||
@ -245,10 +245,7 @@ function TrackedCornerstoneViewport({
|
|||||||
setIsTracked(!isTracked);
|
setIsTracked(!isTracked);
|
||||||
}
|
}
|
||||||
|
|
||||||
const label =
|
const label = viewports.length > 1 ? _viewportLabels[viewportIndex] : '';
|
||||||
viewports.length > 1
|
|
||||||
? _viewportLabels[firstViewportIndexWithMatchingDisplaySetUid]
|
|
||||||
: '';
|
|
||||||
|
|
||||||
function switchMeasurement(direction) {
|
function switchMeasurement(direction) {
|
||||||
if (!element) {
|
if (!element) {
|
||||||
|
|||||||
@ -15,7 +15,6 @@ const ThumbnailNoImage = ({
|
|||||||
onDoubleClick,
|
onDoubleClick,
|
||||||
dragData,
|
dragData,
|
||||||
isActive,
|
isActive,
|
||||||
viewportIdentificator = '',
|
|
||||||
}) => {
|
}) => {
|
||||||
const [collectedProps, drag, dragPreview] = useDrag({
|
const [collectedProps, drag, dragPreview] = useDrag({
|
||||||
item: { ...dragData },
|
item: { ...dragData },
|
||||||
@ -84,7 +83,6 @@ ThumbnailNoImage.propTypes = {
|
|||||||
onClick: PropTypes.func.isRequired,
|
onClick: PropTypes.func.isRequired,
|
||||||
onDoubleClick: PropTypes.func.isRequired,
|
onDoubleClick: PropTypes.func.isRequired,
|
||||||
isActive: PropTypes.bool.isRequired,
|
isActive: PropTypes.bool.isRequired,
|
||||||
viewportIdentificator: PropTypes.string,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default ThumbnailNoImage;
|
export default ThumbnailNoImage;
|
||||||
|
|||||||
@ -21,6 +21,35 @@ const ThumbnailTracked = ({
|
|||||||
isActive,
|
isActive,
|
||||||
}) => {
|
}) => {
|
||||||
const trackedIcon = isTracked ? 'circled-checkmark' : 'dotted-circle';
|
const trackedIcon = isTracked ? 'circled-checkmark' : 'dotted-circle';
|
||||||
|
const viewportIdentificatorLabel = viewportIdentificator.join(', ');
|
||||||
|
const renderViewportLabels = () => {
|
||||||
|
const MAX_LABELS_PER_COL = 3;
|
||||||
|
const shouldShowStack = viewportIdentificator.length > MAX_LABELS_PER_COL;
|
||||||
|
if (shouldShowStack) {
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<div>
|
||||||
|
{viewportIdentificator.slice(0, MAX_LABELS_PER_COL).map(label => (
|
||||||
|
<div key={label}>{label}</div>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
<Tooltip
|
||||||
|
position="right"
|
||||||
|
content={
|
||||||
|
<div className="text-left max-w-40">
|
||||||
|
Series is displayed <br /> in viewport{' '}
|
||||||
|
{viewportIdentificatorLabel}
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Icon name="tool-more-menu" className="text-white py-2" />
|
||||||
|
</Tooltip>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return viewportIdentificator.map(label => <div key={label}>{label}</div>);
|
||||||
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
@ -48,11 +77,11 @@ const ThumbnailTracked = ({
|
|||||||
{isTracked ? ' tracked' : ' untracked'}
|
{isTracked ? ' tracked' : ' untracked'}
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
{viewportIdentificator && (
|
{!!viewportIdentificator.length && (
|
||||||
<span>
|
<span>
|
||||||
in viewport
|
in viewport
|
||||||
<span className="ml-1 text-white">
|
<span className="ml-1 text-white">
|
||||||
{viewportIdentificator}
|
{viewportIdentificatorLabel}
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
)}
|
)}
|
||||||
@ -64,10 +93,10 @@ const ThumbnailTracked = ({
|
|||||||
}
|
}
|
||||||
>
|
>
|
||||||
<Icon name={trackedIcon} className="w-4 mb-2 text-primary-light" />
|
<Icon name={trackedIcon} className="w-4 mb-2 text-primary-light" />
|
||||||
<div className="h-5 text-xl leading-tight text-white">
|
|
||||||
{viewportIdentificator}
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
</Tooltip>
|
||||||
|
<div className="text-xl leading-tight text-white text-center">
|
||||||
|
{renderViewportLabels()}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{isTracked && (
|
{isTracked && (
|
||||||
<div onClick={onClickUntrack}>
|
<div onClick={onClickUntrack}>
|
||||||
@ -113,7 +142,7 @@ ThumbnailTracked.propTypes = {
|
|||||||
onClick: PropTypes.func.isRequired,
|
onClick: PropTypes.func.isRequired,
|
||||||
onDoubleClick: PropTypes.func.isRequired,
|
onDoubleClick: PropTypes.func.isRequired,
|
||||||
onClickUntrack: PropTypes.func.isRequired,
|
onClickUntrack: PropTypes.func.isRequired,
|
||||||
viewportIdentificator: PropTypes.string,
|
viewportIdentificator: PropTypes.array,
|
||||||
isTracked: PropTypes.bool,
|
isTracked: PropTypes.bool,
|
||||||
isActive: PropTypes.bool.isRequired,
|
isActive: PropTypes.bool.isRequired,
|
||||||
};
|
};
|
||||||
|
|||||||
@ -88,6 +88,8 @@ export function ViewportGridProvider({ children, service }) {
|
|||||||
DEFAULT_STATE
|
DEFAULT_STATE
|
||||||
);
|
);
|
||||||
|
|
||||||
|
console.log('viewportGridState',viewportGridState)
|
||||||
|
|
||||||
const getState = useCallback(() => viewportGridState, [viewportGridState]);
|
const getState = useCallback(() => viewportGridState, [viewportGridState]);
|
||||||
const setActiveViewportIndex = useCallback(
|
const setActiveViewportIndex = useCallback(
|
||||||
index => dispatch({ type: 'SET_ACTIVE_VIEWPORT_INDEX', payload: index }),
|
index => dispatch({ type: 'SET_ACTIVE_VIEWPORT_INDEX', payload: index }),
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user