import React from 'react'; import { PanelSection, ToolSettings } from '@ohif/ui-next'; import { useSystem, useToolbar } from '@ohif/core'; import classnames from 'classnames'; interface ButtonProps { isActive?: boolean; options?: unknown; } /** * A toolbox is a collection of buttons and commands that they invoke, used to provide * custom control panels to users. This component is a generic UI component that * interacts with services and commands in a generic fashion. While it might * seem unconventional to import it from the UI and integrate it into the JSX, * it belongs in the UI components as there isn't anything in this component that * couldn't be used for a completely different type of app. It plays a crucial * role in enhancing the app with a toolbox by providing a way to integrate * and display various tools and their corresponding options */ export function Toolbox({ buttonSectionId, title }: { buttonSectionId: string; title: string }) { const { servicesManager } = useSystem(); const { toolbarService } = servicesManager.services; const { toolbarButtons: toolboxSections, onInteraction } = useToolbar({ servicesManager, buttonSection: buttonSectionId, }); if (!toolboxSections.length) { return null; } // Ensure we have proper button sections at the top level. if (!toolboxSections.every(section => section.componentProps.buttonSection)) { throw new Error( 'Toolbox accepts only button sections at the top level, not buttons. Create at least one button section.' ); } // Helper to check a list of buttons for an active tool. const findActiveOptions = (buttons: any[]): unknown => { for (const tool of buttons) { if (tool.componentProps.isActive) { return tool.componentProps.options; } if (tool.componentProps.buttonSection) { const nestedButtons = toolbarService.getButtonPropsInButtonSection( tool.componentProps.buttonSection ) as ButtonProps[]; const activeNested = nestedButtons.find(nested => nested.isActive); if (activeNested) { return activeNested.options; } } } return null; }; // Look for active tool options across all sections. const activeToolOptions = toolboxSections.reduce((activeOptions, section) => { if (activeOptions) { return activeOptions; } const sectionId = section.componentProps.buttonSection; const buttons = toolbarService.getButtonSection(sectionId); return findActiveOptions(buttons); }, null); // Define the interaction handler once. const handleInteraction = ({ itemId }: { itemId: string }) => { onInteraction?.({ itemId }); }; return ( {title} {toolboxSections.map(section => { const sectionId = section.componentProps.buttonSection; const buttons = toolbarService.getButtonSection(sectionId) as any[]; return (
{buttons.map(tool => { if (!tool) { return null; } const { id, Component, componentProps } = tool; return (
); })}
); })} {activeToolOptions && (
)}
); }