fix(modal and dialogues): fixes as per specifications (#3438)

Co-authored-by: Alireza <ar.sedghi@gmail.com>
This commit is contained in:
Joe Boccanfuso 2023-06-07 08:31:09 -04:00 committed by GitHub
parent ffaffbdfa3
commit da5c32bce3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
27 changed files with 180 additions and 170 deletions

View File

@ -24,7 +24,7 @@ function callInputDialog(uiDialogService, label, callback) {
showOverlay: true, showOverlay: true,
content: Dialog, content: Dialog,
contentProps: { contentProps: {
title: 'Enter Segment Label', title: 'Segment',
value: { label }, value: { label },
noCloseButton: true, noCloseButton: true,
onClose: () => uiDialogService.dismiss({ id: dialogId }), onClose: () => uiDialogService.dismiss({ id: dialogId }),
@ -35,12 +35,12 @@ function callInputDialog(uiDialogService, label, callback) {
onSubmit: onSubmitHandler, onSubmit: onSubmitHandler,
body: ({ value, setValue }) => { body: ({ value, setValue }) => {
return ( return (
<div className="p-4 bg-primary-dark">
<Input <Input
label="Enter the segment label"
labelClassName="text-white text-[14px] leading-[1.2]"
autoFocus autoFocus
className="mt-2 bg-black border-primary-main" className="bg-black border-primary-main"
type="text" type="text"
containerClassName="mr-2"
value={value.label} value={value.label}
onChange={event => { onChange={event => {
event.persist(); event.persist();
@ -52,7 +52,6 @@ function callInputDialog(uiDialogService, label, callback) {
} }
}} }}
/> />
</div>
); );
}, },
}, },

View File

@ -97,7 +97,7 @@ const DicomUploadProgressItem = memo(
)} )}
<div className="flex cursor-pointer ml-auto"> <div className="flex cursor-pointer ml-auto">
<Icon <Icon
className="w-6 h-6 self-center text-primary-active" className="self-center text-primary-active"
name="close" name="close"
onClick={cancelUpload} onClick={cancelUpload}
/> />

View File

@ -27,8 +27,8 @@ function callInputDialog(
: data.label : data.label
: ''; : '';
const { const {
dialogTitle = 'Enter your annotation', dialogTitle = 'Annotation',
inputLabel = '', inputLabel = 'Enter your annotation',
validateFunc = value => true, validateFunc = value => true,
} = dialogConfig; } = dialogConfig;
@ -66,15 +66,13 @@ function callInputDialog(
onSubmit: onSubmitHandler, onSubmit: onSubmitHandler,
body: ({ value, setValue }) => { body: ({ value, setValue }) => {
return ( return (
<div className="p-4 bg-primary-dark">
<Input <Input
autoFocus autoFocus
className="mt-2 bg-black border-primary-main" className="bg-black border-primary-main"
type="text" type="text"
id="annotation" id="annotation"
containerClassName="mr-2"
label={inputLabel} label={inputLabel}
labelClassName="text-primary-light" labelClassName="text-white text-[14px] leading-[1.2]"
value={value.label} value={value.label}
onChange={event => { onChange={event => {
event.persist(); event.persist();
@ -86,7 +84,6 @@ function callInputDialog(
} }
}} }}
/> />
</div>
); );
}, },
}, },

View File

