feat(actions): simplify action corner api through the toolbarService (#5033)
This commit is contained in:
1 parent
f71b88e639
commit
7c15bb8901
246 files changed
+7930
-4270
No files matched your search
@@ -53,7 +53,7 @@
|
||||
"@cornerstonejs/codec-libjpeg-turbo-8bit": "^1.2.2",
|
||||
"@cornerstonejs/codec-openjpeg": "^1.2.4",
|
||||
"@cornerstonejs/codec-openjph": "^2.4.5",
|
||||
"@cornerstonejs/dicom-image-loader": "^3.12.2",
|
||||
"@cornerstonejs/dicom-image-loader": "^3.15.1",
|
||||
"@emotion/serialize": "^1.1.3",
|
||||
"@ohif/core": "3.11.0-beta.32",
|
||||
"@ohif/extension-cornerstone": "3.11.0-beta.32",
|
||||
|
||||
@@ -13,6 +13,7 @@ import {
|
||||
HotkeysManager,
|
||||
ServiceProvidersManager,
|
||||
SystemContextProvider,
|
||||
ViewportRefsProvider,
|
||||
} from '@ohif/core';
|
||||
import {
|
||||
ThemeWrapper as ThemeWrapperNext,
|
||||
@@ -26,7 +27,6 @@ import {
|
||||
ModalProvider,
|
||||
ViewportDialogProvider,
|
||||
UserAuthenticationProvider,
|
||||
ViewportActionCornersProvider,
|
||||
} from '@ohif/ui-next';
|
||||
// Viewer Project
|
||||
// TODO: Should this influence study list?
|
||||
@@ -105,7 +105,6 @@ function App({
|
||||
userAuthenticationService,
|
||||
uiNotificationService,
|
||||
customizationService,
|
||||
viewportActionCornersService,
|
||||
} = servicesManager.services;
|
||||
|
||||
const providers = [
|
||||
@@ -114,6 +113,7 @@ function App({
|
||||
[I18nextProvider, { i18n }],
|
||||
[ThemeWrapperNext],
|
||||
[SystemContextProvider, { commandsManager, extensionManager, hotkeysManager, servicesManager }],
|
||||
[ViewportRefsProvider],
|
||||
[ViewportGridProvider, { service: viewportGridService }],
|
||||
[ViewportDialogProvider, { service: uiViewportDialogService }],
|
||||
[CineProvider, { service: cineService }],
|
||||
@@ -121,7 +121,6 @@ function App({
|
||||
[TooltipProvider],
|
||||
[DialogProvider, { service: uiDialogService, dialog: ManagedDialog }],
|
||||
[ModalProvider, { service: uiModalService, modal: ModalNext }],
|
||||
[ViewportActionCornersProvider, { service: viewportActionCornersService }],
|
||||
[ShepherdJourneyProvider],
|
||||
];
|
||||
|
||||
|
||||
@@ -4,13 +4,11 @@ import { ViewportGrid, ViewportPane } from '@ohif/ui-next';
|
||||
import { useViewportGrid } from '@ohif/ui-next';
|
||||
import EmptyViewport from './EmptyViewport';
|
||||
import { useAppConfig } from '@state';
|
||||
import { useViewportActionCornersWithGrid } from '../hooks';
|
||||
|
||||
function ViewerViewportGrid(props: withAppTypes) {
|
||||
const { servicesManager, viewportComponents = [], dataSource, commandsManager } = props;
|
||||
const [viewportGrid, viewportGridService] = useViewportGrid();
|
||||
const [appConfig] = useAppConfig();
|
||||
const { initializeViewportCorners } = useViewportActionCornersWithGrid();
|
||||
|
||||
const { layout, activeViewportId, viewports, isHangingProtocolLayout } = viewportGrid;
|
||||
const { numCols, numRows } = layout;
|
||||
@@ -419,12 +417,6 @@ function ViewerViewportGrid(props: withAppTypes) {
|
||||
isHangingProtocolLayout={isHangingProtocolLayout}
|
||||
onElementEnabled={evt => {
|
||||
viewportGridService.setViewportIsReady(viewportId, true);
|
||||
|
||||
// Initialize the viewport action corners for this viewport
|
||||
if (evt?.detail?.element) {
|
||||
const elementRef = { current: evt.detail.element };
|
||||
initializeViewportCorners(viewportId, elementRef, displaySets, commandsManager);
|
||||
}
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
@@ -433,7 +425,7 @@ function ViewerViewportGrid(props: withAppTypes) {
|
||||
}
|
||||
|
||||
return viewportPanes;
|
||||
}, [viewports, activeViewportId, viewportComponents, dataSource, initializeViewportCorners]);
|
||||
}, [viewports, activeViewportId, viewportComponents, dataSource]);
|
||||
|
||||
/**
|
||||
* Loading indicator until numCols and numRows are gotten from the HangingProtocolService
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import useDebounce from './useDebounce';
|
||||
import useSearchParams from './useSearchParams';
|
||||
import useViewportActionCornersWithGrid from './useViewportActionCornersWithGrid';
|
||||
|
||||
export { useDebounce, useSearchParams, useViewportActionCornersWithGrid };
|
||||
export { useDebounce, useSearchParams };
|
||||
@@ -1,5 +1,4 @@
|
||||
import useViewportActionCornersWithGrid from './useViewportActionCornersWithGrid';
|
||||
import useDebounce from './useDebounce';
|
||||
import useSearchParams from './useSearchParams';
|
||||
|
||||
export { useViewportActionCornersWithGrid, useDebounce, useSearchParams };
|
||||
export { useDebounce, useSearchParams };
|
||||
@@ -1,112 +0,0 @@
|
||||
import { useCallback, MutableRefObject, useRef } from 'react';
|
||||
import { useViewportActionCorners, ViewportActionCornersLocations } from '@ohif/ui-next';
|
||||
import { useSystem } from '@ohif/core';
|
||||
|
||||
/**
|
||||
* Hook that manages viewport action corner components for all viewports in the grid
|
||||
* @returns A function that can be called to initialize action corners for a viewport
|
||||
*/
|
||||
export default function useViewportActionCornersWithGrid() {
|
||||
const [, api] = useViewportActionCorners();
|
||||
const { servicesManager } = useSystem();
|
||||
const { customizationService } = servicesManager.services;
|
||||
|
||||
// Keep a ref to track processed viewports to avoid duplicates
|
||||
const processedViewports = useRef<Set<string>>(new Set());
|
||||
|
||||
// Map of customization keys to their corresponding enum values
|
||||
const locationMap = {
|
||||
'viewportActionMenu.topLeft': ViewportActionCornersLocations.topLeft,
|
||||
'viewportActionMenu.topRight': ViewportActionCornersLocations.topRight,
|
||||
'viewportActionMenu.bottomLeft': ViewportActionCornersLocations.bottomLeft,
|
||||
'viewportActionMenu.bottomRight': ViewportActionCornersLocations.bottomRight,
|
||||
};
|
||||
|
||||
// Function to process customizations for a viewport
|
||||
const initializeViewportCorners = useCallback(
|
||||
(
|
||||
viewportId: string,
|
||||
elementRef: MutableRefObject<HTMLDivElement>,
|
||||
displaySets: any[],
|
||||
commandsManager: any
|
||||
) => {
|
||||
if (!viewportId || !elementRef?.current) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Prevent duplicate processing
|
||||
if (processedViewports.current.has(viewportId)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Mark this viewport as processed
|
||||
processedViewports.current.add(viewportId);
|
||||
|
||||
// Clear any existing components for this viewport
|
||||
api.clear(viewportId);
|
||||
|
||||
// Process each location
|
||||
Object.entries(locationMap).forEach(([locationKey, locationValue]) => {
|
||||
const items = customizationService.getCustomization(locationKey);
|
||||
if (!items || !items.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
items.forEach(item => {
|
||||
try {
|
||||
if (typeof item.component === 'function') {
|
||||
// Use the component renderer provided directly in the item
|
||||
const component = item.component({
|
||||
viewportId,
|
||||
element: elementRef.current,
|
||||
displaySets,
|
||||
location: locationValue,
|
||||
commandsManager,
|
||||
});
|
||||
|
||||
if (component) {
|
||||
api.addComponent({
|
||||
viewportId,
|
||||
id: item.id,
|
||||
component,
|
||||
location: locationValue,
|
||||
indexPriority: item.indexPriority,
|
||||
});
|
||||
}
|
||||
} else if (item.component) {
|
||||
// Handle static components
|
||||
api.addComponent({
|
||||
viewportId,
|
||||
id: item.id,
|
||||
component: item.component,
|
||||
location: locationValue,
|
||||
indexPriority: item.indexPriority,
|
||||
});
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(`Error adding component ${item.id} to viewport corner:`, error);
|
||||
}
|
||||
});
|
||||
});
|
||||
},
|
||||
[api, customizationService]
|
||||
);
|
||||
|
||||
// Cleanup function for unmounting viewports
|
||||
const cleanupViewportCorners = useCallback(
|
||||
(viewportId: string) => {
|
||||
if (!viewportId) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove from processed set
|
||||
processedViewports.current.delete(viewportId);
|
||||
|
||||
// Clear from the store
|
||||
api.clear(viewportId);
|
||||
},
|
||||
[api]
|
||||
);
|
||||
|
||||
return { initializeViewportCorners, cleanupViewportCorners };
|
||||
}
|
||||
@@ -83,10 +83,10 @@ export default function ModeRoute({
|
||||
extensionManager.setActiveDataSource(dataSourceName);
|
||||
}
|
||||
|
||||
const dataSource = extensionManager.getActiveDataSource()[0];
|
||||
const dataSource = extensionManager.getActiveDataSourceOrNull();
|
||||
|
||||
// Only handling one route per mode for now
|
||||
const route = mode.routes[0];
|
||||
const route = mode.routes?.[0] ?? null;
|
||||
|
||||
useEffect(() => {
|
||||
const loadExtensions = async () => {
|
||||
|
||||
Reference in new issue
Block a user