@ -160,7 +160,7 @@ export default function PanelMeasurementTable({
showOverlay: true, showOverlay: true,
content: Dialog, content: Dialog,
contentProps: { contentProps: {
title: 'Enter your annotation', title: 'Annotation',
noCloseButton: true, noCloseButton: true,
value: { label: measurement.label || '' }, value: { label: measurement.label || '' },
body: ({ value, setValue }) => { body: ({ value, setValue }) => {
@ -175,18 +175,17 @@ export default function PanelMeasurementTable({
} }
}; };
return ( return (
<div className="p-4 bg-primary-dark">
<Input <Input
label="Enter your annotation"
labelClassName="text-white text-[14px] leading-[1.2]"
autoFocus autoFocus
id="annotation" id="annotation"
className="mt-2 bg-black border-primary-main" className="bg-black border-primary-main"
type="text" type="text"
containerClassName="mr-2"
value={value.label} value={value.label}
onChange={onChangeHandler} onChange={onChangeHandler}
onKeyPress={onKeyPressHandler} onKeyPress={onKeyPressHandler}
/> />
</div>
); );
}, },
actions: [ actions: [

View File

@ -73,7 +73,7 @@ export default function createReportDialogPrompt(
useLastPosition: false, useLastPosition: false,
showOverlay: true, showOverlay: true,
contentProps: { contentProps: {
title: 'Provide a name for your report', title: 'Create Report',
value: { value: {
label: '', label: '',
dataSourceName: extensionManager.activeDataSource, dataSourceName: extensionManager.activeDataSource,
@ -102,7 +102,6 @@ export default function createReportDialogPrompt(
}; };
return ( return (
<> <>
<div className="p-4 bg-primary-dark">
{dataSourcesOpts.length > 1 && ( {dataSourcesOpts.length > 1 && (
<Select <Select
closeMenuOnSelect={true} closeMenuOnSelect={true}
@ -120,20 +119,17 @@ export default function createReportDialogPrompt(
isClearable={false} isClearable={false}
/> />
)} )}
</div>
<div className="p-4 bg-primary-dark">
<Input <Input
autoFocus autoFocus
className="mt-2 bg-black border-primary-main" label="Enter the report name"
labelClassName="text-white text-[14px] leading-[1.2]"
className="bg-black border-primary-main"
type="text" type="text"
placeholder="Enter Report Name"
containerClassName="mr-2"
value={value.label} value={value.label}
onChange={onChangeHandler} onChange={onChangeHandler}
onKeyPress={onKeyPressHandler} onKeyPress={onKeyPressHandler}
required required
/> />
</div>
</> </>
); );
}, },

View File

@ -31,7 +31,6 @@ export default function getCommandsModule({
callInputDialog({ callInputDialog({
uiDialogService, uiDialogService,
title: 'Enter your annotation',
defaultValue: '', defaultValue: '',
callback: (value: string, action: string) => { callback: (value: string, action: string) => {
switch (action) { switch (action) {

View File

@ -12,7 +12,7 @@ import { Input, Dialog } from '@ohif/ui';
*/ */
export default function callInputDialog({ export default function callInputDialog({
uiDialogService, uiDialogService,
title = 'Enter your annotation', title = 'Annotation',
defaultValue = '', defaultValue = '',
callback = (value: string, action: string) => {} callback = (value: string, action: string) => {}
}) { }) {
@ -49,12 +49,12 @@ export default function callInputDialog({
onSubmit: onSubmitHandler, onSubmit: onSubmitHandler,
body: ({ value, setValue }) => { body: ({ value, setValue }) => {
return ( return (
<div className="p-4 bg-primary-dark">
<Input <Input
label="Enter your annotation"
labelClassName="text-white text-[14px] leading-[1.2]"
autoFocus autoFocus
className="mt-2 bg-black border-primary-main" className="bg-black border-primary-main"
type="text" type="text"
containerClassName="mr-2"
value={value.defaultValue} value={value.defaultValue}
onChange={event => { onChange={event => {
event.persist(); event.persist();
@ -66,7 +66,6 @@ export default function callInputDialog({
} }
}} }}
/> />
</div>
); );
}, },
}, },

View File

@ -38,7 +38,7 @@ export default function createReportDialogPrompt(uiDialogService) {
useLastPosition: false, useLastPosition: false,
showOverlay: true, showOverlay: true,
contentProps: { contentProps: {
title: 'Provide a name for your report', title: 'Create Report',
value: { label: '' }, value: { label: '' },
noCloseButton: true, noCloseButton: true,
onClose: _handleClose, onClose: _handleClose,
@ -60,12 +60,13 @@ export default function createReportDialogPrompt(uiDialogService) {
} }
}; };
return ( return (
<div className="p-4 bg-primary-dark"> <div className="">
<Input <Input
label="Enter the report name"
labelClassName="text-white grow leading-[1.2] text-[14px]"
autoFocus autoFocus
className="mt-2 bg-black border-primary-main" className="bg-black border-primary-main grow"
type="text" type="text"
containerClassName="mr-2"
value={value.label} value={value.label}
onChange={onChangeHandler} onChange={onChangeHandler}
onKeyPress={onKeyPressHandler} onKeyPress={onKeyPressHandler}

View File

@ -188,7 +188,7 @@ function PanelMeasurementTableTracking({ servicesManager, extensionManager }) {
showOverlay: true, showOverlay: true,
content: Dialog, content: Dialog,
contentProps: { contentProps: {
title: 'Enter your annotation', title: 'Annotation',
noCloseButton: true, noCloseButton: true,
value: { label: measurement.label || '' }, value: { label: measurement.label || '' },
body: ({ value, setValue }) => { body: ({ value, setValue }) => {
@ -203,18 +203,17 @@ function PanelMeasurementTableTracking({ servicesManager, extensionManager }) {
} }
}; };
return ( return (
<div className="p-4 bg-primary-dark">
<Input <Input
label="Enter your annotation"
labelClassName="text-white grow text-[14px] leading-[1.2]"
autoFocus autoFocus
id="annotation" id="annotation"
className="mt-2 bg-black border-primary-main" className="bg-black border-primary-main"
type="text" type="text"
containerClassName="mr-2"
value={value.label} value={value.label}
onChange={onChangeHandler} onChange={onChangeHandler}
onKeyPress={onKeyPressHandler} onKeyPress={onKeyPressHandler}
/> />
</div>
); );
}, },
actions: [ actions: [

View File

@ -33,7 +33,7 @@ window.config = {
supportsWildcard: true, supportsWildcard: true,
dicomUploadEnabled: true, dicomUploadEnabled: true,
bulkDataURI: { bulkDataURI: {
enabled: false, enabled: true,
}, },
}, },
}, },

View File

@ -43,3 +43,11 @@ The Dockerfile and entry point use the `${PORT}` environment variable as the por
```sh ```sh
docker run -d -e PORT=8080 -p 3000:8080/tcp --name ohif-viewer-container ohif-viewer-image docker run -d -e PORT=8080 -p 3000:8080/tcp --name ohif-viewer-container ohif-viewer-image
``` ```
### Configuring the OHIF config file
The OHIF [config file](../configuration/configurationFiles.md) to use can be specified by mounting it as a volume for the Docker container using the `-v` flag. If the OHIF config file is on the local file system then it can be specified as below. Note that depending on the version of Docker, an absolute path to the config file might be required.
```sh
docker run -d -p 3000:80/tcp -v /path/to/config/file.js:/usr/share/nginx/html/app-config.js --name ohif-viewer-container ohif-viewer-image
```

View File

@ -1,7 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 19 19">
<g fill="currentColor" fill-rule="evenodd">
<g stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5">
<path d="M.188.187L8.813 8.812M8.813.187L.188 8.812" transform="translate(5 5)"/>
</g>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 332 B

View File

@ -0,0 +1,3 @@
<svg width="12" height="12" viewBox="0 0 12 12" xmlns="http://www.w3.org/2000/svg">
<path d="M12 1.05 10.95 0 6 4.95 1.05 0 0 1.05 4.95 6 0 10.95 1.05 12 6 7.05 10.95 12 12 10.95 7.05 6z" fill="currentColor" fill-rule="evenodd"/>
</svg>

After

Width:  |  Height:  |  Size: 241 B

View File

@ -49,7 +49,11 @@ const AboutModal = ({ buildNumber, versionNumber, commitHash }) => {
const renderRowTitle = title => ( const renderRowTitle = title => (
<div className="pb-3 mb-3 border-b-2 border-black"> <div className="pb-3 mb-3 border-b-2 border-black">
<Typography variant="h6" className="text-primary-light"> <Typography
variant="inherit"
color="primaryLight"
className="text-[16px] font-semibold !leading-[1.2]"
>
{title} {title}
</Typography> </Typography>
</div> </div>

View File

@ -8,12 +8,14 @@ const Body = ({ text, className }) => {
const theme = 'bg-primary-dark'; const theme = 'bg-primary-dark';
return ( return (
<div className={classNames('relative flex-auto', theme, className)}> <div className={classNames('relative flex-auto', theme, className)}>
<div className="p-6"> <Typography
<Typography variant="body" className="my-4 leading-relaxed"> variant="inherit"
color="initial"
className="text-[14px] !leading-[1.2]"
>
{text} {text}
</Typography> </Typography>
</div> </div>
</div>
); );
}; };

View File

@ -22,12 +22,13 @@ const Dialog = ({
}) => { }) => {
const [value, setValue] = useState(defaultValue); const [value, setValue] = useState(defaultValue);
const theme = 'bg-secondary-light'; const theme = 'bg-primary-dark';
const flex = 'flex flex-col'; const flex = 'flex flex-col';
const border = 'border-0 rounded-lg drop-shadow-lg'; const border = 'border-0 rounded';
const outline = 'outline-none focus:outline-none'; const outline = 'outline-none focus:outline-none';
const position = 'relative'; const position = 'relative';
const width = 'w-full'; const width = 'w-full';
const padding = 'px-[20px] pb-[20px] pt-[13px]';
useEffect(() => { useEffect(() => {
if (onShow) { if (onShow) {
@ -36,7 +37,17 @@ const Dialog = ({
}, [onShow]); }, [onShow]);
return ( return (
<div className={classNames(theme, flex, border, outline, position, width)}> <div
className={classNames(
theme,
flex,
border,
outline,
position,
width,
padding
)}
>
<HeaderComponent <HeaderComponent
title={title} title={title}
noCloseButton={noCloseButton} noCloseButton={noCloseButton}

View File

@ -6,12 +6,10 @@ import { Button } from '..';
const Footer = ({ actions, className, onSubmit, value }) => { const Footer = ({ actions, className, onSubmit, value }) => {
const flex = 'flex items-center justify-end'; const flex = 'flex items-center justify-end';
const border = 'border-t-2 border-solid border-black rounded-b'; const padding = 'pt-[20px]';
const spacing = 'p-6';
const theme = 'bg-primary-dark';
return ( return (
<div className={classNames(flex, border, spacing, theme, className)}> <div className={classNames(flex, padding, className)}>
{actions.map((action, index) => { {actions.map((action, index) => {
const isFirst = index === 0; const isFirst = index === 0;
const isPrimary = action.type === 'primary'; const isPrimary = action.type === 'primary';

View File

@ -10,7 +10,7 @@ const CloseButton = ({ onClick }) => {
data-cy="close-button" data-cy="close-button"
onClick={onClick} onClick={onClick}
name="close" name="close"
className="cursor-pointer text-primary-active w-6 h-6" className="cursor-pointer text-primary-active"
/> />
); );
}; };
@ -20,14 +20,13 @@ CloseButton.propTypes = {
}; };
const Header = ({ title, noCloseButton, onClose }) => { const Header = ({ title, noCloseButton, onClose }) => {
const theme = 'bg-secondary-main'; const theme = 'bg-primary-dark';
const flex = 'flex items-center justify-between'; const flex = 'flex items-center justify-between';
const border = 'border-b-2 border-solid border-black rounded-t'; const padding = 'pb-[20px]';
const spacing = 'p-4';
return ( return (
<div className={classNames(theme, flex, border, spacing)}> <div className={classNames(theme, flex, padding)}>
<Typography variant="h6" color="primaryActive"> <Typography variant="h6" color="primaryLight" className="!leading-[1.2]">
{title} {title}
</Typography> </Typography>
{!noCloseButton && <CloseButton onClick={onClose} />} {!noCloseButton && <CloseButton onClick={onClose} />}

View File

@ -8,7 +8,7 @@ import arrowRightSmall from './../../assets/icons/arrow-right-small.svg';
import calendar from './../../assets/icons/calendar.svg'; import calendar from './../../assets/icons/calendar.svg';
import cancel from './../../assets/icons/cancel.svg'; import cancel from './../../assets/icons/cancel.svg';
import clipboard from './../../assets/icons/clipboard.svg'; import clipboard from './../../assets/icons/clipboard.svg';
import close from './../../assets/icons/close.svg'; import close from './../../assets/icons/closeIcon.svg';
import dottedCircle from './../../assets/icons/dotted-circle.svg'; import dottedCircle from './../../assets/icons/dotted-circle.svg';
import circledCheckmark from './../../assets/icons/circled-checkmark.svg'; import circledCheckmark from './../../assets/icons/circled-checkmark.svg';
import chevronDown from './../../assets/icons/chevron-down.svg'; import chevronDown from './../../assets/icons/chevron-down.svg';

View File

@ -62,7 +62,7 @@ const LegacyCinePlayer = ({
className="mr-3 border rounded-full text-primary-active border-primary-active" className="mr-3 border rounded-full text-primary-active border-primary-active"
onClick={onClose} onClick={onClose}
> >
<Icon name="close" width="15px" height="15px" /> <Icon name="close" />
</IconButton> </IconButton>
</div> </div>
); );

View File

@ -29,10 +29,11 @@ const Modal = ({
const renderHeader = () => { const renderHeader = () => {
return ( return (
title && ( title && (
<header className="flex items-center p-4 border-b-2 border-black bg-secondary-dark rounded-tl rounded-tr"> <header className="flex items-center px-[20px] py-[13px] bg-primary-dark rounded-tl rounded-tr">
<Typography <Typography
variant="h4" variant="h6"
className="flex grow text-primary-light font-light" color="primaryLight"
className="flex grow !leading-[1.2]"
data-cy="modal-header" data-cy="modal-header"
> >
{title} {title}
@ -41,7 +42,7 @@ const Modal = ({
<Icon <Icon
onClick={onClose} onClick={onClose}
name="close" name="close"
className="cursor-pointer text-primary-active w-6 h-6" className="cursor-pointer text-primary-active"
/> />
)} )}
</header> </header>
@ -60,7 +61,7 @@ const Modal = ({
shouldCloseOnOverlayClick={shouldCloseOnOverlayClick} shouldCloseOnOverlayClick={shouldCloseOnOverlayClick}
> >
{renderHeader()} {renderHeader()}
<section className="ohif-scrollbar modal-content overflow-y-auto px-4 py-6 rounded-bl rounded-br bg-primary-dark"> <section className="ohif-scrollbar modal-content overflow-y-auto px-[20px] pt-2 pb-[20px] rounded-bl rounded-br bg-primary-dark">
{children} {children}
</section> </section>
</ReactModal> </ReactModal>

View File

@ -66,7 +66,7 @@ const SegmentItem = ({
{isSegmentIndexHovering && showSegmentDelete ? ( {isSegmentIndexHovering && showSegmentDelete ? (
<Icon <Icon
name="close" name="close"
className={classnames('w-5 h-5 pr-2')} className={classnames('pr-0.5')}
onClick={e => { onClick={e => {
e.stopPropagation(); e.stopPropagation();
onDelete(segmentationId, segmentIndex); onDelete(segmentationId, segmentIndex);

View File

@ -55,7 +55,7 @@ const SegmentationItem = ({
<Icon <Icon
name="close" name="close"
className={classnames( className={classnames(
'w-5 transition duration-500 text-center hover:opacity-80', 'w-[10px] transition duration-500 text-center hover:opacity-80',
{ {
'bg-primary-light text-black': isActive, 'bg-primary-light text-black': isActive,
'bg-primary-dark text-primary-light group-hover:bg-secondary-main': !isActive, 'bg-primary-dark text-primary-light group-hover:bg-secondary-main': !isActive,

View File

@ -56,7 +56,7 @@ const SnackbarItem = ({ options, onClose }) => {
onClick={handleClose} onClick={handleClose}
className="w-5 h-5 rounded-full flex items-center justify-center self-start ml-auto relative left-[3px] top-[-3px] text-[#0944b3]" className="w-5 h-5 rounded-full flex items-center justify-center self-start ml-auto relative left-[3px] top-[-3px] text-[#0944b3]"
> >
<Icon name="close" className="w-5 h-5 text-black" /> <Icon name="close" className="text-black" />
</div> </div>
</div> </div>
</div> </div>

View File

@ -46,6 +46,7 @@ const classes = {
inherit: 'text-inherit', inherit: 'text-inherit',
primary: 'text-primary-main', primary: 'text-primary-main',
primaryActive: 'text-primary-active', primaryActive: 'text-primary-active',
primaryLight: 'text-primary-light',
secondary: 'text-common-light', secondary: 'text-common-light',
error: 'text-red-600', error: 'text-red-600',
}, },
@ -133,7 +134,7 @@ Typography.propTypes = {
'primaryActive', 'primaryActive',
'secondary', 'secondary',
'error', 'error',
'primaryActive', 'primaryLight',
]), ]),
className: PropTypes.string, className: PropTypes.string,
children: PropTypes.node, children: PropTypes.node,

View File

@ -63,8 +63,9 @@ const UserPreferences = ({
<> <>
<div className="border-b-2 border-black mb-2"> <div className="border-b-2 border-black mb-2">
<Typography <Typography
variant="h5" variant="inherit"
className="flex grow text-primary-light font-light pb-2" color="primaryLight"
className="flex text-[16px] font-semibold pb-2 !leading-[1.2]"
> >
{title} {title}
</Typography> </Typography>
@ -74,7 +75,7 @@ const UserPreferences = ({
); );
return ( return (
<div className="p-2"> <>
<Section title={t('General')}> <Section title={t('General')}>
<div className="flex flex-row justify-center items-center w-72"> <div className="flex flex-row justify-center items-center w-72">
<Typography variant="subtitle" className="mr-5 text-right h-full"> <Typography variant="subtitle" className="mr-5 text-right h-full">
@ -122,7 +123,7 @@ const UserPreferences = ({
</Button> </Button>
</div> </div>
</div> </div>
</div> </>
); );
}; };

View File

@ -219,7 +219,7 @@ const DialogProvider = ({ children, service }) => {
isDragging && 'dragging', isDragging && 'dragging',
isDraggable && 'draggable' isDraggable && 'draggable'
)} )}
style={{ zIndex: '999', position: 'absolute' }} style={{ zIndex: '999', position: 'absolute', width: '350px' }}
onClick={() => _bringToFront(id)} onClick={() => _bringToFront(id)}
> >
<DialogContent {...dialog} {...contentProps} /> <DialogContent {...dialog} {...contentProps} />